/********************************************************************************************************* ** 函数名称: aio_fsync ** 功能描述: aio 同步文件的内容, 将缓冲内部的数据写入文件 ** 输 入 : op 操作选项 (O_SYNC or O_DSYNC) ** paiocb aio 请求控制块 ** 输 出 : ERROR or OK ** 全局变量: ** 调用模块: API 函数 *********************************************************************************************************/ LW_API int aio_fsync (int op, struct aiocb *paiocb) { INT iRet; #ifdef __SYLIXOS_KERNEL if (__PROC_GET_PID_CUR() != 0) { /* 需要使用外部库提供的 aio */ errno = ENOSYS; return (PX_ERROR); } #endif /* __SYLIXOS_KERNEL */ if (!paiocb) { errno = EINVAL; return (PX_ERROR); } paiocb->aio_lio_opcode = LIO_SYNC; paiocb->aio_req.aioreq_thread = API_ThreadIdSelf(); paiocb->aio_pwait = LW_NULL; API_SemaphoreMPend(_G_aioqueue.aioq_mutex, LW_OPTION_WAIT_INFINITE); iRet = __aioEnqueue(paiocb); API_SemaphoreMPost(_G_aioqueue.aioq_mutex); return (iRet); }
/********************************************************************************************************* ** 函数名称: __aioCancelFd ** 功能描述: 取消一个 AIO_REQ_CHAIN 节点, ** 输 入 : paiorc AIO_REQ_CHAIN 节点 ** 输 出 : NONE ** 全局变量: ** 调用模块: *********************************************************************************************************/ VOID __aioCancelFd (AIO_REQ_CHAIN *paiorc) { API_SemaphoreMPend(paiorc->aiorc_mutex, LW_OPTION_WAIT_INFINITE); __aioRemoveAllAiocb(paiorc, PX_ERROR, ECANCELED); /* 删除所有同文件描述符节点 */ paiorc->aiorc_iscancel = 1; API_ThreadCondSignal(&paiorc->aiorc_cond); /* 通知代理线程删除 aiorc */ API_SemaphoreMPost(paiorc->aiorc_mutex); }
/********************************************************************************************************* ** 函数名称: __pthread_rwlock_init_invisible ** 功能描述: 读写锁隐形创建. (静态初始化) ** 输 入 : prwlock 句柄 ** 输 出 : NONE ** 全局变量: ** 调用模块: *********************************************************************************************************/ static void __pthread_rwlock_init_invisible (pthread_rwlock_t *prwlock) { if (prwlock) { if (prwlock->PRWLOCK_ulMutex == LW_OBJECT_HANDLE_INVALID) { API_SemaphoreMPend(_G_ulPRWLockInitLock, LW_OPTION_WAIT_INFINITE); if (prwlock->PRWLOCK_ulMutex == LW_OBJECT_HANDLE_INVALID) { pthread_rwlock_init(prwlock, LW_NULL); } API_SemaphoreMPost(_G_ulPRWLockInitLock); } } }
/********************************************************************************************************* ** 函数名称: __aioDeleteFd ** 功能描述: 从指定的 AIO_REQ_CHAIN 中删除一个 AIO_REQ_CHAIN 节点 (这里必须锁定 _G_aioqueue) ** 输 入 : paiorc AIO_REQ_CHAIN 节点 ** pplineHeader 创建后加入的链表表头地址 ** 输 出 : NONE ** 全局变量: ** 调用模块: *********************************************************************************************************/ static VOID __aioDeleteFd (AIO_REQ_CHAIN *paiorc, LW_LIST_LINE_HEADER *pplineHeader) { API_SemaphoreMPend(paiorc->aiorc_mutex, LW_OPTION_WAIT_INFINITE); __aioRemoveAllAiocb(paiorc, PX_ERROR, ECANCELED); /* 删除所有同文件描述符节点 */ API_SemaphoreMPost(paiorc->aiorc_mutex); _List_Line_Del(&paiorc->aiorc_line, pplineHeader); API_SemaphoreMDelete(&paiorc->aiorc_mutex); API_ThreadCondDestroy(&paiorc->aiorc_cond); __SHEAP_FREE(paiorc); }
/********************************************************************************************************* ** 函数名称: __aioAttachWait ** 功能描述: 向指定的 aiocb 中连接 wait 信息 (这里必须锁定 _G_aioqueue) ** 输 入 : paiocb 指定的 aiocb ** paiowait wait 信息 ** 输 出 : ERROR or OK ** 全局变量: ** 调用模块: *********************************************************************************************************/ INT __aioAttachWait (const struct aiocb *paiocb, struct aiowait *paiowait) { PLW_LIST_LINE plineTempAiorc; PLW_LIST_LINE plineTempAiocb; AIO_REQ_CHAIN *paiorc; struct aioreq *paioreqTemp; struct aiocb *paiocbTemp; BOOL bIsOk = LW_FALSE; for (plineTempAiorc = _G_aioqueue.aioq_plinework; plineTempAiorc != LW_NULL; plineTempAiorc = _list_line_get_next(plineTempAiorc)) { paiorc = _LIST_ENTRY(plineTempAiorc, AIO_REQ_CHAIN, aiorc_line); if (paiorc->aiorc_fildes == paiocb->aio_fildes) { API_SemaphoreMPend(paiorc->aiorc_mutex, LW_OPTION_WAIT_INFINITE); for (plineTempAiocb = paiorc->aiorc_plineaiocb; plineTempAiocb != LW_NULL; plineTempAiocb = _list_line_get_next(plineTempAiocb)) { paioreqTemp = _LIST_ENTRY(plineTempAiocb, struct aioreq, aioreq_line); paiocbTemp = _LIST_ENTRY(paioreqTemp, struct aiocb, aio_req); if (paiocbTemp == paiocb) { if (paiocbTemp->aio_pwait) { /* 不允许重复保存 */ API_SemaphoreMPost(paiorc->aiorc_mutex); return (PX_ERROR); } paiocbTemp->aio_pwait = paiowait; paiowait->aiowt_paiocb = paiocbTemp; bIsOk = LW_TRUE; break; } } API_SemaphoreMPost(paiorc->aiorc_mutex); break; } }
/********************************************************************************************************* ** 函数名称: aio_suspend ** 功能描述: 等待指定的一个或多个异步 I/O 请求操作完成 ** 输 入 : list aio 请求控制块数组 (如果其中有 NULL, 程序将忽略) ** nent 数组元素个数 ** timeout 超时时间 ** 输 出 : ERROR or OK ** 全局变量: ** 调用模块: API 函数 *********************************************************************************************************/ LW_API int aio_suspend (const struct aiocb * const list[], int nent, const struct timespec *timeout) { AIO_WAIT_CHAIN *paiowc; struct aiowait *paiowait; ULONG ulTimeout; BOOL bNeedWait = LW_FALSE; int iWait = 0; /* paiowait 下标 */ int iCnt; /* list 下标 */ int iRet = ERROR_NONE; #ifdef __SYLIXOS_KERNEL if (__PROC_GET_PID_CUR() != 0) { /* 需要使用外部库提供的 aio */ errno = ENOSYS; return (PX_ERROR); } #endif /* __SYLIXOS_KERNEL */ __THREAD_CANCEL_POINT(); /* 测试取消点 */ if ((nent <= 0) || (list == LW_NULL)) { errno = EINVAL; return (PX_ERROR); } if (timeout == LW_NULL) { /* 永久等待 */ ulTimeout = LW_OPTION_WAIT_INFINITE; } else { ulTimeout = __timespecToTick(timeout); } paiowc = __aioCreateWaitChain(nent, LW_TRUE); /* 创建等待队列 */ if (paiowc == LW_NULL) { errno = ENOMEM; /* should be EAGAIN ? */ return (PX_ERROR); } paiowait = paiowc->aiowc_paiowait; API_SemaphoreMPend(_G_aioqueue.aioq_mutex, LW_OPTION_WAIT_INFINITE); for (iCnt = 0; iCnt < nent; iCnt++) { if (list[iCnt]) { if (list[iCnt]->aio_req.aioreq_error == EINPROGRESS) { /* 必须为正在处理状态 */ paiowait[iWait].aiowt_pcond = &paiowc->aiowc_cond; paiowait[iWait].aiowt_pcnt = LW_NULL; paiowait[iWait].aiowt_psigevent = LW_NULL; paiowait[iWait].aiowt_paiowc = LW_NULL; /* 不需要代理线程释放 */ iRet = __aioAttachWait(list[iCnt], &paiowait[iWait]); if (iRet != ERROR_NONE) { errno = EINVAL; break; } _List_Line_Add_Tail(&paiowait[iWait].aiowt_line, &paiowc->aiowc_pline); /* 加入 wait 链表 */ iWait++; bNeedWait = LW_TRUE; /* 有 wait 链表节点连接, */ } else { break; } } } if (iRet != ERROR_NONE) { /* __aioAttachWait 失败 */ __aioDeleteWaitChain(paiowc); API_SemaphoreMPost(_G_aioqueue.aioq_mutex); errno = EINVAL; return (PX_ERROR); } if ((iCnt == nent) && bNeedWait) { /* 是否需要等待 */ API_ThreadCleanupPush(__aioWaitCleanup, paiowc); iRet = (INT)API_ThreadCondWait(&paiowc->aiowc_cond, _G_aioqueue.aioq_mutex, ulTimeout); API_ThreadCleanupPop(LW_FALSE); /* 这里已经锁定 _G_aioqueue */ /* 不能运行 __aioWaitCleanup */ __aioDeleteWaitChain(paiowc); if (iRet != ERROR_NONE) { API_SemaphoreMPost(_G_aioqueue.aioq_mutex); errno = EAGAIN; return (PX_ERROR); } } else { /* 不需要等待 */ __aioDeleteWaitChain(paiowc); } API_SemaphoreMPost(_G_aioqueue.aioq_mutex); return (iRet); }
/********************************************************************************************************* ** 函数名称: __aioWaitCleanup ** 功能描述: 清理 wait 队列 ** 输 入 : paiowt paiowait 链表头 ** 输 出 : NONE ** 全局变量: ** 调用模块: *********************************************************************************************************/ static VOID __aioWaitCleanup (AIO_WAIT_CHAIN *paiowt) { API_SemaphoreMPend(_G_aioqueue.aioq_mutex, LW_OPTION_WAIT_INFINITE); __aioDeleteWaitChain(paiowt); API_SemaphoreMPost(_G_aioqueue.aioq_mutex); }
/********************************************************************************************************* ** 函数名称: aio_cancel ** 功能描述: 取消一个 aio 请求 ** 输 入 : fildes 文件描述符 ** paiocb aio 请求控制块 (可以为 NULL) ** 输 出 : ERROR or OK ** 全局变量: ** 调用模块: API 函数 *********************************************************************************************************/ LW_API int aio_cancel (int fildes, struct aiocb *paiocb) { AIO_REQ_CHAIN *paiorc; INT iRet; #ifdef __SYLIXOS_KERNEL if (__PROC_GET_PID_CUR() != 0) { /* 需要使用外部库提供的 aio */ errno = ENOSYS; return (PX_ERROR); } #endif /* __SYLIXOS_KERNEL */ API_SemaphoreMPend(_G_aioqueue.aioq_mutex, LW_OPTION_WAIT_INFINITE); if (paiocb == LW_NULL) { /* * 如果是 cancel 整个文件描述符, 那么这里调用 __aioCancelFd() 进行, __aioCancelFd() 内部将所有 * 等待操作的节点释放, 然后通知代理线程删除 paiorc 结构, 这样是最安全的操作方式, 如果这里直接删除 * 那么正在操作的 paiorc 可能会有危险, * 从应用层角度是看不到这个过程的! 我们保证在函数返回前, 将所有的 aiocb 处理完毕! */ paiorc = __aioSearchFd(_G_aioqueue.aioq_plinework, fildes); /* 搜索工作队列中有没有相同的 */ if (paiorc == LW_NULL) { if (_G_aioqueue.aioq_plineidle) { paiorc = __aioSearchFd(_G_aioqueue.aioq_plineidle, fildes); /* 搜索空闲队列 */ if (paiorc == LW_NULL) { API_SemaphoreMPost(_G_aioqueue.aioq_mutex); return (AIO_ALLDONE); } else { __aioCancelFd(paiorc); /* 删除所有节点后通知任务删除 */ API_SemaphoreMPost(_G_aioqueue.aioq_mutex); return (AIO_CANCELED); } } else { API_SemaphoreMPost(_G_aioqueue.aioq_mutex); return (AIO_ALLDONE); } } else { __aioCancelFd(paiorc); /* 删除所有节点后通知任务删除 */ API_SemaphoreMPost(_G_aioqueue.aioq_mutex); return (AIO_CANCELED); } } else { if (paiocb->aio_fildes != fildes) { API_SemaphoreMPost(_G_aioqueue.aioq_mutex); errno = EINVAL; return (PX_ERROR); } paiorc = __aioSearchFd(_G_aioqueue.aioq_plinework, fildes); /* 搜索工作队列中有没有相同的 */ if (paiorc == LW_NULL) { if (_G_aioqueue.aioq_plineidle) { paiorc = __aioSearchFd(_G_aioqueue.aioq_plineidle, fildes); /* 搜索空闲队列 */ if (paiorc == LW_NULL) { API_SemaphoreMPost(_G_aioqueue.aioq_mutex); return (AIO_ALLDONE); } else { API_SemaphoreMPend(paiorc->aiorc_mutex, LW_OPTION_WAIT_INFINITE); iRet = __aioRemoveAiocb(paiorc, paiocb, PX_ERROR, ECANCELED); /* 移除 aiocb */ API_SemaphoreMPost(paiorc->aiorc_mutex); API_SemaphoreMPost(_G_aioqueue.aioq_mutex); return (iRet); } } else { API_SemaphoreMPost(_G_aioqueue.aioq_mutex); return (AIO_ALLDONE); } } else { API_SemaphoreMPend(paiorc->aiorc_mutex, LW_OPTION_WAIT_INFINITE); iRet = __aioRemoveAiocb(paiorc, paiocb, PX_ERROR, ECANCELED); /* 移除 aiocb */ API_SemaphoreMPost(paiorc->aiorc_mutex); API_SemaphoreMPost(_G_aioqueue.aioq_mutex); return (iRet); } } API_SemaphoreMPost(_G_aioqueue.aioq_mutex); return (AIO_ALLDONE); }
/********************************************************************************************************* ** 函数名称: lio_listio ** 功能描述: 同时发起多个传输 mode 参数可以是 LIO_WAIT 或 LIO_NOWAIT。LIO_WAIT 会阻塞这个调用, 直到所有的 I/O 都完成为止. 在操作进行排队之后,LIO_NOWAIT 就会返回. sigevent 引用定义了在所有 I/O 操作都完成时产生信号的方法。 ** 输 入 : mode LIO_WAIT or LIO_NOWAIT。LIO_WAIT ** list aio 请求控制块数组 (如果其中有 NULL, 程序将忽略) ** nent 数组元素个数 ** sig 所有 I/O 操作都完成时产生信号的方法 LIO_WAIT 将会忽略此参数! ** 输 出 : ERROR or OK ** 全局变量: ** 调用模块: API 函数 *********************************************************************************************************/ LW_API int lio_listio (int mode, struct aiocb * const list[], int nent, struct sigevent *sig) { AIO_WAIT_CHAIN *paiowc; struct aiowait *paiowait; int iWait = 0; /* paiowait 下标 */ int iCnt; /* list 下标 */ int iRet = ERROR_NONE; #ifdef __SYLIXOS_KERNEL if (__PROC_GET_PID_CUR() != 0) { /* 需要使用外部库提供的 aio */ errno = ENOSYS; return (PX_ERROR); } #endif /* __SYLIXOS_KERNEL */ if ((mode != LIO_WAIT) && (mode != LIO_NOWAIT)) { errno = EINVAL; return (PX_ERROR); } if ((nent <= 0) || (list == LW_NULL)) { errno = EINVAL; return (PX_ERROR); } if (mode == LIO_WAIT) { paiowc = __aioCreateWaitChain(nent, LW_TRUE); /* 创建等待队列 */ } else { paiowc = __aioCreateWaitChain(nent, LW_FALSE); } if (paiowc == LW_NULL) { errno = ENOMEM; /* should be EAGAIN ? */ return (PX_ERROR); } if (sig) { paiowc->aiowc_sigevent = *sig; } else { paiowc->aiowc_sigevent.sigev_signo = 0; /* 无效信号不投递 */ } paiowait = paiowc->aiowc_paiowait; API_SemaphoreMPend(_G_aioqueue.aioq_mutex, LW_OPTION_WAIT_INFINITE); for (iCnt = 0; iCnt < nent; iCnt++) { if (list[iCnt]) { if ((list[iCnt]->aio_lio_opcode != LIO_NOP) && (list[iCnt]->aio_req.aioreq_error != EINPROGRESS)) { list[iCnt]->aio_sigevent.sigev_notify = SIGEV_NONE; /* 不使用 aiocb 的 sigevent */ list[iCnt]->aio_req.aioreq_thread = API_ThreadIdSelf(); if (mode == LIO_WAIT) { paiowait[iWait].aiowt_pcond = &paiowc->aiowc_cond; paiowait[iWait].aiowt_pcnt = LW_NULL; paiowait[iWait].aiowt_psigevent = LW_NULL; paiowait[iWait].aiowt_paiowc = LW_NULL; /* 不需要代理线程释放 */ } else { paiowait[iWait].aiowt_pcond = LW_NULL; paiowait[iWait].aiowt_pcnt = LW_NULL; paiowait[iWait].aiowt_psigevent = &paiowc->aiowc_sigevent; paiowait[iWait].aiowt_paiowc = (void *)paiowc; } __aioAttachWaitNoCheck(list[iCnt], &paiowait[iWait]); /* aiocb and aiowait attach */ if (__aioEnqueue(list[iCnt]) == ERROR_NONE) { _List_Line_Add_Tail(&paiowait[iWait].aiowt_line, &paiowc->aiowc_pline); /* 加入 wait 链表 */ iWait++; } else { __aioDetachWait(LW_NULL, &paiowait[iWait]); /* 删除关联关系 */ iRet = PX_ERROR; } } } } if (iWait == 0) { /* 没有一个节点加入队列 */ __aioDeleteWaitChain(paiowc); API_SemaphoreMPost(_G_aioqueue.aioq_mutex); if (mode == LIO_NOWAIT) { if (sig && __issig(sig->sigev_signo)) { _doSigEvent(API_ThreadIdSelf(), sig, SI_ASYNCIO); } } return (ERROR_NONE); } else if (mode == LIO_WAIT) { /* 需要等待 */ __aioWaitChainSetCnt(paiowc, &iWait); /* 设置计数变量 */ while (iWait > 0) { if (API_ThreadCondWait(&paiowc->aiowc_cond, _G_aioqueue.aioq_mutex, LW_OPTION_WAIT_INFINITE)) { /* 等待所有请求执行完毕 */ break; } } __aioDeleteWaitChain(paiowc); /* 清除 wait 队列 */ } else { /* LIO_NOWAIT */ paiowc->aiowc_icnt = iWait; /* 必须使用全局变量 */ __aioWaitChainSetCnt(paiowc, &paiowc->aiowc_icnt); /* 设置计数变量 */ } API_SemaphoreMPost(_G_aioqueue.aioq_mutex); return (iRet); }