Ignore:
Timestamp:
2013-12-31T04:12:59Z (10 years ago)
Author:
Jan Vesely <jano.vesely@…>
Branches:
lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
Children:
99e8fb7b
Parents:
0c322fa
Message:

libdrv, libusbhid: Move usbhid client iface to libdrv

File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/lib/drv/generic/remote_usbhid.c

    r0c322fa ra44424f  
    4242#include "ddf/driver.h"
    4343
     44/** IPC methods for USB HID device interface. */
     45typedef enum {
     46        /** Get number of events reported in single burst.
     47         * Parameters: none
     48         * Answer:
     49         * - Size of one report in bytes.
     50         */
     51        IPC_M_USBHID_GET_EVENT_LENGTH,
     52        /** Get single event from the HID device.
     53         * The word single refers to set of individual events that were
     54         * available at particular point in time.
     55         * Parameters:
     56         * - flags
     57         * The call is followed by data read expecting two concatenated
     58         * arrays.
     59         * Answer:
     60         * - EOK - events returned
     61         * - EAGAIN - no event ready (only in non-blocking mode)
     62         *
     63         * It is okay if the client requests less data. Extra data must
     64         * be truncated by the driver.
     65         *
     66         * @todo Change this comment.
     67         */
     68        IPC_M_USBHID_GET_EVENT,
     69       
     70        /** Get the size of the report descriptor from the HID device.
     71         *
     72         * Parameters:
     73         * - none
     74         * Answer:
     75         * - EOK - method is implemented (expected always)
     76         * Parameters of the answer:
     77         * - Size of the report in bytes.
     78         */
     79        IPC_M_USBHID_GET_REPORT_DESCRIPTOR_LENGTH,
     80       
     81        /** Get the report descriptor from the HID device.
     82         *
     83         * Parameters:
     84         * - none
     85         * The call is followed by data read expecting the descriptor itself.
     86         * Answer:
     87         * - EOK - report descriptor returned.
     88         */
     89        IPC_M_USBHID_GET_REPORT_DESCRIPTOR
     90} usbhid_iface_funcs_t;
     91
     92/** Ask for event array length.
     93 *
     94 * @param dev_sess Session to DDF device providing USB HID interface.
     95 *
     96 * @return Number of usages returned or negative error code.
     97 *
     98 */
     99int usbhid_dev_get_event_length(async_sess_t *dev_sess, size_t *size)
     100{
     101        if (!dev_sess)
     102                return EINVAL;
     103       
     104        async_exch_t *exch = async_exchange_begin(dev_sess);
     105       
     106        sysarg_t len;
     107        int rc = async_req_1_1(exch, DEV_IFACE_ID(USBHID_DEV_IFACE),
     108            IPC_M_USBHID_GET_EVENT_LENGTH, &len);
     109       
     110        async_exchange_end(exch);
     111       
     112        if (rc == EOK) {
     113                if (size != NULL)
     114                        *size = (size_t) len;
     115        }
     116       
     117        return rc;
     118}
     119
     120/** Request for next event from HID device.
     121 *
     122 * @param[in]  dev_sess    Session to DDF device providing USB HID interface.
     123 * @param[out] usage_pages Where to store usage pages.
     124 * @param[out] usages      Where to store usages (actual data).
     125 * @param[in]  usage_count Length of @p usage_pages and @p usages buffer
     126 *                         (in items, not bytes).
     127 * @param[out] actual_usage_count Number of usages actually returned by the
     128 *                                device driver.
     129 * @param[in] flags        Flags (see USBHID_IFACE_FLAG_*).
     130 *
     131 * @return Error code.
     132 *
     133 */
     134int usbhid_dev_get_event(async_sess_t *dev_sess, uint8_t *buf,
     135    size_t size, size_t *actual_size, int *event_nr, unsigned int flags)
     136{
     137        if (!dev_sess)
     138                return EINVAL;
     139       
     140        if (buf == NULL)
     141                return ENOMEM;
     142       
     143        if (size == 0)
     144                return EINVAL;
     145       
     146        size_t buffer_size =  size;
     147        uint8_t *buffer = malloc(buffer_size);
     148        if (buffer == NULL)
     149                return ENOMEM;
     150       
     151        async_exch_t *exch = async_exchange_begin(dev_sess);
     152       
     153        ipc_call_t opening_request_call;
     154        aid_t opening_request = async_send_2(exch,
     155            DEV_IFACE_ID(USBHID_DEV_IFACE), IPC_M_USBHID_GET_EVENT,
     156            flags, &opening_request_call);
     157       
     158        if (opening_request == 0) {
     159                async_exchange_end(exch);
     160                free(buffer);
     161                return ENOMEM;
     162        }
     163       
     164        ipc_call_t data_request_call;
     165        aid_t data_request = async_data_read(exch, buffer, buffer_size,
     166            &data_request_call);
     167       
     168        async_exchange_end(exch);
     169       
     170        if (data_request == 0) {
     171                async_forget(opening_request);
     172                free(buffer);
     173                return ENOMEM;
     174        }
     175       
     176        sysarg_t data_request_rc;
     177        sysarg_t opening_request_rc;
     178        async_wait_for(data_request, &data_request_rc);
     179        async_wait_for(opening_request, &opening_request_rc);
     180       
     181        if (data_request_rc != EOK) {
     182                /* Prefer return code of the opening request. */
     183                if (opening_request_rc != EOK)
     184                        return (int) opening_request_rc;
     185                else
     186                        return (int) data_request_rc;
     187        }
     188       
     189        if (opening_request_rc != EOK)
     190                return (int) opening_request_rc;
     191       
     192        size_t act_size = IPC_GET_ARG2(data_request_call);
     193       
     194        /* Copy the individual items. */
     195        memcpy(buf, buffer, act_size);
     196       
     197        if (actual_size != NULL)
     198                *actual_size = act_size;
     199       
     200        if (event_nr != NULL)
     201                *event_nr = IPC_GET_ARG1(opening_request_call);
     202       
     203        return EOK;
     204}
     205
     206int usbhid_dev_get_report_descriptor_length(async_sess_t *dev_sess,
     207    size_t *size)
     208{
     209        if (!dev_sess)
     210                return EINVAL;
     211       
     212        async_exch_t *exch = async_exchange_begin(dev_sess);
     213       
     214        sysarg_t arg_size;
     215        int rc = async_req_1_1(exch, DEV_IFACE_ID(USBHID_DEV_IFACE),
     216            IPC_M_USBHID_GET_REPORT_DESCRIPTOR_LENGTH, &arg_size);
     217       
     218        async_exchange_end(exch);
     219       
     220        if (rc == EOK) {
     221                if (size != NULL)
     222                        *size = (size_t) arg_size;
     223        }
     224       
     225        return rc;
     226}
     227
     228int usbhid_dev_get_report_descriptor(async_sess_t *dev_sess, uint8_t *buf,
     229    size_t size, size_t *actual_size)
     230{
     231        if (!dev_sess)
     232                return EINVAL;
     233       
     234        if (buf == NULL)
     235                return ENOMEM;
     236       
     237        if (size == 0)
     238                return EINVAL;
     239       
     240        async_exch_t *exch = async_exchange_begin(dev_sess);
     241       
     242        aid_t opening_request = async_send_1(exch,
     243            DEV_IFACE_ID(USBHID_DEV_IFACE), IPC_M_USBHID_GET_REPORT_DESCRIPTOR,
     244            NULL);
     245        if (opening_request == 0) {
     246                async_exchange_end(exch);
     247                return ENOMEM;
     248        }
     249       
     250        ipc_call_t data_request_call;
     251        aid_t data_request = async_data_read(exch, buf, size,
     252            &data_request_call);
     253       
     254        async_exchange_end(exch);
     255       
     256        if (data_request == 0) {
     257                async_forget(opening_request);
     258                return ENOMEM;
     259        }
     260       
     261        sysarg_t data_request_rc;
     262        sysarg_t opening_request_rc;
     263        async_wait_for(data_request, &data_request_rc);
     264        async_wait_for(opening_request, &opening_request_rc);
     265       
     266        if (data_request_rc != EOK) {
     267                /* Prefer return code of the opening request. */
     268                if (opening_request_rc != EOK)
     269                        return (int) opening_request_rc;
     270                else
     271                        return (int) data_request_rc;
     272        }
     273       
     274        if (opening_request_rc != EOK)
     275                return (int) opening_request_rc;
     276       
     277        size_t act_size = IPC_GET_ARG2(data_request_call);
     278       
     279        if (actual_size != NULL)
     280                *actual_size = act_size;
     281       
     282        return EOK;
     283}
     284
    44285static void remote_usbhid_get_event_length(ddf_fun_t *, void *, ipc_callid_t, ipc_call_t *);
    45286static void remote_usbhid_get_event(ddf_fun_t *, void *, ipc_callid_t, ipc_call_t *);
Note: See TracChangeset for help on using the changeset viewer.