1.VxWorks I/O系统

VxWorks I/O系统可以为任何类型的设备提供简单、统一、与设备独立的管理接口。这些设备包括:

  1. 字符设备:如终端或通信线路;
  2. 随机访问块设备:如磁盘;
  3. 虚拟设备:如任务间的管道pipes和sockets;
  4. 监控设备:如数字和模拟I/O设备;
  5. 网络设备:如可进行远程访问的设备;

VxWorks I/O系统为基础I/O与带缓冲的I/O均提供了标准的C库。基础I/O库与Unix兼容;带缓冲的I/O库与ANSI兼容。

内核I/O

因其独特的设计,使得VxWorks I/O系统比大多数的其他I/O系统更快、更灵活。这对实时系统是一个很重要的属性。

下图展示了VxWorks内核I/O系统中不同元素之间的关系。除了文件系统函数与网络元素之外,其余元素具有进行描述。

VxWorks 7 System IO

I/O系统与RTP应用程序

下图展示了可供RTP使用的VxWorks I/O系统元素之间的关系。后续将对这些元素进行描述。

VxWorks 7 System IO

VxWorks I/O与主机系统I/O之间的区别

VxWorks在内核中提供了看门狗机制,允许任何C函数以特定的延时挂接到一个定时器上。

看门狗定时器被作为系统时钟ISR的一部分而维持。由看门狗定时器触发的函数,将作为系统时钟的中断服务代码而执行。如下函数由wdLib库提供:

VxWorks 7 Watch Dog

看门狗定时器示例

VxWorks 7 Watch Dog

静态实例化看门狗定时器

1.信号

信号作为一种操作系统机制,用于处理异常条件并对控制流进行异步通知。在很多方面,信号是一种类似于硬件中断的软件机制。为响应总线错误、浮点数异常等,操作系统都会产生对应的信号。信号机制提供了用于产生与管理信号的API。

对于应用程序,信号最适合用于错误和异常处理,对于任务间通信则不太适合。常见的使用方式包括:使用信号杀死进程和任务、当定时器到达或当一个消息到达消息队列,则发送一个信号事件,等等。

为了与POSIX保持一致,VxWorks提供了63个信号,每个信号都有单独的信号值以及默认的动作(在signal.h中定义)。NULL signal将使用预留的信号值0。

信号可以在任务到任务或任务到进程之间发送。任务可以选择接受或忽略一个信号。信号是被接收或被忽略,都取决于信号掩码(signal mask)的设置情况。在内核中,信号掩码是任务所特有的,如果没有任务被设置为接受某个特定的信号,那么这个信号将被忽略。在用户空间中,信号掩码是进程所特有的。有些信号如SIGKILL和SIGSTOP是不能被忽略的。

为了响应信号,可以创建并注册信号处理函数,使得任务可以响应一个特定的信号。一个内核任务或ISR可以向特定的任务和进程发送信号。在内核中,信号的产生与传递过程都是在产生信号的任务上下文或ISR中进行。为了与POSIX标准保持一致,一个发送给进程的信号,都是由第一个已经设置了可以处理该信号的进程负责。

每个内核任务都有一个与之相关的信号掩码。信号掩码决定了任务将接受哪些信号。默认情况下,信号掩码在初始化时被设置为不屏蔽任何信号(在内核中不存在掩码继承)。可以使用sigprocmask()函数修改掩码。

在内核中,可以为一个特定的任务注册信号处理函数。信号处理函数在接收信号的任务的上下文中执行,并且使用了该任务的执行栈空间。即使任务被阻塞,也会调用信号处理函数。

VxWorks提供了软件信号机制,其中包括了POSIX函数、UNIX BSD兼容的函数以及VxWorks原生的函数。POSIX兼容的信号接口既包括由POSIX1003.1规定的基本信号接口,也包含了由POSIX1003.1B规定的队列信号扩展。

此外,非POSIX API提供了内核与用户应用程序之间的信号。包括taskSigquue()、rtpSigqueue()、rtpTaskSigqueue()、taskKill()、rtpTaskKill()、taskRaise()。

在VxWorks内核中(为了向后兼容),当类POSIX接口需要使用进程ID作为其参数时,应该使用任务ID代替。

一个RTP任务(用户模式)可以向如下目标发送信号:

1.中断服务程序ISR

外部事件通常通过中断的方式通知系统,因此硬件中断处理是实时操作系统中的关键功能。

为了以最快速度响应中断,VxWorks中断服务程序执行在独有的上下文,而非任何任务是上下文中。除非系统专门进行过配置,否则不会推迟ISR的执行。

2.针对ISR的VxWorks配置

VxWorks系统默认支持SIR。中断栈可以按大小和附加特性进行配置。中断栈必须足够大,以处理中断嵌套时的最坏情况。

中断栈配置

所有的的ISR使用相同的中断栈空间。系统将在初始化时根据设定的配置参数为中断栈分配空间。其大小必须足够大,以应付中断嵌套时的最坏情况。中断栈大小由宏ISR_STACK_SIZE定义。

注意:某些架构不允许使用独立的中断栈,而需要使用被中断任务的栈空间。在这种架构下,必须确保创建任务时分配了足够大的栈空间,以处理中断嵌套和嵌套调用的最坏情况。

中断栈填充

默认情况下,中断栈空间被填充为0xEE。对栈空间进行填充的做法,对于开发过程中的调试很有帮助。具体可以使用checkStack()函数进行栈空间检查。

在进行系统配置时,建议不要对中断栈空间进行填充,以获得更佳的性能。可以使用配置参数VX_GLOBAL_NO_STACK_FILL关闭栈空间填充功能。

中断栈保护

如果使能了MMU功能,系统就可以通过配置INCLUDE_PROTECT_INTERRUPT_STACK组件,提供对中断栈始末的guard zone保护。

可以通过如下配置参数设置guard zone的大小:

  • INTERRUPT_STACK_OVERFLOW_SIZE:设置中断栈上溢大小;
  • INTERRUPT_STACK_UNDERFLOW_SIZE:设置中断栈下溢大小;

当添加了guard zone,栈空间的大小通常是MMU大小的整数倍。

1. 任务与多任务

多任务环境允许实时应用程序由一系列独立的任务构成,这些任务拥有自己的执行与系统资源。

2. VxWorks系统任务

根据具体的配置,VxWorks在启动时将运行各种系统任务,其中有些任务会一直运行。

VxWorks基础任务如下: