|
@@ -59,7 +59,7 @@ static TimerHandle_t fpga_timesync_timer;
|
|
|
static SemaphoreHandle_t spi_mutex;
|
|
|
static EventGroupHandle_t spi_done_evgroup;
|
|
|
static volatile bool spi_abort_all;
|
|
|
-static const volatile struct esplink_timesync *tsync_addr;
|
|
|
+static struct esplink_head head;
|
|
|
|
|
|
#define NOTIFY_INDEX 0
|
|
|
#define NOTIFY_FPGA (1 << 0)
|
|
@@ -235,8 +235,6 @@ static void fpga_poll_set_time(void);
|
|
|
|
|
|
static bool fpga_online(void)
|
|
|
{
|
|
|
- struct esplink_head head;
|
|
|
-
|
|
|
fpga_io_read(FPGA_CMD_ACK(EL_UIRQ_READY), ESPLINK_HDR_ADDR,
|
|
|
&head, sizeof head);
|
|
|
|
|
@@ -255,8 +253,6 @@ static bool fpga_online(void)
|
|
|
head.board.major, head.board.minor,
|
|
|
head.board.fixes, head.board.fpga);
|
|
|
|
|
|
- tsync_addr = head.tsync;
|
|
|
-
|
|
|
printf("[FPGA] online, signature \"%.*s\"\n",
|
|
|
(int)(sizeof head.signature - 1), head.signature);
|
|
|
esplink_start(&head);
|
|
@@ -272,7 +268,7 @@ static bool fpga_online(void)
|
|
|
|
|
|
static void fpga_offline(void)
|
|
|
{
|
|
|
- tsync_addr = NULL;
|
|
|
+ memset(&head, 0, sizeof head);
|
|
|
xSemaphoreTakeRecursive(spi_mutex, portMAX_DELAY);
|
|
|
xTimerStop(fpga_timesync_timer, portMAX_DELAY);
|
|
|
setenv_bool("status.max80.fpga", false);
|
|
@@ -363,7 +359,7 @@ fail:
|
|
|
return err;
|
|
|
}
|
|
|
|
|
|
-esp_err_t fpga_io_write(unsigned int cmd, const void *addr,
|
|
|
+esp_err_t fpga_io_write(unsigned int cmd, const volatile void *addr,
|
|
|
const void *data, size_t len)
|
|
|
{
|
|
|
struct fpga_iov iov;
|
|
@@ -376,7 +372,7 @@ esp_err_t fpga_io_write(unsigned int cmd, const void *addr,
|
|
|
return fpga_iov(&iov, 1);
|
|
|
}
|
|
|
|
|
|
-esp_err_t fpga_io_read(unsigned int cmd, const void *addr,
|
|
|
+esp_err_t fpga_io_read(unsigned int cmd, const volatile void *addr,
|
|
|
void *data, size_t len)
|
|
|
{
|
|
|
struct fpga_iov iov;
|
|
@@ -406,7 +402,7 @@ static void fpga_get_time(void)
|
|
|
struct esplink_timesync_buf get;
|
|
|
} tsbuf;
|
|
|
|
|
|
- if (!tsync_addr) {
|
|
|
+ if (!head.tsync) {
|
|
|
fpga_io_status(FPGA_CMD_ACK(EL_UIRQ_TIME));
|
|
|
return;
|
|
|
}
|
|
@@ -422,7 +418,7 @@ static void fpga_get_time(void)
|
|
|
trans.base.rxlength = sizeof tsbuf << 3;
|
|
|
trans.base.rx_buffer = &tsbuf;
|
|
|
|
|
|
- trans.base.addr = (size_t)&tsync_addr->get;
|
|
|
+ trans.base.addr = (size_t)&head.tsync->get;
|
|
|
trans.base.cmd = FPGA_CMD_RD | FPGA_CMD_ACK(EL_UIRQ_TIME);
|
|
|
|
|
|
xSemaphoreTakeRecursive(spi_mutex, portMAX_DELAY);
|
|
@@ -454,7 +450,7 @@ static void fpga_get_time(void)
|
|
|
|
|
|
static void fpga_poll_set_time(void)
|
|
|
{
|
|
|
- if (!tsync_addr)
|
|
|
+ if (!head.tsync)
|
|
|
return;
|
|
|
|
|
|
if (!time_net_sync_status) {
|
|
@@ -494,7 +490,7 @@ static void fpga_poll_set_time(void)
|
|
|
trans.length = sizeof tset << 3;
|
|
|
trans.tx_buffer = &tset;
|
|
|
|
|
|
- trans.addr = (size_t)&tsync_addr->set;
|
|
|
+ trans.addr = (size_t)&head.tsync->set;
|
|
|
trans.cmd = FPGA_CMD_WR | FPGA_CMD_IRQ(EL_DIRQ_TIME) |
|
|
|
FPGA_CMD_ACK(EL_UIRQ_TIME);
|
|
|
|
|
@@ -533,6 +529,34 @@ uint32_t fpga_io_status(unsigned int cmd)
|
|
|
return err ? 0 : *(const uint32_t *)trans.rx_data;
|
|
|
}
|
|
|
|
|
|
+static int fpga_read_func(token_t token, void *buf, size_t len)
|
|
|
+{
|
|
|
+ const void **pp = token;
|
|
|
+ const char *p = *pp;
|
|
|
+ esp_err_t err;
|
|
|
+
|
|
|
+ err = fpga_io_read(0, p, buf, len);
|
|
|
+ if (err)
|
|
|
+ return -1;
|
|
|
+
|
|
|
+ p += len;
|
|
|
+ *pp = p;
|
|
|
+ return len;
|
|
|
+}
|
|
|
+
|
|
|
+static void fpga_ota_update(void)
|
|
|
+{
|
|
|
+ struct esplink_ota ota;
|
|
|
+
|
|
|
+ fpga_io_read(0, head.ota, &ota, sizeof ota);
|
|
|
+ if (!ota.data)
|
|
|
+ return;
|
|
|
+
|
|
|
+ esp_update(fpga_read_func, &ota.data, ota.len);
|
|
|
+ fpga_io_status(FPGA_CMD_ACK(EL_UIRQ_OTA)|FPGA_CMD_IRQ(EL_DIRQ_DONE));
|
|
|
+ reboot_delayed();
|
|
|
+}
|
|
|
+
|
|
|
static void fpga_service_task(void *dummy)
|
|
|
{
|
|
|
(void)dummy;
|
|
@@ -565,17 +589,18 @@ static void fpga_service_task(void *dummy)
|
|
|
printf("[FPGA] FPGA status flags = 0x%08x\n", status);
|
|
|
|
|
|
if (!digitalRead(PIN_FPGA_INT)) {
|
|
|
- for (unsigned int i = 2; i < 8; i++) {
|
|
|
+ for (unsigned int i = 1; i < 8; i++) {
|
|
|
if (status & (0x100 << i))
|
|
|
status = fpga_io_status(FPGA_CMD_ACK(i));
|
|
|
}
|
|
|
if ((status & 0x301) == 0x300) {
|
|
|
- if (fpga_online())
|
|
|
+ if (fpga_online()) {
|
|
|
fpga_state = FPGA_ONLINE;
|
|
|
+ break;
|
|
|
+ }
|
|
|
}
|
|
|
- } else {
|
|
|
- notifiers = notify_wait_for(NOTIFY_FPGA|NOTIFY_DISABLE);
|
|
|
}
|
|
|
+ notifiers = notify_wait_for(NOTIFY_FPGA|NOTIFY_DISABLE);
|
|
|
break;
|
|
|
|
|
|
case FPGA_ONLINE:
|
|
@@ -604,7 +629,10 @@ static void fpga_service_task(void *dummy)
|
|
|
if (status & (0x100 << EL_UIRQ_RINGBUF))
|
|
|
esplink_poll();
|
|
|
|
|
|
- for (unsigned int i = 4; i < 8; i++) {
|
|
|
+ if (status & (0x100 << EL_UIRQ_OTA))
|
|
|
+ fpga_ota_update();
|
|
|
+
|
|
|
+ for (unsigned int i = 5; i < 8; i++) {
|
|
|
if (status & (0x100 << i)) {
|
|
|
printf("[FPGA] Invalid interrupt %u received\n", i);
|
|
|
status = fpga_io_status(FPGA_CMD_ACK(i));
|