嵌入式 WEB 服務(wù)器 BOA 和 CGI
一、嵌入式 WEB 服務(wù)器 BOA 簡介
嵌入式 WEB 服務(wù)器常見的有:
boa
lighttpd
shttpd
thttpd
mathopd
minihttpd
appweb
goahead
隨著 Internet 技術(shù)的興起,在嵌入式設(shè)備的管理與交互中,基于 Web 方式
的應用成為目前的主流,這種程序結(jié)構(gòu)也就是大家非常熟悉的 B/S 結(jié)構(gòu),即在
嵌入式設(shè)備上運行一個支持腳本或 CGI 功能的 Web 服務(wù)器,能夠生成動態(tài)頁面,
在用戶端只需要通過 Web 瀏覽器就可以對嵌入式設(shè)備進行管理和監(jiān)控,非常方
便實用。
本節(jié)主要介紹這種應用的開發(fā)和移植工作。
用戶首先需要在嵌入式設(shè)備上成功移植支持腳本或 CGI 功能的 Web 服務(wù)器,然
后才能進行應用程序的開發(fā)。
1、 嵌入式 Web 服務(wù)器移植 ,由于嵌入式設(shè)備資源一般都比較有限,并且
也不需要能同時處理很多用戶的請求,因此不會使用 Linux 下最常用的如
Apache 等服務(wù)器,而需要使用一些專門為嵌入式設(shè)備設(shè)計的 Web 服務(wù)器,這些
Web 服務(wù)器在存貯空間和運行時所占有的內(nèi)存空間上都會非常適合于嵌入式應
用場合。典型的嵌入式 Web 服務(wù)器有 Boa (www.boa.org)和 thttpd
(http://www.acme.com/software/thttpd/)等,它們和 Apache 等高性能的
Web 服務(wù)器主要的區(qū)別在于它們一般是 單進程服務(wù)器,只有在完成一個用戶請
求后才能響應另一個用戶的請求,而無法并發(fā)響應,但這在嵌入式設(shè)備的應用
場合里已經(jīng)足夠了。
Boa 是一個非常小巧的 Web 服務(wù)器,可執(zhí)行代碼只有約 60KB。它是一個單
任務(wù) Web 服務(wù)器,只能依次完成用戶的請求,而不會 fork 出新的進程來處理
并發(fā)連接請求。但 Boa 支持 CGI,能夠為 CGI 程序 fork 出一個進程來執(zhí)行。
Boa 的設(shè)計目標是速度和安全,在其站點公布的性能測試中,Boa 的性能 要好
于 Apache 服務(wù)器。
Boa 程序的移植見附錄一。
二、CGI 和 CGIC 簡介
1、CGI
目前 Web 技術(shù)中生成動態(tài) Web 頁面的方法有 CGI 和服務(wù)器腳本,如 JSP,
ASP 等,但后者需要 Web 服務(wù)器具有這些腳本的運行支持模塊。在嵌入式 Web
服務(wù)器中,考慮到資源限制問題,一般都只提供 CGI 支持,因此在嵌入式設(shè)備
中 Web 方式應用實際上就是基于 CGI 的程序開發(fā)。
CGI(Common Gateway Intergace 通用網(wǎng)關(guān)界面)是一段運行在 Web 服務(wù)
器上的程序,提供同客戶端 Html 頁面的接口。我們舉個實際例子:常見的個人
主頁上大都有一個留言本,留言本的工作方式是這樣的:先由用戶輸入一些信
息,如名字之類的東西,接著用戶按一下“留言”(到目前為止工作都在客戶
端),瀏覽器就把這些信息傳送到服務(wù)器的 CGI 程序中,于是 CGI 程序在服務(wù)
器上按照預定的方法進行處理,在本例中就是把用戶提交的信息存入指定的文
件中,最后 CGI 程序給客戶端發(fā)回一個“留言結(jié)束”字樣的頁面,用戶可以在
瀏覽器里看到。
在進行 CGI 編程之前,我們先了解 HTML 的一些知識。CGI 可以使用多種編程
語言來實現(xiàn),包括 C、 C++、Perl 等,但在嵌入式設(shè)備的開發(fā)中,一般都不會
采用 Perl 等解釋性語言,因為這種語言還需要有解釋執(zhí)行的支撐模塊,會占用
存貯空間和內(nèi)存,最常用的方法當然是用 C 來編寫,但 C 并不是很適合開發(fā)象
CGI 這種需要大量進行字符串操作的程序,編程比較煩瑣,因此,對于一個專
業(yè)的開發(fā)人員來說,首先想到的應該是有沒有可復用的庫來支持快速高效的開
發(fā) CGI 程序。幸運的是目前就有不少開放源碼的支持 CGI 開發(fā)的 C 庫。我們在
此只介紹 CGIC,有興趣的朋友可以自己在 Internet 上搜索其他的 C 庫。
2、CGIC
CGIC 是一個支持 CGI 開發(fā)的開放源碼的標準 C 庫,可以免費使用,只需要
在開發(fā)的站點和程序文檔中有個公開聲明即可,表明程序使用了 CGIC 庫,用戶
也可以購買商業(yè)授權(quán)而無需公開聲明。
CGIC 能夠提供以下功能:
1 分析數(shù)據(jù),并自動校正一些有缺陷的瀏覽器發(fā)來的數(shù)據(jù);
2 透明接收用 GET 或 POST 方法發(fā)來的 From 數(shù)據(jù);
3 能接受上傳文件;
4 能夠設(shè)置和接收 cookies;
5 用一致的方式處理 From 元素里的回車;
6 提供字符串,整數(shù),浮點數(shù),單選或多選功能來接收數(shù)據(jù);
7 提供數(shù)字字段的邊界檢查;
8 能夠?qū)?CGI 環(huán)境變量轉(zhuǎn)化成 C 中的非空字符串;
9 提供 CGI 程序的調(diào)試手段,能夠回放 CGI 程序執(zhí)行時的 CGI 狀態(tài);
總之,CGIC 是一個功能比較強大的支持 CGI 開發(fā)的標準 C 庫,并支持 Linux,
Unix 和 Windows 等多操作系統(tǒng)。
使用 CGIC 的基本思路:
從 cgic.c 的代碼可以看出,它定義了 main 函數(shù),而在 cgictest.c 中
定義了一個 cgiMain 函數(shù)。也就是說,對于使用 CGIC 編寫的 CGI 程序,都
是從 cgic.c 中的代碼進入,在庫函數(shù)完成了一系列必要的操作(比如解析參
數(shù)、獲取系統(tǒng)環(huán)境變量)之后,它才會調(diào)用你的代碼(從你定義的 cgiMain 進
入)。
CGIC 庫的 移植與 cgi 編寫測試見附錄二。
附錄一:Boa 程序的移植(未測試,僅供參考,先用現(xiàn)成的)
第一步完成 Boa 程序的移植。從 www.boa.org 下載 Boa 源碼,
當前最新版本為 0.94.13,將其解壓并進入源碼目錄的 src
子目錄
# tar xzf boa-0.94.13.tar.gz
# cd boa-0.94.13/src
生成 Makefile 文件
# ./configure
修改 Makefile 文件,找到 CC=gcc,將其改成 CC = arm-linuxgcc,再找到 CPP = gcc –E,
將其改成 CPP = arm-linux-gcc –E,并保存退出。
然后運行 make 進行編譯,得到的可執(zhí)行程序為 boa,將調(diào)試信
息剝?nèi)?,得到的最后程序只有約 60KB 大小。
# make
# arm-linux-strip boa
第二步完成 Boa 的配置,使其能夠支持 CGI 程序的執(zhí)行。Boa 需
要在/etc 目錄下建立一個 boa 目錄,里面放入 Boa 的主要
配置文件 boa.conf。在 Boa 源碼目錄下已有一個示例 boa.conf,可
以在其基礎(chǔ)上進行修改,下面解釋一下該文件的含義:
#監(jiān)聽的端口號,缺省都是 80,一般無需修改
Port 80
# bind 調(diào)用的 IP 地址,一般注釋掉,表明綁定到 INADDR_ANY,
通配于服務(wù)器的所有 IP 地址
#Listen 192.68.0.5
#作為哪個用戶運行,即它擁有該用戶的權(quán)限,一般都是 nobody,
需要/etc/passwd 中有
#nobody 用戶
User nobody
#作為哪個用戶組運行,即它擁有該用戶組的權(quán)限,一般都是
nogroup,需要在/etc/group 文
#件中有 nogroup 組
Group nogroup
#當服務(wù)器發(fā)生問題時發(fā)送報警的 email 地址,目前未用,注釋掉
#ServerAdmin root@localhost
#錯誤日志文件。如果沒有以/開始,則表示從服務(wù)器的根路徑開始。
如果不需要錯誤日志,
則用#/dev/null。在下面設(shè)置時,注意一定要建立/var/log/boa 目錄
ErrorLog /var/log/boa/error_log
#訪問日志文件。如果沒有以/開始,則表示從服務(wù)器的根路徑開始。
如果不需要錯誤日志,
則用#/dev/null 或直接注釋掉。在下面設(shè)置時,注意一定要建立
/var/log/boa 目錄
#AccessLog /var/log/boa/access_log
#是否使用本地時間。如果沒有注釋掉,則使用本地時間。注釋掉則
使用 UTC 時間
#UseLocaltime
#是否記錄 CGI 運行信息,如果沒有注釋掉,則記錄,注釋掉則不
記錄
#VerboseCGILogs
#服務(wù)器名字
ServerName www.hyesco.com
#是否啟動虛擬主機功能,即設(shè)備可以有多個網(wǎng)絡(luò)接口,每個接口都
可以擁有一個虛擬的 Web 服
#務(wù)器。一般注釋掉,即不需要啟動
#VirtualHost
#非常重要,HTML 文檔的主目錄。如果沒有以/開始,則表示從服
務(wù)器的根路徑開始。
DocumentRoot /var/www
#如果收到一個用戶請求的話,在用戶主目錄后再增加的目錄名
UserDir public_html
#HTML 目錄索引的文件名,也是沒有用戶只指明訪問目錄時返回的
文件名
DirectoryIndex index.html
#當 HTML 目錄沒有索引文件時,用戶只指明訪問目錄時,boa 會調(diào)
用該程序生成索引文件然后
#返回給用戶,因為該過程比較慢最好不執(zhí)行,可以注釋掉或者給每
個 HTML 目錄加上#DirectoryIndex 指明的文件
#DirectoryMaker /usr/lib/boa/boa_indexer
#如果 DirectoryIndex 不存在,并且 DirectoryMaker 被注釋,那么
就用 Boa 自帶的索引
#生成程序來生成目錄的索引文件并輸出到下面目錄,該目錄必須是
Boa 能讀寫
# DirectoryCache /var/spool/boa/dircache
#一個連接所允許的 HTTP 持續(xù)作用請求數(shù)目,注釋或設(shè)為 0
都將關(guān)閉 HTTP 持續(xù)作用
KeepAliveMax 1000
#HTTP 持續(xù)作用中服務(wù)器在兩次請求之間等待的時間數(shù),以秒為單
位,超時將關(guān)閉連接
KeepAliveTimeout 10
#指明 mime.types 文件位置。如果沒有以/開始,則表示從服務(wù)器的
根路徑開始??梢宰⑨尩?br />#避免使用 mime.types 文件,此時需要用 AddType 在本文件里指明
MimeTypes /etc/mime.types
#文件擴展名沒有或未知的話,使用的缺省 MIME 類型
DefaultType text/plain
#提供 CGI 程序的 PATH 環(huán)境變量值
CGIPath /bin:/usr/bin:/usr/local/bin
#將文件擴展名和 MIME 類型關(guān)聯(lián)起來,和 mime.types 文件作用一
樣。如果用 mime.types
#文件,則注釋掉,如果不使用 mime.types 文件,則必須使用
#AddType application/x-httpd-cgi cgi
#指明文檔重定向路徑
#Redirect /bar http://elsewhere/feh/bar
#為路徑加上別名
Alias /doc /usr/doc
#非常重要,指明 CGI 腳本的虛擬路徑對應的實際路徑。一般所有
的 CGI 腳本都要放在實際路徑
#里,用戶訪問執(zhí)行時輸入站點+虛擬路徑+CGI 腳本名
ScriptAlias /cgi-bin/ /var/www/cgi-bin/
用戶可以根據(jù)自己需要,對 boa.conf 進行修改,但必須要保證其
他的輔助文件和設(shè)置必須和 boa.conf 里的配置相符,
不然 Boa 就不能正常工作。 在上面的例子中,我們還需要創(chuàng)建日志
文件所在目錄/var/log/boa,
創(chuàng)建 HTML 文檔的主目錄/var/www,將 mime.types 文件拷貝 到
/etc 目錄,
創(chuàng)建 CGI 腳本所在目錄/var/www/cgi-bin/。mime.types 文件用來指
明不同文件擴展名對應的 MIME 類型,
一般 可以直接從 Linux 主機上拷貝一個,大部分也都是在主機的
/etc 目錄下。
==================================================
=================
===================host
test=======================================
1.進入 boa-0.94.13/src
./configure
make
2.在 etc/下建立 boa 目錄并將 boa.conf 拷貝到該目錄下.更改
boa.conf
Group nogroup ===》Group 0
3.在 /var/log/下建立 boa 目錄,該目錄下可以查看 boa 服務(wù)器的日
志
4.其它的一些路徑
默認是/var/www 下的內(nèi)容可以訪問 (DocumentRoot
/var/www)
默認 cgi :ScriptAlias /cgi-bin/ /usr/lib/cgi-bin/ (cgi 可執(zhí)行程序放
在 /usr/lib/cgi-bin/目錄下)
例子 http://201.201.201.249/cgi-bin/cgi-test.cgi
CGIPath /bin:/usr/bin:/usr/local/bin
只有這些目錄下的命令可以被調(diào)用,如果要 root 的權(quán)限(如
ifconfig 配置 ip)需要加上/sbin
附錄二:CGIC 庫移植(測試通過,目標是路由器,mips架構(gòu))
一、CGIC 的移植過程:
從 CGIC 的主站點 http://www.boutell.com/cgic/下載源碼,當前最
新版本是 2.05 版。在任一目錄將其解壓并進入源碼目錄。
# tar xzf cgic205.tar.gz
# cd cgic205
# chmod 777 cgic205
修改 cgic205 中 Makefile 文件,
1. 找到 CC=gcc,將其改成 CC= mipsel -linux-gcc,
2. 找到 AR=ar,將其改成 AR= mipsel -linux-ar,
3. 找到 RANLIB=ranlib,將其改成 RANLIB= mipsel -linux-ranlib。
4. 找到 gcc cgictest.o -o cgictest.cgi ${LIBS},將其改成$(CC)
$(CFLAGS) cgictest.o -o cgictest.cgi ${LIBS},
5. 找到 gcc capture.o -o capture ${LIBS},將其改成$(CC)
$(CFLAGS) capture.o -o capture ${LIBS},
6. 文件存放路徑:找到
install: libcgic.a
cp libcgic.a /usr/local/lib
cp cgic.h /usr/local/include
改成:
install: libcgic.a
cp libcgic.a /work/RT288x_SDK/RT288x_SDK/source/lib/lib
cp cgic.h
/work/RT288x_SDK/RT288x_SDK/source/user/boa/cgi-bin
注意 cp 等命令前以 tab 鍵開頭,不要用空格鍵。
接下來第 7,8 兩步要獲取反轉(zhuǎn)意函數(shù)功能:
7.打開 cgic.c,找到這一行語句:
static cgiUnescapeResultType cgiUnescapeChars(char **sp,
char *cp, int len);
將 static 去掉,將聲明添加到 cgic.h,加 extern:
extern cgiUnescapeResultType cgiUnescapeChars(char **sp,
char *cp, int len);
8. 將結(jié)構(gòu)體:
typedef enum {
cgiUnescapeSuccess,
cgiUnescapeMemory
} cgiUnescapeResultType;
把這幾行語句復制到 cgic.h 文件中,并在這里把它注釋掉:
#if 0
typedef enum {
cgiUnescapeSuccess,
cgiUnescapeMemory
} cgiUnescapeResultType;
#endif
并保存退出。 然后運行 make 進行編譯。
添加編譯器路徑:
#export PATH=$PATH:/opt/buildroot-gcc342/bin/
#make
#make install
這樣 就生成庫文件 libcgic.a。
接下來用 cgic 編寫一個 cgi 例子:
二、用 cgic 編寫一個 cgi
1. 寫一段完整代碼 cgi_string_escape.c,保存到文件夾
/work/RT288x_SDK/RT288x_SDK/source /user/boa/cgi-bin 。
#include <stdio.h>
#include "cgic.h"
#include <string.h>
#include <stdlib.h>
extern char *cgiQueryString;
extern cgiUnescapeResultType cgiUnescapeChars(char **sp,
char *cp, int len);
int cgiMain() {
char * buffer;
cgiHeaderContentType("text/html");
fprintf(cgiOut, "<HTML><HEAD>n");
fprintf(cgiOut, "<TITLE>MyCGIC</TITLE></HEAD>n");
fprintf(cgiOut, "<BODY>");
cgiUnescapeChars(&buffer, cgiQueryString,
strlen(cgiQueryString));
fprintf(cgiOut, "<H1>I LOVE CGIC!東明電子研發(fā)部</H1>");
fprintf(cgiOut, "<H2>%s</H2>",buffer);
fprintf(cgiOut, "</BODY>n");
fprintf(cgiOut, "</HTML>n");
return 0;
}
2. 修改/work/RT288x_SDK/RT288x_SDK/source /user/boa/cgibin 下 makefile 文件。在相似處添加文件信息。
1)在 LDLIBS += -lnvram 下添加鏈接庫
LDLIBS += -lcgic
2)在 CGI_STRING = cgi_string.cgi 下添加變量
CGI_STRING_ESCAPE = cgi_string_escape.cgi
3)在 ALL_EXE += $(CGI_STRING)下添加
ALL_EXE += $(CGI_STRING_ESCAPE)
4)在
$(CGI_STRING): cgi_string.o
$(CC) -o $@ cgi_string.o $(LDFLAGS) $(EXTRALIBS)
$(LDLIBS)
下添加規(guī)則:
$(CGI_STRING_ESCAPE): cgi_string_escape.o
$(CC) -o $@ cgi_string_escape.o $(LDFLAGS) $(EXTRALIBS)
$(LDLIBS)
5)在
$(ROMFSINST) $(WEB_DIRECTORY)/cgi-bin/$(CGI_STRING)
下添加:
$(ROMFSINST) $(WEB_DIRECTORY)/cgibin/$(CGI_STRING_ESCAPE)
6)在
cgi_dtring.o: cgi_dtring.c $(CONF_H) $(UCONF_H)
$(BUSYBOXCONF_H) $(CGIC_H)
下添加依賴關(guān)系:
cgi_dtring_escape.o: cgi_dtring_escape.c $(CONF_H)
$(UCONF_H) $(BUSYBOXCONF_H) $(CGIC_H)
保存退出。
3.到路徑下/work/RT288x_SDK/RT288x_SDK/source/編譯工程。將
RT288x_SDKRT288x_SDKsourceimages 中 uImage 燒
寫到機器。
4.局域網(wǎng)中:將 pc 機 ip 地址改成與機器同一網(wǎng)段.
Ip 地址:192.168.0.132
網(wǎng)關(guān):192.168.0.1
5.在瀏覽器中輸入:
http://192.168.0.178/cgi-bin/cgi_string_escape.cgi?東明電子
company!
注意字符前用?號連接。將字符“東明電子 company!”傳給服務(wù)
器。
網(wǎng)頁中接受反饋顯示如下則測試通過: (本例結(jié)束。)
新聞名稱:boa與cgic庫寫cgi簡介
當前路徑:http://chinadenli.net/article8/cjjjip.html
成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供標簽優(yōu)化、虛擬主機、網(wǎng)站收錄、網(wǎng)站設(shè)計、品牌網(wǎng)站制作、動態(tài)網(wǎng)站
聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請盡快告知,我們將會在第一時間刪除。文章觀點不代表本網(wǎng)站立場,如需處理請聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時需注明來源: 創(chuàng)新互聯(lián)