summaryrefslogtreecommitdiff
path: root/utils/hwstub/stub/main.c
diff options
context:
space:
mode:
Diffstat (limited to 'utils/hwstub/stub/main.c')
-rw-r--r--utils/hwstub/stub/main.c241
1 files changed, 64 insertions, 177 deletions
diff --git a/utils/hwstub/stub/main.c b/utils/hwstub/stub/main.c
index 0923bf85ce..37590e88f8 100644
--- a/utils/hwstub/stub/main.c
+++ b/utils/hwstub/stub/main.c
@@ -51,16 +51,16 @@ static struct usb_device_descriptor __attribute__((aligned(2)))
51 .bLength = sizeof(struct usb_device_descriptor), 51 .bLength = sizeof(struct usb_device_descriptor),
52 .bDescriptorType = USB_DT_DEVICE, 52 .bDescriptorType = USB_DT_DEVICE,
53 .bcdUSB = 0x0200, 53 .bcdUSB = 0x0200,
54 .bDeviceClass = USB_CLASS_PER_INTERFACE, 54 .bDeviceClass = HWSTUB_CLASS,
55 .bDeviceSubClass = 0, 55 .bDeviceSubClass = HWSTUB_SUBCLASS,
56 .bDeviceProtocol = 0, 56 .bDeviceProtocol = HWSTUB_PROTOCOL,
57 .bMaxPacketSize0 = 64, 57 .bMaxPacketSize0 = 64,
58 .idVendor = HWSTUB_USB_VID, 58 .idVendor = HWSTUB_USB_VID,
59 .idProduct = HWSTUB_USB_PID, 59 .idProduct = HWSTUB_USB_PID,
60 .bcdDevice = HWSTUB_VERSION_MAJOR << 8 | HWSTUB_VERSION_MINOR, 60 .bcdDevice = HWSTUB_VERSION_MAJOR << 8 | HWSTUB_VERSION_MINOR,
61 .iManufacturer = 1, 61 .iManufacturer = 1,
62 .iProduct = 2, 62 .iProduct = 2,
63 .iSerialNumber = 3, 63 .iSerialNumber = 0,
64 .bNumConfigurations = 1 64 .bNumConfigurations = 1
65}; 65};
66 66
@@ -72,40 +72,13 @@ static struct usb_config_descriptor __attribute__((aligned(2)))
72 .bLength = sizeof(struct usb_config_descriptor), 72 .bLength = sizeof(struct usb_config_descriptor),
73 .bDescriptorType = USB_DT_CONFIG, 73 .bDescriptorType = USB_DT_CONFIG,
74 .wTotalLength = 0, /* will be filled in later */ 74 .wTotalLength = 0, /* will be filled in later */
75 .bNumInterfaces = 1, 75 .bNumInterfaces = 0,
76 .bConfigurationValue = 1, 76 .bConfigurationValue = 1,
77 .iConfiguration = 0, 77 .iConfiguration = 0,
78 .bmAttributes = USB_CONFIG_ATT_ONE | USB_CONFIG_ATT_SELFPOWER, 78 .bmAttributes = USB_CONFIG_ATT_ONE | USB_CONFIG_ATT_SELFPOWER,
79 .bMaxPower = (USB_MAX_CURRENT + 1) / 2, /* In 2mA units */ 79 .bMaxPower = (USB_MAX_CURRENT + 1) / 2, /* In 2mA units */
80}; 80};
81 81
82/* main interface */
83static struct usb_interface_descriptor __attribute__((aligned(2)))
84 interface_descriptor =
85{
86 .bLength = sizeof(struct usb_interface_descriptor),
87 .bDescriptorType = USB_DT_INTERFACE,
88 .bInterfaceNumber = 0,
89 .bAlternateSetting = 0,
90 .bNumEndpoints = 3,
91 .bInterfaceClass = HWSTUB_CLASS,
92 .bInterfaceSubClass = HWSTUB_SUBCLASS,
93 .bInterfaceProtocol = HWSTUB_PROTOCOL,
94 .iInterface = 4
95};
96
97
98static struct usb_endpoint_descriptor __attribute__((aligned(2)))
99 endpoint_descriptor =
100{
101 .bLength = sizeof(struct usb_endpoint_descriptor),
102 .bDescriptorType = USB_DT_ENDPOINT,
103 .bEndpointAddress = 0,
104 .bmAttributes = USB_ENDPOINT_XFER_BULK,
105 .wMaxPacketSize = 0,
106 .bInterval = 0
107};
108
109static const struct usb_string_descriptor __attribute__((aligned(2))) 82static const struct usb_string_descriptor __attribute__((aligned(2)))
110 usb_string_iManufacturer = 83 usb_string_iManufacturer =
111{ 84{
@@ -117,42 +90,38 @@ static const struct usb_string_descriptor __attribute__((aligned(2)))
117static const struct usb_string_descriptor __attribute__((aligned(2))) 90static const struct usb_string_descriptor __attribute__((aligned(2)))
118 usb_string_iProduct = 91 usb_string_iProduct =
119{ 92{
120 52, 93 44,
121 USB_DT_STRING, 94 USB_DT_STRING,
122 {'R', 'o', 'c', 'k', 'b', 'o', 'x', ' ', 95 {'R', 'o', 'c', 'k', 'b', 'o', 'x', ' ',
123 'h', 'a', 'r', 'd', 'w', 'a', 'r', 'e', ' ', 96 'h', 'a', 'r', 'd', 'w', 'a', 'r', 'e', ' ',
124 'e', 'm', 'u', 'l', 'a', 't', 'e', 'r'} 97 's', 't', 'u', 'b'}
125}; 98};
126 99
127static struct usb_string_descriptor __attribute__((aligned(2))) 100/* this is stringid #0: languages supported */
128 usb_string_iSerial = 101static const struct usb_string_descriptor __attribute__((aligned(2)))
102 lang_descriptor =
129{ 103{
130 84, 104 4,
131 USB_DT_STRING, 105 USB_DT_STRING,
132 {'0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', 106 {0x0409} /* LANGID US English */
133 '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0',
134 '0', '0', '0', '0', '0', '0', '0', '0', '0', '0', '0',
135 '0', '0', '0', '0', '0', '0', '0', '0'}
136}; 107};
137 108
138static struct usb_string_descriptor __attribute__((aligned(2))) 109static struct hwstub_version_desc_t __attribute__((aligned(2)))
139 usb_string_iInterface = 110 version_descriptor =
140{ 111{
141 28, 112 sizeof(struct hwstub_version_desc_t),
142 USB_DT_STRING, 113 HWSTUB_DT_VERSION,
143 {'A', 'c', 'i', 'd', ' ', 114 HWSTUB_VERSION_MAJOR,
144 '0' + (HWSTUB_VERSION_MAJOR >> 4), '0' + (HWSTUB_VERSION_MAJOR & 0xf), '.', 115 HWSTUB_VERSION_MINOR,
145 '0' + (HWSTUB_VERSION_MINOR >> 4), '0' + (HWSTUB_VERSION_MINOR & 0xf), '.', 116 HWSTUB_VERSION_REV
146 '0' + (HWSTUB_VERSION_REV >> 4), '0' + (HWSTUB_VERSION_REV & 0xf) }
147}; 117};
148 118
149/* this is stringid #0: languages supported */ 119static struct hwstub_layout_desc_t __attribute__((aligned(2)))
150static const struct usb_string_descriptor __attribute__((aligned(2))) 120 layout_descriptor =
151 lang_descriptor =
152{ 121{
153 4, 122 sizeof(struct hwstub_layout_desc_t),
154 USB_DT_STRING, 123 HWSTUB_DT_LAYOUT,
155 {0x0409} /* LANGID US English */ 124 0, 0, 0, 0, 0, 0
156}; 125};
157 126
158#define USB_NUM_STRINGS 5 127#define USB_NUM_STRINGS 5
@@ -162,26 +131,25 @@ static const struct usb_string_descriptor* const usb_strings[USB_NUM_STRINGS] =
162 &lang_descriptor, 131 &lang_descriptor,
163 &usb_string_iManufacturer, 132 &usb_string_iManufacturer,
164 &usb_string_iProduct, 133 &usb_string_iProduct,
165 &usb_string_iSerial,
166 &usb_string_iInterface
167}; 134};
168 135
169uint8_t *usb_buffer = oc_bufferstart; 136uint8_t *usb_buffer = oc_bufferstart;
170uint32_t usb_buffer_size = 0; 137uint32_t usb_buffer_size = 0;
171 138
172#define EP_BULK 1 139static void fill_layout_info(void)
173#define EP_INT 2
174
175static void set_config(void)
176{ 140{
177 usb_drv_configure_endpoint(EP_BULK, USB_ENDPOINT_XFER_BULK); 141 layout_descriptor.dCodeStart = (uint32_t)oc_codestart;
178 usb_drv_configure_endpoint(EP_INT, USB_ENDPOINT_XFER_INT); 142 layout_descriptor.dCodeSize = oc_codesize;
143 layout_descriptor.dStackStart = (uint32_t)oc_stackstart;
144 layout_descriptor.dStackSize = oc_stacksize;
145 layout_descriptor.dBufferStart = (uint32_t)oc_bufferstart;
146 layout_descriptor.dBufferSize = oc_buffersize;
179} 147}
180 148
181static void handle_std_dev_desc(struct usb_ctrlrequest *req) 149static void handle_std_dev_desc(struct usb_ctrlrequest *req)
182{ 150{
183 int size; 151 int size;
184 const void* ptr = NULL; 152 void* ptr = NULL;
185 unsigned index = req->wValue & 0xff; 153 unsigned index = req->wValue & 0xff;
186 154
187 switch(req->wValue >> 8) 155 switch(req->wValue >> 8)
@@ -208,32 +176,22 @@ static void handle_std_dev_desc(struct usb_ctrlrequest *req)
208 } 176 }
209 size = sizeof(struct usb_config_descriptor); 177 size = sizeof(struct usb_config_descriptor);
210 178
211 /* interface */ 179 /* hwstub version */
212 memcpy(usb_buffer + size, (void *)&interface_descriptor, 180 memcpy(usb_buffer + size, (void *)&version_descriptor,
213 sizeof(interface_descriptor)); 181 sizeof(version_descriptor));
214 size += sizeof(interface_descriptor); 182 size += sizeof(version_descriptor);
215 /* endpoint 1: bulk out */ 183 /* hwstub layout */
216 endpoint_descriptor.bEndpointAddress = EP_BULK | USB_DIR_OUT; 184 fill_layout_info();
217 endpoint_descriptor.bmAttributes = USB_ENDPOINT_XFER_BULK; 185 memcpy(usb_buffer + size, (void *)&layout_descriptor,
218 endpoint_descriptor.wMaxPacketSize = 512; 186 sizeof(layout_descriptor));
219 memcpy(usb_buffer + size, (void *)&endpoint_descriptor, 187 size += sizeof(layout_descriptor);
220 sizeof(endpoint_descriptor)); 188 /* hwstub target */
221 size += sizeof(endpoint_descriptor); 189 fill_layout_info();
222 /* endpoint 2: bulk in */ 190 memcpy(usb_buffer + size, (void *)&target_descriptor,
223 endpoint_descriptor.bEndpointAddress = EP_BULK | USB_DIR_IN; 191 sizeof(target_descriptor));
224 endpoint_descriptor.bmAttributes = USB_ENDPOINT_XFER_BULK; 192 size += sizeof(target_descriptor);
225 endpoint_descriptor.wMaxPacketSize = 512; 193 /* target specific descriptors */
226 memcpy(usb_buffer + size, (void *)&endpoint_descriptor, 194 target_get_config_desc(usb_buffer + size, &size);
227 sizeof(endpoint_descriptor));
228 size += sizeof(endpoint_descriptor);
229 /* endpoint 3: int in */
230 endpoint_descriptor.bEndpointAddress = EP_INT | USB_DIR_IN;
231 endpoint_descriptor.bmAttributes = USB_ENDPOINT_XFER_INT;
232 endpoint_descriptor.wMaxPacketSize = 1024;
233 memcpy(usb_buffer + size, (void *)&endpoint_descriptor,
234 sizeof(endpoint_descriptor));
235 size += sizeof(endpoint_descriptor);
236
237 /* fix config descriptor */ 195 /* fix config descriptor */
238 config_descriptor.bNumInterfaces = 1; 196 config_descriptor.bNumInterfaces = 1;
239 config_descriptor.wTotalLength = size; 197 config_descriptor.wTotalLength = size;
@@ -246,12 +204,27 @@ static void handle_std_dev_desc(struct usb_ctrlrequest *req)
246 if(index < USB_NUM_STRINGS) 204 if(index < USB_NUM_STRINGS)
247 { 205 {
248 size = usb_strings[index]->bLength; 206 size = usb_strings[index]->bLength;
249 ptr = usb_strings[index]; 207 ptr = (void *)usb_strings[index];
250 } 208 }
251 else 209 else
252 usb_drv_stall(EP_CONTROL, true, true); 210 usb_drv_stall(EP_CONTROL, true, true);
253 break; 211 break;
212 case HWSTUB_DT_VERSION:
213 ptr = &version_descriptor;
214 size = sizeof(version_descriptor);
215 break;
216 case HWSTUB_DT_LAYOUT:
217 ptr = &layout_descriptor;
218 size = sizeof(layout_descriptor);
219 break;
220 case HWSTUB_DT_TARGET:
221 ptr = &target_descriptor;
222 size = sizeof(target_descriptor);
223 break;
254 default: 224 default:
225 target_get_desc(req->wValue >> 8, &ptr);
226 if(ptr != 0)
227 size = ((struct usb_descriptor_header *)ptr)->bLength;
255 break; 228 break;
256 } 229 }
257 230
@@ -280,7 +253,6 @@ static void handle_std_dev_req(struct usb_ctrlrequest *req)
280 break; 253 break;
281 case USB_REQ_SET_CONFIGURATION: 254 case USB_REQ_SET_CONFIGURATION:
282 usb_drv_send(EP_CONTROL, NULL, 0); 255 usb_drv_send(EP_CONTROL, NULL, 0);
283 set_config();
284 break; 256 break;
285 case USB_REQ_GET_DESCRIPTOR: 257 case USB_REQ_GET_DESCRIPTOR:
286 handle_std_dev_desc(req); 258 handle_std_dev_desc(req);
@@ -311,67 +283,6 @@ static void handle_std_req(struct usb_ctrlrequest *req)
311 } 283 }
312} 284}
313 285
314struct usb_resp_info_version_t g_version =
315{
316 .major = HWSTUB_VERSION_MAJOR,
317 .minor = HWSTUB_VERSION_MINOR,
318 .revision = HWSTUB_VERSION_REV
319};
320
321struct usb_resp_info_layout_t g_layout;
322
323struct usb_resp_info_features_t g_features =
324{
325 .feature_mask = HWSTUB_FEATURE_LOG | HWSTUB_FEATURE_MEM |
326 HWSTUB_FEATURE_CALL | HWSTUB_FEATURE_JUMP
327};
328
329static void fill_layout_info(void)
330{
331 g_layout.oc_code_start = (uint32_t)oc_codestart;
332 g_layout.oc_code_size = oc_codesize;
333 g_layout.oc_stack_start = (uint32_t)oc_stackstart;
334 g_layout.oc_stack_size = oc_stacksize;
335 g_layout.oc_buffer_start = (uint32_t)oc_bufferstart;
336 g_layout.oc_buffer_size = oc_buffersize;
337}
338
339static void handle_get_info(struct usb_ctrlrequest *req)
340{
341 void *ptr = NULL;
342 int size = 0;
343 switch(req->wIndex)
344 {
345 case HWSTUB_INFO_VERSION:
346 ptr = &g_version;
347 size = sizeof(g_version);
348 break;
349 case HWSTUB_INFO_LAYOUT:
350 fill_layout_info();
351 ptr = &g_layout;
352 size = sizeof(g_layout);
353 break;
354 case HWSTUB_INFO_FEATURES:
355 ptr = &g_features;
356 size = sizeof(g_features);
357 break;
358 default:
359 size = target_get_info(req->wIndex, &ptr);
360 if(size < 0)
361 usb_drv_stall(EP_CONTROL, true, true);
362 }
363
364 if(ptr)
365 {
366 int length = MIN(size, req->wLength);
367
368 if(ptr != usb_buffer)
369 memcpy(usb_buffer, ptr, length);
370 usb_drv_send(EP_CONTROL, usb_buffer, length);
371 usb_drv_recv(EP_CONTROL, NULL, 0);
372 }
373}
374
375static void handle_get_log(struct usb_ctrlrequest *req) 286static void handle_get_log(struct usb_ctrlrequest *req)
376{ 287{
377 enable_logf(false); 288 enable_logf(false);
@@ -421,28 +332,10 @@ static void handle_call_jump(struct usb_ctrlrequest *req)
421 } 332 }
422} 333}
423 334
424static void handle_atexit(struct usb_ctrlrequest *req)
425{
426 if(target_atexit(req->wIndex) < 0)
427 usb_drv_stall(EP_CONTROL, true, true);
428 else
429 usb_drv_send(EP_CONTROL, NULL, 0);
430}
431
432static void handle_exit(struct usb_ctrlrequest *req)
433{
434 (void)req;
435 usb_drv_send(EP_CONTROL, NULL, 0);
436 g_exit = true;
437}
438
439static void handle_class_dev_req(struct usb_ctrlrequest *req) 335static void handle_class_dev_req(struct usb_ctrlrequest *req)
440{ 336{
441 switch(req->bRequest) 337 switch(req->bRequest)
442 { 338 {
443 case HWSTUB_GET_INFO:
444 handle_get_info(req);
445 break;
446 case HWSTUB_GET_LOG: 339 case HWSTUB_GET_LOG:
447 handle_get_log(req); 340 handle_get_log(req);
448 break; 341 break;
@@ -453,11 +346,6 @@ static void handle_class_dev_req(struct usb_ctrlrequest *req)
453 case HWSTUB_JUMP: 346 case HWSTUB_JUMP:
454 handle_call_jump(req); 347 handle_call_jump(req);
455 break; 348 break;
456 case HWSTUB_ATEXIT:
457 handle_atexit(req);
458 break;
459 case HWSTUB_EXIT:
460 handle_exit(req);
461 break; 349 break;
462 default: 350 default:
463 usb_drv_stall(EP_CONTROL, true, true); 351 usb_drv_stall(EP_CONTROL, true, true);
@@ -510,5 +398,4 @@ void main(uint32_t arg)
510 } 398 }
511 } 399 }
512 usb_drv_exit(); 400 usb_drv_exit();
513 target_exit();
514} 401}