# HG changeset patch # User John Tsiombikas # Date 1359359535 -7200 # Node ID 40b150fedb0ef0969abe30d317c4e21f929f92bd # Parent d26d73ef2db7394fda0904d5dd40c6cca0cd6bb3 foo diff -r d26d73ef2db7 -r 40b150fedb0e voltmeter.c --- a/voltmeter.c Sun Jan 27 10:11:40 2013 +0200 +++ b/voltmeter.c Mon Jan 28 09:52:15 2013 +0200 @@ -3,6 +3,7 @@ #include #include +#include #include /* hardware setup @@ -12,6 +13,7 @@ * bit 1: R/W * bit 2: E */ +#define LCD_BUS_WIDTH 8 #define BIT_RS 3 #define BIT_RW 4 @@ -57,10 +59,23 @@ FILE stream_lcd = FDEV_SETUP_STREAM(lcd_stream_write, NULL, _FDEV_SETUP_WRITE); +int bn_pressed; +unsigned char foo; + int main(void) { stdout = stderr = &stream_lcd; + /* port B[0] out -> backlight + * port B[1] in <- backlight switch + */ + DDRB = 1; + PORTB = 0xfe; /* enable all pullups, leave bit0 -> 0 (backlight) */ + /* enable PIN B1 interrupt */ + PCMSK0 = 2; + PCICR = 1; + sei(); /* enable interrupts */ + DDRC = 0xfe; PORTC = 0; /* disable pullups */ @@ -74,18 +89,36 @@ long val = read_adc(); double ref = 1.08 * 1.47 / 0.47; double voltage = ref * (double)val / (double)1024; + lcd_clear(); if(val == 1023) { - printf("*** RANGE *** "); + printf("*** RANGE ***"); } else { - printf("%.2f volts ", voltage); + printf("%.2f volts", voltage); + } + + /* check if the backlight button was pressed */ + if(bn_pressed & 1) { + if(PORTB & 1) { + PORTB &= 0xfe; + } else { + PORTB |= 1; + } + bn_pressed = 0; } _delay_ms(500); } return 0; } + +ISR(PCINT0_vect) { + if((PINB & 2) == 0) { + bn_pressed = 1; + } +} + void setup_adc(void) { /* disable digital input buffer on ADC0 pin */ @@ -114,10 +147,39 @@ return low | ((long)ADCH << 8); } +void lcd_write_byte(unsigned char byte) +{ +#if LCD_BUS_WIDTH == 8 + DDRD = 0xff; + PORTD = byte; +#else + DDRD = (DDRD & 0xf0) | 0xf; + + PORTD = (PORTD & 0xf0) | ((byte >> 4) & 0xf); + PORTD = (PORTD & 0xf0) | (byte & 0xf); +#endif +} + +unsigned char lcd_read_byte(void) +{ +#if LCD_BUS_WIDTH == 8 + DDRD = 0; + PORTD = 0; /* disable pull-ups */ + + return PIND; +#else + unsigned char byte; + + DDRD = DDRD & 0xf0; + PORTD &= 0xf0; /* disable pull-ups */ + + byte = (PIND & 0xf) << 4; + return byte | (PIND & 0xf); +#endif +} + void lcd_init(void) { - DDRD = 0x0f; /* port d[0, 3] -> output */ - /* make sure the display has time to boot up */ _delay_ms(20); @@ -125,55 +187,53 @@ clear_bit(BIT_E); clear_bit(BIT_RS); - PORTD = CMD_FUNC | FUNC_BUS_8BIT | FUNC_LINES_2 | FUNC_FONT_5x8; +#if LCD_BUS_WIDTH == 8 + lcd_write_byte(CMD_FUNC | FUNC_BUS_8BIT | FUNC_LINES_2 | FUNC_FONT_5x8); +#else + lcd_write_byte(CMD_FUNC | FUNC_BUS_4BIT | FUNC_LINES_2 | FUNC_FONT_5x8); +#endif enable(); lcd_wait_busy(); clear_bit(BIT_RS); - PORTD = CMD_ONOFF | ONOFF_DISP | ONOFF_CURSOR; + lcd_write_byte(CMD_ONOFF | ONOFF_DISP); enable(); lcd_wait_busy(); clear_bit(BIT_RS); - PORTD = CMD_ENTRY_MODE | (1 << 1); + lcd_write_byte(CMD_ENTRY_MODE | (1 << 1)); enable(); lcd_wait_busy(); } void lcd_clear(void) { - DDRD = 0xff; /* port d -> output */ - clear_bit(BIT_RW); clear_bit(BIT_E); clear_bit(BIT_RS); - PORTD = CMD_CLEAR; + lcd_write_byte(CMD_CLEAR); enable(); lcd_wait_busy(); } void lcd_set_cursor_addr(unsigned int addr) { - DDRD = 0xff; /* port d -> output */ - clear_bit(BIT_RW); clear_bit(BIT_E); clear_bit(BIT_RS); - PORTD = CMD_DDRAM_ADDR | addr; + lcd_write_byte(CMD_DDRAM_ADDR | addr); enable(); lcd_wait_busy(); } void lcd_putchar(char c) { - DDRD = 0xff; /* port d -> output */ - clear_bit(BIT_RW); set_bit(BIT_RS); - PORTD = c; + lcd_write_byte(c); enable(); lcd_wait_busy(); } @@ -196,9 +256,6 @@ { unsigned char data; - DDRD = 0; /* port d -> input */ - PORTD = 0; /* disable pull-ups */ - do { NSDELAY(); clear_bit(BIT_E); @@ -209,13 +266,11 @@ NSDELAY(); set_bit(BIT_E); NSDELAY(); - data = PIND; + data = lcd_read_byte(); clear_bit(BIT_E); clear_bit(BIT_RW); } while(data & (1 << 7)); - - DDRD = 0xff; /* port d -> output */ } static void enable(void)