#include "cse_avr_board.h" void uart_putn(unsigned int i, unsigned int base); void keypad_press(unsigned int *after_milliseconds, int *key_row, int *key_column); int main(void) { const int lcd_length = 14; uart_puts("Link PB0-PB7 to LCD D0-D7 (8 wires)\n"); uart_puts("Link PD0-PD3 to LCD BE-RS (4 wires)\n"); uart_puts("Link PC0-PC3 to Keypad R0..R3 (4 wires)\n"); uart_puts("Link PA0-PA3 to Keypad C0..C3 (4 wires)\n"); while (1) { lcd_set_line(0,""); lcd_set_line(1,"Texting Lab"); char buffer[lcd_length + 1]; for (int i = 0; i < sizeof buffer;i++) buffer[i] = 0; for (int column = 0; column < lcd_length; column++) { int milliseconds, key_row, key_column; keypad_press(&milliseconds, &key_row, &key_column); char c = "123A456B789C*0#D"[key_row*4+key_column]; uart_puts("After "); uart_putn(milliseconds, 10); uart_puts("ms you typed a: '"); uart_putchar(c); uart_puts("'\n"); buffer[0] = c; lcd_set_line(0, buffer); } } return 0; } // // wait for keypad key to be pressed and released // row, column and waiting time before it was pressed are returned // void keypad_press(unsigned int *after_milliseconds, int *key_row, int *key_column) { volatile unsigned char *portc_control_address = (char *)0x34; volatile unsigned char *portc_output_address = (char *)0x35; volatile unsigned char *porta_input_address = (char *)0x39; volatile unsigned char *porta_control_address = (char *)0x3A; volatile unsigned char *porta_output_address = (char *)0x3B; *portc_control_address = 0x0f; *porta_control_address = 0x00; int milliseconds = 0; while (1) { for (int row = 0; row < 4; row++) { *porta_output_address = 0x0f; // pull PA0..PA3 = keypad C0-C3 high *portc_output_address = 0x0f & ~(1 << row); // pull a row line low wait(1,0); // wait 1 millisecond for settling int input = *porta_input_address & 0xf; // input PA0..PA3 = keypad C0-C3 milliseconds++; int column; for (column = 0; column < 4; column++) if (!(input & (1 << column))) break; if (column != 4) { while ((*porta_input_address & 0xf) == input) ; *key_row = row; *key_column = column; *after_milliseconds = milliseconds; return; } } } } // print to uart number in specified base void uart_putn(unsigned int i, unsigned int base) { if (base > 16) base = 16; unsigned int j = i / base; if (j) { uart_putn(j, base); i -= j * base; } uart_putchar("0123456789ABCDEF"[i]); }