Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- .nolist
- .include "m128def.inc"
- .include "hd44780.inc"
- .list
- .dseg
- .def temp = r16
- .def sys = r17
- .def counter = r18
- .def hours = r19
- .def minutes = r20
- .equ KEYPAD_PORT = PORTE
- .equ KEYPAD_DDR = DDRE
- .equ KEYPAD_PIN = PINE
- .equ FREQ = 8000000
- .equ LCD_PORT = PORTB
- .equ LCD_DDR = DDRB
- .equ LCD_PIN = PINB
- .equ LCD_D4 = 4
- .equ LCD_D5 = 5
- .equ LCD_D6 = 6
- .equ LCD_D7 = 7
- .equ LCD_RS = 0
- .equ LCD_EN = 2
- PressureSensorByte: // 2 байта под данные регистров АЦП вход ADC0
- .byte 2
- TemperatureSensorByte: // 2 байта под данные регистров АЦП вход ADC1
- .byte 2
- PressureSensor: // 4 байта под промежуточный расчет данных Вольтметра 1
- .byte 4
- TemperatureSensor: // 4 байта под промежуточный расчет данных Вольтметра 2
- .byte 4
- .cseg
- .org 0 ;reset interruption
- jmp Reset
- .org $0002
- jmp EXT_INT0 ; Keypad
- .org $0014
- jmp TIM2_OVF ; Timer2 Overflow Handler
- .org $0020
- jmp TIM0_OVF ; Timer0 Overflow Handler
- .org $002A // Адрес вектора прерывания по конвертации АЦП
- jmp ADC_Conv
- Reset:
- ldi temp, high(RAMEND)
- out sph, temp
- ldi temp, low(RAMEND)
- out spl, temp
- ldi temp, 0b11110111
- out DDRB, temp
- ldi temp, 0b00000000
- out KEYPAD_DDR, temp
- ldi temp, 0b00001111
- out KEYPAD_PORT, temp
- ldi temp, 0b00000011 ; rising edge for INT0
- sts EICRA, temp
- ldi temp, 0b00000001 ; enable INT0
- out EIMSK, temp
- rcall LCD_init
- ldi temp, 0b00000101
- out TCCR2, temp
- ldi temp, 0b00000010
- out TCCR0, temp
- ldi temp, 0b01000001
- out TIFR, temp
- out TIMSK, temp
- ldi temp, 0xf0
- out TCNT0, temp
- ldi temp, 0xf0
- out TCNT2, temp
- ldi temp, 0b01000000 // REFS = 01, ADLAR = 0, опорное напряжение выход AVCC, Мультиплексор
- out ADMUX, temp // на ADC0
- ldi temp, 0b11011110 // Разрешаем АЦП, запускаем конвертацию, и предделитель на 64
- out ADCSRA, temp // частота АЦП должна быть 50-200 кГц, при наших 8 Мгц, у нас будет 125 Кгц
- ldi hours, 0x17
- ldi minutes, 0x3b
- ldi counter, 0x00
- ldi temp, 0
- mov R15, temp
- sei
- start:
- nop
- rjmp start
- TIM2_OVF:
- cli
- push temp
- inc counter
- cpi counter, 0xff
- breq Timer_DEC
- Vix:
- ldi temp, 0xf0
- out TCNT2, temp
- pop temp
- sei
- reti
- Timer_DEC:
- dec minutes
- ldi counter, 0x00
- cpi minutes, 0x00
- breq Minutes_RESET
- rjmp Vix
- Hours_RESET:
- ldi hours, 0x17
- rjmp Vix
- Minutes_RESET:
- ldi minutes, 0x3b
- dec hours
- cpi hours, 0x00
- brlt Hours_RESET
- rjmp Vix
- TIM0_OVF:
- cli
- push temp
- push sys
- ldi temp, (128+0x63)
- rcall LCD_command
- mov temp, minutes
- call bin_to_dec ;temp - единицы / sys - десятки
- /*
- ldi zh, high(<STRING_NAME>*2)
- ldi zl, low(<STRING_NAME>*2)
- ldi sys, <STRING_LENGTH>
- loop:
- lpm temp, z+
- rcall LCD_data
- dec sys
- brne loop*/
- mov temp, hours
- mov R1, temp
- rcall fpconv8
- mov temp, R7
- rcall LCD_data
- mov temp, R8
- rcall LCD_data
- ldi temp, ':'
- rcall LCD_data
- mov temp, minutes
- mov R1, temp
- rcall fpconv8
- mov temp, R7
- rcall LCD_data
- mov temp, R8
- rcall LCD_data
- pop sys
- pop temp
- sei
- reti
- EXT_INT0:
- cli
- push temp
- ldi temp, (128+0x00)
- rcall LCD_command
- ReadKey:
- ;
- ldi temp, 0x0f
- andi temp, KEYPAD_PIN
- cpi temp, 0x00
- breq Put0
- ;
- ldi temp, 0x0f
- andi temp, KEYPAD_PIN
- cpi temp, 0x01
- breq Put1
- ;
- ldi temp, 0x0f
- andi temp, KEYPAD_PIN
- cpi temp, 0x02
- breq Put2
- ;
- ldi temp, 0x0f
- andi temp, KEYPAD_PIN
- cpi temp, 0x03
- breq Put3
- ;
- ldi temp, 0x0f
- andi temp, KEYPAD_PIN
- cpi temp, 0x04
- breq Put4
- ;
- ldi temp, 0x0f
- andi temp, KEYPAD_PIN
- cpi temp, 0x05
- breq Put5
- ;
- ldi temp, 0x0f
- andi temp, KEYPAD_PIN
- cpi temp, 0x06
- breq Put6
- ;
- ldi temp, 0x0f
- andi temp, KEYPAD_PIN
- cpi temp, 0x07
- breq Put7
- ;
- ldi temp, 0x0f
- andi temp, KEYPAD_PIN
- cpi temp, 0x08
- breq Put8
- ;
- ldi temp, 0x0f
- andi temp, KEYPAD_PIN
- cpi temp, 0x09
- breq Put9
- ;
- ldi temp, 0x0f
- andi temp, KEYPAD_PIN
- cpi temp, 0x0a
- breq PutA
- ;
- ldi temp, 0x0f
- andi temp, KEYPAD_PIN
- cpi temp, 0x0b
- breq PutB
- ;
- ldi temp, 0x0f
- andi temp, KEYPAD_PIN
- cpi temp, 0x0c
- breq PutC
- ;
- ldi temp, 0x0f
- andi temp, KEYPAD_PIN
- cpi temp, 0x0d
- breq PutD
- ;
- ldi temp, 0x0f
- andi temp, KEYPAD_PIN
- cpi temp, 0x0e
- breq PutE
- ;
- ldi temp, 0x0f
- andi temp, KEYPAD_PIN
- cpi temp, 0x0f
- breq PutF
- NoKey:
- jmp exit_interrupt
- Put0:
- ldi temp, '0'
- jmp print_key_interrupt
- Put1:
- ldi temp, '1'
- jmp print_key_interrupt
- Put2:
- ldi temp, '2'
- jmp print_key_interrupt
- Put3:
- ldi temp, '3'
- jmp print_key_interrupt
- Put4:
- ldi temp, '4'
- jmp print_key_interrupt
- Put5:
- ldi temp, '5'
- jmp print_key_interrupt
- Put6:
- ldi temp, '6'
- jmp print_key_interrupt
- Put7:
- ldi temp, '7'
- jmp print_key_interrupt
- Put8:
- ldi temp, '8'
- jmp print_key_interrupt
- Put9:
- ldi temp, '9'
- jmp print_key_interrupt
- PutA:
- ldi temp, 'A'
- jmp print_key_interrupt
- PutB:
- ldi temp, 'B'
- jmp print_key_interrupt
- PutC:
- ldi temp, 'C'
- jmp print_key_interrupt
- PutD:
- ldi temp, 'D'
- jmp print_key_interrupt
- PutE:
- ldi temp, 'E'
- jmp print_key_interrupt
- PutF:
- ldi temp, 'F'
- print_key_interrupt:
- rcall LCD_data
- exit_interrupt:
- pop temp
- sei
- reti
- LCD_init:
- sbi LCD_DDR, LCD_D4
- sbi LCD_DDR, LCD_D5
- sbi LCD_DDR, LCD_D6
- sbi LCD_DDR, LCD_D7
- sbi LCD_DDR, LCD_RS
- sbi LCD_DDR, LCD_EN
- cbi LCD_PORT, LCD_RS
- cbi LCD_PORT, LCD_EN
- ldi temp, 100
- rcall WaitMiliseconds
- ldi sys, 0b0000011
- LCD_init_loop:
- ldi temp, 0x03
- rcall LCD_write_nibble
- ldi temp, 5
- rcall WaitMiliseconds
- dec sys
- brne LCD_init_loop
- ldi temp, 0x02
- rcall LCD_write_nibble
- ldi temp, 1
- rcall WaitMiliseconds
- ldi temp, HD44780_FUNCTION_SET | HD44780_FONT5x7 | HD44780_TWO_LINE | HD44780_4_BIT
- rcall LCD_command
- ldi temp, HD44780_DISPLAY_ONOFF | HD44780_DISPLAY_OFF
- rcall LCD_command
- ldi temp, HD44780_CLEAR
- rcall LCD_command
- ldi temp, HD44780_ENTRY_MODE | HD44780_EM_SHIFT_CURSOR | HD44780_EM_INCREMENT
- rcall LCD_command
- ldi temp, HD44780_DISPLAY_ONOFF | HD44780_DISPLAY_ON | HD44780_CURSOR_OFF | HD44780_CURSOR_NOBLINK
- rcall LCD_command
- ret
- LCD_data:
- push zh
- push zl
- sbi LCD_PORT, LCD_RS
- push temp
- swap temp
- rcall LCD_write_nibble
- pop temp
- rcall LCD_write_nibble
- clr xh
- ldi xl, low(FREQ/80000)
- rcall Wait4xCycles
- pop zl
- pop zh
- ret
- LCD_command:
- cbi LCD_PORT, LCD_RS
- push temp
- swap temp
- rcall LCD_write_nibble
- pop temp
- rcall LCD_write_nibble
- ldi temp, 2
- rcall WaitMiliseconds
- ret
- LCD_write_nibble:
- sbi LCD_PORT, LCD_EN
- sbrs temp, 0
- cbi LCD_PORT, LCD_D4
- sbrc temp, 0
- sbi LCD_PORT, LCD_D4
- sbrs temp, 1
- cbi LCD_PORT, LCD_D5
- sbrc temp, 1
- sbi LCD_PORT, LCD_D5
- sbrs temp, 2
- cbi LCD_PORT, LCD_D6
- sbrc temp, 2
- sbi LCD_PORT, LCD_D6
- sbrs temp, 3
- cbi LCD_PORT, LCD_D7
- sbrc temp, 3
- sbi LCD_PORT, LCD_D7
- cbi LCD_PORT, LCD_EN
- ret
- WaitMiliseconds:
- push zh
- push zl
- push temp
- WaitMsLoop:
- ldi xh, high(FREQ/17777)
- ldi xl, low(FREQ/17777)
- rcall Wait4xCycles
- ldi xh, high(FREQ/17777)
- ldi xl, low(FREQ/17777)
- rcall Wait4xCycles
- dec temp
- brne WaitMsLoop
- pop temp
- pop zl
- pop zh
- ret
- Wait4xCycles:
- sbiw xh:xl, 1
- brne Wait4xCycles
- ret
- bin_to_dec:
- ldi sys, 0
- subi temp, 10
- inc sys
- brcc PC-2
- dec sys
- subi temp, -10
- ret
- fpconv8:
- rcall fpconv8a ; convert to ASCII string
- ldi temp,'.' ; set decimal char
- mov R6,temp
- ret ; all done
- fpconv8m:
- clr R4 ; set the multiplicant to 502
- ldi temp,$01
- mov R3,temp
- ldi temp,$F6
- mov R2,temp
- clr R7 ; clear the result
- clr R6
- clr R5
- fpconv8m1:
- or R1,R1 ; check if the number is all zeros
- brne fpconv8m2 ; still one's, go on convert
- ret ; ready, return back
- fpconv8m2:
- lsr R1 ; shift number to the right (div by 2)
- brcc fpconv8m3 ; if the lowest bit was 0, then skip adding
- add R5,R2 ; add the number in R6:R5:R4:R3 to the result
- adc R6,R3
- adc R7,R4
- fpconv8m3:
- lsl R2 ; multiply R4:R3:R2 by 2
- rol R3
- rol R4
- rjmp fpconv8m1
- fpconv8r:
- clr temp ; put zero to rmp
- lsl R5 ; rotate bit 7 to carry
- adc R6,temp ; add LSB with carry
- adc R7,temp ; add MSB with carry
- mov R2,R7 ; copy the value to R2:R1 (divide by 256)
- mov R1,R6
- ret
- fpconv8a:
- clr R4 ; Set the decimal divider value to 100
- ldi temp,100
- mov R3,temp
- rcall fpconv8d ; get ASCII digit by repeated subtraction
- mov R5,temp ; set hundreds string char
- ldi temp,10 ; Set the decimal divider value to 10
- mov R3,temp
- rcall fpconv8d ; get the next ASCII digit
- mov R7,temp ; set tens string char
- ldi temp,'0' ; convert the rest to an ASCII char
- add temp,R1
- mov R8,temp ; set ones string char
- ret
- fpconv8d:
- ldi temp,'0' ; start with decimal value 0
- fpconv8d1:
- cp R1,R3 ; Compare word with decimal divider value
- cpc R2,R4
- brcc fpconv8d2 ; Carry clear, subtract divider value
- ret ; done subtraction
- fpconv8d2:
- sub R1,R3 ; subtract divider value
- sbc R2,R4
- inc temp ; up one digit
- rjmp fpconv8d1 ; once again
- ADC_Conv: // Прерывание по конвертации АЦП
- cli // Запрещаем прерывания
- push temp // Запихиваем temp в стек
- push sys
- in temp, ADCL // Читаем младший, а потом старший регистр АЦП,
- push temp
- in temp, ADCH // при записи будет наоборот, не забывать
- push temp
- mov sys, R15
- cpi sys, 0 // Проверяем какой канал в прошлый раз запускали на конвертацию
- breq ADC_Conv0 // Переходим по метке, если 0
- ldi sys, 0 // иначе sys = 0
- mov R15, sys
- pop temp
- sts PressureSensorByte, temp // Сохраняем наши данные с АЦП в ОЗУ
- pop temp
- sts PressureSensorByte+1, temp
- ldi temp, 0b01000001 // Настраиваем мультиплексор на ADC1
- out ADMUX, temp
- ADC_Conv_exit:
- ldi temp, 0b11011110 // Повторяем запуск конвертации
- out ADCSRA, temp
- pop sys
- pop temp // Дергаем значение temp из стека
- sei // Разрешаем прерывания
- reti // Выход из прерывания
- ADC_Conv0:
- pop temp
- mov R14, temp
- ldi sys, 1 // sys = 1
- mov R15, sys
- pop temp
- sts TemperatureSensorByte, temp // Сохраняем наши данные с АЦП в ОЗУ
- pop temp
- sts TemperatureSensorByte+1, temp
- ldi temp, 0b01000000 // Настраиваем мультиплексор на ADC0
- out ADMUX, temp
- mov temp, r14
- push temp
- rjmp ADC_Conv_exit // Переходим
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement