forked from mirror/qmk_firmware
add split_scomm.c/split_scomm.h and change serial.c/serial.h
serial.c was divided into 2 layers, split_scom.c and serial.c. The upper layer split_scomm.c is called from matrix.c. The lower layer serial.c accesses the hardware.
This commit is contained in:
@@ -34,7 +34,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|||||||
#ifdef USE_MATRIX_I2C
|
#ifdef USE_MATRIX_I2C
|
||||||
# include "i2c.h"
|
# include "i2c.h"
|
||||||
#else // USE_SERIAL
|
#else // USE_SERIAL
|
||||||
# include "serial.h"
|
# include "split_scomm.h"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifndef DEBOUNCE
|
#ifndef DEBOUNCE
|
||||||
@@ -182,7 +182,7 @@ i2c_error: // the cable is disconnceted, or something else went wrong
|
|||||||
|
|
||||||
int serial_transaction(void) {
|
int serial_transaction(void) {
|
||||||
int slaveOffset = (isLeftHand) ? (ROWS_PER_HAND) : 0;
|
int slaveOffset = (isLeftHand) ? (ROWS_PER_HAND) : 0;
|
||||||
int ret=serial_update_buffers();
|
int ret=serial_update_buffers(1);
|
||||||
if (ret ) {
|
if (ret ) {
|
||||||
if(ret==2)RXLED1;
|
if(ret==2)RXLED1;
|
||||||
return 1;
|
return 1;
|
||||||
|
|||||||
@@ -1,3 +1,4 @@
|
|||||||
SRC += rev2/matrix.c \
|
SRC += rev2/matrix.c
|
||||||
rev2/split_util.c \
|
SRC += rev2/split_util.c
|
||||||
ws2812.c
|
SRC += rev2/split_scomm.c
|
||||||
|
SRC += ws2812.c
|
||||||
|
|||||||
@@ -8,9 +8,6 @@
|
|||||||
#define SERIAL_PIN_MASK _BV(PD2)
|
#define SERIAL_PIN_MASK _BV(PD2)
|
||||||
#define SERIAL_PIN_INTERRUPT INT2_vect
|
#define SERIAL_PIN_INTERRUPT INT2_vect
|
||||||
|
|
||||||
#define SERIAL_SLAVE_BUFFER_LENGTH MATRIX_ROWS/2
|
|
||||||
#define SERIAL_MASTER_BUFFER_LENGTH MATRIX_ROWS/2
|
|
||||||
|
|
||||||
//// #error rev2 serial config
|
//// #error rev2 serial config
|
||||||
|
|
||||||
#endif /* SOFT_SERIAL_CONFIG_H */
|
#endif /* SOFT_SERIAL_CONFIG_H */
|
||||||
|
|||||||
36
keyboards/helix/rev2/split_scomm.c
Normal file
36
keyboards/helix/rev2/split_scomm.c
Normal file
@@ -0,0 +1,36 @@
|
|||||||
|
#ifdef USE_SERIAL
|
||||||
|
#include <stdbool.h>
|
||||||
|
#include <stdint.h>
|
||||||
|
#include <stddef.h>
|
||||||
|
#include <split_scomm.h>
|
||||||
|
#include "serial.h"
|
||||||
|
|
||||||
|
uint8_t volatile serial_slave_buffer[SERIAL_SLAVE_BUFFER_LENGTH] = {0};
|
||||||
|
uint8_t volatile serial_master_buffer[SERIAL_MASTER_BUFFER_LENGTH] = {0};
|
||||||
|
uint8_t volatile status0 = 0;
|
||||||
|
|
||||||
|
SSTD_t transactions[] = {
|
||||||
|
{ (uint8_t *)&status0,
|
||||||
|
sizeof(serial_master_buffer), (uint8_t *)serial_master_buffer,
|
||||||
|
sizeof(serial_slave_buffer), (uint8_t *)serial_slave_buffer
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
void serial_master_init(void)
|
||||||
|
{
|
||||||
|
soft_serial_initiator_init(transactions);
|
||||||
|
}
|
||||||
|
|
||||||
|
void serial_slave_init(void)
|
||||||
|
{
|
||||||
|
soft_serial_target_init(transactions);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 0 => no error
|
||||||
|
// 1 => slave did not respond
|
||||||
|
// 2 => checksum error
|
||||||
|
int serial_update_buffers(int master_update)
|
||||||
|
{
|
||||||
|
return soft_serial_transaction(0);
|
||||||
|
}
|
||||||
|
#endif /* USE_SERIAL */
|
||||||
15
keyboards/helix/rev2/split_scomm.h
Normal file
15
keyboards/helix/rev2/split_scomm.h
Normal file
@@ -0,0 +1,15 @@
|
|||||||
|
#ifndef SPLIT_COMM_H
|
||||||
|
#define SPLIT_COMM_H
|
||||||
|
|
||||||
|
// Buffers for master - slave communication
|
||||||
|
#define SERIAL_SLAVE_BUFFER_LENGTH MATRIX_ROWS/2
|
||||||
|
#define SERIAL_MASTER_BUFFER_LENGTH MATRIX_ROWS/2
|
||||||
|
|
||||||
|
extern volatile uint8_t serial_slave_buffer[SERIAL_SLAVE_BUFFER_LENGTH];
|
||||||
|
extern volatile uint8_t serial_master_buffer[SERIAL_MASTER_BUFFER_LENGTH];
|
||||||
|
|
||||||
|
void serial_master_init(void);
|
||||||
|
void serial_slave_init(void);
|
||||||
|
int serial_update_buffers(int master_changed);
|
||||||
|
|
||||||
|
#endif /* SPLIT_COMM_H */
|
||||||
@@ -11,7 +11,7 @@
|
|||||||
#ifdef USE_MATRIX_I2C
|
#ifdef USE_MATRIX_I2C
|
||||||
# include "i2c.h"
|
# include "i2c.h"
|
||||||
#else
|
#else
|
||||||
# include "serial.h"
|
# include "split_scomm.h"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
volatile bool isLeftHand = true;
|
volatile bool isLeftHand = true;
|
||||||
|
|||||||
@@ -1,6 +1,9 @@
|
|||||||
SRC += i2c.c \
|
SRC += i2c.c
|
||||||
serial.c \
|
SRC += serial.c
|
||||||
ssd1306.c
|
SRC += ssd1306.c
|
||||||
|
|
||||||
|
# if firmware size over limit, try this option
|
||||||
|
# CFLAGS += -flto
|
||||||
|
|
||||||
# MCU name
|
# MCU name
|
||||||
#MCU = at90usb1287
|
#MCU = at90usb1287
|
||||||
|
|||||||
@@ -9,8 +9,10 @@
|
|||||||
#include <avr/io.h>
|
#include <avr/io.h>
|
||||||
#include <avr/interrupt.h>
|
#include <avr/interrupt.h>
|
||||||
#include <util/delay.h>
|
#include <util/delay.h>
|
||||||
|
#include <stddef.h>
|
||||||
#include <stdbool.h>
|
#include <stdbool.h>
|
||||||
#include "serial.h"
|
#include "serial.h"
|
||||||
|
//#include <pro_micro.h>
|
||||||
|
|
||||||
#ifdef USE_SERIAL
|
#ifdef USE_SERIAL
|
||||||
|
|
||||||
@@ -55,11 +57,7 @@
|
|||||||
#define SLAVE_INT_WIDTH 1
|
#define SLAVE_INT_WIDTH 1
|
||||||
#define SLAVE_INT_RESPONSE_TIME SERIAL_DELAY
|
#define SLAVE_INT_RESPONSE_TIME SERIAL_DELAY
|
||||||
|
|
||||||
uint8_t volatile serial_slave_buffer[SERIAL_SLAVE_BUFFER_LENGTH] = {0};
|
static SSTD_t *Transaction_table = NULL;
|
||||||
uint8_t volatile serial_master_buffer[SERIAL_MASTER_BUFFER_LENGTH] = {0};
|
|
||||||
|
|
||||||
#define SLAVE_DATA_CORRUPT (1<<0)
|
|
||||||
volatile uint8_t status = 0;
|
|
||||||
|
|
||||||
inline static
|
inline static
|
||||||
void serial_delay(void) {
|
void serial_delay(void) {
|
||||||
@@ -109,26 +107,30 @@ void serial_high(void) {
|
|||||||
SERIAL_PIN_PORT |= SERIAL_PIN_MASK;
|
SERIAL_PIN_PORT |= SERIAL_PIN_MASK;
|
||||||
}
|
}
|
||||||
|
|
||||||
void serial_master_init(void) {
|
void soft_serial_initiator_init(SSTD_t *sstd_table)
|
||||||
serial_debug_init();
|
{
|
||||||
serial_output();
|
serial_debug_init();
|
||||||
serial_high();
|
Transaction_table = sstd_table;
|
||||||
|
serial_output();
|
||||||
|
serial_high();
|
||||||
}
|
}
|
||||||
|
|
||||||
void serial_slave_init(void) {
|
void soft_serial_target_init(SSTD_t *sstd_table)
|
||||||
serial_debug_init();
|
{
|
||||||
serial_input_with_pullup();
|
serial_debug_init();
|
||||||
|
Transaction_table = sstd_table;
|
||||||
|
serial_input_with_pullup();
|
||||||
|
|
||||||
#if SERIAL_PIN_MASK == _BV(PD0)
|
#if SERIAL_PIN_MASK == _BV(PD0)
|
||||||
// Enable INT0
|
// Enable INT0
|
||||||
EIMSK |= _BV(INT0);
|
EIMSK |= _BV(INT0);
|
||||||
// Trigger on falling edge of INT0
|
// Trigger on falling edge of INT0
|
||||||
EICRA &= ~(_BV(ISC00) | _BV(ISC01));
|
EICRA &= ~(_BV(ISC00) | _BV(ISC01));
|
||||||
#elif SERIAL_PIN_MASK == _BV(PD2)
|
#elif SERIAL_PIN_MASK == _BV(PD2)
|
||||||
// Enable INT2
|
// Enable INT2
|
||||||
EIMSK |= _BV(INT2);
|
EIMSK |= _BV(INT2);
|
||||||
// Trigger on falling edge of INT2
|
// Trigger on falling edge of INT2
|
||||||
EICRA &= ~(_BV(ISC20) | _BV(ISC21));
|
EICRA &= ~(_BV(ISC20) | _BV(ISC21));
|
||||||
#else
|
#else
|
||||||
#error unknown SERIAL_PIN_MASK value
|
#error unknown SERIAL_PIN_MASK value
|
||||||
#endif
|
#endif
|
||||||
@@ -228,7 +230,7 @@ uint8_t serial_recive_packet(uint8_t *buffer, uint8_t size) {
|
|||||||
uint8_t checksum_received = serial_read_byte();
|
uint8_t checksum_received = serial_read_byte();
|
||||||
debug_bytewidth_end();
|
debug_bytewidth_end();
|
||||||
|
|
||||||
return checksum_computed != checksum_received;
|
return checksum_computed == checksum_received;
|
||||||
}
|
}
|
||||||
|
|
||||||
inline static
|
inline static
|
||||||
@@ -255,38 +257,38 @@ ISR(SERIAL_PIN_INTERRUPT) {
|
|||||||
|
|
||||||
serial_low();
|
serial_low();
|
||||||
serial_output();
|
serial_output();
|
||||||
|
SSTD_t *trans = Transaction_table;
|
||||||
|
|
||||||
// slave send phase
|
// slave send phase
|
||||||
serial_send_packet((uint8_t *)serial_slave_buffer, SERIAL_SLAVE_BUFFER_LENGTH);
|
serial_send_packet((uint8_t *)trans->target2initiator_buffer,
|
||||||
|
trans->target2initiator_buffer_size);
|
||||||
// slave switch to input
|
// slave switch to input
|
||||||
change_sender2reciver();
|
change_sender2reciver();
|
||||||
|
|
||||||
// slave recive phase
|
// slave recive phase
|
||||||
if (serial_recive_packet((uint8_t *)serial_master_buffer,SERIAL_MASTER_BUFFER_LENGTH) ) {
|
if (serial_recive_packet((uint8_t *)trans->initiator2target_buffer,
|
||||||
status |= SLAVE_DATA_CORRUPT;
|
trans->initiator2target_buffer_size) ) {
|
||||||
|
*trans->status = RECIVE_ACCEPTED;
|
||||||
} else {
|
} else {
|
||||||
status &= ~SLAVE_DATA_CORRUPT;
|
*trans->status = RECIVE_DATA_ERROR;
|
||||||
}
|
}
|
||||||
|
|
||||||
sync_recv(); //weit master output to high
|
sync_recv(); //weit master output to high
|
||||||
debug_output_mode(); debug_input_mode(); // indicate intterupt exit
|
debug_output_mode(); debug_input_mode(); // indicate intterupt exit
|
||||||
}
|
}
|
||||||
|
|
||||||
inline
|
/////////
|
||||||
bool serial_slave_DATA_CORRUPT(void) {
|
// start transaction by initiator
|
||||||
return status & SLAVE_DATA_CORRUPT;
|
//
|
||||||
}
|
// int soft_serial_transaction(int sstd_index)
|
||||||
|
|
||||||
// Copies the serial_slave_buffer to the master and sends the
|
|
||||||
// serial_master_buffer to the slave.
|
|
||||||
//
|
//
|
||||||
// Returns:
|
// Returns:
|
||||||
// 0 => no error
|
// TRANSACTION_END
|
||||||
// 1 => slave did not respond
|
// TRANSACTION_NO_RESPONSE
|
||||||
// 2 => checksum error
|
// TRANSACTION_DATA_ERROR
|
||||||
int serial_update_buffers(void) {
|
int soft_serial_transaction(int sstd_index) {
|
||||||
// this code is very time dependent, so we need to disable interrupts
|
// this code is very time dependent, so we need to disable interrupts
|
||||||
|
SSTD_t *trans = &Transaction_table[sstd_index];
|
||||||
cli();
|
cli();
|
||||||
|
|
||||||
// signal to the slave that we want to start a transaction
|
// signal to the slave that we want to start a transaction
|
||||||
@@ -309,7 +311,8 @@ int serial_update_buffers(void) {
|
|||||||
|
|
||||||
// master recive phase
|
// master recive phase
|
||||||
// if the slave is present syncronize with it
|
// if the slave is present syncronize with it
|
||||||
if (serial_recive_packet((uint8_t *)serial_slave_buffer, SERIAL_SLAVE_BUFFER_LENGTH) ) {
|
if (!serial_recive_packet((uint8_t *)trans->target2initiator_buffer,
|
||||||
|
trans->target2initiator_buffer_size) ) {
|
||||||
serial_output();
|
serial_output();
|
||||||
serial_high();
|
serial_high();
|
||||||
sei();
|
sei();
|
||||||
@@ -320,7 +323,8 @@ int serial_update_buffers(void) {
|
|||||||
change_reciver2sender();
|
change_reciver2sender();
|
||||||
|
|
||||||
// master send phase
|
// master send phase
|
||||||
serial_send_packet((uint8_t *)serial_master_buffer, SERIAL_MASTER_BUFFER_LENGTH);
|
serial_send_packet((uint8_t *)trans->initiator2target_buffer,
|
||||||
|
trans->initiator2target_buffer_size);
|
||||||
|
|
||||||
// always, release the line when not in use
|
// always, release the line when not in use
|
||||||
sync_send();
|
sync_send();
|
||||||
|
|||||||
@@ -12,18 +12,31 @@
|
|||||||
// #define SERIAL_PIN_INPUT PIND
|
// #define SERIAL_PIN_INPUT PIND
|
||||||
// #define SERIAL_PIN_MASK _BV(PD?) ?=0,2
|
// #define SERIAL_PIN_MASK _BV(PD?) ?=0,2
|
||||||
// #define SERIAL_PIN_INTERRUPT INT?_vect ?=0,2
|
// #define SERIAL_PIN_INTERRUPT INT?_vect ?=0,2
|
||||||
// #define SERIAL_SLAVE_BUFFER_LENGTH MATRIX_ROWS/2
|
|
||||||
// #define SERIAL_MASTER_BUFFER_LENGTH MATRIX_ROWS/2
|
|
||||||
|
|
||||||
// Buffers for master - slave communication
|
// Soft Serial Transaction Descriptor
|
||||||
extern volatile uint8_t serial_slave_buffer[SERIAL_SLAVE_BUFFER_LENGTH];
|
typedef struct _SSTD_t {
|
||||||
extern volatile uint8_t serial_master_buffer[SERIAL_MASTER_BUFFER_LENGTH];
|
uint8_t *status;
|
||||||
|
uint8_t initiator2target_buffer_size;
|
||||||
|
uint8_t *initiator2target_buffer;
|
||||||
|
uint8_t target2initiator_buffer_size;
|
||||||
|
uint8_t *target2initiator_buffer;
|
||||||
|
} SSTD_t;
|
||||||
|
|
||||||
void serial_master_init(void);
|
// initiator is transaction start side
|
||||||
void serial_slave_init(void);
|
void soft_serial_initiator_init(SSTD_t *sstd_table);
|
||||||
int serial_update_buffers(void);
|
// target is interrupt accept side
|
||||||
bool serial_slave_data_corrupt(void);
|
void soft_serial_target_init(SSTD_t *sstd_table);
|
||||||
|
|
||||||
|
// initiator resullt
|
||||||
|
#define TRANSACTION_END 0
|
||||||
|
#define TRANSACTION_NO_RESPONSE 1
|
||||||
|
#define TRANSACTION_DATA_ERROR 2
|
||||||
|
int soft_serial_transaction(int sstd_index);
|
||||||
|
|
||||||
|
// target status
|
||||||
|
#define RECIVE_ACCEPTED 1
|
||||||
|
#define RECIVE_DATA_ERROR 2
|
||||||
|
int soft_serial_get_and_clean_target_status(int sstd_index);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user