Changeset 95c675b in mainline for uspace/lib/usbhost/src/ddf_helpers.c


Ignore:
Timestamp:
2017-10-17T13:11:35Z (7 years ago)
Author:
Ondřej Hlavatý <aearsis@…>
Branches:
lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
Children:
60af4cdb
Parents:
dbf32b1 (diff), a416d070 (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.
Message:

Merge mainline

File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/lib/usbhost/src/ddf_helpers.c

    rdbf32b1 r95c675b  
    4747#include <ddf/interrupt.h>
    4848#include <device/hw_res_parsed.h>
    49 #include <devman.h>
    5049#include <errno.h>
    5150#include <fibril_synch.h>
     
    607606}
    608607
    609 //TODO: Move this to generic ddf?
    610 /** Call the parent driver with a request to enable interrupts
     608//TODO: Cache parent session in HCD
     609/** Call the parent driver with a request to enable interrupt
    611610 *
    612611 * @param[in] device Device asking for interrupts
     612 * @param[in] inum Interrupt number
    613613 * @return Error code.
    614614 */
    615 int hcd_ddf_enable_interrupts(ddf_dev_t *device)
    616 {
    617         assert(device);
    618         async_sess_t *parent_sess =
    619             devman_parent_device_connect(ddf_dev_get_handle(device),
    620             IPC_FLAG_BLOCKING);
    621         const bool enabled = hw_res_enable_interrupt(parent_sess);
    622         async_hangup(parent_sess);
    623 
    624         return enabled ? EOK : EIO;
    625 }
    626 
    627 //TODO: Move this to generic ddf?
     615int hcd_ddf_enable_interrupt(ddf_dev_t *device, int inum)
     616{
     617        async_sess_t *parent_sess = ddf_dev_parent_sess_get(device);
     618        if (parent_sess == NULL)
     619                return EIO;
     620
     621        return hw_res_enable_interrupt(parent_sess, inum);
     622}
     623
     624//TODO: Cache parent session in HCD
    628625int hcd_ddf_get_registers(ddf_dev_t *device, hw_res_list_parsed_t *hw_res)
    629626{
    630         assert(device);
    631         assert(hw_res);
    632 
    633         async_sess_t *parent_sess =
    634             devman_parent_device_connect(ddf_dev_get_handle(device),
    635             IPC_FLAG_BLOCKING);
     627        async_sess_t *parent_sess = ddf_dev_parent_sess_get(device);
     628        if (parent_sess == NULL)
     629                return EIO;
     630
    636631        hw_res_list_parsed_init(hw_res);
    637632        const int ret = hw_res_get_list_parsed(parent_sess, hw_res, 0);
    638         async_hangup(parent_sess);
    639633        if (ret != EOK)
    640634                hw_res_list_parsed_clean(hw_res);
     
    663657 * @param[in] gen_irq_code IRQ code generator.
    664658 *
    665  * @return EOK on success or negative error code
     659 * @return IRQ capability handle on success.
     660 * @return Negative error code.
    666661 */
    667662int hcd_ddf_setup_interrupts(ddf_dev_t *device,
     
    687682
    688683        /* Register handler to avoid interrupt lockup */
    689         int ret = register_interrupt_handler(device, irq, handler, &irq_code);
     684        const int irq_cap = register_interrupt_handler(device, irq, handler,
     685            &irq_code);
    690686        irq_code_clean(&irq_code);
    691         if (ret != EOK) {
     687        if (irq_cap < 0) {
    692688                usb_log_error("Failed to register interrupt handler: %s.\n",
    693                     str_error(ret));
    694                 return ret;
     689                    str_error(irq_cap));
     690                return irq_cap;
    695691        }
    696692
    697693        /* Enable interrupts */
    698         ret = hcd_ddf_enable_interrupts(device);
     694        int ret = hcd_ddf_enable_interrupt(device, irq);
    699695        if (ret != EOK) {
    700696                usb_log_error("Failed to enable interrupts: %s.\n",
    701697                    str_error(ret));
    702                 unregister_interrupt_handler(device, irq);
     698                unregister_interrupt_handler(device, irq_cap);
    703699                return ret;
    704700        }
    705         assert(irq > 0);
    706         return irq;
     701        return irq_cap;
    707702}
    708703
     
    796791        interrupt_handler_t *irq_handler =
    797792            driver->irq_handler ? driver->irq_handler : ddf_hcd_gen_irq_handler;
    798         const int irq = hcd_ddf_setup_interrupts(device, &hw_res, irq_handler, driver->irq_code_gen);
    799         if (!(irq < 0)) {
     793        const int irq_cap = hcd_ddf_setup_interrupts(device, &hw_res,
     794            irq_handler, driver->irq_code_gen);
     795        bool irqs_enabled = !(irq_cap < 0);
     796        if (irqs_enabled) {
    800797                usb_log_debug("Hw interrupts enabled.\n");
    801798        }
     
    812809        /* Start hw driver */
    813810        if (driver->start)
    814                 ret = driver->start(hcd, !(irq < 0));
     811                ret = driver->start(hcd, irqs_enabled);
    815812        if (ret != EOK) {
    816813                usb_log_error("Failed to start HCD: %s.\n", str_error(ret));
     
    819816
    820817        /* Need working irq replacement to setup root hub */
    821         if ((irq < 0) && hcd->ops.status_hook) {
     818        if (!irqs_enabled && hcd->ops.status_hook) {
    822819                hcd->polling_fibril = fibril_create(interrupt_polling, hcd);
    823820                if (hcd->polling_fibril == 0) {
     
    828825                fibril_add_ready(hcd->polling_fibril);
    829826                usb_log_warning("Failed to enable interrupts: %s."
    830                     " Falling back to polling.\n", str_error(irq));
     827                    " Falling back to polling.\n", str_error(irq_cap));
    831828        }
    832829
     
    854851                driver->stop(hcd);
    855852err_irq:
    856         unregister_interrupt_handler(device, irq);
     853        unregister_interrupt_handler(device, irq_cap);
    857854        if (driver->fini)
    858855                driver->fini(hcd);
Note: See TracChangeset for help on using the changeset viewer.