root / trunk / cardbox / rs485_int.c @ 285
History | View | Annotate | Download (2.1 KB)
| 1 | /********
|
|---|---|
| 2 | * This file is part of Tooltron. |
| 3 | * |
| 4 | * Tooltron is free software: you can redistribute it and/or modify |
| 5 | * it under the terms of the Lesser GNU General Public License as published by |
| 6 | * the Free Software Foundation, either version 3 of the License, or |
| 7 | * (at your option) any later version. |
| 8 | * |
| 9 | * Tooltron is distributed in the hope that it will be useful, |
| 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 12 | * Lesser GNU General Public License for more details. |
| 13 | * You should have received a copy of the Lesser GNU General Public License |
| 14 | * along with Tooltron. If not, see <http://www.gnu.org/licenses/>. |
| 15 | * |
| 16 | * Copyright 2009 Kevin Woo <kwoo@2ndt.com> |
| 17 | * |
| 18 | ********/ |
| 19 | /** @file rs485_int.c
|
| 20 | * |
| 21 | * @brief Implements UART functionality in hardware |
| 22 | * |
| 23 | * @author Kevin Woo (kwoo) |
| 24 | */ |
| 25 | |
| 26 | #include "rs485_int.h" |
| 27 | #include <util/delay.h> |
| 28 | #include <stdint.h> |
| 29 | |
| 30 | uint8_t received_byte; //Byte received
|
| 31 | uint8_t byte_ready; //New byte has been received
|
| 32 | |
| 33 | void rs485_init(uint16_t baud) {
|
| 34 | // Set baud rate
|
| 35 | UBRR0H = (uint8_t)(baud>>8);
|
| 36 | UBRR0L = (uint8_t)baud; |
| 37 | |
| 38 | // Enable RX/TX and RX/TX Interrupt
|
| 39 | UCSR0B = _BV(RXCIE0) | _BV(RXEN0) | _BV(TXCIE0) | _BV(TXEN0); |
| 40 | |
| 41 | // Enable the TXEN pin as output
|
| 42 | DDRD |= TX_EN; |
| 43 | |
| 44 | // Initialize receive variables
|
| 45 | byte_ready = 0;
|
| 46 | received_byte = 0x0;
|
| 47 | |
| 48 | // Set to receive mode
|
| 49 | rs485_toggle_transmit(RS485_TX_OFF); |
| 50 | } |
| 51 | |
| 52 | int8_t rs485_get_byte(uint8_t *output_byte) {
|
| 53 | if (byte_ready) {
|
| 54 | byte_ready = 0;
|
| 55 | *output_byte = received_byte; |
| 56 | return 0; |
| 57 | } else {
|
| 58 | return -1; |
| 59 | } |
| 60 | } |
| 61 | |
| 62 | void rs485_send_byte(uint8_t data) {
|
| 63 | //Waits until current transmit is done
|
| 64 | while (!(UCSR0A & _BV(UDRE0)));
|
| 65 | |
| 66 | // Enable writes and send
|
| 67 | rs485_toggle_transmit(RS485_TX_ON); |
| 68 | UDR0 = data; |
| 69 | return;
|
| 70 | } |
| 71 | |
| 72 | void rs485_toggle_transmit(uint8_t state) {
|
| 73 | if (state == RS485_TX_ON) {
|
| 74 | PORTD |= TX_EN; |
| 75 | } else {
|
| 76 | PORTD &= ~TX_EN; |
| 77 | } |
| 78 | } |
| 79 | |
| 80 | ISR(USART_RX_vect) {
|
| 81 | received_byte = UDR0; |
| 82 | byte_ready = 1;
|
| 83 | } |
| 84 | |
| 85 | ISR(USART_TX_vect) {
|
| 86 | // Re-enable reads
|
| 87 | rs485_toggle_transmit(RS485_TX_OFF); |
| 88 | } |