VxWorks 6.9 內核編程指導之讀書筆記 -- VxWorks kernel application (一)


#1 什么是內核應用程序?

#2 開發內核應用程序注意事項

 

什么是內核應用程序?

內核應用程序不同於RTP程序,它允許在內核態,與操作系統使用相同的地址空間。因此,它與操作系統會相互干擾。它可以編譯成內核應用程序模塊,亦可以與操作系統映像靜態連接生成一個映像。應用程序模塊可以被動態加載,因此在開發和調試階段非常有用,它不必重新編譯操作系統映像,並且可以存放在任何內核支持的文件系統中,如NFS,使用ROMFS文件系統的FLASH或ROM中,或磁盤上。但是,與操作系統靜態鏈接顯然更適合生產使用。

由於,內核應用程序運行在內核態,因此可以直接訪問硬件,這與RTP不同,RTP運行在用戶態,無法與硬件直接交流。內核應用程序無法直接啟動,必須由其它程序或操作系統來啟動它(可以通過shell或workbench來啟動),也可以通過配置在引導時自動啟動。

 內核應用程序的代碼構建的二進制對於不同的處理器並不兼容,因此,針對不同的處理器需要構建不同的二進制文件,如UP,SMP,32位的VxWorks或64位的VxWorks等。

開發注意事項

使用的C或C++類庫

應用程序類型

C語言

C++語言

內核應用程序

VxWorks本地庫

Dinkum C++和嵌入式(abridged)C++庫

RTP應用程序

Dinkum C庫

Dinkum C++和嵌入式(abridged)C++庫

內核應用程序結構

內容應用程序類似普通的C/C++應用程序,但是它不需要傳統的main函數(不像RTP需要main)。它可以是任意函數,在該函數中啟動所有需要運行的任務。

 1 void myAppStartUp (void)
 2 {
 3     runFoo();
 4     tidThis = taskSpawn("tThis", 200, 0, STACK_SIZE,
 5         (FUNCPTR) thisRoutine,0,0,0,0,0,0,0,0,0,0);
 6     tidThat = taskSpawn("tThat", 220, 0, STACK_SIZE,
 7         (FUNCPTR) thatRoutine,0,0,0,0,0,0,0,0,0,0); 
 8     tidAnother = taskSpawn("tAnother", 230, 0, STACK_SIZE,
 9         (FUNCPTR) anotherRoutine,0,0,0,0,0,0,0,0,0,0);
10     return (OK);
11 }

VxWorks的頭文件

要使用VxWorks的工具類庫,必須要包含相應的頭文件。VxWorks頭文件只支持ANSI C函數原型,遵循ANSI X3.159-1989標准。

  1. 首先,必須先包含頭文件vxWorks.h -- 它包含了基本定義和類型
  2. 其次,可以根據需要包含其它頭文件如lstLib.h
  3. ANSI頭文件,大部分是與編譯器無關,但是有少部分與編譯相關(如stdef.h和stdarg.h),工具鏈會自動找到內部頭文件,不必用戶指定。
  4. ANSI C++頭文件,每個編譯器都有自己的C++庫和C++頭文件(如iosream和new)。C++頭文件在安裝編譯器時存放在安裝目錄,而不是/target/h里。
  5. -I編譯選項,該選項可以指定,編譯器搜索頭文件的路徑。
  6. 一些頭文件包含了更底層的頭文件,如tylib.h使用了rnglib.h。
  7. VxWork私有頭文件,通常以/*HIDDEN*/ ... /*END HIDDEN*/包含。

自定義頭文件

在自定義頭文件中別用extern “C”語句來保護系統頭文件。所有VxWorks系統頭文件已經被配置成可以被C和C++使用。因此,你不可以強迫使用C連接這些頭文件內容。如下是錯誤的:

#ifdef _cplusplus                                                                                  #include <stdio.h>

extern "C" {                                     ==========>                            #ifdef _cplusplus

#endif                                                                                                  extern "C" {

#include <stdio.h>                                                                                #endif

另外,也別在C++源代碼文件中使用 extern “C”{ #include <stdio.h>},而應該直接使用 #include <stdio.h>

內核對象的靜態實例化

VxWorks內核對象--如任務或信號量--既可以靜態實例化亦可以動態實例化,靜態實例化提高了性能。有特定的C宏來靜態實例化內核對象。

靜態實例化

靜態實例化,指的是對象在編譯時被聲明(使用特定的VxWorks宏),通常是全局對象。因此在編譯時分配了內存,而不需要在運行時分配。對象可以在啟動初始化時直接獲得。

相對靜態實例化,動態實例化涉及到運行時分配,並在使用前初始化,在刪除時需要刪除對象,並釋放系統內存等,通常使用malloc和new來進行。使用動態實例化,必須考慮內存不足,另外,性能更差。

 

Dynamic Instantiation 
struct my_object * pMyObj;
...
pMyObj = (struct my_object *) malloc (sizeof (struct my_object));
if (pMyObj != NULL)
{
fooObjectInit (pMyOjb);
return (OK);
}
else
{
/* failure path */
return (ERROR);
}
Static Instantiation 
struct my_object myObj;
...
fooObjectInit (&myOjb);
/* myObj now ready for use */

可以被靜態實例化的內核對象

  1. 任務
  2. 信號量
  3. 消息隊列
  4. 看門狗時鍾

靜態實例化的代碼大小

編譯時聲明的對象並不占用可執行文件、VxWorks映像或存儲介質的任何空間。如果只聲明而沒有初始化,則編譯器將數據存放在bss段。

靜態實例化的好處

  1. 訪問更快,更確定
  2. 應用程序邏輯更簡單,因為不需要考慮內存不足問題。
  3. 對象的靜態實例化不會失敗,除非應用程序本身太大,無法加載到系統內存。
  4. 可以移除動態內存分配模塊,使得VxWorks內核更小。

應用程序和靜態實例化

靜態初始化提供了更好的性能和優勢。如果對象永遠不會被刪除,則盡量使用靜態實例化。靜態實例化應該只用於內核應用程序,而不應該在RTP中使用。

靜態實例化范圍

內核對象通常做為全局變量,因為對象ID常用來任務間通信和同步。但是,並不是必須是全局的,也可以函數范圍的。

宏的使用

如何代碼太長需要要反斜杠來連接,如

myTask = VX_TASK_INSTANTIATE(myTask,100,0,4096,pEntry,\

                          0,1,2,3,4,5,6,7,8,9);

宏VX_TASK_INSTANTIATE用來靜態實例化任務

下載內核應用程序對象模塊到目標

內核應用程序對象模塊可以從Workbench或kernel的shell中下載。一旦被加載到目標系統內存,模塊的任何子函數可以被調用,可以啟動任務,調試等。

鏈接內核應用程序對象模塊到VxWorks中

可以使用Workbench和命令行與VxWorks映像連接在一起。

配置VxWorks自動運行內核應用程序

  1. 配置VxWorks啟用INCLUDE_USER_APPL組件
  2. 在usrAppInit函數中調用應用程序的入口函數,假設應用程序的入口點函數是myAppStartUp,那么按如下方式添加到usrAppInit中,void usrAppInit(){... myAppStartUp();}
  3. 鏈接內核應用程序與內核映像。

映像大小的考慮

一般bootloader會把bootloader的代碼拷貝到RAM_HIGH_ADRS處的RAM中的,而把VxWorks映像拷貝到RAM_LOW_ADRS,因此,必須確保VxWorks的映像不會超過RAM_HIGH_ADRS-ROW_LOW_ADRS,否則將覆蓋bootloader的代碼,導致bootloader進程意外終止。

對應自啟動的VxWorks映像,則需包裝RAM_HIGH_ADRS小於LOCAL_MEM_SIZE。

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM