sw: wip commit -- dfu state machine works, spi broken
Need to fix SPI and SB_WARMBOOT, but the DFU state machine now works. Signed-off-by: Sean Cross <sean@xobs.io>
This commit is contained in:
		@@ -12,6 +12,33 @@ extern uint32_t csr_readl(uint32_t addr);
 | 
			
		||||
#include <hw/common.h>
 | 
			
		||||
#endif /* ! CSR_ACCESSORS_DEFINED */
 | 
			
		||||
 | 
			
		||||
/* bbspi */
 | 
			
		||||
#define CSR_BBSPI_BASE 0xe0005000
 | 
			
		||||
#define CSR_BBSPI_DO_ADDR 0xe0005000
 | 
			
		||||
#define CSR_BBSPI_DO_SIZE 1
 | 
			
		||||
static inline unsigned char bbspi_do_read(void) {
 | 
			
		||||
	unsigned char r = csr_readl(0xe0005000);
 | 
			
		||||
	return r;
 | 
			
		||||
}
 | 
			
		||||
static inline void bbspi_do_write(unsigned char value) {
 | 
			
		||||
	csr_writel(value, 0xe0005000);
 | 
			
		||||
}
 | 
			
		||||
#define CSR_BBSPI_OE_ADDR 0xe0005004
 | 
			
		||||
#define CSR_BBSPI_OE_SIZE 1
 | 
			
		||||
static inline unsigned char bbspi_oe_read(void) {
 | 
			
		||||
	unsigned char r = csr_readl(0xe0005004);
 | 
			
		||||
	return r;
 | 
			
		||||
}
 | 
			
		||||
static inline void bbspi_oe_write(unsigned char value) {
 | 
			
		||||
	csr_writel(value, 0xe0005004);
 | 
			
		||||
}
 | 
			
		||||
#define CSR_BBSPI_DI_ADDR 0xe0005008
 | 
			
		||||
#define CSR_BBSPI_DI_SIZE 1
 | 
			
		||||
static inline unsigned char bbspi_di_read(void) {
 | 
			
		||||
	unsigned char r = csr_readl(0xe0005008);
 | 
			
		||||
	return r;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/* ctrl */
 | 
			
		||||
#define CSR_CTRL_BASE 0xe0000000
 | 
			
		||||
#define CSR_CTRL_RESET_ADDR 0xe0000000
 | 
			
		||||
@@ -54,31 +81,16 @@ static inline unsigned int ctrl_bus_errors_read(void) {
 | 
			
		||||
	return r;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/* picospi */
 | 
			
		||||
#define CSR_PICOSPI_BASE 0xe0005000
 | 
			
		||||
#define CSR_PICOSPI_DO_ADDR 0xe0005000
 | 
			
		||||
#define CSR_PICOSPI_DO_SIZE 1
 | 
			
		||||
static inline unsigned char picospi_do_read(void) {
 | 
			
		||||
	unsigned char r = csr_readl(0xe0005000);
 | 
			
		||||
/* reboot */
 | 
			
		||||
#define CSR_REBOOT_BASE 0xe0005800
 | 
			
		||||
#define CSR_REBOOT_CTRL_ADDR 0xe0005800
 | 
			
		||||
#define CSR_REBOOT_CTRL_SIZE 1
 | 
			
		||||
static inline unsigned char reboot_ctrl_read(void) {
 | 
			
		||||
	unsigned char r = csr_readl(0xe0005800);
 | 
			
		||||
	return r;
 | 
			
		||||
}
 | 
			
		||||
static inline void picospi_do_write(unsigned char value) {
 | 
			
		||||
	csr_writel(value, 0xe0005000);
 | 
			
		||||
}
 | 
			
		||||
#define CSR_PICOSPI_OE_ADDR 0xe0005004
 | 
			
		||||
#define CSR_PICOSPI_OE_SIZE 1
 | 
			
		||||
static inline unsigned char picospi_oe_read(void) {
 | 
			
		||||
	unsigned char r = csr_readl(0xe0005004);
 | 
			
		||||
	return r;
 | 
			
		||||
}
 | 
			
		||||
static inline void picospi_oe_write(unsigned char value) {
 | 
			
		||||
	csr_writel(value, 0xe0005004);
 | 
			
		||||
}
 | 
			
		||||
#define CSR_PICOSPI_DI_ADDR 0xe0005008
 | 
			
		||||
#define CSR_PICOSPI_DI_SIZE 1
 | 
			
		||||
static inline unsigned char picospi_di_read(void) {
 | 
			
		||||
	unsigned char r = csr_readl(0xe0005008);
 | 
			
		||||
	return r;
 | 
			
		||||
static inline void reboot_ctrl_write(unsigned char value) {
 | 
			
		||||
	csr_writel(value, 0xe0005800);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/* timer0 */
 | 
			
		||||
@@ -177,78 +189,6 @@ static inline void timer0_ev_enable_write(unsigned char value) {
 | 
			
		||||
	csr_writel(value, 0xe0002840);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/* uart */
 | 
			
		||||
#define CSR_UART_BASE 0xe0001800
 | 
			
		||||
#define CSR_UART_RXTX_ADDR 0xe0001800
 | 
			
		||||
#define CSR_UART_RXTX_SIZE 1
 | 
			
		||||
static inline unsigned char uart_rxtx_read(void) {
 | 
			
		||||
	unsigned char r = csr_readl(0xe0001800);
 | 
			
		||||
	return r;
 | 
			
		||||
}
 | 
			
		||||
static inline void uart_rxtx_write(unsigned char value) {
 | 
			
		||||
	csr_writel(value, 0xe0001800);
 | 
			
		||||
}
 | 
			
		||||
#define CSR_UART_TXFULL_ADDR 0xe0001804
 | 
			
		||||
#define CSR_UART_TXFULL_SIZE 1
 | 
			
		||||
static inline unsigned char uart_txfull_read(void) {
 | 
			
		||||
	unsigned char r = csr_readl(0xe0001804);
 | 
			
		||||
	return r;
 | 
			
		||||
}
 | 
			
		||||
#define CSR_UART_RXEMPTY_ADDR 0xe0001808
 | 
			
		||||
#define CSR_UART_RXEMPTY_SIZE 1
 | 
			
		||||
static inline unsigned char uart_rxempty_read(void) {
 | 
			
		||||
	unsigned char r = csr_readl(0xe0001808);
 | 
			
		||||
	return r;
 | 
			
		||||
}
 | 
			
		||||
#define CSR_UART_EV_STATUS_ADDR 0xe000180c
 | 
			
		||||
#define CSR_UART_EV_STATUS_SIZE 1
 | 
			
		||||
static inline unsigned char uart_ev_status_read(void) {
 | 
			
		||||
	unsigned char r = csr_readl(0xe000180c);
 | 
			
		||||
	return r;
 | 
			
		||||
}
 | 
			
		||||
static inline void uart_ev_status_write(unsigned char value) {
 | 
			
		||||
	csr_writel(value, 0xe000180c);
 | 
			
		||||
}
 | 
			
		||||
#define CSR_UART_EV_PENDING_ADDR 0xe0001810
 | 
			
		||||
#define CSR_UART_EV_PENDING_SIZE 1
 | 
			
		||||
static inline unsigned char uart_ev_pending_read(void) {
 | 
			
		||||
	unsigned char r = csr_readl(0xe0001810);
 | 
			
		||||
	return r;
 | 
			
		||||
}
 | 
			
		||||
static inline void uart_ev_pending_write(unsigned char value) {
 | 
			
		||||
	csr_writel(value, 0xe0001810);
 | 
			
		||||
}
 | 
			
		||||
#define CSR_UART_EV_ENABLE_ADDR 0xe0001814
 | 
			
		||||
#define CSR_UART_EV_ENABLE_SIZE 1
 | 
			
		||||
static inline unsigned char uart_ev_enable_read(void) {
 | 
			
		||||
	unsigned char r = csr_readl(0xe0001814);
 | 
			
		||||
	return r;
 | 
			
		||||
}
 | 
			
		||||
static inline void uart_ev_enable_write(unsigned char value) {
 | 
			
		||||
	csr_writel(value, 0xe0001814);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/* uart_phy */
 | 
			
		||||
#define CSR_UART_PHY_BASE 0xe0001000
 | 
			
		||||
#define CSR_UART_PHY_TUNING_WORD_ADDR 0xe0001000
 | 
			
		||||
#define CSR_UART_PHY_TUNING_WORD_SIZE 4
 | 
			
		||||
static inline unsigned int uart_phy_tuning_word_read(void) {
 | 
			
		||||
	unsigned int r = csr_readl(0xe0001000);
 | 
			
		||||
	r <<= 8;
 | 
			
		||||
	r |= csr_readl(0xe0001004);
 | 
			
		||||
	r <<= 8;
 | 
			
		||||
	r |= csr_readl(0xe0001008);
 | 
			
		||||
	r <<= 8;
 | 
			
		||||
	r |= csr_readl(0xe000100c);
 | 
			
		||||
	return r;
 | 
			
		||||
}
 | 
			
		||||
static inline void uart_phy_tuning_word_write(unsigned int value) {
 | 
			
		||||
	csr_writel(value >> 24, 0xe0001000);
 | 
			
		||||
	csr_writel(value >> 16, 0xe0001004);
 | 
			
		||||
	csr_writel(value >> 8, 0xe0001008);
 | 
			
		||||
	csr_writel(value, 0xe000100c);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
/* usb */
 | 
			
		||||
#define CSR_USB_BASE 0xe0004800
 | 
			
		||||
#define CSR_USB_PULLUP_OUT_ADDR 0xe0004800
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,9 @@
 | 
			
		||||
#ifndef __GENERATED_MEM_H
 | 
			
		||||
#define __GENERATED_MEM_H
 | 
			
		||||
 | 
			
		||||
#define VEXRISCV_DEBUG_BASE 0xf00f0000
 | 
			
		||||
#define VEXRISCV_DEBUG_SIZE 0x00000010
 | 
			
		||||
 | 
			
		||||
#define SRAM_BASE 0x10000000
 | 
			
		||||
#define SRAM_SIZE 0x00020000
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -56,4 +56,15 @@ static inline void mtspr(unsigned long add, unsigned long val)
 | 
			
		||||
}
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
#include <generated/csr.h>
 | 
			
		||||
 | 
			
		||||
__attribute__((noreturn)) static inline void reboot(void) {
 | 
			
		||||
	reboot_ctrl_write(0xac);
 | 
			
		||||
	while (1);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
__attribute__((noreturn)) static inline void reboot_to_image(uint8_t image_index) {
 | 
			
		||||
	reboot_ctrl_write(0xac | image_index);
 | 
			
		||||
	while (1);
 | 
			
		||||
}
 | 
			
		||||
#endif /* __SYSTEM_H */
 | 
			
		||||
 
 | 
			
		||||
@@ -11,14 +11,16 @@ struct usb_setup_request;
 | 
			
		||||
void usb_isr(void);
 | 
			
		||||
void usb_init(void);
 | 
			
		||||
void usb_connect(void);
 | 
			
		||||
void usb_disconnect(void);
 | 
			
		||||
 | 
			
		||||
void usb_poll(void);
 | 
			
		||||
int usb_irq_happened(void);
 | 
			
		||||
void usb_setup(struct usb_device *dev, const struct usb_setup_request *setup);
 | 
			
		||||
int usb_send(struct usb_device *dev, int epnum, const void *data, int total_count);
 | 
			
		||||
int usb_ack(struct usb_device *dev, int epnum);
 | 
			
		||||
int usb_err(struct usb_device *dev, int epnum);
 | 
			
		||||
int usb_recv(struct usb_device *dev, void *buffer, unsigned int buffer_len);
 | 
			
		||||
void usb_poll(struct usb_device *dev);
 | 
			
		||||
int usb_wait_for_send_done(struct usb_device *dev);
 | 
			
		||||
 | 
			
		||||
#ifdef __cplusplus
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										20
									
								
								sw/src/dfu.c
									
									
									
									
									
								
							
							
						
						
									
										20
									
								
								sw/src/dfu.c
									
									
									
									
									
								
							@@ -73,7 +73,7 @@ static struct toboot_state {
 | 
			
		||||
 | 
			
		||||
static dfu_state_t dfu_state = dfuIDLE;
 | 
			
		||||
static dfu_status_t dfu_status = OK;
 | 
			
		||||
static unsigned dfu_poll_timeout = 1;
 | 
			
		||||
static unsigned dfu_poll_timeout_ms = 100;
 | 
			
		||||
 | 
			
		||||
static uint32_t dfu_buffer[DFU_TRANSFER_SIZE/4];
 | 
			
		||||
static uint32_t dfu_buffer_offset;
 | 
			
		||||
@@ -200,10 +200,18 @@ uint8_t dfu_getstate(void)
 | 
			
		||||
    return dfu_state;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
unsigned last_blockNum;
 | 
			
		||||
unsigned last_blockLength;
 | 
			
		||||
unsigned last_packetOffset;
 | 
			
		||||
unsigned last_packetLength;
 | 
			
		||||
bool dfu_download(unsigned blockNum, unsigned blockLength,
 | 
			
		||||
                  unsigned packetOffset, unsigned packetLength, const uint8_t *data)
 | 
			
		||||
{
 | 
			
		||||
    // uint32_t i;
 | 
			
		||||
    last_packetLength = packetLength;
 | 
			
		||||
    last_packetOffset = packetOffset;
 | 
			
		||||
    last_blockLength = blockLength;
 | 
			
		||||
    last_blockNum = blockNum;
 | 
			
		||||
 | 
			
		||||
    if (packetOffset + packetLength > DFU_TRANSFER_SIZE ||
 | 
			
		||||
        packetOffset + packetLength > blockLength) {
 | 
			
		||||
@@ -374,13 +382,13 @@ bool dfu_getstatus(uint8_t status[8])
 | 
			
		||||
            // Ready to reboot. The main thread will take care of this. Also let the DFU tool
 | 
			
		||||
            // know to leave us alone until this happens.
 | 
			
		||||
            dfu_state = dfuMANIFEST;
 | 
			
		||||
            dfu_poll_timeout = 10;
 | 
			
		||||
            dfu_poll_timeout_ms = 10;
 | 
			
		||||
            break;
 | 
			
		||||
 | 
			
		||||
        case dfuMANIFEST:
 | 
			
		||||
            // Perform the reboot
 | 
			
		||||
            dfu_state = dfuMANIFEST_WAIT_RESET;
 | 
			
		||||
            dfu_poll_timeout = 1000;
 | 
			
		||||
            dfu_poll_timeout_ms = 1000;
 | 
			
		||||
            break;
 | 
			
		||||
 | 
			
		||||
        default:
 | 
			
		||||
@@ -388,9 +396,9 @@ bool dfu_getstatus(uint8_t status[8])
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    status[0] = dfu_status;
 | 
			
		||||
    status[1] = dfu_poll_timeout;
 | 
			
		||||
    status[2] = dfu_poll_timeout >> 8;
 | 
			
		||||
    status[3] = dfu_poll_timeout >> 16;
 | 
			
		||||
    status[1] = dfu_poll_timeout_ms;
 | 
			
		||||
    status[2] = dfu_poll_timeout_ms >> 8;
 | 
			
		||||
    status[3] = dfu_poll_timeout_ms >> 16;
 | 
			
		||||
    status[4] = dfu_state;
 | 
			
		||||
    status[5] = 0;  // iString
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -4,8 +4,8 @@
 | 
			
		||||
#include <uart.h>
 | 
			
		||||
#include <usb.h>
 | 
			
		||||
#include <time.h>
 | 
			
		||||
 | 
			
		||||
#include "spi.h"
 | 
			
		||||
#include <dfu.h>
 | 
			
		||||
#include <spi.h>
 | 
			
		||||
#include <generated/csr.h>
 | 
			
		||||
 | 
			
		||||
struct ff_spi *spi;
 | 
			
		||||
@@ -19,10 +19,13 @@ void isr(void)
 | 
			
		||||
    if (irqs & (1 << USB_INTERRUPT))
 | 
			
		||||
        usb_isr();
 | 
			
		||||
 | 
			
		||||
#ifdef CSR_UART_BASE
 | 
			
		||||
    if (irqs & (1 << UART_INTERRUPT))
 | 
			
		||||
        uart_isr();
 | 
			
		||||
#endif
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#ifdef CSR_UART_BASE
 | 
			
		||||
static void rv_putchar(void *ignored, char c)
 | 
			
		||||
{
 | 
			
		||||
    (void)ignored;
 | 
			
		||||
@@ -32,10 +35,13 @@ static void rv_putchar(void *ignored, char c)
 | 
			
		||||
        return;
 | 
			
		||||
    uart_write(c);
 | 
			
		||||
}
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
static void init(void)
 | 
			
		||||
{
 | 
			
		||||
#ifdef CSR_UART_BASE
 | 
			
		||||
    init_printf(NULL, rv_putchar);
 | 
			
		||||
#endif
 | 
			
		||||
    irq_setmask(0);
 | 
			
		||||
    irq_setie(1);
 | 
			
		||||
    uart_init();
 | 
			
		||||
@@ -82,71 +88,15 @@ int main(int argc, char **argv)
 | 
			
		||||
 | 
			
		||||
    init();
 | 
			
		||||
 | 
			
		||||
    // // picospi_cfg_write(0);
 | 
			
		||||
    // picospi_oe_write(0xff);
 | 
			
		||||
    // picospi_do_write(0);
 | 
			
		||||
    // // uint8_t last_value = 0;
 | 
			
		||||
    // printf("\nToggling: %02x  ", picospi_oe_read());
 | 
			
		||||
    // while (1) {
 | 
			
		||||
    //     // uint8_t new_value = picospi_di_read();
 | 
			
		||||
    //     // if (new_value != last_value) {
 | 
			
		||||
    //     //     printf("SPI %02x -> %02x\n", last_value, new_value);
 | 
			
		||||
    //     //     last_value = new_value;
 | 
			
		||||
    //     // }
 | 
			
		||||
    //     // picospi_oe_write(0xff);
 | 
			
		||||
    //     // printf("\b0");
 | 
			
		||||
    //     // picospi_oe_write(0x00);
 | 
			
		||||
    //     // printf("\b1");
 | 
			
		||||
 | 
			
		||||
    //     // picospi_do_write(0x00);
 | 
			
		||||
    //     // printf("\b0");
 | 
			
		||||
    //     // picospi_do_write(0xff);
 | 
			
		||||
    //     // printf("\b1");
 | 
			
		||||
    // }
 | 
			
		||||
    // printf("\nPress any key to read...");
 | 
			
		||||
    // while(1) {
 | 
			
		||||
    //     uart_read();
 | 
			
		||||
    //     struct spi_id id = spiId(spi);
 | 
			
		||||
    //     printf("Manufacturer ID: %s (%02x)\n", id.manufacturer, id.manufacturer_id);
 | 
			
		||||
    //     if (id.manufacturer_id != id._manufacturer_id)
 | 
			
		||||
    //         printf("!! JEDEC Manufacturer ID: %02x\n",
 | 
			
		||||
    //         id._manufacturer_id);
 | 
			
		||||
    //     printf("Memory model: %s (%02x)\n", id.model, id.memory_type);
 | 
			
		||||
    //     printf("Memory size: %s (%02x)\n", id.capacity, id.memory_size);
 | 
			
		||||
    //     printf("Device ID: %02x\n", id.device_id);
 | 
			
		||||
    //     if (id.device_id != id.signature)
 | 
			
		||||
    //         printf("!! Electronic Signature: %02x\n", id.signature);
 | 
			
		||||
    //     printf("Serial number: %02x %02x %02x %02x\n", id.serial[0], id.serial[1], id.serial[2], id.serial[3]);
 | 
			
		||||
    //     printf("Status 1: %02x\n", spiReadStatus(spi, 1));
 | 
			
		||||
    //     printf("Status 2: %02x\n", spiReadStatus(spi, 2));
 | 
			
		||||
    //     printf("Status 3: %02x\n", spiReadStatus(spi, 3));
 | 
			
		||||
    // }
 | 
			
		||||
    // puts("\nPress any key to start...");
 | 
			
		||||
    // uart_read();
 | 
			
		||||
 | 
			
		||||
    // printf("\n\nUSB API: %s\n", usb_hw_api());
 | 
			
		||||
    // puts("Enabling USB");
 | 
			
		||||
    usb_connect();
 | 
			
		||||
    // printf("USB enabled.\n");
 | 
			
		||||
    // usb_print_status();
 | 
			
		||||
    int last = 0;
 | 
			
		||||
    int i;
 | 
			
		||||
    while (1)
 | 
			
		||||
    {
 | 
			
		||||
        // if (usb_irq_happened() != last) {
 | 
			
		||||
        //     last = usb_irq_happened();
 | 
			
		||||
        //     // printf("USB %d IRQ happened\n", last);
 | 
			
		||||
        // }
 | 
			
		||||
        usb_poll();
 | 
			
		||||
        /*
 | 
			
		||||
        printf("Press any key to send...  ");
 | 
			
		||||
        uart_read();
 | 
			
		||||
        printf("Sending...  ");
 | 
			
		||||
        bfr[0] = 0;
 | 
			
		||||
        bfr[1] = ~0;
 | 
			
		||||
        bfr[2] = 0;
 | 
			
		||||
        usb_send(NULL, 0, bfr, 1);
 | 
			
		||||
        printf("Sent\n");
 | 
			
		||||
        */
 | 
			
		||||
        usb_poll(NULL);
 | 
			
		||||
        i++;
 | 
			
		||||
 | 
			
		||||
    //     if (i > 200)
 | 
			
		||||
            // reboot_ctrl_write(0xac);
 | 
			
		||||
    }
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
@@ -24,7 +24,7 @@ static void gpioSetMode(int pin, int mode) {
 | 
			
		||||
        oe_mirror |= 1 << pin;
 | 
			
		||||
    else
 | 
			
		||||
        oe_mirror &= ~(1 << pin);
 | 
			
		||||
    picospi_oe_write(oe_mirror);
 | 
			
		||||
    bbspi_oe_write(oe_mirror);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static void gpioWrite(int pin, int val) {
 | 
			
		||||
@@ -32,11 +32,11 @@ static void gpioWrite(int pin, int val) {
 | 
			
		||||
        do_mirror |= 1 << pin;
 | 
			
		||||
    else
 | 
			
		||||
        do_mirror &= ~(1 << pin);
 | 
			
		||||
    picospi_do_write(do_mirror);
 | 
			
		||||
    bbspi_do_write(do_mirror);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
static int gpioRead(int pin) {
 | 
			
		||||
    return !!(picospi_di_read() & (1 << pin));
 | 
			
		||||
    return !!(bbspi_di_read() & (1 << pin));
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#define SPI_ONLY_SINGLE
 | 
			
		||||
 
 | 
			
		||||
@@ -2,7 +2,7 @@
 | 
			
		||||
#include <unistd.h>
 | 
			
		||||
#include <usb.h>
 | 
			
		||||
#include <dfu.h>
 | 
			
		||||
 | 
			
		||||
#include <system.h>
 | 
			
		||||
#include <printf.h>
 | 
			
		||||
 | 
			
		||||
#include <usb-desc.h>
 | 
			
		||||
@@ -10,7 +10,7 @@
 | 
			
		||||
static uint8_t reply_buffer[8];
 | 
			
		||||
static uint8_t usb_configuration = 0;
 | 
			
		||||
#define USB_MAX_PACKET_SIZE 64
 | 
			
		||||
static uint8_t rx_buffer[USB_MAX_PACKET_SIZE];
 | 
			
		||||
static uint32_t rx_buffer[USB_MAX_PACKET_SIZE/4];
 | 
			
		||||
 | 
			
		||||
void usb_setup(struct usb_device *dev, const struct usb_setup_request *setup)
 | 
			
		||||
{
 | 
			
		||||
@@ -167,22 +167,39 @@ void usb_setup(struct usb_device *dev, const struct usb_setup_request *setup)
 | 
			
		||||
        int bytes_remaining = setup->wLength;
 | 
			
		||||
        int ep0_rx_offset = 0;
 | 
			
		||||
        while (bytes_remaining > 0) {
 | 
			
		||||
 | 
			
		||||
            // Fill the buffer, or if there is enough space transfer the whole packet.
 | 
			
		||||
            unsigned int len = setup->wLength;
 | 
			
		||||
            if (len > sizeof(rx_buffer))
 | 
			
		||||
                len = sizeof(rx_buffer);
 | 
			
		||||
            unsigned int i;
 | 
			
		||||
            for (i = 0; i < sizeof(rx_buffer)/4; i++)
 | 
			
		||||
                rx_buffer[i] = 0xffffffff;
 | 
			
		||||
 | 
			
		||||
            // Receive DATA packets (which are automatically ACKed)
 | 
			
		||||
            usb_recv(dev, rx_buffer, len);
 | 
			
		||||
            len = usb_recv(dev, (void *)rx_buffer, len);
 | 
			
		||||
 | 
			
		||||
            // Append the data to the download buffer.
 | 
			
		||||
            dfu_download(setup->wValue, setup->wLength, ep0_rx_offset, len, rx_buffer);
 | 
			
		||||
            dfu_download(setup->wValue, setup->wLength, ep0_rx_offset, len, (void *)rx_buffer);
 | 
			
		||||
 | 
			
		||||
            bytes_remaining -= len;
 | 
			
		||||
            ep0_rx_offset += len;
 | 
			
		||||
        }
 | 
			
		||||
        return;
 | 
			
		||||
 | 
			
		||||
    case 0x0021: // DFU_DETACH
 | 
			
		||||
        // Send the "ACK" packet and wait for it
 | 
			
		||||
        // to be received.
 | 
			
		||||
        usb_ack(dev, 0);
 | 
			
		||||
        usb_wait_for_send_done(dev);
 | 
			
		||||
        usb_disconnect();
 | 
			
		||||
 | 
			
		||||
        // Issue a reboot
 | 
			
		||||
        reboot_to_image(1);
 | 
			
		||||
        while (1)
 | 
			
		||||
           ;
 | 
			
		||||
        return;
 | 
			
		||||
 | 
			
		||||
    case 0x03a1: // DFU_GETSTATUS
 | 
			
		||||
        if (setup->wIndex > 0)
 | 
			
		||||
        {
 | 
			
		||||
 
 | 
			
		||||
@@ -4,6 +4,7 @@
 | 
			
		||||
#include <string.h>
 | 
			
		||||
#include <printf.h>
 | 
			
		||||
#include <uart.h>
 | 
			
		||||
#include <usb.h>
 | 
			
		||||
 | 
			
		||||
#ifdef CSR_USB_EP_0_OUT_EV_PENDING_ADDR
 | 
			
		||||
 | 
			
		||||
@@ -39,6 +40,10 @@ enum epfifo_response {
 | 
			
		||||
#define USB_EV_ERROR 1
 | 
			
		||||
#define USB_EV_PACKET 2
 | 
			
		||||
 | 
			
		||||
void usb_disconnect(void) {
 | 
			
		||||
    usb_pullup_out_write(0);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void usb_connect(void) {
 | 
			
		||||
 | 
			
		||||
    usb_ep_0_out_ev_pending_write(usb_ep_0_out_ev_enable_read());
 | 
			
		||||
@@ -56,6 +61,7 @@ void usb_connect(void) {
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void usb_init(void) {
 | 
			
		||||
    usb_pullup_out_write(0);
 | 
			
		||||
    return;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@@ -115,6 +121,14 @@ int usb_send(struct usb_device *dev, int epnum, const void *data, int total_coun
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int usb_wait_for_send_done(struct usb_device *dev) {
 | 
			
		||||
    while (current_data && current_length)
 | 
			
		||||
        usb_poll(dev);
 | 
			
		||||
    while (usb_ep_0_in_respond_read() == EPF_ACK)
 | 
			
		||||
        ;
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void usb_isr(void) {
 | 
			
		||||
    irq_count++;
 | 
			
		||||
    uint8_t ep0o_pending = usb_ep_0_out_ev_pending_read();
 | 
			
		||||
@@ -133,7 +147,7 @@ void usb_isr(void) {
 | 
			
		||||
            usb_ep_0_out_obuf_head_write(0);
 | 
			
		||||
        }
 | 
			
		||||
        usb_ep_0_out_ev_pending_write(ep0o_pending);
 | 
			
		||||
        usb_ep0out_buffer_len[usb_ep0out_wr_ptr] = byte_count;
 | 
			
		||||
        usb_ep0out_buffer_len[usb_ep0out_wr_ptr] = byte_count - 2 /* Strip off CRC16 */;
 | 
			
		||||
        usb_ep0out_wr_ptr = (usb_ep0out_wr_ptr + 1) & (EP0OUT_BUFFERS-1);
 | 
			
		||||
 | 
			
		||||
        if (last_tok == USB_PID_SETUP) {
 | 
			
		||||
@@ -154,6 +168,7 @@ void usb_isr(void) {
 | 
			
		||||
 | 
			
		||||
        usb_ep_0_in_respond_write(EPF_NAK);
 | 
			
		||||
    }
 | 
			
		||||
    
 | 
			
		||||
    return;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@@ -214,7 +229,8 @@ int usb_recv(struct usb_device *dev, void *buffer, unsigned int buffer_len) {
 | 
			
		||||
    return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void usb_poll(void) {
 | 
			
		||||
void usb_poll(struct usb_device *dev) {
 | 
			
		||||
    (void)dev;
 | 
			
		||||
    // If some data was received, then process it.
 | 
			
		||||
    if (usb_ep0out_rd_ptr != usb_ep0out_wr_ptr) {
 | 
			
		||||
        const struct usb_setup_request *request = (const struct usb_setup_request *)(usb_ep0out_buffer[usb_ep0out_rd_ptr]);
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										5
									
								
								sw/third_party/libbase/uart.c
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										5
									
								
								sw/third_party/libbase/uart.c
									
									
									
									
										vendored
									
									
								
							@@ -3,6 +3,7 @@
 | 
			
		||||
#include <generated/csr.h>
 | 
			
		||||
#include <hw/flags.h>
 | 
			
		||||
 | 
			
		||||
#ifdef CSR_UART_BASE
 | 
			
		||||
/*
 | 
			
		||||
 * Buffer sizes must be a power of 2 so that modulos can be computed
 | 
			
		||||
 * with logical AND.
 | 
			
		||||
@@ -108,3 +109,7 @@ void uart_sync(void)
 | 
			
		||||
{
 | 
			
		||||
	while(tx_consume != tx_produce);
 | 
			
		||||
}
 | 
			
		||||
#else /* !CSR_UART_BASE */
 | 
			
		||||
void uart_init(void) {}
 | 
			
		||||
void uart_isr(void) {}
 | 
			
		||||
#endif
 | 
			
		||||
		Reference in New Issue
	
	Block a user