Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/drv/bus/usb/usbhid/kbd/kbddev.c

    r5da7199 r2a5b62b  
    174174{
    175175        sysarg_t method = IPC_GET_IMETHOD(*icall);
    176        
     176
    177177        usb_kbd_t *kbd_dev = (usb_kbd_t *) fun->driver_data;
    178178        if (kbd_dev == NULL) {
     
    182182                return;
    183183        }
    184        
     184
    185185        async_sess_t *sess =
    186186            async_callback_receive_start(EXCHANGE_SERIALIZE, icall);
     
    240240            USB_HID_PATH_COMPARE_END | USB_HID_PATH_COMPARE_USAGE_PAGE_ONLY,
    241241            USB_HID_REPORT_TYPE_OUTPUT);
    242        
     242
    243243        while (field != NULL) {
    244244               
     
    263263                        USB_HID_REPORT_TYPE_OUTPUT);
    264264        }
    265        
     265
    266266        // TODO: what about the Report ID?
    267267        int rc = usb_hid_report_output_translate(hid_dev->report, 0,
    268268            kbd_dev->output_buffer, kbd_dev->output_size);
    269        
     269
    270270        if (rc != EOK) {
    271271                usb_log_warning("Error translating LED output to output report"
     
    273273                return;
    274274        }
    275        
     275
    276276        usb_log_debug("Output report buffer: %s\n",
    277277            usb_debug_str_buffer(kbd_dev->output_buffer, kbd_dev->output_size,
    278278                0));
    279        
     279
    280280        usbhid_req_set_report(&hid_dev->usb_dev->ctrl_pipe,
    281281            hid_dev->usb_dev->interface_no, USB_HID_REPORT_TYPE_OUTPUT,
     
    300300                return;
    301301        }
    302        
     302
    303303        async_exch_t *exch = async_exchange_begin(kbd_dev->console_sess);
    304304        async_msg_2(exch, KBDEV_EVENT, type, key);
     
    347347        unsigned int key;
    348348        size_t i;
    349        
     349
    350350        /*
    351351         * First of all, check if the kbd have reported phantom state.
     
    362362                return;
    363363        }
    364        
     364
    365365        /*
    366366         * Key releases
     
    382382                }
    383383        }
    384        
     384
    385385        /*
    386386         * Key presses
     
    402402                }
    403403        }
    404        
     404
    405405        memcpy(kbd_dev->keys_old, kbd_dev->keys, kbd_dev->key_count * 4);
    406        
     406
    407407        char key_buffer[512];
    408408        ddf_dump_buffer(key_buffer, 512,
     
    435435        assert(hid_dev != NULL);
    436436        assert(kbd_dev != NULL);
    437        
     437
    438438        usb_hid_report_path_t *path = usb_hid_report_path();
    439439        usb_hid_report_path_append_item(path, USB_HIDUT_PAGE_KEYBOARD, 0);
    440440
    441441        usb_hid_report_path_set_report_id (path, hid_dev->report_id);
    442        
     442
    443443        // fill in the currently pressed keys
    444        
     444
    445445        usb_hid_report_field_t *field = usb_hid_report_get_sibling(
    446446            hid_dev->report, NULL, path,
     
    448448            USB_HID_REPORT_TYPE_INPUT);
    449449        unsigned i = 0;
    450        
     450
    451451        while (field != NULL) {
    452452                usb_log_debug2("FIELD (%p) - VALUE(%d) USAGE(%u)\n",
     
    470470                    USB_HID_REPORT_TYPE_INPUT);
    471471        }
    472        
     472
    473473        usb_hid_report_path_free(path);
    474        
     474
    475475        usb_kbd_check_key_changes(hid_dev, kbd_dev);
    476476}
     
    502502
    503503        if (kbd_dev == NULL) {
    504                 usb_log_fatal("No memory!\n");
     504                usb_log_error("No memory!\n");
    505505                return NULL;
    506506        }
    507        
     507
    508508        kbd_dev->console_sess = NULL;
    509509        kbd_dev->initialized = USB_KBD_STATUS_UNINITIALIZED;
    510        
     510
    511511        return kbd_dev;
    512512}
     
    514514/*----------------------------------------------------------------------------*/
    515515
    516 static int usb_kbd_create_function(usb_hid_dev_t *hid_dev, usb_kbd_t *kbd_dev)
    517 {
    518         assert(hid_dev != NULL);
    519         assert(hid_dev->usb_dev != NULL);
     516static int usb_kbd_create_function(usb_kbd_t *kbd_dev)
     517{
    520518        assert(kbd_dev != NULL);
    521        
     519        assert(kbd_dev->hid_dev != NULL);
     520        assert(kbd_dev->hid_dev->usb_dev != NULL);
     521
    522522        /* Create the exposed function. */
    523523        usb_log_debug("Creating DDF function %s...\n", HID_KBD_FUN_NAME);
    524         ddf_fun_t *fun = ddf_fun_create(hid_dev->usb_dev->ddf_dev, fun_exposed,
    525             HID_KBD_FUN_NAME);
     524        ddf_fun_t *fun = ddf_fun_create(kbd_dev->hid_dev->usb_dev->ddf_dev,
     525            fun_exposed, HID_KBD_FUN_NAME);
    526526        if (fun == NULL) {
    527527                usb_log_error("Could not create DDF function node.\n");
    528528                return ENOMEM;
    529529        }
    530        
     530
    531531        /*
    532532         * Store the initialized HID device and HID ops
     
    540540                usb_log_error("Could not bind DDF function: %s.\n",
    541541                    str_error(rc));
     542                fun->driver_data = NULL; /* We need this later */
    542543                ddf_fun_destroy(fun);
    543544                return rc;
    544545        }
    545        
     546
    546547        usb_log_debug("%s function created. Handle: %" PRIun "\n",
    547548            HID_KBD_FUN_NAME, fun->handle);
    548        
     549
    549550        usb_log_debug("Adding DDF function to category %s...\n",
    550551            HID_KBD_CLASS_NAME);
     
    554555                    "Could not add DDF function to category %s: %s.\n",
    555556                    HID_KBD_CLASS_NAME, str_error(rc));
     557                fun->driver_data = NULL; /* We need this later */
    556558                ddf_fun_destroy(fun);
    557559                return rc;
    558560        }
    559        
     561        kbd_dev->fun = fun;
     562
    560563        return EOK;
    561564}
     
    587590{
    588591        usb_log_debug("Initializing HID/KBD structure...\n");
    589        
     592
    590593        if (hid_dev == NULL) {
    591594                usb_log_error("Failed to init keyboard structure: no structure"
     
    593596                return EINVAL;
    594597        }
    595        
     598
    596599        usb_kbd_t *kbd_dev = usb_kbd_new();
    597600        if (kbd_dev == NULL) {
     
    603606        /* Store link to HID device */
    604607        kbd_dev->hid_dev = hid_dev;
    605        
     608
    606609        /*
    607610         * TODO: make more general
     
    609612        usb_hid_report_path_t *path = usb_hid_report_path();
    610613        usb_hid_report_path_append_item(path, USB_HIDUT_PAGE_KEYBOARD, 0);
    611        
     614
    612615        usb_hid_report_path_set_report_id(path, 0);
    613        
     616
    614617        kbd_dev->key_count = usb_hid_report_size(
    615618            hid_dev->report, 0, USB_HID_REPORT_TYPE_INPUT);
    616619        usb_hid_report_path_free(path);
    617        
     620
    618621        usb_log_debug("Size of the input report: %zu\n", kbd_dev->key_count);
    619        
     622
    620623        kbd_dev->keys = (int32_t *)calloc(kbd_dev->key_count, sizeof(int32_t));
    621        
     624
    622625        if (kbd_dev->keys == NULL) {
    623                 usb_log_fatal("No memory!\n");
     626                usb_log_error("No memory!\n");
    624627                free(kbd_dev);
    625628                return ENOMEM;
    626629        }
    627        
     630
    628631        kbd_dev->keys_old =
    629632                (int32_t *)calloc(kbd_dev->key_count, sizeof(int32_t));
    630        
     633
    631634        if (kbd_dev->keys_old == NULL) {
    632                 usb_log_fatal("No memory!\n");
     635                usb_log_error("No memory!\n");
    633636                free(kbd_dev->keys);
    634637                free(kbd_dev);
    635638                return ENOMEM;
    636639        }
    637        
     640
    638641        /*
    639642         * Output report
     
    647650                return ENOMEM;
    648651        }
    649        
     652
    650653        usb_log_debug("Output buffer size: %zu\n", kbd_dev->output_size);
    651        
     654
    652655        kbd_dev->led_path = usb_hid_report_path();
    653656        usb_hid_report_path_append_item(
    654657            kbd_dev->led_path, USB_HIDUT_PAGE_LED, 0);
    655        
     658
    656659        kbd_dev->led_output_size = usb_hid_report_size(hid_dev->report,
    657660            0, USB_HID_REPORT_TYPE_OUTPUT);
    658        
     661
    659662        usb_log_debug("Output report size (in items): %zu\n",
    660663            kbd_dev->led_output_size);
    661        
     664
    662665        kbd_dev->led_data = (int32_t *)calloc(
    663666            kbd_dev->led_output_size, sizeof(int32_t));
    664        
     667
    665668        if (kbd_dev->led_data == NULL) {
    666669                usb_log_warning("Error creating buffer for LED output report."
     
    671674                return ENOMEM;
    672675        }
    673        
     676
    674677        /*
    675678         * Modifiers and locks
     
    678681        kbd_dev->mods = DEFAULT_ACTIVE_MODS;
    679682        kbd_dev->lock_keys = 0;
    680        
     683
    681684        /*
    682685         * Autorepeat
     
    686689        kbd_dev->repeat.delay_before = DEFAULT_DELAY_BEFORE_FIRST_REPEAT;
    687690        kbd_dev->repeat.delay_between = DEFAULT_REPEAT_DELAY;
    688        
    689         kbd_dev->repeat_mtx = (fibril_mutex_t *)(
    690             malloc(sizeof(fibril_mutex_t)));
    691         if (kbd_dev->repeat_mtx == NULL) {
    692                 usb_log_fatal("No memory!\n");
    693                 free(kbd_dev->keys);
    694                 usb_hid_report_output_free(kbd_dev->output_buffer);
    695                 free(kbd_dev);
    696                 return ENOMEM;
    697         }
    698        
    699         fibril_mutex_initialize(kbd_dev->repeat_mtx);
    700        
     691
     692        fibril_mutex_initialize(&kbd_dev->repeat_mtx);
     693
    701694        // save the KBD device structure into the HID device structure
    702695        *data = kbd_dev;
    703        
     696
    704697        // set handler for incoming calls
    705698        kbd_dev->ops.default_handler = default_connection_handler;
    706        
     699
    707700        /*
    708701         * Set LEDs according to initial setup.
     
    710703         */
    711704        usb_kbd_set_led(hid_dev, kbd_dev);
    712        
     705
    713706        usbhid_req_set_idle(&hid_dev->usb_dev->ctrl_pipe,
    714707            hid_dev->usb_dev->interface_no, IDLE_RATE);
    715        
     708
    716709        /*
    717710         * Create new fibril for auto-repeat
     
    723716        }
    724717        fibril_add_ready(fid);
    725        
     718
    726719        kbd_dev->initialized = USB_KBD_STATUS_INITIALIZED;
    727720        usb_log_debug("HID/KBD device structure initialized.\n");
    728        
     721
    729722        usb_log_debug("Creating KBD function...\n");
    730         int rc = usb_kbd_create_function(hid_dev, kbd_dev);
     723        int rc = usb_kbd_create_function(kbd_dev);
    731724        if (rc != EOK) {
    732725                usb_kbd_destroy(kbd_dev);
    733726                return rc;
    734727        }
    735        
     728
    736729        return EOK;
    737730}
     
    745738                return false;
    746739        }
    747        
     740
    748741        usb_kbd_t *kbd_dev = (usb_kbd_t *)data;
    749742        assert(kbd_dev != NULL);
    750        
     743
    751744        // TODO: add return value from this function
    752745        usb_kbd_process_data(hid_dev, kbd_dev);
    753        
     746
    754747        return true;
    755748}
     
    780773                return;
    781774        }
    782        
     775
    783776        // hangup session to the console
    784777        async_hangup(kbd_dev->console_sess);
    785        
    786         if (kbd_dev->repeat_mtx != NULL) {
    787                 //assert(!fibril_mutex_is_locked((*kbd_dev)->repeat_mtx));
    788                 // FIXME - the fibril_mutex_is_locked may not cause
    789                 // fibril scheduling
    790                 while (fibril_mutex_is_locked(kbd_dev->repeat_mtx)) {}
    791                 free(kbd_dev->repeat_mtx);
    792         }
    793        
     778
     779        //assert(!fibril_mutex_is_locked((*kbd_dev)->repeat_mtx));
     780        // FIXME - the fibril_mutex_is_locked may not cause
     781        // fibril scheduling
     782        while (fibril_mutex_is_locked(&kbd_dev->repeat_mtx)) {}
     783
    794784        // free all buffers
    795         if (kbd_dev->keys != NULL) {
    796                 free(kbd_dev->keys);
    797         }
    798         if (kbd_dev->keys_old != NULL) {
    799                 free(kbd_dev->keys_old);
    800         }
    801         if (kbd_dev->led_data != NULL) {
    802                 free(kbd_dev->led_data);
    803         }
     785        free(kbd_dev->keys);
     786        free(kbd_dev->keys_old);
     787        free(kbd_dev->led_data);
     788
    804789        if (kbd_dev->led_path != NULL) {
    805790                usb_hid_report_path_free(kbd_dev->led_path);
     
    808793                usb_hid_report_output_free(kbd_dev->output_buffer);
    809794        }
     795
     796        if (ddf_fun_unbind(kbd_dev->fun) != EOK) {
     797                usb_log_warning("Failed to unbind kbd function.\n");
     798        } else {
     799                usb_log_debug2("%s unbound.\n", kbd_dev->fun->name);
     800                kbd_dev->fun->driver_data = NULL;
     801                ddf_fun_destroy(kbd_dev->fun);
     802        }
    810803}
    811804
     
    817810                return;
    818811        }
    819        
     812
    820813        if (data != NULL) {
    821                 usb_kbd_t *kbd_dev = (usb_kbd_t *)data;
     814                usb_kbd_t *kbd_dev = data;
    822815                if (usb_kbd_is_initialized(kbd_dev)) {
    823816                        usb_kbd_mark_unusable(kbd_dev);
    824                 } else {
     817                        /* wait for autorepeat */
     818                        async_usleep(CHECK_DELAY);
    825819                        usb_kbd_destroy(kbd_dev);
    826820                }
     
    835829            USB_KBD_BOOT_REPORT_DESCRIPTOR,
    836830            USB_KBD_BOOT_REPORT_DESCRIPTOR_SIZE);
    837        
     831
    838832        if (rc != EOK) {
    839833                usb_log_error("Failed to parse boot report descriptor: %s\n",
     
    841835                return rc;
    842836        }
    843        
     837
    844838        rc = usbhid_req_set_protocol(&hid_dev->usb_dev->ctrl_pipe,
    845839            hid_dev->usb_dev->interface_no, USB_HID_PROTOCOL_BOOT);
    846        
     840
    847841        if (rc != EOK) {
    848842                usb_log_warning("Failed to set boot protocol to the device: "
     
    850844                return rc;
    851845        }
    852        
     846
    853847        return EOK;
    854848}
Note: See TracChangeset for help on using the changeset viewer.