vxWorks编程API

一、官方的Program Guide
位于安装目录下:\docs\vxworks\guide\index.html
二、常用的库:
#i nclude "taskLib.h"
#i nclude "msgQLib.h"
#i nclude "semLib.h"
#i nclude "ioLib.h"
#i nclude "wdLib.h"
#i nclude "logLib.h"
#i nclude "socket.h"

三、IO系统:ioLib.h
1、系统中的IO设备,包括键盘、串口、文件等,都用统一的接口访问。第一步通常先得到文件描述符,然后进行读写或者设置的工作,最后关闭该描述符。
creat:建立文件
open:得到文件或设备的描述符
read:读文件或设备
write:写文件或设备
ioctl:设置参数
close:关闭文件描述符
remove:删除文件

2、内存文件
memDrv( ) - 初始化伪内存设备
memDevCreate( ) - 建立伪内存设备
memDevCreateDir( ) - 建立一组伪内存设备
memDevDelete( ) - 删除伪内存设备

Init() {
uchar_t buffer[1024];
int fd;
memDrv( );
memDevCreate("/mem/mem1", buffer, sizeof(buffer));
if ((fd = open("/mem/mem1", O_RDWR, 0644)) != ERROR) {
write(fd, &data, sizeof(data));
... ...
close(fd);
}
memDevDelete("/mem/mem1");
}

3、通过Select函数实现多个IO监听:selectLib.h
当等待多个IO时,我们可以使用Select函数,fd为文件描述符:
int select(
int width,
fd_set * pReadFds,
fd_set * pWriteFds,
fd_set * pExceptFds,
struct timeval * pTimeOut
)
还有几个宏:
FD_SET(fd, &fdset) 设置fd的监听位
FD_CLR(fd, &fdset) 清除fd的监听位
FD_ZERO(&fdset) 清除所有监听位
FD_ISSET(fd, &fdset) fd是否有数据
例子,其中MAX意为取最大值:
Init() {
struct fd_set readFds;
int fds[4];
int width;

fds[0] = open(..);... ...;fds[3] = open(..);
width = MAX(fds[0], ... ... , fds[3])+1;

FD_ZERO(&readFds);
FD_SET(fds[0], & readFds);... ...; FD_SET(fds[3], & readFds);

if (select(width, &readFds, NULL, NULL, NULL) == ERROR) {
close(fds[0]); ... ...; close(fds[3]);
return;
}
for(i=0; i
if (FD_ISSET(fds[i], &readFds)) {
... ...;
}
}
}

四、多任务环境的编程:
1、任务控制:taskLib.h
taskSpawn( ) - 创建任务
taskInit( ) -初始化任务,用户自己指定栈和PCB地址
taskActivate( ) - 激活已经初始化的任务
exit( ) - 在任务中结束 (ANSI)
taskDelete( ) - 删除任务
taskDeleteForce( ) - 强制删除,即使被保护
taskSuspend( ) - 挂起任务
taskResume( ) - 恢复挂起的任务
taskRestart( ) - 重新启动任务
taskPrioritySet( ) - 改变任务优先级
taskPriorityGet( ) - 读取任务优先级
taskLock( ) - 禁止任务调度
taskUnlock( ) - 允许任务调度
taskSafe( ) - 保护任务不被删除
taskUnsafe( ) - 解除保护
taskDelay( ) - 延时
taskIdSelf( ) - 得到当前任务的ID
taskIdVerify( ) - 任务ID是否存在
taskTcb( ) - 得到任务控制块(TCB)的地址
taskOptionsSet( ) - 改变任务选项
taskOptionsGet( ) - 得到任务当前选项
taskRegsGet( ) - 得到任务TCB中寄存器的信息
taskRegsSet( ) - 设定任务TCB中寄存器的信息
taskName( ) - 得到任务名称
taskNameToId( ) - 由名称得到ID
taskIdDefault( ) - 设置默认的任务ID
taskIsReady( ) - 任务是否就绪
taskIsSuspended( ) - 任务是否挂起
taskIdListGet( ) - 得到活动的任务列表

2、任务互斥 - 信号量:semLib.h
semGive( ) – 释放一个信号量
semTake( ) – 获取一个信号量,会阻塞
semFlush( ) – 使所有阻塞在本信号量上的任务变为就绪状态
semDelete( ) – 删除一个信号量
1)二进制信号量:semBCreate
可用于任务同步和互斥,但常用于任务同步
2)互斥信号量:semMCreate
专门用于任务互斥的信号量,保护临界资源
3)计数信号量:semCCreate
多实例资源的访问控制

3、任务同步
1)消息队列:msgQLib.h
消息队列
msgQCreate( ) - 创建消息队列
msgQDelete( ) - 删除消息队列
msgQSend( ) - 发送消息
msgQReceive( ) - 接受消息,调用后阻塞
msgQNumMsgs( ) - 得到消息队列中的消息数量

Init() {
if ((msgQID = msgQCreate(8, 1, MSG_Q_FIFO)) == NULL) {
printf("Message queue create failed!\n");
}
}

taskSend() {
if (OK != msgQSend(msgQID, "A", 1, NO_WAIT, MSG_PRI_NORMAL)) {
printf("Message send failed!");
}
}

taskReceive() {
uchar_t ch;
msgQReceive(msgQID, &ch, 1, WAIT_FOREVER);
printf("Received from msgq: %c ", ch);
}

2)管道:ioLib.h,系统默认包含了pipe驱动组件
pipeDevCreate( ) - 创建管道
pipeDevDelete( ) - 删除管道
由于管道属于IO,所以可以使用Select监听,消息队列不是IO,不能使用Select

Init() {
if (pipeDevCreate("/pipe/mypipe", 8, 1) != OK) {
printf("/pipe/mypipe create fialed!\n");
}

if ((semMID = semMCreate(SEM_Q_FIFO)) == NULL)
{
printf("Mutex semaphore create failed!\n");
}
}

taskSend() {
int pd;
if ((pd = open("/pipe/mypipe", O_WRONLY, 0644)) == ERROR) {
printf("Open pipe failed!");
}
if (semTake(semMID, NO_WAIT) == ERROR) {
printf("Pipe in use!");
}
write(pd, "a", 1);
semGive(semMID);
close(pd);
}

taskReceive() {
int pd;
uchar_t ch;
if ((pd = open("/pipe/mypipe", O_RDONLY, 0644)) == ERROR) {
printf("Open pipe failed!");
}
if (read(pd, &ch, 1)>0) {
printf("Received from pipe: %c", ch);
}
}

3)二进制信号量
Init() {

if ((semBID = semBCreate(SEM_Q_FIFO, SEM_EMPTY)) == NULL) {
printf("Binary semaphore create failed!\n");
}
}

taskSend() {
semGive(semBID);
}

taskReceive() {
semTake(semBID, WAIT_FOREVER);
}

4)事件:eventLib
发送事件要指定目标任务的ID
eventReceive( ) - 等待事件
eventSend( ) - 发送事件
eventClear( ) - 清除当前任务的事件.

taskSend() {
if (OK != eventSend(taskReceiveID, 0x00000001)) {
printf("Event send failed!");
}
}
taskReceive() {
UINT32 Ev;
if (OK!=eventReceive(0x00ffffff, EVENTS_WAIT_ANY, WAIT_FOREVER, &Ev)) {
printf("eventReceive Error!\n");
}
else {
Ev &= 0x00000001;
if (Ev) {
printf("Event %d received!", Ev);
}
}
}

五、Watch dog :wdLib.h
系统提供了软看门狗定时器,使用也简便:
wdCreate( ) - 创建看门狗
wdDelete( ) - 删除
wdStart( ) - 启动
wdCancel( ) - 停止

Init() {
if ((wdID = wdCreate()) == NULL) {
printf("Watch dog create failed!\n");
}
}
task() {
if (OK != wdStart(wdID, sysClkRateGet()*5, proc_wd, 0)) {
printf("Watch dog start failed!\n");
}
}
int proc_wd(int param) {
logMsg(... ...);
}
六、网络编程:sockLib.h
使用标准的BSD Socket套接字,使用TCP或者UDP协议进行通讯。
socket( ) - 打开套接字
bind( ) - 与端口、地址等绑定
listen( ) - 监听模式
accept( ) - 允许对方的连接
connect( ) - 主动与远端连接
connectWithTimeout( ) - 超时功能的connect函数
sendto( ) - 发送
send( ) - 发送
sendmsg( ) - 发送
recvfrom( ) - 接收
recv( ) - 接收
recvmsg( ) -接收
setsockopt( ) - 设定套接字参数
getsockopt( ) - 得到套接字参数
getsockname( ) - 得到套接字名称
getpeername( ) -得到连接的对点的名称
shutdown( ) - 关闭连接
七、异常处理
1、错误号:errnoLib.h
32位有符号整数,1~500被系统占用,其他程序内可用。如
#define MEMORY_LEAK 0x20005
errnoGet( ) - 得到当前任务的错误号
errnoOfTaskGet( ) - 得到指定任务的错误号
errnoSet( ) - 设定当前任务的错误号
errnoOfTaskSet( ) - 设定指定任务的错误号

2、信号:sigLib.h
signal( ) - 指定信号的入口函数
raise( ) - 发送信号给当前任务
kill( ) - 发送信号给指定任务

task1() {
signal(30, proc_sig);

}

task2() {
kill(task1ID, 30);
}
void proc_sig(int param) {
logMsg("Error message...");
}

八、中断:iv.h
x86的0x0~0xf号中断对应vxWorks中0x20~0x2f号中断
以9号中断为例:
初始化中断:
intConnect( INUM_TO_IVEC(9+0x20), Int9Handler, 0);
sysIntEnablePIC(9);
中断函数原型:
void Int9Handler(int Param);

takeSpawn与semCreate说明

int taskSpawn
(
char *name, /*任务名*/
int priority, /*任务优先级,vxWorks好像共255个,而且调度采用优先级抢占式,同优先级轮换式的调度方式*/
int options, /*任务的一些特性,例如VX_SUPERVISOR_MODE 0x0001 OBSOLETE: tasks always in sup mode*/
int stackSize, /* 需要申请堆栈的大小*/
FUNCPTR entryPt, /*任务处理函数*/
int arg1, /*任务处理函数需要的参数*/
int arg2,
int arg3,
int arg4,
int arg5,
int arg6,
int arg7,
int arg8,
int arg9,
int arg10
)
SEM_ID semBCreate
(
int options, /*信号量的特性,例如信号量的阻塞队列类型为优先级优先行还是FIFO*/
SEM_B_STATE initialState /* 信号量的初始状态:empty or full,用来同步或者资源互斥*/
)
返回的值就是改信号量的ID,实际上就是指向信号量的指针啦

部分函数详细说明

1.taskSpawn 创建(产生并激活)新任务
int taskSpawn
(
char *name,
int priority,
int options,
int stackSize,
FUNCPTR entryPt,
int arg1,
int arg2, int arg3,
int arg4, int arg5,
int arg6, int arg7,
int arg8, int arg9,
int arg10
)
函数运行成功返回任务ID号,否则为ERROR。
任务可选项的几种模式如下表:
名 称

描 述
VX_FP_TASK
VX_NO_STACK_FILL
VX_PRIVATE_ENV
VX_UNBREAKABLE
VX_SUPERVISOR_MODE
0x8
0x100
0x80
0x2
运行带浮点的协处理器
不使用0xee填充堆栈
用私有环境运行任务
断点失效
用户任务常用值

2.taskDelete 删除一个任务
STATUS taskDelete
(
int tid
)
删除指定ID号的任务,并释放任务所占有的内存
3.taskDelay 延迟任务
STATUS taskDelay
(
int ticks
)
任务延迟为某一任务休眠一定时间提供了简单的处理方法,一般用于任务的周期性循环执行。当输入参数为NO_WAIT(其值为零)时,表示将所延迟的任务切换到同一优先级就绪队列的尾部。
4.taskSuspend 任务悬置
STATUS taskSuspend
(
int tid
)
5.taskResume 恢复任务
STATUS taskResume
(
int tid
)
6.msgQCreate 创建并初始化消息队列
#include <msgQLib.h>
MSG_Q_ID msgQCreate
(
int maxMsgs,
int maxMsgLength,
int options
)
消息入列方式有两种:MSG_Q_FIFO 先进先出 ,按时间先后顺序考虑;MSG_Q_PRIORITY 按消息优先级考虑。
7.msgQSend 向一消息队列发送消息包
STATUS msgQSend
(
MSG_Q_ID msgQId,
char * buffer,
UINT nBytes,
int timeout,
int priority
)
该函数将长度为nBytes的缓冲区buffer消息包发向消息队列msgQId. 如果任务正在等待接收该消息队列的消息包,消息将立即被送到第一个等待的任务。如果没有任务等待此消息,消息包被保留在消息队列中。
参数timeout指明:当消息队列已满时,等待消息队列有空间时所等待的时间。超过该时间还没空间可用的话,消息包被舍弃。它有两个特殊值:NO_WAIT(0)立即返回,不管消息包是否被发送;WAIT_FOREVER(-1)一直等待消息队列有空间可用。
参数priority指明发送的消息的优先级,可能值有:MSG_PRI_NORMAL(0)正常优先级,将消息置于消息队列的尾部;MSG_PRI_URGENT(1)紧急消息,将消息置于消息队列的首部。
8.msgQReceive 接收消息
int msgQReceive
(
MSG_Q_ID msgQId,
char * buffer,
UINT maxNBytes,
int timeout
)
该函数从消息队列msgQId接收消息,将其拷贝到最大长度为maxNBytes的缓冲区buffer。如果消息包长度超过maxNBytes,多余部分被舍弃。等待时间timeout有两个特殊值: NO_WAIT(0)立即返回;WAIT_FOREVER(-1)一直等待消息队列有消息可取。
9.msgQDelete 删除一个消息队列
STATUS msgQDelete
(
MSG_Q_ID msgQId
)
任何因发送或接收该消息队列的消息的任务都将解阻,并返回错误errno.
10. wdCreate 创建看门狗定时器
WDOG_ID wdCreate(void)
11. wdStart 启动定时器
STATUS wdStart

WDOG_ID wdId,
int delay,
FUNCPTR pRoutine,
int parameter

12. wdCancel 取消一个当前工作的定时器
STATUS wdCancel
(
WDOG_ID wdId
)
该函数只是让定时器的延迟值为零来取消其工作。
13. wdDelete 删除定时器
STATUS wdDelete
(
WDOG_ID wdId
)
14. semBCreate 创建并初始化二进制信号量
SEM_ID semBCreate
(
int options,
SEM_B_STATE initialState
)
信号量初始化状态值有两种:SEM_FULL(1)或SEM_EMPTY(0)。选项参数指明被阻塞任务的入列方式:基于优先级(SEM_Q_PRIORITY)和先进先出(SEM_Q_FIFO).
15. semCCreate 创建并初始化计数信号量
SEM_ID semCCreate
(
int options,
int initialCount
)
选项参数指明被阻塞任务的入列方式:基于优先级(SEM_Q_PRIORITY)和先进先出(SEM_Q_FIFO).
16. semGive 给出信号量
STATUS semGive
(
SEM_ID semId
)
17. semTake 获得信号量
STATUS semTake
(
SEM_ID semId
int timeout
)
如果任务在规定时间内未得到信号量,函数semTake返回错误。等待时间值WAIT_FOREVER和NO_WAIT分别表示一直等待和不等待。
18. semDelete 删除信号量
STATUS semDelete
(
SEM_ID semId
)
该函数释放与此信号量相关的资源,所有等待此信号量的任务解阻。
semMCreate( ) 分配并初始化一个互斥信号量

semCCreate( ) 分配并初始化一个计数信号量

semDelete( ) 终止一个自由的信号量

semTake( ) 占有一个信号量

semGive( ) 释放一个信号量

semFlush( ) 解锁所有等待信号量的任务

semBCreate( ), semMCreate( ), and semCCreate( )返回一个信号量ID作为其它后续任务使用该信号量的的句柄。当一个信号量被创建,它的队列(queue)类型就被确定。等待信号量的任务队列以优先级的高低排列(SEM_Q_PRIORITY),或者一先到先得的方式排列(SEM_Q_FIFO).

·         当一个Semaphore创建时,指定了任务队列的种类

A.    semBCreat( SEM_Q_PRIORITY, SEM_FULL),   SEM_Q_PRIORITY 指明处于等待状态的任务在等待队列中以优先级的顺序排列

B.    semBCreat(SEM_Q_FIFO,SEM_FULL),   SEM_Q_FIFO指明 处于等待状态的任务在等待队列中以先进先出的顺序排列

1.  二进制信号量(  binary)

Taking a Semaphore

Giving a Semaphore

互斥进程(Mutual Exclusion)

互斥信号量有效的内锁对共享资源的进入,与屏蔽中断(disabling interrupts)和优先级锁定(preemptive locks)相比,二进制信号量将互斥的范围限制在仅与其有关的资源上。从技术上说,创建一个信号量来保护(guarding)资源。信号量初始化位可用的(FULL)。

当一个Semaphore创建时,指定了这个semaphore是用在解决互斥还是用来同步任务

A.    semBCreat( SEM_Q_FIFO, SEM_FULL) ,  SEM_FULL 指明用于任务间互斥.

SEM_ID semMutex;

semMutex = semBCreate (SEM_Q_PRIORITY, SEM_FULL);

当一个任务要进入资源,首先要得到一个信号量(take that semaphore),只要有任务在使用这个信号量,其它的要进入资源的任务要停止执行(blocked from execution),当这个任务完成了对资源的使用,它会释放信号量,允许另一个任务来使用资源。

semTake (semMutex, WAIT_FOREVER);

. .  critical region, only accessible by a single task at a time .

semGive (semMutex);

同步协调进程(Synchronization)

B.    semBCreat(SEM_Q_FIFO,SEM_EMPTY),  SEM_EMPTY 指明用于任务间同步.

#include "vxWorks.h"

#include "semLib.h"

SEM_ID syncSem;

init ( int someIntNum )

{

intConnect (INUM_TO_IVEC (someIntNum), eventInterruptSvcRout, 0);

syncSem = semBCreate (SEM_Q_FIFO, SEM_EMPTY);

taskSpawn ("sample", 100, 0, 20000, task1, 0,0,0,0,0,0,0,0,0,0);

}

task1 (void)

{ ...

semTake (syncSem, WAIT_FOREVER);

printf ("task 1 got the semaphore/n");

...

}

eventInterruptSvcRout (void)

{ ...

semGive (syncSem);

...

}

semTake(semID,time out)--------有Semaphore空闲,就Take, 如果没有,由time out 定,超时则向下执行

2.  互斥信号量

互斥信号量是一个特殊的二进制信号量,设计用于优先级继承,安全删除和回归。

互斥信号量的使用基本和二进制信号量是类似的。但有以下不同:

·         仅仅被用做互斥。

·         只能被使用它的任务释放.(It can be given only by the task that took it.)

·         ISR 不能释放它。

·         不能使用函数semFlush( )。

优先级反转(Priority Inversion)

优先级反转是指一个任务等待比它优先级低的任务释放资源而被阻塞,如果这时有中等优先级的就绪任务,阻塞会进一步恶化。优先级继承技术可用来解决优先级反转问题。

Priority inversion arises when a higher-priority task is forced to wait an indefinite period of time for a lower-priority task to complete.

优先级继承(Priority Inheritance)

优先级继承可用来解决优先级反转问题。当优先级反转发生时,优先级较低的任务被暂时地提高它的优先级,使得该任务能尽快执行,释放出优先级较高的任务所需要的资源。

Priority Inheritance

The mutual-exclusion semaphore has the option SEM_INVERSION_SAFE, which enables a priority-inheritance algorithm. The priority-inheritance protocol assures that a task that owns a resource executes at the priority of the highest-priority task blocked on that resource. Once the task priority has been elevated, it remains at the higher level until all mutual-exclusion semaphores that the task owns are released; then the task returns to its normal, or standard, priority. Hence, the "inheriting" task is protected from preemption by any intermediate-priority tasks. This option must be used in conjunction with a priority queue (SEM_Q_PRIORITY).

3.  计数信号量(Counting Semaphores)

计数信号量是任务同步和互斥的另一种实现方式.计数信号量除了保留信号量被释放的次数以外和二进制信号量是一样的。每次信号量被释放(gaven)一次,计数增加;每次信号量被占用(taken)一次,计数减少;当计数减少为0时,要求得到信号量的任务被阻塞(blocked)。二进制信号量是如果一个信号量被释放,有一个任务阻塞等待,则这个任务就被unblock.而计数信号量如果一个信号量被释放,没有任务阻塞等待,则计数增加。这说明一个被释放两次的计数信号量可以被占用(taken)两次,没有阻塞。

Counting semaphores are useful for guarding multiple copies of resources. For example, the use of five tape drives might be coordinated using a counting semaphore with an initial count of 5, or a ring buffer with 256 entries might be implemented using a counting semaphore with an initial count of 256. The initial count is specified as an argument to the semCCreate( ) routine.

Counting Semaphore Example

--------------------------------------------------------------------------------

Semaphore Call
 Count after Call
 Resulting Behavior

--------------------------------------------------------------------------------

semCCreate( )  
 3
 Semaphore initialized with initial count of 3. 
 
semTake( ) 
 2
 Semaphore taken. 
 
semTake( ) 
 1
 Semaphore taken. 
 
semTake( ) 
 0
 Semaphore taken. 
 
semTake( ) 
 0
 Task blocks waiting for semaphore to be available. 
 
semGive( ) 
 0
 Task waiting is given semaphore. 
 
semGive( ) 
 1
 No task waiting for semaphore; count incremented.

--------------------------------------------------------------------------------

消息队列(Message queues)

现实的实时应用由一系列互相独立又协同工作的任务组成。信号量为任务间同步和联锁提供了高效机制。在VxWorks中,用于但一CPU任务之间通信主要(primary)的机制是消息队列。

Full Duplex Communication Using Message Queues

消息队列允许一定数量不同长度的消息进行排列。任何任务或中断服务程序(ISR)能够发送消息给消息队列。任何任务可以从消息队列接受消息。多任务可以从同意消息队列发送和接受消息。两个任务之间的全双工(Full-duplex)通信需要针对不同方向的两个消息队列。

消息队列函数介绍

msgQCreate( )  创建斌初始化一个消息队列

msgQDelete( ) 终止并释放一个消息队列

msgQSend( )  发送一个消息到消息队列

msgQReceive( ) 从消息队列接受一个消息

消息队列是由函数msgQCreate (MAX_MSGS, MAX_MSG_LEN, MSG_Q_PRIORITY)创建。它的参数MAX_MSGS指定了消息队列中可允许最多可以排列的消息数和每个消息允许的最大的字节数MAX_MSG_LEN。

一个任务或中断服务程序(ISR)用函数msgQSend( )发送一个消息到消息队列。如果没有任务等待消息队列的消息,这个消息被添加消息缓存的队列里。如果某些任务已经在等待消息队列中的消息,消息立刻被传递给第一个等待的消息的任务。

一个任务用函数msgQReceive( )从消息队列得到一个消息。如果消息队列缓存中有消息存在,第一个消息立刻出列并回到调用处(caller).如果没有消息存在,则任务(calling task)停止(blocks)并被添加到等待消息的任务队列中。这个等待的任务队列按照优先级或先进先出(FIFO)规则排列,这个规则有消息队列创建时所指定。

等待时间限制(time out)

msgQSend( ) 和 msgQReceive( )都有时间限制参数。当发送一个消息,如果消息队列缓存这时没有空间,这个参数指定允许等待的时间(ticks数),直到队列缓存有空间来接收消息。当接收消息时,如果消息队列没有消息,这个参数指定允许等待的时间(ticks数),直到消息队列有消息。

#include "vxWorks.h"

#include "msgQLib.h"

#define MAX_MSGS (10)

#define MAX_MSG_LEN (100)

MSG_Q_ID myMsgQId;

task2 (void)

{

char msgBuf[MAX_MSG_LEN];

if (msgQReceive(myMsgQId, msgBuf, MAX_MSG_LEN, WAIT_FOREVER) == ERROR)

return (ERROR);

printf ("Message from task 1:/n%s/n", msgBuf);

}

#define MESSAGE "Greetings from Task 1"

task1 (void)

{

if ((myMsgQId = msgQCreate (MAX_MSGS, MAX_MSG_LEN, MSG_Q_PRIORITY))

== NULL)

return (ERROR);

if (msgQSend (myMsgQId, MESSAGE, sizeof (MESSAGE), WAIT_FOREVER,

MSG_PRI_NORMAL) == ERROR)

return (ERROR);

}

管道(Pipes)

管道对消息队列提供了一个可供选择的接口,VxWorks的I/O系统。管道是虚拟的I/O设备,由驱动pipeDrv管理。函数pipeDevCreate()创建一个管道设备,这个调用指定管道的名字,能被排列的最多的消息数,和每个消息允许的长度。

status = pipeDevCreate ("/pipe/name", max_msgs, max_length);

被创建的管道是一个通常命名(named)的I/O设备,任务能用标准的I/O函数打开,读,写管道,并能调用ioctl例程。当任务试图从一个空的管道中读取数据,或向一个满的管道中写入数据时,任务被阻塞。和消息队列一样,ISR可以向管道写入,但不能从管道读取。

做为I/O设备,管道提供了消息队列所没有的重要特性,调用select()

常用Vxworks编程API的更多相关文章

  1. 已看1.熟练的使用Java语言进行面向对象程序设计,有良好的编程习惯,熟悉常用的Java API,包括集合框架、多线程(并发编程)、I/O(NIO)、Socket、JDBC、XML、反射等。[泛型]\

    1.熟练的使用Java语言进行面向对象程序设计,有良好的编程习惯,熟悉常用的Java API,包括集合框架.多线程(并发编程).I/O(NIO).Socket.JDBC.XML.反射等.[泛型]\1* ...

  2. Hadoop MapReduce编程 API入门系列之压缩和计数器(三十)

    不多说,直接上代码. Hadoop MapReduce编程 API入门系列之小文件合并(二十九) 生成的结果,作为输入源. 代码 package zhouls.bigdata.myMapReduce. ...

  3. WPF工作笔记:本地化支持、主进程通知、两种最常用异步编程方式

    1.本地化支持 (1)重写控件默认的依赖属性LanguageProperty FrameworkElement.LanguageProperty.OverrideMetadata( typeof(Fr ...

  4. Func常用模块及API

    Func常用模块及API Func提供了非常丰富的功能模块,包括: CommandModule(执行命令) CopyFileModule(拷贝文件) CpuModule(CPU信息) DiskModu ...

  5. 社交网络编程API之iOS系统自带分享

    社交网络编程API 社交网络编程主要使用iOS提供的Social框架,目前Social框架主要包含两个类: SLComposeViewController 提供撰写社交信息(如微博信息)的视图控制器, ...

  6. 常用的百度API地图操作

    常用的百度API地图操作,包括模糊搜索,放大缩小,并支持移动端 效果图如下 完整代码: http://download.csdn.net/detail/jine515073/8778167

  7. HBase编程 API入门系列之create(管理端而言)(8)

    大家,若是看过我前期的这篇博客的话,则 HBase编程 API入门系列之put(客户端而言)(1) 就知道,在这篇博文里,我是在HBase Shell里创建HBase表的. 这里,我带领大家,学习更高 ...

  8. 描述一下你最常用的编程风格---JAVA

    描述一下你最常用的编程风格---JAVA     描述一下你最常用的编程风格---JAVA   (1)类名首字母应该大写.字段.方法以及对象(句柄)的首字母应小写.对于所有标识符,其中包含的所有单词都 ...

  9. HBase编程 API入门系列之delete(客户端而言)(3)

    心得,写在前面的话,也许,中间会要多次执行,连接超时,多试试就好了. 前面的基础,如下 HBase编程 API入门系列之put(客户端而言)(1) HBase编程 API入门系列之get(客户端而言) ...

随机推荐

  1. 实现mysql的分组排名问题

    如下图所示的表结构,mysql中查出按照相同class的成员按照年龄排序. sql语句实现如下: SELECT id,name,age,rank FROM ( ,) AS rank,@pa:=ff.c ...

  2. 浏览器的重绘repaints与重排reflows深入分析

    重绘是一个元素外观的改变所触发的浏览器行为,浏览器会根据元素的新属性重新绘制,使元素呈现新的外观,接下来将详细介绍,需要了解的朋友可以参考下: 在项目的交互或视觉评审中,前端同学常常会对一些交互效果质 ...

  3. php-mysql 问题笔记一——在命令行中可以执行的sql语句,无法从php页面页面执行!

    我的情况: 1.由于外键较多,插入数据时,提前关闭外键(SET FOREIGN_KEY_CHECKS=0). 2.所使用的sql语句中,有外键绑定到其他表中,所以无法从php页面插入. 原因分析: S ...

  4. 《零基础学习Python》01

    前言 Python是一种跨平台的语言 安装Python(Mac OS X) 1.在www.python.org/downloads 中下载Python,然后像安装其他软件一样进行安装. 2.打开: 找 ...

  5. Hibernate实现分页

    转自:http://blog.csdn.net/huqiub/article/details/4329541 分页在任何系统中都是非常头疼的事情,有的数据库在语法上支持分页,而有的数据库则需要使用可滚 ...

  6. 传智播客C/C++学员荣膺微软&Cocos 2d-x黑客松最佳创新奖

     6月30日,历时32小时的微软开放技术Cocos 2d-x 编程黑客松在北京望京微软大厦成功落下帷幕,这是微软开放技术首次联合Cocos 2d-x 在中国举办黑客松.此次活动共有包括传智播客C/ ...

  7. 二叉查找树的Find,FindMin,FindMax的递归和非递归实现

    typedef struct TreeNode *Position; typedef struct TreeNode *SearchTree; struct TreeNode{ ElementType ...

  8. OpenGL红宝书学习笔记(1)

    OpenGL对场景中的图像进行渲染时所执行的主要操作: 1.根据几何图元创建形状,从而建立物体的数学描述,(OpenGL把点,直线,多边形和位图作为基本的图元) 2.在三维空间中排列物体,并选择观察复 ...

  9. getBoundingClientRect()来获取页面元素的位置”

    getBoundingClientRect()来获取页面元素的位置” 获取的是一个对象; 延伸阅读; https://mp.weixin.qq.com/s?__biz=MzAxODE2MjM1MA== ...

  10. ListView实现上拉下拉刷新加载功能

    第一步.首先在你项目中创建一个包存放支持下拉刷新和上拉加载的类: