/* * This file is part of the libsigrok project. * * Copyright (C) 2013 Bert Vermeulen * Copyright (C) 2012 Joel Holdsworth * * 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 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . */ #include #include #include #include #include #include #include "protocol.h" #define FW_BUFSIZE 4096 int dslogic_fpga_firmware_upload(struct libusb_device_handle *hdl, const char *filename) { FILE *fw; struct stat st; int chunksize, result, ret; unsigned char *buf; int sum, transferred; sr_info("Uploading FPGA firmware at %s.", filename); if (stat(filename, &st) < 0) { sr_err("Unable to upload FPGA firmware: %s", strerror(errno)); return SR_ERR; } /* Tell the device firmware is coming. */ if ((ret = libusb_control_transfer(hdl, LIBUSB_REQUEST_TYPE_VENDOR | LIBUSB_ENDPOINT_OUT, CMD_DSLOGIC_CONFIG, 0x0000, 0x0000, NULL, 0, 3000)) < 0) { sr_err("Failed to upload FPGA firmware: %s.", libusb_error_name(ret)); return SR_ERR; } buf = g_malloc(FW_BUFSIZE); if ((fw = g_fopen(filename, "rb")) == NULL) { sr_err("Unable to open %s for reading: %s.", filename, strerror(errno)); return SR_ERR; } /* Give the FX2 time to get ready for FPGA firmware upload. */ g_usleep(10 * 1000); sum = 0; result = SR_OK; while (1) { if ((chunksize = fread(buf, 1, FW_BUFSIZE, fw)) == 0) break; if ((ret = libusb_bulk_transfer(hdl, 2 | LIBUSB_ENDPOINT_OUT, buf, chunksize, &transferred, 1000)) < 0) { sr_err("Unable to configure FPGA firmware: %s.", libusb_error_name(ret)); result = SR_ERR; break; } sum += transferred; sr_info("Uploaded %d/%d bytes.", sum, st.st_size); if (transferred != chunksize) { sr_err("Short transfer while uploading FPGA firmware."); result = SR_ERR; break; } } fclose(fw); if (result == SR_OK) sr_info("FPGA firmware upload done."); return result; }