+/*
+ * Configure the FPGA for bitbang mode.
+ * This sequence is documented in section 2. of the ASIX Sigma programming
+ * manual. This sequence is necessary to configure the FPGA in the Sigma
+ * into Bitbang mode, in which it can be programmed with the firmware.
+ */
+static int sigma_fpga_init_bitbang(struct dev_context *devc)
+{
+ uint8_t suicide[] = {
+ 0x84, 0x84, 0x88, 0x84, 0x88, 0x84, 0x88, 0x84,
+ };
+ uint8_t init_array[] = {
+ 0x01, 0x03, 0x03, 0x01, 0x01, 0x01, 0x01, 0x01,
+ 0x01, 0x01,
+ };
+ int i, ret, timeout = 10000;
+ uint8_t data;
+
+ /* Section 2. part 1), do the FPGA suicide. */
+ sigma_write(suicide, sizeof(suicide), devc);
+ sigma_write(suicide, sizeof(suicide), devc);
+ sigma_write(suicide, sizeof(suicide), devc);
+ sigma_write(suicide, sizeof(suicide), devc);
+
+ /* Section 2. part 2), do pulse on D1. */
+ sigma_write(init_array, sizeof(init_array), devc);
+ ftdi_usb_purge_buffers(&devc->ftdic);
+
+ /* Wait until the FPGA asserts D6/INIT_B. */
+ for (i = 0; i < timeout; i++) {
+ ret = sigma_read(&data, 1, devc);
+ if (ret < 0)
+ return ret;
+ /* Test if pin D6 got asserted. */
+ if (data & (1 << 5))
+ return 0;
+ /* The D6 was not asserted yet, wait a bit. */
+ usleep(10000);
+ }
+
+ return SR_ERR_TIMEOUT;
+}
+
+/*
+ * Configure the FPGA for logic-analyzer mode.
+ */
+static int sigma_fpga_init_la(struct dev_context *devc)
+{
+ /* Initialize the logic analyzer mode. */
+ uint8_t logic_mode_start[] = {
+ REG_ADDR_LOW | (READ_ID & 0xf),
+ REG_ADDR_HIGH | (READ_ID >> 8),
+ REG_READ_ADDR, /* Read ID register. */
+
+ REG_ADDR_LOW | (WRITE_TEST & 0xf),
+ REG_DATA_LOW | 0x5,
+ REG_DATA_HIGH_WRITE | 0x5,
+ REG_READ_ADDR, /* Read scratch register. */
+
+ REG_DATA_LOW | 0xa,
+ REG_DATA_HIGH_WRITE | 0xa,
+ REG_READ_ADDR, /* Read scratch register. */
+
+ REG_ADDR_LOW | (WRITE_MODE & 0xf),
+ REG_DATA_LOW | 0x0,
+ REG_DATA_HIGH_WRITE | 0x8,
+ };
+
+ uint8_t result[3];
+ int ret;
+
+ /* Initialize the logic analyzer mode. */
+ sigma_write(logic_mode_start, sizeof(logic_mode_start), devc);
+
+ /* Expect a 3 byte reply since we issued three READ requests. */
+ ret = sigma_read(result, 3, devc);
+ if (ret != 3)
+ goto err;
+
+ if (result[0] != 0xa6 || result[1] != 0x55 || result[2] != 0xaa)
+ goto err;
+
+ return SR_OK;
+err:
+ sr_err("Configuration failed. Invalid reply received.");
+ return SR_ERR;
+}