Changeset 52b7b1bb in mainline for uspace/lib/libdrv/generic/driver.c


Ignore:
Timestamp:
2010-04-01T14:08:55Z (15 years ago)
Author:
Lenka Trochtova <trochtova.lenka@…>
Branches:
lfn, master, serial, ticket/834-toolchain-update, topic/msim-upgrade, topic/simplify-dev-export
Children:
57937dd
Parents:
a1769ee
Message:

device interfaces - parts of code

File:
1 edited

Legend:

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

    ra1769ee r52b7b1bb  
    3535/** @file
    3636 */
    37  
     37
    3838#include <assert.h>
    3939#include <ipc/services.h>
     
    6262        device_t *dev = (device_t *)malloc(sizeof(device_t));
    6363        if (NULL != dev) {
    64                 memset(dev, 0, sizeof(device_t));               
    65         }       
    66         return dev;     
    67 }
    68 
    69 static device_t * driver_get_device(link_t *devices, device_handle_t handle) 
    70 {       
     64                memset(dev, 0, sizeof(device_t));
     65        }
     66        return dev;
     67}
     68
     69static device_t * driver_get_device(link_t *devices, device_handle_t handle)
     70{
    7171        device_t *dev = NULL;
    7272        link_t *link = devices->next;
    73        
     73
    7474        while (link != devices) {
    7575                dev = list_get_instance(link, device_t, link);
     
    7878                }
    7979        }
    80        
     80
    8181        return NULL;
    8282}
    8383
    84 static void driver_add_device(ipc_callid_t iid, ipc_call_t *icall) 
     84static void driver_add_device(ipc_callid_t iid, ipc_call_t *icall)
    8585{
    8686        printf("%s: driver_add_device\n", driver->name);
    87        
     87
    8888        // result of the operation - device was added, device is not present etc.
    89         ipcarg_t ret = 0;       
    90         device_handle_t dev_handle =  IPC_GET_ARG1(*icall);     
     89        ipcarg_t ret = 0;
     90        device_handle_t dev_handle =  IPC_GET_ARG1(*icall);
    9191        device_t *dev = driver_create_device();
    9292        dev->handle = dev_handle;
     
    9696        }
    9797        printf("%s: new device with handle = %x was added.\n", driver->name, dev_handle);
    98        
     98
    9999        ipc_answer_1(iid, EOK, ret);
    100100}
     
    103103{
    104104        printf("%s: driver_connection_devman \n", driver->name);
    105        
     105
    106106        /* Accept connection */
    107107        ipc_answer_0(iid, EOK);
    108        
     108
    109109        bool cont = true;
    110110        while (cont) {
    111111                ipc_call_t call;
    112112                ipc_callid_t callid = async_get_call(&call);
    113                
     113
    114114                switch (IPC_GET_METHOD(call)) {
    115115                case IPC_M_PHONE_HUNGUP:
     
    123123                                ipc_answer_0(callid, ENOENT);
    124124                }
    125         }       
    126 }
    127 
    128 /** 
     125        }
     126}
     127
     128/**
    129129 * Generic client connection handler both for applications and drivers.
    130  *
    131  * @param driver true for driver client, false for other clients (applications, services etc.).
    132  */
    133 static void driver_connection_gen(ipc_callid_t iid, ipc_call_t *icall, bool driver) {
    134         /*
    135          * Answer the first IPC_M_CONNECT_ME_TO call and remember the handle of the device to which the client connected.
    136          */
    137         device_handle_t handle = IPC_GET_ARG1(*icall);
     130 *
     131 * @param driver true for driver client, false for other clients (applications, services etc.).
     132 */
     133static void driver_connection_gen(ipc_callid_t iid, ipc_call_t *icall, bool driver)
     134{
     135        // Answer the first IPC_M_CONNECT_ME_TO call and remember the handle of the device to which the client connected.
     136        device_handle_t handle = IPC_GET_ARG1(*icall);
    138137        device_t *dev = driver_get_device(&devices, handle);
    139        
     138
    140139        if (dev == NULL) {
    141140                ipc_answer_0(iid, ENOENT);
    142141                return;
    143142        }
     143
     144        // TODO open the device (introduce some callbacks for opening and closing devices registered by the driver)
    144145       
    145         // TODO introduce generic device interface for opening and closing devices
    146         // and call its open callback here to find out wheter the device can be used by the connecting client
    147                
    148 
    149146        ipc_answer_0(iid, EOK);
    150        
     147
    151148        while (1) {
    152149                ipc_callid_t callid;
    153150                ipc_call_t call;
    154        
     151
    155152                callid = async_get_call(&call);
    156153                ipcarg_t method = IPC_GET_METHOD(call);
    157154                switch  (method) {
    158155                case IPC_M_PHONE_HUNGUP:
    159                         // TODO close the device
     156               
     157                        // TODO close the device
     158                       
    160159                        ipc_answer_0(callid, EOK);
    161160                        return;
    162161                default:
    163                         if (DEV_IFACE_FIRST <= method && method < DEV_IFACE_MAX) {
    164                                 // TODO - try to find interface, if supported
    165                                 // otherwise return  ENOTSUP                           
    166                         } else {
     162
     163                        if (!is_valid_iface_id(method)) {
     164                                // this is not device's interface
    167165                                ipc_answer_0(callid, ENOTSUP);
     166                                break;
    168167                        }
     168
     169                        // calling one of the device's interfaces
     170                       
     171                        // get the device interface structure
     172                        void *iface = device_get_iface(dev, method);
     173                        if (NULL == iface) {
     174                                ipc_answer_0(callid, ENOTSUP);
     175                                break;
     176                        }
     177
     178                        // get the corresponding interface for remote request handling ("remote interface")
     179                        remote_iface_t* rem_iface = get_remote_iface(method);
     180                        assert(NULL != rem_iface);
     181
     182                        // get the method of the remote interface
     183                        ipcarg_t iface_method_idx = IPC_GET_ARG1(call);
     184                        remote_iface_func_ptr_t iface_method_ptr = get_remote_method(rem_iface, iface_method_idx);
     185                        if (NULL == iface_method_ptr) {
     186                                // the interface has not such method
     187                                ipc_answer_0(callid, ENOTSUP);
     188                                break;
     189                        }
     190                       
     191                        // call the remote interface's method, which will receive parameters from the remote client
     192                        // and it will pass it to the corresponding local interface method associated with the device
     193                        // by its driver
     194                        (*iface_method_ptr)(dev, iface, callid, &call);
    169195                        break;
    170196                }
     
    174200static void driver_connection_driver(ipc_callid_t iid, ipc_call_t *icall)
    175201{
    176         driver_connection_gen(iid, icall, true); 
     202        driver_connection_gen(iid, icall, true);
    177203}
    178204
    179205static void driver_connection_client(ipc_callid_t iid, ipc_call_t *icall)
    180206{
    181         driver_connection_gen(iid, icall, false); 
     207        driver_connection_gen(iid, icall, false);
    182208}
    183209
     
    199225                break;
    200226        case DRIVER_CLIENT:
    201                 // handle requests from client applications 
     227                // handle requests from client applications
    202228                driver_connection_client(iid, icall);
    203229                break;
    204230
    205231        default:
    206                 /* No such interface */ 
     232                /* No such interface */
    207233                ipc_answer_0(iid, ENOENT);
    208234        }
     
    212238{
    213239        printf("%s: child_device_register\n", driver->name);
    214        
     240
    215241        assert(NULL != child->name);
    216        
     242
    217243        if (EOK == devman_child_device_register(child->name, &child->match_ids, parent->handle, &child->handle)) {
    218244                return true;
     
    221247}
    222248
    223 int driver_main(driver_t *drv) 
     249int driver_main(driver_t *drv)
    224250{
    225251        // remember the driver structure - driver_ops will be called by generic handler for incoming connections
    226252        driver = drv;
    227        
     253
    228254        // register driver by device manager with generic handler for incoming connections
    229         devman_driver_register(driver->name, driver_connection);               
     255        devman_driver_register(driver->name, driver_connection);
    230256
    231257        async_manager();
    232258
    233259        // Never reached
    234         return 0;       
     260        return 0;
    235261}
    236262
Note: See TracChangeset for help on using the changeset viewer.