diff --git a/F0:F030,F042,F072/usbcan_ringbuffer/Makefile b/F0:F030,F042,F072/usbcan_ringbuffer/Makefile index f585984..a997924 100644 --- a/F0:F030,F042,F072/usbcan_ringbuffer/Makefile +++ b/F0:F030,F042,F072/usbcan_ringbuffer/Makefile @@ -8,6 +8,7 @@ FAMILY ?= F0 MCU ?= F042x6 # change this linking script depending on particular MCU model, LDSCRIPT ?= stm32f042x6.ld +#DEFS = -DEBUG # autoincremental version & build date VERSION_FILE = version.inc diff --git a/F0:F030,F042,F072/usbcan_ringbuffer/can.c b/F0:F030,F042,F072/usbcan_ringbuffer/can.c index 2727695..7076f51 100644 --- a/F0:F030,F042,F072/usbcan_ringbuffer/can.c +++ b/F0:F030,F042,F072/usbcan_ringbuffer/can.c @@ -21,17 +21,14 @@ #include "proto.h" #include "usb.h" -#include // memcpy - // circular buffer for received messages static CAN_message messages[CAN_INMESSAGE_SIZE]; static uint8_t first_free_idx = 0; // index of first empty cell static int8_t first_nonfree_idx = -1; // index of first data cell static uint16_t oldspeed = 100; // speed of last init +uint32_t floodT = FLOOD_PERIOD_MS-1; // flood period in ms -#ifdef EBUG static uint32_t last_err_code = 0; -#endif static CAN_status can_status = CAN_STOP; static void can_process_fifo(uint8_t fifo_num); @@ -65,7 +62,7 @@ static int CAN_messagebuf_push(CAN_message *msg){ return 1; // no free space } if(first_nonfree_idx < 0) first_nonfree_idx = 0; // first message in empty buffer - memcpy(&messages[first_free_idx++], msg, sizeof(CAN_message)); + messages[first_free_idx++] = *msg; // need to roll? if(first_free_idx == CAN_INMESSAGE_SIZE) first_free_idx = 0; return 0; @@ -146,9 +143,7 @@ void CAN_setup(uint16_t speed){ /* (13) Set error interrupts enable */ CAN->MCR |= CAN_MCR_INRQ; /* (1) */ while((CAN->MSR & CAN_MSR_INAK)!=CAN_MSR_INAK) /* (2) */ - { if(--tmout == 0) break; - } CAN->MCR &=~ CAN_MCR_SLEEP; /* (3) */ CAN->MCR |= CAN_MCR_ABOM; /* allow automatically bus-off */ @@ -174,6 +169,36 @@ void CAN_setup(uint16_t speed){ can_status = CAN_READY; } +void printCANerr(){ + if(!last_err_code) last_err_code = CAN->ESR; + if(!last_err_code){ + USB_sendstr("No errors\n"); + return; + } + USB_sendstr("Receive error counter: "); + printu((last_err_code & CAN_ESR_REC)>>24); + USB_sendstr("\nTransmit error counter: "); + printu((last_err_code & CAN_ESR_TEC)>>16); + USB_sendstr("\nLast error code: "); + int lec = (last_err_code & CAN_ESR_LEC) >> 4; + const char *errmsg = "No"; + switch(lec){ + case 1: errmsg = "Stuff"; break; + case 2: errmsg = "Form"; break; + case 3: errmsg = "Ack"; break; + case 4: errmsg = "Bit recessive"; break; + case 5: errmsg = "Bit dominant"; break; + case 6: errmsg = "CRC"; break; + case 7: errmsg = "(set by software)"; break; + } + USB_sendstr(errmsg); USB_sendstr(" error\n"); + if(last_err_code & CAN_ESR_BOFF) USB_sendstr("Bus off "); + if(last_err_code & CAN_ESR_EPVF) USB_sendstr("Passive error limit "); + if(last_err_code & CAN_ESR_EWGF) USB_sendstr("Error counter limit"); + last_err_code = 0; + USB_putbyte('\n'); +} + void can_proc(){ #ifdef EBUG if(last_err_code){ @@ -193,27 +218,7 @@ void can_proc(){ IWDG->KR = IWDG_REFRESH; if(CAN->ESR & (CAN_ESR_BOFF | CAN_ESR_EPVF | CAN_ESR_EWGF)){ // much errors - restart CAN BUS USB_sendstr("\nToo much errors, restarting CAN!\n"); - USB_sendstr("Receive error counter: "); - printu((CAN->ESR & CAN_ESR_REC)>>24); - USB_sendstr("\nTransmit error counter: "); - printu((CAN->ESR & CAN_ESR_TEC)>>16); - USB_sendstr("\nLast error code: "); - int lec = (CAN->ESR & CAN_ESR_LEC) >> 4; - const char *errmsg = "No"; - switch(lec){ - case 1: errmsg = "Stuff"; break; - case 2: errmsg = "Form"; break; - case 3: errmsg = "Ack"; break; - case 4: errmsg = "Bit recessive"; break; - case 5: errmsg = "Bit dominant"; break; - case 6: errmsg = "CRC"; break; - case 7: errmsg = "(set by software)"; break; - } - USB_sendstr(errmsg); USB_sendstr(" error\n"); - if(CAN->ESR & CAN_ESR_BOFF) USB_sendstr("Bus off "); - if(CAN->ESR & CAN_ESR_EPVF) USB_sendstr("Passive error limit "); - if(CAN->ESR & CAN_ESR_EWGF) USB_sendstr("Error counter limit"); - USB_putbyte('\n'); + printCANerr(); // request abort for all mailboxes CAN->TSR |= CAN_TSR_ABRQ0 | CAN_TSR_ABRQ1 | CAN_TSR_ABRQ2; // reset CAN bus @@ -222,7 +227,7 @@ void can_proc(){ CAN_setup(0); } static uint32_t lastFloodTime = 0; - if(flood_msg && (Tms - lastFloodTime) > (FLOOD_PERIOD_MS-1)){ // flood every ~5ms + if(flood_msg && (Tms - lastFloodTime) > (floodT)){ // flood every ~5ms lastFloodTime = Tms; can_send(flood_msg->data, flood_msg->length, flood_msg->ID); } @@ -285,7 +290,21 @@ CAN_status can_send(uint8_t *msg, uint8_t len, uint16_t target_id){ void set_flood(CAN_message *msg){ if(!msg) flood_msg = NULL; else{ - memcpy(&loc_flood_msg, msg, sizeof(CAN_message)); +#ifdef EBUG + USB_sendstr("flood msg: #"); + printuhex(msg->ID); + for(uint8_t ctr = 0; ctr < msg->length; ++ctr){ + USB_putbyte(' '); + printuhex(msg->data[ctr]); + } + USB_putbyte('\n'); +#endif + // I meet strange problems with `loc_flood_msg = *msg` and system memcpy, so.. + loc_flood_msg.ID = msg->ID; + loc_flood_msg.length = msg->length; + *((uint32_t*)loc_flood_msg.data) = *((uint32_t*)msg->data); + if(loc_flood_msg.length > 4) + *((uint32_t*)&loc_flood_msg.data[4]) = *((uint32_t*)&msg->data[4]); flood_msg = &loc_flood_msg; } } @@ -364,3 +383,4 @@ void cec_can_isr(){ #endif } } + diff --git a/F0:F030,F042,F072/usbcan_ringbuffer/can.h b/F0:F030,F042,F072/usbcan_ringbuffer/can.h index 2ba2b03..50492be 100644 --- a/F0:F030,F042,F072/usbcan_ringbuffer/can.h +++ b/F0:F030,F042,F072/usbcan_ringbuffer/can.h @@ -18,7 +18,7 @@ #pragma once -#include "hardware.h" +#include // amount of filter banks in STM32F0 #define STM32F0FBANKNO 28 @@ -28,6 +28,8 @@ // incoming message buffer size #define CAN_INMESSAGE_SIZE (8) +extern uint32_t floodT; + // CAN message typedef struct{ uint8_t data[8]; // up to 8 bytes of data @@ -50,6 +52,7 @@ void CAN_setup(uint16_t speed); CAN_status can_send(uint8_t *msg, uint8_t len, uint16_t target_id); void can_proc(); +void printCANerr(); CAN_message *CAN_messagebuf_pop(); diff --git a/F0:F030,F042,F072/usbcan_ringbuffer/main.c b/F0:F030,F042,F072/usbcan_ringbuffer/main.c index 4506239..0b20083 100644 --- a/F0:F030,F042,F072/usbcan_ringbuffer/main.c +++ b/F0:F030,F042,F072/usbcan_ringbuffer/main.c @@ -68,7 +68,7 @@ int main(void){ USB_sendstr(" #"); printuhex(can_mesg->ID); for(uint8_t ctr = 0; ctr < len; ++ctr){ - USB_putbyte('\n'); + USB_putbyte(' '); printuhex(can_mesg->data[ctr]); } USB_putbyte('\n'); diff --git a/F0:F030,F042,F072/usbcan_ringbuffer/proto.c b/F0:F030,F042,F072/usbcan_ringbuffer/proto.c index 92b9a88..4624132 100644 --- a/F0:F030,F042,F072/usbcan_ringbuffer/proto.c +++ b/F0:F030,F042,F072/usbcan_ringbuffer/proto.c @@ -137,6 +137,7 @@ static char *getbin(const char *buf, uint32_t *N){ char *getnum(const char *txt, uint32_t *N){ char *nxt = NULL; char *s = omit_spaces(txt); + if(!*s) return (char*)txt; if(*s == '0'){ // hex, oct or 0 if(s[1] == 'x' || s[1] == 'X'){ // hex nxt = gethex(s+2, N); @@ -166,7 +167,6 @@ static CAN_message *parseCANmsg(char *txt){ int ctr = -1; canmsg.ID = 0xffff; do{ - txt = omit_spaces(txt); n = getnum(txt, &N); if(txt == n) break; txt = n; @@ -200,16 +200,19 @@ static CAN_message *parseCANmsg(char *txt){ // USB_sendstr command, format: ID (hex/bin/dec) data bytes (up to 8 bytes, space-delimeted) TRUE_INLINE void USB_sendstrCANcommand(char *txt){ + if(CAN->MSR & CAN_MSR_INAK){ + USB_sendstr("CAN bus is off, try to restart it\n"); + return; + } CAN_message *msg = parseCANmsg(txt); if(!msg) return; - uint32_t N = 1000000; + uint32_t N = 5; while(CAN_BUSY == can_send(msg->data, msg->length, msg->ID)){ if(--N == 0) break; } } TRUE_INLINE void CANini(char *txt){ - txt = omit_spaces(txt); uint32_t N; char *n = getnum(txt, &N); if(txt == n){ @@ -318,6 +321,17 @@ TRUE_INLINE void list_filters(){ } } +TRUE_INLINE void setfloodt(char *s){ + uint32_t N; + s = omit_spaces(s); + char *n = getnum(s, &N); + if(s == n || N == 0){ + USB_sendstr("t="); printu(floodT); USB_putbyte('\n'); + return; + } + floodT = N - 1; +} + /** * @brief add_filter - add/modify filter * @param str - string in format "bank# FIFO# mode num0 .. num3" @@ -414,10 +428,12 @@ const char *helpmsg = "https://github.com/eddyem/stm32samples/tree/master/F0-nolib/usbcan_ringbuffer build#" BUILD_NUMBER " @ " BUILD_DATE "\n" "'a' - add ID to ignore list (max 10 IDs)\n" "'b' - reinit CAN with given baudrate\n" + "'c' - get CAN status\n" "'d' - delete ignore list\n" "'D' - activate DFU mode\n" + "'e' - get CAN errcodes\n" "'f' - add/delete filter, format: bank# FIFO# mode(M/I) num0 [num1 [num2 [num3]]]\n" - "'F' - USB_sendstr/clear flood message: F ID byte0 ... byteN\n" + "'F' - send/clear flood message: F ID byte0 ... byteN\n" "'I' - reinit CAN\n" "'l' - list all active filters\n" "'o' - turn LEDs OFF\n" @@ -425,10 +441,22 @@ const char *helpmsg = "'p' - print ignore buffer\n" "'P' - pause/resume in packets displaying\n" "'R' - software reset\n" - "'s/S' - USB_sendstr data over CAN: s ID byte0 .. byteN\n" + "'s/S' - send data over CAN: s ID byte0 .. byteN\n" + "'t' - change flood period (>=1ms)\n" "'T' - get time from start (ms)\n" ; +TRUE_INLINE void getcanstat(){ + USB_sendstr("CAN_MSR="); + printuhex(CAN->MSR); + USB_sendstr("\nCAN_TSR="); + printuhex(CAN->TSR); + USB_sendstr("\nCAN_RF0R="); + printuhex(CAN->RF0R); + USB_sendstr("\nCAN_RF1R="); + printuhex(CAN->RF1R); +} + /** * @brief cmd_parser - command parsing * @param txt - buffer with commands & data @@ -436,37 +464,48 @@ const char *helpmsg = */ void cmd_parser(char *txt){ char _1st = txt[0]; + ++txt; /* * parse long commands here */ switch(_1st){ case 'a': - addIGN(txt + 1); + addIGN(txt); goto eof; break; case 'b': - CANini(txt + 1); + CANini(txt); goto eof; break; case 'f': - add_filter(txt + 1); + add_filter(txt); goto eof; break; case 'F': - set_flood(parseCANmsg(txt + 1)); + set_flood(parseCANmsg(txt)); goto eof; break; case 's': case 'S': - USB_sendstrCANcommand(txt + 1); + USB_sendstrCANcommand(txt); + goto eof; + break; + case 't': + setfloodt(txt); goto eof; break; } - if(txt[1] != '\n') *txt = '?'; // help for wrong message length + if(*txt != '\n') _1st = '?'; // help for wrong message length switch(_1st){ + case 'c': + getcanstat(); + break; case 'd': IgnSz = 0; break; + case 'e': + printCANerr(); + break; case 'D': USB_sendstr("Go into DFU mode\n"); USB_sendall(); diff --git a/F0:F030,F042,F072/usbcan_ringbuffer/usbcan.bin b/F0:F030,F042,F072/usbcan_ringbuffer/usbcan.bin index bbaa173..570f512 100755 Binary files a/F0:F030,F042,F072/usbcan_ringbuffer/usbcan.bin and b/F0:F030,F042,F072/usbcan_ringbuffer/usbcan.bin differ diff --git a/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.cflags b/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.cflags new file mode 100644 index 0000000..68d5165 --- /dev/null +++ b/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.cflags @@ -0,0 +1 @@ +-std=c17 \ No newline at end of file diff --git a/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.config b/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.config new file mode 100644 index 0000000..0402e5c --- /dev/null +++ b/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.config @@ -0,0 +1,5 @@ +// Add predefined macros for your project here. For example: +// #define THE_ANSWER 42 +#define EBUG +#define STM32F0 +#define STM32F042x6 diff --git a/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.creator b/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.creator new file mode 100644 index 0000000..e94cbbd --- /dev/null +++ b/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.creator @@ -0,0 +1 @@ +[General] diff --git a/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.creator.user b/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.creator.user new file mode 100644 index 0000000..819893c --- /dev/null +++ b/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.creator.user @@ -0,0 +1,160 @@ + + + + + + EnvironmentId + {cf63021e-ef53-49b0-b03b-2f2570cdf3b6} + + + ProjectExplorer.Project.ActiveTarget + 0 + + + ProjectExplorer.Project.EditorSettings + + true + false + true + + Cpp + + CppGlobal + + + + QmlJS + + QmlJSGlobal + + + 2 + KOI8-R + false + 4 + false + 80 + true + true + 1 + false + false + false + 1 + true + true + 0 + 8 + true + false + 2 + true + true + true + *.md, *.MD, Makefile + true + true + + + + ProjectExplorer.Project.PluginSettings + + + true + true + Builtin.DefaultTidyAndClazy + 4 + + + + true + + + + + ProjectExplorer.Project.Target.0 + + Desktop + Desktop + Desktop + {91347f2c-5221-46a7-80b1-0a054ca02f79} + 0 + 0 + 0 + + /home/eddy/Docs/SAO/ELECTRONICS/STM32/F0-srcs/usbcan_ringbuffer + + + + all + + true + GenericProjectManager.GenericMakeStep + + 1 + Сборка + Сборка + ProjectExplorer.BuildSteps.Build + + + + + clean + + true + GenericProjectManager.GenericMakeStep + + 1 + Очистка + Очистка + ProjectExplorer.BuildSteps.Clean + + 2 + false + + false + + По умолчанию + GenericProjectManager.GenericBuildConfiguration + + 1 + + + 0 + Развёртывание + Развёртывание + ProjectExplorer.BuildSteps.Deploy + + 1 + + false + ProjectExplorer.DefaultDeployConfiguration + + 1 + + + 2 + + ProjectExplorer.CustomExecutableRunConfiguration + + false + true + false + true + + 1 + + + + ProjectExplorer.Project.TargetCount + 1 + + + ProjectExplorer.Project.Updater.FileVersion + 22 + + + Version + 22 + + diff --git a/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.cxxflags b/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.cxxflags new file mode 100644 index 0000000..6435dfc --- /dev/null +++ b/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.cxxflags @@ -0,0 +1 @@ +-std=c++17 \ No newline at end of file diff --git a/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.files b/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.files new file mode 100644 index 0000000..f1d9ab8 --- /dev/null +++ b/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.files @@ -0,0 +1,16 @@ +can.c +can.h +hardware.c +hardware.h +main.c +proto.c +proto.h +ringbuffer.c +ringbuffer.h +usb.c +usb.h +usb_defs.h +usb_lib.c +usb_lib.h +usbhw.c +usbhw.h diff --git a/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.includes b/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.includes new file mode 100644 index 0000000..06d1130 --- /dev/null +++ b/F0:F030,F042,F072/usbcan_ringbuffer/usbcanrb.includes @@ -0,0 +1,6 @@ +. +../inc +../inc/Fx +../inc/cm +../inc/ld +../inc/startup diff --git a/F0:F030,F042,F072/usbcan_ringbuffer/version.inc b/F0:F030,F042,F072/usbcan_ringbuffer/version.inc index 57ec54d..154ebc2 100644 --- a/F0:F030,F042,F072/usbcan_ringbuffer/version.inc +++ b/F0:F030,F042,F072/usbcan_ringbuffer/version.inc @@ -1,2 +1,2 @@ -#define BUILD_NUMBER "1" -#define BUILD_DATE "2022-10-28" +#define BUILD_NUMBER "23" +#define BUILD_DATE "2022-12-05" diff --git a/F1:F103/canUART/CANUART.bin b/F1:F103/canUART/CANUART.bin index 67ae620..1ea38a8 100755 Binary files a/F1:F103/canUART/CANUART.bin and b/F1:F103/canUART/CANUART.bin differ diff --git a/F1:F103/canUART/Makefile b/F1:F103/canUART/Makefile index 1f25d88..7d5b885 100644 --- a/F1:F103/canUART/Makefile +++ b/F1:F103/canUART/Makefile @@ -157,6 +157,6 @@ dfuboot: $(BIN) openocd: openocd -f openocd.cfg dbg: - arm-none-eabi-gdb $(ELF) -ex 'target remote localhost:3333' -ex 'monitor reset halt' + arm-none-eabi-gdb $(ELF) -ex 'target extended-remote localhost:3333' -ex 'monitor reset halt' .PHONY: size clean flash boot dfuboot openocd dbg diff --git a/F1:F103/canUART/Readme.md b/F1:F103/canUART/Readme.md index d20e982..43f065c 100644 --- a/F1:F103/canUART/Readme.md +++ b/F1:F103/canUART/Readme.md @@ -1,2 +1,4 @@ CAN bus (PB8/PB9) <> UART1 (PA9/PA10) The same thing as canusb for STM32F0x2 + +Baudrate - 921600 diff --git a/F1:F103/canUART/can.c b/F1:F103/canUART/can.c index 9d31b6f..937d5d8 100644 --- a/F1:F103/canUART/can.c +++ b/F1:F103/canUART/can.c @@ -30,6 +30,7 @@ static CAN_message messages[CAN_INMESSAGE_SIZE]; static uint8_t first_free_idx = 0; // index of first empty cell static int8_t first_nonfree_idx = -1; // index of first data cell static uint16_t oldspeed = 100; // speed of last init +uint32_t floodT = FLOOD_PERIOD_MS-1; // flood period in ms static uint32_t last_err_code = 0; static CAN_status can_status = CAN_STOP; @@ -229,7 +230,7 @@ void can_proc(){ CAN_setup(0); } static uint32_t lastFloodTime = 0; - if(flood_msg && (Tms - lastFloodTime) > (FLOOD_PERIOD_MS-1)){ // flood every ~5ms + if(flood_msg && (Tms - lastFloodTime) > (floodT)){ // flood every ~5ms lastFloodTime = Tms; can_send(flood_msg->data, flood_msg->length, flood_msg->ID); } diff --git a/F1:F103/canUART/can.h b/F1:F103/canUART/can.h index fa09374..4ba1eb6 100644 --- a/F1:F103/canUART/can.h +++ b/F1:F103/canUART/can.h @@ -27,6 +27,7 @@ // incoming message buffer size #define CAN_INMESSAGE_SIZE (8) +extern uint32_t floodT; // CAN message typedef struct{ diff --git a/F1:F103/canUART/main.c b/F1:F103/canUART/main.c index 833e4be..0fb0694 100644 --- a/F1:F103/canUART/main.c +++ b/F1:F103/canUART/main.c @@ -30,9 +30,7 @@ void sys_tick_handler(void){ int main(void){ uint32_t lastT = 0; -#ifdef BLUEPILL uint32_t bplastT = 0; -#endif CAN_message *can_mesg; StartHSE(); SysTick_Config(72000); @@ -50,12 +48,13 @@ int main(void){ LED_off(LED0); lastT = 0; } -#ifdef BLUEPILL if(Tms - bplastT > 499){ + usart_transmit(); +#ifdef BLUEPILL pin_toggle(LEDB_port, LEDB_pin); +#endif bplastT = Tms; } -#endif can_proc(); CAN_status st = CAN_get_status(); if(st == CAN_FIFO_OVERRUN){ @@ -63,30 +62,34 @@ int main(void){ }else if(st == CAN_ERR){ usart_send("Some CAN error occured\n"); } + int errflag = 0; while((can_mesg = CAN_messagebuf_pop())){ + IWDG->KR = IWDG_REFRESH; if(can_mesg && isgood(can_mesg->ID)){ LED_on(LED0); lastT = Tms; if(!lastT) lastT = 1; if(ShowMsgs){ // new data in buff - IWDG->KR = IWDG_REFRESH; uint8_t len = can_mesg->length; printu(Tms); - usart_send(" #"); + if(!usart_send(" #")) errflag = 1; printuhex(can_mesg->ID); for(uint8_t ctr = 0; ctr < len; ++ctr){ - usart_putchar(' '); + if(!usart_putchar(' ')) errflag = 1; printuhex(can_mesg->data[ctr]); } - usart_putchar('\n'); + if(!usart_putchar('\n')) errflag = 1; } } } char *str; int g = usart_getline(&str); - if(g < 0) usart_send("USART buffer overflow!\n"); + if(g < 0) usart_send("USART IN buffer overflow!\n"); else if(g > 0) cmd_parser(str); - usart_transmit(); + if(errflag){ + while(!usart_txrdy) IWDG->KR = IWDG_REFRESH; + usart_send("USART OUT buffer overflow!\n"); + } } return 0; } diff --git a/F1:F103/canUART/proto.c b/F1:F103/canUART/proto.c index aae7b3c..997e7da 100644 --- a/F1:F103/canUART/proto.c +++ b/F1:F103/canUART/proto.c @@ -137,6 +137,7 @@ static char *getbin(const char *buf, uint32_t *N){ char *getnum(const char *txt, uint32_t *N){ char *nxt = NULL; char *s = omit_spaces(txt); + if(!*s) return (char*)txt; if(*s == '0'){ // hex, oct or 0 if(s[1] == 'x' || s[1] == 'X'){ // hex nxt = gethex(s+2, N); @@ -166,7 +167,6 @@ static CAN_message *parseCANmsg(char *txt){ int ctr = -1; canmsg.ID = 0xffff; do{ - txt = omit_spaces(txt); n = getnum(txt, &N); if(txt == n) break; txt = n; @@ -206,14 +206,13 @@ TRUE_INLINE void usart_sendCANcommand(char *txt){ } CAN_message *msg = parseCANmsg(txt); if(!msg) return; - uint32_t N = 3; + uint32_t N = 5; while(CAN_BUSY == can_send(msg->data, msg->length, msg->ID)){ if(--N == 0) break; } } TRUE_INLINE void CANini(char *txt){ - txt = omit_spaces(txt); uint32_t N; char *n = getnum(txt, &N); if(txt == n){ @@ -237,7 +236,6 @@ TRUE_INLINE void addIGN(char *txt){ usart_send("Ignore buffer is full"); return; } - txt = omit_spaces(txt); uint32_t N; char *n = getnum(txt, &N); if(txt == n){ @@ -333,7 +331,6 @@ TRUE_INLINE void list_filters(){ */ static void add_filter(char *str){ uint32_t N; - str = omit_spaces(str); char *n = getnum(str, &N); if(n == str){ usart_send("No bank# given"); @@ -431,6 +428,7 @@ const char *helpmsg = "'P' - pause/resume in packets displaying\n" "'R' - software reset\n" "'s/S' - usart_send data over CAN: s ID byte0 .. byteN\n" + "'t' - change flood period (>=1ms)\n" "'T' - get time from start (ms)\n" ; @@ -445,39 +443,54 @@ TRUE_INLINE void getcanstat(){ printuhex(CAN1->RF1R); } +TRUE_INLINE void setfloodt(char *s){ + uint32_t N; + char *n = getnum(s, &N); + if(s == n || N == 0){ + usart_send("t="); printu(floodT); usart_putchar('\n'); + return; + } + floodT = N - 1; +} + /** * @brief cmd_parser - command parsing * @param txt - buffer with commands & data */ void cmd_parser(char *txt){ char _1st = txt[0]; + ++txt; /* * parse long commands here */ switch(_1st){ case 'a': - addIGN(txt + 1); + addIGN(txt); goto eof; break; case 'b': - CANini(txt + 1); + CANini(txt); goto eof; break; case 'f': - add_filter(txt + 1); + add_filter(txt); goto eof; break; case 'F': - set_flood(parseCANmsg(txt + 1)); + set_flood(parseCANmsg(txt)); goto eof; break; case 's': case 'S': - usart_sendCANcommand(txt + 1); + usart_sendCANcommand(txt); + goto eof; + break; + case 't': + setfloodt(txt); goto eof; break; } - if(txt[1] != '\n') *txt = '?'; // help for wrong message length + if(txt[1] != 0) _1st = '?'; // help for wrong message length switch(_1st){ case 'c': getcanstat(); diff --git a/F1:F103/canUART/usart.c b/F1:F103/canUART/usart.c index 7927473..9c0035b 100644 --- a/F1:F103/canUART/usart.c +++ b/F1:F103/canUART/usart.c @@ -53,11 +53,18 @@ int usart_getline(char **line){ } // transmit current tbuf and swap buffers -void usart_transmit(){ +int usart_transmit(){ register int l = odatalen[tbufno]; - if(!l) return; - uint32_t tmout = 16000000; - while(!usart_txrdy){if(--tmout == 0) return;}; // wait for previos buffer transmission + if(!l) return 0; + uint32_t tmout = 1600000; +/*tbuf[tbufno][0] = '*'; +tbuf[tbufno][1] = '0' + tbufno; +tbuf[tbufno][l-1] = '*'; +tbuf[tbufno][l-2] = '0' + tbufno;*/ + while(!usart_txrdy){ + IWDG->KR = IWDG_REFRESH; + if(--tmout == 0) return 0; + }; // wait for previos buffer transmission usart_txrdy = 0; odatalen[tbufno] = 0; DMA1_Channel4->CCR &= ~DMA_CCR_EN; @@ -65,18 +72,27 @@ void usart_transmit(){ DMA1_Channel4->CNDTR = l; DMA1_Channel4->CCR |= DMA_CCR_EN; tbufno = !tbufno; + return l; } -void usart_putchar(const char ch){ - if(odatalen[tbufno] == UARTBUFSZO) usart_transmit(); - tbuf[tbufno][odatalen[tbufno]++] = ch; -} - -void usart_send(const char *str){ - while(*str){ - if(odatalen[tbufno] == UARTBUFSZO) usart_transmit(); - tbuf[tbufno][odatalen[tbufno]++] = *str++; +int usart_putchar(const char ch){ + if(odatalen[tbufno] == UARTBUFSZO){ + if(!usart_transmit()) return 0; } + tbuf[tbufno][odatalen[tbufno]++] = ch; + return 1; +} + +int usart_send(const char *str){ + int l = 0; + while(*str){ + if(odatalen[tbufno] == UARTBUFSZO){ + if(!usart_transmit()) return 0; + } + tbuf[tbufno][odatalen[tbufno]++] = *str++; + ++l; + } + return l; } /* @@ -102,7 +118,7 @@ void usart_setup(){ NVIC_EnableIRQ(DMA1_Channel4_IRQn); NVIC_SetPriority(USART1_IRQn, 0); // setup usart1 - USART1->BRR = 72000000 / 115200; + USART1->BRR = 72000000 / 921600; USART1->CR1 = USART_CR1_TE | USART_CR1_RE | USART_CR1_UE; // 1start,8data,nstop; enable Rx,Tx,USART while(!(USART1->SR & USART_SR_TC)){if(--tmout == 0) break;} // polling idle frame Transmission USART1->SR = 0; // clear flags @@ -116,15 +132,15 @@ void usart1_isr(){ if(USART1->SR & USART_SR_RXNE){ // RX not emty - receive next char uint8_t rb = USART1->DR; if(idatalen[rbufno] < UARTBUFSZI){ // put next char into buf - rbuf[rbufno][idatalen[rbufno]++] = rb; if(rb == '\n'){ // got newline - line ready + rbuf[rbufno][idatalen[rbufno]] = 0; usart_linerdy = 1; dlen = idatalen[rbufno]; recvdata = rbuf[rbufno]; // prepare other buffer rbufno = !rbufno; idatalen[rbufno] = 0; - } + }else rbuf[rbufno][idatalen[rbufno]++] = rb; }else{ // buffer overrun usart_bufovr = 1; idatalen[rbufno] = 0; diff --git a/F1:F103/canUART/usart.h b/F1:F103/canUART/usart.h index 3d20150..78af94b 100644 --- a/F1:F103/canUART/usart.h +++ b/F1:F103/canUART/usart.h @@ -19,16 +19,16 @@ #pragma once // input and output buffers size -#define UARTBUFSZI (128) -#define UARTBUFSZO (128) +#define UARTBUFSZI (256) +#define UARTBUFSZO (1024) #define usartrx() (usart_linerdy) #define usartovr() (usart_bufovr) extern volatile int usart_txrdy; -void usart_transmit(); +int usart_transmit(); void usart_setup(); int usart_getline(char **line); -void usart_send(const char *str); -void usart_putchar(const char ch); +int usart_send(const char *str); +int usart_putchar(const char ch); diff --git a/F1:F103/canUART/version.inc b/F1:F103/canUART/version.inc index fc513df..a292e52 100644 --- a/F1:F103/canUART/version.inc +++ b/F1:F103/canUART/version.inc @@ -1,2 +1,2 @@ -#define BUILD_NUMBER "64" +#define BUILD_NUMBER "98" #define BUILD_DATE "2022-12-05"