Till mitt datorkylningsprojekt (vars problem-trådar snart fyller hela forumet) ska jag styra fläktar med PWM från en 12F675. En av fläktarna är lite svårstartad vid låga dutycycles. Därför tänkte jag ge den en liten putt i början av koden. Därför lade jag till dessa rader i init-proceduren:
PWM_ut = 1
LED0 = 1
LED1 = 1
LED2 = 1
delay_ms(100)
LED0 = 0
LED1 = 0
LED2 = 0
PWM_ut är pinnen som går till fläkten (via en transistor.)
LED0, LED1 och LED2 är pinnar som går till tre lysdioder som visar hur varm datorns CPU är.
När jag lagt till raderna ovan så märkte jag något skumt:
Lysdioderna tänds (som väntat). Sedan ser man värdet på hur varm datorn är (detta visas binärt), sedan tänds lysdioderna igen och så håller det på och blinkar.
Har även märkt att delayet inte alls ser ut att vara 100ms. Snarare ca en halv sekund.
Jag kör med intern oscillator på 4MHz. (FOSC2:FOSC0 satt till 100 som ger "INTOSC oscillator: I/O function on GP4/OSC2/CLKOUT pin, I/O function on GP5/OSC1/CLKIN".) I MikroBasic sätter man detta genom att markera INTRC_OSC_NOCLKOUT under Project -> Edit -> Device Flags. Jag har läst databladet noga och inte funnit något mer som ska konfigureras för att få 4MHz. I Mikrobasic har jag ställt in 4MHz så att hex-filen som byggs motsvarar rätt tider.
Vad sägs om en titt på koden?

Kod: Markera allt
'GPIO.0 = LED 0 visar bit0
'GPIO.1 = LED 1 visar bit1
'GPIO.2 = LED 2 visar bit2
'GPIO.4 = Från TempKoll (Analog in. Det blir AN3)
'GPIO.5 = PWM ut
symbol LED0 = GPIO.0 ' Visar bit0
symbol LED1 = GPIO.1 ' Visar bit1
symbol LED2 = GPIO.2 ' Visar bit2
symbol PWM_UT = GPIO.5 ' PWM-pulsen (utgång)
dim ntc_lo as byte ' Låga delen av NTC-värdet
dim ntc_hi as byte ' Höga delen av NTC-värdet
dim ntc as word 'Hela NTC-värdet (10bit används) Förväntar spänning mellan 2.3V och 4.4V
sub procedure Init
TRISIO = %00011000 ' Utgångar överallt, förutom GP4 (AN3) som är ingång. GP3 är alltid ingång.
IOC = %00000000 ' Interrupt on change - Disabled
CMCON.CM2 = 1 ' Comparator Off
CMCON.CM1 = 1 ' Comparator Off
CMCON.CM0 = 1 ' Comparator Off
VRCON = 0 ' VoltRef (Comparator) off
T1CON.TMR1ON = 0 ' Stoppar timern
WPU = %00000000 'Weak Pullup - Disabled
'AD-omvandling initiering
ADCON0.ADFM = 1 ' Högerjusterad
ADCON0.VCFG = 0 ' VDD som referens
ADCON0.CHS1 = 1 ' AN3 som ingång
ADCON0.CHS0 = 1 ' AN3 som ingång
ADCON0.ADON = 1 ' AD-modulen är igång
delay_ms(10)
ADCON0.1 = 1 ' GO/DONE - Sätt den här hög för att starta en AD-omvandling
ANSEL.ADCS2 = 1 ' FOSC/16
ANSEL.ADCS1 = 0 ' FOSC/16
ANSEL.ADCS0 = 1 ' FOSC/16
ANSEL.ANS3 = 1 ' AN3 som analog in
ANSEL.ANS2 = 0 ' Digital I/O
ANSEL.ANS1 = 0 ' Digital I/O
ANSEL.ANS0 = 0 ' Digital I/O
'Interrupt initiering
INTCON.GIE = 1 ' Global interrupt enable
INTCON.PEIE = 1 ' Peripheral Interrupt Enable (AD t.ex)
PIE1.ADIE = 1 ' AD-omvandlare ger interrupt
PIR1.ADIF = 0 ' Clearat interruptet
ntc = 0 ' Nollställer NTC-värdet
'Putta igång fläktarna
PWM_ut = 1
LED0 = 1
LED1 = 1
LED2 = 1
delay_ms(100)
LED0 = 0
LED1 = 0
LED2 = 0
delay_ms(100)
end sub
sub procedure interrupt
'Ett interrupt har hänt:
if TestBit(PIR1, ADIF) = 1 then
ClearBit(PIR1, ADIF)
'Läsa av AD-omvandlaren:
ntc_lo = ADRESL
ntc_hi = ADRESH
ntc = (word(ntc_hi << 8)) OR ntc_lo
end if
SetBit(ADCON0, ADON) 'Gör klart för en ny omvandling
SetBit(ADCON0, 1) 'GO/DONE
end sub
main:
Init
while true
--Har rensat här i sann debugg-anda :-)
wend
end.
Hoppas någon orkar kika på detta.
