aboutsummaryrefslogtreecommitdiff
path: root/avr/usi.c
diff options
context:
space:
mode:
authorOtto Mattik <otto@mattik.org>2021-07-08 18:10:55 +0200
committerOtto Mattik <otto@mattik.org>2021-07-08 18:10:55 +0200
commitda34d97efb21719b2b332f8c60b2750d11bcde1f (patch)
tree2de9fe89f6d79b8ebfcde64c5e86204e904aedf2 /avr/usi.c
downloadarmen-a861fb554ced7709555d2d1b639c534e3f45a83f.tar.gz
armen-a861fb554ced7709555d2d1b639c534e3f45a83f.zip
git: update to v1.0HEADv1.0master
Diffstat (limited to 'avr/usi.c')
-rw-r--r--avr/usi.c170
1 files changed, 170 insertions, 0 deletions
diff --git a/avr/usi.c b/avr/usi.c
new file mode 100644
index 0000000..cbc913e
--- /dev/null
+++ b/avr/usi.c
@@ -0,0 +1,170 @@
+/************************************************************************/
+/* */
+/* File: avr/usi.c */
+/* Description: serial line device. */
+/* Version: 1.0 */
+/* Author: Otto Mattik */
+/* */
+/* (C)Copyright Otto Mattik 2014-2021. */
+/* */
+/* This file is a part of 'armen' (a tiny operating system). */
+/* 'armen' is distributed under the CeCILL-V2.1 licence. For more */
+/* details about this licence, please visit the website cecill.info */
+/* */
+/************************************************************************/
+
+#ifndef AVR_UART_C
+ #error "do not use this code directly, it must be included via avr_uart.c"
+#endif
+
+#ifdef USE_PWM
+ #error "pwm and uart, used together, are incompatible"
+#endif
+
+/* TO DO: implement serial line via usi interface */
+
+#include <avr/io.h>
+#include <avr/interrupt.h>
+
+/*
+ * this code is based on the AVR307 publication.
+ * it use the timer 1 (16 bits on ATtiny84, 8 bits on ATtiny85).
+ * the uart is configured with 8 data bits, no parity and 1 stop bit.
+ * the used pins are DI (input) and DO (output).
+*/
+#if defined(__AVR_ATtiny84__)
+
+ #define USI_INPUT_PIN PA6 /* receive */
+ #define USI_OUTPUT_PIN PA5 /* transmit */
+ #define USI_CONFIG_PINS() (\
+ PORTA |= (1<<USI_INPUT_PIN),\
+ DDRA = (DDRA\
+ | (1<<USI_OUTPUT_PIN))\
+ & ~(1<<USI_INPUT_PIN)\
+ )
+ #define USI_INPUT_START_BIT() (PINA & (1<<USI_INPUT_PIN) ? 0 : 1)
+ #define USI_CONFIG_TIMER(p) (\
+ TIMSK1 = 0, TCCR1A = 0,\
+ TCCR1B = (1<<ICNC1) | (p)\
+ )
+ #define USI_CONFIG_DEVICE() ()
+
+ #define USI_INPUT_CAPTURE_INT PCINT6_vect
+
+#elif defined(__AVR_ATtiny85__)
+
+ #define USI_INPUT_PIN PB0 /* receive */
+ #define USI_OUTPUT_PIN PB1 /* transmit */
+ #define USI_CONFIG_PINS() (\
+ PORTB |= (1<<USI_INPUT_PIN),\
+ DDRB = (DDRB\
+ | (1<<USI_OUTPUT_PIN))\
+ & ~(1<<USI_INPUT_PIN)\
+ )
+ #define USI_INPUT_START_BIT() (PINB & (1<<USI_INPUT_PIN) ? 0 : 1)
+ #define USI_CONFIG_TIMER(p) (TIMSK = 0, TCCR1 = (p))
+ #define USI_CONFIG_DEVICE() ()
+
+ #define USI_INPUT_CAPTURE_INT PCINT0_vect
+
+#else
+ #error "no or unavailable cpu defined"
+#endif
+
+#define USI_OVERFLOW_INTERRUPT USI_OVF_vect
+#define TIMER_OVERFLOW_INTERRUPT TIMER1_OVF_vect
+
+#define CONFIG_RS485(p) (CONFIG_RS485_DRIVER(), \
+ CONFIG_TIMER_PRESCALE(p), \
+ CONFIG_USI_DEVICE())
+
+#define USI_RX_BUFFER_SIZE 16
+#define UART_ECHOO_CHECK 0x40
+
+/*
+ * reverse bits order lsb<->msb
+ *
+ * input:
+ * byte byte to reverse
+ * output:
+ * reversed byte
+*/
+static uint8_t reverse_byte( uint8_t byte )
+{
+ byte = ((byte >> 1) & 0x55) | ((byte << 1) & 0xaa);
+ byte = ((byte >> 2) & 0x33) | ((byte << 2) & 0xcc);
+ byte = ((byte >> 4) & 0x0f) | ((byte << 4) & 0xf0);
+ return( byte );
+}
+
+/*
+ * initialize device
+ *
+ * input:
+ * device identifier (always 0)
+ * config uart configuration
+ * output:
+ * 0 if success, otherwise -1
+*/
+static int8_t uart_open( uint8_t device, uint8_t config )
+{
+ return( -1 );
+}
+
+/*
+ * release device
+ *
+ * input:
+ * device identifier
+ * output:
+ * 0 if success, otherwise -1
+*/
+static int8_t uart_close( uint8_t device )
+{
+ return( -1 );
+}
+
+/*
+ * read from device
+ *
+ * input:
+ * device identifier (always 0)
+ * byte address of byte to read
+ * output:
+ * 0 if success, otherwise -1
+*/
+static int8_t uart_read( uint8_t device, uint8_t* byte )
+{
+ return( -1 );
+}
+
+/*
+ * write to device
+ *
+ * input:
+ * device identifier (always 0)
+ * byte byte to write
+ * output:
+ * 0 if success, otherwise -1
+*/
+static int8_t uart_write( uint8_t device, uint8_t byte )
+{
+ return( -1 );
+}
+
+/*
+ * device special feature
+ *
+ * input:
+ * device identifier (always 0)
+ * request device dependent
+ * args list of arguments
+ * output:
+ * 0 if success, otherwise -1
+*/
+#ifdef UART_IOCTL
+static int8_t uart_ioctl( uint8_t device, uint8_t request, va_list args )
+{
+ return( -1 );
+}
+#endif