diff options
author | Mark Meserve <mark.meserve@ni.com> | 2019-04-11 15:14:37 -0500 |
---|---|---|
committer | michael-west <michael.west@ettus.com> | 2019-05-21 16:08:43 -0700 |
commit | 4f57ecab13e37f132c99ec797d412def3f1e2a66 (patch) | |
tree | 4789bce38abf657f52a4ebd1dabce720e1e62f68 /firmware/fx3/b200 | |
parent | 914206e04182d2446de14be29ef886ae7c013641 (diff) | |
download | uhd-4f57ecab13e37f132c99ec797d412def3f1e2a66.tar.gz uhd-4f57ecab13e37f132c99ec797d412def3f1e2a66.tar.bz2 uhd-4f57ecab13e37f132c99ec797d412def3f1e2a66.zip |
b200: add custom bootloader
- Adds custom bootloader code
- Refactor common functions in firmware and bootloader
Diffstat (limited to 'firmware/fx3/b200')
21 files changed, 2039 insertions, 630 deletions
diff --git a/firmware/fx3/b200/.gitignore b/firmware/fx3/b200/.gitignore index 13c187886..2c36b03cd 100644 --- a/firmware/fx3/b200/.gitignore +++ b/firmware/fx3/b200/.gitignore @@ -1,4 +1,7 @@ +lib +!common *.o *.elf *.hex *.map +*.img diff --git a/firmware/fx3/b200/bootloader/.gitignore b/firmware/fx3/b200/bootloader/.gitignore new file mode 100644 index 000000000..75d01c18d --- /dev/null +++ b/firmware/fx3/b200/bootloader/.gitignore @@ -0,0 +1,5 @@ +cyfx3.ld +cyfx_gcc_startup.S +elf2img +fx3_armgcc_config.mak +fx3_build_config.mak diff --git a/firmware/fx3/b200/bootloader/main.c b/firmware/fx3/b200/bootloader/main.c new file mode 100644 index 000000000..f46690813 --- /dev/null +++ b/firmware/fx3/b200/bootloader/main.c @@ -0,0 +1,55 @@ +// +// Copyright 2011-2012 Cypress Semiconductor Corporation +// Copyright 2019 Ettus Research, a National Instruments Brand +// +// SPDX-License-Identifier: GPL-3.0-or-later +// + +#include "cyfx3usb.h" +#include "cyfx3device.h" + +extern void usbBoot (void); +extern uint8_t glCheckForDisconnect; +extern uint8_t glInCompliance; + +int main (void) +{ + CyFx3BootErrorCode_t status; + CyFx3BootIoMatrixConfig_t ioCfg = { + .isDQ32Bit = CyFalse, + .useUart = CyFalse, + .useI2C = CyTrue, + .useI2S = CyFalse, + .useSpi = CyFalse, + .gpioSimpleEn[0] = 0, + .gpioSimpleEn[1] = 0 + }; + + CyFx3BootDeviceInit(CyTrue); + + status = CyFx3BootDeviceConfigureIOMatrix(&ioCfg); + + if (status != CY_FX3_BOOT_SUCCESS) + { + return status; + } + + usbBoot(); + + while (1) + { + if (glCheckForDisconnect) + { + CyFx3BootUsbCheckUsb3Disconnect(); + glCheckForDisconnect = 0; + } + + if (glInCompliance) + { + CyFx3BootUsbSendCompliancePatterns(); + glInCompliance = 0; + } + } + return 0; +} + diff --git a/firmware/fx3/b200/bootloader/makefile b/firmware/fx3/b200/bootloader/makefile new file mode 100644 index 000000000..3dc7fcb80 --- /dev/null +++ b/firmware/fx3/b200/bootloader/makefile @@ -0,0 +1,92 @@ +# +# Copyright 2019 Ettus Research, a National Instruments Brand +# +# SPDX-License-Identifier: GPL-3.0-or-later +# + +IMGOUT = usrp_b200_bl.img + +all:$(IMGOUT) + +BL_ROOT=../../boot_fw +BL_INC=$(BL_ROOT)/include +BL_LIB=$(BL_ROOT)/lib +BL_CYP_SRC=$(BL_ROOT)/src + +ELF2IMG_SRC=../../elf2img/elf2img.c +ELF2IMG=elf2img + +CYFXBUILD = gcc + +include fx3_build_config.mak + +MODULE = cyfx_boot_app + +APP_SOURCE = main.c usb_boot.c usb_descriptors.c ../common/common_descriptors.c ../common/common_helpers.c + +INCFLAGS = -I$(BL_INC) -I../common + +APP_OBJECT=$(APP_SOURCE:%.c=./%.o) + +APP_ASM_OBJECT=$(APP_ASM_SOURCE:%.S=./%.o) + +EXES = $(MODULE).$(EXEEXT) + +ifeq ($(CYFXBUILD), gcc) + +APP_ASM_SOURCE = cyfx_gcc_startup.S + +else + +APP_ASM_SOURCE = + +endif + +$(APP_ASM_OBJECT) : %.o : %.S + $(ASSEMBLE) + +$(APP_OBJECT) : %.o : %.c ../lib/cyfx3_boot.a cyfx3.ld + $(COMPILE) $(INCFLAGS) + +$(MODULE).$(EXEEXT): $(APP_OBJECT) $(APP_ASM_OBJECT) + $(LINK) + +$(ELF2IMG): + gcc -o $(ELF2IMG) $(ELF2IMG_SRC) + +fx3_build_config.mak: + cp $(BL_CYP_SRC)/fx3_build_config.mak . +fx3_armgcc_config.mak: + cp $(BL_CYP_SRC)/fx3_armgcc_config.mak . +cyfx_gcc_startup.S: + cp $(BL_CYP_SRC)/cyfx_gcc_startup.S . +cyfx3.ld: + cp $(BL_CYP_SRC)/cyfx3.ld . +../lib/cyfx3_boot.a: + mkdir -p ../lib + cp $(BL_LIB)/cyfx3_boot.a ../lib + + +clean: + rm -f ./$(MODULE).$(EXEEXT) + rm -f ./$(MODULE).map + rm -f ./$(IMGOUT) + rm -f ./fx3_build_config.mak + rm -f ./fx3_armgcc_config.mak + rm -f ./cyfx_gcc_startup.S + rm -f ./cyfx3.ld + rm -f ../lib/cyfx3_boot.a + rmdir ../lib --ignore-fail-on-non-empty + rm -f ./*.o + rm -f ../common/*.o + rm -f ./$(ELF2IMG) +ifeq ($(CYFXBUILD), gcc) + rm -f ./gcceclipse_files/*.o +endif + +compile: $(APP_OBJECT) $(APP_ASM_OBJECT) $(EXES) + +$(IMGOUT): compile $(EXES) $(ELF2IMG) + ./$(ELF2IMG) -i $(EXES) -o $(IMGOUT) -i2cconf 0x1A + +#[]# diff --git a/firmware/fx3/b200/bootloader/usb_boot.c b/firmware/fx3/b200/bootloader/usb_boot.c new file mode 100644 index 000000000..ba7eb9dfb --- /dev/null +++ b/firmware/fx3/b200/bootloader/usb_boot.c @@ -0,0 +1,807 @@ +// +// Copyright 2011-2012 Cypress Semiconductor Corporation +// Copyright 2019 Ettus Research, a National Instruments Brand +// +// SPDX-License-Identifier: GPL-3.0-or-later +// + +#include "cyfx3usb.h" +#include "cyfx3device.h" +#include "cyfx3utils.h" +#include "cyfx3i2c.h" + +#include "common_helpers.h" +#include "common_descriptors.h" +#include "usb_descriptors.h" + +typedef enum +{ + eStall = 0, /* Send STALL */ + eDataIn, /* Data IN Stage */ + eDataOut, /* Data Out Stage */ + eStatus /* Status Stage */ +} eUsbStage; + +typedef int (*PFI)(); + +#define USB_SETUP_DIR (0x80) /* 0x80 = To Host */ +#define USB_SETUP_MASK (0x60) /* Used to mask off request type */ +#define USB_STANDARD_REQUEST (0x00) /* Standard Request */ +#define USB_VENDOR_REQUEST (0x40) /* Vendor Request */ +#define USB_REQ_MASK (0x3F) /* USB Request mask */ +#define USB_REQ_DEV (0) /* Device Request */ +#define USB_REQ_INTERFACE (1) /* Interface Request */ +#define USB_REQ_ENDPOINT (2) /* Endpoint Request */ +#define USB_SET_INTERFACE (11) +#define USB_SC_SET_SEL (0x30) /* Set system exit latency. */ +#define USB_SC_SET_ISOC_DELAY (0x31) + +#define SELF_POWERED (0x01) +#define REMOTE_WAKEUP (0x02) +#define U1_ENABLE (0x04) +#define U2_ENABLE (0x08) +#define LTM_ENABLE (0x10) + +uint8_t glUsbState = 0; +uint8_t gConfig = 0; /* Variable to hold the config info. */ +uint8_t gAltSetting = 0; /* Variable to hold the interface info. */ +uint8_t gUsbDevStatus = 0; +uint8_t glCheckForDisconnect = 0; +uint8_t glInCompliance = 0; + +/* 4KB of buffer area used for control endpoint transfers. */ +#define gpUSBData (uint8_t*)(0x40077000) +#define USB_DATA_BUF_SIZE (1024*4) + +CyU3PUsbDescrPtrs *gpUsbDescPtr; /* Pointer to the USB Descriptors */ +CyFx3BootUsbEp0Pkt_t gEP0; + +void myMemCopy(uint8_t* d, uint8_t* s, int32_t cnt) +{ + int32_t i; + for (i = 0; i < cnt; i++) { + *d++ = *s++; + } +} + +void myMemSet(uint8_t* d, uint8_t c, int32_t cnt) +{ + int32_t i; + for (i = 0; i < cnt; i++) { + *d++ = c; + } +} + +/************************************************ + * Request handlers + ***********************************************/ + +/* Function to handle the GET_STATUS Standard request. */ +int getStatus (void) +{ + uint16_t data = 0; + + switch (gEP0.bmReqType & USB_REQ_MASK) + { + case USB_REQ_DEV: + if (CyFx3BootUsbGetSpeed () == CY_FX3_BOOT_SUPER_SPEED) + { + data = (gpUsbDescPtr->usbSSConfigDesc_p[7] & 0x40) ? 1 : 0; + data |= gUsbDevStatus; + } + else + { + data = (gpUsbDescPtr->usbHSConfigDesc_p[7] & 0x40) ? 1 : 0; + data |= gUsbDevStatus; + } + break; + + case USB_REQ_INTERFACE: + if (!gConfig) + { + return eStall; + } + break; + + case USB_REQ_ENDPOINT: + if (CyFx3BootUsbGetEpCfg (gEP0.bIdx0, 0, (CyBool_t *)&data) != 0) + { + return eStall; + } + break; + default: + return eStall; + } + + *(uint16_t*)gEP0.pData = data; + return eDataIn; +} + +/* Function to handle the GET_DESCRIPTOR Standard request */ +int getDescriptor (void) +{ + uint32_t len = 0; + uint8_t *p = 0; + uint8_t *cfg_p = 0; + uint8_t usbSpeed; + + usbSpeed = CyFx3BootUsbGetSpeed(); + + gpUsbDescPtr->usbHSConfigDesc_p[1] = CY_U3P_USB_CONFIG_DESCR; + gpUsbDescPtr->usbFSConfigDesc_p[1] = CY_U3P_USB_CONFIG_DESCR; + + if (usbSpeed == CY_FX3_BOOT_HIGH_SPEED) + { + cfg_p = (uint8_t*)gpUsbDescPtr->usbHSConfigDesc_p; + len = ((gpUsbDescPtr->usbHSConfigDesc_p[3] << 8) | gpUsbDescPtr->usbHSConfigDesc_p[2]); + } + else if (usbSpeed == CY_FX3_BOOT_SUPER_SPEED) + { + cfg_p = (uint8_t*)gpUsbDescPtr->usbSSConfigDesc_p; + len = ((gpUsbDescPtr->usbSSConfigDesc_p[3] << 8) | gpUsbDescPtr->usbSSConfigDesc_p[2]); + } + else if (usbSpeed == CY_FX3_BOOT_FULL_SPEED) + { + cfg_p = (uint8_t*)gpUsbDescPtr->usbFSConfigDesc_p; + len = ((gpUsbDescPtr->usbFSConfigDesc_p[3] << 8) | gpUsbDescPtr->usbFSConfigDesc_p[2]); + } + + switch (gEP0.bVal1) + { + case CY_U3P_USB_DEVICE_DESCR: + { + if ((usbSpeed == CY_FX3_BOOT_HIGH_SPEED) || (usbSpeed == CY_FX3_BOOT_FULL_SPEED)) + { + p = (uint8_t*)gpUsbDescPtr->usbDevDesc_p; + len = gpUsbDescPtr->usbDevDesc_p[0]; + } + else if (usbSpeed == CY_FX3_BOOT_SUPER_SPEED) + { + p = (uint8_t*)gpUsbDescPtr->usbSSDevDesc_p; + len = gpUsbDescPtr->usbSSDevDesc_p[0]; + } + break; + } + case CY_U3P_BOS_DESCR: + { + p = (uint8_t *)gpUsbDescPtr->usbSSBOSDesc_p; + len = (gpUsbDescPtr->usbSSBOSDesc_p[3] << 8) | gpUsbDescPtr->usbSSBOSDesc_p[2]; + break; + } + case CY_U3P_USB_CONFIG_DESCR: + { + p = cfg_p; + break; + } + case CY_U3P_USB_DEVQUAL_DESCR: + { + if ((usbSpeed == CY_FX3_BOOT_HIGH_SPEED) || (usbSpeed == CY_FX3_BOOT_FULL_SPEED)) + { + p = (uint8_t*)gpUsbDescPtr->usbDevQualDesc_p; + len = gpUsbDescPtr->usbDevQualDesc_p[0]; + break; + } + return eStall; + } + case CY_U3P_USB_STRING_DESCR: + { + /* Ensure that we do not index past the limit of the array. */ + if (gEP0.bVal0 < CY_FX3_USB_MAX_STRING_DESC_INDEX) + { + p = (uint8_t*)gpUsbDescPtr->usbStringDesc_p[gEP0.bVal0]; + if (p != 0) + len = p[0]; + } + else + return eStall; + break; + } + case CY_U3P_USB_OTHERSPEED_DESCR: + { + if (usbSpeed == CY_FX3_BOOT_HIGH_SPEED) + { + gpUsbDescPtr->usbFSConfigDesc_p[1] = CY_U3P_USB_OTHERSPEED_DESCR; + p = (uint8_t*)gpUsbDescPtr->usbFSConfigDesc_p; + + len = ((gpUsbDescPtr->usbFSConfigDesc_p[3] < 8) | gpUsbDescPtr->usbFSConfigDesc_p[2]); + + if (len > gEP0.wLen) + { + len = gEP0.wLen; + } + } + else if (usbSpeed == CY_FX3_BOOT_FULL_SPEED) + { + gpUsbDescPtr->usbHSConfigDesc_p[1] = CY_U3P_USB_OTHERSPEED_DESCR; + p = (uint8_t*)gpUsbDescPtr->usbHSConfigDesc_p; + len = ((gpUsbDescPtr->usbHSConfigDesc_p[3] < 8) | gpUsbDescPtr->usbHSConfigDesc_p[2]); + + if (len > gEP0.wLen) + { + len = gEP0.wLen; + } + } + } + break; + default: + { + return eStall; + } + } + + if (p != 0) + { + myMemCopy (gpUSBData, p, len); + if (gEP0.wLen > len) + { + gEP0.wLen = len; + } + + return eDataIn; + } + else + /* Stall EP0 if the descriptor sought is not available. */ + return eStall; +} + +/* Function to handle the SET_CONFIG Standard request */ +int setConfig (void) +{ + uint8_t usbSpeed = 0; + uint32_t retVal = 0; + CyFx3BootUsbEpConfig_t epCfg; + + if ((gEP0.bVal0 == 0) || (gEP0.bVal0 == 1)) + { + glUsbState = gEP0.bVal0; + gConfig = gEP0.bVal0; + + /* Get the Bus speed */ + usbSpeed = CyFx3BootUsbGetSpeed(); + + epCfg.pcktSize = 512; + /* Based on the Bus Speed configure the endpoint packet size */ + if (usbSpeed == CY_FX3_BOOT_HIGH_SPEED) + { + epCfg.pcktSize = 512; + } + if (usbSpeed == CY_FX3_BOOT_SUPER_SPEED) + { + epCfg.pcktSize = 1024; + } + if (usbSpeed == CY_FX3_BOOT_FULL_SPEED) + { + epCfg.pcktSize = 64; + } + + /* Producer Endpoint configuration */ + epCfg.enable = 1; + epCfg.epType = CY_FX3_BOOT_USB_EP_BULK; + epCfg.burstLen = 1; + epCfg.streams = 0; + epCfg.isoPkts = 0; + + /* Configure the Endpoint */ + retVal = CyFx3BootUsbSetEpConfig(0x01, &epCfg); + if (retVal != 0) + { + /* TODO: Error Handling */ + return eStall; + } + + /* Consumer Endpoint configuration */ + epCfg.enable = 1; + epCfg.epType = CY_FX3_BOOT_USB_EP_BULK; + epCfg.burstLen = 1; + epCfg.streams = 0; + epCfg.isoPkts = 0; + + /* Configure the Endpoint */ + retVal = CyFx3BootUsbSetEpConfig (0x81, &epCfg); + if (retVal != 0) + { + /* TODO: Error Handling */ + return eStall; + } + + return eStatus; + } + + return eStall; +} + +/* Function to handle the GET_INTERFACE Standard request */ +int getInterface (void) +{ + if (gConfig == 0) + { + return eStall; + } + + gEP0.pData = (uint8_t *)&gAltSetting; + return eDataIn; +} + +/* Function to handle the SET_INTERFACE Standard request */ +int setInterface (void) +{ + gAltSetting = gEP0.bVal0; + return eStatus; +} + +/* This function returns stall for not supported requests. */ +int stall (void) +{ + return eStall; +} + +/* Function to handle the SET_ADDRESS Standard request. */ +int setAddress (void) +{ + return eStatus; +} + +/* Function to handle the CLEAR_FEATURE Standard request. */ +int clearFeature (void) +{ + /* All of the actual handling for the CLEAR_FEATURE request is done in the API. + We only need to update the device status flags here. + */ + if (CyFx3BootUsbSetClrFeature (0, (CyBool_t)glUsbState, &gEP0) != 0) + { + return eStall; + } + + if (gEP0.bmReqType == USB_REQ_DEV) + { + /* Update the device status flags as required. */ + if (CyFx3BootUsbGetSpeed () == CY_FX3_BOOT_SUPER_SPEED) + { + switch (gEP0.bVal0) + { + case 48: + gUsbDevStatus &= ~U1_ENABLE; + break; + case 49: + gUsbDevStatus &= ~U2_ENABLE; + break; + case 50: + gUsbDevStatus &= ~LTM_ENABLE; + break; + default: + break; + } + } + else + { + if (gEP0.bVal0 == 1) + { + gUsbDevStatus &= ~REMOTE_WAKEUP; + } + } + } + + return eStatus; +} + +/* Function to handle the SET_FEATURE Standard request. */ +int setFeature (void) +{ + /* All of the actual handling for the SET_FEATURE command is done in the API. + * We only need to update the device status flags here. + */ + if (CyFx3BootUsbSetClrFeature (1, (CyBool_t)glUsbState, &gEP0) != 0) + { + return eStall; + } + + if (gEP0.bmReqType == USB_REQ_DEV) + { + /* Update the device status flags as required. */ + if (CyFx3BootUsbGetSpeed () == CY_FX3_BOOT_SUPER_SPEED) + { + switch (gEP0.bVal0) + { + case 48: + gUsbDevStatus |= U1_ENABLE; + break; + case 49: + gUsbDevStatus |= U2_ENABLE; + break; + case 50: + gUsbDevStatus |= LTM_ENABLE; + break; + default: + break; + } + } + else + { + if (gEP0.bVal0 == 1) + { + gUsbDevStatus |= REMOTE_WAKEUP; + } + } + } + return eStatus; +} + +/* Function to handle the GET_CONFIG Standard request. */ +int getConfig (void) +{ + gEP0.pData = (uint8_t *)&gConfig; + return eDataIn; +} + +const PFI chapter9_cmds[] = +{ + getStatus, /* USB_GET_STATUS 0 */ + clearFeature, /* USB_CLEAR_FEATURE 1 */ + stall, /* Reserved 2 */ + setFeature, /* USB_SET_FEATURE 3 */ + stall, /* Reserved 4 */ + setAddress, /* USB_SET_ADDRESS 5 */ + getDescriptor, /* USB_GET_DESCRIPTOR 6 */ + stall, /* USB_SET_DESCRIPTOR 7 */ + getConfig, /* USB_GET_CONFIGURATION 8 */ + setConfig, /* USB_SET_CONFIGURATION 9 */ + getInterface, /* USB_GET_INTERFACE 10 */ + setInterface, /* USB_SET_INTERFACE 11 */ +}; + +/* This function validates the addresses being written to/read from + Return Value: + 0 - Address is valid + -1 - Address is not valid +*/ +int checkAddress (uint32_t address, uint32_t len) +{ + if (address & 3) + { + /* expect long word boundary */ + return -1; + } + + len += address; + + if ((address >= CY_FX3_BOOT_SYSMEM_BASE1) && (len <= CY_FX3_BOOT_SYSMEM_END)) + { + return 0; + } + + if (len <= CY_FX3_BOOT_ITCM_END) + { + return 0; + } + + return -1; +} + +/* Function to handle the vendor commands. */ +void vendorCmdHandler (void) +{ + int stage; + int status; + uint32_t address = ((gEP0.bIdx1 << 24) | (gEP0.bIdx0 << 16) | (gEP0.bVal1 << 8) | (gEP0.bVal0)); + uint16_t len = gEP0.wLen; + uint16_t bReq = gEP0.bReq; + uint16_t dir = gEP0.bmReqType & USB_SETUP_DIR; + + if (len > USB_DATA_BUF_SIZE) + { + CyFx3BootUsbStall (0, CyTrue, CyFalse); + return; + } + + if (dir) + { + stage = eDataIn; + } + else + { + stage = eDataOut; + } + + /* Vendor Command 0xA0 handling */ + if (bReq == 0xA0) + { + /* Note: This is a command issued by the CyControl Application to detect the legacy products. + As we are an FX3 device we stall the endpoint to indicate that this is not a legacy device. + */ + if (address == 0xE600) + { + /* Stall the Endpoint */ + CyFx3BootUsbStall (0, CyTrue, CyFalse); + return; + } + + status = checkAddress (address, len); + if (len == 0) + { + /* Mask the USB Interrupts and Disconnect the USB Phy. */ + CyFx3BootUsbConnect (CyFalse, CyTrue); + /* Transfer to Program Entry */ + CyFx3BootJumpToProgramEntry (address); + return; + } + + if (status < 0) + { + /* Stall the endpoint */ + CyFx3BootUsbStall (0, CyTrue, CyFalse); + return; + } + + /* Validate the SYSMEM address being accessed */ + if ((address >= CY_FX3_BOOT_SYSMEM_BASE1) && (address < CY_FX3_BOOT_SYSMEM_END)) + { + gEP0.pData = (uint8_t*)address; + } + + CyFx3BootUsbAckSetup (); + + if (eDataIn == stage) + { + if ((address + gEP0.wLen) <= CY_FX3_BOOT_ITCM_END) + { + myMemCopy(gEP0.pData, (uint8_t *)address , len); + } + + status = CyFx3BootUsbDmaXferData (0x80, (uint32_t)gEP0.pData, gEP0.wLen, CY_FX3_BOOT_WAIT_FOREVER); + if (status != CY_FX3_BOOT_SUCCESS) + { + /* USB DMA Transfer failed. Stall the Endpoint. */ + CyFx3BootUsbStall (0, CyTrue, CyFalse); + return; + } + } + else if (stage == eDataOut) + { + status = CyFx3BootUsbDmaXferData (0x00, (uint32_t)gEP0.pData, gEP0.wLen, CY_FX3_BOOT_WAIT_FOREVER); + if (status != CY_FX3_BOOT_SUCCESS) + { + /* USB DMA Transfer failed. Stall the Endpoint. */ + CyFx3BootUsbStall (0, CyTrue, CyFalse); + return; + } + + /* Validate ITCM Memory */ + if ((address + gEP0.wLen) <= CY_FX3_BOOT_ITCM_END) + { + /* Avoid writing to the interrupt table. */ + if (address < 0xFF) { + gEP0.pData += 0xFF-address; + gEP0.wLen -= 0xFF-address; + address = 0xFF; + } + myMemCopy((uint8_t *)address, gEP0.pData, gEP0.wLen); + } + } + return; + } + + /* Version request */ + if (dir && bReq == 0xB8) { + uint8_t version_info[] = {1, 21, 0, 0, 0, 0}; + + CyFx3BootUsbAckSetup (); + status = CyFx3BootUsbDmaXferData (0x80, (uint32_t)version_info, + sizeof(version_info), CY_FX3_BOOT_WAIT_FOREVER); + if (status != CY_FX3_BOOT_SUCCESS) { + /* USB DMA Transfer failed. Stall the Endpoint. */ + CyFx3BootUsbStall (0, CyTrue, CyFalse); + } + + return; + } + + /* Stall the Endpoint */ + CyFx3BootUsbStall (0, CyTrue, CyFalse); + return; +} + +/* Setup Data handler */ +void setupDataHandler (uint32_t setupDat0, uint32_t setupDat1) +{ + uint32_t *p; + int status = eStall; + + p = (uint32_t*)&gEP0; + p[0] = setupDat0; + p[1] = setupDat1; + + gEP0.pData = gpUSBData; + + switch (gEP0.bmReqType & USB_SETUP_MASK) + { + case USB_STANDARD_REQUEST: + if (gEP0.bReq <= USB_SET_INTERFACE) + { + status = (*chapter9_cmds[gEP0.bReq])(); + } + else + { + if (gEP0.bReq == USB_SC_SET_SEL) + { + if ((CyFx3BootUsbGetSpeed () == CY_FX3_BOOT_SUPER_SPEED) && (gEP0.bIdx0 == 0) && + (gEP0.bIdx1 == 0) && (gEP0.bVal0 == 0) && (gEP0.bVal1 == 0) && (gEP0.wLen == 6)) + { + gEP0.wLen = 32; + status = eDataOut; + } + else + { + status = eStall; + } + } + else if (gEP0.bReq == USB_SC_SET_ISOC_DELAY) + { + status = eStatus; + if ((CyFx3BootUsbGetSpeed () != CY_FX3_BOOT_SUPER_SPEED) || (gEP0.bIdx0 != 0) || + (gEP0.bIdx1 != 0) || (gEP0.wLen != 0)) + { + status = eStall; + } + } + else + { + status = eStall; + } + } + break; + + case USB_VENDOR_REQUEST: + vendorCmdHandler(); + return; + } + + switch (status) + { + case eDataIn: + CyFx3BootUsbAckSetup (); + status = CyFx3BootUsbDmaXferData (0x80, (uint32_t)gEP0.pData, gEP0.wLen, 1000); + if (status != CY_FX3_BOOT_SUCCESS) + { + CyFx3BootUsbStall (0, CyTrue, CyFalse); + } + break; + case eDataOut: + CyFx3BootUsbAckSetup (); + status = CyFx3BootUsbDmaXferData (0x00, (uint32_t)gEP0.pData, gEP0.wLen, CY_FX3_BOOT_WAIT_FOREVER); + if (status != CY_FX3_BOOT_SUCCESS) + { + CyFx3BootUsbStall (0, CyTrue, CyFalse); + } + break; + case eStatus: + CyFx3BootUsbAckSetup (); + break; + default: + CyFx3BootUsbStall (0, CyTrue, CyFalse); + return; + } + + return; +} + +/* USB Event Handler. This function is invoked from the USB ISR and as such MUST not be + blocked. +*/ +void usbEventCallback (CyFx3BootUsbEventType_t event) +{ + if (event == CY_FX3_BOOT_USB_RESET) + { + gConfig = 0; + gAltSetting = 0; + gUsbDevStatus = 0; + glUsbState = 0; + glInCompliance = 0; + } + + if ((event == CY_FX3_BOOT_USB_CONNECT) || + (event == CY_FX3_BOOT_USB_DISCONNECT)) + { + glUsbState = 0; + gUsbDevStatus = 0; + } + + if (event == CY_FX3_BOOT_USB_IN_SS_DISCONNECT) + { + glCheckForDisconnect = CyTrue; + } + + if (event == CY_FX3_BOOT_USB_COMPLIANCE) + { + glInCompliance = CyTrue; + } + + return; +} + +/* Function passed to common EEPROM functions to access the EEPROM */ +void eeprom_read(uint16_t addr, uint8_t* buffer, uint8_t length) +{ + CyFx3BootI2cPreamble_t preamble; + preamble.length = 4; + preamble.buffer[0] = 0xA0; + preamble.buffer[1] = addr >> 8; + preamble.buffer[2] = addr & 0xFF; + preamble.buffer[3] = 0xA1; + preamble.ctrlMask = 0x0004; + CyFx3BootI2cReceiveBytes(&preamble, buffer, length, 0); +} + +/* USB initialization */ +void usbBoot() +{ + /* Reset globals */ + gConfig = 0; + gAltSetting = 0; + gUsbDevStatus = 0; + glUsbState = 0; + glCheckForDisconnect = 0; + glInCompliance = 0; + + /* Init */ + CyFx3BootUsbStart (CyFalse, usbEventCallback); + + /* Run USB circuitry off of host power, not internal power. */ + CyFx3BootUsbVBattEnable (CyFalse); + + /* Register callbacks */ + CyFx3BootRegisterSetupCallback (setupDataHandler); + + /* Enable I2C for EEPROM access */ + CyFx3BootI2cInit(); + CyFx3BootI2cConfig_t i2cCfg = { + .bitRate = 100000, + .isDma = CyFalse, + .busTimeout = 0xFFFFFFFF, + .dmaTimeout = 0xFFFF}; + CyFx3BootI2cSetConfig(&i2cCfg); + + /* Retrieve VID and PID from EEPROM */ + const uint16_t vid = get_vid(&eeprom_read); + const uint16_t pid = get_pid(&eeprom_read); + + /* Power down I2C */ + CyFx3BootI2cDeInit(); + + /* Populate device descriptors with IDs */ + common_usb2_dev_desc[8] = vid & 0xFF; + common_usb2_dev_desc[9] = vid >> 8; + common_usb2_dev_desc[10] = pid & 0xFF; + common_usb2_dev_desc[11] = pid >> 8; + + common_usb3_dev_desc[8] = vid & 0xFF; + common_usb3_dev_desc[9] = vid >> 8; + common_usb3_dev_desc[10] = pid & 0xFF; + common_usb3_dev_desc[11] = pid >> 8; + + /* Copy all descriptors */ + CyFx3BootUsbSetDesc( + CY_U3P_USB_SET_HS_DEVICE_DESCR, 0, (uint8_t*)common_usb2_dev_desc); + CyFx3BootUsbSetDesc( + CY_U3P_USB_SET_SS_DEVICE_DESCR, 0, (uint8_t*)common_usb3_dev_desc); + + CyFx3BootUsbSetDesc(CY_U3P_USB_SET_DEVQUAL_DESCR, 0, (uint8_t*)common_dev_qual_desc); + + CyFx3BootUsbSetDesc(CY_U3P_USB_SET_HS_CONFIG_DESCR, 0, (uint8_t*)bl_hs_config_desc); + CyFx3BootUsbSetDesc(CY_U3P_USB_SET_FS_CONFIG_DESCR, 0, (uint8_t*)bl_fs_config_desc); + CyFx3BootUsbSetDesc(CY_U3P_USB_SET_SS_CONFIG_DESCR, 0, (uint8_t*)bl_ss_config_desc); + + CyFx3BootUsbSetDesc(CY_U3P_USB_SET_SS_BOS_DESCR, 0, (uint8_t*)common_usb_bos_desc); + + CyFx3BootUsbSetDesc( + CY_U3P_USB_SET_STRING_DESCR, 0, (uint8_t*)common_string_lang_id_desc); + + CyFx3BootUsbSetDesc(CY_U3P_USB_SET_STRING_DESCR, 1, (uint8_t*)bl_manufacturer_desc); + CyFx3BootUsbSetDesc(CY_U3P_USB_SET_STRING_DESCR, 2, (uint8_t*)bl_product_desc); + CyFx3BootUsbSetDesc(CY_U3P_USB_SET_STRING_DESCR, 3, (uint8_t*)bl_dev_serial_desc); + + gpUsbDescPtr = CyFx3BootUsbGetDesc(); + + /* Connect! */ + CyFx3BootUsbConnect (CyTrue, CyTrue); +} + diff --git a/firmware/fx3/b200/bootloader/usb_descriptors.c b/firmware/fx3/b200/bootloader/usb_descriptors.c new file mode 100644 index 000000000..47d3175a8 --- /dev/null +++ b/firmware/fx3/b200/bootloader/usb_descriptors.c @@ -0,0 +1,187 @@ +// +// Copyright 2019 Ettus Research, a National Instruments Brand +// +// SPDX-License-Identifier: GPL-3.0-or-later +// + +/* Bootloader's unique config and string descriptors. */ + +/* Bootloader Full Speed Configuration Descriptor */ +const unsigned char bl_fs_config_desc[] = +{ + /* Configuration Descriptor Type */ + 0x09, /* Descriptor Size */ + 0x02, /* Configuration Descriptor Type */ + 0x20,0x00, /* Length of this descriptor and all sub descriptors */ + 0x01, /* Number of interfaces */ + 0x01, /* Configuration number */ + 0x00, /* COnfiguration string index */ + 0x80, /* Config characteristics - Bus powered */ + 0x32, /* Max power consumption of device (in 2mA unit) : 100mA */ + + /* Interface Descriptor */ + 0x09, /* Descriptor size */ + 0x04, /* Interface Descriptor type */ + 0x00, /* Interface number */ + 0x00, /* Alternate setting number */ + 0x02, /* Number of end points */ + 0xFF, /* Interface class */ + 0x00, /* Interface sub class */ + 0x00, /* Interface protocol code */ + 0x00, /* Interface descriptor string index */ + + /* Endpoint Descriptor for Producer EP */ + 0x07, /* Descriptor size */ + 0x05, /* Endpoint Descriptor Type */ + 0x01, /* Endpoint address and description */ + 0x02, /* Bulk End point Type */ + 0x40,0x00, /* Max packet size = 64 bytes */ + 0x00, /* Servicing interval for data transfers : NA for Bulk */ + + /* Endpoint Descriptor for Consumer EP */ + 0x07, /* Descriptor size */ + 0x05, /* Endpoint Descriptor Type */ + 0x81, /* Endpoint address and description */ + 0x02, /* Bulk End point Type */ + 0x40,0x00, /* Max packet size = 64 bytes */ + 0x00 /* Servicing interval for data transfers : NA for Bulk */ +}; + +/* Bootloader High Speed Configuration Descriptor */ +const unsigned char bl_hs_config_desc[] = +{ + 0x09, /* Descriptor Size */ + 0x02, /* Configuration Descriptor Type */ + 0x20,0x00, /* Length of this descriptor and all sub descriptors */ + 0x01, /* Number of interfaces */ + 0x01, /* Configuration number */ + 0x00, /* COnfiguration string index */ + 0x80, /* Config characteristics - Bus powered */ + 0x32, /* Max power consumption of device (in 2mA unit) : 100mA */ + + /* Interface Descriptor */ + 0x09, /* Descriptor size */ + 0x04, /* Interface Descriptor type */ + 0x00, /* Interface number */ + 0x00, /* Alternate setting number */ + 0x02, /* Number of end points */ + 0xFF, /* Interface class */ + 0x00, /* Interface sub class */ + 0x00, /* Interface protocol code */ + 0x00, /* Interface descriptor string index */ + + /* Endpoint Descriptor for Producer EP */ + 0x07, /* Descriptor size */ + 0x05, /* Endpoint Descriptor Type */ + 0x01, /* Endpoint address and description */ + 0x02, /* Bulk End point Type */ + 0x00, /* Max packet size = 512 bytes */ + 0x02, + 0x00, /* Servicing interval for data transfers : NA for Bulk */ + + /* Endpoint Descriptor for Consumer EP */ + 0x07, /* Descriptor size */ + 0x05, /* Endpoint Descriptor Type */ + 0x81, /* Endpoint address and description */ + 0x02, /* Bulk End point Type */ + 0x00, /* Max packet size = 512 bytes */ + 0x02, + 0x00 /* Servicing interval for data transfers : NA for Bulk */ +}; + +/* Bootloader Super Speed Configuration Descriptor */ +const unsigned char bl_ss_config_desc[] = +{ + /* Configuration Descriptor Type */ + 0x09, /* Descriptor Size */ + 0x02, /* Configuration Descriptor Type */ + 0x2C,0x00, /* Length of this descriptor and all sub descriptors */ + 0x01, /* Number of interfaces */ + 0x01, /* Configuration number */ + 0x00, /* COnfiguration string index */ + 0x80, /* Config characteristics - D6: Self power; D5: Remote Wakeup */ + 0x32, /* Max power consumption of device (in 8mA unit) : 400mA */ + + /* Interface Descriptor */ + 0x09, /* Descriptor size */ + 0x04, /* Interface Descriptor type */ + 0x00, /* Interface number */ + 0x00, /* Alternate setting number */ + 0x02, /* Number of end points */ + 0xFF, /* Interface class */ + 0x00, /* Interface sub class */ + 0x00, /* Interface protocol code */ + 0x00, /* Interface descriptor string index */ + + /* Endpoint Descriptor for Producer EP */ + 0x07, /* Descriptor size */ + 0x05, /* Endpoint Descriptor Type */ + 0x01, /* Endpoint address and description */ + 0x02, /* Bulk End point Type */ + 0x00,0x04, /* Max packet size = 1024 bytes */ + 0x00, /* Servicing interval for data transfers : NA for Bulk */ + + /* Super Speed Endpoint Companion Descriptor for Producer EP */ + 0x06, /* Descriptor size */ + 0x30, /* SS Endpoint Companion Descriptor Type */ + 0x00, /* Max no. of packets in a Burst : 0: Burst 1 packet at a time */ + 0x00, /* Max streams for Bulk EP = 0 (No streams)*/ + 0x00,0x00, /* Service interval for the EP : NA for Bulk */ + + /* Endpoint Descriptor for Consumer EP */ + 0x07, /* Descriptor size */ + 0x05, /* Endpoint Descriptor Type */ + 0x81, /* Endpoint address and description */ + 0x02, /* Bulk End point Type */ + 0x00,0x04, /* Max packet size = 1024 bytes */ + 0x00, /* Servicing interval for data transfers : NA for Bulk */ + + /* Super Speed Endpoint Companion Descriptor for Consumer EP */ + 0x06, /* Descriptor size */ + 0x30, /* SS Endpoint Companion Descriptor Type */ + 0x00, /* Max no. of packets in a Burst : 0: Burst 1 packet at a time */ + 0x00, /* Max streams for Bulk EP = 0 (No streams)*/ + 0x00,0x00 /* Service interval for the EP : NA for Bulk */ +}; + +/* Bootloader Product String Descriptor */ +const unsigned char bl_manufacturer_desc[] = +{ + 0x10, + 0x03, + 'C', 0x00, + 'y', 0x00, + 'p', 0x00, + 'r', 0x00, + 'e', 0x00, + 's', 0x00, + 's', 0x00 +}; + +/* Bootloader Manufacturer String Descriptor */ +const unsigned char bl_product_desc[] = +{ + 0x16, + 0x03, + 'W', 0x00, + 'e', 0x00, + 's', 0x00, + 't', 0x00, + 'B', 0x00, + 'r', 0x00, + 'i', 0x00, + 'd', 0x00, + 'g', 0x00, + 'e', 0x00 +}; + +/* Bootloader Device Serial String Descriptor */ +const unsigned char bl_dev_serial_desc [] = +{ + 0x1A, /* bLength */ + 0x03, /* bDescType */ + '0',0,'0',0,'0',0,'0',0,'0',0,'0',0, + '0',0,'0',0,'0',0,'4',0,'B',0,'E',0, + 0,0, /* long word align */ +}; + diff --git a/firmware/fx3/b200/bootloader/usb_descriptors.h b/firmware/fx3/b200/bootloader/usb_descriptors.h new file mode 100644 index 000000000..8a7942327 --- /dev/null +++ b/firmware/fx3/b200/bootloader/usb_descriptors.h @@ -0,0 +1,26 @@ +// +// Copyright 2019 Ettus Research, a National Instruments Brand +// +// SPDX-License-Identifier: GPL-3.0-or-later +// + +/* Bootloader's unique config and string descriptors. */ + +/* Bootloader Full Speed Configuration Descriptor */ +extern const unsigned char bl_fs_config_desc[]; + +/* Bootloader High Speed Configuration Descriptor */ +extern const unsigned char bl_hs_config_desc[]; + +/* Bootloader Super Speed Configuration Descriptor */ +extern const unsigned char bl_ss_config_desc[]; + +/* Bootloader Manufacturer String Descriptor */ +extern const unsigned char bl_manufacturer_desc[]; + +/* Bootloader Product String Descriptor */ +extern const unsigned char bl_product_desc[]; + +/* Bootloader Device Serial String Descriptor */ +extern const unsigned char bl_dev_serial_desc[]; + diff --git a/firmware/fx3/b200/common/common_const.h b/firmware/fx3/b200/common/common_const.h new file mode 100644 index 000000000..1b40a7fdd --- /dev/null +++ b/firmware/fx3/b200/common/common_const.h @@ -0,0 +1,51 @@ +// +// Copyright 2019 Ettus Research, a National Instruments Brand +// +// SPDX-License-Identifier: GPL-3.0-or-later +// + +#ifndef _COMMON_CONST_H +#define _COMMON_CONST_H + +#define EEPROM_REV_UNRECOGNIZED -1 + +#define EEPROM_SIGNATURE_ADDR 0x0000 +#define EEPROM_SIGNATURE_LENGTH 4 + +#define EEPROM_REV0_SIGNATURE 0xB2145943 +#define EEPROM_REV1_OR_GREATER_SIGNATURE 0xB01A5943 + +#define EEPROM_REV0_VID_ADDR 0x0006 +#define EEPROM_REV1_VID_ADDR 0x7F06 +#define EEPROM_VID_LENGTH 2 + +#define VID_ETTUS_RESEARCH 0x2500 +#define VID_NATIONAL_INSTRUMENTS 0x3923 +#define VID_CYPRESS 0x04B4 + +#define EEPROM_REV0_PID_ADDR 0x0004 +#define EEPROM_REV1_PID_ADDR 0x7F08 +#define EEPROM_PID_LENGTH 2 + +#define PID_ETTUS_B200_B210 0x0020 +#define PID_NI_USRP_2900 0x7813 +#define PID_NI_USRP_2901 0x7814 +#define PID_CYPRESS_DEFAULT 0x00F0 + +#define EEPROM_REV0_SERIAL_ADDR 0x04F7 +#define EEPROM_REV1_SERIAL_ADDR 0x7F23 +#define EEPROM_SERIAL_LENGTH 9 + +#define EEPROM_REV1_MAGIC_ADDR 0x7F00 +#define EEPROM_MAGIC_LENGTH 2 +#define EEPROM_EXPECTED_MAGIC 0xB200 + +#define EEPROM_REV1_REV_ADDR 0x7F02 +#define EEPROM_REV_LENGTH 2 +#define EEPROM_EXPECTED_REV 1 + +#define EEPROM_REV1_COMPAT_ADDR 0x7F04 +#define EEPROM_COMPAT_LENGTH 2 +#define EEPROM_EXPECTED_COMPAT 1 + +#endif /* _COMMON_CONST_H */ diff --git a/firmware/fx3/b200/common/common_descriptors.c b/firmware/fx3/b200/common/common_descriptors.c new file mode 100644 index 000000000..7cb670a4a --- /dev/null +++ b/firmware/fx3/b200/common/common_descriptors.c @@ -0,0 +1,237 @@ +// +// Copyright 2019 Ettus Research, a National Instruments Brand +// +// SPDX-License-Identifier: GPL-3.0-or-later +// + +/* This file contains all descriptors that are common between the bootloader + and firmware code. Non-const descriptors are modified at runtime based on + information read from the EEPROM. */ + +/* Standard Device Descriptor for USB 2.0 */ +unsigned char common_usb2_dev_desc[] = +{ + 0x12, /* Descriptor size */ + 0x01,/* CY_U3P_USB_DEVICE_DESCR Device descriptor type */ + 0x10,0x02, /* USB 2.10 */ + 0xFF, /* Device class */ + 0x00, /* Device sub-class */ + 0x00, /* Device protocol */ + 0x40, /* Maxpacket size for EP0 : 64 bytes */ + 0xB4,0x04, /* Vendor ID */ + 0xF0,0x00, /* Product ID */ + 0x00,0x00, /* Device release number */ + 0x01, /* Manufacture string index */ + 0x02, /* Product string index */ + 0x03, /* Serial number string index */ + 0x01 /* Number of configurations */ +}; + +/* Standard Device Descriptor for USB 3.0 */ +unsigned char common_usb3_dev_desc[] = +{ + 0x12, /* Descriptor size */ + 0x01,/* CY_U3P_USB_DEVICE_DESCR Device descriptor type */ + 0x00,0x03, /* USB 3.0 */ + 0xFF, /* Device class */ + 0x00, /* Device sub-class */ + 0x00, /* Device protocol */ + 0x09, /* Maxpacket size for EP0 : 2^9 */ + 0xB4,0x04, /* Vendor ID */ + 0xF0,0x00, /* Product ID */ + 0x00,0x00, /* Device release number */ + 0x01, /* Manufacture string index */ + 0x02, /* Product string index */ + 0x03, /* Serial number string index */ + 0x01 /* Number of configurations */ +}; + +/* Standard Device Qualifier Descriptor */ +const unsigned char common_dev_qual_desc[] = +{ + 0x0A, /* Descriptor size */ + 0x06,/* CY_U3P_USB_DEVQUAL_DESCR Device qualifier descriptor type */ + 0x00,0x02, /* USB 2.0 */ + 0xFF, /* Device class */ + 0x00, /* Device sub-class */ + 0x00, /* Device protocol */ + 0x40, /* Maxpacket size for EP0 : 64 bytes */ + 0x01, /* Number of configurations */ + 0x00 /* Reserved */ +}; + +/* Standard Binary Device Object Store Descriptor */ +const unsigned char common_usb_bos_desc[] = +{ + 0x05, /* Descriptor size */ + 0x0F,/* CY_U3P_BOS_DESCR Device descriptor type */ + 0x16,0x00, /* Length of this descriptor and all sub descriptors */ + 0x02, /* Number of device capability descriptors */ + + /* USB 2.0 extension */ + 0x07, /* Descriptor size */ + 0x10,/* CY_U3P_DEVICE_CAPB_DESCR Device capability type descriptor */ + 0x02,/* CY_U3P_USB2_EXTN_CAPB_TYPE USB 2.0 extension capability type */ + 0x02,0x00,0x00,0x00, /* Supported device level features: LPM support */ + + /* SuperSpeed device capability */ + 0x0A, /* Descriptor size */ + 0x10,/* CY_U3P_DEVICE_CAPB_DESCR Device capability type descriptor */ + 0x03,/* CY_U3P_SS_USB_CAPB_TYPE SuperSpeed device capability type */ + 0x00, /* Supported device level features */ + 0x0E,0x00, /* Speeds supported by the device : SS, HS and FS */ + 0x03, /* Functionality support */ + 0x00, /* U1 Device Exit latency */ + 0x00,0x00 /* U2 Device Exit latency */ +}; + +/* Standard Language ID String Descriptor */ +const unsigned char common_string_lang_id_desc[] = +{ + 0x04, /* Descriptor Size */ + 0x03,/* CY_U3P_USB_STRING_DESCR Device Descriptor Type */ + 0x09,0x04 /* Language ID supported */ +}; + + +/* Ettus Manufacturer String Descriptor */ +const unsigned char common_ettus_manufacturer_desc[] = +{ + 0x26, /* Descriptor Size */ + 0x03,/* CY_U3P_USB_STRING_DESCR Device Descriptor Type */ + 'E',0x00, + 't',0x00, + 't',0x00, + 'u',0x00, + 's',0x00, + ' ',0x00, + 'R',0x00, + 'e',0x00, + 's',0x00, + 'e',0x00, + 'a',0x00, + 'r',0x00, + 'c',0x00, + 'h',0x00, + ' ',0x00, + 'L',0x00, + 'L',0x00, + 'C',0x00 +}; + +/* NI Manufacturer String Descriptor */ +const unsigned char common_ni_manufacturer_desc[] = +{ + 0x36, /* Descriptor Size */ + 0x03,/* CY_U3P_USB_STRING_DESCR Device Descriptor Type */ + 'N',0x00, + 'a',0x00, + 't',0x00, + 'i',0x00, + 'o',0x00, + 'n',0x00, + 'a',0x00, + 'l',0x00, + ' ',0x00, + 'I',0x00, + 'n',0x00, + 's',0x00, + 't',0x00, + 'r',0x00, + 'u',0x00, + 'm',0x00, + 'e',0x00, + 'n',0x00, + 't',0x00, + 's',0x00, + ' ',0x00, + 'C',0x00, + 'o',0x00, + 'r',0x00, + 'p',0x00, + '.',0x00 +}; + + +/* Ettus Product String Descriptor */ +const unsigned char common_b200_product_desc[] = +{ + 0x14, /* Descriptor Size */ + 0x03,/* CY_U3P_USB_STRING_DESCR Device Descriptor Type */ + 'U',0x00, + 'S',0x00, + 'R',0x00, + 'P',0x00, + ' ',0x00, + 'B',0x00, + '2',0x00, + '0',0x00, + '0',0x00 +}; + +/* NI-USRP 2900 Product String Descriptor */ +const unsigned char common_niusrp_2900_product_desc[] = +{ + 0x1A, /* Descriptor Size */ + 0x03,/* CY_U3P_USB_STRING_DESCR Device Descriptor Type */ + 'N',0x00, + 'I',0x00, + ' ',0x00, + 'U',0x00, + 'S',0x00, + 'R',0x00, + 'P',0x00, + '-',0x00, + '2',0x00, + '9',0x00, + '0',0x00, + '0',0x00 +}; + +/* NI-USRP 2901 Product String Descriptor */ +const unsigned char common_niusrp_2901_product_desc[] = +{ + 0x1A, /* Descriptor Size */ + 0x03,/* CY_U3P_USB_STRING_DESCR Device Descriptor Type */ + 'N',0x00, + 'I',0x00, + ' ',0x00, + 'U',0x00, + 'S',0x00, + 'R',0x00, + 'P',0x00, + '-',0x00, + '2',0x00, + '9',0x00, + '0',0x00, + '1',0x00 +}; + +/* Unknown Product String Descriptor */ +const unsigned char common_unknown_desc[] = +{ + 0x10, /* Descriptor Size */ + 0x03,/* CY_U3P_USB_STRING_DESCR Device Descriptor Type */ + 'U',0x00, + 'n',0x00, + 'k',0x00, + 'n',0x00, + 'o',0x00, + 'w',0x00, + 'n',0x00 +}; + +unsigned char common_dev_serial_desc[] = +{ + 0x14, /* Descriptor Size */ + 0x03,/* CY_U3P_USB_STRING_DESCR Device Descriptor Type */ + '0', 0x00, + '0', 0x00, + '0', 0x00, + '0', 0x00, + '0', 0x00, + '0', 0x00, + '0', 0x00, + '0', 0x00, + '0', 0x00 +}; diff --git a/firmware/fx3/b200/common/common_descriptors.h b/firmware/fx3/b200/common/common_descriptors.h new file mode 100644 index 000000000..15acac3fa --- /dev/null +++ b/firmware/fx3/b200/common/common_descriptors.h @@ -0,0 +1,50 @@ +// +// Copyright 2019 Ettus Research, a National Instruments Brand +// +// SPDX-License-Identifier: GPL-3.0-or-later +// + +#ifndef _COMMON_DESCRIPTORS_H +#define _COMMON_DESCRIPTORS_H + +/* This file contains all descriptors that are common between the bootloader + and firmware code. Non-const descriptors are modified at runtime based on + information read from the EEPROM. */ + +/* Standard Device Descriptor for USB 2.0 */ +extern unsigned char common_usb2_dev_desc[]; + +/* Standard Device Descriptor for USB 3.0 */ +extern unsigned char common_usb3_dev_desc[]; + +/* Standard Device Qualifier Descriptor */ +extern const unsigned char common_dev_qual_desc[]; + +/* Standard Binary Device Object Store Descriptor */ +extern const unsigned char common_usb_bos_desc[]; + +/* Standard Language ID String Descriptor */ +extern const unsigned char common_string_lang_id_desc[]; + +/* Ettus Manufacturer String Descriptor */ +extern const unsigned char common_ettus_manufacturer_desc[]; + +/* NI Manufacturer String Descriptor */ +extern const unsigned char common_ni_manufacturer_desc[]; + +/* Ettus Product String Descriptor */ +extern const unsigned char common_b200_product_desc[]; + +/* NI-USRP 2900 Product String Descriptor */ +extern const unsigned char common_niusrp_2900_product_desc[]; + +/* NI-USRP 2901 Product String Descriptor */ +extern const unsigned char common_niusrp_2901_product_desc[]; + +/* Unknown Product String Descriptor */ +extern const unsigned char common_unknown_desc[]; + +/* Common Serial String Descriptor */ +extern unsigned char common_dev_serial_desc[]; + +#endif
\ No newline at end of file diff --git a/firmware/fx3/b200/common/common_helpers.c b/firmware/fx3/b200/common/common_helpers.c new file mode 100644 index 000000000..5a21a2106 --- /dev/null +++ b/firmware/fx3/b200/common/common_helpers.c @@ -0,0 +1,199 @@ +// +// Copyright 2019 Ettus Research, a National Instruments Brand +// +// SPDX-License-Identifier: GPL-3.0-or-later +// + +#include "common_helpers.h" +#include "common_const.h" +#include "common_descriptors.h" + +#define UNREAD 0xFFFF + +/* Check the rev, magic value, and eeprom compatibility field to determine if + our eeprom map is up-to-date with what is written on the device */ +int eeprom_is_readable(eeprom_read_t read_fn) { + /* Only check this once, then store that info */ + static int is_readable = UNREAD; + + if (is_readable != UNREAD) { + return is_readable; + } + + int rev = get_rev(read_fn); + + if (rev == EEPROM_REV_UNRECOGNIZED) + { + is_readable = 0; + return is_readable; + } + + + /* If rev is 0, there's no further checks available */ + if (rev == 0) + { + is_readable = 1; + return is_readable; + } + + /* For rev 1, check the EEPROM magic value and compat number */ + + if (rev == 1) { + { + uint8_t buffer[EEPROM_MAGIC_LENGTH]; + read_fn(EEPROM_REV1_MAGIC_ADDR, buffer, EEPROM_MAGIC_LENGTH); + if ((buffer[1] << 8 | buffer[0]) != EEPROM_EXPECTED_MAGIC) { + is_readable = 0; + return is_readable; + } + } + { + uint8_t buffer[EEPROM_COMPAT_LENGTH]; + read_fn(EEPROM_REV1_COMPAT_ADDR, buffer, EEPROM_COMPAT_LENGTH); + if ((buffer[1] << 8 | buffer[0]) > EEPROM_EXPECTED_COMPAT) { + is_readable = 0; + return is_readable; + } + } + is_readable = 1; + return is_readable; + } + + /* some other unrecognized rev */ + is_readable = 0; + return is_readable; +} + +/* Read the EEPROM layout revision number from EEPROM using the function + specified */ +int get_rev(eeprom_read_t read_fn) +{ + /* Only check the rev once, then store that info */ + static int rev = UNREAD; + + if (rev != UNREAD) { + return rev; + } + + uint8_t buffer[EEPROM_SIGNATURE_LENGTH]; + read_fn(EEPROM_SIGNATURE_ADDR, buffer, EEPROM_SIGNATURE_LENGTH); + + const uint32_t signature = buffer[3] << 24 | buffer[2] << 16 | buffer[1] << 8 + | buffer[0]; + if (signature == EEPROM_REV0_SIGNATURE) { + rev = 0; + } else if (signature == EEPROM_REV1_OR_GREATER_SIGNATURE) { + rev = 1; + } else { + rev = EEPROM_REV_UNRECOGNIZED; + } + return rev; +} + + + +/* Read the vendor ID from EEPROM using the function specified*/ +uint16_t get_vid(eeprom_read_t read_fn) +{ + static uint16_t vid = UNREAD; + + if (vid != UNREAD) { + return vid; + } + + if (!eeprom_is_readable(read_fn)) { + vid = VID_CYPRESS; + return vid; + } + + // eeprom_is_readable guarantees rev is valid + int rev = get_rev(read_fn); + + const uint16_t addr = (rev == 0) ? EEPROM_REV0_VID_ADDR : EEPROM_REV1_VID_ADDR; + + uint8_t buffer[EEPROM_VID_LENGTH]; + read_fn(addr, buffer, EEPROM_VID_LENGTH); + vid = buffer[1] << 8 | buffer[0]; + return vid; +} + +/* Read the product ID from EEPROM using the function specified*/ +uint16_t get_pid(eeprom_read_t read_fn) +{ + static uint16_t pid = UNREAD; + + if (pid != UNREAD) { + return pid; + } + + if (!eeprom_is_readable(read_fn)) { + pid = PID_CYPRESS_DEFAULT; + return pid; + } + + // eeprom_is_readable guarantees rev is valid + int rev = get_rev(read_fn); + + const uint16_t addr = (rev == 0) ? EEPROM_REV0_PID_ADDR : EEPROM_REV1_PID_ADDR; + + uint8_t buffer[EEPROM_PID_LENGTH]; + read_fn(addr, buffer, EEPROM_PID_LENGTH); + pid = buffer[1] << 8 | buffer[0]; + return pid; +} + +/* Read the vendor ID from EEPROM using the function specified */ +const uint8_t* get_serial_string_descriptor(eeprom_read_t read_fn) +{ + static uint8_t* serial_string_descriptor = 0; + if (serial_string_descriptor) { + return serial_string_descriptor; + } + + /* All code paths will eventually return this value, but some will modify + it beforehand */ + serial_string_descriptor = common_dev_serial_desc; + + if (!eeprom_is_readable(read_fn)) { + return serial_string_descriptor; + } + + // eeprom_is_readable guarantees rev is valid + int rev = get_rev(read_fn); + + const uint16_t addr = (rev == 0) ? EEPROM_REV0_SERIAL_ADDR : EEPROM_REV1_SERIAL_ADDR; + + uint8_t buffer[EEPROM_SERIAL_LENGTH]; + read_fn(addr, buffer, EEPROM_SERIAL_LENGTH); + int i; + for (i = 0; i < EEPROM_SERIAL_LENGTH; ++i) { + common_dev_serial_desc[2 + i * 2] = buffer[i]; + } + return serial_string_descriptor; +} + +/* Return the string descriptor based on the VID given */ +const uint8_t* get_manufacturer_string_descriptor(uint16_t vid) +{ + if (vid == VID_ETTUS_RESEARCH) { + return common_ettus_manufacturer_desc; + } else if (vid == VID_NATIONAL_INSTRUMENTS) { + return common_ni_manufacturer_desc; + } else { + return common_unknown_desc; + } +} + +/* Return the string descriptor based on the PID given */ +const uint8_t* get_product_string_descriptor(uint16_t pid) +{ + if (pid == PID_ETTUS_B200_B210) { + return common_b200_product_desc; + } else if (pid == PID_NI_USRP_2900) { + return common_niusrp_2900_product_desc; + } else if (pid == PID_NI_USRP_2901) { + return common_niusrp_2901_product_desc; + } else { + return common_unknown_desc; + } +} diff --git a/firmware/fx3/b200/common/common_helpers.h b/firmware/fx3/b200/common/common_helpers.h new file mode 100644 index 000000000..8ff28fb09 --- /dev/null +++ b/firmware/fx3/b200/common/common_helpers.h @@ -0,0 +1,34 @@ +// +// Copyright 2019 Ettus Research, a National Instruments Brand +// +// SPDX-License-Identifier: GPL-3.0-or-later +// + +#ifndef _COMMON_HELPERS_H +#define _COMMON_HELPERS_H + +#include "cyu3types.h" + +typedef void (*eeprom_read_t)(uint16_t, uint8_t*, uint8_t); + +/* Read the EEPROM layout revision number from EEPROM using the function + specified */ +int get_rev(eeprom_read_t read_fn); + +/* Read the vendor ID from EEPROM using the function specified*/ +uint16_t get_vid(eeprom_read_t read_fn); + +/* Read the product ID from EEPROM using the function specified*/ +uint16_t get_pid(eeprom_read_t read_fn); + +/* Read the vendor ID from EEPROM using the function specified + Buffer must be at least length 20 */ +const uint8_t* get_serial_string_descriptor(eeprom_read_t read_fn); + +/* Return the string descriptor based on the VID given */ +const uint8_t* get_manufacturer_string_descriptor(uint16_t vid); + +/* Return the string descriptor based on the PID given */ +const uint8_t* get_product_string_descriptor(uint16_t pid); + +#endif /* _COMMON_HELPERS_H */ diff --git a/firmware/fx3/b200/b200_main.h b/firmware/fx3/b200/firmware/b200_const.h index ddcc504b5..886643021 100644 --- a/firmware/fx3/b200/b200_main.h +++ b/firmware/fx3/b200/firmware/b200_const.h @@ -1,9 +1,12 @@ // // Copyright 2013-2014 Ettus Research LLC +// Copyright 2019 Ettus Research, a National Instruments Brand +// +// SPDX-License-Identifier: GPL-3.0-or-later // -#ifndef _B200_MAIN_H -#define _B200_MAIN_H +#ifndef _B200_CONST_H +#define _B200_CONST_H #include "cyu3externcstart.h" @@ -116,25 +119,6 @@ #define CTRL_COMM_PPORT_SOCKET CY_U3P_PIB_SOCKET_2 #define CTRL_RESP_PPORT_SOCKET CY_U3P_PIB_SOCKET_3 - -/* Descriptor definitions for USB enumerations. */ -extern uint8_t b200_usb2_dev_desc[]; -extern uint8_t b200_usb3_dev_desc[]; -extern const uint8_t b200_dev_qual_desc[]; -extern const uint8_t b200_usb_fs_config_desc[]; -extern const uint8_t b200_usb_hs_config_desc[]; -extern const uint8_t b200_usb_bos_desc[]; -extern const uint8_t b200_usb_ss_config_desc[]; -extern const uint8_t b200_string_lang_id_desc[]; -extern const uint8_t b200_usb_manufacture_desc[]; -extern const uint8_t b200_usb_product_desc[]; -extern const uint8_t niusrp_usb_manufacture_desc[]; -extern const uint8_t niusrp_2900_usb_product_desc[]; -extern const uint8_t niusrp_2901_usb_product_desc[]; -extern const uint8_t unknown_desc[]; -extern uint8_t dev_serial[]; - - #include "cyu3externcend.h" -#endif /* _B200_MAIN_H */ +#endif /* _B200_CONST_H */ diff --git a/firmware/fx3/b200/b200_gpifconfig.h b/firmware/fx3/b200/firmware/b200_gpifconfig.h index a6a24e0c5..aa1c36551 100755..100644 --- a/firmware/fx3/b200/b200_gpifconfig.h +++ b/firmware/fx3/b200/firmware/b200_gpifconfig.h @@ -1,176 +1,176 @@ -/*
- * Project Name: ssf2-edit.cyfx
- * Time : 11/17/2014 13:01:01
- * Device Type: FX3
- * Project Type: GPIF2
- *
- *
- *
- *
- * This is a generated file and should not be modified
- * This file need to be included only once in the firmware
- * This file is generated by Gpif2 designer tool version - 1.0.837.1
- *
- */
-
-#ifndef _INCLUDED_CYFXGPIF2CONFIG_
-#define _INCLUDED_CYFXGPIF2CONFIG_
-#include "cyu3types.h"
-#include "cyu3gpif.h"
-
-/* Summary
- Number of states in the state machine
- */
-#define CY_NUMBER_OF_STATES 7
-
-/* Summary
- Mapping of user defined state names to state indices
- */
-#define RESET 0
-#define IDLE 1
-#define READ 2
-#define WRITE 3
-#define SHORT_PKT 4
-#define ZLP 5
-#define DSS_STATE 6
-
-
-/* Summary
- Initial value of early outputs from the state machine.
- */
-#define ALPHA_RESET 0xC
-
-
-/* Summary
- Transition function values used in the state machine.
- */
-uint16_t CyFxGpifTransition[] = {
- 0x0000, 0x8080, 0x2222, 0x5555, 0x7F7F, 0x1F1F, 0x8888
-};
-
-/* Summary
- Table containing the transition information for various states.
- This table has to be stored in the WAVEFORM Registers.
- This array consists of non-replicated waveform descriptors and acts as a
- waveform table.
- */
-CyU3PGpifWaveData CyFxGpifWavedata[] = {
- {{0x1E086001,0x000302C4,0x80000000},{0x00000000,0x00000000,0x00000000}},
- {{0x4E080302,0x00000300,0x80000000},{0x1E086006,0x000302C4,0x80000000}},
- {{0x1E086001,0x000302C4,0x80000000},{0x4E040704,0x20000300,0xC0100000}},
- {{0x4E080302,0x00000300,0x80000000},{0x1E086001,0x000302C4,0x80000000}},
- {{0x00000000,0x00000000,0x00000000},{0x00000000,0x00000000,0x00000000}},
- {{0x00000000,0x00000000,0x00000000},{0x3E738705,0x00000300,0xC0100000}},
- {{0x00000000,0x00000000,0x00000000},{0x5E002703,0x2003030C,0x80000000}},
- {{0x00000000,0x00000000,0x00000000},{0x4E040704,0x20000300,0xC0100000}}
-};
-
-/* Summary
- Table that maps state indices to the descriptor table indices.
- */
-uint8_t CyFxGpifWavedataPosition[] = {
- 0,1,0,2,0,0,3,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,
- 4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,
- 0,5,0,2,0,0,5,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,
- 4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,
- 0,6,0,2,0,0,6,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,
- 4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,
- 0,7,0,2,0,0,7
-};
-
-/* Summary
- GPIF II configuration register values.
- */
-uint32_t CyFxGpifRegValue[] = {
- 0x80000380, /* CY_U3P_PIB_GPIF_CONFIG */
- 0x000010AC, /* CY_U3P_PIB_GPIF_BUS_CONFIG */
- 0x01070002, /* CY_U3P_PIB_GPIF_BUS_CONFIG2 */
- 0x00000044, /* CY_U3P_PIB_GPIF_AD_CONFIG */
- 0x00000000, /* CY_U3P_PIB_GPIF_STATUS */
- 0x00000000, /* CY_U3P_PIB_GPIF_INTR */
- 0x00000000, /* CY_U3P_PIB_GPIF_INTR_MASK */
- 0x00000082, /* CY_U3P_PIB_GPIF_SERIAL_IN_CONFIG */
- 0x00000782, /* CY_U3P_PIB_GPIF_SERIAL_OUT_CONFIG */
- 0x00000500, /* CY_U3P_PIB_GPIF_CTRL_BUS_DIRECTION */
- 0x0000FFCF, /* CY_U3P_PIB_GPIF_CTRL_BUS_DEFAULT */
- 0x000000BF, /* CY_U3P_PIB_GPIF_CTRL_BUS_POLARITY */
- 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_TOGGLE */
- 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */
- 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */
- 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */
- 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */
- 0x00000018, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */
- 0x00000019, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */
- 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */
- 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */
- 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */
- 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */
- 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */
- 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */
- 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */
- 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */
- 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */
- 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */
- 0x00000006, /* CY_U3P_PIB_GPIF_CTRL_COUNT_CONFIG */
- 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_COUNT_RESET */
- 0x0000FFFF, /* CY_U3P_PIB_GPIF_CTRL_COUNT_LIMIT */
- 0x0000010A, /* CY_U3P_PIB_GPIF_ADDR_COUNT_CONFIG */
- 0x00000000, /* CY_U3P_PIB_GPIF_ADDR_COUNT_RESET */
- 0x0000FFFF, /* CY_U3P_PIB_GPIF_ADDR_COUNT_LIMIT */
- 0x00000000, /* CY_U3P_PIB_GPIF_STATE_COUNT_CONFIG */
- 0x0000FFFF, /* CY_U3P_PIB_GPIF_STATE_COUNT_LIMIT */
- 0x0000010A, /* CY_U3P_PIB_GPIF_DATA_COUNT_CONFIG */
- 0x00000000, /* CY_U3P_PIB_GPIF_DATA_COUNT_RESET */
- 0x0000FFFF, /* CY_U3P_PIB_GPIF_DATA_COUNT_LIMIT */
- 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_COMP_VALUE */
- 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_COMP_MASK */
- 0x00000000, /* CY_U3P_PIB_GPIF_DATA_COMP_VALUE */
- 0x00000000, /* CY_U3P_PIB_GPIF_DATA_COMP_MASK */
- 0x00000000, /* CY_U3P_PIB_GPIF_ADDR_COMP_VALUE */
- 0x00000000, /* CY_U3P_PIB_GPIF_ADDR_COMP_MASK */
- 0x00000000, /* CY_U3P_PIB_GPIF_DATA_CTRL */
- 0x00000000, /* CY_U3P_PIB_GPIF_INGRESS_DATA */
- 0x00000000, /* CY_U3P_PIB_GPIF_INGRESS_DATA */
- 0x00000000, /* CY_U3P_PIB_GPIF_INGRESS_DATA */
- 0x00000000, /* CY_U3P_PIB_GPIF_INGRESS_DATA */
- 0x00000000, /* CY_U3P_PIB_GPIF_EGRESS_DATA */
- 0x00000000, /* CY_U3P_PIB_GPIF_EGRESS_DATA */
- 0x00000000, /* CY_U3P_PIB_GPIF_EGRESS_DATA */
- 0x00000000, /* CY_U3P_PIB_GPIF_EGRESS_DATA */
- 0x00000000, /* CY_U3P_PIB_GPIF_INGRESS_ADDRESS */
- 0x00000000, /* CY_U3P_PIB_GPIF_INGRESS_ADDRESS */
- 0x00000000, /* CY_U3P_PIB_GPIF_INGRESS_ADDRESS */
- 0x00000000, /* CY_U3P_PIB_GPIF_INGRESS_ADDRESS */
- 0x00000000, /* CY_U3P_PIB_GPIF_EGRESS_ADDRESS */
- 0x00000000, /* CY_U3P_PIB_GPIF_EGRESS_ADDRESS */
- 0x00000000, /* CY_U3P_PIB_GPIF_EGRESS_ADDRESS */
- 0x00000000, /* CY_U3P_PIB_GPIF_EGRESS_ADDRESS */
- 0x80010400, /* CY_U3P_PIB_GPIF_THREAD_CONFIG */
- 0x80010401, /* CY_U3P_PIB_GPIF_THREAD_CONFIG */
- 0x80010402, /* CY_U3P_PIB_GPIF_THREAD_CONFIG */
- 0x80010403, /* CY_U3P_PIB_GPIF_THREAD_CONFIG */
- 0x00000000, /* CY_U3P_PIB_GPIF_LAMBDA_STAT */
- 0x00000000, /* CY_U3P_PIB_GPIF_ALPHA_STAT */
- 0x00000000, /* CY_U3P_PIB_GPIF_BETA_STAT */
- 0x000C0000, /* CY_U3P_PIB_GPIF_WAVEFORM_CTRL_STAT */
- 0x00000000, /* CY_U3P_PIB_GPIF_WAVEFORM_SWITCH */
- 0x00000000, /* CY_U3P_PIB_GPIF_WAVEFORM_SWITCH_TIMEOUT */
- 0x00000000, /* CY_U3P_PIB_GPIF_CRC_CONFIG */
- 0x00000000, /* CY_U3P_PIB_GPIF_CRC_DATA */
- 0xFFFFFFC1 /* CY_U3P_PIB_GPIF_BETA_DEASSERT */
-};
-
-/* Summary
- This structure holds all the configuration inputs for the GPIF II.
- */
-const CyU3PGpifConfig_t CyFxGpifConfig = {
- (uint16_t)(sizeof(CyFxGpifWavedataPosition)/sizeof(uint8_t)),
- CyFxGpifWavedata,
- CyFxGpifWavedataPosition,
- (uint16_t)(sizeof(CyFxGpifTransition)/sizeof(uint16_t)),
- CyFxGpifTransition,
- (uint16_t)(sizeof(CyFxGpifRegValue)/sizeof(uint32_t)),
- CyFxGpifRegValue
-};
-
-#endif /* _INCLUDED_CYFXGPIF2CONFIG_ */
+/* + * Project Name: ssf2-edit.cyfx + * Time : 11/17/2014 13:01:01 + * Device Type: FX3 + * Project Type: GPIF2 + * + * + * + * + * This is a generated file and should not be modified + * This file need to be included only once in the firmware + * This file is generated by Gpif2 designer tool version - 1.0.837.1 + * + */ + +#ifndef _INCLUDED_CYFXGPIF2CONFIG_ +#define _INCLUDED_CYFXGPIF2CONFIG_ +#include "cyu3types.h" +#include "cyu3gpif.h" + +/* Summary + Number of states in the state machine + */ +#define CY_NUMBER_OF_STATES 7 + +/* Summary + Mapping of user defined state names to state indices + */ +#define RESET 0 +#define IDLE 1 +#define READ 2 +#define WRITE 3 +#define SHORT_PKT 4 +#define ZLP 5 +#define DSS_STATE 6 + + +/* Summary + Initial value of early outputs from the state machine. + */ +#define ALPHA_RESET 0xC + + +/* Summary + Transition function values used in the state machine. + */ +uint16_t CyFxGpifTransition[] = { + 0x0000, 0x8080, 0x2222, 0x5555, 0x7F7F, 0x1F1F, 0x8888 +}; + +/* Summary + Table containing the transition information for various states. + This table has to be stored in the WAVEFORM Registers. + This array consists of non-replicated waveform descriptors and acts as a + waveform table. + */ +CyU3PGpifWaveData CyFxGpifWavedata[] = { + {{0x1E086001,0x000302C4,0x80000000},{0x00000000,0x00000000,0x00000000}}, + {{0x4E080302,0x00000300,0x80000000},{0x1E086006,0x000302C4,0x80000000}}, + {{0x1E086001,0x000302C4,0x80000000},{0x4E040704,0x20000300,0xC0100000}}, + {{0x4E080302,0x00000300,0x80000000},{0x1E086001,0x000302C4,0x80000000}}, + {{0x00000000,0x00000000,0x00000000},{0x00000000,0x00000000,0x00000000}}, + {{0x00000000,0x00000000,0x00000000},{0x3E738705,0x00000300,0xC0100000}}, + {{0x00000000,0x00000000,0x00000000},{0x5E002703,0x2003030C,0x80000000}}, + {{0x00000000,0x00000000,0x00000000},{0x4E040704,0x20000300,0xC0100000}} +}; + +/* Summary + Table that maps state indices to the descriptor table indices. + */ +uint8_t CyFxGpifWavedataPosition[] = { + 0,1,0,2,0,0,3,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4, + 4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4, + 0,5,0,2,0,0,5,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4, + 4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4, + 0,6,0,2,0,0,6,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4, + 4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4,4, + 0,7,0,2,0,0,7 +}; + +/* Summary + GPIF II configuration register values. + */ +uint32_t CyFxGpifRegValue[] = { + 0x80000380, /* CY_U3P_PIB_GPIF_CONFIG */ + 0x000010AC, /* CY_U3P_PIB_GPIF_BUS_CONFIG */ + 0x01070002, /* CY_U3P_PIB_GPIF_BUS_CONFIG2 */ + 0x00000044, /* CY_U3P_PIB_GPIF_AD_CONFIG */ + 0x00000000, /* CY_U3P_PIB_GPIF_STATUS */ + 0x00000000, /* CY_U3P_PIB_GPIF_INTR */ + 0x00000000, /* CY_U3P_PIB_GPIF_INTR_MASK */ + 0x00000082, /* CY_U3P_PIB_GPIF_SERIAL_IN_CONFIG */ + 0x00000782, /* CY_U3P_PIB_GPIF_SERIAL_OUT_CONFIG */ + 0x00000500, /* CY_U3P_PIB_GPIF_CTRL_BUS_DIRECTION */ + 0x0000FFCF, /* CY_U3P_PIB_GPIF_CTRL_BUS_DEFAULT */ + 0x000000BF, /* CY_U3P_PIB_GPIF_CTRL_BUS_POLARITY */ + 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_TOGGLE */ + 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */ + 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */ + 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */ + 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */ + 0x00000018, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */ + 0x00000019, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */ + 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */ + 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */ + 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */ + 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */ + 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */ + 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */ + 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */ + 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */ + 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */ + 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_BUS_SELECT */ + 0x00000006, /* CY_U3P_PIB_GPIF_CTRL_COUNT_CONFIG */ + 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_COUNT_RESET */ + 0x0000FFFF, /* CY_U3P_PIB_GPIF_CTRL_COUNT_LIMIT */ + 0x0000010A, /* CY_U3P_PIB_GPIF_ADDR_COUNT_CONFIG */ + 0x00000000, /* CY_U3P_PIB_GPIF_ADDR_COUNT_RESET */ + 0x0000FFFF, /* CY_U3P_PIB_GPIF_ADDR_COUNT_LIMIT */ + 0x00000000, /* CY_U3P_PIB_GPIF_STATE_COUNT_CONFIG */ + 0x0000FFFF, /* CY_U3P_PIB_GPIF_STATE_COUNT_LIMIT */ + 0x0000010A, /* CY_U3P_PIB_GPIF_DATA_COUNT_CONFIG */ + 0x00000000, /* CY_U3P_PIB_GPIF_DATA_COUNT_RESET */ + 0x0000FFFF, /* CY_U3P_PIB_GPIF_DATA_COUNT_LIMIT */ + 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_COMP_VALUE */ + 0x00000000, /* CY_U3P_PIB_GPIF_CTRL_COMP_MASK */ + 0x00000000, /* CY_U3P_PIB_GPIF_DATA_COMP_VALUE */ + 0x00000000, /* CY_U3P_PIB_GPIF_DATA_COMP_MASK */ + 0x00000000, /* CY_U3P_PIB_GPIF_ADDR_COMP_VALUE */ + 0x00000000, /* CY_U3P_PIB_GPIF_ADDR_COMP_MASK */ + 0x00000000, /* CY_U3P_PIB_GPIF_DATA_CTRL */ + 0x00000000, /* CY_U3P_PIB_GPIF_INGRESS_DATA */ + 0x00000000, /* CY_U3P_PIB_GPIF_INGRESS_DATA */ + 0x00000000, /* CY_U3P_PIB_GPIF_INGRESS_DATA */ + 0x00000000, /* CY_U3P_PIB_GPIF_INGRESS_DATA */ + 0x00000000, /* CY_U3P_PIB_GPIF_EGRESS_DATA */ + 0x00000000, /* CY_U3P_PIB_GPIF_EGRESS_DATA */ + 0x00000000, /* CY_U3P_PIB_GPIF_EGRESS_DATA */ + 0x00000000, /* CY_U3P_PIB_GPIF_EGRESS_DATA */ + 0x00000000, /* CY_U3P_PIB_GPIF_INGRESS_ADDRESS */ + 0x00000000, /* CY_U3P_PIB_GPIF_INGRESS_ADDRESS */ + 0x00000000, /* CY_U3P_PIB_GPIF_INGRESS_ADDRESS */ + 0x00000000, /* CY_U3P_PIB_GPIF_INGRESS_ADDRESS */ + 0x00000000, /* CY_U3P_PIB_GPIF_EGRESS_ADDRESS */ + 0x00000000, /* CY_U3P_PIB_GPIF_EGRESS_ADDRESS */ + 0x00000000, /* CY_U3P_PIB_GPIF_EGRESS_ADDRESS */ + 0x00000000, /* CY_U3P_PIB_GPIF_EGRESS_ADDRESS */ + 0x80010400, /* CY_U3P_PIB_GPIF_THREAD_CONFIG */ + 0x80010401, /* CY_U3P_PIB_GPIF_THREAD_CONFIG */ + 0x80010402, /* CY_U3P_PIB_GPIF_THREAD_CONFIG */ + 0x80010403, /* CY_U3P_PIB_GPIF_THREAD_CONFIG */ + 0x00000000, /* CY_U3P_PIB_GPIF_LAMBDA_STAT */ + 0x00000000, /* CY_U3P_PIB_GPIF_ALPHA_STAT */ + 0x00000000, /* CY_U3P_PIB_GPIF_BETA_STAT */ + 0x000C0000, /* CY_U3P_PIB_GPIF_WAVEFORM_CTRL_STAT */ + 0x00000000, /* CY_U3P_PIB_GPIF_WAVEFORM_SWITCH */ + 0x00000000, /* CY_U3P_PIB_GPIF_WAVEFORM_SWITCH_TIMEOUT */ + 0x00000000, /* CY_U3P_PIB_GPIF_CRC_CONFIG */ + 0x00000000, /* CY_U3P_PIB_GPIF_CRC_DATA */ + 0xFFFFFFC1 /* CY_U3P_PIB_GPIF_BETA_DEASSERT */ +}; + +/* Summary + This structure holds all the configuration inputs for the GPIF II. + */ +const CyU3PGpifConfig_t CyFxGpifConfig = { + (uint16_t)(sizeof(CyFxGpifWavedataPosition)/sizeof(uint8_t)), + CyFxGpifWavedata, + CyFxGpifWavedataPosition, + (uint16_t)(sizeof(CyFxGpifTransition)/sizeof(uint16_t)), + CyFxGpifTransition, + (uint16_t)(sizeof(CyFxGpifRegValue)/sizeof(uint32_t)), + CyFxGpifRegValue +}; + +#endif /* _INCLUDED_CYFXGPIF2CONFIG_ */ diff --git a/firmware/fx3/b200/b200_i2c.c b/firmware/fx3/b200/firmware/b200_i2c.c index c6fa67c77..c6fa67c77 100644 --- a/firmware/fx3/b200/b200_i2c.c +++ b/firmware/fx3/b200/firmware/b200_i2c.c diff --git a/firmware/fx3/b200/b200_i2c.h b/firmware/fx3/b200/firmware/b200_i2c.h index c5c781946..c5c781946 100644 --- a/firmware/fx3/b200/b200_i2c.h +++ b/firmware/fx3/b200/firmware/b200_i2c.h diff --git a/firmware/fx3/b200/b200_main.c b/firmware/fx3/b200/firmware/b200_main.c index ac4988ae0..26507dda7 100644 --- a/firmware/fx3/b200/b200_main.c +++ b/firmware/fx3/b200/firmware/b200_main.c @@ -1,5 +1,8 @@ // // Copyright 2013-2015 Ettus Research LLC +// Copyright 2019 Ettus Research, a National Instruments Brand +// +// SPDX-License-Identifier: GPL-3.0-or-later // /* This file defines the application that runs on the Cypress FX3 device, and @@ -10,10 +13,14 @@ #include <stdarg.h> #include <stdio.h> -#include "b200_main.h" +#include "b200_const.h" #include "b200_gpifconfig.h" #include "b200_i2c.h" +#include "common_helpers.h" +#include "common_descriptors.h" +#include "b200_usb_descriptors.h" + #include "cyu3dma.h" #include "cyu3error.h" #include "cyu3gpif.h" @@ -789,6 +796,10 @@ void reset_gpif(void) { g_fx3_state = STATE_RUNNING; } +void eeprom_read(uint16_t addr, uint8_t* buffer, uint8_t length) +{ + CyFxUsbI2cTransfer(addr, 0xA0, length, buffer, CyTrue); +} CyU3PReturnStatus_t b200_set_io_matrix(CyBool_t fpga_config_mode) { CyU3PIoMatrixConfig_t io_config_matrix; @@ -1571,13 +1582,16 @@ CyBool_t usb_setup_callback(uint32_t data0, uint32_t data1) { && (bRequest == CY_U3P_USB_SC_GET_DESCRIPTOR) \ && (wValue == ((CY_U3P_USB_STRING_DESCR << 8) | 0xEE))) { /* Make sure we do not send more data than requested. */ - if(wLength > b200_usb_product_desc[0]) { - wLength = b200_usb_product_desc[0]; + const uint8_t* product_desc = get_product_string_descriptor( + get_pid(&eeprom_read)); + if (wLength > product_desc[0]) + { + wLength = product_desc[0]; } //msg("MS string desc"); - CyU3PUsbSendEP0Data(wLength, ((uint8_t *) b200_usb_product_desc)); + CyU3PUsbSendEP0Data(wLength, ((uint8_t*)product_desc)); handled = CyTrue; } @@ -2160,7 +2174,6 @@ void b200_gpif_init(void) { CyU3PPibRegisterCallback(gpif_error_cb, CYU3P_PIB_INTR_ERROR); } - /*! Start and configure the FX3's SPI module. * * This module is used for programming the FPGA. After the FPGA is configured, @@ -2222,115 +2235,66 @@ void b200_usb_init(void) { CyU3PUsbRegisterLPMRequestCallback(lpm_request_callback); /* Check to see if a VID/PID is in the EEPROM that we should use. */ - uint8_t valid[4]; - uint8_t vidpid[4]; - CyU3PMemSet(valid, 0, 4); - CyFxUsbI2cTransfer(0x0, 0xA0, 4, valid, CyTrue); - if(*((uint32_t *) &(valid[0])) == 0xB2145943) { - - /* Pull the programmed device serial out of the i2c EEPROM, and copy the - * characters into the device serial string, which is then advertised as - * part of the USB descriptors. */ - CyU3PMemSet(vidpid, 0, 4); - CyFxUsbI2cTransfer(0x4, 0xA0, 4, vidpid, CyTrue); - b200_usb2_dev_desc[8] = vidpid[2]; - b200_usb2_dev_desc[9] = vidpid[3]; - b200_usb2_dev_desc[10] = vidpid[0]; - b200_usb2_dev_desc[11] = vidpid[1]; - - b200_usb3_dev_desc[8] = vidpid[2]; - b200_usb3_dev_desc[9] = vidpid[3]; - b200_usb3_dev_desc[10] = vidpid[0]; - b200_usb3_dev_desc[11] = vidpid[1]; - } + const uint16_t vid = get_vid(&eeprom_read); + const uint16_t pid = get_pid(&eeprom_read); - /* We support two VIDs: - * Ettus Research: 0x2500 - * National Instruments: 0x3923 - * - * We support three PIDs: - * Ettus B200/B210: 0x0020 - * NI USRP-2900: 0x7813 - * NI USRP-2901: 0x7814 - */ - uint8_t *mfr_string = NULL; - uint8_t *product_string = NULL; - if((vidpid[3] == 0x25) && (vidpid[2] == 0x00)) { - mfr_string = b200_usb_manufacture_desc; - product_string = b200_usb_product_desc; - } else if((vidpid[3] == 0x39) && (vidpid[2] == 0x23)) { - mfr_string = niusrp_usb_manufacture_desc; - - if((vidpid[1] == 0x78) && (vidpid[0] == 0x13)) { - product_string = niusrp_2900_usb_product_desc; - } else if((vidpid[1] == 0x78) && (vidpid[0] == 0x14)) { - product_string = niusrp_2901_usb_product_desc; - } else { - product_string = unknown_desc; - } - } else { - mfr_string = unknown_desc; - product_string = unknown_desc; - } + common_usb2_dev_desc[8] = vid & 0xFF; + common_usb2_dev_desc[9] = vid >> 8; + common_usb2_dev_desc[10] = pid & 0xFF; + common_usb2_dev_desc[11] = pid >> 8; - uint8_t ascii_serial[9]; - CyU3PMemSet(ascii_serial, 0, 9); - CyFxUsbI2cTransfer(0x4f7, 0xA0, 9, ascii_serial, CyTrue); - uint8_t count; - dev_serial[0] = 2; - for(count = 0; count < 9; count++) { - uint8_t byte = ascii_serial[count]; - if (byte < 32 || byte > 127) break; - dev_serial[2 + (count * 2)] = byte; - // FIXME: Set count*2 + 1 = 0x00 ? - dev_serial[0] += 2; - } + common_usb3_dev_desc[8] = vid & 0xFF; + common_usb3_dev_desc[9] = vid >> 8; + common_usb3_dev_desc[10] = pid & 0xFF; + common_usb3_dev_desc[11] = pid >> 8; + + const uint8_t *mfr_string = get_manufacturer_string_descriptor(vid); + const uint8_t *product_string = get_product_string_descriptor(pid); + const uint8_t *serial_string = get_serial_string_descriptor(&eeprom_read); /* Set our USB enumeration descriptors! Note that there are different * function calls for each USB speed: FS, HS, SS. */ /* Device descriptors */ CyU3PUsbSetDesc(CY_U3P_USB_SET_HS_DEVICE_DESCR, 0, - (uint8_t *) b200_usb2_dev_desc); + (uint8_t *)common_usb2_dev_desc); CyU3PUsbSetDesc(CY_U3P_USB_SET_SS_DEVICE_DESCR, 0, - (uint8_t *) b200_usb3_dev_desc); + (uint8_t *)common_usb3_dev_desc); /* Device qualifier descriptors */ CyU3PUsbSetDesc(CY_U3P_USB_SET_DEVQUAL_DESCR, 0, - (uint8_t *) b200_dev_qual_desc); + (uint8_t *)common_dev_qual_desc); /* Configuration descriptors */ CyU3PUsbSetDesc(CY_U3P_USB_SET_HS_CONFIG_DESCR, 0, - (uint8_t *) b200_usb_hs_config_desc); + (uint8_t *)b200_usb_hs_config_desc); CyU3PUsbSetDesc(CY_U3P_USB_SET_FS_CONFIG_DESCR, 0, - (uint8_t *) b200_usb_fs_config_desc); + (uint8_t *)b200_usb_fs_config_desc); CyU3PUsbSetDesc(CY_U3P_USB_SET_SS_CONFIG_DESCR, 0, - (uint8_t *) b200_usb_ss_config_desc); + (uint8_t *)b200_usb_ss_config_desc); /* BOS Descriptor */ CyU3PUsbSetDesc(CY_U3P_USB_SET_SS_BOS_DESCR, 0, - (uint8_t *) b200_usb_bos_desc); + (uint8_t *)common_usb_bos_desc); /* String descriptors */ CyU3PUsbSetDesc(CY_U3P_USB_SET_STRING_DESCR, 0, - (uint8_t *) b200_string_lang_id_desc); + (uint8_t *)common_string_lang_id_desc); CyU3PUsbSetDesc(CY_U3P_USB_SET_STRING_DESCR, 1, - (uint8_t *) mfr_string); + (uint8_t *)mfr_string); CyU3PUsbSetDesc(CY_U3P_USB_SET_STRING_DESCR, 2, - (uint8_t *) product_string); + (uint8_t *)product_string); CyU3PUsbSetDesc(CY_U3P_USB_SET_STRING_DESCR, 3, - (uint8_t *) dev_serial); + (uint8_t *)serial_string); //////////////////////////////////////////////////////// - // FIXME: CyU3PUsbSetTxDeemphasis(0x11); <0x1F // Shouldn't need to change this - const uint32_t tx_swing = g_config.tx_swing/*65*//*45*/; // 65 & 45 are OK, 120 causes much link recovery. <128. 1.2V is USB3 limit. if (CyU3PUsbSetTxSwing(tx_swing) == CY_U3P_SUCCESS) msg("CyU3PUsbSetTxSwing: %d", tx_swing); diff --git a/firmware/fx3/b200/b200_usb_descriptors.c b/firmware/fx3/b200/firmware/b200_usb_descriptors.c index 53979219b..30e6d876c 100644 --- a/firmware/fx3/b200/b200_usb_descriptors.c +++ b/firmware/fx3/b200/firmware/b200_usb_descriptors.c @@ -1,97 +1,16 @@ // // Copyright 2013-2015 Ettus Research LLC +// Copyright 2019 Ettus Research, a National Instruments Brand +// +// SPDX-License-Identifier: GPL-3.0-or-later // -/* Define the USB 2.0 and USB 3.0 enumeration descriptions for the USRP B200 - * device. */ - - -#include "b200_main.h" - - -/* Standard Device Descriptor for USB 2.0 */ -uint8_t b200_usb2_dev_desc[] __attribute__ ((aligned (32))) = -{ - 0x12, /* Descriptor size */ - CY_U3P_USB_DEVICE_DESCR, /* Device descriptor type */ - 0x10,0x02, /* USB 2.10 */ - 0xFF, /* Device class */ - 0x00, /* Device sub-class */ - 0x00, /* Device protocol */ - 0x40, /* Maxpacket size for EP0 : 64 bytes */ - 0xB4,0x04, /* Vendor ID */ - 0xF0,0x00, /* Product ID */ - 0x00,0x00, /* Device release number */ - 0x01, /* Manufacture string index */ - 0x02, /* Product string index */ - 0x03, /* Serial number string index */ - 0x01 /* Number of configurations */ -}; - - -/* Standard Device Descriptor for USB 3.0 */ -uint8_t b200_usb3_dev_desc[] __attribute__ ((aligned (32))) = -{ - 0x12, /* Descriptor size */ - CY_U3P_USB_DEVICE_DESCR, /* Device descriptor type */ - 0x00,0x03, /* USB 3.0 */ - 0xFF, /* Device class */ - 0x00, /* Device sub-class */ - 0x00, /* Device protocol */ - 0x09, /* Maxpacket size for EP0 : 2^9 */ - 0xB4,0x04, /* Vendor ID */ - 0xF0,0x00, /* Product ID */ - 0x00,0x00, /* Device release number */ - 0x01, /* Manufacture string index */ - 0x02, /* Product string index */ - 0x03, /* Serial number string index */ - 0x01 /* Number of configurations */ -}; - - -/* Binary Device Object Store Descriptor */ -const uint8_t b200_usb_bos_desc[] __attribute__ ((aligned (32))) = -{ - 0x05, /* Descriptor size */ - CY_U3P_BOS_DESCR, /* Device descriptor type */ - 0x16,0x00, /* Length of this descriptor and all sub descriptors */ - 0x02, /* Number of device capability descriptors */ - - /* USB 2.0 extension */ - 0x07, /* Descriptor size */ - CY_U3P_DEVICE_CAPB_DESCR, /* Device capability type descriptor */ - CY_U3P_USB2_EXTN_CAPB_TYPE, /* USB 2.0 extension capability type */ - 0x02,0x00,0x00,0x00, /* Supported device level features: LPM support */ - - /* SuperSpeed device capability */ - 0x0A, /* Descriptor size */ - CY_U3P_DEVICE_CAPB_DESCR, /* Device capability type descriptor */ - CY_U3P_SS_USB_CAPB_TYPE, /* SuperSpeed device capability type */ - 0x00, /* Supported device level features */ - 0x0E,0x00, /* Speeds supported by the device : SS, HS and FS */ - 0x03, /* Functionality support */ - 0x00, /* U1 Device Exit latency */ - 0x00,0x00 /* U2 Device Exit latency */ -}; - - -/* Standard Device Qualifier Descriptor */ -const uint8_t b200_dev_qual_desc[] __attribute__ ((aligned (32))) = -{ - 0x0A, /* Descriptor size */ - CY_U3P_USB_DEVQUAL_DESCR, /* Device qualifier descriptor type */ - 0x00,0x02, /* USB 2.0 */ - 0xFF, /* Device class */ - 0x00, /* Device sub-class */ - 0x00, /* Device protocol */ - 0x40, /* Maxpacket size for EP0 : 64 bytes */ - 0x01, /* Number of configurations */ - 0x00 /* Reserved */ -}; +/* Firmware's unique config and string descriptors */ +#include "b200_const.h" -/* Standard Full Speed Configuration Descriptor */ -const uint8_t b200_usb_fs_config_desc[] __attribute__ ((aligned (32))) = +/* Firmware Full Speed Configuration Descriptor */ +const uint8_t b200_usb_fs_config_desc[] = { /* Configuration descriptor */ 0x09, /* Descriptor size */ @@ -192,8 +111,8 @@ const uint8_t b200_usb_fs_config_desc[] __attribute__ ((aligned (32))) = }; -/* Standard High Speed Configuration Descriptor */ -const uint8_t b200_usb_hs_config_desc[] __attribute__ ((aligned (32))) = +/* Firmware High Speed Configuration Descriptor */ +const uint8_t b200_usb_hs_config_desc[] = { /* Configuration descriptor */ 0x09, /* Descriptor size */ @@ -294,8 +213,8 @@ const uint8_t b200_usb_hs_config_desc[] __attribute__ ((aligned (32))) = }; -/* Standard Super Speed Configuration Descriptor */ -const uint8_t b200_usb_ss_config_desc[] __attribute__ ((aligned (32))) = +/* Firmware Super Speed Configuration Descriptor */ +const uint8_t b200_usb_ss_config_desc[] = { /* Configuration descriptor */ 0x09, /* Descriptor size */ @@ -423,256 +342,11 @@ const uint8_t b200_usb_ss_config_desc[] __attribute__ ((aligned (32))) = 0x00,0x00 /* Service interval for the EP : 0 for bulk */ }; - -const uint8_t b200_usb_ss_config_desc_new[] __attribute__ ((aligned (32))) = -{ - /* Configuration descriptor */ - 0x09, /* Descriptor size */ - CY_U3P_USB_CONFIG_DESCR, /* Configuration descriptor type */ - 0x4F,0x00, /* Length of this descriptor and all sub descriptors */ - 0x02, /* Number of interfaces */ - 0x01, /* Configuration number */ - 0x00, /* COnfiguration string index */ - 0x80, /* Config characteristics - D6: Self power; D5: Remote wakeup */ - 0x01, /* Lie about the max power consumption (in 8mA unit) : 8mA */ - - /* Interface descriptor */ - 0x09, /* Descriptor size */ - CY_U3P_USB_INTRFC_DESCR, /* Interface Descriptor type */ - 0x00, /* Interface number */ - 0x00, /* Alternate setting number */ - 0x00, /* Number of end points */ - 0xFF, /* Interface class */ - 0x00, /* Interface sub class */ - 0x00, /* Interface protocol code */ - 0x02, /* Interface descriptor string index */ - - /* Interface descriptor */ - 0x09, /* Descriptor size */ - CY_U3P_USB_INTRFC_DESCR, /* Interface Descriptor type */ - 0x01, /* Interface number */ - 0x00, /* Alternate setting number */ - 0x04, /* Number of end points */ - 0xFF, /* Interface class */ - 0x00, /* Interface sub class */ - 0x00, /* Interface protocol code */ - 0x02, /* Interface descriptor string index */ - - /* Endpoint descriptor for producer EP */ - 0x07, /* Descriptor size */ - CY_U3P_USB_ENDPNT_DESCR, /* Endpoint descriptor type */ - DATA_ENDPOINT_PRODUCER, /* Endpoint address and description */ - CY_U3P_USB_EP_BULK, /* Bulk endpoint type */ - 0x00,0x04, /* Max packet size = 1024 bytes */ - 0x00, /* Servicing interval for data transfers : 0 for bulk */ - - /* Super speed endpoint companion descriptor for producer EP */ - 0x06, /* Descriptor size */ - CY_U3P_SS_EP_COMPN_DESCR, /* SS endpoint companion descriptor type */ - (USB3_PACKETS_PER_BURST - 1), /* Max no. of packets in a burst : 0: burst 1 packet at a time */ - 0x00, /* Max streams for bulk EP = 0 (No streams) */ - 0x00,0x00, /* Service interval for the EP : 0 for bulk */ - - /* Endpoint descriptor for consumer EP */ - 0x07, /* Descriptor size */ - CY_U3P_USB_ENDPNT_DESCR, /* Endpoint descriptor type */ - DATA_ENDPOINT_CONSUMER, /* Endpoint address and description */ - CY_U3P_USB_EP_BULK, /* Bulk endpoint type */ - 0x00,0x04, /* Max packet size = 1024 bytes */ - 0x00, /* Servicing interval for data transfers : 0 for Bulk */ - - /* Super speed endpoint companion descriptor for consumer EP */ - 0x06, /* Descriptor size */ - CY_U3P_SS_EP_COMPN_DESCR, /* SS endpoint companion descriptor type */ - (USB3_PACKETS_PER_BURST - 1), /* Max no. of packets in a burst : 0: burst 1 packet at a time */ - 0x00, /* Max streams for bulk EP = 0 (No streams) */ - 0x00,0x00, /* Service interval for the EP : 0 for bulk */ - - /* Endpoint descriptor for producer EP */ - 0x07, /* Descriptor size */ - CY_U3P_USB_ENDPNT_DESCR, /* Endpoint descriptor type */ - CTRL_ENDPOINT_PRODUCER, /* Endpoint address and description */ - CY_U3P_USB_EP_BULK, /* Bulk endpoint type */ - 0x00,0x04, /* Max packet size = 1024 bytes */ - 0x00, /* Servicing interval for data transfers : 0 for bulk */ - - /* Super speed endpoint companion descriptor for producer EP */ - 0x06, /* Descriptor size */ - CY_U3P_SS_EP_COMPN_DESCR, /* SS endpoint companion descriptor type */ - (USB3_PACKETS_PER_BURST - 1), /* Max no. of packets in a burst : 0: burst 1 packet at a time */ - 0x00, /* Max streams for bulk EP = 0 (No streams) */ - 0x00,0x00, /* Service interval for the EP : 0 for bulk */ - - /* Endpoint descriptor for consumer EP */ - 0x07, /* Descriptor size */ - CY_U3P_USB_ENDPNT_DESCR, /* Endpoint descriptor type */ - CTRL_ENDPOINT_CONSUMER, /* Endpoint address and description */ - CY_U3P_USB_EP_BULK, /* Bulk endpoint type */ - 0x00,0x04, /* Max packet size = 1024 bytes */ - 0x00, /* Servicing interval for data transfers : 0 for Bulk */ - - /* Super speed endpoint companion descriptor for consumer EP */ - 0x06, /* Descriptor size */ - CY_U3P_SS_EP_COMPN_DESCR, /* SS endpoint companion descriptor type */ - (USB3_PACKETS_PER_BURST - 1), /* Max no. of packets in a burst : 0: burst 1 packet at a time */ - 0x00, /* Max streams for bulk EP = 0 (No streams) */ - 0x00,0x00 /* Service interval for the EP : 0 for bulk */ -}; - - -/* Standard Language ID String Descriptor */ -const uint8_t b200_string_lang_id_desc[] __attribute__ ((aligned (32))) = - { - 0x04, /* Descriptor Size */ - CY_U3P_USB_STRING_DESCR, /* Device Descriptor Type */ - 0x09,0x04 /* Language ID supported */ - }; - - -/* Standard Manufacturer String Descriptor */ -const uint8_t b200_usb_manufacture_desc[] __attribute__ ((aligned (32))) = - { - 0x26, /* Descriptor Size */ - CY_U3P_USB_STRING_DESCR, /* Device Descriptor Type */ - 'E',0x00, - 't',0x00, - 't',0x00, - 'u',0x00, - 's',0x00, - ' ',0x00, - 'R',0x00, - 'e',0x00, - 's',0x00, - 'e',0x00, - 'a',0x00, - 'r',0x00, - 'c',0x00, - 'h',0x00, - ' ',0x00, - 'L',0x00, - 'L',0x00, - 'C',0x00 - }; - -/* NI Manufacturer String Descriptor */ -const uint8_t niusrp_usb_manufacture_desc[] __attribute__ ((aligned (32))) = - { - 0x36, /* Descriptor Size */ - CY_U3P_USB_STRING_DESCR, /* Device Descriptor Type */ - 'N',0x00, - 'a',0x00, - 't',0x00, - 'i',0x00, - 'o',0x00, - 'n',0x00, - 'a',0x00, - 'l',0x00, - ' ',0x00, - 'I',0x00, - 'n',0x00, - 's',0x00, - 't',0x00, - 'r',0x00, - 'u',0x00, - 'm',0x00, - 'e',0x00, - 'n',0x00, - 't',0x00, - 's',0x00, - ' ',0x00, - 'C',0x00, - 'o',0x00, - 'r',0x00, - 'p',0x00, - '.',0x00 - }; - - -/* Standard Product String Descriptor */ -const uint8_t b200_usb_product_desc[] __attribute__ ((aligned (32))) = - { - 0x14, /* Descriptor Size */ - CY_U3P_USB_STRING_DESCR, /* Device Descriptor Type */ - 'U',0x00, - 'S',0x00, - 'R',0x00, - 'P',0x00, - ' ',0x00, - 'B',0x00, - '2',0x00, - '0',0x00, - '0',0x00 - }; - -/* NI-USRP 2900 Product String Descriptor */ -const uint8_t niusrp_2900_usb_product_desc[] __attribute__ ((aligned (32))) = - { - 0x1A, /* Descriptor Size */ - CY_U3P_USB_STRING_DESCR, /* Device Descriptor Type */ - 'N',0x00, - 'I',0x00, - ' ',0x00, - 'U',0x00, - 'S',0x00, - 'R',0x00, - 'P',0x00, - '-',0x00, - '2',0x00, - '9',0x00, - '0',0x00, - '0',0x00 - }; - -/* NI-USRP 2901 Product String Descriptor */ -const uint8_t niusrp_2901_usb_product_desc[] __attribute__ ((aligned (32))) = - { - 0x1A, /* Descriptor Size */ - CY_U3P_USB_STRING_DESCR, /* Device Descriptor Type */ - 'N',0x00, - 'I',0x00, - ' ',0x00, - 'U',0x00, - 'S',0x00, - 'R',0x00, - 'P',0x00, - '-',0x00, - '2',0x00, - '9',0x00, - '0',0x00, - '1',0x00 - }; - -const uint8_t unknown_desc[] __attribute__ ((aligned (32))) = - { - 0x10, /* Descriptor Size */ - CY_U3P_USB_STRING_DESCR, /* Device Descriptor Type */ - 'U',0x00, - 'n',0x00, - 'k',0x00, - 'n',0x00, - 'o',0x00, - 'w',0x00, - 'n',0x00 - }; - -/* Microsoft OS Descriptor. */ -const uint8_t CyFxUsbOSDscr[] __attribute__ ((aligned (32))) = -{ - 0x10, - CY_U3P_USB_STRING_DESCR, - 'O', 0x00, - 'S', 0x00, - ' ', 0x00, - 'D', 0x00, - 'e', 0x00, - 's', 0x00, - 'c', 0x00 -}; - -uint8_t dev_serial[20] __attribute__ ((aligned (32))) = +/* Firmware Device Serial String Descriptor */ +uint8_t b200_dev_serial_desc[20] = { 0x14, - CY_U3P_USB_STRING_DESCR, + 0x03,/* CY_U3P_USB_STRING_DESCR Device Descriptor Type */ '0', 0x00, '0', 0x00, '0', 0x00, @@ -682,9 +356,4 @@ uint8_t dev_serial[20] __attribute__ ((aligned (32))) = '0', 0x00, '0', 0x00, '0', 0x00 -}; - -/* Place this buffer as the last buffer so that no other variable / code shares - * the same cache line. Do not add any other variables / arrays in this file. - * This will lead to variables sharing the same cache line. */ -const uint8_t CyFxUsbDscrAlignBuffer[32] __attribute__ ((aligned (32))); +};
\ No newline at end of file diff --git a/firmware/fx3/b200/firmware/b200_usb_descriptors.h b/firmware/fx3/b200/firmware/b200_usb_descriptors.h new file mode 100644 index 000000000..f3889b9af --- /dev/null +++ b/firmware/fx3/b200/firmware/b200_usb_descriptors.h @@ -0,0 +1,21 @@ +// +// Copyright 2013-2014 Ettus Research LLC +// Copyright 2019 Ettus Research, a National Instruments Brand +// +// SPDX-License-Identifier: GPL-3.0-or-later +// + +#ifndef _B200_USB_DESCRIPTORS_H +#define _B200_USB_DESCRIPTORS_H + +#include "cyu3externcstart.h" + +/* Descriptor definitions for USB enumerations. */ +extern uint8_t b200_usb_fs_config_desc[]; +extern uint8_t b200_usb_hs_config_desc[]; +extern uint8_t b200_usb_ss_config_desc[]; +extern uint8_t b200_dev_serial_desc[]; + +#include "cyu3externcend.h" + +#endif /* _B200_USB_DESCRIPTORS_H */ diff --git a/firmware/fx3/b200/makefile b/firmware/fx3/b200/firmware/makefile index 22eb1bbcc..53d423dfb 100644 --- a/firmware/fx3/b200/makefile +++ b/firmware/fx3/b200/firmware/makefile @@ -1,5 +1,8 @@ # # Copyright 2013-2014 Ettus Research LLC +# Copyright 2019 Ettus Research, a National Instruments Brand +# +# SPDX-License-Identifier: GPL-3.0-or-later # HEX_OUT = usrp_b200_fw.hex @@ -7,8 +10,8 @@ HEX_OUT = usrp_b200_fw.hex all:$(HEX_OUT) # Pull in the Cypress SDK files to build the firmware -FX3FWROOT=.. -FX3PFWROOT=../u3p_firmware +FX3FWROOT=../.. +FX3PFWROOT=../../u3p_firmware include $(FX3FWROOT)/common/fx3_build_config.mak ifndef OC @@ -17,11 +20,9 @@ endif MODULE = b200_main -SOURCE += $(MODULE).c -SOURCE += b200_usb_descriptors.c -SOURCE += b200_i2c.c +SOURCE += $(MODULE).c b200_i2c.c b200_usb_descriptors.c ../common/common_helpers.c ../common/common_descriptors.c -INCLUDES = b200_main.h b200_gpifconfig.h b200_i2c.h +INCFLAGS = -I../common LDLIBS += \ "$$ARMGCC_INSTALL_PATH"/arm-none-eabi/lib/libm.a @@ -34,7 +35,7 @@ EXES = $(MODULE).$(EXEEXT) $(MODULE).$(EXEEXT): $(A_OBJECT) $(C_OBJECT) $(LINK) $(LINKFLAGS) -$(C_OBJECT) : %.o : %.c $(INCLUDES) +$(C_OBJECT) : %.o : %.c $(COMPILE) $(INCFLAGS) $(A_OBJECT) : %.o : %.S @@ -44,6 +45,7 @@ clean: rm -f ./$(MODULE).$(EXEEXT) rm -f ./$(MODULE).map rm -f ./*.o + rm -f ../common/*.o $(HEX_OUT): $(C_OBJECT) $(A_OBJECT) $(EXES) $(OC) -O ihex $(EXES) $@ diff --git a/firmware/fx3/b200/fx3_mem_map.patch b/firmware/fx3/b200/fx3_mem_map.patch index 37d704ace..df9ff0e7a 100644 --- a/firmware/fx3/b200/fx3_mem_map.patch +++ b/firmware/fx3/b200/fx3_mem_map.patch @@ -66,3 +66,26 @@ diff -ur 1.2.3-orig/common/fx3.ld 1.2.3/common/fx3.ld + PROVIDE(__heap_size = __heap_end - __heap_start);
}
+diff -ur 1.2.3-orig/boot_fw/src/cyfx3.ld 1.2.3/boot_fw/src/cyfx3.ld +--- 1.2.3-orig/boot_fw/src/cyfx3.ld 2019-02-12 16:40:48.000000000 -0800 ++++ 1.2.3/boot_fw/src/cyfx3.ld 2019-03-20 14:36:18.992529192 -0700 +@@ -34,12 +34,18 @@ +
+ MEMORY
+ {
++ BLANK : ORIGIN = 0x40070000 LENGTH = 0x0100
+ SYS_MEM : ORIGIN = 0x40078000 LENGTH = 0x7000
+ DATA : ORIGIN = 0x4007F000 LENGTH = 0x1000
+ }
+
+ SECTIONS
+ {
++ . = 0x40070000;
++ .blank :
++ {
++ . += 0x100;
++ } > BLANK
+ . = 0x40078000;
+ .text :
+ {
+
|