summaryrefslogtreecommitdiff
path: root/rbutil/jztool/src/usb.c
diff options
context:
space:
mode:
authorAidan MacDonald <amachronic@protonmail.com>2021-07-17 19:35:09 +0100
committerAidan MacDonald <amachronic@protonmail.com>2021-07-20 14:56:58 +0000
commit740a50687f67f3684e4b5698f8f30e3adebb8f6e (patch)
treecc2afcc989f0ca89e849338ad136e4042acd6bc1 /rbutil/jztool/src/usb.c
parent6f042e91dd8730bf72b423248aa2c520708f03c5 (diff)
downloadrockbox-740a50687f67f3684e4b5698f8f30e3adebb8f6e.tar.gz
rockbox-740a50687f67f3684e4b5698f8f30e3adebb8f6e.zip
jztool: add support for Shanling Q1 and Eros Qbootloader_shanlingq1_v1
Change-Id: I8e93162d1a9d82e9d132219f2803b1856d24ae6c
Diffstat (limited to 'rbutil/jztool/src/usb.c')
-rw-r--r--rbutil/jztool/src/usb.c40
1 files changed, 33 insertions, 7 deletions
diff --git a/rbutil/jztool/src/usb.c b/rbutil/jztool/src/usb.c
index c101f2be77..cfc3ba60cb 100644
--- a/rbutil/jztool/src/usb.c
+++ b/rbutil/jztool/src/usb.c
@@ -22,6 +22,7 @@
22#include "jztool_private.h" 22#include "jztool_private.h"
23#include <stdlib.h> 23#include <stdlib.h>
24#include <stdbool.h> 24#include <stdbool.h>
25#include <string.h>
25 26
26#define VR_GET_CPU_INFO 0 27#define VR_GET_CPU_INFO 0
27#define VR_SET_DATA_ADDRESS 1 28#define VR_SET_DATA_ADDRESS 1
@@ -145,11 +146,12 @@ void jz_usb_close(jz_usbdev* dev)
145 146
146// Does an Ingenic-specific vendor request 147// Does an Ingenic-specific vendor request
147// Written with X1000 in mind but other Ingenic CPUs have the same commands 148// Written with X1000 in mind but other Ingenic CPUs have the same commands
148static int jz_usb_vendor_req(jz_usbdev* dev, int req, uint32_t arg) 149static int jz_usb_vendor_req(jz_usbdev* dev, int req, uint32_t arg,
150 void* buffer, int buflen)
149{ 151{
150 int rc = libusb_control_transfer(dev->handle, 152 int rc = libusb_control_transfer(dev->handle,
151 LIBUSB_ENDPOINT_OUT | LIBUSB_REQUEST_TYPE_VENDOR | LIBUSB_RECIPIENT_DEVICE, 153 LIBUSB_ENDPOINT_OUT | LIBUSB_REQUEST_TYPE_VENDOR | LIBUSB_RECIPIENT_DEVICE,
152 req, arg >> 16, arg & 0xffff, NULL, 0, 1000); 154 req, arg >> 16, arg & 0xffff, buffer, buflen, 1000);
153 155
154 if(rc < 0) { 156 if(rc < 0) {
155 jz_log(dev->jz, JZ_LOG_ERROR, "libusb_control_transfer: %s", libusb_strerror(rc)); 157 jz_log(dev->jz, JZ_LOG_ERROR, "libusb_control_transfer: %s", libusb_strerror(rc));
@@ -200,11 +202,11 @@ static int jz_usb_sendrecv(jz_usbdev* dev, bool write, uint32_t addr,
200 size_t len, void* data) 202 size_t len, void* data)
201{ 203{
202 int rc; 204 int rc;
203 rc = jz_usb_vendor_req(dev, VR_SET_DATA_ADDRESS, addr); 205 rc = jz_usb_vendor_req(dev, VR_SET_DATA_ADDRESS, addr, NULL, 0);
204 if(rc < 0) 206 if(rc < 0)
205 return rc; 207 return rc;
206 208
207 rc = jz_usb_vendor_req(dev, VR_SET_DATA_LENGTH, len); 209 rc = jz_usb_vendor_req(dev, VR_SET_DATA_LENGTH, len, NULL, 0);
208 if(rc < 0) 210 if(rc < 0)
209 return rc; 211 return rc;
210 212
@@ -242,7 +244,7 @@ int jz_usb_recv(jz_usbdev* dev, uint32_t addr, size_t len, void* data)
242 */ 244 */
243int jz_usb_start1(jz_usbdev* dev, uint32_t addr) 245int jz_usb_start1(jz_usbdev* dev, uint32_t addr)
244{ 246{
245 return jz_usb_vendor_req(dev, VR_PROGRAM_START1, addr); 247 return jz_usb_vendor_req(dev, VR_PROGRAM_START1, addr, NULL, 0);
246} 248}
247 249
248/** \brief Execute stage2 program jumping to the specified address 250/** \brief Execute stage2 program jumping to the specified address
@@ -252,7 +254,7 @@ int jz_usb_start1(jz_usbdev* dev, uint32_t addr)
252 */ 254 */
253int jz_usb_start2(jz_usbdev* dev, uint32_t addr) 255int jz_usb_start2(jz_usbdev* dev, uint32_t addr)
254{ 256{
255 return jz_usb_vendor_req(dev, VR_PROGRAM_START2, addr); 257 return jz_usb_vendor_req(dev, VR_PROGRAM_START2, addr, NULL, 0);
256} 258}
257 259
258/** \brief Ask device to flush CPU caches 260/** \brief Ask device to flush CPU caches
@@ -261,5 +263,29 @@ int jz_usb_start2(jz_usbdev* dev, uint32_t addr)
261 */ 263 */
262int jz_usb_flush_caches(jz_usbdev* dev) 264int jz_usb_flush_caches(jz_usbdev* dev)
263{ 265{
264 return jz_usb_vendor_req(dev, VR_FLUSH_CACHES, 0); 266 return jz_usb_vendor_req(dev, VR_FLUSH_CACHES, 0, NULL, 0);
267}
268
269/** \brief Ask device for CPU info string
270 * \param dev USB device
271 * \param buffer Buffer to hold the info string
272 * \param buflen Size of the buffer, in bytes
273 * \return either JZ_SUCCESS on success or a failure code
274 *
275 * The buffer will always be null terminated, but to ensure the info string is
276 * not truncated the buffer needs to be at least `JZ_CPUINFO_BUFLEN` byes long.
277 */
278int jz_usb_get_cpu_info(jz_usbdev* dev, char* buffer, size_t buflen)
279{
280 char tmpbuf[JZ_CPUINFO_BUFLEN];
281 int rc = jz_usb_vendor_req(dev, VR_GET_CPU_INFO, 0, tmpbuf, 8);
282 if(rc != JZ_SUCCESS)
283 return rc;
284
285 if(buflen > 0) {
286 strncpy(buffer, tmpbuf, buflen);
287 buffer[buflen - 1] = 0;
288 }
289
290 return JZ_SUCCESS;
265} 291}