[Pic16F628] Multiplikation och division i asm av 24bits tal

PIC, AVR, Arduino, Raspberry Pi, Basic Stamp, PLC mm.
eriikh
Inlägg: 258
Blev medlem: 5 maj 2006, 10:52:15

[Pic16F628] Multiplikation och division i asm av 24bits tal

Inlägg av eriikh »

Jag håller på med en varvräknare som ska mäta varvtal mellan ~500-20000rpm med ca 50rpm upplösning. Jag vill ha 25fps uppdatering.
Jag har skrivit ett program som räknar mikrosekunder och sparar i 3 vaiabler, cnt_l cnt_m och cnt_h. De är konstruerade som ett 24bitars tal.
Varje ökning i räknaren betyder 1,4us.

Jaja, nu till problemet:
Jag vill 25ggr/s (timer-interrupt) räkna om detta tal till rpm. Frågan är då hur man multiplicerar resp. dividerar i assembler? Och särskilt när talen består av 24bitar...

Har ni någon idé?

/Erik
sodjan
EF Sponsor
Inlägg: 43251
Blev medlem: 10 maj 2005, 16:29:20
Ort: Söderköping

Inlägg av sodjan »

www.piclist.com (i "source code library") finns det massor av exempel.
Användarvisningsbild
bengt-re
EF Sponsor
Inlägg: 4829
Blev medlem: 4 april 2005, 16:18:59
Skype: bengt-re
Ort: Söder om söder
Kontakt:

Inlägg av bengt-re »

Jag tror att du tänker lite fel. Det finns vägar runt så du helt slipper flyttal. Att räkna på 1/t / 1/T är lite vanskligt då ett fel ger ett stort hopp. Är elektroniken fri från störningar kan det fungera bra, men ändå lite vansklig konstruktion. En ren klassisk gate räkna pulser ger dig för låg uppdateringsfrekvens.

En lösning där du ger varje puls en viss "bredd" motsvarande att vid max prf in ger dig 100% duty är ett enkelt sätt att helt slippa flyttal och ändå få ett linjärt förhållande på din "ut-variabel" där 0 är stillastående och FF är max konstruktionsvarvtal.

Visst kan du göra som du hade tänkt, men känns onödigt struligt att jobba med flyttal när det inte behövs.
sodjan
EF Sponsor
Inlägg: 43251
Blev medlem: 10 maj 2005, 16:29:20
Ort: Söderköping

Inlägg av sodjan »

Håller helt med bengt-re, jag tänkte det men han inte med att skriva det...

I de allra flesta fall går det med smart skalning av värden, justeringar
av intervall o.s.v, att runda av beräkningarna så att de t.ex alltid blir
med jämna 2-potenser, vilket gör alla multiplikationer och divisioner
till snabba shift-operationer. En eller flera vänstershift för multiplikation
med 2, 4, 8 o.s.v eller en eller flera högershift för division med 2, 4, 8 o.s.v.

Sen, om du går vidare med mult/div så är jag inte säker på att det måste
ske med flyttal, sannolikt klarar du dig lika bra med fixed-point, vilket
är mycket enklare och snabbare.

Multiply sidan på www.piclist.com : http://www.piclist.com/techref/microchi ... /index.htm

Divide sidan på www.piclist.com : http://www.piclist.com/techref/microchi ... /index.htm

Det finns i båda fallen flera exempel, speciellt för 24-bit, signed/unsigned o.s.v.
För den som är intresserad av matematisk analys och algoritmer finns det
mycket intressant teori där.
eriikh
Inlägg: 258
Blev medlem: 5 maj 2006, 10:52:15

Inlägg av eriikh »

Fördelen med metoden jag valt äratt jag har en nogrannhet på 1rpm upp till ca 10'000.
Problemet verkar vara 1/t divisionen, finns det ett enklare sätt att omvandla us till pulse/sec?

bengt-re: Ok, men hur får jag den logaritmiska kurvan som finns just nu att bli linjär utan att använda flyttal? Eller hur får man den linjär från början?


Sodjan: Låter riktigt smart, frågan är väl hur man genomför det praktiskt? Man får köra med kanske 32bitar så att man klarar av nogrannheten, men hur gör man en smart algoritm på hur man delar upp talen i 4 lämpliga "2-potens-byte".

/Erik
Användarvisningsbild
bengt-re
EF Sponsor
Inlägg: 4829
Blev medlem: 4 april 2005, 16:18:59
Skype: bengt-re
Ort: Söder om söder
Kontakt:

Inlägg av bengt-re »

Det är det som är finessen - kurvan ÄR linjär. Vi tar ett exempel med enkla värden för att visa principen.

Säg max prf in på 500Hz
Sätt varje count till 2ms
Du har nu en "pwm" signal med varierande prf, men där dutycykeln är linjär emot varvtalet.
Prf in 250 Hz och du har duty 50% (250x2/1000)
Prf in 100 Hz och du har duty 20% (100x2/1000)

Det fina är att du inte är beroende av någon tigger gate utan kan LP-filtrera signalen efter önskat beteende med den tidskonstant du önskar. Metoden används/användes ofta förr i analoga varvräknare, men fungerar bra som princip även i uC världen.

Säger inte att du inte kan räkna med flyttal om du vill, men flyttal är jobbiga, tar mycket resurser och är långsamma - så oftast bättre att räkna sig runt flyttal om det går.

1Hz noggranheten förutsätter att du lyckas mäta pulserna perfekt och att givaren inte har något gitter. 50-100 rpm när måste väl ändå vara tillräckligt så länge vi inte pratar lågvarviga marindieslar... Mätupplösningen är i praktiken ändå ungefär 250 rpm när på en analog visare...
eriikh
Inlägg: 258
Blev medlem: 5 maj 2006, 10:52:15

Inlägg av eriikh »

Men jag förstår inte.
Jag får mina data i tex 2us takter.
då skiljer det väldigt mycket mer mellan 1 och 2 än det gör mellan 254 och 255?

Har tänkt mycket nu.
Kom fram tillen lösning då jag inte behöver några flyttal men ändå kan få en hög upplösning.
Lösningen blir inte helt exakt, men det löser sig ändå då applikationen inte riktigt kräver det.
Det hät kom jag fram till:

Kod: Markera allt

  2^19
---------
 cnt+2^5
Det enda krångliga är då att använda division, men det löser sig nog efter lite letande på piclist.

Synpunkter?
Skriv svar