Changeset 1d1f894 in mainline


Ignore:
Timestamp:
2010-11-03T15:05:41Z (13 years ago)
Author:
Vojtech Horky <vojtechhorky@…>
Branches:
lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
Children:
d70a463
Parents:
af894a21
Message:

Old code removal

Completely removed old methods for communicating with HCD (the ones
that used callback phones). Now only methods using the async framework
are available.

Location:
uspace
Files:
9 edited

Legend:

Unmodified
Added
Removed
  • uspace/app/usb/example.c

    raf894a21 r1d1f894  
    8282}
    8383
    84 static void client_connection(ipc_callid_t iid, ipc_call_t *icall)
    85 {
    86         ipc_answer_0(iid, EOK);
    87         //printf("%s: client connection()\n", NAME);
    88        
    89         while (true) {
    90                 ipc_callid_t callid;
    91                 ipc_call_t call;
    92                 int rc;
    93                 void * buffer;
    94                 size_t len;
    95                
    96                 callid = async_get_call(&call);
    97                
    98                 switch (IPC_GET_METHOD(call)) {
    99                         case IPC_M_USB_HCD_DATA_SENT:
    100                                 printf("%s: >> Data sent over USB (handle %d, outcome %s).\n",
    101                                     NAME, IPC_GET_ARG1(call),
    102                                     usb_str_transaction_outcome(IPC_GET_ARG2(call)));
    103                                 ipc_answer_0(callid, EOK);
    104                                 break;
    105                                
    106                         case IPC_M_USB_HCD_DATA_RECEIVED:
    107                                 printf("%s: << Data received over USB (handle %d, outcome %s).\n",
    108                                     NAME, IPC_GET_ARG1(call),
    109                                     usb_str_transaction_outcome(IPC_GET_ARG2(call)));
    110                                 if (IPC_GET_ARG2(call) != USB_OUTCOME_OK) {
    111                                         ipc_answer_0(callid, EOK);
    112                                         break;
    113                                 }
    114                                 len = IPC_GET_ARG3(call);
    115                                 if (len > 0) {
    116                                         rc = async_data_write_accept(&buffer, false,
    117                                             1, MAX_SIZE_RECEIVE,
    118                                             0, &len);
    119                                         if (rc != EOK) {
    120                                                 ipc_answer_0(callid, rc);
    121                                                 break;
    122                                         }
    123                                         free(buffer);
    124                                 }
    125                                 printf("%s: << Received %uB long buffer (handle %d).\n",
    126                                     NAME, len, IPC_GET_ARG1(call));
    127                                 ipc_answer_0(callid, EOK);
    128                                 break;
    129                                
    130                         case IPC_M_PHONE_HUNGUP:
    131                                 //printf("%s: hang-up.\n", NAME);
    132                                 return;
    133                                
    134                         default:
    135                                 printf("%s: method %d called.\n", NAME, IPC_GET_METHOD(call));
    136                                 ipc_answer_0(callid, EOK);
    137                                 break;
    138                 }
    139         }
    140 }
    141 
    14284static void data_dump(uint8_t *data, size_t len)
    14385{
     
    15496int main(int argc, char * argv[])
    15597{
    156         int hcd_phone = usb_hcd_create_phones(DEV_HCD_NAME, client_connection);
     98        int hcd_phone = usb_hcd_connect(DEV_HCD_NAME);
    15799        if (hcd_phone < 0) {
    158100                printf("%s: Unable to start comunication with HCD at usb://%s (%d: %s).\n",
     
    233175       
    234176        fibril_sleep(1);
    235        
    236 #if 0
    237         int rc;
    238        
    239         printf("%s: usb_hcd_transfer_control_write_setup(...)\n", NAME);
    240         rc = usb_hcd_transfer_control_write_setup(hcd_phone, target,
    241             &setup_packet, sizeof(setup_packet), NULL);
    242         if (rc != EOK) {
    243                 printf("%s: failed setting address (%d).\n", NAME, rc);
    244                 return rc;
    245         }
    246        
    247         printf("%s: usb_hcd_transfer_control_write_status(...)\n", NAME);
    248         rc = usb_hcd_transfer_control_write_status(hcd_phone, target, NULL);
    249         if (rc != EOK) {
    250                 printf("%s: failed completing control transfer (%d).\n", NAME, rc);
    251                 return rc;
    252         }
    253        
    254         printf("%s: sleeping for a while...\n", NAME);
    255         fibril_sleep(5);
    256 #endif
    257177
    258178        printf("%s: exiting.\n", NAME);
  • uspace/app/virtusbkbd/virtusbkbd.c

    raf894a21 r1d1f894  
    5858#define NAME "virt-usb-kbd"
    5959
    60 #define DEV_HCD_NAME "hcd-virt"
     60#define DEV_HCD_NAME "hcd-virt-dev"
    6161
    6262#define __QUOTEME(x) #x
  • uspace/lib/usb/hcd.c

    raf894a21 r1d1f894  
    9090}
    9191
    92 /** Create necessary phones for comunicating with HCD.
     92/** Create necessary phones for communicating with HCD.
    9393 * This function wraps following calls:
    9494 * -# open <code>/dev/usb/<i>hcd_path</i></code> for reading
    9595 * -# access phone of file opened in previous step
    96  * -# create callback through just opened phone
    97  * -# set handler for this callback
    9896 * -# return the (outgoing) phone
    9997 *
    10098 * @warning This function is wrapper for several actions and therefore
    10199 * it is not possible - in case of error - to determine at which point
    102  * error occured.
     100 * error occurred.
    103101 *
    104102 * @param hcd_path HCD identification under devfs
    105103 *     (without <code>/dev/usb/</code>).
    106  * @param callback_connection Handler for callbacks from HCD.
    107  * @return Phone for comunicating with HCD or error code from errno.h.
    108  */
    109 int usb_hcd_create_phones(const char * hcd_path,
    110     async_client_conn_t callback_connection)
     104 * @return Phone for communicating with HCD or error code from errno.h.
     105 */
     106int usb_hcd_connect(const char * hcd_path)
    111107{
    112108        char dev_path[DEVMAP_NAME_MAXLEN + 1];
     
    124120                return hcd_phone;
    125121        }
    126        
    127         ipcarg_t phonehash;
    128         int rc = ipc_connect_to_me(hcd_phone, 0, 0, 0, &phonehash);
    129         if (rc != EOK) {
    130                 return rc;
    131         }
    132         async_new_connection(phonehash, 0, NULL, callback_connection);
    133        
     122
    134123        return hcd_phone;
    135124}
    136 
    137 /** Send data from USB host to a function.
    138  *
    139  * @param hcd_phone Connected phone to HCD.
    140  * @param target USB function address.
    141  * @param transfer_type USB transfer type.
    142  * @param buffer Buffer with data to be sent.
    143  * @param len Buffer @p buffer size.
    144  * @param[out] transaction_handle Handle of created transaction (NULL to ignore).
    145  * @return Error status.
    146  * @retval EOK Everything OK, buffer transfered to HCD and queued there.
    147  * @retval EINVAL Invalid phone.
    148  * @retval EINVAL @p buffer is NULL.
    149  */
    150 int usb_hcd_send_data_to_function(int hcd_phone,
    151     usb_target_t target, usb_transfer_type_t transfer_type,
    152     void * buffer, size_t len,
    153     usb_transaction_handle_t * transaction_handle)
    154 {
    155         if (hcd_phone < 0) {
    156                 return EINVAL;
    157         }
    158         if (buffer == NULL) {
    159                 return EINVAL;
    160         }
    161 
    162         ipc_call_t answer_data;
    163         ipcarg_t answer_rc;
    164         aid_t req;
    165         int rc;
    166        
    167         req = async_send_4(hcd_phone,
    168             IPC_M_USB_HCD_SEND_DATA,
    169             target.address, target.endpoint,
    170             transfer_type, 0,
    171             &answer_data);
    172        
    173         rc = async_data_write_start(hcd_phone, buffer, len);
    174         if (rc != EOK) {
    175                 async_wait_for(req, NULL);
    176                 return rc;
    177         }
    178        
    179         async_wait_for(req, &answer_rc);
    180         rc = (int)answer_rc;
    181         if (rc != EOK) {
    182                 return rc;
    183         }
    184        
    185         if (transaction_handle != NULL) {
    186                 *transaction_handle = IPC_GET_ARG1(answer_data);
    187         }
    188        
    189         return EOK;
    190 }
    191 
    192 
    193 /** Inform HCD about data reception.
    194  * The actual reception is handled in callback.
    195  *
    196  * @param hcd_phone Connected phone to HCD.
    197  * @param target USB function address.
    198  * @param transfer_type USB transfer type.
    199  * @param len Maximum accepted packet size.
    200  * @param[out] transaction_handle Handle of created transaction (NULL to ignore).
    201  * @return Error status.
    202  */
    203 int usb_hcd_prepare_data_reception(int hcd_phone,
    204     usb_target_t target, usb_transfer_type_t transfer_type,
    205     size_t len,
    206     usb_transaction_handle_t * transaction_handle)
    207 {
    208         if (hcd_phone < 0) {
    209                 return EINVAL;
    210         }
    211        
    212         usb_transaction_handle_t handle;
    213        
    214         int rc = ipc_call_sync_5_1(hcd_phone, IPC_M_USB_HCD_RECEIVE_DATA,
    215             target.address, target.endpoint,
    216             transfer_type, len, 0, &handle);
    217        
    218         if (rc != EOK) {
    219                 return rc;
    220         }
    221        
    222         if (transaction_handle != NULL) {
    223                 *transaction_handle = handle;
    224         }
    225        
    226         return EOK;
    227 }
    228 
    229 
    230 static int send_buffer(int phone, ipcarg_t method, usb_target_t target,
    231     void *buffer, size_t size, usb_transaction_handle_t * transaction_handle)
    232 {
    233         if (phone < 0) {
    234                 return EINVAL;
    235         }
    236        
    237         if ((buffer == NULL) && (size > 0)) {
    238                 return EINVAL;
    239         }
    240 
    241         ipc_call_t answer_data;
    242         ipcarg_t answer_rc;
    243         aid_t req;
    244         int rc;
    245        
    246         req = async_send_3(phone,
    247             method,
    248             target.address, target.endpoint,
    249             size,
    250             &answer_data);
    251        
    252         if (size > 0) {
    253                 rc = async_data_write_start(phone, buffer, size);
    254                 if (rc != EOK) {
    255                         async_wait_for(req, NULL);
    256                         return rc;
    257                 }
    258         }
    259        
    260         async_wait_for(req, &answer_rc);
    261         rc = (int)answer_rc;
    262         if (rc != EOK) {
    263                 return rc;
    264         }
    265        
    266         if (transaction_handle != NULL) {
    267                 *transaction_handle = IPC_GET_ARG1(answer_data);
    268         }
    269        
    270         return EOK;
    271 }
    272 
    273 
    274 static int prep_receive_data(int phone, ipcarg_t method, usb_target_t target,
    275     size_t size, usb_transaction_handle_t * transaction_handle)
    276 {
    277         if (phone < 0) {
    278                 return EINVAL;
    279         }
    280        
    281         usb_transaction_handle_t handle;
    282        
    283         int rc = ipc_call_sync_3_1(phone,
    284             method,
    285             target.address, target.endpoint,
    286             size,
    287             &handle);
    288        
    289         if (rc != EOK) {
    290                 return rc;
    291         }
    292        
    293         if (transaction_handle != NULL) {
    294                 *transaction_handle = handle;
    295         }
    296        
    297         return EOK;
    298 }
    299 
    300 
    301 int usb_hcd_transfer_interrupt_out(int hcd_phone, usb_target_t target,
    302     void *buffer, size_t size, usb_transaction_handle_t *handle)
    303 {
    304         return send_buffer(hcd_phone, IPC_M_USB_HCD_INTERRUPT_OUT,
    305             target, buffer, size, handle);
    306 }
    307 
    308 int usb_hcd_transfer_interrupt_in(int hcd_phone, usb_target_t target,
    309     size_t size, usb_transaction_handle_t *handle)
    310 {
    311         return prep_receive_data(hcd_phone, IPC_M_USB_HCD_INTERRUPT_IN,
    312             target, size, handle);
    313 }
    314 
    315 int usb_hcd_transfer_control_write_setup(int hcd_phone, usb_target_t target,
    316     void *buffer, size_t size, usb_transaction_handle_t *handle)
    317 {
    318         return send_buffer(hcd_phone, IPC_M_USB_HCD_CONTROL_WRITE_SETUP,
    319             target, buffer, size, handle);
    320 }
    321 
    322 int usb_hcd_transfer_control_write_data(int hcd_phone, usb_target_t target,
    323     void *buffer, size_t size, usb_transaction_handle_t *handle)
    324 {
    325         return send_buffer(hcd_phone, IPC_M_USB_HCD_CONTROL_WRITE_DATA,
    326             target, buffer, size, handle);
    327        
    328 }
    329 int usb_hcd_transfer_control_write_status(int hcd_phone, usb_target_t target,
    330     usb_transaction_handle_t *handle)
    331 {
    332         return prep_receive_data(hcd_phone, IPC_M_USB_HCD_CONTROL_WRITE_STATUS,
    333             target, 0, handle);
    334 }
    335 
    336 int usb_hcd_transfer_control_read_setup(int hcd_phone, usb_target_t target,
    337     void *buffer, size_t size, usb_transaction_handle_t *handle)
    338 {
    339         return send_buffer(hcd_phone, IPC_M_USB_HCD_CONTROL_READ_SETUP,
    340             target, buffer, size, handle);
    341 }
    342 int usb_hcd_transfer_control_read_data(int hcd_phone, usb_target_t target,
    343     size_t size, usb_transaction_handle_t *handle)
    344 {
    345         return prep_receive_data(hcd_phone, IPC_M_USB_HCD_CONTROL_READ_DATA,
    346            target, size, handle);
    347 }
    348 int usb_hcd_transfer_control_read_status(int hcd_phone, usb_target_t target,
    349     usb_transaction_handle_t *handle)
    350 {
    351         return send_buffer(hcd_phone, IPC_M_USB_HCD_CONTROL_READ_STATUS,
    352             target, NULL, 0, handle);
    353 }
    354 
    355 
    356 
    357 
    358 
    359 /*
    360  * =================
    361  * async versions of the above functions
    362  * =================
    363  */
    364125
    365126/** Send data to HCD.
  • uspace/lib/usb/hcd.h

    raf894a21 r1d1f894  
    133133 * OUT transactions buffers can be freed immediatelly after call is dispatched
    134134 * (i.e. after return from wrapping function).
    135  *
    136  * Async methods for retrieving data from device:
    137  */
    138 typedef enum {
    139         /** Send data over USB to a function.
    140          * This method initializes large data transfer that must follow
    141          * immediatelly.
    142          * The recipient of this method must issue immediately data reception
    143          * and answer this call after data buffer was transfered.
    144          *
    145          * Arguments of the call:
    146          * - USB address of the function
    147          * - endpoint of the function
    148          * - transfer type
    149          * - flags (not used)
    150          *
    151          * Answer:
    152          * - EOK - ready to accept the data buffer
    153          * - ELIMIT - too many transactions for current connection
    154          * - ENOENT - callback connection does not exist
    155          * - EINVAL - other kind of error
    156          *
    157          * Arguments of the answer:
    158          * - opaque transaction handle (used in callbacks)
    159          */
    160         IPC_M_USB_HCD_SEND_DATA = IPC_FIRST_USER_METHOD,
    161        
    162         /** Initiate data receive from a function.
    163          * This method announces the HCD that some data will come.
    164          * When this data arrives, the HCD will call back with
    165          * IPC_M_USB_HCD_DATA_RECEIVED.
    166          *
    167          * Arguments of the call:
    168          * - USB address of the function
    169          * - endpoint of the function
    170          * - transfer type
    171          * - buffer size
    172          * - flags (not used)
    173          *
    174          * Answer:
    175          * - EOK - HCD accepted the request
    176          * - ELIMIT - too many transactions for current connection
    177          * - ENOENT - callback connection does not exist
    178          *
    179          * Arguments of the answer:
    180          * - opaque transaction handle (used in callbacks)
    181          */
    182         IPC_M_USB_HCD_RECEIVE_DATA,
    183        
     135 *
     136 */
     137typedef enum {
    184138        /** Tell maximum size of the transaction buffer (payload).
    185139         *
     
    193147         * - buffer size (in bytes):
    194148         */
    195         IPC_M_USB_HCD_TRANSACTION_SIZE,
    196        
    197        
    198         IPC_M_USB_HCD_INTERRUPT_OUT,
    199         IPC_M_USB_HCD_INTERRUPT_IN,
    200        
    201         IPC_M_USB_HCD_CONTROL_WRITE_SETUP,
    202         IPC_M_USB_HCD_CONTROL_WRITE_DATA,
    203         IPC_M_USB_HCD_CONTROL_WRITE_STATUS,
    204        
    205         IPC_M_USB_HCD_CONTROL_READ_SETUP,
    206         IPC_M_USB_HCD_CONTROL_READ_DATA,
    207         IPC_M_USB_HCD_CONTROL_READ_STATUS,
    208        
    209         /* async methods */
     149        IPC_M_USB_HCD_TRANSACTION_SIZE = IPC_FIRST_USER_METHOD,
    210150       
    211151        /** Asks for data buffer.
     
    293233
    294234
    295 int usb_hcd_create_phones(const char *, async_client_conn_t);
    296 int usb_hcd_send_data_to_function(int, usb_target_t, usb_transfer_type_t,
    297     void *, size_t, usb_transaction_handle_t *);
    298 int usb_hcd_prepare_data_reception(int, usb_target_t, usb_transfer_type_t,
    299     size_t, usb_transaction_handle_t *);
    300 
    301 
    302 int usb_hcd_transfer_interrupt_out(int, usb_target_t,
    303     void *, size_t, usb_transaction_handle_t *);
    304 int usb_hcd_transfer_interrupt_in(int, usb_target_t,
    305     size_t, usb_transaction_handle_t *);
    306 
    307 int usb_hcd_transfer_control_write_setup(int, usb_target_t,
    308     void *, size_t, usb_transaction_handle_t *);
    309 int usb_hcd_transfer_control_write_data(int, usb_target_t,
    310     void *, size_t, usb_transaction_handle_t *);
    311 int usb_hcd_transfer_control_write_status(int, usb_target_t,
    312     usb_transaction_handle_t *);
    313 
    314 int usb_hcd_transfer_control_read_setup(int, usb_target_t,
    315     void *, size_t, usb_transaction_handle_t *);
    316 int usb_hcd_transfer_control_read_data(int, usb_target_t,
    317     size_t, usb_transaction_handle_t *);
    318 int usb_hcd_transfer_control_read_status(int, usb_target_t,
    319     usb_transaction_handle_t *);
     235int usb_hcd_connect(const char *);
    320236
    321237int usb_hcd_async_transfer_interrupt_out(int, usb_target_t,
  • uspace/lib/usbvirt/main.c

    raf894a21 r1d1f894  
    225225       
    226226        ipcarg_t phonehash;
    227         int rc = ipc_connect_to_me(hcd_phone, 1, 0, 0, &phonehash);
     227        int rc = ipc_connect_to_me(hcd_phone, 0, 0, 0, &phonehash);
    228228        if (rc != EOK) {
    229229                return rc;
  • uspace/srv/hw/bus/usb/hcd/virtual/conn.h

    raf894a21 r1d1f894  
    4040#include "devices.h"
    4141
    42 void connection_handler_host(ipcarg_t, int);
     42void connection_handler_host(ipcarg_t);
    4343void connection_handler_device(ipcarg_t, virtdev_connection_t *);
    4444
  • uspace/srv/hw/bus/usb/hcd/virtual/connhost.c

    raf894a21 r1d1f894  
    4141#include "hc.h"
    4242
    43 static usb_transaction_handle_t g_handle_seed = 1;
    44 static usb_transaction_handle_t create_transaction_handle(int phone)
    45 {
    46         return g_handle_seed++;
    47 }
    48 
    4943typedef struct {
    50         int phone;
    51         usb_transaction_handle_t handle;
    52 } transaction_details_t;
    53 
    54 
    55 /** Callback for outgoing transaction.
    56  */
    57 static void out_callback(void * buffer, size_t len, usb_transaction_outcome_t outcome, void * arg)
    58 {
    59         dprintf(2, "out_callback(buffer, %u, %d, %p)", len, outcome, arg);
    60        
    61         transaction_details_t * trans = (transaction_details_t *)arg;
    62        
    63         async_msg_2(trans->phone, IPC_M_USB_HCD_DATA_SENT, trans->handle, outcome);
     44        ipc_callid_t caller;
     45        void *buffer;
     46        size_t size;
     47} async_transaction_t;
     48
     49static void async_out_callback(void * buffer, size_t len,
     50    usb_transaction_outcome_t outcome, void * arg)
     51{
     52        async_transaction_t * trans = (async_transaction_t *)arg;
     53       
     54        dprintf(2, "async_out_callback(buffer, %u, %d, %p) -> %x",
     55            len, outcome, arg, trans->caller);
     56       
     57        // FIXME - answer according to outcome
     58        ipc_answer_1(trans->caller, EOK, 0);
    6459       
    6560        free(trans);
     
    6762                free(buffer);
    6863        }
    69 }
    70 
    71 /** Callback for incoming transaction.
    72  */
    73 static void in_callback(void * buffer, size_t len, usb_transaction_outcome_t outcome, void * arg)
    74 {
    75         dprintf(2, "in_callback(buffer, %u, %d, %p)", len, outcome, arg);
    76         transaction_details_t * trans = (transaction_details_t *)arg;
    77        
    78         ipc_call_t answer_data;
    79         ipcarg_t answer_rc;
    80         aid_t req;
    81         int rc;
    82        
    83         req = async_send_3(trans->phone,
    84             IPC_M_USB_HCD_DATA_RECEIVED,
    85             trans->handle, outcome,
    86             len,
    87             &answer_data);
    88        
    89         if (len > 0) {
    90                 rc = async_data_write_start(trans->phone, buffer, len);
    91                 if (rc != EOK) {
    92                         async_wait_for(req, NULL);
    93                         goto leave;
    94                 }
    95         }
    96        
    97         async_wait_for(req, &answer_rc);
    98         rc = (int)answer_rc;
    99         if (rc != EOK) {
    100                 goto leave;
    101         }
    102        
    103 leave:
    104         free(trans);
    105         if (buffer != NULL) {
    106                 free(buffer);
    107         }
    108 }
    109 
    110 /** Handle data from host to function.
    111  */
    112 static void handle_data_to_function(ipc_callid_t iid, ipc_call_t icall,
    113     bool setup_transaction, int callback_phone)
     64        dprintf(4, "async_out_callback answered");
     65}
     66
     67static void async_to_device(ipc_callid_t iid, ipc_call_t icall, bool setup_transaction)
    11468{
    11569        size_t expected_len = IPC_GET_ARG3(icall);
     
    11973        };
    12074       
    121         dprintf(1, "pretending transfer to function (dev=%d:%d)",
    122             target.address, target.endpoint);
    123        
    124         if (callback_phone == -1) {
    125                 ipc_answer_0(iid, ENOENT);
    126                 return;
    127         }
    128        
    129         usb_transaction_handle_t handle
    130             = create_transaction_handle(callback_phone);
     75        dprintf(1, "async_to_device: dev=%d:%d, size=%d, iid=%x",
     76            target.address, target.endpoint, expected_len, iid);
    13177       
    13278        size_t len = 0;
     
    14389        }
    14490       
    145         transaction_details_t * trans = malloc(sizeof(transaction_details_t));
    146         trans->phone = callback_phone;
    147         trans->handle = handle;
     91        async_transaction_t * trans = malloc(sizeof(async_transaction_t));
     92        trans->caller = iid;
     93        trans->buffer = NULL;
     94        trans->size = 0;
    14895       
    14996        hc_add_transaction_to_device(setup_transaction, target,
    15097            buffer, len,
    151             out_callback, trans);
    152        
    153         ipc_answer_1(iid, EOK, handle);
    154         dprintf(2, "transfer to function scheduled (handle %d)", handle);
    155 }
    156 
    157 /** Handle data from function to host.
    158  */
    159 static void handle_data_from_function(ipc_callid_t iid, ipc_call_t icall, int callback_phone)
     98            async_out_callback, trans);
     99       
     100        dprintf(2, "async transaction to device scheduled (%p)", trans);
     101}
     102
     103static void async_in_callback(void * buffer, size_t len,
     104    usb_transaction_outcome_t outcome, void * arg)
     105{       
     106        async_transaction_t * trans = (async_transaction_t *)arg;
     107       
     108        dprintf(2, "async_in_callback(buffer, %u, %d, %p) -> %x",
     109            len, outcome, arg, trans->caller);
     110       
     111        trans->buffer = buffer;
     112        trans->size = len;
     113       
     114        ipc_callid_t caller = trans->caller;
     115       
     116        if (buffer == NULL) {
     117                free(trans);
     118                trans = NULL;
     119        }
     120       
     121       
     122        // FIXME - answer according to outcome
     123        ipc_answer_1(caller, EOK, (ipcarg_t)trans);
     124        dprintf(4, "async_in_callback answered (%#x)", (ipcarg_t)trans);
     125}
     126
     127static void async_from_device(ipc_callid_t iid, ipc_call_t icall)
    160128{
    161129        usb_target_t target = {
     
    165133        size_t len = IPC_GET_ARG3(icall);
    166134       
    167         dprintf(1, "pretending transfer from function (dev=%d:%d)",
    168             target.address, target.endpoint);
    169        
    170         if (callback_phone == -1) {
    171                 ipc_answer_0(iid, ENOENT);
    172                 return;
    173         }
    174        
    175         usb_transaction_handle_t handle
    176             = create_transaction_handle(callback_phone);
    177        
    178         void * buffer = NULL;
    179         if (len > 0) {
    180                 buffer = malloc(len);
    181         }
    182        
    183         transaction_details_t * trans = malloc(sizeof(transaction_details_t));
    184         trans->phone = callback_phone;
    185         trans->handle = handle;
    186        
    187         hc_add_transaction_from_device(target,
    188             buffer, len,
    189             in_callback, trans);
    190        
    191         ipc_answer_1(iid, EOK, handle);
    192         dprintf(2, "transfer from function scheduled (handle %d)", handle);
    193 }
    194 
    195 
    196 typedef struct {
    197         ipc_callid_t caller;
    198         void *buffer;
    199         size_t size;
    200 } async_transaction_t;
    201 
    202 static void async_out_callback(void * buffer, size_t len,
    203     usb_transaction_outcome_t outcome, void * arg)
    204 {
    205         async_transaction_t * trans = (async_transaction_t *)arg;
    206        
    207         dprintf(2, "async_out_callback(buffer, %u, %d, %p) -> %x",
    208             len, outcome, arg, trans->caller);
    209        
    210         // FIXME - answer according to outcome
    211         ipc_answer_1(trans->caller, EOK, 0);
    212        
    213         free(trans);
    214         if (buffer) {
    215                 free(buffer);
    216         }
    217         dprintf(4, "async_out_callback answered");
    218 }
    219 
    220 static void async_to_device(ipc_callid_t iid, ipc_call_t icall, bool setup_transaction)
    221 {
    222         size_t expected_len = IPC_GET_ARG3(icall);
    223         usb_target_t target = {
    224                 .address = IPC_GET_ARG1(icall),
    225                 .endpoint = IPC_GET_ARG2(icall)
    226         };
    227        
    228         dprintf(1, "async_to_device: dev=%d:%d, size=%d, iid=%x",
    229             target.address, target.endpoint, expected_len, iid);
    230        
    231         size_t len = 0;
    232         void * buffer = NULL;
    233         if (expected_len > 0) {
    234                 int rc = async_data_write_accept(&buffer, false,
    235                     1, USB_MAX_PAYLOAD_SIZE,
    236                     0, &len);
    237                
    238                 if (rc != EOK) {
    239                         ipc_answer_0(iid, rc);
    240                         return;
    241                 }
    242         }
    243        
    244         async_transaction_t * trans = malloc(sizeof(async_transaction_t));
    245         trans->caller = iid;
    246         trans->buffer = NULL;
    247         trans->size = 0;
    248        
    249         hc_add_transaction_to_device(setup_transaction, target,
    250             buffer, len,
    251             async_out_callback, trans);
    252        
    253         dprintf(2, "async transaction to device scheduled (%p)", trans);
    254 }
    255 
    256 static void async_in_callback(void * buffer, size_t len,
    257     usb_transaction_outcome_t outcome, void * arg)
    258 {       
    259         async_transaction_t * trans = (async_transaction_t *)arg;
    260        
    261         dprintf(2, "async_in_callback(buffer, %u, %d, %p) -> %x",
    262             len, outcome, arg, trans->caller);
    263        
    264         trans->buffer = buffer;
    265         trans->size = len;
    266        
    267         ipc_callid_t caller = trans->caller;
    268        
    269         if (buffer == NULL) {
    270                 free(trans);
    271                 trans = NULL;
    272         }
    273        
    274        
    275         // FIXME - answer according to outcome
    276         ipc_answer_1(caller, EOK, (ipcarg_t)trans);
    277         dprintf(4, "async_in_callback answered (%#x)", (ipcarg_t)trans);
    278 }
    279 
    280 static void async_from_device(ipc_callid_t iid, ipc_call_t icall)
    281 {
    282         usb_target_t target = {
    283                 .address = IPC_GET_ARG1(icall),
    284                 .endpoint = IPC_GET_ARG2(icall)
    285         };
    286         size_t len = IPC_GET_ARG3(icall);
    287        
    288135        dprintf(1, "async_from_device: dev=%d:%d, size=%d, iid=%x",
    289136            target.address, target.endpoint, len, iid);
     
    345192 *
    346193 * @param phone_hash Incoming phone hash.
    347  * @param host_phone Callback phone to host.
    348  */
    349 void connection_handler_host(ipcarg_t phone_hash, int host_phone)
    350 {
    351         assert(host_phone > 0);
    352        
     194 */
     195void connection_handler_host(ipcarg_t phone_hash)
     196{
    353197        dprintf(0, "host connected through phone %#x", phone_hash);
    354198       
     
    368212               
    369213                switch (IPC_GET_METHOD(call)) {
     214
     215                        /* standard IPC methods */
     216
    370217                        case IPC_M_PHONE_HUNGUP:
    371                                 ipc_hangup(host_phone);
    372218                                ipc_answer_0(callid, EOK);
    373219                                dprintf(0, "phone%#x: host hung-up",
     
    379225                                break;
    380226                       
     227
     228                        /* USB methods */
     229
    381230                        case IPC_M_USB_HCD_TRANSACTION_SIZE:
    382231                                ipc_answer_1(callid, EOK, USB_MAX_PAYLOAD_SIZE);
    383232                                break;
    384                        
    385                         /* callback-result methods */
    386                        
    387                         case IPC_M_USB_HCD_INTERRUPT_OUT:
    388                                 handle_data_to_function(callid, call,
    389                                     false, host_phone);
    390                                 break;
    391                                
    392                         case IPC_M_USB_HCD_INTERRUPT_IN:
    393                                 handle_data_from_function(callid, call, host_phone);
    394                                 break;
    395                        
    396                         case IPC_M_USB_HCD_CONTROL_WRITE_SETUP:
    397                                 handle_data_to_function(callid, call,
    398                                     true, host_phone);
    399                                 break;
    400                                
    401                         case IPC_M_USB_HCD_CONTROL_WRITE_DATA:
    402                                 handle_data_to_function(callid, call,
    403                                     false, host_phone);
    404                                 break;
    405                                
    406                         case IPC_M_USB_HCD_CONTROL_WRITE_STATUS:
    407                                 handle_data_from_function(callid, call, host_phone);
    408                                 break;
    409                        
    410                         case IPC_M_USB_HCD_CONTROL_READ_SETUP:
    411                                 handle_data_to_function(callid, call,
    412                                     true, host_phone);
    413                                 break;
    414                        
    415                         /* async methods */
    416233                       
    417234                        case IPC_M_USB_HCD_GET_BUFFER_ASYNC:
     
    436253                                break;
    437254                       
     255
    438256                        /* end of known methods */
    439257                       
  • uspace/srv/hw/bus/usb/hcd/virtual/hcd.c

    raf894a21 r1d1f894  
    5252
    5353
     54static dev_handle_t handle_virtual_device;
     55static dev_handle_t handle_host_driver;
     56
    5457static void client_connection(ipc_callid_t iid, ipc_call_t *icall)
    5558{
    5659        ipcarg_t phone_hash = icall->in_phone_hash;
     60        dev_handle_t handle = (dev_handle_t)IPC_GET_ARG1(*icall);
    5761       
    58         ipc_answer_0(iid, EOK);
    59        
    60         while (true) {
    61                 ipc_callid_t callid;
    62                 ipc_call_t call;
    63                
    64                 callid = async_get_call(&call);
    65                
     62        if (handle == handle_host_driver) {
    6663                /*
    67                  * We can do nothing until we have the callback phone.
    68                  * Thus, we will wait for the callback and start processing
    69                  * after that.
     64                 * We can connect host controller driver immediately.
    7065                 */
    71                 int method = (int) IPC_GET_METHOD(call);
    72                
    73                 if (method == IPC_M_PHONE_HUNGUP) {
    74                         ipc_answer_0(callid, EOK);
    75                         return;
    76                 }
    77                
    78                 if (method == IPC_M_CONNECT_TO_ME) {
    79                         int kind = IPC_GET_ARG1(call);
    80                         int callback = IPC_GET_ARG5(call);
    81                        
     66                ipc_answer_0(iid, EOK);
     67                connection_handler_host(phone_hash);
     68        } else if (handle == handle_virtual_device) {
     69                ipc_answer_0(iid, EOK);
     70
     71                while (true) {
    8272                        /*
    83                          * Determine whether host connected to us
    84                          * or a device.
     73                         * We need to wait for callback request to allow
     74                         * connection of virtual device.
    8575                         */
    86                         if (kind == 0) {
     76                        ipc_callid_t callid;
     77                        ipc_call_t call;
     78
     79                        callid = async_get_call(&call);
     80
     81                        /*
     82                         * We can do nothing until we have the callback phone.
     83                         * Thus, we will wait for the callback and start processing
     84                         * after that.
     85                         */
     86                        int method = (int) IPC_GET_METHOD(call);
     87
     88                        if (method == IPC_M_PHONE_HUNGUP) {
    8789                                ipc_answer_0(callid, EOK);
    88                                 connection_handler_host(phone_hash, callback);
    8990                                return;
    90                         } else if (kind == 1) {
     91                        }
     92
     93                        if (method == IPC_M_CONNECT_TO_ME) {
     94                                int callback = IPC_GET_ARG5(call);
    9195                                virtdev_connection_t *dev
    9296                                    = virtdev_add_device(callback);
     
    100104                                virtdev_destroy_device(dev);
    101105                                return;
    102                         } else {
    103                                 ipc_answer_0(callid, EINVAL);
    104                                 ipc_hangup(callback);
    105                                 return;
    106106                        }
     107
     108                        /*
     109                         * No other methods could be served now.
     110                         */
     111                        dprintf_inval_call(1, call, phone_hash);
     112                        ipc_answer_0(callid, ENOTSUP);
    107113                }
    108                
     114        } else {
    109115                /*
    110                  * No other methods could be served now.
     116                 * Hmmm, someone else just tried to connect to us.
     117                 * Kick him out ;-).
    111118                 */
    112                 dprintf_inval_call(1, call, phone_hash);
    113                 ipc_answer_0(callid, ENOTSUP);
     119                ipc_answer_0(iid, ENOTSUP);
     120                return;
    114121        }
    115122}
     
    135142        }
    136143
    137         rc = devmap_device_register(DEVMAP_PATH, NULL);
     144        rc = devmap_device_register(DEVMAP_PATH_HC, &handle_host_driver);
    138145        if (rc != EOK) {
    139146                printf("%s: unable to register device %s (%s).\n",
    140                     NAME, DEVMAP_PATH, str_error(rc));
     147                    NAME, DEVMAP_PATH_HC, str_error(rc));
    141148                return 1;
    142149        }
    143150       
     151        rc = devmap_device_register(DEVMAP_PATH_DEV, &handle_virtual_device);
     152        if (rc != EOK) {
     153                printf("%s: unable to register device %s (%s).\n",
     154                    NAME, DEVMAP_PATH_DEV, str_error(rc));
     155                return 1;
     156        }
     157
    144158        hub_init();
    145159       
    146         printf("%s: accepting connections [devmap=%s, debug=%d].\n", NAME,
    147             DEVMAP_PATH, debug_level);
     160        printf("%s: accepting connections [debug=%d]\n", NAME, debug_level);
     161        printf("%s:  -> host controller at %s\n", NAME, DEVMAP_PATH_HC);
     162        printf("%s:  -> virtual hub at %s\n", NAME, DEVMAP_PATH_DEV);
     163
    148164        hc_manager();
    149165       
  • uspace/srv/hw/bus/usb/hcd/virtual/vhcd.h

    raf894a21 r1d1f894  
    3737
    3838#define NAME "hcd-virt"
     39#define NAME_DEV "hcd-virt-dev"
    3940#define NAMESPACE "usb"
    4041
    41 #define DEVMAP_PATH NAMESPACE "/" NAME
     42#define DEVMAP_PATH_HC NAMESPACE "/" NAME
     43#define DEVMAP_PATH_DEV NAMESPACE "/" NAME_DEV
    4244
    4345extern int debug_level;
Note: See TracChangeset for help on using the changeset viewer.