<?xml version="1.0" encoding="UTF-8"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="pl-pl">
<link rel="self" type="application/atom+xml" href="https://forum.atnel.pl/feed.php?f=4&amp;t=13348&amp;mode" />

<title>ATNEL tech-forum</title>
<link href="https://forum.atnel.pl/index.php" />
<updated>2015-10-29T23:32:54+01:00</updated>

<author><name><![CDATA[ATNEL tech-forum]]></name></author>
<id>https://forum.atnel.pl/feed.php?f=4&amp;t=13348&amp;mode</id>
<entry>
<author><name><![CDATA[dakki]]></name></author>
<updated>2015-10-29T23:32:54+01:00</updated>
<published>2015-10-29T23:32:54+01:00</published>
<id>https://forum.atnel.pl/viewtopic.php?t=13348&amp;p=143771#p143771</id>
<link href="https://forum.atnel.pl/viewtopic.php?t=13348&amp;p=143771#p143771"/>
<title type="html"><![CDATA[Re: Sterownik bipolarnego silnika krokowego - program]]></title>

<content type="html" xml:base="https://forum.atnel.pl/viewtopic.php?t=13348&amp;p=143771#p143771"><![CDATA[
zamieniłem i dokładnie ten sam problem...nie wiem czy ten program można napisać dobrze.<br /><br />[syntax=c]#include &lt;avr/io.h&gt;<br />#include &lt;stdio.h&gt;<br />#include &lt;avr/interrupt.h&gt; <br />#include &lt;util/delay.h&gt;<br />#include &quot;HD44780.h&quot;<br />#include &quot;HD44780.c&quot;<br />#include &lt;avr/eeprom.h&gt;<br />#include &lt;avr/wdt.h&gt;<br /><br />volatile short step;                               //zmienne ulotne okreslajace wartosc kroku i poprzedniego kroku<br />volatile short adcwynik1,adcwynik2;<br />volatile short g;<br />volatile short standby;<br /><br />void timer0_init(void)                             //konfiguracja rejestru<br />{<br />TCCR0 = (1&lt;&lt;CS00) | (1&lt;&lt;CS02) ;             //preskaler FCPU / 1024<br />TIMSK = (1&lt;&lt;TOIE0);                            //odblokowanie przerwan<br />TCNT0 = 0;                                   //wartosc poczatkowa licznika<br />}<br /><br />void extint_init(void)<br />{<br />MCUCR |= (1&lt;&lt;ISC00) | (1&lt;&lt;ISC01);         //przerwanie INT0 wyzwalane zboczem narastajacym<br />GICR |= (1&lt;&lt;INT0);                        //odblokowanie przerwania zewnetrznego INT0<br />}<br /><br />void ADC_init(void)<br />{<br />ADMUX=_BV(REFS0)  ;                        //napiecie odniesienia refs0 -avcc both0 - aref both1 - 2.56v <br /><br />ADCSRA=_BV(ADEN) | _BV(ADSC)  | _BV(ADIE) | _BV(ADPS2) | _BV(ADPS1) | _BV(ADPS0); //wlaczanie przerwan adc, preskaler cpu/1024<br /><br />}<br /><br />int main(void){<br /><br /><br /><br />DDRC= 0b00;<br />PORTC = 0b00001000;<br />DDRB = 0xFF;                             //port B jako wyjscia<br />DDRD = 0b11110000;                    //cztery najstarsze bity portu D jako wyjscia, cztery najmlodsze wejscia<br /><br /><br />LCD_Initalize();                        //inicjalizacja lcd, przetwornika adc<br />ADC_init();<br />//timer0_init();<br />extint_init();<br />sei();                                //inicjacja timera i przerwania zewn, odblokowanie przerwan globalnych<br /><br /><br />   <br />PORTD=0x00;              //upewnienie sie, ze wszystkie wyjscia sa niewysterowane, wszystkie klucze zamkniete<br /><br /><br /><br />while(1){                     //sterowanie polkrokowe, sterowanie kluczami w zaleznosci od stanu zmiennej step <br />int z;<br />z++;<br />if(z==19000) LCD_Clear();<br />if(z==20000){<br />char adcbuf1&#91;10&#93;;                               //bufory wyswietlania<br />char adcbuf2&#91;10&#93;;<br /><br />itoa(adcwynik1/10,adcbuf1,10);                    //konwersja zmiennych na zmienne dziesietne do wyswietlenia<br /><br />itoa(adcwynik2/10,adcbuf2,10);<br /><br />LCD_GoTo(0,0);<br /><br />LCD_WriteText(adcbuf1);                         //wyswietlanie wartosci pradu obu cewek<br /><br />LCD_GoTo(0,1);<br /><br />LCD_WriteText(adcbuf2);<br /><br />z=0;<br />}<br /><br /><br />standby++; <br />if(standby&gt;=2000) PORTD=0b00000000;       //w przypadku gdy sygnal nie przychodzi przez 2000 cykli odlacz napiecie cewek<br /><br />}<br /><br /><br />}<br /><br />ISR(INT0_vect)                             //struktura przerwania zewnetrznego wyzwalanego sygnalem wejsciowym STEP<br /><br />{<br />if (!(PINC &amp; (1&lt;&lt;PC3))) step=step+1;   //inkrementacja zmiennej step jezeli wejscie DIR znajduje sie w logicznym 0<br />if ((PINC &amp; (1&lt;&lt;PC3))) step=step-1;    //dekrementacja zmiennej step jezeli wejscie DIR znajduje sie w logicznej 1<br /><br />if(step&gt;7) step=0;                     //granica gorna zmiennej step<br />if(step&lt;0) step=7;                     //granica dolna zmiennej step<br /><br /><br />if(step==0) PORTD=0b10000000;<br />if(step==1) PORTD=0b10100000;<br />if(step==2) PORTD=0b00100000;<br />if(step==3) PORTD=0b01100000;<br />if(step==4) PORTD=0b01000000;<br />if(step==5) PORTD=0b01010000;<br />if(step==6) PORTD=0b00010000;<br />if(step==7) PORTD=0b10010000;<br /><br />standby=0;                          //inkrementacja zmiennej standby<br /><br />}<br /><br />ISR(TIMER0_OVF_vect) //struktura przerwania wyzwalanego przepelnieniem timera 0 (raz na 1024 * (255-250) = 5120 cykli) <br />{<br /><br /><br /><br /><br /><br />TCNT0 = 0;                                  //ustawienie wartosci poczatkowej licznika<br /><br />}<br /><br /><br />ISR(ADC_vect)                                //przerwanie od zakonczenia konwersji przez przetwornik - wyniki gotowe<br />{<br />static long int t,u;<br /><br />g++;<br /><br /><br />if bit_is_clear(ADMUX,MUX0) t=ADC+t;               //jezeli ustawiony kanal 0 przypisz do zmiennej t<br />if bit_is_set(ADMUX,MUX0) u=ADC+u;                  //jezeli ustawiony kanal 0 przypisz do zmiennej u<br /><br />if(g==500){                                        //usrednianie 50 wynikow<br />adcwynik1=t/500;<br />adcwynik2=u/500;<br /><br />g=0;<br />t=0;<br />u=0;<br />}<br />ADMUX ^= _BV(MUX0);                               //zmiana kanalu z 0 na 1 lub z 1 na 0<br /><br />ADCSRA |= (1&lt;&lt;ADSC);                              //rozpocznij nastepna konwersje<br />}[/syntax]<p>Statystyki: Napisane przez <a href="https://forum.atnel.pl/memberlist.php?mode=viewprofile&amp;u=9768">dakki</a> — 29 paź 2015, o 23:32</p><hr />
]]></content>
</entry>
<entry>
<author><name><![CDATA[rskup]]></name></author>
<updated>2015-10-28T22:33:04+01:00</updated>
<published>2015-10-28T22:33:04+01:00</published>
<id>https://forum.atnel.pl/viewtopic.php?t=13348&amp;p=143600#p143600</id>
<link href="https://forum.atnel.pl/viewtopic.php?t=13348&amp;p=143600#p143600"/>
<title type="html"><![CDATA[Re: Sterownik bipolarnego silnika krokowego - program]]></title>

<content type="html" xml:base="https://forum.atnel.pl/viewtopic.php?t=13348&amp;p=143600#p143600"><![CDATA[
W przerwaniu <div class="codetitle"><b>Code:</b></div><div class="codecontent">ISR(TIMER0_OVF_vect) //struktura przerwania wyzwalanego przepelnieniem timera 0 (raz na 1024 * (255-250) = 5120 cykli)</div>masz<div class="codetitle"><b>Code:</b></div><div class="codecontent">if(z==9) LCD_Clear();<br />...<br />LCD_GoTo(0,0);<br />LCD_WriteText(adcbuf1);<br />LCD_GoTo(0,1);<br />LCD_WriteText(adcbuf2);</div><br /> <img src="https://forum.atnel.pl/images/smilies/icon_e_surprised.gif" alt=":o" title="Zdziwiony" /><br /><br />Chyba powinieneś poczytać o zasadach tworzenia kodu dla przerwań ... <br /><br />-- <br />Pozdrawiam,<br />Robert<p>Statystyki: Napisane przez <a href="https://forum.atnel.pl/memberlist.php?mode=viewprofile&amp;u=3427">rskup</a> — 28 paź 2015, o 22:33</p><hr />
]]></content>
</entry>
<entry>
<author><name><![CDATA[dakki]]></name></author>
<updated>2015-10-28T01:16:42+01:00</updated>
<published>2015-10-28T01:16:42+01:00</published>
<id>https://forum.atnel.pl/viewtopic.php?t=13348&amp;p=143526#p143526</id>
<link href="https://forum.atnel.pl/viewtopic.php?t=13348&amp;p=143526#p143526"/>
<title type="html"><![CDATA[Re: Sterownik bipolarnego silnika krokowego - program]]></title>

<content type="html" xml:base="https://forum.atnel.pl/viewtopic.php?t=13348&amp;p=143526#p143526"><![CDATA[
@edit: Mam jeszcze jeden problem - dodałem opcję pomiaru prądu na rezystorze między źródłami mosfetów a masą wzmocnionego przez op amp. Wszystko działa pięknie do wartości ~400, potem na wyświetlaczu pojawiają się krzaki i cały wyświetlacz się wysypuje. Skąd to ograniczenie ?<br /><br />[syntax=c]#include &lt;avr/io.h&gt;<br />#include &lt;stdio.h&gt;<br />#include &lt;avr/interrupt.h&gt; <br />#include &lt;util/delay.h&gt;<br />#include &quot;HD44780.h&quot;<br />#include &quot;HD44780.c&quot;<br />#include &lt;avr/eeprom.h&gt;<br />#include &lt;avr/wdt.h&gt;<br /><br />volatile short step;                               //zmienne ulotne okreslajace wartosc kroku i poprzedniego kroku<br />volatile short adcwynik1,adcwynik2;<br />volatile short g,z;<br />volatile short standby;<br /><br />void timer0_init(void)                             //konfiguracja rejestru<br />{<br />TCCR0 = (1&lt;&lt;CS00) | (1&lt;&lt;CS02) ;             //preskaler FCPU / 1024<br />TIMSK = (1&lt;&lt;TOIE0);                            //odblokowanie przerwan<br />TCNT0 = 0;                                   //wartosc poczatkowa licznika<br />}<br /><br />void extint_init(void)<br />{<br />MCUCR |= (1&lt;&lt;ISC00) | (1&lt;&lt;ISC01);         //przerwanie INT0 wyzwalane zboczem narastajacym<br />GICR |= (1&lt;&lt;INT0);                        //odblokowanie przerwania zewnetrznego INT0<br />}<br /><br />void ADC_init(void)<br />{<br />ADMUX=_BV(REFS0)  ;  //uref refs0 -avcc both0 - aref both1 - 2.56v <br /><br />ADCSRA=_BV(ADEN) | _BV(ADSC)  | _BV(ADIE) | _BV(ADPS2) | _BV(ADPS1) | _BV(ADPS0); <br /><br />}<br /><br />int main(void){<br /><br /><br />DDRC= 0b00;<br />PORTC = 0b00001000;<br />DDRB = 0xFF;                             //port B jako wyjscia<br />DDRD = 0b11110000;                    //cztery najstarsze bity portu D jako wyjscia, cztery najmlodsze wejscia<br /><br />LCD_Initalize();<br />ADC_init();<br />timer0_init();<br />extint_init();<br />sei();                                //inicjacja timera i przerwania zewn, odblokowanie przerwan globalnych<br /><br /><br />   <br />PORTD=0x00;              //upewnienie sie, ze wszystkie wyjscia sa niewysterowane, wszystkie klucze zamkniete<br /><br /><br /><br />while(1){                     //sterowanie polkrokowe, sterowanie kluczami w zaleznosci od stanu zmiennej step <br />if(( bit_is_set(PIND,PD7)) &amp; (bit_is_set(PIND,PD6))) break;<br />if(( bit_is_set(PIND,PD5)) &amp; (bit_is_set(PIND,PD4))) break;<br /><br />if(step==0) PORTD=0b10000000;<br />if(step==1) PORTD=0b10100000;<br />if(step==2) PORTD=0b00100000;<br />if(step==3) PORTD=0b01100000;<br />if(step==4) PORTD=0b01000000;<br />if(step==5) PORTD=0b01010000;<br />if(step==6) PORTD=0b00010000;<br />if(step==7) PORTD=0b10010000;<br />if(step==9) PORTD=0b00000000;<br /><br />standby++;<br />if(standby&gt;=2000) step=9;<br /><br />}<br /><br /><br />}<br /><br />ISR(INT0_vect)                             //struktura przerwania zewnetrznego wyzwalanego sygnalem wejsciowym STEP<br /><br />{<br />if (!(PINC &amp; (1&lt;&lt;PC3))) step=step+1;   //inkrementacja zmiennej step jezeli wejscie DIR znajduje sie w logicznym 0<br />if ((PINC &amp; (1&lt;&lt;PC3))) step=step-1;    //dekrementacja zmiennej step jezeli wejscie DIR znajduje sie w logicznej 1<br /><br />if(step&gt;7) step=0;                     //granica gorna zmiennej step<br />if(step&lt;0) step=7;                     //granica dolna zmiennej step<br />standby=0;<br />}<br /><br />ISR(TIMER0_OVF_vect) //struktura przerwania wyzwalanego przepelnieniem timera 0 (raz na 1024 * (255-250) = 5120 cykli) <br />{<br /><br /><br />z++;<br />if(z==9) LCD_Clear();<br />if(z==10){<br />char adcbuf1&#91;10&#93;;<br />char adcbuf2&#91;10&#93;;<br /><br />itoa(adcwynik1,adcbuf1,10);<br /><br />itoa(adcwynik2,adcbuf2,10);<br /><br />LCD_GoTo(0,0);<br /><br />LCD_WriteText(adcbuf1);<br /><br />LCD_GoTo(0,1);<br /><br />LCD_WriteText(adcbuf2);<br /><br />z=0;<br /><br /><br />}<br />TCNT0 = 0;                   //ustawienie wartosci poczatkowej licznika<br /><br />}<br /><br /><br />ISR(ADC_vect)<br />{<br />static long int t,u;<br /><br />g++;<br /><br /><br />if bit_is_clear(ADMUX,MUX0) t=ADC+t;<br />if bit_is_set(ADMUX,MUX0) u=ADC+u;<br /><br />if(g==50){<br />adcwynik1=t/50;<br />adcwynik2=u/50;<br /><br />g=0;<br />t=0;<br />u=0;<br />}<br />ADMUX ^= _BV(MUX0);<br /><br />ADCSRA |= (1&lt;&lt;ADSC);<br />}[/syntax]<p>Statystyki: Napisane przez <a href="https://forum.atnel.pl/memberlist.php?mode=viewprofile&amp;u=9768">dakki</a> — 28 paź 2015, o 01:16</p><hr />
]]></content>
</entry>
<entry>
<author><name><![CDATA[dakki]]></name></author>
<updated>2015-10-27T23:42:08+01:00</updated>
<published>2015-10-27T23:42:08+01:00</published>
<id>https://forum.atnel.pl/viewtopic.php?t=13348&amp;p=143523#p143523</id>
<link href="https://forum.atnel.pl/viewtopic.php?t=13348&amp;p=143523#p143523"/>
<title type="html"><![CDATA[Re: Sterownik bipolarnego silnika krokowego - program]]></title>

<content type="html" xml:base="https://forum.atnel.pl/viewtopic.php?t=13348&amp;p=143523#p143523"><![CDATA[
i to jest rozwiązanie <img src="https://forum.atnel.pl/images/smilies/icon_e_smile.gif" alt=":)" title="Szczęśliwy" /> Dzięki piękne !<p>Statystyki: Napisane przez <a href="https://forum.atnel.pl/memberlist.php?mode=viewprofile&amp;u=9768">dakki</a> — 27 paź 2015, o 23:42</p><hr />
]]></content>
</entry>
<entry>
<author><name><![CDATA[eMCe2]]></name></author>
<updated>2015-10-26T12:34:24+01:00</updated>
<published>2015-10-26T12:34:24+01:00</published>
<id>https://forum.atnel.pl/viewtopic.php?t=13348&amp;p=143395#p143395</id>
<link href="https://forum.atnel.pl/viewtopic.php?t=13348&amp;p=143395#p143395"/>
<title type="html"><![CDATA[Re: Sterownik bipolarnego silnika krokowego - program]]></title>

<content type="html" xml:base="https://forum.atnel.pl/viewtopic.php?t=13348&amp;p=143395#p143395"><![CDATA[
może w tym while() daj sobie jakąś zmienną volatille uint8_t timeout++; którą zerujesz sobie w obsłudze przerwania, a w tym while dodatkowy warunek że if(timeout&gt;=xx) step=9;<p>Statystyki: Napisane przez <a href="https://forum.atnel.pl/memberlist.php?mode=viewprofile&amp;u=1363">eMCe2</a> — 26 paź 2015, o 12:34</p><hr />
]]></content>
</entry>
<entry>
<author><name><![CDATA[dakki]]></name></author>
<updated>2015-10-25T17:22:39+01:00</updated>
<published>2015-10-25T17:22:39+01:00</published>
<id>https://forum.atnel.pl/viewtopic.php?t=13348&amp;p=143337#p143337</id>
<link href="https://forum.atnel.pl/viewtopic.php?t=13348&amp;p=143337#p143337"/>
<title type="html"><![CDATA[Sterownik bipolarnego silnika krokowego - program]]></title>

<content type="html" xml:base="https://forum.atnel.pl/viewtopic.php?t=13348&amp;p=143337#p143337"><![CDATA[
Witam,<br />Projektuje sterowniki do unipolarnego sterowania silnikami krokowymi do frezarki CNC sterowanej z programu Mach3 (step/dir). Ze względu na małą dostępność gotowych aplikacji dla prądów &gt;3A i nieograniczone możliwości zmian postanowiłem zastosować procesor ATMega8 i podwójny mostek H na mosfetach IRFPZ44. <br />Napisałem banalny program, który wydaje się działać bardzo dobrze, ale brakuje mi pomysłu na rozwiązanie jednego problemu. Mianowicie kiedy z komputera przychodzą impulsy step w jakiejś tam częstotliwości układ przełącza kombinacje tranzystorów zasilając odpowiednio cewki silnika. Problem powstaje gdy impulsy chwilowo nie dochodzą (dana oś nie jest w użyciu) - wtedy ostatnio użyta kombinacja cały czas zasila jedną lub dwie cewki silnika (sterowanie półkrokowe), przez uzwojenie płynie stały prąd o dużym natężeniu i silnik oraz tranzystory się grzeją, a nie ma takiej potrzeby gdyż śruby napędowe będą zamocowane na stałe. Nie wiem w jaki sposób najlepiej wykryć brak przychodzących impulsów wyzwalających przerwanie INT0.<br /><br />[syntax=c]#include &lt;avr/io.h&gt;<br />#include &lt;stdio.h&gt;<br />#include &lt;avr/interrupt.h&gt; <br />#include &lt;util/delay.h&gt;<br />#include &lt;avr/eeprom.h&gt;<br />#include &lt;avr/wdt.h&gt;<br /><br />volatile short step;                               //zmienne ulotne okreslajace wartosc kroku i poprzedniego kroku<br />volatile short adcwynik;<br />volatile short g;<br /><br />void timer0_init(void)                             //konfiguracja rejestru<br />{<br />TCCR0 = (1&lt;&lt;CS00) | (1&lt;&lt;CS02) ;             //preskaler FCPU / 1024<br />TIMSK = (1&lt;&lt;TOIE0);                            //odblokowanie przerwan<br />TCNT0 = 128;                                   //wartosc poczatkowa licznika<br />}<br /><br />void extint_init(void)<br />{<br />MCUCR |= (1&lt;&lt;ISC00) | (1&lt;&lt;ISC01);         //przerwanie INT0 wyzwalane zboczem narastajacym<br />GICR |= (1&lt;&lt;INT0);                        //odblokowanie przerwania zewnetrznego INT0<br />}<br /><br />void ADC_init(void)<br />{<br />ADMUX=_BV(REFS0)  ;<br /><br />ADCSRA=_BV(ADEN) | _BV(ADSC)  | _BV(ADIE) | _BV(ADPS2) | _BV(ADPS1) | _BV(ADPS0); <br /><br />}<br /><br />int main(void){<br /><br /><br />DDRC= 0b00;<br />PORTC = 0b00001000;<br />DDRB = 0xFF;                             //port B jako wyjscia<br />DDRD = 0b11110000;                    //cztery najstarsze bity portu D jako wyjscia, cztery najmlodsze wejscia<br /><br /><br />extint_init();<br />sei();                                //inicjacja timera i przerwania zewn, odblokowanie przerwan globalnych<br /><br />   <br />PORTD=0x00;              //upewnienie sie, ze wszystkie wyjscia sa niewysterowane, wszystkie klucze zamkniete<br /><br /><br /><br />while(1){                     //sterowanie polkrokowe, sterowanie kluczami w zaleznosci od stanu zmiennej step <br /><br />if(step==0) PORTD=0b10000000;<br />if(step==1) PORTD=0b10100000;<br />if(step==2) PORTD=0b00100000;<br />if(step==3) PORTD=0b01100000;<br />if(step==4) PORTD=0b01000000;<br />if(step==5) PORTD=0b01010000;<br />if(step==6) PORTD=0b00010000;<br />if(step==7) PORTD=0b10010000;<br />if(step==9) PORTD=0b00000000;<br /><br />}<br /><br /><br />}<br /><br />ISR(INT0_vect)                             //struktura przerwania zewnetrznego wyzwalanego sygnalem wejsciowym STEP<br /><br />{<br />if (!(PINC &amp; (1&lt;&lt;PC3))) step=step+1;   //inkrementacja zmiennej step jezeli wejscie DIR znajduje sie w logicznym 0<br />if ((PINC &amp; (1&lt;&lt;PC3))) step=step-1;    //dekrementacja zmiennej step jezeli wejscie DIR znajduje sie w logicznej 1<br /><br />if(step&gt;7) step=0;                     //granica gorna zmiennej step<br />if(step&lt;0) step=7;                     //granica dolna zmiennej step<br />}[/syntax]<br />Próbowałem od przepełnienia timera0 w stałym interwale czasowym generować następne przerwanie, które będzie sprawdzało stan pinu INT0 i jeżeli jest on niewysterowany przez okres dłuższy niż okres przy najmniejszej używanej częstotliwości silnika będzie wprowadzało zmienną step w krok nr 9 - wszystkie klucze niewysterowane, ale nie mogę dobrać częstotliwości wyzwalania tego przerwania tak, aby zawsze &quot;trafiało&quot; w ewentualne pojawienie się sygnału step na pinie INT0.<br />Badanie czy zmienna step pozostaje bez zmian przez jakiś okres czasu też wydaje się być nie najlepszym rozwiązaniem bo ona może się zmieniać ale akurat mogę trafić dwukrotnie przypadkowo na tą samą wartość. W jaki sposób można rozwiązać ten problem tak, aby rozwiązanie zawsze się sprawdzało bez względu na częstotliwość sygnału STEP ?<br /><br />Z góry dzięki za każde sugestie odnoście programu, pozdrawiam.<p>Statystyki: Napisane przez <a href="https://forum.atnel.pl/memberlist.php?mode=viewprofile&amp;u=9768">dakki</a> — 25 paź 2015, o 17:22</p><hr />
]]></content>
</entry>
</feed>