Changeset ec4538d in mainline for uspace/drv/uhci-hcd
- Timestamp:
- 2011-03-07T19:08:13Z (15 years ago)
- Branches:
- lfn, master, serial, ticket/834-toolchain-update, topic/fix-logger-deadlock, topic/msim-upgrade, topic/simplify-dev-export
- Children:
- 1d115c8, a8e98498
- Parents:
- f16a76b (diff), 18e9eeb (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the(diff)links above to see all the changes relative to each parent. - Location:
- uspace/drv/uhci-hcd
- Files:
-
- 12 edited
-
batch.c (modified) (21 diffs)
-
iface.c (modified) (11 diffs)
-
main.c (modified) (5 diffs)
-
pci.c (modified) (5 diffs)
-
root_hub.c (modified) (5 diffs)
-
transfer_list.c (modified) (7 diffs)
-
transfer_list.h (modified) (1 diff)
-
uhci.c (modified) (15 diffs)
-
uhci.h (modified) (1 diff)
-
uhci_struct/queue_head.h (modified) (2 diffs)
-
uhci_struct/transfer_descriptor.c (modified) (2 diffs)
-
utils/device_keeper.c (modified) (14 diffs)
Legend:
- Unmodified
- Added
- Removed
-
uspace/drv/uhci-hcd/batch.c
rf16a76b rec4538d 57 57 58 58 59 /** Allocates memory and initializes internal data structures. 60 * 61 * @param[in] fun DDF function to pass to callback. 62 * @param[in] target Device and endpoint target of the transaction. 63 * @param[in] transfer_type Interrupt, Control or Bulk. 64 * @param[in] max_packet_size maximum allowed size of data packets. 65 * @param[in] speed Speed of the transaction. 66 * @param[in] buffer Data source/destination. 67 * @param[in] size Size of the buffer. 68 * @param[in] setup_buffer Setup data source (if not NULL) 69 * @param[in] setup_size Size of setup_buffer (should be always 8) 70 * @param[in] func_in function to call on inbound transaction completion 71 * @param[in] func_out function to call on outbound transaction completion 72 * @param[in] arg additional parameter to func_in or func_out 73 * @param[in] manager Pointer to toggle management structure. 74 * @return False, if there is an active TD, true otherwise. 75 */ 59 76 batch_t * batch_get(ddf_fun_t *fun, usb_target_t target, 60 77 usb_transfer_type_t transfer_type, size_t max_packet_size, … … 69 86 assert(func_in != NULL || func_out != NULL); 70 87 88 #define CHECK_NULL_DISPOSE_RETURN(ptr, message...) \ 89 if (ptr == NULL) { \ 90 usb_log_error(message); \ 91 if (instance) { \ 92 batch_dispose(instance); \ 93 } \ 94 return NULL; \ 95 } else (void)0 96 71 97 batch_t *instance = malloc(sizeof(batch_t)); 72 if (instance == NULL) { 73 usb_log_error("Failed to allocate batch instance.\n"); 74 return NULL; 75 } 76 77 instance->qh = queue_head_get(); 78 if (instance->qh == NULL) { 79 usb_log_error("Failed to allocate queue head.\n"); 80 free(instance); 81 return NULL; 82 } 98 CHECK_NULL_DISPOSE_RETURN(instance, 99 "Failed to allocate batch instance.\n"); 100 bzero(instance, sizeof(batch_t)); 101 102 instance->qh = malloc32(sizeof(queue_head_t)); 103 CHECK_NULL_DISPOSE_RETURN(instance->qh, 104 "Failed to allocate batch queue head.\n"); 105 queue_head_init(instance->qh); 83 106 84 107 instance->packets = (size + max_packet_size - 1) / max_packet_size; … … 88 111 89 112 instance->tds = malloc32(sizeof(td_t) * instance->packets); 90 if (instance->tds == NULL) { 91 usb_log_error("Failed to allocate transfer descriptors.\n"); 92 queue_head_dispose(instance->qh); 93 free(instance); 94 return NULL; 95 } 113 CHECK_NULL_DISPOSE_RETURN( 114 instance->tds, "Failed to allocate transfer descriptors.\n"); 96 115 bzero(instance->tds, sizeof(td_t) * instance->packets); 97 116 98 const size_t transport_size = max_packet_size * instance->packets; 99 100 instance->transport_buffer = 101 (size > 0) ? malloc32(transport_size) : NULL; 102 103 if ((size > 0) && (instance->transport_buffer == NULL)) { 104 usb_log_error("Failed to allocate device accessible buffer.\n"); 105 queue_head_dispose(instance->qh); 106 free32(instance->tds); 107 free(instance); 108 return NULL; 109 } 110 111 instance->setup_buffer = setup_buffer ? malloc32(setup_size) : NULL; 112 if ((setup_size > 0) && (instance->setup_buffer == NULL)) { 113 usb_log_error("Failed to allocate device accessible setup buffer.\n"); 114 queue_head_dispose(instance->qh); 115 free32(instance->tds); 116 free32(instance->transport_buffer); 117 free(instance); 118 return NULL; 119 } 120 if (instance->setup_buffer) { 117 // const size_t transport_size = max_packet_size * instance->packets; 118 119 if (size > 0) { 120 instance->transport_buffer = malloc32(size); 121 CHECK_NULL_DISPOSE_RETURN(instance->transport_buffer, 122 "Failed to allocate device accessible buffer.\n"); 123 } 124 125 if (setup_size > 0) { 126 instance->setup_buffer = malloc32(setup_size); 127 CHECK_NULL_DISPOSE_RETURN(instance->setup_buffer, 128 "Failed to allocate device accessible setup buffer.\n"); 121 129 memcpy(instance->setup_buffer, setup_buffer, setup_size); 122 130 } 123 131 132 133 link_initialize(&instance->link); 134 124 135 instance->max_packet_size = max_packet_size; 125 126 link_initialize(&instance->link);127 128 136 instance->target = target; 129 137 instance->transfer_type = transfer_type; 130 131 if (func_out)132 instance->callback_out = func_out;133 if (func_in)134 instance->callback_in = func_in;135 136 138 instance->buffer = buffer; 137 139 instance->buffer_size = size; … … 142 144 instance->manager = manager; 143 145 144 queue_head_element_td(instance->qh, addr_to_phys(instance->tds)); 146 if (func_out) 147 instance->callback_out = func_out; 148 if (func_in) 149 instance->callback_in = func_in; 150 151 queue_head_set_element_td(instance->qh, addr_to_phys(instance->tds)); 152 145 153 usb_log_debug("Batch(%p) %d:%d memory structures ready.\n", 146 154 instance, target.address, target.endpoint); … … 148 156 } 149 157 /*----------------------------------------------------------------------------*/ 158 /** Checks batch TDs for activity. 159 * 160 * @param[in] instance Batch structure to use. 161 * @return False, if there is an active TD, true otherwise. 162 */ 150 163 bool batch_is_complete(batch_t *instance) 151 164 { … … 165 178 instance, i, instance->tds[i].status); 166 179 167 device_keeper_set_toggle(instance->manager, instance->target,168 td_toggle(&instance->tds[i]));180 device_keeper_set_toggle(instance->manager, 181 instance->target, td_toggle(&instance->tds[i])); 169 182 if (i > 0) 170 183 goto substract_ret; … … 181 194 } 182 195 /*----------------------------------------------------------------------------*/ 196 /** Prepares control write transaction. 197 * 198 * @param[in] instance Batch structure to use. 199 */ 183 200 void batch_control_write(batch_t *instance) 184 201 { 185 202 assert(instance); 186 203 /* we are data out, we are supposed to provide data */ 187 memcpy(instance->transport_buffer, instance->buffer, instance->buffer_size); 204 memcpy(instance->transport_buffer, instance->buffer, 205 instance->buffer_size); 188 206 batch_control(instance, USB_PID_OUT, USB_PID_IN); 189 207 instance->next_step = batch_call_out_and_dispose; … … 192 210 } 193 211 /*----------------------------------------------------------------------------*/ 212 /** Prepares control read transaction. 213 * 214 * @param[in] instance Batch structure to use. 215 */ 194 216 void batch_control_read(batch_t *instance) 195 217 { … … 201 223 } 202 224 /*----------------------------------------------------------------------------*/ 225 /** Prepares interrupt in transaction. 226 * 227 * @param[in] instance Batch structure to use. 228 */ 203 229 void batch_interrupt_in(batch_t *instance) 204 230 { … … 210 236 } 211 237 /*----------------------------------------------------------------------------*/ 238 /** Prepares interrupt out transaction. 239 * 240 * @param[in] instance Batch structure to use. 241 */ 212 242 void batch_interrupt_out(batch_t *instance) 213 243 { 214 244 assert(instance); 245 /* we are data out, we are supposed to provide data */ 215 246 memcpy(instance->transport_buffer, instance->buffer, instance->buffer_size); 216 247 batch_data(instance, USB_PID_OUT); … … 220 251 } 221 252 /*----------------------------------------------------------------------------*/ 253 /** Prepares bulk in transaction. 254 * 255 * @param[in] instance Batch structure to use. 256 */ 222 257 void batch_bulk_in(batch_t *instance) 223 258 { … … 229 264 } 230 265 /*----------------------------------------------------------------------------*/ 266 /** Prepares bulk out transaction. 267 * 268 * @param[in] instance Batch structure to use. 269 */ 231 270 void batch_bulk_out(batch_t *instance) 232 271 { … … 239 278 } 240 279 /*----------------------------------------------------------------------------*/ 280 /** Prepares generic data transaction 281 * 282 * @param[in] instance Batch structure to use. 283 * @param[in] pid to use for data packets. 284 */ 241 285 void batch_data(batch_t *instance, usb_packet_id pid) 242 286 { 243 287 assert(instance); 244 288 const bool low_speed = instance->speed == USB_SPEED_LOW; 245 int toggle = device_keeper_get_toggle(instance->manager, instance->target); 289 int toggle = 290 device_keeper_get_toggle(instance->manager, instance->target); 246 291 assert(toggle == 0 || toggle == 1); 247 292 … … 253 298 - remain_size; 254 299 255 256 300 const size_t packet_size = 257 301 (instance->max_packet_size > remain_size) ? 258 302 remain_size : instance->max_packet_size; 259 303 260 td_init(&instance->tds[packet], 261 DEFAULT_ERROR_COUNT, packet_size, toggle, false, low_speed, 262 instance->target, pid, data, 263 &instance->tds[packet + 1]); 304 td_t *next_packet = (packet + 1 < instance->packets) 305 ? &instance->tds[packet + 1] : NULL; 306 307 assert(packet < instance->packets); 308 assert(packet_size <= remain_size); 309 310 td_init( 311 &instance->tds[packet], DEFAULT_ERROR_COUNT, packet_size, 312 toggle, false, low_speed, instance->target, pid, data, 313 next_packet); 314 264 315 265 316 toggle = 1 - toggle; 317 remain_size -= packet_size; 266 318 ++packet; 267 assert(packet <= instance->packets);268 assert(packet_size <= remain_size);269 remain_size -= packet_size;270 319 } 271 320 device_keeper_set_toggle(instance->manager, instance->target, toggle); 272 273 instance->tds[packet - 1].status |= TD_STATUS_COMPLETE_INTERRUPT_FLAG; 274 instance->tds[packet - 1].next = 0 | LINK_POINTER_TERMINATE_FLAG; 275 } 276 /*----------------------------------------------------------------------------*/ 321 } 322 /*----------------------------------------------------------------------------*/ 323 /** Prepares generic control transaction 324 * 325 * @param[in] instance Batch structure to use. 326 * @param[in] data_stage to use for data packets. 327 * @param[in] status_stage to use for data packets. 328 */ 277 329 void batch_control(batch_t *instance, 278 330 usb_packet_id data_stage, usb_packet_id status_stage) … … 301 353 remain_size : instance->max_packet_size; 302 354 303 td_init( &instance->tds[packet],304 DEFAULT_ERROR_COUNT, packet_size, toggle, false, low_speed,305 instance->target, data_stage, data,306 &instance->tds[packet + 1]);355 td_init( 356 &instance->tds[packet], DEFAULT_ERROR_COUNT, packet_size, 357 toggle, false, low_speed, instance->target, data_stage, 358 data, &instance->tds[packet + 1]); 307 359 308 360 ++packet; … … 323 375 } 324 376 /*----------------------------------------------------------------------------*/ 377 /** Prepares data, gets error status and calls callback in. 378 * 379 * @param[in] instance Batch structure to use. 380 */ 325 381 void batch_call_in(batch_t *instance) 326 382 { … … 328 384 assert(instance->callback_in); 329 385 330 memcpy(instance->buffer, instance->transport_buffer, instance->buffer_size); 386 /* we are data in, we need data */ 387 memcpy(instance->buffer, instance->transport_buffer, 388 instance->buffer_size); 331 389 332 390 int err = instance->error; … … 335 393 instance->transfered_size); 336 394 337 instance->callback_in(instance->fun, 338 err, instance->transfered_size, 339 instance->arg); 340 } 341 /*----------------------------------------------------------------------------*/ 395 instance->callback_in( 396 instance->fun, err, instance->transfered_size, instance->arg); 397 } 398 /*----------------------------------------------------------------------------*/ 399 /** Gets error status and calls callback out. 400 * 401 * @param[in] instance Batch structure to use. 402 */ 342 403 void batch_call_out(batch_t *instance) 343 404 { … … 352 413 } 353 414 /*----------------------------------------------------------------------------*/ 415 /** Prepares data, gets error status, calls callback in and dispose. 416 * 417 * @param[in] instance Batch structure to use. 418 */ 354 419 void batch_call_in_and_dispose(batch_t *instance) 355 420 { … … 359 424 } 360 425 /*----------------------------------------------------------------------------*/ 426 /** Gets error status, calls callback out and dispose. 427 * 428 * @param[in] instance Batch structure to use. 429 */ 361 430 void batch_call_out_and_dispose(batch_t *instance) 362 431 { … … 366 435 } 367 436 /*----------------------------------------------------------------------------*/ 437 /** Correctly disposes all used data structures. 438 * 439 * @param[in] instance Batch structure to use. 440 */ 368 441 void batch_dispose(batch_t *instance) 369 442 { 370 443 assert(instance); 371 444 usb_log_debug("Batch(%p) disposing.\n", instance); 445 /* free32 is NULL safe */ 372 446 free32(instance->tds); 373 447 free32(instance->qh); -
uspace/drv/uhci-hcd/iface.c
rf16a76b rec4538d 43 43 #include "utils/device_keeper.h" 44 44 45 /** Reserve default address interface function 46 * 47 * @param[in] fun DDF function that was called. 48 * @param[in] speed Speed to associate with the new default address. 49 * @return Error code. 50 */ 45 51 /*----------------------------------------------------------------------------*/ 46 52 static int reserve_default_address(ddf_fun_t *fun, usb_speed_t speed) … … 54 60 } 55 61 /*----------------------------------------------------------------------------*/ 62 /** Release default address interface function 63 * 64 * @param[in] fun DDF function that was called. 65 * @return Error code. 66 */ 56 67 static int release_default_address(ddf_fun_t *fun) 57 68 { … … 64 75 } 65 76 /*----------------------------------------------------------------------------*/ 77 /** Request address interface function 78 * 79 * @param[in] fun DDF function that was called. 80 * @param[in] speed Speed to associate with the new default address. 81 * @param[out] address Place to write a new address. 82 * @return Error code. 83 */ 66 84 static int request_address(ddf_fun_t *fun, usb_speed_t speed, 67 85 usb_address_t *address) … … 80 98 } 81 99 /*----------------------------------------------------------------------------*/ 100 /** Bind address interface function 101 * 102 * @param[in] fun DDF function that was called. 103 * @param[in] address Address of the device 104 * @param[in] handle Devman handle of the device driver. 105 * @return Error code. 106 */ 82 107 static int bind_address( 83 108 ddf_fun_t *fun, usb_address_t address, devman_handle_t handle) … … 91 116 } 92 117 /*----------------------------------------------------------------------------*/ 118 /** Release address interface function 119 * 120 * @param[in] fun DDF function that was called. 121 * @param[in] address USB address to be released. 122 * @return Error code. 123 */ 93 124 static int release_address(ddf_fun_t *fun, usb_address_t address) 94 125 { … … 101 132 } 102 133 /*----------------------------------------------------------------------------*/ 134 /** Interrupt out transaction interface function 135 * 136 * @param[in] fun DDF function that was called. 137 * @param[in] target USB device to write to. 138 * @param[in] max_packet_size maximum size of data packet the device accepts 139 * @param[in] data Source of data. 140 * @param[in] size Size of data source. 141 * @param[in] callback Function to call on transaction completion 142 * @param[in] arg Additional for callback function. 143 * @return Error code. 144 */ 103 145 static int interrupt_out(ddf_fun_t *fun, usb_target_t target, 104 146 size_t max_packet_size, void *data, size_t size, … … 122 164 } 123 165 /*----------------------------------------------------------------------------*/ 166 /** Interrupt in transaction interface function 167 * 168 * @param[in] fun DDF function that was called. 169 * @param[in] target USB device to write to. 170 * @param[in] max_packet_size maximum size of data packet the device accepts 171 * @param[out] data Data destination. 172 * @param[in] size Size of data source. 173 * @param[in] callback Function to call on transaction completion 174 * @param[in] arg Additional for callback function. 175 * @return Error code. 176 */ 124 177 static int interrupt_in(ddf_fun_t *fun, usb_target_t target, 125 178 size_t max_packet_size, void *data, size_t size, … … 142 195 } 143 196 /*----------------------------------------------------------------------------*/ 197 /** Bulk out transaction interface function 198 * 199 * @param[in] fun DDF function that was called. 200 * @param[in] target USB device to write to. 201 * @param[in] max_packet_size maximum size of data packet the device accepts 202 * @param[in] data Source of data. 203 * @param[in] size Size of data source. 204 * @param[in] callback Function to call on transaction completion 205 * @param[in] arg Additional for callback function. 206 * @return Error code. 207 */ 144 208 static int bulk_out(ddf_fun_t *fun, usb_target_t target, 145 209 size_t max_packet_size, void *data, size_t size, … … 163 227 } 164 228 /*----------------------------------------------------------------------------*/ 229 /** Bulk in transaction interface function 230 * 231 * @param[in] fun DDF function that was called. 232 * @param[in] target USB device to write to. 233 * @param[in] max_packet_size maximum size of data packet the device accepts 234 * @param[out] data Data destination. 235 * @param[in] size Size of data source. 236 * @param[in] callback Function to call on transaction completion 237 * @param[in] arg Additional for callback function. 238 * @return Error code. 239 */ 165 240 static int bulk_in(ddf_fun_t *fun, usb_target_t target, 166 241 size_t max_packet_size, void *data, size_t size, … … 183 258 } 184 259 /*----------------------------------------------------------------------------*/ 260 /** Control write transaction interface function 261 * 262 * @param[in] fun DDF function that was called. 263 * @param[in] target USB device to write to. 264 * @param[in] max_packet_size maximum size of data packet the device accepts. 265 * @param[in] setup_data Data to send with SETUP packet. 266 * @param[in] setup_size Size of data to send with SETUP packet (should be 8B). 267 * @param[in] data Source of data. 268 * @param[in] size Size of data source. 269 * @param[in] callback Function to call on transaction completion. 270 * @param[in] arg Additional for callback function. 271 * @return Error code. 272 */ 185 273 static int control_write(ddf_fun_t *fun, usb_target_t target, 186 274 size_t max_packet_size, … … 208 296 } 209 297 /*----------------------------------------------------------------------------*/ 298 /** Control read transaction interface function 299 * 300 * @param[in] fun DDF function that was called. 301 * @param[in] target USB device to write to. 302 * @param[in] max_packet_size maximum size of data packet the device accepts. 303 * @param[in] setup_data Data to send with SETUP packet. 304 * @param[in] setup_size Size of data to send with SETUP packet (should be 8B). 305 * @param[out] data Source of data. 306 * @param[in] size Size of data source. 307 * @param[in] callback Function to call on transaction completion. 308 * @param[in] arg Additional for callback function. 309 * @return Error code. 310 */ 210 311 static int control_read(ddf_fun_t *fun, usb_target_t target, 211 312 size_t max_packet_size, -
uspace/drv/uhci-hcd/main.c
rf16a76b rec4538d 60 60 }; 61 61 /*----------------------------------------------------------------------------*/ 62 /** IRQ handling callback, identifies devic 63 * 64 * @param[in] dev DDF instance of the device to use. 65 * @param[in] iid (Unused). 66 * @param[in] call Pointer to the call that represents interrupt. 67 */ 62 68 static void irq_handler(ddf_dev_t *dev, ipc_callid_t iid, ipc_call_t *call) 63 69 { … … 69 75 } 70 76 /*----------------------------------------------------------------------------*/ 71 static int uhci_add_device(ddf_dev_t *device) 77 /** Initializes a new ddf driver instance of UHCI hcd. 78 * 79 * @param[in] device DDF instance of the device to initialize. 80 * @return Error code. 81 * 82 * Gets and initialies hardware resources, disables any legacy support, 83 * and reports root hub device. 84 */ 85 int uhci_add_device(ddf_dev_t *device) 72 86 { 73 87 assert(device); … … 96 110 ret = pci_disable_legacy(device); 97 111 CHECK_RET_FREE_HC_RETURN(ret, 98 "Failed(%d) disable legacy USB: %s.\n", ret, str_error(ret));112 "Failed(%d) to disable legacy USB: %s.\n", ret, str_error(ret)); 99 113 100 114 #if 0 … … 113 127 114 128 ret = uhci_init(hcd, device, (void*)io_reg_base, io_reg_size); 115 CHECK_RET_FREE_HC_RETURN(ret, "Failed(%d) to init uhci-hcd.\n", 116 ret); 129 CHECK_RET_FREE_HC_RETURN(ret, "Failed(%d) to init uhci-hcd.\n", ret); 117 130 #undef CHECK_RET_FREE_HC_RETURN 118 131 … … 155 168 } 156 169 /*----------------------------------------------------------------------------*/ 170 /** Initializes global driver structures (NONE). 171 * 172 * @param[in] argc Nmber of arguments in argv vector (ignored). 173 * @param[in] argv Cmdline argument vector (ignored). 174 * @return Error code. 175 * 176 * Driver debug level is set here. 177 */ 157 178 int main(int argc, char *argv[]) 158 179 { -
uspace/drv/uhci-hcd/pci.c
rf16a76b rec4538d 65 65 66 66 int rc; 67 68 67 hw_resource_list_t hw_resources; 69 68 rc = hw_res_get_resource_list(parent_phone, &hw_resources); … … 82 81 for (i = 0; i < hw_resources.count; i++) { 83 82 hw_resource_t *res = &hw_resources.resources[i]; 84 switch (res->type) { 85 case INTERRUPT: 86 irq = res->res.interrupt.irq; 87 irq_found = true; 88 usb_log_debug2("Found interrupt: %d.\n", irq); 89 break; 90 case IO_RANGE: 91 io_address = res->res.io_range.address; 92 io_size = res->res.io_range.size; 93 usb_log_debug2("Found io: %llx %zu.\n", 94 res->res.io_range.address, res->res.io_range.size); 95 io_found = true; 96 break; 97 default: 98 break; 83 switch (res->type) 84 { 85 case INTERRUPT: 86 irq = res->res.interrupt.irq; 87 irq_found = true; 88 usb_log_debug2("Found interrupt: %d.\n", irq); 89 break; 90 91 case IO_RANGE: 92 io_address = res->res.io_range.address; 93 io_size = res->res.io_range.size; 94 usb_log_debug2("Found io: %llx %zu.\n", 95 res->res.io_range.address, res->res.io_range.size); 96 io_found = true; 97 98 default: 99 break; 99 100 } 100 101 } 101 102 102 if (!io_found) { 103 rc = ENOENT; 104 goto leave; 105 } 106 107 if (!irq_found) { 103 if (!io_found || !irq_found) { 108 104 rc = ENOENT; 109 105 goto leave; … … 121 117 } 122 118 /*----------------------------------------------------------------------------*/ 119 /** Calls the PCI driver with a request to enable interrupts 120 * 121 * @param[in] device Device asking for interrupts 122 * @return Error code. 123 */ 123 124 int pci_enable_interrupts(ddf_dev_t *device) 124 125 { … … 130 131 } 131 132 /*----------------------------------------------------------------------------*/ 133 /** Calls the PCI driver with a request to clear legacy support register 134 * 135 * @param[in] device Device asking to disable interrupts 136 * @return Error code. 137 */ 132 138 int pci_disable_legacy(ddf_dev_t *device) 133 139 { 134 140 assert(device); 135 int parent_phone = devman_parent_device_connect(device->handle,136 IPC_FLAG_BLOCKING);141 int parent_phone = 142 devman_parent_device_connect(device->handle, IPC_FLAG_BLOCKING); 137 143 if (parent_phone < 0) { 138 144 return parent_phone; … … 144 150 sysarg_t value = 0x8f00; 145 151 146 int rc = async_req_3_0(parent_phone, DEV_IFACE_ID(PCI_DEV_IFACE),152 int rc = async_req_3_0(parent_phone, DEV_IFACE_ID(PCI_DEV_IFACE), 147 153 IPC_M_CONFIG_SPACE_WRITE_16, address, value); 148 154 async_hangup(parent_phone); 149 155 150 return rc;156 return rc; 151 157 } 152 158 /*----------------------------------------------------------------------------*/ -
uspace/drv/uhci-hcd/root_hub.c
rf16a76b rec4538d 45 45 46 46 /*----------------------------------------------------------------------------*/ 47 static int usb_iface_get_hc_handle_rh_impl(ddf_fun_t *root_hub_fun, 48 devman_handle_t *handle) 47 /** Gets handle of the respective hc (parent device). 48 * 49 * @param[in] root_hub_fun Root hub function seeking hc handle. 50 * @param[out] handle Place to write the handle. 51 * @return Error code. 52 */ 53 static int usb_iface_get_hc_handle_rh_impl( 54 ddf_fun_t *root_hub_fun, devman_handle_t *handle) 49 55 { 56 /* TODO: Can't this use parent pointer? */ 50 57 ddf_fun_t *hc_fun = root_hub_fun->driver_data; 51 58 assert(hc_fun != NULL); … … 56 63 } 57 64 /*----------------------------------------------------------------------------*/ 58 static int usb_iface_get_address_rh_impl(ddf_fun_t *fun, devman_handle_t handle, 59 usb_address_t *address) 65 /** Gets USB address of the calling device. 66 * 67 * @param[in] fun Root hub function. 68 * @param[in] handle Handle of the device seeking address. 69 * @param[out] address Place to store found address. 70 * @return Error code. 71 */ 72 static int usb_iface_get_address_rh_impl( 73 ddf_fun_t *fun, devman_handle_t handle, usb_address_t *address) 60 74 { 75 /* TODO: What does this do? Is it neccessary? Can't it use implemented 76 * hc function?*/ 61 77 assert(fun); 62 78 ddf_fun_t *hc_fun = fun->driver_data; … … 65 81 assert(hc); 66 82 67 usb_address_t addr = device_keeper_find(&hc->device_manager, 68 handle); 83 usb_address_t addr = device_keeper_find(&hc->device_manager, handle); 69 84 if (addr < 0) { 70 85 return addr; … … 83 98 }; 84 99 /*----------------------------------------------------------------------------*/ 100 /** Gets root hub hw resources. 101 * 102 * @param[in] fun Root hub function. 103 * @return Pointer to the resource list used by the root hub. 104 */ 85 105 static hw_resource_list_t *get_resource_list(ddf_fun_t *dev) 86 106 { … … 91 111 assert(hc); 92 112 93 / /TODO: fix memory leak113 /* TODO: fix memory leak */ 94 114 hw_resource_list_t *resource_list = malloc(sizeof(hw_resource_list_t)); 95 115 assert(resource_list); -
uspace/drv/uhci-hcd/transfer_list.c
rf16a76b rec4538d 38 38 #include "transfer_list.h" 39 39 40 static void transfer_list_remove_batch( 41 transfer_list_t *instance, batch_t *batch); 42 /*----------------------------------------------------------------------------*/ 43 /** Initializes transfer list structures. 44 * 45 * @param[in] instance Memory place to use. 46 * @param[in] name Name of te new list. 47 * @return Error code 48 * 49 * Allocates memory for internat queue_head_t structure. 50 */ 40 51 int transfer_list_init(transfer_list_t *instance, const char *name) 41 52 { … … 43 54 instance->next = NULL; 44 55 instance->name = name; 45 instance->queue_head = queue_head_get();56 instance->queue_head = malloc32(sizeof(queue_head_t)); 46 57 if (!instance->queue_head) { 47 58 usb_log_error("Failed to allocate queue head.\n"); 48 59 return ENOMEM; 49 60 } 50 instance->queue_head_pa = (uintptr_t)addr_to_phys(instance->queue_head);61 instance->queue_head_pa = addr_to_phys(instance->queue_head); 51 62 52 63 queue_head_init(instance->queue_head); … … 56 67 } 57 68 /*----------------------------------------------------------------------------*/ 69 /** Set the next list in chain. 70 * 71 * @param[in] instance List to lead. 72 * @param[in] next List to append. 73 * @return Error code 74 */ 58 75 void transfer_list_set_next(transfer_list_t *instance, transfer_list_t *next) 59 76 { … … 66 83 } 67 84 /*----------------------------------------------------------------------------*/ 85 /** Submits a new transfer batch to list and queue. 86 * 87 * @param[in] instance List to use. 88 * @param[in] batch Transfer batch to submit. 89 * @return Error code 90 */ 68 91 void transfer_list_add_batch(transfer_list_t *instance, batch_t *batch) 69 92 { 70 93 assert(instance); 71 94 assert(batch); 72 usb_log_debug2("Adding batch(%p) to queue %s.\n", batch, instance->name); 95 usb_log_debug2( 96 "Adding batch(%p) to queue %s.\n", batch, instance->name); 73 97 74 98 uint32_t pa = (uintptr_t)addr_to_phys(batch->qh); … … 97 121 queue_head_append_qh(last->qh, pa); 98 122 list_append(&batch->link, &instance->batch_list); 123 99 124 usb_log_debug("Batch(%p) added to queue %s last, first is %p.\n", 100 batch, instance->name, first );125 batch, instance->name, first); 101 126 fibril_mutex_unlock(&instance->guard); 102 127 } 103 128 /*----------------------------------------------------------------------------*/ 104 static void transfer_list_remove_batch( 105 transfer_list_t *instance, batch_t *batch) 129 /** Removes a transfer batch from list and queue. 130 * 131 * @param[in] instance List to use. 132 * @param[in] batch Transfer batch to remove. 133 * @return Error code 134 */ 135 void transfer_list_remove_batch(transfer_list_t *instance, batch_t *batch) 106 136 { 107 137 assert(instance); … … 109 139 assert(instance->queue_head); 110 140 assert(batch->qh); 111 usb_log_debug2("Removing batch(%p) from queue %s.\n", batch, instance->name); 141 usb_log_debug2( 142 "Removing batch(%p) from queue %s.\n", batch, instance->name); 112 143 113 /* I'm the first one here */114 144 if (batch->link.prev == &instance->batch_list) { 115 usb_log_debug("Batch(%p) removed (FIRST) from queue %s, next element %x.\n", 116 batch, instance->name, batch->qh->next_queue); 145 /* I'm the first one here */ 146 usb_log_debug( 147 "Batch(%p) removed (FIRST) from %s, next element %x.\n", 148 batch, instance->name, batch->qh->next_queue); 117 149 instance->queue_head->element = batch->qh->next_queue; 118 150 } else { 119 usb_log_debug("Batch(%p) removed (NOT FIRST) from queue, next element %x.\n", 120 batch, instance->name, batch->qh->next_queue); 121 batch_t *prev = list_get_instance(batch->link.prev, batch_t, link); 151 usb_log_debug( 152 "Batch(%p) removed (FIRST:NO) from %s, next element %x.\n", 153 batch, instance->name, batch->qh->next_queue); 154 batch_t *prev = 155 list_get_instance(batch->link.prev, batch_t, link); 122 156 prev->qh->next_queue = batch->qh->next_queue; 123 157 } … … 125 159 } 126 160 /*----------------------------------------------------------------------------*/ 161 /** Checks list for finished transfers. 162 * 163 * @param[in] instance List to use. 164 * @return Error code 165 */ 127 166 void transfer_list_remove_finished(transfer_list_t *instance) 128 167 { -
uspace/drv/uhci-hcd/transfer_list.h
rf16a76b rec4538d 58 58 { 59 59 assert(instance); 60 queue_head_dispose(instance->queue_head);60 free32(instance->queue_head); 61 61 } 62 62 void transfer_list_remove_finished(transfer_list_t *instance); -
uspace/drv/uhci-hcd/uhci.c
rf16a76b rec4538d 61 61 }; 62 62 63 static int usb_iface_get_address(ddf_fun_t *fun, devman_handle_t handle, 64 usb_address_t *address) 63 /** Gets USB address of the calling device. 64 * 65 * @param[in] fun UHCI hc function. 66 * @param[in] handle Handle of the device seeking address. 67 * @param[out] address Place to store found address. 68 * @return Error code. 69 */ 70 static int usb_iface_get_address( 71 ddf_fun_t *fun, devman_handle_t handle, usb_address_t *address) 65 72 { 66 73 assert(fun); … … 99 106 100 107 static bool allowed_usb_packet( 101 bool low_speed, usb_transfer_type_t, size_t size); 102 103 108 bool low_speed, usb_transfer_type_t transfer, size_t size); 109 /*----------------------------------------------------------------------------*/ 110 /** Initializes UHCI hcd driver structure 111 * 112 * @param[in] instance Memory place to initialize. 113 * @param[in] dev DDF device. 114 * @param[in] regs Address of I/O control registers. 115 * @param[in] size Size of I/O control registers. 116 * @return Error code. 117 * @note Should be called only once on any structure. 118 */ 104 119 int uhci_init(uhci_t *instance, ddf_dev_t *dev, void *regs, size_t reg_size) 105 120 { … … 156 171 } 157 172 /*----------------------------------------------------------------------------*/ 173 /** Initializes UHCI hcd hw resources. 174 * 175 * @param[in] instance UHCI structure to use. 176 */ 158 177 void uhci_init_hw(uhci_t *instance) 159 178 { 160 179 assert(instance); 161 162 /* reset everything, who knows what touched it before us */ 163 pio_write_16(&instance->registers->usbcmd, UHCI_CMD_GLOBAL_RESET); 180 regs_t *registers = instance->registers; 181 182 /* Reset everything, who knows what touched it before us */ 183 pio_write_16(®isters->usbcmd, UHCI_CMD_GLOBAL_RESET); 164 184 async_usleep(10000); /* 10ms according to USB spec */ 165 pio_write_16(& instance->registers->usbcmd, 0);166 167 /* reset hc, all states and counters */168 pio_write_16(& instance->registers->usbcmd, UHCI_CMD_HCRESET);185 pio_write_16(®isters->usbcmd, 0); 186 187 /* Reset hc, all states and counters */ 188 pio_write_16(®isters->usbcmd, UHCI_CMD_HCRESET); 169 189 do { async_usleep(10); } 170 while ((pio_read_16(& instance->registers->usbcmd) & UHCI_CMD_HCRESET) != 0);171 172 /* set framelist pointer */190 while ((pio_read_16(®isters->usbcmd) & UHCI_CMD_HCRESET) != 0); 191 192 /* Set framelist pointer */ 173 193 const uint32_t pa = addr_to_phys(instance->frame_list); 174 pio_write_32(& instance->registers->flbaseadd, pa);175 176 /* enable all interrupts, but resume interrupt */194 pio_write_32(®isters->flbaseadd, pa); 195 196 /* Enable all interrupts, but resume interrupt */ 177 197 // pio_write_16(&instance->registers->usbintr, 178 198 // UHCI_INTR_CRC | UHCI_INTR_COMPLETE | UHCI_INTR_SHORT_PACKET); 179 199 180 uint16_t status = pio_read_16(&instance->registers->usbcmd); 181 usb_log_warning("Previous command value: %x.\n", status); 200 uint16_t status = pio_read_16(®isters->usbcmd); 201 if (status != 0) 202 usb_log_warning("Previous command value: %x.\n", status); 203 182 204 /* Start the hc with large(64B) packet FSBR */ 183 pio_write_16(& instance->registers->usbcmd,205 pio_write_16(®isters->usbcmd, 184 206 UHCI_CMD_RUN_STOP | UHCI_CMD_MAX_PACKET | UHCI_CMD_CONFIGURE); 185 207 } 186 208 /*----------------------------------------------------------------------------*/ 209 /** Initializes UHCI hcd memory structures. 210 * 211 * @param[in] instance UHCI structure to use. 212 * @return Error code 213 * @note Should be called only once on any structure. 214 */ 187 215 int uhci_init_mem_structures(uhci_t *instance) 188 216 { … … 196 224 } else (void) 0 197 225 198 /* init interrupt code */226 /* Init interrupt code */ 199 227 instance->interrupt_code.cmds = malloc(sizeof(uhci_cmds)); 200 228 int ret = (instance->interrupt_code.cmds == NULL) ? ENOMEM : EOK; 201 CHECK_RET_DEST_CMDS_RETURN(ret, "Failed to allocate interrupt cmds space.\n"); 229 CHECK_RET_DEST_CMDS_RETURN(ret, 230 "Failed to allocate interrupt cmds space.\n"); 202 231 203 232 { 204 233 irq_cmd_t *interrupt_commands = instance->interrupt_code.cmds; 205 234 memcpy(interrupt_commands, uhci_cmds, sizeof(uhci_cmds)); 206 interrupt_commands[0].addr = (void*)&instance->registers->usbsts; 207 interrupt_commands[1].addr = (void*)&instance->registers->usbsts; 235 interrupt_commands[0].addr = 236 (void*)&instance->registers->usbsts; 237 interrupt_commands[1].addr = 238 (void*)&instance->registers->usbsts; 208 239 instance->interrupt_code.cmdcount = 209 240 sizeof(uhci_cmds) / sizeof(irq_cmd_t); 210 241 } 211 242 212 /* init transfer lists */243 /* Init transfer lists */ 213 244 ret = uhci_init_transfer_lists(instance); 214 CHECK_RET_DEST_CMDS_RETURN(ret, "Failed to init ializetransfer lists.\n");245 CHECK_RET_DEST_CMDS_RETURN(ret, "Failed to init transfer lists.\n"); 215 246 usb_log_debug("Initialized transfer lists.\n"); 216 247 217 /* frame list initialization*/248 /* Init USB frame list page*/ 218 249 instance->frame_list = get_page(); 219 250 ret = instance ? EOK : ENOMEM; … … 221 252 usb_log_debug("Initialized frame list.\n"); 222 253 223 /* initializeall frames to point to the first queue head */254 /* Set all frames to point to the first queue head */ 224 255 const uint32_t queue = 225 256 instance->transfers_interrupt.queue_head_pa … … 231 262 } 232 263 233 /* init address keeper(libusb)*/264 /* Init device keeper*/ 234 265 device_keeper_init(&instance->device_manager); 235 266 usb_log_debug("Initialized device manager.\n"); … … 239 270 } 240 271 /*----------------------------------------------------------------------------*/ 272 /** Initializes UHCI hcd transfer lists. 273 * 274 * @param[in] instance UHCI structure to use. 275 * @return Error code 276 * @note Should be called only once on any structure. 277 */ 241 278 int uhci_init_transfer_lists(uhci_t *instance) 242 279 { … … 257 294 CHECK_RET_CLEAR_RETURN(ret, "Failed to init BULK list."); 258 295 259 ret = transfer_list_init(&instance->transfers_control_full, "CONTROL_FULL"); 296 ret = transfer_list_init( 297 &instance->transfers_control_full, "CONTROL_FULL"); 260 298 CHECK_RET_CLEAR_RETURN(ret, "Failed to init CONTROL FULL list."); 261 299 262 ret = transfer_list_init(&instance->transfers_control_slow, "CONTROL_SLOW"); 300 ret = transfer_list_init( 301 &instance->transfers_control_slow, "CONTROL_SLOW"); 263 302 CHECK_RET_CLEAR_RETURN(ret, "Failed to init CONTROL SLOW list."); 264 303 … … 279 318 #endif 280 319 281 instance->transfers[0][USB_TRANSFER_INTERRUPT] = 320 /* Assign pointers to be used during scheduling */ 321 instance->transfers[USB_SPEED_FULL][USB_TRANSFER_INTERRUPT] = 282 322 &instance->transfers_interrupt; 283 instance->transfers[ 1][USB_TRANSFER_INTERRUPT] =323 instance->transfers[USB_SPEED_LOW][USB_TRANSFER_INTERRUPT] = 284 324 &instance->transfers_interrupt; 285 instance->transfers[ 0][USB_TRANSFER_CONTROL] =325 instance->transfers[USB_SPEED_FULL][USB_TRANSFER_CONTROL] = 286 326 &instance->transfers_control_full; 287 instance->transfers[ 1][USB_TRANSFER_CONTROL] =327 instance->transfers[USB_SPEED_LOW][USB_TRANSFER_CONTROL] = 288 328 &instance->transfers_control_slow; 289 instance->transfers[ 0][USB_TRANSFER_BULK] =329 instance->transfers[USB_SPEED_FULL][USB_TRANSFER_BULK] = 290 330 &instance->transfers_bulk_full; 291 331 … … 294 334 } 295 335 /*----------------------------------------------------------------------------*/ 336 /** Schedules batch for execution. 337 * 338 * @param[in] instance UHCI structure to use. 339 * @param[in] batch Transfer batch to schedule. 340 * @return Error code 341 */ 296 342 int uhci_schedule(uhci_t *instance, batch_t *batch) 297 343 { … … 301 347 if (!allowed_usb_packet( 302 348 low_speed, batch->transfer_type, batch->max_packet_size)) { 303 usb_log_warning("Invalid USB packet specified %s SPEED %d %zu.\n", 349 usb_log_warning( 350 "Invalid USB packet specified %s SPEED %d %zu.\n", 304 351 low_speed ? "LOW" : "FULL" , batch->transfer_type, 305 352 batch->max_packet_size); … … 316 363 } 317 364 /*----------------------------------------------------------------------------*/ 365 /** Takes action based on the interrupt cause. 366 * 367 * @param[in] instance UHCI structure to use. 368 * @param[in] status Value of the stsatus regiser at the time of interrupt. 369 */ 318 370 void uhci_interrupt(uhci_t *instance, uint16_t status) 319 371 { 320 372 assert(instance); 373 /* TODO: Check interrupt cause here */ 321 374 transfer_list_remove_finished(&instance->transfers_interrupt); 322 375 transfer_list_remove_finished(&instance->transfers_control_slow); … … 325 378 } 326 379 /*----------------------------------------------------------------------------*/ 380 /** Polling function, emulates interrupts. 381 * 382 * @param[in] arg UHCI structure to use. 383 * @return EOK 384 */ 327 385 int uhci_interrupt_emulator(void* arg) 328 386 { … … 343 401 } 344 402 /*---------------------------------------------------------------------------*/ 403 /** Debug function, checks consistency of memory structures. 404 * 405 * @param[in] arg UHCI structure to use. 406 * @return EOK 407 */ 345 408 int uhci_debug_checker(void *arg) 346 409 { … … 401 464 async_usleep(UHCI_DEBUGER_TIMEOUT); 402 465 } 403 return 0;466 return EOK; 404 467 #undef QH 405 468 } 406 469 /*----------------------------------------------------------------------------*/ 470 /** Checks transfer packets, for USB validity 471 * 472 * @param[in] low_speed Transfer speed. 473 * @param[in] transfer Transer type 474 * @param[in] size Maximum size of used packets 475 * @return EOK 476 */ 407 477 bool allowed_usb_packet( 408 478 bool low_speed, usb_transfer_type_t transfer, size_t size) -
uspace/drv/uhci-hcd/uhci.h
rf16a76b rec4538d 84 84 device_keeper_t device_manager; 85 85 86 volatileregs_t *registers;86 regs_t *registers; 87 87 88 88 link_pointer_t *frame_list; -
uspace/drv/uhci-hcd/uhci_struct/queue_head.h
rf16a76b rec4538d 71 71 } 72 72 73 static inline void queue_head_ element_td(queue_head_t *instance, uint32_t pa)73 static inline void queue_head_set_element_td(queue_head_t *instance, uint32_t pa) 74 74 { 75 75 if (pa) { … … 78 78 } 79 79 80 static inline queue_head_t * queue_head_get() {81 queue_head_t *ret = malloc32(sizeof(queue_head_t));82 if (ret)83 queue_head_init(ret);84 return ret;85 }86 87 static inline void queue_head_dispose(queue_head_t *head)88 { free32(head); }89 90 91 80 #endif 92 81 /** -
uspace/drv/uhci-hcd/uhci_struct/transfer_descriptor.c
rf16a76b rec4538d 38 38 #include "utils/malloc32.h" 39 39 40 /** Initializes Transfer Descriptor 41 * 42 * @param[in] instance Memory place to initialize. 43 * @param[in] err_count Number of retries hc should attempt. 44 * @param[in] size Size of data source. 45 * @param[in] toggle Value of toggle bit. 46 * @param[in] iso True if TD is for Isochronous transfer. 47 * @param[in] low_speed Target device's speed. 48 * @param[in] target Address and endpoint receiving the transfer. 49 * @param[in] pid Packet identification (SETUP, IN or OUT). 50 * @param[in] buffer Source of data. 51 * @param[in] next Net TD in transaction. 52 * @return Error code. 53 */ 40 54 void td_init(td_t *instance, int err_count, size_t size, bool toggle, bool iso, 41 bool low_speed, usb_target_t target, usb_packet_id pid, void *buffer, td_t *next) 55 bool low_speed, usb_target_t target, usb_packet_id pid, void *buffer, 56 td_t *next) 42 57 { 43 58 assert(instance); 44 59 assert(size < 1024); 45 assert((pid == USB_PID_SETUP) || (pid == USB_PID_IN) || (pid == USB_PID_OUT)); 60 assert((pid == USB_PID_SETUP) || (pid == USB_PID_IN) 61 || (pid == USB_PID_OUT)); 46 62 47 63 instance->next = 0 … … 81 97 } 82 98 /*----------------------------------------------------------------------------*/ 99 /** Converts TD status into standard error code 100 * 101 * @param[in] instance TD structure to use. 102 * @return Error code. 103 */ 83 104 int td_status(td_t *instance) 84 105 { -
uspace/drv/uhci-hcd/utils/device_keeper.c
rf16a76b rec4538d 39 39 40 40 /*----------------------------------------------------------------------------*/ 41 /** Initializes device keeper structure. 42 * 43 * @param[in] instance Memory place to initialize. 44 */ 41 45 void device_keeper_init(device_keeper_t *instance) 42 46 { … … 53 57 } 54 58 /*----------------------------------------------------------------------------*/ 55 void device_keeper_reserve_default( 56 device_keeper_t *instance, usb_speed_t speed) 59 /** Attempts to obtain address 0, blocks. 60 * 61 * @param[in] instance Device keeper structure to use. 62 * @param[in] speed Speed of the device requesting default address. 63 */ 64 void device_keeper_reserve_default(device_keeper_t *instance, usb_speed_t speed) 57 65 { 58 66 assert(instance); … … 67 75 } 68 76 /*----------------------------------------------------------------------------*/ 77 /** Attempts to obtain address 0, blocks. 78 * 79 * @param[in] instance Device keeper structure to use. 80 * @param[in] speed Speed of the device requesting default address. 81 */ 69 82 void device_keeper_release_default(device_keeper_t *instance) 70 83 { … … 76 89 } 77 90 /*----------------------------------------------------------------------------*/ 91 /** Checks setup data for signs of toggle reset. 92 * 93 * @param[in] instance Device keeper structure to use. 94 * @param[in] target Device to receive setup packet. 95 * @param[in] data Setup packet data. 96 */ 78 97 void device_keeper_reset_if_need( 79 98 device_keeper_t *instance, usb_target_t target, const unsigned char *data) … … 84 103 || target.address >= USB_ADDRESS_COUNT || target.address < 0 85 104 || !instance->devices[target.address].occupied) { 86 goto the_end; 105 fibril_mutex_unlock(&instance->guard); 106 return; 87 107 } 88 108 … … 90 110 { 91 111 case 0x01: /*clear feature*/ 92 /* recipient is en point, value is zero (ENDPOINT_STALL) */112 /* recipient is endpoint, value is zero (ENDPOINT_STALL) */ 93 113 if (((data[0] & 0xf) == 1) && ((data[2] | data[3]) == 0)) { 94 /* enpoint number is < 16, thus first byte is enough */ 95 instance->devices[target.address].toggle_status &= ~(1 << data[4]); 114 /* endpoint number is < 16, thus first byte is enough */ 115 instance->devices[target.address].toggle_status &= 116 ~(1 << data[4]); 96 117 } 97 118 break; … … 102 123 break; 103 124 } 104 the_end: 105 fibril_mutex_unlock(&instance->guard); 106 } 107 /*----------------------------------------------------------------------------*/ 125 fibril_mutex_unlock(&instance->guard); 126 } 127 /*----------------------------------------------------------------------------*/ 128 /** Gets current value of endpoint toggle. 129 * 130 * @param[in] instance Device keeper structure to use. 131 * @param[in] target Device and endpoint used. 132 * @return Error code 133 */ 108 134 int device_keeper_get_toggle(device_keeper_t *instance, usb_target_t target) 109 135 { … … 116 142 ret = EINVAL; 117 143 } else { 118 ret = (instance->devices[target.address].toggle_status >> target.endpoint) & 1; 144 ret = 145 (instance->devices[target.address].toggle_status 146 >> target.endpoint) & 1; 119 147 } 120 148 fibril_mutex_unlock(&instance->guard); … … 122 150 } 123 151 /*----------------------------------------------------------------------------*/ 152 /** Sets current value of endpoint toggle. 153 * 154 * @param[in] instance Device keeper structure to use. 155 * @param[in] target Device and endpoint used. 156 * @param[in] toggle Current toggle value. 157 * @return Error code. 158 */ 124 159 int device_keeper_set_toggle( 125 160 device_keeper_t *instance, usb_target_t target, bool toggle) … … 144 179 } 145 180 /*----------------------------------------------------------------------------*/ 181 /** Gets a free USB address 182 * 183 * @param[in] instance Device keeper structure to use. 184 * @param[in] speed Speed of the device requiring address. 185 * @return Free address, or error code. 186 */ 146 187 usb_address_t device_keeper_request( 147 188 device_keeper_t *instance, usb_speed_t speed) … … 171 212 } 172 213 /*----------------------------------------------------------------------------*/ 214 /** Binds USB address to devman handle. 215 * 216 * @param[in] instance Device keeper structure to use. 217 * @param[in] address Device address 218 * @param[in] handle Devman handle of the device. 219 */ 173 220 void device_keeper_bind( 174 221 device_keeper_t *instance, usb_address_t address, devman_handle_t handle) … … 183 230 } 184 231 /*----------------------------------------------------------------------------*/ 232 /** Releases used USB address. 233 * 234 * @param[in] instance Device keeper structure to use. 235 * @param[in] address Device address 236 */ 185 237 void device_keeper_release(device_keeper_t *instance, usb_address_t address) 186 238 { … … 195 247 } 196 248 /*----------------------------------------------------------------------------*/ 249 /** Finds USB address associated with the device 250 * 251 * @param[in] instance Device keeper structure to use. 252 * @param[in] handle Devman handle of the device seeking its address. 253 * @return USB Address, or error code. 254 */ 197 255 usb_address_t device_keeper_find( 198 256 device_keeper_t *instance, devman_handle_t handle) … … 212 270 } 213 271 /*----------------------------------------------------------------------------*/ 272 /** Gets speed associated with the address 273 * 274 * @param[in] instance Device keeper structure to use. 275 * @param[in] address Address of the device. 276 * @return USB speed. 277 */ 214 278 usb_speed_t device_keeper_speed( 215 279 device_keeper_t *instance, usb_address_t address)
Note:
See TracChangeset
for help on using the changeset viewer.
