; Accelerometer control program by devik@cdi.cz .equ DDRB = 0x17 .equ PORTB = 0x18 .equ PINB = 0x16 .equ GIMSK = 0x3b .equ SREG = 0x3f .equ MCUCR = 0x35 .equ ADCSR = 0x6 .equ ADMUX = 0x7 .equ ADCH = 0x5 .equ ADCL = 0x4 .equ TCNT0 = 0x32 .equ TCCR0 = 0x33 .equ TIMSK = 0x39 .equ TIFR = 0x38 ; Register usage: ; r0-r16 is TX fifo ; r16-r24 are global, r25-r31 local ; Global regs: .def data = r16 .def tmp = r17 .def adcerr = r18 .def sum = r19 .def cnt = r20 .def b4 = r21 reset: ldi tmp,0x2 ; pb1 out out DDRB,tmp out PORTB,tmp ldi tmp,0x8c out 0x31,tmp ; calibrate OSC .macro START_AD ; 8 cycle ldi cnt,@2 out ADMUX,cnt sbis ADCSR,4 ; was the ADC complete ? ldi adcerr,0x40 ; mark the error ldi cnt,0xd3 out ADCSR,cnt ; clear ADIF, start ADC in @0,ADCL in @1,ADCH .endmacro .macro BINS lsl @0 bst @2,@3 bld @0,@1 .endmacro .macro ASY_TX ; send 'data'; delay N cycle before further ldi cnt,@0 ; invocation of ASY_TX, N=7 for cnt=8 or ; ldi data,0x35 rcall bsend ; N=21 for cnt=7 .endmacro mloop: clr adcerr START_AD data,b4,1 BINS b4,0,data,7 mov sum,data ; 15 cycles here (with prev rjmp) rcall delay7 ; = 22 ASY_TX 7 ; = 139 1st START_AD data,tmp,2 lsl b4 lsl b4 or b4,tmp BINS b4,0,data,7 eor sum,data ; 15 cycles rcall delay7 ; = 22 ASY_TX 7 ; =139 2nd START_AD data,tmp,3 BINS tmp,0,data,7 eor sum,data ; 11 cycles rcall delay10 ; = 21 ASY_TX 7 ; = 138 3rd eor sum,b4 ; add b4 to the sum mov data,b4 swap data eor data,tmp ; add tmp2[0..2] to the sum andi data,7 eor sum,data ; xor with itself - we are done mov data,b4 ; 7 cycles or data,adcerr ; add error bit rcall delay7 rcall delay7 ; = 22 ASY_TX 8 ; = 153 b4 with zero MSB ! swap tmp ; 3rd sample result to high andi sum,15 or tmp,sum ; add 4bit checksum mov data,tmp ; = 4 rcall delay10 rcall delay10 ; = 24 sync rs232 here ASY_TX 7 ; = 141 tx the last one rjmp mloop ; total loop time is 139+139+138+153+141=710cycles ; kHz kSamples/s ; 1600 2253 ; 1610 2267 ; 1650 2323 delay10:nop delay9: nop nop delay7: ret ; sends byte 'data' using rs232 at PB1 (idle at 1) ; timing is 115kbit @ 1.6MHz = 14 cycles per bit ; call with ints disabled, changes cnt ; Timing: 6+14+cnt*14-1 = 19+14*cnt = 117(7) or 131(8) bsend: cbi PORTB,1 ; start bit nop rjmp _n0 _n0: rjmp nxbit ; =6 nxbit: rjmp _n1 ; =2 _n1: rjmp _n2 ; =4 _n2: rjmp _n3 ; =6 _n3: ror data ; =7 brcs onebit cbi PORTB,1 ; zero bit rjmp endbit onebit: sbi PORTB,1 ; one bit nop endbit: dec cnt ; =12 brne nxbit ; 14 cycle; 9 remains to stop ; = 1 rcall delay9 ; = 10 sbi PORTB,1 ; = 11 stop bit ret ; = 15 stop bit still active after ret (10 cycles)