Changeset 478e243 in mainline for uspace/drv/bus/usb/ehci/hc.c
- Timestamp:
- 2014-01-22T00:00:18Z (10 years ago)
- Branches:
- lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
- Children:
- 64c96b9
- Parents:
- bdddc9d
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
uspace/drv/bus/usb/ehci/hc.c
rbdddc9d r478e243 89 89 }; 90 90 91 static void hc_gain_control(hc_t *instance);92 91 static void hc_start(hc_t *instance); 93 92 static int hc_init_memory(hc_t *instance); … … 185 184 } 186 185 187 hc_gain_control(instance);188 189 186 ehci_rh_init( 190 187 &instance->rh, instance->caps, instance->registers, "ehci rh"); … … 262 259 } 263 260 264 /** Turn off any (BIOS)driver that might be in control of the device. 265 * 266 * This function implements routines described in chapter 5.1.1.3 of the EHCI 267 * specification (page 40, pdf page 54). 261 /** EHCI hw initialization routine. 268 262 * 269 263 * @param[in] instance EHCI hc driver structure. 270 264 */ 271 void hc_gain_control(hc_t *instance)272 {273 assert(instance);274 }275 276 /** EHCI hw initialization routine.277 *278 * @param[in] instance EHCI hc driver structure.279 */280 265 void hc_start(hc_t *instance) 281 266 { 282 267 assert(instance); 268 /* Turn of the HC if it's running, Reseting a running device is 269 * undefined */ 270 if (!(EHCI_RD(instance->registers->usbsts) & USB_STS_HC_HALTED_FLAG)) { 271 /* disable all interrupts */ 272 EHCI_WR(instance->registers->usbintr, 0); 273 /* ack all interrupts */ 274 EHCI_WR(instance->registers->usbsts, 0x3f); 275 /* Stop HC hw */ 276 EHCI_WR(instance->registers->usbcmd, 0); 277 /* Wait until hc is halted */ 278 while ((EHCI_RD(instance->registers->usbsts) & USB_STS_HC_HALTED_FLAG) == 0) { 279 async_usleep(1); 280 } 281 usb_log_info("EHCI turned off.\n"); 282 } else { 283 usb_log_info("EHCI was not running.\n"); 284 } 285 286 /* Hw initialization sequence, see page 53 (pdf 63) */ 287 EHCI_SET(instance->registers->usbcmd, USB_CMD_HC_RESET_FLAG); 288 while (EHCI_RD(instance->registers->usbcmd) & USB_CMD_HC_RESET_FLAG) { 289 async_usleep(1); 290 } 291 /* Enable interrupts */ 292 EHCI_WR(instance->registers->usbintr, USB_INTR_PORT_CHANGE_FLAG | USB_INTR_IRQ_FLAG); 293 /* Use lower 4G segment */ 294 EHCI_WR(instance->registers->ctrldssegment, 0); 295 /* Set periodic list */ 296 assert(instance->periodic_list_base); 297 const uintptr_t phys_base = 298 addr_to_phys((void*)instance->periodic_list_base); 299 assert((phys_base & USB_PERIODIC_LIST_BASE_MASK) == phys_base); 300 EHCI_WR(instance->registers->periodiclistbase, phys_base); 301 302 /* start hc and get all ports */ 303 EHCI_SET(instance->registers->usbcmd, USB_CMD_RUN_FLAG); 304 EHCI_SET(instance->registers->configflag, USB_CONFIG_FLAG_FLAG); 305 #if 0 283 306 /* 284 307 * TURN OFF EHCI FOR NOW 285 308 */ 286 287 309 usb_log_debug("USBCMD value: %x.\n", 288 310 EHCI_RD(instance->registers->usbcmd)); … … 301 323 usb_log_info("EHCI was not running.\n"); 302 324 } 325 #endif 303 326 usb_log_debug("Registers: \n" 304 327 "\t USBCMD(%p): %x(0x00080000 = at least 1ms between interrupts)\n" … … 319 342 int hc_init_memory(hc_t *instance) 320 343 { 344 assert(instance); 345 346 /* Take 1024 periodic list heads, we ignore low mem options */ 347 instance->periodic_list_base = get_page(); 348 if (!instance->periodic_list_base) 349 return ENOMEM; 350 for (unsigned i = 0; 351 i < PAGE_SIZE/sizeof(instance->periodic_list_base[0]); ++i) 352 { 353 /* Disable everything for now */ 354 instance->periodic_list_base[i] = LINK_POINTER_TERM; 355 } 321 356 return EOK; 322 357 }
Note:
See TracChangeset
for help on using the changeset viewer.