// >>>>>>>>>>>>>>>>>>>>>>> COPYRIGHT NOTICE <<<<<<<<<<<<<<<<<<<<<<<<< // ------------------------------------------------------------------ // Copyright (c) 2019-2023 by Lattice Semiconductor Corporation // ALL RIGHTS RESERVED // ------------------------------------------------------------------ // // IMPORTANT: THIS FILE IS USED BY OR GENERATED BY the LATTICE PROPEL™ // DEVELOPMENT SUITE, WHICH INCLUDES PROPEL BUILDER AND PROPEL SDK. // // Lattice grants permission to use this code pursuant to the // terms of the Lattice Propel License Agreement. // // DISCLAIMER: // // LATTICE MAKES NO WARRANTIES ON THIS FILE OR ITS CONTENTS, WHETHER // EXPRESSED, IMPLIED, STATUTORY, OR IN ANY PROVISION OF THE LATTICE // PROPEL LICENSE AGREEMENT OR COMMUNICATION WITH LICENSEE, AND LATTICE // SPECIFICALLY DISCLAIMS ANY IMPLIED WARRANTY OF MERCHANTABILITY OR // FITNESS FOR A PARTICULAR PURPOSE. LATTICE DOES NOT WARRANT THAT THE // FUNCTIONS CONTAINED HEREIN WILL MEET LICENSEE'S REQUIREMENTS, OR THAT // LICENSEE'S OPERATION OF ANY DEVICE, SOFTWARE OR SYSTEM USING THIS FILE // OR ITS CONTENTS WILL BE UNINTERRUPTED OR ERROR FREE, OR THAT DEFECTS // HEREIN WILL BE CORRECTED. LICENSEE ASSUMES RESPONSIBILITY FOR // SELECTION OF MATERIALS TO ACHIEVE ITS INTENDED RESULTS, AND FOR THE // PROPER INSTALLATION, USE, AND RESULTS OBTAINED THEREFROM. LICENSEE // ASSUMES THE ENTIRE RISK OF THE FILE AND ITS CONTENTS PROVING DEFECTIVE // OR FAILING TO PERFORM PROPERLY AND IN SUCH EVENT, LICENSEE SHALL // ASSUME THE ENTIRE COST AND RISK OF ANY REPAIR, SERVICE, CORRECTION, OR // ANY OTHER LIABILITIES OR DAMAGES CAUSED BY OR ASSOCIATED WITH THE // SOFTWARE. IN NO EVENT SHALL LATTICE BE LIABLE TO ANY PARTY FOR DIRECT, // INDIRECT,SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES, INCLUDING LOST // PROFITS, ARISING OUT OF THE USE OF THIS FILE OR ITS CONTENTS, EVEN IF // LATTICE HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES. LATTICE'S // SOLE LIABILITY, AND LICENSEE'S SOLE REMEDY, IS SET FORTH ABOVE. // LATTICE DOES NOT WARRANT OR REPRESENT THAT THIS FILE, ITS CONTENTS OR // USE THEREOF DOES NOT INFRINGE ON THIRD PARTIES' INTELLECTUAL PROPERTY // RIGHTS, INCLUDING ANY PATENT. IT IS THE USER'S RESPONSIBILITY TO VERIFY // THE USER SOFTWARE DESIGN FOR CONSISTENCY AND FUNCTIONALITY THROUGH THE // USE OF FORMAL SOFTWARE VALIDATION METHODS. // ------------------------------------------------------------------ #include "uart.h" #include "pic.h" #include "utils.h" #include #include // RISC V Addresses #define RISCV_USB_CONFIGURATION_ADDRESS 0x00100000 #define RISCV_EVENT_BUFFER_ADDRESS 0x00200000 #define RISCV_TRB_BUFFER_ADDRESS 0x00300000 #define RISCV_REQUEST_BUFFER_ADDRESS 0x00400000 #define RISCV_DESCRIPTOR_BUFFER_ADDRESS 0x00500000 // USB23 Addresses #define USB23_EVENT_ADDRESS 0x00000010 #define SETUP_PACKET_ADDRESS 0x0004ff00 #define USB23_TRB_ADDRESS 0x00001000 #define USB23_DESCRIPTOR_ADDRESS 0x00050000 #define USB23_BULK_ADDRESS 0x00060000 #define USB23_CONTROL_ADDRESS 0x00070000 #define USB23_INTERRUPT_ADDRESS 0x00080000 // Size of Bulk and Interrupt TRBs #define SIZE_OF_INTERRUPT_IN_HS_DATA 0x400 //1024 #define SIZE_OF_SS_DATA 0x400 //1024 #define SIZE_OF_INTERRUPT_IN_FS_DATA 0x40 //64 #define SIZE_OF_INTERRUPT_OUT_HS_DATA 0x400 //1024 #define SIZE_OF_INTERRUPT_OUT_FS_DATA 0x40 //64 #define SIZE_OF_BULK_IN_HS_DATA 0x200 //512 #define SIZE_OF_BULK_IN_FS_DATA 0x40 //64 #define SIZE_OF_BULK_OUT_HS_DATA 0x200 //512 #define SIZE_OF_BULK_OUT_FS_DATA 0x40 //64 //Suspend enable #define SUSPEND_MODE_EN 0 // Simulation Parameter #define SIM_EN 0 // External Clock Parameter #define EXT_CLK_EN 0 // High speed - 0x0 // Full speed - 0x1 // Super speed - 0x4 #define USB_SPEED 0x4 //UART Print enable #define UART_EN 1 unsigned int Connect_Speed; unsigned int bconfiguration_value; // Device Descriptor unsigned int Device_SS_data[] = { 0x03200112, 0x09FFFFFF, 0x20C82AC1, 0x02010600,0x00000103, 0x00000000 }; unsigned int Device_data[] = { 0x02000112, 0x40FFFFFF, 0x20C82AC1, 0x02010600,0x00000103, 0x00000000 }; unsigned int Device_Hub_data[] = { 0x02100112, 0x40FFFFFF, 0x20C82AC1, 0x02010600,0x00000103, 0x00000000 }; unsigned int Device_Data_Buffer_size = (sizeof(Device_data) / 4); unsigned int Device_Descriptor_size = 0x12; //BOS Descriptor unsigned int BOS_Descriptor_data[] = { 0x00160f05, 0x00000002}; unsigned int BOS_Descriptor_Data_Buffer_size = (sizeof(BOS_Descriptor_data) / 4); unsigned int BOS_Descriptor_size = 0x05; //BOS + Device Capability Descriptor unsigned int BOS_Device_Capability_Descriptor_data[] = { 0x00160f05, 0x02100702, 0x00000002, 0x0003100a, 0x0a02000e, 0x000007ff}; unsigned int BOS_Device_Capability_Descriptor_Data_Buffer_size = (sizeof(BOS_Device_Capability_Descriptor_data) / 4); unsigned int BOS_Device_Capability_Descriptor_size = 0x16; // Device Qualifier Descriptor unsigned int Device_Qualifier_data[] = { 0x0200060A, 0x40ffffff, 0x00000001,0x00000000 }; unsigned int Device_Qualifier_Data_Buffer_size = (sizeof(Device_Qualifier_data) / 4); unsigned int Device_Qualifier_Descriptor_size = 0xA; // Other Speed Configuartion Descriptor unsigned int Other_Speed_Configuartion_data[] = { 0x002e0709, 0xc0000101, 0x000000fa,0x00000000 }; unsigned int Other_Speed_Configuartion_Data_Buffer_size = (sizeof(Other_Speed_Configuartion_data) / 4); unsigned int Other_Speed_Configuartion_Descriptor_size = 0x09; // Other Speed Configuartion + Interface + Endpoint Descriptor unsigned int Other_Speed_Configuartion_Interface_Endpoint_data[] = { 0x002e0709, 0xc0000101, 0x000409fa, 0xffff0400, 0x050700ff, 0x00400281, 0x01050700, 0x00004002, 0x03850507, 0x07010040, 0x40030505, 0x00000100 }; unsigned int Other_Speed_Configuartion_Interface_Endpoint_Data_Buffer_size = (sizeof(Other_Speed_Configuartion_Interface_Endpoint_data) / 4); unsigned int Other_Speed_Configuartion_Interface_Endpoint_Descriptor_size = 0x2e; // Configuration Descriptor (Bulk + Interrupt) unsigned int Configuration_data[] = { 0x002e0209, 0xc0000101, 0x000000fa,0x00000000 }; //added for usb 3.0 unsigned int Configuration_SS_data[] = { 0x00460209, 0xc0000101, 0x000000fa,0x00000000 }; unsigned int Configuration_Data_Buffer_size = (sizeof(Configuration_data) / 4); unsigned int Configuration_Descriptor_size = 0x9; // Configuration + Interface + Endpoint Descriptor (Bulk + Interrupt) unsigned int Configuration_Interface_Endpoint_HS_data[] = { 0x002e0209, 0xc0000101, 0x000409fa, 0xffff0400, 0x050700ff, 0x02000281, 0x01050700, 0x00020002, 0x03850507, 0x07010400, 0x00030505, 0x00000104 }; unsigned int Configuration_Interface_Endpoint_FS_data[] = { 0x002e0209, 0xc0000101, 0x000409fa, 0xffff0400, 0x050700ff, 0x00400281, 0x01050700, 0x00004002, 0x03850507, 0x07010040, 0x40030505, 0x00000100 }; //added for usb 3.0 unsigned int Configuration_Interface_Endpoint_SS_data[] = { 0x00460209, 0xc0000101, 0x000409fa, 0xffff0400, 0x050700ff, 0x04000281, 0x03300600, 0x07000000, 0x00020105, 0x30060004,0x0000003,0x03850507,0x06010400,0x00000030,0x05050700,0x01040003,0x00003006,0x00000000 }; unsigned int Configuration_Interface_Endpoint_data_Buffer_size = (sizeof(Configuration_Interface_Endpoint_FS_data) / 4); unsigned int Configuration_Interface_Endpoint_SS_data_Buffer_size = (sizeof(Configuration_Interface_Endpoint_SS_data) / 4); //added for usb 3.0 unsigned int Configuration_Interface_Endpoint_Descriptor_SS_size = 0x46; unsigned int Configuration_Interface_Endpoint_Descriptor_size = 0x2e; // String Language Descriptor unsigned int String_Language_data[] = { 0x04090304, 0x00000000 }; unsigned int String_Language_Data_Buffer_size = (sizeof(String_Language_data) / 4); unsigned int String_Language_Descriptor_size = 0x4; // String Index 1 Descriptor (Lattice Vendor Specific Device) unsigned int String_Index1_data[] = { 0x004c033e, 0x00740061, 0x00690074, 0x00650063, 0x00560020, 0x006e0065, 0x006f0064, 0x00200072, 0x00700053, 0x00630065, 0x00660069, 0x00630069, 0x00440020, 0x00760065, 0x00630069, 0x00000065 }; unsigned int String_Index1_Data_Buffer_size = (sizeof(String_Index1_data) / 4); unsigned int String_Index1_Descriptor_size = 0x3e; // String Index 2 Descriptor (Lattice Vendor Specific Device) unsigned int String_Index2_data[] = { 0x004c033e, 0x00740061, 0x00690074, 0x00650063, 0x00560020, 0x006e0065, 0x006f0064, 0x00200072, 0x00700053, 0x00630065, 0x00660069, 0x00630069, 0x00440020, 0x00760065, 0x00630069, 0x00000065 }; unsigned int String_Index2_Data_Buffer_size = (sizeof(String_Index2_data) / 4); unsigned int String_Index2_Descriptor_size = 0x3e; // String Index 3 Descriptor (Lattice Vendor Specific Device) unsigned int String_Index3_data[] = { 0x004c033e, 0x00740061, 0x00690074, 0x00650063, 0x00560020, 0x006e0065, 0x006f0064, 0x00200072, 0x00700053, 0x00630065, 0x00660069, 0x00630069, 0x00440020, 0x00760065, 0x00630069, 0x00000065 }; unsigned int String_Index3_Data_Buffer_size = (sizeof(String_Index3_data) / 4); unsigned int String_Index3_Descriptor_size = 0x3e; int Request_Buffer_interrupt_flag; int Event_Buffer_interrupt_flag; struct uart_instance uart_core_uart; static int lscc_uart_putc(char c, FILE *file) { #ifdef LSCC_STDIO_UART_APB int ret = EOF; ret = uart_putc(&uart_core_uart, c); if (c == '\n' && ret == 0) ret = uart_putc(&uart_core_uart, '\r'); return ret; #else return EOF; #endif } static int lscc_uart_getc(FILE *file) { (void) file; return EOF; } static int lscc_uart_flush(FILE *file) { (void) file; return 0; } // ----------------------------------------------------------- // Device Physical Endpoint-Specific Command Structure // ----------------------------------------------------------- // DEPSTARTCFG -- Device EndPoint Start Configuration -- 0x9 -- No Parameters are required void DEPSTARTCFG(unsigned int ep_number) { unsigned int data; reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c80c + 16 * ep_number,0x00000409); // Poll for CmdAct reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c80c + 16 * ep_number, &data); while ((data & (0x00000400)) != 0x00000000) reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c80c + 16 * ep_number, &data); } // DEPSTRTXFER -- Device End Point Start Transfer Resource Configuration -- 0x6 -- 64 bit Parameter void DEPSTRTXFER(unsigned int ep_number, unsigned int parameter1, unsigned int parameter0) { unsigned int data; reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000C804 + 16 * ep_number, parameter1); reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000C808 + 16 * ep_number, parameter0); reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000C80C + 16 * ep_number, 0x00000406); // Poll for CmdAct reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000C80C + 16 * ep_number, &data); while ((data & (0x00000400)) != 0x00000000) reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000C80C + 16 * ep_number, &data); } // DEPENDXFER -- Device End Point End Transfer command void DEPENDXFER() { unsigned int data; reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000C80C, 0x00000D08); // Poll for CmdAct reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000C80C, &data); while ((data & (0x00000400)) != 0x00000000) reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x00000C80C, &data); } // DEPCFG -- Set EndPoint Configuration -- Device EndPoint Configuration -- 0x1 -- 64 or 96 bit Parameters void DEPCFG(unsigned int ep_number, unsigned int parameter2, unsigned int parameter1, unsigned int parameter0) { unsigned int data; reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c800 + 16 * ep_number, parameter2); reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c804 + 16 * ep_number, parameter1); reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c808 + 16 * ep_number, parameter0); reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c80c + 16 * ep_number, 0x00000401); // Poll for CmdAct reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c80c + 16 * ep_number, &data); while ((data & (0x00000400)) != 0x00000000) reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c80c + 16 * ep_number, &data); } // DEPXFERCFG -- Device End Point Transfer Resource Configuration -- 0x2 -- 32 bit Parameter void DEPXFERCFG(unsigned int ep_number) { unsigned int data; reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c808 + 16 * ep_number, 0x00000001); reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c80c + 16 * ep_number, 0x00000402); // Poll for CmdAct reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c80c + 16 * ep_number, &data); while ((data & (0x00000400)) != 0x00000000) reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c80c + 16 * ep_number, &data); } // DEPSSTALL -- Device End Point Stall void DEPSSTALL(unsigned int ep_number) { unsigned int data; reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c80c + 16 * ep_number, 0x00000404); // Poll for CmdAct reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c80c + 16 * ep_number, &data); while ((data & (0x00000400)) != 0x00000000) reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c80c + 16 * ep_number, &data); } // ----------------------------------------------------------- // Buffer Setting Commands // ----------------------------------------------------------- // TRB Buffer void TRB_buffer_set(unsigned int address_low, unsigned int address_high, unsigned int buffer_size, unsigned int TRB_parameter) { reg_32b_write(RISCV_TRB_BUFFER_ADDRESS, address_low); reg_32b_write(RISCV_TRB_BUFFER_ADDRESS, address_high); reg_32b_write(RISCV_TRB_BUFFER_ADDRESS, buffer_size); reg_32b_write(RISCV_TRB_BUFFER_ADDRESS, TRB_parameter); } // Descriptor Buffer void Descriptor_buffer_set(unsigned int size, unsigned int data[]) { int i; for (i = 0; i < size; i = i + 1) { reg_32b_write(RISCV_DESCRIPTOR_BUFFER_ADDRESS, data[i]); } } // ----------------------------------------------------------- // TRB's for Different Packets // ----------------------------------------------------------- // Control Setup void TRB_Control_setup() { TRB_buffer_set(SETUP_PACKET_ADDRESS, 0x00000000, 0x00000008, 0x00000823); DEPSTRTXFER(0x0, USB23_TRB_ADDRESS, 0x00000000); } // Control Data void TRB_Control_Data(unsigned int Size_of_descriptor, unsigned int data_buffer_size, unsigned int descriptor_data[]) { TRB_buffer_set(USB23_DESCRIPTOR_ADDRESS, 0x00000000, Size_of_descriptor, 0x00000853); Descriptor_buffer_set(data_buffer_size,descriptor_data); DEPSTRTXFER(0x1, USB23_TRB_ADDRESS, 0x00000000); } // Control Status 2 void TRB_Control_Status2() { TRB_buffer_set(USB23_TRB_ADDRESS, 0x00000000, 0x00000000, 0x00000833); DEPSTRTXFER(0x1, USB23_TRB_ADDRESS, 0x00000000); } // Control Status 3 void TRB_Control_Status3(unsigned int direction) { TRB_buffer_set(USB23_TRB_ADDRESS, 0x00000000, 0x00000000, 0x00000843); DEPSTRTXFER(0x0 + direction, USB23_TRB_ADDRESS, 0x00000000); } // ----------------------------------------------------------- // Others // ----------------------------------------------------------- // Event Buffer Monitoring void event_while(unsigned int event) { unsigned int data_lower; unsigned int data_higher; reg_32b_read(RISCV_EVENT_BUFFER_ADDRESS, &data_lower); reg_32b_read(RISCV_EVENT_BUFFER_ADDRESS, &data_higher); while (((data_lower & (0x00000FFF)) != (event)) & ((data_higher & (0x00000FFF)) != (event))) { reg_32b_read(RISCV_EVENT_BUFFER_ADDRESS, &data_lower); reg_32b_read(RISCV_EVENT_BUFFER_ADDRESS, &data_higher); } // if(UART_EN) printf("higher %x & lower %x\r\n",data_higher,data_lower); } void device_initiated_disconnect() { unsigned int data; // Set DCTL.RunStop to ‘0’ to disconnect from the host reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c704, 0x40000000 | 0x00f00000); // 31c1 reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c70c, &data); //poll until DSTS.DevCtrlHlt is '1' while ((data & (0x00400000)) != 0x00000000) reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c70c, &data); } // ----------------------------------------------------------- // USB Sequences // ----------------------------------------------------------- // 1. USB Reset Sequence void usb_reset_seq() { unsigned int DSTS; unsigned int state; //reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c70c, &DSTS); //state = DSTS & (0x003c0000); //if(UART_EN) printf("F:%x\r\n",state); // UTMI PHY Soft Reset -- Causes the usb2phy_reset signal to be asserted to reset a UTMI PHY reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c200, 0x80000000 | 0x00102400); //3080 // USB3 PHY Soft Reset -- After setting this bit to '1', the software needs to clear this bit. if(SUSPEND_MODE_EN) reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c2c0, 0x80000000 | 0x010c0002|0x00020000); //30b0 else reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c2c0, 0x80000000 | 0x010c0002); //30b0 // USB 2.0 PHY Internal CSR Configuration // Default Value = 300 reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x00018008, 0x00000700); // 6002 if (EXT_CLK_EN) // External Clock reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x00018004, 0x00000100); // 6001 else // Internal Clock reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x00018004, 0x01000100); // 6001 // USB 3.0 PHY Internal CSR Configuration reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x00014010, 0x00060000); // 5004 // USB 3.0 PHY External CSR Configuration // USB3 PHY 0xc8 to 0xcb reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x000100C8, 0x00000040); // 4032 // USB3 PHY 0x8c to 0x8f reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0001008C, 0x90940001); // 4023 // USB3 PHY 0x90 to 0x93 reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x00010090, 0x3f7a03d0); // 4024 // USB3 PHY 0x94 to 0x97 reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x00010094, 0x03d09000); // 4025 // USB3 PHY 0x40 to 0x43 // Added by Pavan if (EXT_CLK_EN) // External Clock reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x00010040, 0x7FE78032); // 4010 else // Internal Clock : All Default Values : Not Required reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x00010040, 0x7FE7C032); // 4010 // UTMI PHY Soft Reset -- Causes the usb2phy_reset signal to be asserted to reset a UTMI PHY reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c200, 0x00102400); // 3080 // USB3 PHY Soft Reset -- After setting this bit to '1', the software needs to clear this bit. if(SUSPEND_MODE_EN) reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c2c0, 0x010c0002|0x00020000); // 30b0 else reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c2c0, 0x010c0002); // 30b0 //reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c70c, &DSTS); //state = DSTS & (0x003c0000); //if(UART_EN) printf("S:%x\r\n",state); //printf("RT"); } // 2. Power On / Soft Reset void device_poweron_soft_reset() { unsigned int data; unsigned int DSTS; unsigned int state; //reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c70c, &DSTS); //state = DSTS & (0x003c0000); //if(UART_EN) printf("T:%x\r\n",state); // Set the CSftRst field to ‘1’ and wait for a read to return ‘0’. This resets the device controller // Default Value = 32'h00f00000 reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c704, 0x40000000 | 0x00f00000); // 31c1 // Wait until it reads out 00f00000 reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c704, &data); // 31c1 while ((data & (0x40000000)) != 0x00000000) reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c704, &data); // 31c1 // Global Event Buffer Address (Low) Register // Holds the lower 32 bits of start address of the external memory for the Event Buffer. During operation, hardware does not update this address. reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c400, USB23_EVENT_ADDRESS); // 3100 // Global Event Buffer Address (High) Register // Holds the higher 32 bits of start address of the external memory for the Event Buffer. During operation, hardware does not update this address. reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c404, 0x00000000); // 3101 // Event Buffer Size in bytes (EVNTSiz) Holds the size of the Event Buffer in bytes; must be a multiple of four. This is programmed by software once during initialization. The minimum size of the event buffer is 32 bytes reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c408, 0x00000400); //3102 // This register holds the number of valid bytes in the Event Buffer reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c40c, 0x00000000); //3103 // Simulation Speed Up Factor. Program this register to override scaledown if (SIM_EN){ if(USB_SPEED == 0x4) reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c110,0x30c12004 | 0x00000070); //3044 //changes made for usb 3.0 else reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c110,0x30c12004 | 0x00000030); //3044 }else reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c110,0x30c12004 | 0x00000000); //3044 // Program device speed [2:0] bits and periodic frame interval // DCFG.DEVSPD=3'b000: High-speed // DCFG.DEVSPD=3'b001: Full-speed // DCFG.DEVSPD=3'b100: Super-speed reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c700, 0x00080800 | USB_SPEED); // 31c0 // At a minimum, enable USB Reset, Connection Done, and USB/Link State Change events. reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c708, 0x0000000f); // 31c2 DEPSTARTCFG(0x0); //for usb 3.0 if(USB_SPEED == 0x4){ DEPCFG(0x0, 0x00000000, 0x00000500, 0x00001000); DEPCFG(0x1, 0x00000000, 0x02000500, 0x00001000); } else { DEPCFG(0x0, 0x00000000, 0x00000500, 0x00000200); DEPCFG(0x1, 0x00000000, 0x02000500, 0x00000200); } DEPXFERCFG(0x0); DEPXFERCFG(0x1); // Prepare a buffer for a setup packet, initialize a setup TRB TRB_Control_setup(); // Enable physical endpoints 0 & 1 by writing 0x3 to this register reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c720, 0x00000003); // 31c8 //added for usb3.0 reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x000100AC, 0x020E4500); // 402b // Set DCTL.RunStop to ‘1’ to allow the device to attach to the host reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c704, 0x80000000 | 0x00f00000); // 31c1 // USB3 PHY 0x8c to 0x8f //added for usb3.0 reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0001008C, 0x90940001); // 4023 //reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c70c, &DSTS); //state = DSTS & (0x003c0000) ; //if(UART_EN) printf("Fr:%x\r\n",state); //printf("SR"); } // Set Configuration void Initialization_on_SetConfiguration() { unsigned int data; reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c720, 0x00000003); if(Connect_Speed == 0x4) DEPCFG(0x1, 0x00000000, 0x02000500, 0x80001000);//Changes for USB 3.0 else DEPCFG(0x1, 0x00000000, 0x02000500, 0x80000200); //DEPSTARTCFG(0x0); reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c80c, 0x00020409);//Stream ID = 2 // Poll for CmdAct reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c80c, &data); while ((data & (0x00000400)) != 0x00000000) reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c80c, &data); //BULK if(Connect_Speed == 0x0){ DEPCFG(0x2, 0x00000000, 0x04000500, 0x00001004); //OUT -- EndPoint Number 1 -- MPS = 512 DEPCFG(0x3, 0x00000000, 0x06000500, 0x00021004); //IN -- EndPoint Number 1 -- MPS = 512 DEPCFG(0x4, 0x00000000, 0x08000500, 0x00001004); //OUT -- EndPoint Number 2 -- MPS = 512 DEPCFG(0x5, 0x00000000, 0x0a000500, 0x00041004); //IN -- EndPoint Number 2 -- MPS = 512 } else if(Connect_Speed == 0x1){ DEPCFG(0x2, 0x00000000, 0x04000500, 0x00000204); //OUT -- EndPoint Number 1 -- MPS = 64 DEPCFG(0x3, 0x00000000, 0x06000500, 0x00020204); //IN -- EndPoint Number 1 -- MPS = 64 DEPCFG(0x4, 0x00000000, 0x08000500, 0x00000204); //OUT -- EndPoint Number 2 -- MPS = 64 DEPCFG(0x5, 0x00000000, 0x0a000500, 0x00040204); //IN -- EndPoint Number 2 -- MPS = 64 } else { //Added for USB 3.0 DEPCFG(0x2, 0x00000000, 0x04000500, 0x00c02004); //OUT -- EndPoint Number 1 -- MPS = 1024 -- Burst_Size = 3 DEPCFG(0x3, 0x00000000, 0x06000500, 0x00c22004); //IN -- EndPoint Number 1 -- MPS = 1024 -- Burst_Size = 3 DEPCFG(0x4, 0x00000000, 0x08000500, 0x00002004); //OUT -- EndPoint Number 2 -- MPS = 1024 DEPCFG(0x5, 0x00000000, 0x0a000500, 0x00042004); //IN -- EndPoint Number 2 -- MPS = 1024 } //Isochronous DEPCFG(0x6, 0x00000000, 0x0c000500, 0x00002002); //OUT -- EndPoint Number 3 -- MPS = 1024 DEPCFG(0x7, 0x00000000, 0x0e000500, 0x00062002); //IN -- EndPoint Number 3 -- MPS = 1024 -- FIFO NUM = 3 DEPCFG(0x8, 0x00000000, 0x10000500, 0x00002002); //OUT -- EndPoint Number 4 -- MPS = 1024 DEPCFG(0x9, 0x00000000, 0x12000500, 0x00082002); //IN -- EndPoint Number 4 -- MPS = 1024 -- FIFO NUM = 4 //Interrupt if(Connect_Speed == 0x1){ DEPCFG(0xa, 0x00000000, 0x14000500, 0x00000206); //OUT -- EndPoint Number 5 -- MPS = 64 DEPCFG(0xb, 0x00000000, 0x16000500, 0x000a0206); //IN -- EndPoint Number 5 -- MPS = 64 DEPCFG(0xc, 0x00000000, 0x18000500, 0x00000206); //OUT -- EndPoint Number 6 -- MPS = 64 DEPCFG(0xd, 0x00000000, 0x1a000500, 0x000c0206); //IN -- EndPoint Number 6 -- MPS = 64 } else { DEPCFG(0xa, 0x00000000, 0x14000500, 0x00002006); //OUT -- EndPoint Number 5 -- MPS = 1024 DEPCFG(0xb, 0x00000000, 0x16000500, 0x000a2006); //IN -- EndPoint Number 5 -- MPS = 1024 DEPCFG(0xc, 0x00000000, 0x18000500, 0x00002006); //OUT -- EndPoint Number 6 -- MPS = 1024 DEPCFG(0xd, 0x00000000, 0x1a000500, 0x000c2006); //IN -- EndPoint Number 6 -- MPS = 1024 } DEPXFERCFG(0x2); DEPXFERCFG(0x3); DEPXFERCFG(0x4); DEPXFERCFG(0x5); DEPXFERCFG(0x6); DEPXFERCFG(0x7); DEPXFERCFG(0x8); DEPXFERCFG(0x9); DEPXFERCFG(0xa); DEPXFERCFG(0xb); DEPXFERCFG(0xc); DEPXFERCFG(0xd); reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c720, 0x00003fff); event_while(0x000000c2); TRB_Control_Status2(); } // Enumeration Sequence void enumeration_generic() { unsigned int data_higher; unsigned int data_lower; unsigned int dev_address; unsigned int dev_addr; unsigned int descriptor_type; unsigned int descriptor_index; unsigned int descriptor_length; unsigned int wlength; unsigned int control_in_address; unsigned int data; unsigned int event_count; unsigned int U1_sel; unsigned int U1_pel; unsigned int U2_sel; unsigned int U2_pel; // Reading Data from Request buffer reg_32b_read(RISCV_REQUEST_BUFFER_ADDRESS, &data_lower); reg_32b_read(RISCV_REQUEST_BUFFER_ADDRESS, &data_higher); //if(UART_EN) printf("higher %x & lower %x\r\n",data_higher,data_lower); // Get Descriptor Request if ((data_lower & (0x0000FFFF)) == (0x00000680)) { descriptor_type = (data_lower & (0xff000000)); descriptor_index = (data_lower & (0x00ff0000)); descriptor_length = (data_higher & (0xffff0000)); event_while(0x000000c2); //wait for XferNotReady EP1 // Device Descriptor if (descriptor_type == 0x01000000) { if((Connect_Speed != USB_SPEED) & (USB_SPEED == 0x4)){ TRB_Control_Data(Device_Descriptor_size, Device_Data_Buffer_size, Device_Hub_data); } else { if(Connect_Speed == 0x4) TRB_Control_Data(Device_Descriptor_size, Device_Data_Buffer_size, Device_SS_data); else TRB_Control_Data(Device_Descriptor_size, Device_Data_Buffer_size, Device_data); } //printf("D"); event_while(0x000000c0); //wait for XferNotReady EP0 //TRB Control Status for 3 stages TRB_Control_Status3(0x0); event_while(0x00000040); // Configuartion Descriptor } else if (descriptor_type == 0x02000000) { // Configuration descriptor -- If Descriptor Length is 9 or 255 if ((descriptor_length == 0x00090000) | (descriptor_length == 0x00ff0000)) { if(Connect_Speed == 0x4) TRB_Control_Data(Configuration_Descriptor_size, Configuration_Data_Buffer_size, Configuration_SS_data); else TRB_Control_Data(Configuration_Descriptor_size, Configuration_Data_Buffer_size, Configuration_data); //printf("C"); // Configuration & Interface & Endpoint descriptor -- If Descriptor Length is not 9 } else { if(Connect_Speed == 0x0) TRB_Control_Data(Configuration_Interface_Endpoint_Descriptor_size, Configuration_Interface_Endpoint_data_Buffer_size, Configuration_Interface_Endpoint_HS_data); else if(Connect_Speed == 0x1) TRB_Control_Data(Configuration_Interface_Endpoint_Descriptor_size, Configuration_Interface_Endpoint_data_Buffer_size, Configuration_Interface_Endpoint_FS_data); else TRB_Control_Data(Configuration_Interface_Endpoint_Descriptor_SS_size, Configuration_Interface_Endpoint_SS_data_Buffer_size, Configuration_Interface_Endpoint_SS_data); //printf("CI"); } event_while(0x000000c0); //wait for XferNotReady EP0 //TRB Control Status for 3 stages TRB_Control_Status3(0x0); event_while(0x00000040); // Other Speed Configuartion Descriptor } else if (descriptor_type == 0x07000000) { // Other Speed Configuration descriptor -- If Descriptor Length is 9 or 255 if ((descriptor_length == 0x00090000) | (descriptor_length == 0x00ff0000)) { TRB_Control_Data(Other_Speed_Configuartion_Descriptor_size, Other_Speed_Configuartion_Data_Buffer_size, Other_Speed_Configuartion_data); // Other Speed Configuration & Interface & Endpoint descriptor -- If Descriptor Length is not 9 } else { TRB_Control_Data(Other_Speed_Configuartion_Interface_Endpoint_Descriptor_size, Other_Speed_Configuartion_Interface_Endpoint_Data_Buffer_size, Other_Speed_Configuartion_Interface_Endpoint_data); } event_while(0x000000c0); //wait for XferNotReady EP0 //TRB Control Status for 3 stages TRB_Control_Status3(0x0); event_while(0x00000040); // Device Qualifier Descriptor } else if (descriptor_type == 0x06000000) { TRB_Control_Data(Device_Qualifier_Descriptor_size, Device_Qualifier_Data_Buffer_size, Device_Qualifier_data); //printf("Q"); event_while(0x000000c0); //wait for XferNotReady EP0 //TRB Control Status for 3 stages TRB_Control_Status3(0x0); event_while(0x00000040); // String Descriptor } else if (descriptor_type == 0x03000000) { // String - language descriptor if (descriptor_index == 0x00000000) { //printf("higher %x & lower %x\r\n",data_higher,data_lower); TRB_Control_Data(String_Language_Descriptor_size, String_Language_Data_Buffer_size, String_Language_data); //printf("S"); // String - index 1 descriptor } else if (descriptor_index == 0x00010000) { //printf("higher %x & lower %x\r\n",data_higher,data_lower); TRB_Control_Data(String_Index1_Descriptor_size, String_Index1_Data_Buffer_size, String_Index1_data); //printf("S1"); // String - index 2 descriptor } else if (descriptor_index == 0x00020000) { //printf("higher %x & lower %x\r\n",data_higher,data_lower); TRB_Control_Data(String_Index2_Descriptor_size, String_Index2_Data_Buffer_size, String_Index2_data); //printf("S2"); // String - index 3 descriptor } else { //printf("higher %x & lower %x\r\n",data_higher,data_lower); TRB_Control_Data(String_Index3_Descriptor_size, String_Index3_Data_Buffer_size, String_Index3_data); //printf("S3"); } event_while(0x000000c0); //wait for XferNotReady EP0 //TRB Control Status for 3 stages TRB_Control_Status3(0x0); event_while(0x00000040); //BOS descriptor } else if (descriptor_type == 0x0f000000) { if ((descriptor_length == 0x00050000) | (descriptor_length == 0x00ff0000)) { TRB_Control_Data(BOS_Descriptor_size, BOS_Descriptor_Data_Buffer_size, BOS_Descriptor_data); event_while(0x000000c0); //wait for XferNotReady EP0 TRB_Control_Status3(0x0);//TRB Control Status for 3 stages event_while(0x00000040); // BOS + Device Capability Descriptor } else if (descriptor_length == 0x00160000){ TRB_Control_Data(BOS_Device_Capability_Descriptor_size, BOS_Device_Capability_Descriptor_Data_Buffer_size, BOS_Device_Capability_Descriptor_data); event_while(0x000000c0); //wait for XferNotReady EP0 TRB_Control_Status3(0x0);//TRB Control Status for 3 stages event_while(0x00000040); } else { event_while(0x000000c2); DEPSSTALL(0x0); } } else { event_while(0x000000c2); DEPSSTALL(0x0); } // Set Address Request } else if ((data_lower & (0x0000FFFF)) == (0x00000500)) { dev_address = (data_lower & (0x007f0000)); dev_addr = (dev_address >> 13); // Speed Selection, Device Address reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c700,0x00080800 | USB_SPEED | dev_addr); // 31c0 event_while(0x000000c2); //TRB Control Status for 2 stages TRB_Control_Status2(); event_while(0x00000042); if(UART_EN) printf("A"); // Set Configuartion Request } else if ((data_lower & (0x0000FFFF)) == (0x00000900)) { bconfiguration_value = (data_lower & (0xffff0000)); Initialization_on_SetConfiguration(); event_while(0x00000042); if(UART_EN) printf("P"); // Control OUT } else if ((data_lower & (0x000000FF)) == (0x00000040)) { wlength = (data_higher & (0xffff0000)); //printf("higher %x & lower %x\r\n",data_higher,data_lower); //printf("%x\r\n",wlength); //2 stage if(wlength == 0x00000000){ event_while(0x000000c2); TRB_Control_Status2(); event_while(0x00000042); //3 stage } else { Request_Buffer_interrupt_flag = 0; TRB_Control_setup(); event_while(0x00000040); //wait for XferComplete EP0 while (Request_Buffer_interrupt_flag == 0) {} reg_32b_read(RISCV_REQUEST_BUFFER_ADDRESS, &data_lower); reg_32b_read(RISCV_REQUEST_BUFFER_ADDRESS, &data_higher); //if(UART_EN) printf("higher %x & lower %x\r\n",data_higher,data_lower); event_while(0x000000c2);//wait for XferNotReady EP1 TRB_Control_Status3(0x1); event_while(0x00000042);//wait for XferComplete EP1 } // Control IN } else if ((data_lower & (0x000000FF)) == (0x000000C0)) { control_in_address = (data_higher & (0x0000FFFF)); event_while(0x000000C2); //wait for XferNotReady EP1 TRB_buffer_set((USB23_CONTROL_ADDRESS | control_in_address), 0x00000000, 0x00000008, 0x00000853); DEPSTRTXFER(0x1, USB23_TRB_ADDRESS, 0x00000000); event_while(0x000000c0); //wait for XferNotReady EP0 TRB_Control_Status3(0x0); event_while(0x00000040); //Get Configuration Request // 0 before set_configuration // 1 after set_configuration } else if((data_lower & (0x0000FFFF)) == (0x00000880)) { event_while(0x000000c2); //wait for XferNotReady EP1 unsigned int configuration_value[] = {0x00000000,0x00000000}; if(bconfiguration_value == 0x00010000) configuration_value[0] = 0x00000001; unsigned int size = (sizeof(configuration_value) / 4); TRB_Control_Data(0x1,size,configuration_value ); event_while(0x000000c0); //wait for XferNotReady EP0 //TRB Control Status for 3 stages TRB_Control_Status3(0x0); event_while(0x00000040); //get status -- Recipient Device //self powered(D0 -- 1) //following can be modified by set_feature & clear_feature // 2.0 -- Remote_Wakeup(D1) // 3.2 -- U1_Enable(D2) // -- U2_Enable(D3) // -- LTM Enable(D4) } else if((data_lower & (0x0000FFFF)) == (0x00000080)){ event_while(0x000000c2); //wait for XferNotReady EP1 unsigned int status[] = {0x00000001,0x00000000}; unsigned int size = (sizeof(status) / 4); TRB_Control_Data(0x2,size,status ); event_while(0x000000c0); //wait for XferNotReady EP0 //TRB Control Status for 3 stages TRB_Control_Status3(0x0); event_while(0x00000040); //set_feature -- Recipient Device } else if((data_lower & (0x0000FFFF)) == (0x00000300)){ unsigned int feature_selector = (data_lower & (0x00ff0000)); //if(UART_EN) printf("%x\r\n",feature_selector); event_while(0x000000c2); TRB_Control_Status2(); event_while(0x00000042); //clear_feature - device remote-wakeup } else if((data_lower & (0x000FFFFF)) == (0x00010100)){ event_while(0x000000c2); TRB_Control_Status2(); event_while(0x00000042); //set_sel } else if((data_lower & (0x0000FFFF)) == (0x00003000)){ Request_Buffer_interrupt_flag = 0; TRB_Control_setup(); event_while(0x00000040); //wait for XferComplete EP0 while (Request_Buffer_interrupt_flag == 0) {} reg_32b_read(RISCV_REQUEST_BUFFER_ADDRESS, &data_lower); reg_32b_read(RISCV_REQUEST_BUFFER_ADDRESS, &data_higher); //if(UART_EN) printf("\r\n set_sel higher %x & lower %x\r\n",data_higher,data_lower); U1_sel = (data_lower & (0x000000ff)); U1_pel = ((data_lower & (0x0000ff00)) >> 8); U2_sel = ((data_lower & (0xffff0000)) >> 16); U2_pel = (data_higher & (0x0000ffff)); //if(UART_EN) printf("U1_sel %x & U1_pel %x & U2_sel %x & U2_pel %x \r\n",U1_sel,U1_pel,U2_sel,U2_pel); event_while(0x000000c2);//wait for XferNotReady EP1 TRB_Control_Status3(0x1); event_while(0x00000042);//wait for XferComplete EP1 // Stall } else { event_while(0x000000c2); DEPSSTALL(0x0); } if(UART_EN) printf("D"); // For New packet TRB_Control_setup(); } // Request Interrupt Service Routine void Request_Buffer_isr_handler(void *ctx) { Request_Buffer_interrupt_flag = 1; pic_int_clear(S_INT_PIC2); } // Event Interrupt Service Routine void Event_Buffer_isr_handler(void *ctx) { Event_Buffer_interrupt_flag = 1; pic_int_clear(S_INT_PIC1); } int main(void) { static uint8_t idx = 0; static uint8_t pin_state = 0xFF; unsigned int data; unsigned int data_lower; unsigned int data_higher; unsigned int event_count; unsigned int DSTS; unsigned int state; unsigned int speed; unsigned int ltssm_reg; // initialize PIC pic_init(CPU0_INST_PICTIMER_START_ADDR); //initialize UART uart_core_uart.intrLevel = UART0_INST_IRQ; uart_core_uart.intrAvail = true; uart_init(&uart_core_uart, UART0_INST_BASE_ADDR, UART_INST_SYS_CLK * 1000000, UART0_INST_BAUD_RATE, 1, 8); iob_init(lscc_uart_putc, lscc_uart_getc, lscc_uart_flush); if (UART_EN) printf("\r\nUSB Enumeration Started...\r\n"); // Enabling Interrupt for Request Buffer pic_isr_register(S_INT_PIC2, Request_Buffer_isr_handler, &Request_Buffer_interrupt_flag); // Enabling Interrupt for Event Buffer pic_isr_register(S_INT_PIC1, Event_Buffer_isr_handler, &Event_Buffer_interrupt_flag); // -------------------------------------------- // Enumeration Sequence // -------------------------------------------- // 1. USB Reset Sequence usb_reset_seq(); // 2. Power on and Soft Reset Sequence device_poweron_soft_reset(); while (1) { // Setup Packet Sequence if (Request_Buffer_interrupt_flag == 1) { enumeration_generic(); Request_Buffer_interrupt_flag = 0; Event_Buffer_interrupt_flag = 0; //Event Buffer Size Clearing reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c40c,&event_count); //3103 reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c40c,event_count); //3103 // Request Packet Sequence // ------------------------------------------------------------ // Packet_Type End Point Xfer_NotReady Xfer_Complete // ------------------------------------------------------------ // Control OUT EP 0 C0 40 // Control IN EP 1 C2 42 // Bulk OUT EP 2 C4 44 // Bulk IN EP 3 C6 46 // Interrupt OUT EP 10 D4 54 // Interrupt IN EP 11 D6 56 } else { // Reading Data from Event buffer reg_32b_read(RISCV_EVENT_BUFFER_ADDRESS, &data_lower); reg_32b_read(RISCV_EVENT_BUFFER_ADDRESS, &data_higher); //if(UART_EN) printf("higher %x & lower %x\r\n",data_higher,data_lower); //if(UART_EN) printf("%x:%x\r\n",(data_higher & 0x0000FFFF),(data_lower & 0x0000FFFF)); //event buffer overflow if (((data_lower & (0x00001F00)) == (0x00000B00)) | ((data_higher & (0x00001F00)) == (0x00000B00))) { if(UART_EN) printf("O\r\n"); //Event Buffer Size Clearing reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c40c,&event_count); //3103 reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c40c,event_count); //3103 //Disconnect } else if(((data_lower & (0x00000FFF)) == (0x00000001)) | ((data_higher & (0x00000FFF)) == (0x00000001))) { if(UART_EN) printf("X\r\n"); reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c704, 0x80f00000 | 0x000000a0); // 31c1 //reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c700, 0x00080800 | USB_SPEED); // 31c0 // Interrupt OUT EP 10 } else if (((data_lower & (0x00000FFF)) == (0x000000D4)) | ((data_higher & (0x00000FFF)) == (0x000000D4))) { DEPENDXFER(); if(Connect_Speed == 0x0) TRB_buffer_set(USB23_INTERRUPT_ADDRESS, 0x00000000, SIZE_OF_INTERRUPT_OUT_HS_DATA, 0x00000813); else if(Connect_Speed == 0x4) TRB_buffer_set(USB23_INTERRUPT_ADDRESS, 0x00000000, SIZE_OF_SS_DATA, 0x00000813); else TRB_buffer_set(USB23_INTERRUPT_ADDRESS, 0x00000000, SIZE_OF_INTERRUPT_OUT_FS_DATA, 0x00000813); DEPSTRTXFER(0xa, USB23_TRB_ADDRESS, 0x00000000); // OUT event_while(0x00000054); // wait for XferComplete EP10 if(UART_EN) printf("IO"); TRB_Control_setup(); // Interrupt IN EP 11 } else if (((data_lower & (0x00000FFF)) == (0x000000D6)) | ((data_higher & (0x00000FFF)) == (0x000000D6))) { DEPENDXFER(); if(Connect_Speed == 0x0) TRB_buffer_set(USB23_INTERRUPT_ADDRESS, 0x00000000, SIZE_OF_INTERRUPT_IN_HS_DATA, 0x00000813); else if(Connect_Speed == 0x4) TRB_buffer_set(USB23_INTERRUPT_ADDRESS, 0x00000000, SIZE_OF_SS_DATA, 0x00000813); else TRB_buffer_set(USB23_INTERRUPT_ADDRESS, 0x00000000, SIZE_OF_INTERRUPT_IN_FS_DATA, 0x00000813); DEPSTRTXFER(0xb, USB23_TRB_ADDRESS, 0x00000000); // IN event_while(0x00000056); // wait for XferComplete EP10 if(UART_EN) printf("II"); TRB_Control_setup(); // Bulk OUT EP 2 } else if (((data_lower & (0x00000FFF)) == (0x000000C4)) | ((data_higher & (0x00000FFF)) == (0x000000C4))) { DEPENDXFER(); if(Connect_Speed == 0x0) TRB_buffer_set(USB23_BULK_ADDRESS, 0x00000000, SIZE_OF_BULK_OUT_HS_DATA, 0x00000813); else if(Connect_Speed == 0x4) TRB_buffer_set(USB23_BULK_ADDRESS, 0x00000000, SIZE_OF_SS_DATA, 0x00000813); else TRB_buffer_set(USB23_BULK_ADDRESS, 0x00000000, SIZE_OF_BULK_OUT_FS_DATA, 0x00000813); DEPSTRTXFER(0x2, USB23_TRB_ADDRESS, 0x00000000); // OUT event_while(0x00000044); // wait for XferComplete EP2 if(UART_EN) printf("BO"); TRB_Control_setup(); // Bulk IN EP 3 } else if (((data_lower & (0x00000FFF)) == (0x000000C6)) | ((data_higher & (0x00000FFF)) == (0x000000C6))) { DEPENDXFER(); if(Connect_Speed == 0x0) TRB_buffer_set(USB23_BULK_ADDRESS, 0x00000000, SIZE_OF_BULK_IN_HS_DATA, 0x00000813); else if(Connect_Speed == 0x4) TRB_buffer_set(USB23_BULK_ADDRESS, 0x00000000, SIZE_OF_SS_DATA, 0x00000813); else TRB_buffer_set(USB23_BULK_ADDRESS, 0x00000000, SIZE_OF_BULK_IN_FS_DATA, 0x00000813); DEPSTRTXFER(0x3, USB23_TRB_ADDRESS, 0x00000000); // IN event_while(0x00000046); // wait for XferComplete EP3 if(UART_EN) printf("BI"); TRB_Control_setup(); //reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c40c,&event_count); //3103 //if(UART_EN) printf("%x\r\n",event_count); // Suspend_Resume Mode } else if (((data_lower & (0x000FFFFF)) == (0x00050301)) | ((data_higher & (0x000FFFFF)) == (0x00050301))) { if(UART_EN) printf("R"); //Initialization on USB Reset // USB Reset Event Sequence } else if (((data_lower & (0x00000FFF)) == (0x00000101)) | ((data_higher & (0x00000FFF)) == (0x00000101))) { if(UART_EN) printf("s"); reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c700, 0x00080800 | USB_SPEED); // 31c0 //Initialisation on Connect done // USB Connect Done Event Sequence } else if (((data_lower & (0x00000FFF)) == (0x00000201)) | ((data_higher & (0x00000FFF)) == (0x00000201))) { //Read DSTS for Connect Speed[0:2] reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c70c, &DSTS); Connect_Speed = DSTS & (0x00000007); if(UART_EN) printf("%x",Connect_Speed); if(Connect_Speed == 0x0 | Connect_Speed == 0x1){ DEPCFG(0x0, 0x00000000, 0x00000500, 0x80000200); DEPCFG(0x1, 0x00000000, 0x02000500, 0x80000200); } else if(Connect_Speed == 0x4){ DEPCFG(0x0, 0x00000000, 0x00000500, 0x80001000); DEPCFG(0x1, 0x00000000, 0x02000500, 0x80001000); } if (SIM_EN){ // With Simulation if(USB_SPEED == 0x4) reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c110,(0x30c12004 | 0x00000070)); else reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c110,(0x30c12004 | 0x00000030)); } else // Without Simulation reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c110,(0x30c12004 | 0x00000000)); if(UART_EN) printf("C"); bconfiguration_value = 0x00000000; } else { } //Event Buffer Size Clearing reg_32b_read(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c40c,&event_count); //3103 reg_32b_write(RISCV_USB_CONFIGURATION_ADDRESS | 0x0000c40c,event_count); //3103 } } return 0; }