Ignore:
File:
1 edited

Legend:

Unmodified
Added
Removed
  • uspace/lib/c/generic/loc.c

    rd0dd7b5 rcc574511  
    4545static FIBRIL_MUTEX_INITIALIZE(loc_consumer_mutex);
    4646
    47 static FIBRIL_MUTEX_INITIALIZE(loc_callback_mutex);
    48 static bool loc_callback_created = false;
    49 
    5047static async_sess_t *loc_supp_block_sess = NULL;
    5148static async_sess_t *loc_cons_block_sess = NULL;
     
    5451static async_sess_t *loc_consumer_sess = NULL;
    5552
    56 static loc_cat_change_cb_t cat_change_cb = NULL;
    57 
    58 static void loc_cb_conn(ipc_callid_t iid, ipc_call_t *icall, void *arg)
    59 {
    60         loc_cat_change_cb_t cb_fun;
    61        
    62         while (true) {
    63                 ipc_call_t call;
    64                 ipc_callid_t callid = async_get_call(&call);
    65                
    66                 if (!IPC_GET_IMETHOD(call)) {
    67                         /* TODO: Handle hangup */
    68                         return;
    69                 }
    70                
    71                 int retval;
    72                
    73                 switch (IPC_GET_IMETHOD(call)) {
    74                 case LOC_EVENT_CAT_CHANGE:
    75                         fibril_mutex_lock(&loc_callback_mutex);
    76                         cb_fun = cat_change_cb;
    77                         if (cb_fun != NULL) {
    78                                 (*cb_fun)();
    79                         }
    80                         fibril_mutex_unlock(&loc_callback_mutex);
    81                         retval = 0;
    82                         break;
    83                 default:
    84                         retval = ENOTSUP;
    85                 }
    86                
    87                 async_answer_0(callid, retval);
    88         }
    89 }
    90 
    91 
    9253static void clone_session(fibril_mutex_t *mtx, async_sess_t *src,
    9354    async_sess_t **dst)
     
    9960       
    10061        fibril_mutex_unlock(mtx);
    101 }
    102 
    103 static int loc_callback_create(void)
    104 {
    105         async_exch_t *exch;
    106         sysarg_t retval;
    107         int rc = EOK;
    108 
    109         fibril_mutex_lock(&loc_callback_mutex);
    110        
    111         if (!loc_callback_created) {
    112                 exch = loc_exchange_begin_blocking(LOC_PORT_CONSUMER);
    113                
    114                 ipc_call_t answer;
    115                 aid_t req = async_send_0(exch, LOC_CALLBACK_CREATE, &answer);
    116                 async_connect_to_me(exch, 0, 0, 0, loc_cb_conn, NULL);
    117                 loc_exchange_end(exch);
    118                
    119                 async_wait_for(req, &retval);
    120                 if (rc != EOK)
    121                         goto done;
    122                
    123                 if (retval != EOK) {
    124                         rc = retval;
    125                         goto done;
    126                 }
    127                
    128                 loc_callback_created = true;
    129         }
    130        
    131         rc = EOK;
    132 done:
    133         fibril_mutex_unlock(&loc_callback_mutex);
    134         return rc;
    13562}
    13663
     
    267194}
    268195
    269 /** Register new service.
    270  *
    271  * The @p interface is used when forwarding connection to the server.
     196/** Register new device.
     197 *
     198 * The @p interface is used when forwarding connection to the driver.
    272199 * If not 0, the first argument is the interface and the second argument
    273200 * is the service ID.
     
    276203 * the handle (to ensure backward compatibility).
    277204 *
    278  * @param      fqsn      Fully qualified service name
    279  * @param[out] sid       Service ID of new service
    280  * @param      interface Interface when forwarding
    281  *
    282  */
    283 int loc_service_register_with_iface(const char *fqsn,
    284     service_id_t *sid, sysarg_t interface)
     205 * @param      fqdn      Fully qualified device name.
     206 * @param[out] handle    Handle to the created instance of device.
     207 * @param      interface Interface when forwarding.
     208 *
     209 */
     210int loc_service_register_with_iface(const char *fqdn,
     211    service_id_t *handle, sysarg_t interface)
    285212{
    286213        async_exch_t *exch = loc_exchange_begin_blocking(LOC_PORT_SUPPLIER);
     
    289216        aid_t req = async_send_2(exch, LOC_SERVICE_REGISTER, interface, 0,
    290217            &answer);
    291         sysarg_t retval = async_data_write_start(exch, fqsn, str_size(fqsn));
     218        sysarg_t retval = async_data_write_start(exch, fqdn, str_size(fqdn));
    292219       
    293220        loc_exchange_end(exch);
     
    301228       
    302229        if (retval != EOK) {
    303                 if (sid != NULL)
    304                         *sid = -1;
    305                
    306                 return retval;
    307         }
    308        
    309         if (sid != NULL)
    310                 *sid = (service_id_t) IPC_GET_ARG1(answer);
     230                if (handle != NULL)
     231                        *handle = -1;
     232               
     233                return retval;
     234        }
     235       
     236        if (handle != NULL)
     237                *handle = (service_id_t) IPC_GET_ARG1(answer);
    311238       
    312239        return retval;
    313240}
    314241
    315 /** Register new service.
    316  *
    317  * @param fqsn  Fully qualified service name
    318  * @param sid   Output: ID of new service
    319  *
    320  */
    321 int loc_service_register(const char *fqdn, service_id_t *sid)
    322 {
    323         return loc_service_register_with_iface(fqdn, sid, 0);
    324 }
    325 
    326 /** Unregister service.
    327  *
    328  * @param sid   Service ID
    329  */
    330 int loc_service_unregister(service_id_t sid)
    331 {
    332         async_exch_t *exch;
    333         sysarg_t retval;
    334        
    335         exch = loc_exchange_begin_blocking(LOC_PORT_SUPPLIER);
    336         retval = async_req_1_0(exch, LOC_SERVICE_UNREGISTER, sid);
    337         loc_exchange_end(exch);
    338        
    339         return (int)retval;
     242/** Register new device.
     243 *
     244 * @param fqdn   Fully qualified device name.
     245 * @param handle Output: Handle to the created instance of device.
     246 *
     247 */
     248int loc_service_register(const char *fqdn, service_id_t *handle)
     249{
     250        return loc_service_register_with_iface(fqdn, handle, 0);
    340251}
    341252
     
    378289       
    379290        return retval;
    380 }
    381 
    382 /** Get object name.
    383  *
    384  * Provided ID of an object, return its name.
    385  *
    386  * @param method        IPC method
    387  * @param id            Object ID
    388  * @param name          Place to store pointer to new string. Caller should
    389  *                      free it using free().
    390  * @return              EOK on success or negative error code
    391  */
    392 static int loc_get_name_internal(sysarg_t method, sysarg_t id, char **name)
    393 {
    394         async_exch_t *exch;
    395         char name_buf[LOC_NAME_MAXLEN + 1];
    396         ipc_call_t dreply;
    397         size_t act_size;
    398         sysarg_t dretval;
    399        
    400         *name = NULL;
    401         exch = loc_exchange_begin_blocking(LOC_PORT_CONSUMER);
    402        
    403         ipc_call_t answer;
    404         aid_t req = async_send_1(exch, method, id, &answer);
    405         aid_t dreq = async_data_read(exch, name_buf, LOC_NAME_MAXLEN,
    406             &dreply);
    407         async_wait_for(dreq, &dretval);
    408        
    409         loc_exchange_end(exch);
    410        
    411         if (dretval != EOK) {
    412                 async_wait_for(req, NULL);
    413                 return dretval;
    414         }
    415        
    416         sysarg_t retval;
    417         async_wait_for(req, &retval);
    418        
    419         if (retval != EOK)
    420                 return retval;
    421        
    422         act_size = IPC_GET_ARG2(dreply);
    423         assert(act_size <= LOC_NAME_MAXLEN);
    424         name_buf[act_size] = '\0';
    425 
    426         *name = str_dup(name_buf);
    427         if (*name == NULL)
    428                 return ENOMEM;
    429        
    430         return EOK;
    431 }
    432 
    433 /** Get category name.
    434  *
    435  * Provided ID of a service, return its name.
    436  *
    437  * @param cat_id        Category ID
    438  * @param name          Place to store pointer to new string. Caller should
    439  *                      free it using free().
    440  * @return              EOK on success or negative error code
    441  */
    442 int loc_category_get_name(category_id_t cat_id, char **name)
    443 {
    444         return loc_get_name_internal(LOC_CATEGORY_GET_NAME, cat_id, name);
    445 }
    446 
    447 /** Get service name.
    448  *
    449  * Provided ID of a service, return its name.
    450  *
    451  * @param svc_id        Service ID
    452  * @param name          Place to store pointer to new string. Caller should
    453  *                      free it using free().
    454  * @return              EOK on success or negative error code
    455  */
    456 int loc_service_get_name(service_id_t svc_id, char **name)
    457 {
    458         return loc_get_name_internal(LOC_SERVICE_GET_NAME, svc_id, name);
    459291}
    460292
     
    757589}
    758590
    759 static int loc_category_get_ids_once(sysarg_t method, sysarg_t arg1,
    760     sysarg_t *id_buf, size_t buf_size, size_t *act_size)
     591static int loc_category_get_svcs_internal(category_id_t cat_id,
     592    service_id_t *id_buf, size_t buf_size, size_t *act_size)
    761593{
    762594        async_exch_t *exch = loc_exchange_begin_blocking(LOC_PORT_CONSUMER);
    763595
    764596        ipc_call_t answer;
    765         aid_t req = async_send_1(exch, method, arg1, &answer);
     597        aid_t req = async_send_1(exch, LOC_CATEGORY_GET_SVCS, cat_id,
     598            &answer);
    766599        int rc = async_data_read_start(exch, id_buf, buf_size);
    767600       
     
    784617}
    785618
    786 /** Get list of IDs.
     619/** Get list of services in category.
    787620 *
    788621 * Returns an allocated array of service IDs.
    789622 *
    790  * @param method        IPC method
    791  * @param arg1          IPC argument 1
     623 * @param cat_id        Category ID
    792624 * @param data          Place to store pointer to array of IDs
    793625 * @param count         Place to store number of IDs
    794626 * @return              EOK on success or negative error code
    795627 */
    796 static int loc_get_ids_internal(sysarg_t method, sysarg_t arg1,
    797     sysarg_t **data, size_t *count)
     628int loc_category_get_svcs(category_id_t cat_id, category_id_t **data,
     629    size_t *count)
    798630{
    799631        service_id_t *ids;
     
    805637        act_size = 0;   /* silence warning */
    806638
    807         rc = loc_category_get_ids_once(method, arg1, NULL, 0,
    808             &act_size);
     639        rc = loc_category_get_svcs_internal(cat_id, NULL, 0, &act_size);
    809640        if (rc != EOK)
    810641                return rc;
     
    816647
    817648        while (true) {
    818                 rc = loc_category_get_ids_once(method, arg1, ids, alloc_size,
     649                rc = loc_category_get_svcs_internal(cat_id, ids, alloc_size,
    819650                    &act_size);
    820651                if (rc != EOK)
     
    836667        return EOK;
    837668}
    838 
    839 /** Get list of services in category.
    840  *
    841  * Returns an allocated array of service IDs.
    842  *
    843  * @param cat_id        Category ID
    844  * @param data          Place to store pointer to array of IDs
    845  * @param count         Place to store number of IDs
    846  * @return              EOK on success or negative error code
    847  */
    848 int loc_category_get_svcs(category_id_t cat_id, service_id_t **data,
    849     size_t *count)
    850 {
    851         return loc_get_ids_internal(LOC_CATEGORY_GET_SVCS, cat_id,
    852             data, count);
    853 }
    854 
    855 /** Get list of categories.
    856  *
    857  * Returns an allocated array of category IDs.
    858  *
    859  * @param data          Place to store pointer to array of IDs
    860  * @param count         Place to store number of IDs
    861  * @return              EOK on success or negative error code
    862  */
    863 int loc_get_categories(category_id_t **data, size_t *count)
    864 {
    865         return loc_get_ids_internal(LOC_GET_CATEGORIES, 0,
    866             data, count);
    867 }
    868 
    869 int loc_register_cat_change_cb(loc_cat_change_cb_t cb_fun)
    870 {
    871         if (loc_callback_create() != EOK)
    872                 return EIO;
    873 
    874         cat_change_cb = cb_fun;
    875         return EOK;
    876 }
Note: See TracChangeset for help on using the changeset viewer.