Администраторы ресурсов в QNX
Администратор ресурсов в QNX является пользовательской программой, которая предоставляет стандартизированный по интерфейсу (POSIX) сервис другим программам и при необходимости взаимодействует с оборудованием.
В других операционных системах большая часть этой работы реализуется драйверами устройств (или специальными модулями). Однако, в отличие от обычных драйверов, администратор ресурсов действует в пользовательском пространстве с защитой памяти, что позволяет запускать и останавливать эту программу динамически, а также отлаживать ее, как любое другое пользовательское приложение.
Поиск сервера клиентом fd = open(/dev/ser1, O_WRONLY); клиент – Администратор процессов (ND 0/ PID 1/ CHID 1) АП : (ND 0/ PID 44/ CHID 1) клиент – Администратор ресурса read/write/lseek/close
Общая структура Создание и инициализация библиотечных структур Регистрация префикса(имени) Цикл ожидания и обработки сообщений
Схема работы МР chid функции установления соединения io_openio_unlink io_readlink функции ввода/вывода io_readio_writeio_lseek io_devctl Open Control Block CTP
Создание структуры диспетчеризации #include dispatch_t * dpp; dpp = dispatch_create();
Инициализация аттрибутов remgr_attr_t resmgr_attr; memset(&resmgr_attr,0,sizeof(resmgr_attr); resmgr_attr.nparts_max = 1; resmgr_attr.msg_max_size = 2048;
Назначить обработчики по умолчанию resmgr_connect_funcs_t connect_func; resmgr_io_funcs_t io_func; iofunc_func_init ( _RESMGR_CONNECT_NFUNCS, &connect_func, _RESMGR_IO_NFUNCS, &io_func);
Атрибутная запись об устройстве iofunc_attr_t attr; iofunc_attr_init ( &attr, S_IFNAM | 0666, 0, 0);
Регистрируем префикс regmgr_attach ( dpp, &resmgr_attr, /dev/myname, _FTYPE_ANY, 0, &connect_func, &io_func, &attr);
Выделяем внутренний контекстный блок ctp = resmgr_context_alloc(dpp);
Основной цикл while(1) { ctp = resmgr_block(ctp); resmgr_handler(ctp); }
io_funcs.read = io_read; attr.nbytes = strlen(buffer)+1; int io_read (resmgr_context_t *ctp, io_read_t *msg, RESMGR_OCB_T *ocb)
ctp->iov – таблица векторов ввода/вывода ocb->offset – текущее смещение (lseek) ocb->attr->nbytes размер ресурса(файла) в байтах
io_read int nleft; int nbytes; int nparts; int status; istatus = iofunc_read_verify (ctp, msg, ocb, NULL); nleft = ocb->attr->nbytes - ocb->offset; nbytes = min (msg->i.nbytes, nleft);
if (nbytes > 0) { SETIOV (ctp->iov, buffer + ocb->offset, nbytes); /* set up the number of bytes (returned by client's read()) */ _IO_SET_READ_NBYTES (ctp, nbytes); /* * advance the offset by the number of bytes * returned to the client. */ ocb->offset += nbytes; nparts = 1; }
else { // nbytes