Fórum témák

» Több friss téma
Fórum » PIC programozása C nyelven, C-Compiler
Lapozás: OK   120 / 153
(#) killbill válasza zenetom hozzászólására (») Jan 31, 2016 /
 
Idézet:
„Bár akkor minek a C ?”
Semmi osszefugges a ketto kozott. Az egyik egy eszkoz, a masik egy programozasi nyelv.
(#) zenetom válasza killbill hozzászólására (») Jan 31, 2016 /
 
Ok, félreérthetően írtam, meg hát attól még hogy a Microchip rosszul írta meg a függvény(eke)t, attól nem a C a rossz nyelv.
(#) cua válasza zenetom hozzászólására (») Feb 1, 2016 /
 
Nem gondolom, hogy egy flag torlese automatikusan kell hogy kovesse a kiolvasast, nyelvtol fuggetlenul
(#) ativagyok hozzászólása Feb 2, 2016 /
 
Sziasztok!
Elakadtam egy projekt legelején egy látszólag nagyon egyszerű feladatnál:
A GP2 lábon érkező felfutó él megszakítást okozna, viszont az alábbi kódrészlet nem csinál semmit.
Ha a GP0_bit = ~GP0_bit; sort áthelyezem a megszakításba közvetlenül, akkor helyesen működik, viszont -ha nem tévedek-, oda célszerű a lehető legkevesebb utasítást írni.
PIC12F615, MCLR Disabled, INTOSCIO 8MHz.
Köszönöm előre is.

  1. int adcresult=0, flag=0;
  2. unsigned short  timer=0, cnt;
  3.  
  4. void interrupt() {
  5.   if(INTF_bit){
  6.  
  7.    flag = 1;
  8.    INTF_bit = 0;
  9.   }
  10. }
  11.  
  12. void main() {
  13. ANSEL = 0x02;
  14. CMCON0 = 0;
  15. CMCON1 = 0;
  16. TRISIO5_bit = 1; //
  17. TRISIO0_bit = 0; //
  18. TRISIO2_bit = 1; //
  19. TRISIO1_bit = 1; //
  20. TRISIO3_bit = 1;
  21.  
  22. // Timer1 CFG:
  23. T1CON = 00000111;
  24. T1OSCEN_bit = 0;
  25.  
  26. PIE1 = 1;
  27. PEIE_bit = 1;
  28. GIE_bit = 1;
  29. TMR1IE_bit = 1;
  30. TMR1IF_bit = 0;
  31. INTE_bit = 1; // External interrupt GP2 pin
  32. INTEDG_bit = 1; // INT on rising edge
  33. do{
  34.  if(flag){
  35.   GP0_bit = ~GP0_bit;
  36.   flag = 0;
  37.  }
  38. }while(1);
  39. }
A hozzászólás módosítva: Feb 2, 2016
(#) benjami válasza ativagyok hozzászólására (») Feb 2, 2016 / 2
 
Kb. hetente előkerül, hogy azok a változók amiket megszakításból és a főprogramból is egyaránt felhasználsz, volatile-nek kellene lennie. Tehát a flagnak volatile char-nak kellene lennie (char is elég, felesleges a 16bites int, még egy bit is elegendő lenne).
(#) ativagyok válasza benjami hozzászólására (») Feb 12, 2016 /
 
Köszönöm a segítséget

Van egy másik kérdésem encoderek kezeléséval kapcsolatban:
Eddig így olvastam be az állapotokat:
  1. new_xmov = (PORTF & 0xC0);      
  2.    if(new_xmov != last_xmov)

Ha az encoder két lábát külön portra teszem, és az alábbi módon olvasom be, annak van valamilyen hátránya?

  1. new_xmov = ((PORTF.F0 << 1) | PORTE.F7);                            
  2.    if(new_xmov != last_xmov)
(#) killbill válasza ativagyok hozzászólására (») Feb 12, 2016 / 1
 
Milyen hatranyra gondolsz? Jol fog mukodni, csak pár assembly utasitassal hosszabb lesz a kod, mintha egy porton lennenek egymas mellett az enkoder jelek.
(#) don_peter hozzászólása Feb 13, 2016 /
 
Uraim, lenne egy változóm amiben egy számolás eredményét kellene tárolnom.
A kérdésem az, hogy ezt hogy tudom megoldani,
  1. eredmeny = (5000/1024)*(0-514)*55;

...úgy hogy ha az eredménye 0 vagy negatív szám lenne akkor 0 értéket adjon vissza?
Most az eredménye 17992 unsigned, signed int típusokkal.

Ha az 514 előtti szám kisebb mint az amiből azt ki kell vonni akkor az eredményem 0-nak kellene lennie.

Van erre jó típus módosító?
Vagy több sorban tudom csak megvizsgálni az eredményt és aszerint eldönteni a folytatást?
(#) don_peter válasza don_peter hozzászólására (») Feb 13, 2016 /
 
Most egyelőre így oldottam meg, de ha van jobb megoldás azt szívesen veszem:
  1. eredmeny = (x-514)>0 ? (5000/1024)*(x-514)*55 : 0;
A hozzászólás módosítva: Feb 13, 2016
(#) Kovidivi válasza don_peter hozzászólására (») Feb 14, 2016 /
 
Az 5000\1024 értéke egész számok esetén 4 lesz...
(#) don_peter válasza Kovidivi hozzászólására (») Feb 15, 2016 /
 
Az nem baj, a számolás során lebegőpontosként kezelem, a végeredményt pedig egészként.
Ez itt most nem látszik.
A hozzászólás módosítva: Feb 15, 2016
(#) Kovidivi válasza don_peter hozzászólására (») Feb 15, 2016 /
 
Akkor 5000.0/1024.0-t kellett volna írnod, vagy ((float)5000)/((float)1024)-et.
(#) ativagyok válasza killbill hozzászólására (») Feb 15, 2016 /
 
Szia!
Igen, ehhez hasonló hátrányra gondoltam, köszönöm a válaszod.
Ezt gondolom a gyakorlatban nem igazán lehet észre venni.
(#) don_peter válasza Kovidivi hozzászólására (») Feb 18, 2016 /
 
Igen így volt, de nem ez volt a baj, hanem a végeredményt előjel nélkül kezeltem ezért volt gondom. Most már megoldódott ez a probléma.. Köszi azért.
(#) c27 hozzászólása Feb 25, 2016 /
 
Sziasztok egy kis segítséget szeretnék kérni.
Azt szeretném, ha az rc0-ra kötött nyomógomb megnyomásakor az adc beolvasná és konvertálná az an0 és an1 lévő potik helyzetét. A fordító hibát ír ki, de nem tudom mi a hiba.
(#) don_peter hozzászólása Feb 26, 2016 /
 
Srácok, szeretném ezt egyszerűbb alakra hozni mert szerintem kicsit lassú a struktúrás megoldásom:
  1. struktura.data = adat;
  2. D0 = struktura.D0;
  3. D1 = struktura.D1;
  4. D2 = struktura.D2;
  5. D3 = struktura.D3;
  6. D4 = struktura.D4;
  7. D5 = struktura.D5;
  8. D6 = struktura.D6;
  9. D7 = struktura.D7;

Valami olyasmire gondolok, hogy a biteket tologatnám jobbra és így adnám át egyesével az biteket D?-nek.
Valami ilyesmire:
  1. D0 = adat>>1&1; //persze ez nem jó, de emlékeim szerint valami hasonló lehet a megoldás

Előre is köszi.
(#) don_peter válasza don_peter hozzászólására (») Feb 26, 2016 /
 
Köszönöm, az előzőre az volt a helyes válasz amit meg is adtam
Sajnos nem az volt a lassú, hanem a stiftregiszter meghajtásom.
Kérnék segítséget illetve tanácsot, hogy miképpen tudom gyorsítani a shift regiszter meghajtást.
Most ilyen:
  1. SR_CS=0;                        // Engedélyezés
  2.         for(i=0; i<8; i++){     // Léptetünk
  3.                 if((struktura.addr>>7-i)&1==1){
  4.                         SR_ADAT=1;      // Adat
  5.                         SR_CLK=1;       // Órajel
  6.                         SR_CLK=0;      
  7.                 }else{
  8.                         SR_ADAT=0;      // Nincs adat
  9.                         SR_CLK=1;       // Órajel
  10.                         SR_CLK=0;
  11.                 }
  12.         }
  13.         SR_CS=1;                        //Tíltás
  14.         SR_ADAT=0;
  15.         SR_CLK=0;

A módszer jól működik, de több 100 ezres címzésnél már gyalázatosan lassú.
Hogy írhatnám meg ezt úgy, hogy akár drasztikusan is javítson a lefutáson?
Előre is köszönöm.
(#) Wezuv válasza don_peter hozzászólására (») Feb 26, 2016 /
 
Milyen PIC, milyen sebeséggel hajtod?
(#) don_peter válasza Wezuv hozzászólására (») Feb 26, 2016 /
 
18F442 @40MHz
C18-ban íródik a program.
3db shift regiszter van egymás után a linkelt kód az elsőt vezérli, 24bit-et kell kiléptetni.
A többi annyiban különbözik, hogy a ChipSelect elnevezése után számmal van jelölve: SR_CS, SR_CS2, SR_CS3.
Áhh linkelem az egészet, hogy lehessen látni a problémát:
  1. // Shift regiszteres (24bit)
  2. void Shift(Stukt struktura){
  3.         unsigned char i;
  4.         // Felső 8bit
  5.         SR_CS=0;                        // Engedélyezés
  6.         for(i=0; i<8; i++){     // Léptetünk
  7.                 if((addrADAT.addr>>7-i)&1==1){
  8.                         SR_ADAT=1;      // Adat
  9.                         SR_CLK=1;       // Órajel
  10.                         SR_CLK=0;      
  11.                 }else{
  12.                         SR_ADAT=0;      // Nincs adat
  13.                         SR_CLK=1;       // Órajel
  14.                         SR_CLK=0;
  15.                 }
  16.         }
  17.         SR_CS=1;                        //Tíltás
  18.         SR_ADAT=0;
  19.         SR_CLK=0;
  20.        
  21.         // Alsó 8bit
  22.         SR_CS2=0;                       // Engedélyezés
  23.         for(i=0; i<8; i++){     // Léptetünk
  24.                 if((struktura.addr>>15-i)&1==1){
  25.                         SR_ADAT=1;      // Adat
  26.                         SR_CLK=1;       // Órajel
  27.                         SR_CLK=0;      
  28.                 }else{
  29.                         SR_ADAT=0;      // Nincs adat
  30.                         SR_CLK=1;       // Órajel
  31.                         SR_CLK=0;
  32.                 }
  33.         }
  34.         SR_CS2=1;                       //Tíltás
  35.         SR_ADAT=0;
  36.         SR_CLK=0;
  37.        
  38.         // Legalsó 8bit
  39.         SR_CS3=0;                       // Engedélyezés
  40.         for(i=0; i<8; i++){     // Léptetünk
  41.                 if((struktura.addr>>23-i)&1==1){
  42.                         SR_ADAT=1;      // Adat
  43.                         SR_CLK=1;       // Órajel
  44.                         SR_CLK=0;      
  45.                 }else{
  46.                         SR_ADAT=0;      // Nincs adat
  47.                         SR_CLK=1;       // Órajel
  48.                         SR_CLK=0;
  49.                 }
  50.         }
  51.         SR_CS3=1;                       //Tíltás
  52.         SR_ADAT=0;
  53.         SR_CLK=0;
  54. }

Tehát ezt kellene kicsit hatékonyabbá tennem.
Mivel jelenleg fix a bekötés, nem állnék át SPI meghajtásra.

ui: Adat és órajel közös vezetéken fut.
A hozzászólás módosítva: Feb 26, 2016
(#) Hp41C válasza don_peter hozzászólására (») Feb 26, 2016 / 1
 
  1. if((struktura.addr>>23-i)&1==1){

helyett
  1. if(((struktura.addr>>(23-i))&1)==1){
A hozzászólás módosítva: Feb 26, 2016
(#) don_peter válasza Hp41C hozzászólására (») Feb 26, 2016 /
 
Ez mennyiben fog gyorsítani a lefutáson?
A program működik rendben, csak nagyon lassú ha már 100e-s címzésről beszélünk.
260e címzést 6.5perc alatt léptet végig.

ui: amúgy köszi, és javítom.
A hozzászólás módosítva: Feb 26, 2016
(#) Istvanpisti válasza don_peter hozzászólására (») Feb 26, 2016 / 2
 
  1. mask=0x80;     
  2. for(i=0; i< 8; i++)
  3. {
  4. ...
  5.    if(addrADAT.addr & mask) SR_ADAT=1;  else SR_ADAT=0
  6.    SR_CLK=1;       // Órajel  
  7.    SR_CLK=0;
  8.    mask>>=1;
  9. }
  10.  
  11. vagy
  12. for(i = 0x80; i; i>>=1)
  13. {
  14.   if(addrADAT.addr & i) SR_ADAT=1;  else SR_ADAT=0
  15.   SR_CLK=1;       // Órajel
  16.   SR_CLK=0;
  17. }
(#) killbill válasza don_peter hozzászólására (») Feb 26, 2016 / 1
 
Valoszinuleg attol ennyire lassu, mert minden egyes bitnel egy 32 bites szamot shiftelgetsz. Sokkal jobban jarnal, ha harom darab 8 bites szamra bontanad az adatot es azt is ugy shiftelned ki, hogy mindig csak egy bitet mozditasz rajta.

  1. void addr_out(uint32_t addr)
  2. {
  3.   shift_out(addr >> 16);
  4.   shift_out(addr >> 8);
  5.   shift_out(addr);
  6. }
  7.  
  8. static void shift_out(unsigned char data)
  9. {
  10. unsigned char mask;
  11.  
  12.    for(mask = 0x80; mask; mask >>= 1){
  13.      SR_DATA = !!(data & mask);
  14.      SR_CLK = 1;
  15.      SR_CLK = 0;
  16.   }
  17. }
  18.  
  19. static void shift_out(unsigned char d)
  20. {
  21. unsigned char i;
  22.  
  23.  for(i = 8; i; --i, d >>= 1){
  24.      SR_DATA = !!(d & 0x80);
  25.      SR_CLK = 1;
  26.      SR_CLK = 0;
  27.   }
  28. }

Hogy a ket shift_out() fuggvenybol melyik a gyorsabb, azt ki kell probalni.
A hozzászólás módosítva: Feb 26, 2016
(#) don_peter válasza killbill hozzászólására (») Feb 26, 2016 /
 
Köszönöm, kipróbálom milyen eredményt hoznak.
(#) killbill válasza killbill hozzászólására (») Feb 26, 2016 /
 
A 23. sor hibas! Helyesen:
  1. for(i = 8; i; --i, d <<= 1){
A hozzászólás módosítva: Feb 26, 2016
(#) don_peter válasza killbill hozzászólására (») Feb 26, 2016 /
 
Igen közben erre én is rájöttem.
Köszi.
Tesztek:
1-es verzió gyorsabb 1 másodperccel: 7s és 2103 byte/s
2-es verzió: 8s és 1872 byte/s

A végeredmény az, hogy 3szor hatékonyabb ez a megoldás mint az enyém.
Köszönöm.
(#) killbill válasza don_peter hozzászólására (») Feb 26, 2016 / 1
 
Nincs mit. Ha nem eleg okos a C forditod, akkor lehet, hogy meg egy kicsit gyorsitana rajta, ha igy irnad:

  1. if(data & mask)
  2.   SR_DATA = 1;
  3. else
  4.  SR_DATA = 0;
(#) don_peter válasza killbill hozzászólására (») Feb 26, 2016 /
 
Ki fogom próbálni, bár szerintem ezt már nehéz lesz lemérni.
Még azzal gyorsítottam rajta 3 másodpercet, hogy a 3. kiléptetést csak akkor végeztetem el, ha cím nagyobb mint 65535.
Még ezt az időt is elvileg meg fogom tudni felezni, mivel most byte-onként léptetek, de tud a cucc 16bit-et, így annak használásával feleződni fog az idő.
Köszi még egyszer, most tesztelem ezerrel.
(#) benjami válasza don_peter hozzászólására (») Feb 26, 2016 / 1
 
1. Bár kicsit terjedelmesebb lesz a program én nem raknám ciklusba a 24 bit küldését (a ciklus is sokat lassít).
2. olyan bitmezős struktúrát csinálnék, hogy mind a 24 bithez hozzáférjek.
3. ha nem szempont hogy az adatláb megbillen, akkor fixen kinulláznám az SR_ADAT -ot és csak akkor állítanám vissza 1-be ha szükséges
  1. SR_ADAT=0;
  2. if(addrADAT.addr.bit23) SR_ADAT=1;
  3. SR_CLK=1;
  4. SR_CLK=0;
  5. SR_ADAT=0;
  6. if(addrADAT.addr.bit22) SR_ADAT=1;
  7. SR_CLK=1;
  8. SR_CLK=0;
  9. ...
(#) don_peter válasza benjami hozzászólására (») Feb 26, 2016 /
 
Véleményed szerint ez mennyiben gyorsítana még a programon?
1-2%-ot vagy többet?

ui: a struktúra felépítése lehetővé teszi, hogy minden bit-et külön tudjak kezelni.
A hozzászólás módosítva: Feb 26, 2016
Következő: »»   120 / 153
Bejelentkezés

Belépés

Hirdetés
XDT.hu
Az oldalon sütiket használunk a helyes működéshez. Bővebb információt az adatvédelmi szabályzatban olvashatsz. Megértettem