From e11fa5f74eb49b10ebefbe8882bb50186dffb2a4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tomasz=20Mo=C5=84?= Date: Fri, 2 Jul 2021 12:02:26 +0200 Subject: [PATCH] Sansa Connect: Initial libertas WiFi driver port Import non-free firmware image from linux-firmware package. Firmware loading works but is disabled at compile time because just loading firmware without configuring device results in higher power consumption without any benefit to end user. Change-Id: I8fd252c49385ede1ea4e0f9b1e29adeb331ab8ae --- apps/main.c | 5 + firmware/SOURCES | 10 + .../drivers/libertas/firmware/LICENCE.Marvell | 22 + .../drivers/libertas/firmware/gspi8686_v9.bin | Bin 0 -> 126652 bytes .../libertas/firmware/gspi8686_v9_helper.bin | Bin 0 -> 2140 bytes firmware/drivers/libertas/if_spi.c | 674 ++++++++++++++++++ firmware/drivers/libertas/if_spi.h | 215 ++++++ firmware/drivers/libertas/if_spi_drv.h | 34 + firmware/export/config/sansaconnect.h | 6 + firmware/export/wifi.h | 29 + .../sansa-connect/avr-sansaconnect.c | 10 +- .../sansa-connect/avr-sansaconnect.h | 2 + .../sansa-connect/wifi-sansaconnect.c | 130 ++++ .../target/arm/tms320dm320/system-dm320.c | 2 + tools/buildzip.pl | 5 + 15 files changed, 1142 insertions(+), 2 deletions(-) create mode 100644 firmware/drivers/libertas/firmware/LICENCE.Marvell create mode 100644 firmware/drivers/libertas/firmware/gspi8686_v9.bin create mode 100644 firmware/drivers/libertas/firmware/gspi8686_v9_helper.bin create mode 100644 firmware/drivers/libertas/if_spi.c create mode 100644 firmware/drivers/libertas/if_spi.h create mode 100644 firmware/drivers/libertas/if_spi_drv.h create mode 100644 firmware/export/wifi.h create mode 100644 firmware/target/arm/tms320dm320/sansa-connect/wifi-sansaconnect.c diff --git a/apps/main.c b/apps/main.c index c7b223faea..483d280204 100644 --- a/apps/main.c +++ b/apps/main.c @@ -36,6 +36,7 @@ #include "panic.h" #include "menu.h" #include "usb.h" +#include "wifi.h" #include "powermgmt.h" #if !defined(DX50) && !defined(DX90) #include "adc.h" @@ -636,6 +637,10 @@ static void init(void) CHART("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

je2P!?gEnkPk(vW(h&#Ov6cDo{qT@-$!LN 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

%qA?m9eI44*t<;+$juS=ytM^P85>zQ%@R4X-u1N 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 S0q)n6fOc>GoAlY!rvCxNrR_oh literal 0 HcmV?d00001 diff --git a/firmware/drivers/libertas/firmware/gspi8686_v9_helper.bin b/firmware/drivers/libertas/firmware/gspi8686_v9_helper.bin new file mode 100644 index 0000000000000000000000000000000000000000..424cfb386c910185a2841b07999f19a5c468f150 GIT binary patch literal 2140 zcmY*aVQf=X6h8O$)xK>VdyJ`FDC`yI(wG6oOc~3J9aP>c30Vas5{W6BnxTo-gdh83 z^2RnY2+6i&n(3d_2#G{~6vGltSn^0f2Z_=d`JwSgU*BG~L4f+h41xCf-Pdl+mz;j* zp6}dq&b{Z}TMyA45B>j3(3CCLvHL_hOOvN;KMmLc8n+cGZPrl25{are0tH|zd?Vl) z;xt!uB|Bv+&`BP%g9^u!_A}s5G$D^ddVLkqLWi#bx`9QM=su$Y>NiK*e(lH=Twlu6qknY1P4WKN0<=9sZNPpPy;1W7_NY0EK&+xk$vy09l$55<*_yMe`vm%FpVxh^_ z85vMlzi+W&_>4|$%)AepL`FZLVkg)Q45=UX6fmWxR8l2XRs*V{hSiALuJ)@$sM8uG z`pRR-c?o;PB6ITs9ku*e8#Cr6Sj3oztxZ&R=b2&fahoTyKHm#pQ8|!5LDb*jar;Ho}l^VlQ2_weVr73{eeJqaW(g#(E+q>Qj{;XM$3&6q2;0A11ol-78S z!mSMYG~SF}H6tcFxjkbtWiE!^H{%>MGsS>zKsPvV%F|+y3iMD3I?ERy$XBE*0kr^I zZE!F{g+G^Qf_+X3_YlTfwBvjGV_f$J*9GZ<=LXkTB~p;#WXtNEWcc$Txo$#Qn)JHrRm4XPl6nh_IQJ&urbQXFLri^ zgS+6lxkTH^w9i={bsFQONJ%X@lAKKnnDj$M#SJe0RHQJQV=aFzFlD8RnPRoe{oqz{YtCLU@P6}m zssTdP5RQ1~-vf3+!jJ?+#D79`lb&B!!2Oa*WO1*e9mBikCmp}|Z*X5ZymkD&!`^FR zT+*Yyu8}U67j?K0=`3`^r;S8?Pj07FA@0$bJ{r0@m{QmBBRwgV`;GLbRPR20x_*=Q zrVtl9oaGPhk)qG=I(g0dw6pA#TnmXI&DYgSp{~kY?Za{o7Mk_39x>E~SZ>ULGR|Tw zXcS@twIPNI6-K%cmrfgQWvCTnkH$F)4Ggf*K*fi}CBAAr5Lipx-GPcODiYQa#Tq?` z!?UAz$VS9%EdG>t>sYB1(N@m)8#v#DcaLPApS ugl!yH3o&84z&XgLkbf|~4fztf4S65(8rNatxFTDj--GQJ;CjS64g3#`z3Mdp literal 0 HcmV?d00001 diff --git a/firmware/drivers/libertas/if_spi.c b/firmware/drivers/libertas/if_spi.c new file mode 100644 index 0000000000..be564cc64f --- /dev/null +++ b/firmware/drivers/libertas/if_spi.c @@ -0,0 +1,674 @@ +/*************************************************************************** + * __________ __ ___. + * Open \______ \ ____ ____ | | _\_ |__ _______ ___ + * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / + * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < + * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ + * \/ \/ \/ \/ \/ + * $Id$ + * + * Copyright (C) 2021 by Tomasz Moń + * Ported from Linux libertas driver + * Copyright 2008 Analog Devices Inc. + * Authors: + * Andrey Yurovsky + * Colin McCabe + * Inspired by if_sdio.c, Copyright 2007-2008 Pierre Ossman + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY + * KIND, either express or implied. + * + ****************************************************************************/ + +#include "config.h" +/*#define LOGF_ENABLE*/ +#include "logf.h" +#include "errno.h" +#include "file.h" +#include "panic.h" +#include "system.h" +#include "tick.h" +#include +#include "if_spi.h" +#include "if_spi_drv.h" + +#define ARRAY_SIZE(x) (sizeof(x) / sizeof((x)[0])) +#define DIV_ROUND_UP(n,d) (((n) + (d) - 1)/(d)) + +struct if_spi_card +{ + /* The card ID and card revision, as reported by the hardware. */ + uint16_t card_id; + uint8_t card_rev; + + unsigned long spu_port_delay; + unsigned long spu_reg_delay; + + uint8_t cmd_buffer[IF_SPI_CMD_BUF_SIZE]; +}; + +#define MODEL_8686 0x0b + +static const struct +{ + uint16_t model; + const char *helper; + const char *main; +} +fw_table[] = +{ + { MODEL_8686, ROCKBOX_DIR"/libertas/gspi8686_v9_helper.bin", ROCKBOX_DIR"/libertas/gspi8686_v9.bin" }, + { 0, NULL, NULL } +}; + + +/* + * SPI Interface Unit Routines + * + * The SPU sits between the host and the WLAN module. + * All communication with the firmware is through SPU transactions. + * + * First we have to put a SPU register name on the bus. Then we can + * either read from or write to that register. + * + */ + +static void spu_transaction_init(struct if_spi_card *card) +{ + (void)card; + /* Linux delays 400 ns if spu_transaction_finish() was called + * within the same jiffy. As we don't have jiffy counter nor + * nanosecond delays, simply delay for 1 us. This currently + * does not really matter as this driver simply loads firmware. + */ + udelay(1); + libertas_spi_cs(0); /* assert CS */ +} + +static void spu_transaction_finish(struct if_spi_card *card) +{ + (void)card; + libertas_spi_cs(1); /* drop CS */ +} + +/* + * Write out a byte buffer to an SPI register, + * using a series of 16-bit transfers. + */ +static int spu_write(struct if_spi_card *card, uint16_t reg, const uint8_t *buf, int len) +{ + int err = 0; + uint8_t reg_out[2]; + + /* You must give an even number of bytes to the SPU, even if it + * doesn't care about the last one. */ + if (len & 0x1) + panicf("Odd length in spu_write()"); + + reg |= IF_SPI_WRITE_OPERATION_MASK; + reg_out[0] = (reg & 0x00FF); + reg_out[1] = (reg & 0xFF00) >> 8; + + spu_transaction_init(card); + libertas_spi_tx(reg_out, sizeof(reg_out)); + libertas_spi_tx(buf, len); + spu_transaction_finish(card); + return err; +} + +static inline int spu_write_u16(struct if_spi_card *card, uint16_t reg, uint16_t val) +{ + uint8_t buf[2]; + buf[0] = (val & 0x00FF); + buf[1] = (val & 0xFF00) >> 8; + return spu_write(card, reg, buf, sizeof(buf)); +} + +static inline int spu_reg_is_port_reg(uint16_t reg) +{ + switch (reg) + { + case IF_SPI_IO_RDWRPORT_REG: + case IF_SPI_CMD_RDWRPORT_REG: + case IF_SPI_DATA_RDWRPORT_REG: + return 1; + default: + return 0; + } +} + +static int spu_read(struct if_spi_card *card, uint16_t reg, uint8_t *buf, int len) +{ + unsigned int delay; + int err = 0; + uint8_t reg_out[2]; + + /* + * You must take an even number of bytes from the SPU, even if you + * don't care about the last one. + */ + if (len & 0x1) + panicf("Odd length in spu_read()"); + + reg |= IF_SPI_READ_OPERATION_MASK; + reg_out[0] = (reg & 0x00FF); + reg_out[1] = (reg & 0xFF00) >> 8; + + spu_transaction_init(card); + libertas_spi_tx(reg_out, sizeof(reg_out)); + + delay = spu_reg_is_port_reg(reg) ? card->spu_port_delay : card->spu_reg_delay; + /* Busy-wait while the SPU fills the FIFO */ + delay = DIV_ROUND_UP((100 + (delay * 10)), 1000); + if (delay < 1000) + udelay(delay); + else + mdelay(DIV_ROUND_UP(delay, 1000)); + + libertas_spi_rx(buf, len); + spu_transaction_finish(card); + return err; +} + +/* Read 16 bits from an SPI register */ +static inline int spu_read_u16(struct if_spi_card *card, uint16_t reg, uint16_t *val) +{ + uint8_t buf[2]; + int ret; + + ret = spu_read(card, reg, buf, sizeof(buf)); + if (ret == 0) + *val = buf[0] | (buf[1] << 8); + + return ret; +} + +/* + * Read 32 bits from an SPI register. + * The low 16 bits are read first. + */ +static int spu_read_u32(struct if_spi_card *card, uint16_t reg, uint32_t *val) +{ + uint8_t buf[4]; + int err; + + err = spu_read(card, reg, buf, sizeof(buf)); + if (!err) + *val = buf[0] | (buf[1] << 8) | (buf[2] << 16) | (buf[3] << 24); + return err; +} + +/* + * Keep reading 16 bits from an SPI register until you get the correct result. + * + * If mask = 0, the correct result is any non-zero number. + * If mask != 0, the correct result is any number where + * number & target_mask == target + * + * Returns -ETIMEDOUT if a five seconds passes without the correct result. + */ +static int spu_wait_for_u16(struct if_spi_card *card, uint16_t reg, + uint16_t target_mask, uint16_t target) +{ + int err; + unsigned long timeout = current_tick + 5*HZ; + while (1) + { + uint16_t val; + err = spu_read_u16(card, reg, &val); + if (err) + return err; + if (target_mask) + { + if ((val & target_mask) == target) + return 0; + } + else + { + if (val) + return 0; + } + udelay(100); + if (TIME_AFTER(current_tick, timeout)) + { + logf("%s: timeout with val=%02x, target_mask=%02x, target=%02x", + __func__, val, target_mask, target); + return -ETIMEDOUT; + } + } +} + +/* + * Read 16 bits from an SPI register until you receive a specific value. + * Returns -ETIMEDOUT if a 4 tries pass without success. + */ +static int spu_wait_for_u32(struct if_spi_card *card, uint32_t reg, uint32_t target) +{ + int err, try; + for (try = 0; try < 4; ++try) + { + uint32_t val = 0; + err = spu_read_u32(card, reg, &val); + if (err) + return err; + if (val == target) + return 0; + mdelay(100); + } + return -ETIMEDOUT; +} + +static int spu_set_interrupt_mode(struct if_spi_card *card, + int suppress_host_int, + int auto_int) +{ + int err = 0; + + /* + * We can suppress a host interrupt by clearing the appropriate + * bit in the "host interrupt status mask" register + */ + if (suppress_host_int) { + err = spu_write_u16(card, IF_SPI_HOST_INT_STATUS_MASK_REG, 0); + if (err) + return err; + } else { + err = spu_write_u16(card, IF_SPI_HOST_INT_STATUS_MASK_REG, + IF_SPI_HISM_TX_DOWNLOAD_RDY | + IF_SPI_HISM_RX_UPLOAD_RDY | + IF_SPI_HISM_CMD_DOWNLOAD_RDY | + IF_SPI_HISM_CARDEVENT | + IF_SPI_HISM_CMD_UPLOAD_RDY); + if (err) + return err; + } + + /* + * If auto-interrupts are on, the completion of certain transactions + * will trigger an interrupt automatically. If auto-interrupts + * are off, we need to set the "Card Interrupt Cause" register to + * trigger a card interrupt. + */ + if (auto_int) { + err = spu_write_u16(card, IF_SPI_HOST_INT_CTRL_REG, + IF_SPI_HICT_TX_DOWNLOAD_OVER_AUTO | + IF_SPI_HICT_RX_UPLOAD_OVER_AUTO | + IF_SPI_HICT_CMD_DOWNLOAD_OVER_AUTO | + IF_SPI_HICT_CMD_UPLOAD_OVER_AUTO); + if (err) + return err; + } else { + err = spu_write_u16(card, IF_SPI_HOST_INT_STATUS_MASK_REG, 0); + if (err) + return err; + } + return err; +} + +static int spu_get_chip_revision(struct if_spi_card *card, + uint16_t *card_id, uint8_t *card_rev) +{ + int err = 0; + uint32_t dev_ctrl; + err = spu_read_u32(card, IF_SPI_DEVICEID_CTRL_REG, &dev_ctrl); + if (err) + return err; + *card_id = IF_SPI_DEVICEID_CTRL_REG_TO_CARD_ID(dev_ctrl); + *card_rev = IF_SPI_DEVICEID_CTRL_REG_TO_CARD_REV(dev_ctrl); + return err; +} + +static int spu_set_bus_mode(struct if_spi_card *card, uint16_t mode) +{ + int err = 0; + uint16_t rval; + /* set bus mode */ + err = spu_write_u16(card, IF_SPI_SPU_BUS_MODE_REG, mode); + if (err) + return err; + /* Check that we were able to read back what we just wrote. */ + err = spu_read_u16(card, IF_SPI_SPU_BUS_MODE_REG, &rval); + if (err) + return err; + if ((rval & 0xF) != mode) + { + logf("Can't read bus mode register"); + return -EIO; + } + return 0; +} + +static int spu_init(struct if_spi_card *card) +{ + int err = 0; + uint32_t delay; + + err = spu_set_bus_mode(card, + IF_SPI_BUS_MODE_SPI_CLOCK_PHASE_RISING | + IF_SPI_BUS_MODE_DELAY_METHOD_TIMED | + IF_SPI_BUS_MODE_16_BIT_ADDRESS_16_BIT_DATA); + if (err) + return err; + card->spu_port_delay = 1000; + card->spu_reg_delay = 1000; + err = spu_read_u32(card, IF_SPI_DELAY_READ_REG, &delay); + if (err) + return err; + card->spu_port_delay = delay & 0x0000ffff; + card->spu_reg_delay = (delay & 0xffff0000) >> 16; + + logf("Initialized SPU unit. " + "spu_port_delay=0x%04lx, spu_reg_delay=0x%04lx", + card->spu_port_delay, card->spu_reg_delay); + return err; +} + + +/* + * Firmware Loading + */ + +static int if_spi_prog_helper_firmware(struct if_spi_card *card, int fd) +{ + int err = 0; + int bytes_read; + uint8_t *temp = card->cmd_buffer; + + err = spu_set_interrupt_mode(card, 1, 0); + if (err) + goto out; + + /* Load helper firmware image */ + while ((bytes_read = read(fd, temp, HELPER_FW_LOAD_CHUNK_SZ)) > 0) + { + /* + * Scratch pad 1 should contain the number of bytes we + * want to download to the firmware + */ + err = spu_write_u16(card, IF_SPI_SCRATCH_1_REG, + HELPER_FW_LOAD_CHUNK_SZ); + if (err) + goto out; + + err = spu_wait_for_u16(card, IF_SPI_HOST_INT_STATUS_REG, + IF_SPI_HIST_CMD_DOWNLOAD_RDY, + IF_SPI_HIST_CMD_DOWNLOAD_RDY); + if (err) + goto out; + + /* + * Feed the data into the command read/write port reg + * in chunks of 64 bytes + */ + memset(temp + bytes_read, 0, HELPER_FW_LOAD_CHUNK_SZ - bytes_read); + mdelay(10); + err = spu_write(card, IF_SPI_CMD_RDWRPORT_REG, + temp, HELPER_FW_LOAD_CHUNK_SZ); + if (err) + goto out; + + /* Interrupt the boot code */ + err = spu_write_u16(card, IF_SPI_HOST_INT_STATUS_REG, 0); + if (err) + goto out; + err = spu_write_u16(card, IF_SPI_CARD_INT_CAUSE_REG, + IF_SPI_CIC_CMD_DOWNLOAD_OVER); + if (err) + goto out; + } + + /* + * Once the helper / single stage firmware download is complete, + * write 0 to scratch pad 1 and interrupt the + * bootloader. This completes the helper download. + */ + err = spu_write_u16(card, IF_SPI_SCRATCH_1_REG, FIRMWARE_DNLD_OK); + if (err) + goto out; + err = spu_write_u16(card, IF_SPI_HOST_INT_STATUS_REG, 0); + if (err) + goto out; + err = spu_write_u16(card, IF_SPI_CARD_INT_CAUSE_REG, + IF_SPI_CIC_CMD_DOWNLOAD_OVER); +out: + if (err) + logf("failed to load helper firmware (err=%d)", err); + + return err; +} + +/* + * Returns the length of the next packet the firmware expects us to send. + * Sets crc_err if the previous transfer had a CRC error. + */ +static int if_spi_prog_main_firmware_check_len(struct if_spi_card *card, + int *crc_err) +{ + uint16_t len; + int err = 0; + + /* + * wait until the host interrupt status register indicates + * that we are ready to download + */ + err = spu_wait_for_u16(card, IF_SPI_HOST_INT_STATUS_REG, + IF_SPI_HIST_CMD_DOWNLOAD_RDY, + IF_SPI_HIST_CMD_DOWNLOAD_RDY); + if (err) + { + logf("timed out waiting for host_int_status"); + return err; + } + + /* Ask the device how many bytes of firmware it wants. */ + err = spu_read_u16(card, IF_SPI_SCRATCH_1_REG, &len); + if (err) + return err; + + if (len > IF_SPI_CMD_BUF_SIZE) + { + logf("firmware load device requested a larger transfer than we are prepared to handle (len = %d)", + len); + return -EIO; + } + if (len & 0x1) { + logf("%s: crc error", __func__); + len &= ~0x1; + *crc_err = 1; + } else + *crc_err = 0; + + return len; +} + +static int if_spi_prog_main_firmware(struct if_spi_card *card, int fd) +{ + int len; + int bytes_read = 0, crc_err = 0, err = 0; + uint16_t num_crc_errs; + + err = spu_set_interrupt_mode(card, 1, 0); + if (err) + goto out; + + err = spu_wait_for_u16(card, IF_SPI_SCRATCH_1_REG, 0, 0); + if (err) + { + logf("%s: timed out waiting for initial scratch reg = 0", __func__); + goto out; + } + + num_crc_errs = 0; + while ((len = if_spi_prog_main_firmware_check_len(card, &crc_err))) + { + if (len < 0) + { + err = len; + goto out; + } + if (crc_err) + { + /* Previous transfer failed. */ + if (++num_crc_errs > MAX_MAIN_FW_LOAD_CRC_ERR) + { + logf("Too many CRC errors encountered in firmware load."); + err = -EIO; + goto out; + } + + /* Rewind so we read back the data from previous transfer */ + lseek(fd, -bytes_read, SEEK_CUR); + } + + bytes_read = read(fd, card->cmd_buffer, len); + if (bytes_read < 0) + { + /* + * If there are no more bytes left, we would normally + * expect to have terminated with len = 0 + */ + logf("Firmware load wants more bytes than we have to offer."); + break; + } + else if (bytes_read < len) + { + memset(card->cmd_buffer + bytes_read, 0, len - bytes_read); + } + + err = spu_write_u16(card, IF_SPI_HOST_INT_STATUS_REG, 0); + if (err) + goto out; + err = spu_write(card, IF_SPI_CMD_RDWRPORT_REG, card->cmd_buffer, len); + if (err) + goto out; + err = spu_write_u16(card, IF_SPI_CARD_INT_CAUSE_REG, + IF_SPI_CIC_CMD_DOWNLOAD_OVER); + if (err) + goto out; + } + if (read(fd, card->cmd_buffer, IF_SPI_CMD_BUF_SIZE) > 0) + { + logf("firmware load wants fewer bytes than we have to offer"); + } + + /* Confirm firmware download */ + err = spu_wait_for_u32(card, IF_SPI_SCRATCH_4_REG, + SUCCESSFUL_FW_DOWNLOAD_MAGIC); + if (err) + { + logf("failed to confirm the firmware download"); + goto out; + } + +out: + if (err) + logf("failed to load firmware (err=%d)", err); + + return err; +} + +static int if_spi_init_card(struct if_spi_card *card) +{ + int err; + size_t i; + uint32_t scratch; + int fd; + + err = spu_init(card); + if (err) + goto out; + err = spu_get_chip_revision(card, &card->card_id, &card->card_rev); + if (err) + goto out; + + err = spu_read_u32(card, IF_SPI_SCRATCH_4_REG, &scratch); + if (err) + goto out; + if (scratch == SUCCESSFUL_FW_DOWNLOAD_MAGIC) + logf("Firmware is already loaded for Marvell WLAN 802.11 adapter"); + else { + /* Check if we support this card */ + for (i = 0; i < ARRAY_SIZE(fw_table); i++) { + if (card->card_id == fw_table[i].model) + break; + } + if (i == ARRAY_SIZE(fw_table)) { + logf("Unsupported chip_id: 0x%02x", card->card_id); + err = -ENODEV; + goto out; + } + + logf("Initializing FW for Marvell WLAN 802.11 adapter " + "(chip_id = 0x%04x, chip_rev = 0x%02x)", + card->card_id, card->card_rev); + + fd = open(fw_table[i].helper, O_RDONLY); + if (fd >= 0) + { + err = if_spi_prog_helper_firmware(card, fd); + close(fd); + if (err) + goto out; + } + else + { + logf("failed to find firmware helper (%s)", fw_table[i].helper); + err = -ENOENT; + goto out; + } + + fd = open(fw_table[i].main, O_RDONLY); + if (fd >= 0) + { + err = if_spi_prog_main_firmware(card, fd); + close(fd); + if (err) + goto out; + } + else + { + logf("failed to find firmware (%s)", fw_table[i].main); + err = -ENOENT; + goto out; + } + + logf("loaded FW for Marvell WLAN 802.11 adapter"); + } + + err = spu_set_interrupt_mode(card, 0, 1); + if (err) + goto out; + +out: + return err; +} + +void wifi_init(void) INIT_ATTR +{ +#if 0 + static struct if_spi_card card; + libertas_spi_init(); + libertas_spi_pd(1); + libertas_spi_reset(1); + mdelay(100); + if (!if_spi_init_card(&card)) + { + /* TODO: Configure card and enter deep sleep */ + } + else +#else + libertas_spi_init(); + (void)if_spi_init_card; +#endif + { + /* Keep the lines in lowest power configuration */ + libertas_spi_pd(0); + libertas_spi_reset(1); + libertas_spi_cs(1); + } +} diff --git a/firmware/drivers/libertas/if_spi.h b/firmware/drivers/libertas/if_spi.h new file mode 100644 index 0000000000..bfca12981a --- /dev/null +++ b/firmware/drivers/libertas/if_spi.h @@ -0,0 +1,215 @@ +/*************************************************************************** + * __________ __ ___. + * Open \______ \ ____ ____ | | _\_ |__ _______ ___ + * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / + * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < + * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ + * \/ \/ \/ \/ \/ + * $Id$ + * + * Copyright (C) 2021 by Tomasz Moń + * Ported from Linux libertas driver + * Copyright 2008 Analog Devices Inc. + * Authors: + * Andrey Yurovsky + * Colin McCabe + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY + * KIND, either express or implied. + * + ****************************************************************************/ + +#ifndef _LBS_IF_SPI_H_ +#define _LBS_IF_SPI_H_ + +#define IPFIELD_ALIGN_OFFSET 2 +#define IF_SPI_CMD_BUF_SIZE 2400 + +/***************** Firmware *****************/ + +#define IF_SPI_FW_NAME_MAX 30 + +#define MAX_MAIN_FW_LOAD_CRC_ERR 10 + +/* Chunk size when loading the helper firmware */ +#define HELPER_FW_LOAD_CHUNK_SZ 64 + +/* Value to write to indicate end of helper firmware dnld */ +#define FIRMWARE_DNLD_OK 0x0000 + +/* Value to check once the main firmware is downloaded */ +#define SUCCESSFUL_FW_DOWNLOAD_MAGIC 0x88888888 + +/***************** SPI Interface Unit *****************/ +/* Masks used in SPI register read/write operations */ +#define IF_SPI_READ_OPERATION_MASK 0x0 +#define IF_SPI_WRITE_OPERATION_MASK 0x8000 + +/* SPI register offsets. 4-byte aligned. */ +#define IF_SPI_DEVICEID_CTRL_REG 0x00 /* DeviceID controller reg */ +#define IF_SPI_IO_READBASE_REG 0x04 /* Read I/O base reg */ +#define IF_SPI_IO_WRITEBASE_REG 0x08 /* Write I/O base reg */ +#define IF_SPI_IO_RDWRPORT_REG 0x0C /* Read/Write I/O port reg */ + +#define IF_SPI_CMD_READBASE_REG 0x10 /* Read command base reg */ +#define IF_SPI_CMD_WRITEBASE_REG 0x14 /* Write command base reg */ +#define IF_SPI_CMD_RDWRPORT_REG 0x18 /* Read/Write command port reg */ + +#define IF_SPI_DATA_READBASE_REG 0x1C /* Read data base reg */ +#define IF_SPI_DATA_WRITEBASE_REG 0x20 /* Write data base reg */ +#define IF_SPI_DATA_RDWRPORT_REG 0x24 /* Read/Write data port reg */ + +#define IF_SPI_SCRATCH_1_REG 0x28 /* Scratch reg 1 */ +#define IF_SPI_SCRATCH_2_REG 0x2C /* Scratch reg 2 */ +#define IF_SPI_SCRATCH_3_REG 0x30 /* Scratch reg 3 */ +#define IF_SPI_SCRATCH_4_REG 0x34 /* Scratch reg 4 */ + +#define IF_SPI_TX_FRAME_SEQ_NUM_REG 0x38 /* Tx frame sequence number reg */ +#define IF_SPI_TX_FRAME_STATUS_REG 0x3C /* Tx frame status reg */ + +#define IF_SPI_HOST_INT_CTRL_REG 0x40 /* Host interrupt controller reg */ + +#define IF_SPI_CARD_INT_CAUSE_REG 0x44 /* Card interrupt cause reg */ +#define IF_SPI_CARD_INT_STATUS_REG 0x48 /* Card interrupt status reg */ +#define IF_SPI_CARD_INT_EVENT_MASK_REG 0x4C /* Card interrupt event mask */ +#define IF_SPI_CARD_INT_STATUS_MASK_REG 0x50 /* Card interrupt status mask */ + +#define IF_SPI_CARD_INT_RESET_SELECT_REG 0x54 /* Card interrupt reset select */ + +#define IF_SPI_HOST_INT_CAUSE_REG 0x58 /* Host interrupt cause reg */ +#define IF_SPI_HOST_INT_STATUS_REG 0x5C /* Host interrupt status reg */ +#define IF_SPI_HOST_INT_EVENT_MASK_REG 0x60 /* Host interrupt event mask */ +#define IF_SPI_HOST_INT_STATUS_MASK_REG 0x64 /* Host interrupt status mask */ +#define IF_SPI_HOST_INT_RESET_SELECT_REG 0x68 /* Host interrupt reset select */ + +#define IF_SPI_DELAY_READ_REG 0x6C /* Delay read reg */ +#define IF_SPI_SPU_BUS_MODE_REG 0x70 /* SPU BUS mode reg */ + +/***************** IF_SPI_DEVICEID_CTRL_REG *****************/ +#define IF_SPI_DEVICEID_CTRL_REG_TO_CARD_ID(dc) ((dc & 0xffff0000)>>16) +#define IF_SPI_DEVICEID_CTRL_REG_TO_CARD_REV(dc) (dc & 0x000000ff) + +/***************** IF_SPI_HOST_INT_CTRL_REG *****************/ +/* Host Interrupt Control bit : Wake up */ +#define IF_SPI_HICT_WAKE_UP (1<<0) +/* Host Interrupt Control bit : WLAN ready */ +#define IF_SPI_HICT_WLAN_READY (1<<1) +/*#define IF_SPI_HICT_FIFO_FIRST_HALF_EMPTY (1<<2) */ +/*#define IF_SPI_HICT_FIFO_SECOND_HALF_EMPTY (1<<3) */ +/*#define IF_SPI_HICT_IRQSRC_WLAN (1<<4) */ +/* Host Interrupt Control bit : Tx auto download */ +#define IF_SPI_HICT_TX_DOWNLOAD_OVER_AUTO (1<<5) +/* Host Interrupt Control bit : Rx auto upload */ +#define IF_SPI_HICT_RX_UPLOAD_OVER_AUTO (1<<6) +/* Host Interrupt Control bit : Command auto download */ +#define IF_SPI_HICT_CMD_DOWNLOAD_OVER_AUTO (1<<7) +/* Host Interrupt Control bit : Command auto upload */ +#define IF_SPI_HICT_CMD_UPLOAD_OVER_AUTO (1<<8) + +/***************** IF_SPI_CARD_INT_CAUSE_REG *****************/ +/* Card Interrupt Case bit : Tx download over */ +#define IF_SPI_CIC_TX_DOWNLOAD_OVER (1<<0) +/* Card Interrupt Case bit : Rx upload over */ +#define IF_SPI_CIC_RX_UPLOAD_OVER (1<<1) +/* Card Interrupt Case bit : Command download over */ +#define IF_SPI_CIC_CMD_DOWNLOAD_OVER (1<<2) +/* Card Interrupt Case bit : Host event */ +#define IF_SPI_CIC_HOST_EVENT (1<<3) +/* Card Interrupt Case bit : Command upload over */ +#define IF_SPI_CIC_CMD_UPLOAD_OVER (1<<4) +/* Card Interrupt Case bit : Power down */ +#define IF_SPI_CIC_POWER_DOWN (1<<5) + +/***************** IF_SPI_CARD_INT_STATUS_REG *****************/ +#define IF_SPI_CIS_TX_DOWNLOAD_OVER (1<<0) +#define IF_SPI_CIS_RX_UPLOAD_OVER (1<<1) +#define IF_SPI_CIS_CMD_DOWNLOAD_OVER (1<<2) +#define IF_SPI_CIS_HOST_EVENT (1<<3) +#define IF_SPI_CIS_CMD_UPLOAD_OVER (1<<4) +#define IF_SPI_CIS_POWER_DOWN (1<<5) + +/***************** IF_SPI_HOST_INT_CAUSE_REG *****************/ +#define IF_SPI_HICU_TX_DOWNLOAD_RDY (1<<0) +#define IF_SPI_HICU_RX_UPLOAD_RDY (1<<1) +#define IF_SPI_HICU_CMD_DOWNLOAD_RDY (1<<2) +#define IF_SPI_HICU_CARD_EVENT (1<<3) +#define IF_SPI_HICU_CMD_UPLOAD_RDY (1<<4) +#define IF_SPI_HICU_IO_WR_FIFO_OVERFLOW (1<<5) +#define IF_SPI_HICU_IO_RD_FIFO_UNDERFLOW (1<<6) +#define IF_SPI_HICU_DATA_WR_FIFO_OVERFLOW (1<<7) +#define IF_SPI_HICU_DATA_RD_FIFO_UNDERFLOW (1<<8) +#define IF_SPI_HICU_CMD_WR_FIFO_OVERFLOW (1<<9) +#define IF_SPI_HICU_CMD_RD_FIFO_UNDERFLOW (1<<10) + +/***************** IF_SPI_HOST_INT_STATUS_REG *****************/ +/* Host Interrupt Status bit : Tx download ready */ +#define IF_SPI_HIST_TX_DOWNLOAD_RDY (1<<0) +/* Host Interrupt Status bit : Rx upload ready */ +#define IF_SPI_HIST_RX_UPLOAD_RDY (1<<1) +/* Host Interrupt Status bit : Command download ready */ +#define IF_SPI_HIST_CMD_DOWNLOAD_RDY (1<<2) +/* Host Interrupt Status bit : Card event */ +#define IF_SPI_HIST_CARD_EVENT (1<<3) +/* Host Interrupt Status bit : Command upload ready */ +#define IF_SPI_HIST_CMD_UPLOAD_RDY (1<<4) +/* Host Interrupt Status bit : I/O write FIFO overflow */ +#define IF_SPI_HIST_IO_WR_FIFO_OVERFLOW (1<<5) +/* Host Interrupt Status bit : I/O read FIFO underflow */ +#define IF_SPI_HIST_IO_RD_FIFO_UNDRFLOW (1<<6) +/* Host Interrupt Status bit : Data write FIFO overflow */ +#define IF_SPI_HIST_DATA_WR_FIFO_OVERFLOW (1<<7) +/* Host Interrupt Status bit : Data read FIFO underflow */ +#define IF_SPI_HIST_DATA_RD_FIFO_UNDERFLOW (1<<8) +/* Host Interrupt Status bit : Command write FIFO overflow */ +#define IF_SPI_HIST_CMD_WR_FIFO_OVERFLOW (1<<9) +/* Host Interrupt Status bit : Command read FIFO underflow */ +#define IF_SPI_HIST_CMD_RD_FIFO_UNDERFLOW (1<<10) + +/***************** IF_SPI_HOST_INT_STATUS_MASK_REG *****************/ +/* Host Interrupt Status Mask bit : Tx download ready */ +#define IF_SPI_HISM_TX_DOWNLOAD_RDY (1<<0) +/* Host Interrupt Status Mask bit : Rx upload ready */ +#define IF_SPI_HISM_RX_UPLOAD_RDY (1<<1) +/* Host Interrupt Status Mask bit : Command download ready */ +#define IF_SPI_HISM_CMD_DOWNLOAD_RDY (1<<2) +/* Host Interrupt Status Mask bit : Card event */ +#define IF_SPI_HISM_CARDEVENT (1<<3) +/* Host Interrupt Status Mask bit : Command upload ready */ +#define IF_SPI_HISM_CMD_UPLOAD_RDY (1<<4) +/* Host Interrupt Status Mask bit : I/O write FIFO overflow */ +#define IF_SPI_HISM_IO_WR_FIFO_OVERFLOW (1<<5) +/* Host Interrupt Status Mask bit : I/O read FIFO underflow */ +#define IF_SPI_HISM_IO_RD_FIFO_UNDERFLOW (1<<6) +/* Host Interrupt Status Mask bit : Data write FIFO overflow */ +#define IF_SPI_HISM_DATA_WR_FIFO_OVERFLOW (1<<7) +/* Host Interrupt Status Mask bit : Data write FIFO underflow */ +#define IF_SPI_HISM_DATA_RD_FIFO_UNDERFLOW (1<<8) +/* Host Interrupt Status Mask bit : Command write FIFO overflow */ +#define IF_SPI_HISM_CMD_WR_FIFO_OVERFLOW (1<<9) +/* Host Interrupt Status Mask bit : Command write FIFO underflow */ +#define IF_SPI_HISM_CMD_RD_FIFO_UNDERFLOW (1<<10) + +/***************** IF_SPI_SPU_BUS_MODE_REG *****************/ +/* SCK edge on which the WLAN module outputs data on MISO */ +#define IF_SPI_BUS_MODE_SPI_CLOCK_PHASE_FALLING 0x8 +#define IF_SPI_BUS_MODE_SPI_CLOCK_PHASE_RISING 0x0 + +/* In a SPU read operation, there is a delay between writing the SPU + * register name and getting back data from the WLAN module. + * This can be specified in terms of nanoseconds or in terms of dummy + * clock cycles which the master must output before receiving a response. */ +#define IF_SPI_BUS_MODE_DELAY_METHOD_DUMMY_CLOCK 0x4 +#define IF_SPI_BUS_MODE_DELAY_METHOD_TIMED 0x0 + +/* Some different modes of SPI operation */ +#define IF_SPI_BUS_MODE_8_BIT_ADDRESS_16_BIT_DATA 0x00 +#define IF_SPI_BUS_MODE_8_BIT_ADDRESS_32_BIT_DATA 0x01 +#define IF_SPI_BUS_MODE_16_BIT_ADDRESS_16_BIT_DATA 0x02 +#define IF_SPI_BUS_MODE_16_BIT_ADDRESS_32_BIT_DATA 0x03 + +#endif diff --git a/firmware/drivers/libertas/if_spi_drv.h b/firmware/drivers/libertas/if_spi_drv.h new file mode 100644 index 0000000000..6c8b5c3d92 --- /dev/null +++ b/firmware/drivers/libertas/if_spi_drv.h @@ -0,0 +1,34 @@ +/*************************************************************************** + * __________ __ ___. + * Open \______ \ ____ ____ | | _\_ |__ _______ ___ + * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / + * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < + * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ + * \/ \/ \/ \/ \/ + * $Id$ + * + * Copyright (C) 2021 by Tomasz Moń + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY + * KIND, either express or implied. + * + ****************************************************************************/ + +#ifndef LIBERTAS_IF_SPI_DRV +#define LIBERTAS_IF_SPI_DRV + +#include + +void libertas_spi_init(void); +void libertas_spi_reset(int high); +void libertas_spi_pd(int high); +void libertas_spi_cs(int high); +void libertas_spi_tx(const uint8_t *buf, int len); +void libertas_spi_rx(uint8_t *buf, int len); + +#endif diff --git a/firmware/export/config/sansaconnect.h b/firmware/export/config/sansaconnect.h index 5fc91a2794..874b198316 100644 --- a/firmware/export/config/sansaconnect.h +++ b/firmware/export/config/sansaconnect.h @@ -135,6 +135,12 @@ /* Define this if you have a software controlled poweroff */ #define HAVE_SW_POWEROFF +#ifndef BOOTLOADER +#define HAVE_WIFI +/* define this if the target has Marvell 88W8686 interfaced over SPI */ +#define HAVE_W8686_SPI +#endif + /* The number of bytes reserved for loadable codecs */ #define CODEC_SIZE 0x100000 diff --git a/firmware/export/wifi.h b/firmware/export/wifi.h new file mode 100644 index 0000000000..a70e062cb0 --- /dev/null +++ b/firmware/export/wifi.h @@ -0,0 +1,29 @@ +/*************************************************************************** + * __________ __ ___. + * Open \______ \ ____ ____ | | _\_ |__ _______ ___ + * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / + * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < + * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ + * \/ \/ \/ \/ \/ + * $Id$ + * + * Copyright (C) 2021 by Tomasz Moń + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY + * KIND, either express or implied. + * + ****************************************************************************/ + +#ifndef WIFI_H +#define WIFI_H + +#include "config.h" + +void wifi_init(void) INIT_ATTR; + +#endif diff --git a/firmware/target/arm/tms320dm320/sansa-connect/avr-sansaconnect.c b/firmware/target/arm/tms320dm320/sansa-connect/avr-sansaconnect.c index 12058eba03..a4efe0962a 100644 --- a/firmware/target/arm/tms320dm320/sansa-connect/avr-sansaconnect.c +++ b/firmware/target/arm/tms320dm320/sansa-connect/avr-sansaconnect.c @@ -75,7 +75,7 @@ #define CMD_WHEEL_EN 0xD0 #define CMD_SET_INTCHRG 0xD1 #define CMD_GET_INTCHRG 0xD2 -#define CMD_UNKNOWN_D3 0xD3 +#define CMD_WIFI_PD 0xD3 #define CMD_UNKNOWN_D4 0xD4 #define CMD_UNKNOWN_D5 0xD5 #define CMD_UNKNOWN_D6 0xD6 @@ -315,7 +315,7 @@ static size_t avr_command_data_size(uint8_t opcode) case CMD_WHEEL_EN: return 1; case CMD_SET_INTCHRG: return 1; case CMD_GET_INTCHRG: return 1; - case CMD_UNKNOWN_D3: return 1; + case CMD_WIFI_PD: return 1; case CMD_UNKNOWN_D4: return 1; case CMD_UNKNOWN_D5: return 2; case CMD_UNKNOWN_D6: return 2; @@ -536,6 +536,12 @@ void avr_hid_enable_charger(void) avr_execute_command(CMD_SET_INTCHRG, &enable, sizeof(enable)); } +void avr_hid_wifi_pd(int high) +{ + uint8_t state = high ? 0x01 : 0x00; + avr_execute_command(CMD_WIFI_PD, &state, sizeof(state)); +} + static void avr_hid_lcm_power(uint8_t parameter) { avr_execute_command(CMD_LCM_POWER, ¶meter, sizeof(parameter)); diff --git a/firmware/target/arm/tms320dm320/sansa-connect/avr-sansaconnect.h b/firmware/target/arm/tms320dm320/sansa-connect/avr-sansaconnect.h index 64b44675f7..baa7083760 100644 --- a/firmware/target/arm/tms320dm320/sansa-connect/avr-sansaconnect.h +++ b/firmware/target/arm/tms320dm320/sansa-connect/avr-sansaconnect.h @@ -28,6 +28,8 @@ void avr_hid_init(void); void avr_hid_enable_charger(void); +void avr_hid_wifi_pd(int high); + void avr_hid_lcm_sleep(void); void avr_hid_lcm_wake(void); void avr_hid_lcm_power_on(void); diff --git a/firmware/target/arm/tms320dm320/sansa-connect/wifi-sansaconnect.c b/firmware/target/arm/tms320dm320/sansa-connect/wifi-sansaconnect.c new file mode 100644 index 0000000000..867b1da477 --- /dev/null +++ b/firmware/target/arm/tms320dm320/sansa-connect/wifi-sansaconnect.c @@ -0,0 +1,130 @@ +/*************************************************************************** +* __________ __ ___. +* Open \______ \ ____ ____ | | _\_ |__ _______ ___ +* Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / +* Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < +* Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ +* \/ \/ \/ \/ \/ +* $Id$ +* +* Copyright (C) 2021 by Tomasz Moń +* +* This program is free software; you can redistribute it and/or +* modify it under the terms of the GNU General Public License +* as published by the Free Software Foundation; either version 2 +* of the License, or (at your option) any later version. +* +* This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY +* KIND, either express or implied. +* +****************************************************************************/ + +#include "kernel.h" +#include "system.h" +#include "spi.h" +#include "avr-sansaconnect.h" +#include "libertas/if_spi_drv.h" + +#define IO_SERIAL0_XMIT (0x100) + +void libertas_spi_init(void) +{ + IO_GIO_DIR0 &= ~((1 << 4) /* CS */ | (1 << 3) /* reset */); + libertas_spi_reset(1); + libertas_spi_cs(1); + + /* Enable the clock */ + bitset16(&IO_CLK_MOD2, CLK_MOD2_SIF0); + + /* Disable transmitter */ + IO_SERIAL0_TX_ENABLE = 0x0001; + + /* SELSDEN = 0, SLVEN = 0, SIOCLR = 0, SCLKM = 1, MSB = 1, MSSEL = 0, + * RATE = 2 -> 15MHz + */ + IO_SERIAL0_MODE = 0x0601; + + /* Disable the clock */ + bitclr16(&IO_CLK_MOD2, CLK_MOD2_SIF0); + + /* Make sure the SPI clock is not inverted */ + bitclr16(&IO_CLK_INV, CLK_INV_SIF0); +} + +void libertas_spi_reset(int high) +{ + if (high) + { + IO_GIO_BITSET0 = (1 << 3); + } + else + { + IO_GIO_BITCLR0 = (1 << 3); + } +} + +void libertas_spi_pd(int high) +{ + avr_hid_wifi_pd(high); +} + +void libertas_spi_cs(int high) +{ + if (high) + { + IO_GIO_BITSET0 = (1 << 4); + } + else + { + IO_GIO_BITCLR0 = (1 << 4); + } +} + +void libertas_spi_tx(const uint8_t *buf, int len) +{ + /* Enable the clock */ + bitset16(&IO_CLK_MOD2, CLK_MOD2_SIF0); + IO_SERIAL0_TX_ENABLE = 0x0001; + + while (len > 0) + { + IO_SERIAL0_TX_DATA = *(buf + 1); + while (IO_SERIAL0_RX_DATA & IO_SERIAL0_XMIT) {}; + IO_SERIAL0_TX_DATA = *buf; + while (IO_SERIAL0_RX_DATA & IO_SERIAL0_XMIT) {}; + + buf += 2; + len -= 2; + } + + IO_SERIAL0_TX_ENABLE = 0x0000; + + /* Disable the clock */ + bitclr16(&IO_CLK_MOD2, CLK_MOD2_SIF0); +} + +void libertas_spi_rx(uint8_t *buf, int len) +{ + /* Enable the clock */ + bitset16(&IO_CLK_MOD2, CLK_MOD2_SIF0); + IO_SERIAL0_TX_ENABLE = 0x0001; + + while (len > 0) + { + uint16_t data; + IO_SERIAL0_TX_DATA = 0; + while ((data = IO_SERIAL0_RX_DATA) & IO_SERIAL0_XMIT) {}; + *(buf + 1) = data & 0xFF; + IO_SERIAL0_TX_DATA = 0; + while ((data = IO_SERIAL0_RX_DATA) & IO_SERIAL0_XMIT) {}; + *buf = data & 0xFF; + + buf += 2; + len -= 2; + } + + IO_SERIAL0_TX_ENABLE = 0x0000; + + /* Disable the clock */ + bitclr16(&IO_CLK_MOD2, CLK_MOD2_SIF0); +} diff --git a/firmware/target/arm/tms320dm320/system-dm320.c b/firmware/target/arm/tms320dm320/system-dm320.c index 935f3609a6..c80082afd8 100644 --- a/firmware/target/arm/tms320dm320/system-dm320.c +++ b/firmware/target/arm/tms320dm320/system-dm320.c @@ -369,9 +369,11 @@ void system_init(void) #endif #ifdef SANSA_CONNECT +#ifndef HAVE_WIFI /* keep WIFI CS and reset high to save power */ IO_GIO_DIR0 &= ~((1 << 4) /* CS */ | (1 << 3) /* reset */); IO_GIO_BITSET0 = (1 << 4) | (1 << 3); +#endif i2c_init(); avr_hid_init(); diff --git a/tools/buildzip.pl b/tools/buildzip.pl index 4e9ba79eeb..43c304ff12 100755 --- a/tools/buildzip.pl +++ b/tools/buildzip.pl @@ -387,6 +387,11 @@ sub buildzip { open(NOMEDIA, ">$temp_dir/.nomedia") || die "can't open .nomedia"; close(NOMEDIA); } + # copy wifi firmware + if ($modelname =~ /sansaconnect/) { + glob_mkdir("$temp_dir/libertas"); + glob_copy("$ROOT/firmware/drivers/libertas/firmware/*", "$temp_dir/libertas/"); + } glob_mkdir("$temp_dir/langs"); glob_mkdir("$temp_dir/rocks");