still have unknown problems

This commit is contained in:
eddyem 2023-04-26 23:15:52 +03:00
parent b9cb9f6428
commit 3c7687bb0e
11 changed files with 108 additions and 78 deletions

View File

@ -20,16 +20,17 @@
#include "debug.h" #include "debug.h"
#include "strfunc.h" #include "strfunc.h"
#include "usb.h" #include "usb.h"
#include "usb_lib.h" // USBON
#include "version.inc" #include "version.inc"
#define SEND(str) do{USB_sendstr(CMD_IDX, str);}while(0) #define SEND(str) do{USB_sendstr(CMD_IDX, str);}while(0)
#define SENDN(str) do{USB_sendstr(CMD_IDX, str); USB_putbyte(CMD_IDX, '\n');}while(0) #define SENDN(str) do{USB_sendstr(CMD_IDX, str); USB_putbyte(CMD_IDX, '\n');}while(0)
extern volatile uint32_t Tms; extern volatile uint32_t Tms;
extern uint8_t usbON;
const char* helpmsg = const char* helpmsg =
"https://github.com/eddyem/stm32samples/tree/master/F3:F303/PL2303 build#" BUILD_NUMBER " @ " BUILD_DATE "\n" "https://github.com/eddyem/stm32samples/tree/master/F3:F303/PL2303 build#" BUILD_NUMBER " @ " BUILD_DATE "\n"
"2..7 - send next string to given EP\n"
"'i' - print USB->ISTR state\n" "'i' - print USB->ISTR state\n"
"'N' - read number (dec, 0xhex, 0oct, bbin) and show it in decimal\n" "'N' - read number (dec, 0xhex, 0oct, bbin) and show it in decimal\n"
"'R' - software reset\n" "'R' - software reset\n"
@ -53,8 +54,7 @@ void parse_cmd(const char *buf){
break; break;
case 'U': case 'U':
SEND("USB status: "); SEND("USB status: ");
if(usbON) SENDN("ON"); SENDN(uhex2str(usbON));
else SENDN("OFF");
break; break;
case 'W': case 'W':
SENDN("Wait for reboot"); SENDN("Wait for reboot");
@ -68,9 +68,20 @@ void parse_cmd(const char *buf){
} }
uint32_t Num = 0; uint32_t Num = 0;
const char *nxt; const char *nxt;
switch(*buf){ // long messages char cmd = *buf++;
if(cmd > '0'+CMD_EPNO && cmd <= '0'+DBG_EPNO){ // send data to iface
cmd -= '1';
if(USBON(cmd)){
SENDN("OK");
USB_sendstr(cmd, buf);
USB_putbyte(cmd, '\n');
}else{
SENDN("Not connected");
}
return;
}
switch(cmd){ // long messages
case 'N': case 'N':
++buf;
nxt = getnum(buf, &Num); nxt = getnum(buf, &Num);
if(buf == nxt){ if(buf == nxt){
if(Num == 0) SENDN("Wrong number"); if(Num == 0) SENDN("Wrong number");
@ -84,7 +95,7 @@ void parse_cmd(const char *buf){
}else SEND("\n"); }else SEND("\n");
break; break;
default: default:
SEND(buf); SEND(buf-1); // echo
return; return;
} }
} }

View File

@ -19,6 +19,7 @@
#include "cmdproto.h" #include "cmdproto.h"
#include "debug.h" #include "debug.h"
#include "hardware.h" #include "hardware.h"
#include "strfunc.h"
#include "usart.h" #include "usart.h"
#include "usb.h" #include "usb.h"
@ -30,6 +31,9 @@ void sys_tick_handler(void){
++Tms; ++Tms;
} }
static const char *ebufovr = "ERROR: USB buffer overflow or string was too long\n";
static const char *idxnames[MAX_IDX] = {"CMD", "USART1", "USART2", "USART3", "NOFUNCT", "CAN", "DBG"};
int main(void){ int main(void){
char inbuff[MAXSTRLEN+1]; char inbuff[MAXSTRLEN+1];
USBPU_OFF(); USBPU_OFF();
@ -49,14 +53,32 @@ int main(void){
if(Tms - ctr > 499){ if(Tms - ctr > 499){
ctr = Tms; ctr = Tms;
pin_toggle(GPIOB, 1 << 1 | 1 << 0); // toggle LED @ PB0 pin_toggle(GPIOB, 1 << 1 | 1 << 0); // toggle LED @ PB0
//DBG("blink\n"); //DBGmesg(u2str(Tms));
//DBGnl();
} }
int l = USB_receivestr(CMD_IDX, inbuff, MAXSTRLEN); for(int i = 0; i < MAX_IDX; ++i){
if(l < 0) USB_sendstr(CMD_IDX, "ERROR: USB buffer overflow or string was too long\n"); int l = USB_receivestr(i, inbuff, MAXSTRLEN);
else if(l){ if(l < 0){
USB_sendstr(DBG_IDX, ebufovr);
if(i == CMD_IDX) USB_sendstr(CMD_IDX, ebufovr);
continue;
}
if(l == 0) continue;
USB_sendstr(DBG_IDX, idxnames[i]);
USB_sendstr(DBG_IDX, "> ");
USB_sendstr(DBG_IDX, inbuff);
USB_putbyte(DBG_IDX, '\n');
USB_sendstr(CMD_IDX, idxnames[i]);
USB_sendstr(CMD_IDX, "> ");
USB_sendstr(CMD_IDX, inbuff);
USB_putbyte(CMD_IDX, '\n');
switch(i){
case CMD_IDX:
parse_cmd(inbuff); parse_cmd(inbuff);
break;
default:
break;
}
} }
l = USB_receivestr(DBG_IDX, inbuff, MAXSTRLEN);
if(l) USB_sendstr(DBG_IDX, inbuff); // just echo back all from USB-DBG interface
} }
} }

Binary file not shown.

View File

@ -19,13 +19,14 @@
#include <math.h> #include <math.h>
#include <stm32f3.h> #include <stm32f3.h>
#include <string.h> #include <string.h>
#include "usb.h"
/** /**
* @brief hexdump - dump hex array by 16 bytes in string * @brief hexdump - dump hex array by 16 bytes in string
* @param sendfun - function to send data * @param ifno - USB interface number
* @param arr - array to dump * @param arr - array to dump
* @param len - length of `arr` * @param len - length of `arr`
*/ */
void hexdump(int (*sendfun)(const char *s), uint8_t *arr, uint16_t len){ void hexdump(int ifno, uint8_t *arr, uint16_t len){
char buf[52], *bptr = buf; char buf[52], *bptr = buf;
for(uint16_t l = 0; l < len; ++l, ++arr){ for(uint16_t l = 0; l < len; ++l, ++arr){
for(int16_t j = 1; j > -1; --j){ for(int16_t j = 1; j > -1; --j){
@ -36,14 +37,14 @@ void hexdump(int (*sendfun)(const char *s), uint8_t *arr, uint16_t len){
if(l % 16 == 15){ if(l % 16 == 15){
*bptr++ = '\n'; *bptr++ = '\n';
*bptr = 0; *bptr = 0;
sendfun(buf); USB_sendstr(ifno, buf);
bptr = buf; bptr = buf;
}else *bptr++ = ' '; }else *bptr++ = ' ';
} }
if(bptr != buf){ if(bptr != buf){
*bptr++ = '\n'; *bptr++ = '\n';
*bptr = 0; *bptr = 0;
sendfun(buf); USB_sendstr(ifno, buf);
} }
} }

View File

@ -21,7 +21,7 @@
#include <stdint.h> #include <stdint.h>
#include <string.h> #include <string.h>
void hexdump(int (*sendfun)(const char *s), uint8_t *arr, uint16_t len); void hexdump(int ifno, uint8_t *arr, uint16_t len);
const char *u2str(uint32_t val); const char *u2str(uint32_t val);
const char *i2str(int32_t i); const char *i2str(int32_t i);
const char *uhex2str(uint32_t val); const char *uhex2str(uint32_t val);

View File

@ -36,33 +36,38 @@ volatile uint8_t bufovrfl[WORK_EPs] = {0};
// here and later: ifNo is index of buffers, i.e. ifNo = epno-1 !!! // here and later: ifNo is index of buffers, i.e. ifNo = epno-1 !!!
void send_next(int ifNo){ void send_next(int ifNo){
if(bufisempty[ifNo]) return; if(bufisempty[ifNo]) return;
static int lastdsz = 0; static uint8_t lastdsz[WORK_EPs] = {0};
int buflen = RB_read((ringbuffer*)&rbout[ifNo], (uint8_t*)usbbuff, USB_TRBUFSZ); int buflen = RB_read((ringbuffer*)&rbout[ifNo], (uint8_t*)usbbuff, USB_TRBUFSZ);
if(!buflen){ if(!buflen){
if(lastdsz == 64) EP_Write(ifNo+1, NULL, 0); // send ZLP after 64 bits packet when nothing more to send if(lastdsz[ifNo] == 64) EP_Write(ifNo+1, NULL, 0); // send ZLP after 64 bits packet when nothing more to send
lastdsz = 0; lastdsz[ifNo] = 0;
bufisempty[ifNo] = 1; bufisempty[ifNo] = 1;
return; return;
} }
EP_Write(ifNo+1, (uint8_t*)usbbuff, buflen); EP_Write(ifNo+1, (uint8_t*)usbbuff, buflen);
lastdsz = buflen; lastdsz[ifNo] = buflen;
} }
// blocking send full content of ring buffer // blocking send full content of ring buffer
int USB_sendall(int ifNo){ int USB_sendall(int ifNo){
while(!bufisempty[ifNo]){ while(!bufisempty[ifNo]){
if(!usbON) return 0; if(!USBON(ifNo)) return 0;
} }
return 1; return 1;
} }
// put `buf` into queue to send // put `buf` into queue to send
int USB_send(int ifNo, const uint8_t *buf, int len){ int USB_send(int ifNo, const uint8_t *buf, int len){
if(!buf || !usbON || !len) return 0; if(!buf || !USBON(ifNo) || !len) return 0;
uint32_t T = Tms; uint32_t T = Tms;
while(len){ while(len){
int a = RB_write((ringbuffer*)&rbout[ifNo], buf, len); int a = RB_write((ringbuffer*)&rbout[ifNo], buf, len);
if(a == 0 && Tms - T > 5) return 0; // timeout if(a == 0 && Tms - T > 5){
usbON &= ~(1<<ifNo);
bufisempty[ifNo] = 0;
RB_clearbuf((ringbuffer*)&rbout[ifNo]);
return 0; // timeout - interface is down
}
len -= a; len -= a;
buf += a; buf += a;
if(bufisempty[ifNo]){ if(bufisempty[ifNo]){
@ -74,7 +79,7 @@ int USB_send(int ifNo, const uint8_t *buf, int len){
} }
int USB_putbyte(int ifNo, uint8_t byte){ int USB_putbyte(int ifNo, uint8_t byte){
if(!usbON) return 0; if(!USBON(ifNo)) return 0;
while(0 == RB_write((ringbuffer*)&rbout[ifNo], &byte, 1)){ while(0 == RB_write((ringbuffer*)&rbout[ifNo], &byte, 1)){
if(bufisempty[ifNo]){ if(bufisempty[ifNo]){
bufisempty[ifNo] = 0; bufisempty[ifNo] = 0;
@ -85,7 +90,7 @@ int USB_putbyte(int ifNo, uint8_t byte){
} }
int USB_sendstr(int ifNo, const char *string){ int USB_sendstr(int ifNo, const char *string){
if(!string || !usbON) return 0; if(!string || !USBON(ifNo)) return 0;
int len = 0; int len = 0;
const char *b = string; const char *b = string;
while(*b++) ++len; while(*b++) ++len;

View File

@ -39,12 +39,13 @@
#define USART2_EPNO 3 #define USART2_EPNO 3
#define USART3_EPNO 4 #define USART3_EPNO 4
#define CAN_EPNO 6 #define CAN_EPNO 6
#define DBG_EPNO 7 #define DBG_EPNO 2
#define USARTMAX_EPNO USART3_EPNO #define USARTMAX_EPNO USART3_EPNO
// functional indexes // functional indexes
#define CMD_IDX (CMD_EPNO-1) #define CMD_IDX (CMD_EPNO-1)
#define CAN_IDX (CAN_EPNO-1) #define CAN_IDX (CAN_EPNO-1)
#define DBG_IDX (DBG_EPNO-1) #define DBG_IDX (DBG_EPNO-1)
#define MAX_IDX 7
extern volatile ringbuffer rbout[], rbin[]; extern volatile ringbuffer rbout[], rbin[];
extern volatile uint8_t bufisempty[], bufovrfl[]; extern volatile uint8_t bufisempty[], bufovrfl[];

View File

@ -32,7 +32,7 @@ static uint16_t USB_Addr = 0;
uint8_t ep0databuf[EP0DATABUF_SIZE], setupdatabuf[EP0DATABUF_SIZE]; uint8_t ep0databuf[EP0DATABUF_SIZE], setupdatabuf[EP0DATABUF_SIZE];
config_pack_t *setup_packet = (config_pack_t*) setupdatabuf; config_pack_t *setup_packet = (config_pack_t*) setupdatabuf;
volatile uint8_t usbON = 0; // device disconnected from terminal volatile uint8_t usbON = 0;
// definition of parts common for USB_DeviceDescriptor & USB_DeviceQualifierDescriptor // definition of parts common for USB_DeviceDescriptor & USB_DeviceQualifierDescriptor
#define bcdUSB_L 0x00 #define bcdUSB_L 0x00
@ -95,8 +95,8 @@ static const uint8_t USB_ConfigDescriptor[] = {
0x02, // bInterfaceCount 0x02, // bInterfaceCount
0x02, // bFunctionClass: CDC 0x02, // bFunctionClass: CDC
0x02, // bFunctionSubClass 0x02, // bFunctionSubClass
0x01, // bFunctionProtocol (0 or 1?) 0x00, // bFunctionProtocol
0x02, // Interface string index 0x00, // iFunction
/*---------------------------------------------------------------------------*/ /*---------------------------------------------------------------------------*/
/* Interface Descriptor */ /* Interface Descriptor */
0x09, /* bLength: Interface Descriptor size */ 0x09, /* bLength: Interface Descriptor size */
@ -176,8 +176,8 @@ static const uint8_t USB_ConfigDescriptor[] = {
0x02, // bInterfaceCount 0x02, // bInterfaceCount
0x02, // bFunctionClass: CDC 0x02, // bFunctionClass: CDC
0x02, // bFunctionSubClass 0x02, // bFunctionSubClass
0x01, // bFunctionProtocol (0 or 1?) 0x00, // bFunctionProtocol
0x02, // iFunction 0x00, // iFunction
/*---------------------------------------------------------------------------*/ /*---------------------------------------------------------------------------*/
/*Interface Descriptor */ /*Interface Descriptor */
0x09, /* bLength: Interface Descriptor size */ 0x09, /* bLength: Interface Descriptor size */
@ -257,8 +257,8 @@ static const uint8_t USB_ConfigDescriptor[] = {
0x02, // bInterfaceCount 0x02, // bInterfaceCount
0x02, // bFunctionClass: CDC 0x02, // bFunctionClass: CDC
0x02, // bFunctionSubClass 0x02, // bFunctionSubClass
0x01, // bFunctionProtocol (0 or 1?) 0x00, // bFunctionProtocol
0x02, // iFunction 0x00, // iFunction
/*---------------------------------------------------------------------------*/ /*---------------------------------------------------------------------------*/
/*Interface Descriptor */ /*Interface Descriptor */
0x09, /* bLength: Interface Descriptor size */ 0x09, /* bLength: Interface Descriptor size */
@ -338,8 +338,8 @@ static const uint8_t USB_ConfigDescriptor[] = {
0x02, // bInterfaceCount 0x02, // bInterfaceCount
0x02, // bFunctionClass: CDC 0x02, // bFunctionClass: CDC
0x02, // bFunctionSubClass 0x02, // bFunctionSubClass
0x01, // bFunctionProtocol (0 or 1?) 0x00, // bFunctionProtocol
0x02, // iFunction 0x00, // iFunction
/*---------------------------------------------------------------------------*/ /*---------------------------------------------------------------------------*/
/*Interface Descriptor */ /*Interface Descriptor */
0x09, /* bLength: Interface Descriptor size */ 0x09, /* bLength: Interface Descriptor size */
@ -419,8 +419,8 @@ static const uint8_t USB_ConfigDescriptor[] = {
0x02, // bInterfaceCount 0x02, // bInterfaceCount
0x02, // bFunctionClass: CDC 0x02, // bFunctionClass: CDC
0x02, // bFunctionSubClass 0x02, // bFunctionSubClass
0x01, // bFunctionProtocol (0 or 1?) 0x00, // bFunctionProtocol
0x02, // iFunction 0x00, // iFunction
/*---------------------------------------------------------------------------*/ /*---------------------------------------------------------------------------*/
/*Interface Descriptor */ /*Interface Descriptor */
0x09, /* bLength: Interface Descriptor size */ 0x09, /* bLength: Interface Descriptor size */
@ -500,8 +500,8 @@ static const uint8_t USB_ConfigDescriptor[] = {
0x02, // bInterfaceCount 0x02, // bInterfaceCount
0x02, // bFunctionClass: CDC 0x02, // bFunctionClass: CDC
0x02, // bFunctionSubClass 0x02, // bFunctionSubClass
0x01, // bFunctionProtocol (0 or 1?) 0x00, // bFunctionProtocol
0x02, // iFunction 0x00, // iFunction
/*---------------------------------------------------------------------------*/ /*---------------------------------------------------------------------------*/
/*Interface Descriptor */ /*Interface Descriptor */
0x09, /* bLength: Interface Descriptor size */ 0x09, /* bLength: Interface Descriptor size */
@ -581,8 +581,8 @@ static const uint8_t USB_ConfigDescriptor[] = {
0x02, // bInterfaceCount 0x02, // bInterfaceCount
0x02, // bFunctionClass: CDC 0x02, // bFunctionClass: CDC
0x02, // bFunctionSubClass 0x02, // bFunctionSubClass
0x01, // bFunctionProtocol (0 or 1?) 0x00, // bFunctionProtocol
0x02, // iFunction 0x00, // iFunction
/*---------------------------------------------------------------------------*/ /*---------------------------------------------------------------------------*/
/*Interface Descriptor */ /*Interface Descriptor */
0x09, /* bLength: Interface Descriptor size */ 0x09, /* bLength: Interface Descriptor size */
@ -681,24 +681,6 @@ static void const *StringDescriptor[iDESCR_AMOUNT] = {
[iINTERFACE_DESCR_DBG] = &ID6 [iINTERFACE_DESCR_DBG] = &ID6
}; };
/*
* default handlers
*/
// SET_LINE_CODING
static void linecoding_handler(int ifNo, usb_LineCoding *lc){
if(ifNo < USART1_EPNO || ifNo > USARTMAX_EPNO) return;
usart_config(ifNo + 1 - USART1_EPNO, lc);
}
// SET_CONTROL_LINE_STATE
static void clstate_handler(int __attribute__((unused)) ifNo, uint16_t __attribute__((unused)) val){
}
// SEND_BREAK
static void break_handler(int __attribute__((unused)) ifNo){
}
static void wr0(const uint8_t *buf, uint16_t size){ static void wr0(const uint8_t *buf, uint16_t size){
if(setup_packet->wLength < size) size = setup_packet->wLength; // shortened request if(setup_packet->wLength < size) size = setup_packet->wLength; // shortened request
if(size < endpoints[0].txbufsz){ if(size < endpoints[0].txbufsz){
@ -772,17 +754,20 @@ static void rxtx_Handler(uint8_t epno){
uint8_t buf[USB_TRBUFSZ]; uint8_t buf[USB_TRBUFSZ];
int idx = epno - 1; int idx = epno - 1;
uint16_t epstatus = KEEP_DTOG(USB->EPnR[epno]); uint16_t epstatus = KEEP_DTOG(USB->EPnR[epno]);
DBGmesg("RxTx="); DBGmesg(u2str(epno)); //uint16_t epstatus = USB->EPnR[epno];
DBGmesg(", epst="); DBGmesg(u2str(epstatus)); DBGnl();
if(RX_FLAG(epstatus)){ if(RX_FLAG(epstatus)){
epstatus = (epstatus & ~(USB_EPnR_STAT_TX|USB_EPnR_CTR_RX)) ^ USB_EPnR_STAT_RX; // keep stat Tx & set valid RX, clear CTR Rx
USB->EPnR[epno] = epstatus;
//USB->EPnR[epno] = (KEEP_DTOG(epstatus) & ~USB_EPnR_CTR_RX) ^ USB_EPnR_STAT_RX;
uint8_t sz = EP_Read(epno, (uint8_t*)buf); uint8_t sz = EP_Read(epno, (uint8_t*)buf);
if(sz){ if(sz){
if(RB_write((ringbuffer*)&rbin[idx], buf, sz) != sz) bufovrfl[idx] = 1; if(RB_write((ringbuffer*)&rbin[idx], buf, sz) != sz) bufovrfl[idx] = 1;
} }
epstatus = (epstatus & ~(USB_EPnR_STAT_TX|USB_EPnR_CTR_RX)) ^ USB_EPnR_STAT_RX; // keep stat Tx & set valid RX, clear CTR Rx // set ACK Rx
USB->EPnR[epno] = epstatus; USB->EPnR[epno] = (KEEP_DTOG(USB->EPnR[epno]) & ~(USB_EPnR_STAT_TX)) ^ USB_EPnR_STAT_RX;
}else{ }else{
USB->EPnR[epno] = (epstatus & ~(USB_EPnR_CTR_TX)); // clear TX ctr USB->EPnR[epno] = (epstatus & ~(USB_EPnR_STAT_TX|USB_EPnR_CTR_TX)) ^ USB_EPnR_STAT_RX; // clear TX ctr
//USB->EPnR[epno] = (KEEP_DTOG_STAT(epstatus) & ~(USB_EPnR_CTR_TX)); // clear TX ctr
send_next(idx); send_next(idx);
} }
} }
@ -799,7 +784,6 @@ static inline void std_h2d_req(){
for(uint8_t i = 1; i <= WORK_EPs; ++i){ for(uint8_t i = 1; i <= WORK_EPs; ++i){
EP_Init(i, EP_TYPE_BULK, USB_TRBUFSZ, USB_TRBUFSZ, rxtx_Handler); EP_Init(i, EP_TYPE_BULK, USB_TRBUFSZ, USB_TRBUFSZ, rxtx_Handler);
} }
usbON = 1;
break; break;
default: default:
break; break;
@ -823,6 +807,8 @@ void EP0_Handler(uint8_t __attribute__((unused)) epno){
usb_LineCoding *lc; usb_LineCoding *lc;
// calculate iFno (EP number minus 1) by setup_packet->wIndex (bInterfaceNumber): iFno = wIndex >> 1 // calculate iFno (EP number minus 1) by setup_packet->wIndex (bInterfaceNumber): iFno = wIndex >> 1
int iFno = setup_packet->wIndex >> 1; int iFno = setup_packet->wIndex >> 1;
DBGmesg(uhex2str(epstatus));
DBGmesg(" - "); hexdump(DBG_IDX, (uint8_t*)setup_packet, sizeof(config_pack_t));
if(rxflag && SETUP_FLAG(epstatus)){ if(rxflag && SETUP_FLAG(epstatus)){
switch(reqtype){ switch(reqtype){
case STANDARD_DEVICE_REQUEST_TYPE: // standard device request case STANDARD_DEVICE_REQUEST_TYPE: // standard device request
@ -841,22 +827,24 @@ void EP0_Handler(uint8_t __attribute__((unused)) epno){
case CONTROL_REQUEST_TYPE: case CONTROL_REQUEST_TYPE:
switch(setup_packet->bRequest){ switch(setup_packet->bRequest){
case GET_LINE_CODING: case GET_LINE_CODING:
DBG("GET_LINE_CODING from"); DBGmesg(u2str(iFno)); DBGnl(); DBG("GLC");
lc = getLineCoding(iFno); lc = getLineCoding(iFno);
if(!lc) EP_WriteIRQ(0, (uint8_t *)0, 0); if(!lc) EP_WriteIRQ(0, (uint8_t *)0, 0);
else EP_WriteIRQ(0, (uint8_t*)&lc, sizeof(usb_LineCoding)); else EP_WriteIRQ(0, (uint8_t*)&lc, sizeof(usb_LineCoding));
break; break;
case SET_LINE_CODING: // omit this for next stage, when data will come case SET_LINE_CODING: // omit this for next stage, when data will come
DBG("SLC");
break; break;
case SET_CONTROL_LINE_STATE: case SET_CONTROL_LINE_STATE:
DBG("SET_CONTROL_LINE_STATE from"); DBGmesg(u2str(iFno)); DBGnl(); DBG("SCLS");
clstate_handler(iFno, setup_packet->wValue); usbON |= 1 << iFno; // now this interface is connected
break; break;
case SEND_BREAK: case SEND_BREAK:
DBG("SEND_BREAK from"); DBGmesg(u2str(iFno)); DBGnl(); DBG("B");
break_handler(iFno); usbON &= ~(1<<iFno); // interface is disconnected
break; break;
default: default:
DBG("U");
break; break;
} }
if(setup_packet->bRequest != GET_LINE_CODING) EP_WriteIRQ(0, (uint8_t *)0, 0); // write acknowledgement if(setup_packet->bRequest != GET_LINE_CODING) EP_WriteIRQ(0, (uint8_t *)0, 0); // write acknowledgement
@ -867,15 +855,13 @@ void EP0_Handler(uint8_t __attribute__((unused)) epno){
}else if(rxflag){ // got data over EP0 or host acknowlegement }else if(rxflag){ // got data over EP0 or host acknowlegement
if(endpoints[0].rx_cnt){ if(endpoints[0].rx_cnt){
if(setup_packet->bRequest == SET_LINE_CODING){ if(setup_packet->bRequest == SET_LINE_CODING){
DBG("SET_LINE_CODING from"); DBGmesg(u2str(iFno)); DBGnl(); usart_config(iFno + 1 - USART1_EPNO, (usb_LineCoding*)ep0databuf);
linecoding_handler(iFno, (usb_LineCoding*)ep0databuf);
} }
} }
} else if(TX_FLAG(epstatus)){ // package transmitted } else if(TX_FLAG(epstatus)){ // package transmitted
// now we can change address after enumeration // now we can change address after enumeration
if ((USB->DADDR & USB_DADDR_ADD) != USB_Addr){ if ((USB->DADDR & USB_DADDR_ADD) != USB_Addr){
USB->DADDR = USB_DADDR_EF | USB_Addr; USB->DADDR = USB_DADDR_EF | USB_Addr;
usbON = 0;
} }
} }
epstatus = KEEP_DTOG(USB->EPnR[0]); epstatus = KEEP_DTOG(USB->EPnR[0]);

View File

@ -153,6 +153,8 @@ typedef struct {
} __attribute__ ((packed)) usb_LineCoding; } __attribute__ ((packed)) usb_LineCoding;
extern ep_t endpoints[]; extern ep_t endpoints[];
// device disconnected from terminal (BIT flags!!!)
#define USBON(ifno) (usbON & (1<<ifno))
extern volatile uint8_t usbON; extern volatile uint8_t usbON;
extern config_pack_t *setup_packet; extern config_pack_t *setup_packet;
extern uint8_t ep0databuf[], setupdatabuf[]; extern uint8_t ep0databuf[], setupdatabuf[];

View File

@ -75,6 +75,7 @@ int EP_Init(uint8_t number, uint8_t type, uint16_t txsz, uint16_t rxsz, void (*f
// standard IRQ handler // standard IRQ handler
void usb_lp_isr(){ void usb_lp_isr(){
static uint8_t oldusbon = 0; // to store flags while suspended
if(USB->ISTR & USB_ISTR_RESET){ if(USB->ISTR & USB_ISTR_RESET){
usbON = 0; usbON = 0;
// Reinit registers // Reinit registers
@ -111,6 +112,7 @@ void usb_lp_isr(){
if(endpoints[n].func) endpoints[n].func(n); if(endpoints[n].func) endpoints[n].func(n);
} }
if(USB->ISTR & USB_ISTR_SUSP){ // suspend -> still no connection, may sleep if(USB->ISTR & USB_ISTR_SUSP){ // suspend -> still no connection, may sleep
oldusbon = usbON;
usbON = 0; usbON = 0;
USB->CNTR |= USB_CNTR_FSUSP | USB_CNTR_LP_MODE; USB->CNTR |= USB_CNTR_FSUSP | USB_CNTR_LP_MODE;
USB->ISTR = ~USB_ISTR_SUSP; USB->ISTR = ~USB_ISTR_SUSP;
@ -118,7 +120,7 @@ void usb_lp_isr(){
if(USB->ISTR & USB_ISTR_WKUP){ // wakeup if(USB->ISTR & USB_ISTR_WKUP){ // wakeup
USB->CNTR &= ~(USB_CNTR_FSUSP | USB_CNTR_LP_MODE); // clear suspend flags USB->CNTR &= ~(USB_CNTR_FSUSP | USB_CNTR_LP_MODE); // clear suspend flags
USB->ISTR = ~USB_ISTR_WKUP; USB->ISTR = ~USB_ISTR_WKUP;
usbON = 1; usbON = oldusbon;
} }
} }

View File

@ -1,2 +1,2 @@
#define BUILD_NUMBER "56" #define BUILD_NUMBER "77"
#define BUILD_DATE "2023-04-23" #define BUILD_DATE "2023-04-26"