Ignore:
File:
1 edited

Legend:

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

    ref9460b r26fa82bc  
    139139find_interrupt_context_by_id(interrupt_context_list_t *list, int id)
    140140{
     141        fibril_mutex_lock(&list->mutex);
     142       
     143        link_t *link = list->contexts.next;
    141144        interrupt_context_t *ctx;
    142145       
    143         fibril_mutex_lock(&list->mutex);
    144        
    145         list_foreach(list->contexts, link) {
     146        while (link != &list->contexts) {
    146147                ctx = list_get_instance(link, interrupt_context_t, link);
    147148                if (ctx->id == id) {
     
    149150                        return ctx;
    150151                }
     152                link = link->next;
    151153        }
    152154       
     
    158160find_interrupt_context(interrupt_context_list_t *list, ddf_dev_t *dev, int irq)
    159161{
     162        fibril_mutex_lock(&list->mutex);
     163       
     164        link_t *link = list->contexts.next;
    160165        interrupt_context_t *ctx;
    161166       
    162         fibril_mutex_lock(&list->mutex);
    163        
    164         list_foreach(list->contexts, link) {
     167        while (link != &list->contexts) {
    165168                ctx = list_get_instance(link, interrupt_context_t, link);
    166169                if (ctx->irq == irq && ctx->dev == dev) {
     
    168171                        return ctx;
    169172                }
     173                link = link->next;
    170174        }
    171175       
     
    227231}
    228232
    229 static ddf_fun_t *driver_get_function(list_t *functions, devman_handle_t handle)
     233static ddf_fun_t *driver_get_function(link_t *functions, devman_handle_t handle)
    230234{
    231235        ddf_fun_t *fun = NULL;
    232236       
    233237        fibril_mutex_lock(&functions_mutex);
    234        
    235         list_foreach(*functions, link) {
     238        link_t *link = functions->next;
     239       
     240        while (link != functions) {
    236241                fun = list_get_instance(link, ddf_fun_t, link);
    237242                if (fun->handle == handle) {
     
    239244                        return fun;
    240245                }
     246               
     247                link = link->next;
    241248        }
    242249       
     
    278285        async_answer_0(iid, EOK);
    279286       
    280         while (true) {
     287        bool cont = true;
     288        while (cont) {
    281289                ipc_call_t call;
    282290                ipc_callid_t callid = async_get_call(&call);
    283291               
    284                 if (!IPC_GET_IMETHOD(call))
    285                         break;
    286                
    287292                switch (IPC_GET_IMETHOD(call)) {
     293                case IPC_M_PHONE_HUNGUP:
     294                        cont = false;
     295                        continue;
    288296                case DRIVER_ADD_DEVICE:
    289297                        driver_add_device(callid, &call);
     
    295303}
    296304
    297 /** Generic client connection handler both for applications and drivers.
    298  *
    299  * @param drv True for driver client, false for other clients
    300  *            (applications, services, etc.).
    301  *
     305/**
     306 * Generic client connection handler both for applications and drivers.
     307 *
     308 * @param drv           True for driver client, false for other clients
     309 *                      (applications, services etc.).
    302310 */
    303311static void driver_connection_gen(ipc_callid_t iid, ipc_call_t *icall, bool drv)
     
    309317        devman_handle_t handle = IPC_GET_ARG2(*icall);
    310318        ddf_fun_t *fun = driver_get_function(&functions, handle);
    311        
     319
    312320        if (fun == NULL) {
    313321                printf("%s: driver_connection_gen error - no function with handle"
     
    317325        }
    318326       
    319         if (fun->conn_handler != NULL) {
    320                 /* Driver has a custom connection handler. */
    321                 (*fun->conn_handler)(iid, icall, (void *)fun);
    322                 return;
    323         }
    324327       
    325328        /*
     
    337340                return;
    338341       
    339         while (true) {
     342        while (1) {
    340343                ipc_callid_t callid;
    341344                ipc_call_t call;
    342345                callid = async_get_call(&call);
    343346                sysarg_t method = IPC_GET_IMETHOD(call);
     347                int iface_idx;
    344348               
    345                 if (!method) {
     349                switch  (method) {
     350                case IPC_M_PHONE_HUNGUP:
    346351                        /* Close device function */
    347352                        if (fun->ops != NULL && fun->ops->close != NULL)
     
    349354                        async_answer_0(callid, EOK);
    350355                        return;
    351                 }
    352                
    353                 /* Convert ipc interface id to interface index */
    354                
    355                 int iface_idx = DEV_IFACE_IDX(method);
    356                
    357                 if (!is_valid_iface_idx(iface_idx)) {
    358                         remote_handler_t *default_handler =
    359                             function_get_default_handler(fun);
    360                         if (default_handler != NULL) {
    361                                 (*default_handler)(fun, callid, &call);
    362                                 continue;
     356                default:
     357                        /* convert ipc interface id to interface index */
     358                       
     359                        iface_idx = DEV_IFACE_IDX(method);
     360                       
     361                        if (!is_valid_iface_idx(iface_idx)) {
     362                                remote_handler_t *default_handler =
     363                                    function_get_default_handler(fun);
     364                                if (default_handler != NULL) {
     365                                        (*default_handler)(fun, callid, &call);
     366                                        break;
     367                                }
     368                               
     369                                /*
     370                                 * Function has no such interface and
     371                                 * default handler is not provided.
     372                                 */
     373                                printf("%s: driver_connection_gen error - "
     374                                    "invalid interface id %d.",
     375                                    driver->name, iface_idx);
     376                                async_answer_0(callid, ENOTSUP);
     377                                break;
     378                        }
     379                       
     380                        /* calling one of the function's interfaces */
     381                       
     382                        /* Get the interface ops structure. */
     383                        void *ops = function_get_ops(fun, iface_idx);
     384                        if (ops == NULL) {
     385                                printf("%s: driver_connection_gen error - ",
     386                                    driver->name);
     387                                printf("Function with handle %" PRIun " has no interface "
     388                                    "with id %d.\n", handle, iface_idx);
     389                                async_answer_0(callid, ENOTSUP);
     390                                break;
    363391                        }
    364392                       
    365393                        /*
    366                          * Function has no such interface and
    367                          * default handler is not provided.
     394                         * Get the corresponding interface for remote request
     395                         * handling ("remote interface").
    368396                         */
    369                         printf("%s: driver_connection_gen error - "
    370                             "invalid interface id %d.",
    371                             driver->name, iface_idx);
    372                         async_answer_0(callid, ENOTSUP);
    373                         continue;
     397                        remote_iface_t *rem_iface = get_remote_iface(iface_idx);
     398                        assert(rem_iface != NULL);
     399                       
     400                        /* get the method of the remote interface */
     401                        sysarg_t iface_method_idx = IPC_GET_ARG1(call);
     402                        remote_iface_func_ptr_t iface_method_ptr =
     403                            get_remote_method(rem_iface, iface_method_idx);
     404                        if (iface_method_ptr == NULL) {
     405                                /* The interface has not such method */
     406                                printf("%s: driver_connection_gen error - "
     407                                    "invalid interface method.", driver->name);
     408                                async_answer_0(callid, ENOTSUP);
     409                                break;
     410                        }
     411                       
     412                        /*
     413                         * Call the remote interface's method, which will
     414                         * receive parameters from the remote client and it will
     415                         * pass it to the corresponding local interface method
     416                         * associated with the function by its driver.
     417                         */
     418                        (*iface_method_ptr)(fun, ops, callid, &call);
     419                        break;
    374420                }
    375                
    376                 /* Calling one of the function's interfaces */
    377                
    378                 /* Get the interface ops structure. */
    379                 void *ops = function_get_ops(fun, iface_idx);
    380                 if (ops == NULL) {
    381                         printf("%s: driver_connection_gen error - ", driver->name);
    382                         printf("Function with handle %" PRIun " has no interface "
    383                             "with id %d.\n", handle, iface_idx);
    384                         async_answer_0(callid, ENOTSUP);
    385                         continue;
    386                 }
    387                
    388                 /*
    389                  * Get the corresponding interface for remote request
    390                  * handling ("remote interface").
    391                  */
    392                 remote_iface_t *rem_iface = get_remote_iface(iface_idx);
    393                 assert(rem_iface != NULL);
    394                
    395                 /* get the method of the remote interface */
    396                 sysarg_t iface_method_idx = IPC_GET_ARG1(call);
    397                 remote_iface_func_ptr_t iface_method_ptr =
    398                     get_remote_method(rem_iface, iface_method_idx);
    399                 if (iface_method_ptr == NULL) {
    400                         /* The interface has not such method */
    401                         printf("%s: driver_connection_gen error - "
    402                             "invalid interface method.", driver->name);
    403                         async_answer_0(callid, ENOTSUP);
    404                         continue;
    405                 }
    406                
    407                 /*
    408                  * Call the remote interface's method, which will
    409                  * receive parameters from the remote client and it will
    410                  * pass it to the corresponding local interface method
    411                  * associated with the function by its driver.
    412                  */
    413                 (*iface_method_ptr)(fun, ops, callid, &call);
    414421        }
    415422}
     
    426433
    427434/** Function for handling connections to device driver. */
    428 static void driver_connection(ipc_callid_t iid, ipc_call_t *icall, void *arg)
     435static void driver_connection(ipc_callid_t iid, ipc_call_t *icall)
    429436{
    430437        /* Select interface */
     
    620627                return ENOMEM;
    621628       
    622         match_id->id = str_dup(match_id_str);
     629        match_id->id = match_id_str;
    623630        match_id->score = 90;
    624631       
Note: See TracChangeset for help on using the changeset viewer.