在ARM Linux上使用Apache+PHP

jackxiang 2009-10-4 12:15 | |
在ARM Linux上使用Apache+PHP
我相信这篇文章同样是国内很难搜到的一个HOWTO(呵呵,截至到我写出来之前),我的最初目的是在ARM上使用PHP,尝试了Busybox的httpd,以及boa都没有办法很方便的和PHP接口,因此我狠下心来,编译了Apache。在ARM上使用PHP,好处仅仅是脚本比cgi好写一些,付出的代价是速度和蜗牛一样慢,不要指望很多人同时访问可以响应得过来。
另外说件事,BLOG上的文章多了,经常发现有人转载,但是有的人却不注出处……难道要我吧我的名字和邮件地址写到文章的每一个部分吗?也许国人就是这样缺乏某种精神,在我看到的转载我文章的BLOG中,基本都是网上各种ARM Linux文章的集合,不可否认他们搜集的很好,但是看了这么多文章,连一点心得体会都没有么,写点原创的东西就这么难么?不管怎样,我还是坚持EE小站的风格——原创性。下面开始正题,本文分为三大部分,apache、php和配置。

编译apache
下载apache 1.3.39(1.3.41有些bug,没有办法交叉编译)
下载地址http://apache.mirror.phpchina.com/httpd/apache_1.3.39.tar.bz2


交叉编译apache总体上需要两个步骤:
1.编译本机代码
2.利用本机代码进行交叉编译

这是因为编译apache时,需要使用编译生成的工具制作后续编译使用的头文件,交叉编译的工具当然没有办法在PC上运行,因此,需要借用本机编译生成的工具。假设为本机编译的apache代码已经解压缩到/home/lxz/apache-1.3.39-i586,为ARM编译的apache代码已经解压缩到/home/lxz/apache-1.3.39,交叉编译器arm-linux-gcc已设缺省路径,具体步骤还是用命令来说明:

# cd /home/lxz/apache-1.3.39-i586
# ./configure

因为仅仅是借用下本机代码,所以不用设置配置参数,然后编译

# make

等编译完成后,就可以配置交叉编译的apache了。apache的安装位置为/usr/local/apache

# cd /home/lxz/apache-1.3.39
# CC=arm-linux-gcc ./configure --prefix=/usr/local/apache

会出来这样的提示,因为交叉编译的生成的testfunc这个工具不能在PC上执行,但可以不理会它
./helpers/TestCompile: line 294: /home/lxz/apache-1.3.39/src/helpers/testfunc: cannot execute binary file
打开/home/lxz/apache-1.3.39/src/main/Makefile这个文件,找到这两段代码
uri_delims.h: gen_uri_delims
./gen_uri_delims >uri_delims.h
test_char.h: gen_test_char
./gen_test_char >test_char.h
修改为
uri_delims.h: gen_uri_delims
/home/lxz/apache-1.3.39-i586/src/main/gen_uri_delims >uri_delims.h
test_char.h: gen_test_char
/home/lxz/apache-1.3.39-i586/src/main/gen_test_char >test_char.h
这里借用了刚才编译生成的本机代码里的工具,然后

# make

这就编译好了,下面是安装。由于配置apache的时候“prefix”参数指定的安装位置是/usr/local/apache,在PC上,访问/usr/local是需要有root权限的,需要切换到root用户来进行安装。不建议将apache安装到一个随意的目录然后拷贝,因为这样会造成apache中的脚本调用位置的错误。当然,如果想要将apache安装到一个PC和ARM Linux都能访问的固定位置,如/home/lxz/apache也可以。
如果你不明白上面这段话在说什么,那么请按照下面的步骤进行操作。请确认你的PC Linux上的/usr/local/apache这个目录不存在PC上使用的apache,否则下面的步骤会使你PC Linux上的apache不可用。

# su root

输入密码

# cd /home/lxz/apache-1.3.39/
# make install
# exit

别忘了用exit退出root用户模式,这样,apache的文件就被安装到PC上的/usr/local/apache了。接下来所要做的是将apache拷贝到ARM Linux根文件系统,假设ARM Linux根文件系统在PC上的位置为/home/lxz/root,其中已经有/usr/local这个目录

# cp -r /usr/local/apache /home/lxz/root/usr/local

如果是一路看着我的BLOG建立起根文件系统的,接下来还必须建立nobody用户和nogroup组,因为apache拒绝使用root用户运行。具体来说就是在ARM Linux根文件系统上建立/etc/passwd和/etc/group两个文件,怎么写这两个文件,可以google下。它们的内容可以如下:

/etc/passwd
root::0:0:root:/:/bin/ash
nobody::65534:65533:nobody:/:/bin/ash
/etc/group
nobody::65533:
nogroup::65534:nobody
root::0:
users::100:
当然,如果你的ARM Linux根文件系统中有这两个文件,那么你需要检查一下是不是有nobody用户和nogroup组。接下来,可以制作文件系统映像并测试apache是否可以正常工作了,还是用命令来说明。

# mkfs.cramfs /home/lxz/root /home/lxz/root.img

我一直用cramfs,SUSE 10.2自己就带了mkfs.cramfs这个工具。烧写或者加载文件系统映像的步骤我就不说了,需要注意的是如果你使用了不可写的文件系统,如cramfs,需要把apache的日志路径挂载为临时文件目录,下面这几条命令在ARM Linux上执行。

# mount -t tmpfs tmpfs /usr/local/apache/log

然后就可以启动apache了

# cd /usr/local/apache/bin
# ./apachectl start

假设ARM板的ip地址是192.168.5.118,在浏览器里输入http://192.168.5.118:8080访问ARM板(不修改默认配置,服务端口是8080)。apache的配置一会儿编译了php再说。

编译php
首先下载php-4.4.8,下载地址:http://cn2.php.net/get/php-4.4.8.tar.bz2/from/this/mirror

交叉编译php同样需要两个步骤:
1.编译本机代码
2.利用本机代码进行交叉编译

原因我就不重复了,假设为本机编译的php代码已经解压缩到/home/lxz/php-4.4.8-i586,为ARM编译的php代码已经解压缩到/home/lxz/php-4.4.8,交叉编译器arm-linux-gcc已设缺省路径,具体步骤还是用命令来说明:

# cd /home/lxz/php-4.4.8-i586
# ./configure
# make

在编译的同时,可以打开/home/lxz/php-4.4.8/configure这个文件,搜索“can not run test program while cross compiling”,会搜索到很多个这样的结果:
{ echo "configure: error: can not run test program while cross compiling" 1>&2; exit 1; }
把它们都改为
{ echo "configure: error: can not run test program while cross compiling" 1>&2; }
这样做的目的是直接无视交叉编译测试程序错误。另外,我使用的是arm-linux-gcc 3.4.1版,和代码不太兼容。找到/home/lxz/php-4.4.8/Zend/zend_strtod.c的第238行
#if defined(IEEE_LITTLE_ENDIAN) + defined(IEEE_BIG_ENDIAN) + defined(VAX) + \
    defined(IBM) != 1
Exactly one of IEEE_LITTLE_ENDIAN IEEE_BIG_ENDIAN, VAX, or
IBM should be defined.
#endif
把这段改为
#if defined(IEEE_LITTLE_ENDIAN) + defined(IEEE_BIG_ENDIAN) + defined(VAX) + \
    defined(IBM) != 1
//Exactly one of IEEE_LITTLE_ENDIAN IEEE_BIG_ENDIAN, VAX, or
//IBM should be defined.
#endif
在本机php编译完后,输入如下命令

# cd /home/lxz/php-4.4.8
# CC=arm-linux-gcc ./configure --prefix=/usr/local/php --host=i586-suse-linux --target=arm-linux

别以为可以编译了,还有东西要修改,真汗啊……打开/home/lxz/php-4.4.8/Makefile,找到这段
install-pear-packages: $(top_builddir)/sapi/cli/php
@$(top_builddir)/sapi/cli/php $(PEAR_INSTALL_FLAGS) /home/lxz/php-4.4.8/pear/install-pear.php -d "$(peardir)" -b "$(bindir)" /home/lxz/php-4.4.8/pear/packages/*.tar
用上我们刚才编译的本机php里的文件,把它改成
install-pear-packages: /home/lxz/php-4.4.8-i586/sapi/cli/php
@/home/lxz/php-4.4.8-i586/sapi/cli/php $(PEAR_INSTALL_FLAGS) /home/lxz/php-4.4.8/pear/install-pear.php -d "$(peardir)" -b "$(bindir)" /home/lxz/php-4.4.8/pear/packages/*.tar
终于可以编译了

# make

随后和apache一样,需要切换用户,把php的文件安装到/usr/local/php

# su

输入密码

# cd /home/lxz/php-4.4.8
# make install
# exit

这样,php就编译完成了。

配置Apache和PHP
接下来就需要修改配置文件,让apache和php能够链接起来工作。这个配置过程和Windows下使用apache+php的过程类似,因为我不是把apache和php一起编译的,只是让apache认识“.php”这个扩展名,然后调用php。为了方便,直接给出apache的配置文件,配置文件的位置在ARM Linux文件系统的/usr/local/apache/conf/httpd.conf,其中红色字是在默认配置文件基础上修改或添加的内容。
ServerType standalone
ServerRoot "/usr/local/apache"
PidFile /usr/local/apache/logs/httpd.pid
ScoreBoardFile /usr/local/apache/logs/httpd.scoreboard
Timeout 300
KeepAlive On
MaxKeepAliveRequests 100
KeepAliveTimeout 15
MinSpareServers 5
MaxSpareServers 10
StartServers 5
MaxClients 150
MaxRequestsPerChild 0
Port 80
User nobody
Group nobody
ServerAdmin cosine@126.com
DocumentRoot "/home/webroot"
<Directory />
    Options FollowSymLinks
    AllowOverride None
</Directory>
<Directory "/home/webroot">
    Options Indexes FollowSymLinks MultiViews
    AllowOverride None
    Order allow,deny
    Allow from all
</Directory>
<IfModule mod_userdir.c>
    UserDir public_html
</IfModule>
<IfModule mod_dir.c>
    DirectoryIndex index.html
    DirectoryIndex index.php
    DirectoryIndex index.php3
    DirectoryIndex index.phtml
</IfModule>
AccessFileName .htaccess
<Files ~ "^\.ht">
    Order allow,deny
    Deny from all
    Satisfy All
</Files>
UseCanonicalName On
<IfModule mod_mime.c>
    TypesConfig /usr/local/apache/conf/mime.types
</IfModule>
DefaultType text/plain
<IfModule mod_mime_magic.c>
    MIMEMagicFile /usr/local/apache/conf/magic
</IfModule>
HostnameLookups Off
ErrorLog /usr/local/apache/logs/error_log
LogLevel warn
LogFormat "%h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-Agent}i\"" combined
LogFormat "%h %l %u %t \"%r\" %>s %b" common
LogFormat "%{Referer}i -> %U" referer
LogFormat "%{User-agent}i" agent
CustomLog /usr/local/apache/logs/access_log common
ServerSignature On
<IfModule mod_alias.c>
    Alias /icons/ "/usr/local/apache/icons/"
    <Directory "/usr/local/apache/icons">
        Options Indexes MultiViews
        AllowOverride None
        Order allow,deny
        Allow from all
    </Directory>
    Alias /manual/ "/usr/local/apache/htdocs/manual/"
    <Directory "/usr/local/apache/htdocs/manual">
        Options Indexes FollowSymlinks MultiViews
        AllowOverride None
        Order allow,deny
        Allow from all
    </Directory>
    ScriptAlias /cgi-bin/ "/usr/local/apache/cgi-bin/"
    ScriptAlias /php4/ "/usr/local/php/bin/"
    # 注意 "/usr/local/php/bin/" 中最后一个"/"不可少
    <Directory "/usr/local/apache/cgi-bin">
        AllowOverride None
        Options None
        Order allow,deny
        Allow from all
    </Directory>
</IfModule>
<IfModule mod_autoindex.c>
    IndexOptions FancyIndexing
    AddIconByEncoding (CMP,/icons/compressed.gif) x-compress x-gzip
    AddIconByType (TXT,/icons/text.gif) text/*
    AddIconByType (IMG,/icons/image2.gif) image/*
    AddIconByType (SND,/icons/sound2.gif) audio/*
    AddIconByType (VID,/icons/movie.gif) video/*
    AddIcon /icons/binary.gif .bin .exe
    AddIcon /icons/binhex.gif .hqx
    AddIcon /icons/tar.gif .tar
    AddIcon /icons/world2.gif .wrl .wrl.gz .vrml .vrm .iv
    AddIcon /icons/compressed.gif .Z .z .tgz .gz .zip
    AddIcon /icons/a.gif .ps .ai .eps
    AddIcon /icons/layout.gif .html .shtml .htm .pdf
    AddIcon /icons/text.gif .txt
    AddIcon /icons/c.gif .c
    AddIcon /icons/p.gif .pl .py
    AddIcon /icons/f.gif .for
    AddIcon /icons/dvi.gif .dvi
    AddIcon /icons/uuencoded.gif .uu
    AddIcon /icons/script.gif .conf .sh .shar .csh .ksh .tcl
    AddIcon /icons/tex.gif .tex
    AddIcon /icons/bomb.gif core
    AddIcon /icons/back.gif ..
    AddIcon /icons/hand.right.gif README
    AddIcon /icons/folder.gif ^^DIRECTORY^^
    AddIcon /icons/blank.gif ^^BLANKICON^^
    DefaultIcon /icons/unknown.gif
    ReadmeName README.html
    HeaderName HEADER.html
    IndexIgnore .??* *~ *# HEADER* README* RCS CVS *,v *,t
</IfModule>
<IfModule mod_mime.c>
    AddLanguage da .dk
    AddLanguage nl .nl
    AddLanguage en .en
    AddLanguage et .ee
    AddLanguage fr .fr
    AddLanguage de .de
    AddLanguage el .el
    AddLanguage he .he
    AddCharset ISO-8859-8 .iso8859-8
    AddLanguage it .it
    AddLanguage ja .ja
    AddCharset ISO-2022-JP .jis
    AddLanguage kr .kr
    AddCharset ISO-2022-KR .iso-kr
    AddLanguage nn .nn
    AddLanguage no .no
    AddLanguage pl .po
    AddCharset ISO-8859-2 .iso-pl
    AddLanguage pt .pt
    AddLanguage pt-br .pt-br
    AddLanguage ltz .lu
    AddLanguage ca .ca
    AddLanguage es .es
    AddLanguage sv .sv
    AddLanguage cs .cz .cs
    AddLanguage ru .ru
    AddLanguage zh-TW .zh-tw
    AddCharset Big5         .Big5    .big5
    AddCharset WINDOWS-1251 .cp-1251
    AddCharset CP866        .cp866
    AddCharset ISO-8859-5   .iso-ru
    AddCharset KOI8-R       .koi8-r
    AddCharset UCS-2        .ucs2
    AddCharset UCS-4        .ucs4
    AddCharset UTF-8        .utf8
    <IfModule mod_negotiation.c>
        LanguagePriority en da nl et fr de el it ja kr no pl pt pt-br ru ltz ca es sv tw
    </IfModule>
    AddType application/x-tar .tgz
    AddType application/x-httpd-php .php3
    AddType application/x-httpd-php .php
    AddType application/x-httpd-php .phtml
    AddEncoding x-compress .Z
    AddEncoding x-gzip .gz .tgz
</IfModule>
Action application/x-httpd-php "/php4/php"
<IfModule mod_setenvif.c>
    BrowserMatch "Mozilla/2" nokeepalive
    BrowserMatch "MSIE 4\.0b2;" nokeepalive downgrade-1.0 force-response-1.0
    BrowserMatch "RealPlayer 4\.0" force-response-1.0
    BrowserMatch "Java/1\.0" force-response-1.0
    BrowserMatch "JDK/1\.0" force-response-1.0
</IfModule>
php也有配置文件,但是修改起来比较简单,只需要把/home/lxz/php-4.4.8/php.ini-dist复制到ARM Linux文件系统的/usr/local/php/lib,并改名为php.ini,找到
register_globals = Off
修改为
register_globals = On
保存就可以了。
如果你觉得上面的一切都很麻烦,可以在EE小站的SkyDrive下载我制作好的压缩包,地址http://cid-4201fdc93932ddaf.skydrive.live.com/self.aspx/EE%e5%b0%8f%e7%ab%99%e7%90%90%e7%a2%8e%e6%96%87%e4%bb%b6/armv4-apache-php.tar.bz2,解压缩到ARM Linux根文件系统的/。这个压缩包包含apache 1.3.39和php 4.4.8,默认的网页服务器根目录为/home/webroot,默认监听端口为80。
另外,我在资料站上开了个wiki来测试ARM Linux上Apache+PHP的组合,地址http://cosine.oicp.net/dokuwiki/。测试的时间不会很长,但我会保证这个链接在2008年4月1号前有效。(2009年2月21日追加:这个地址已经失效快一年了)

作者:jackxiang@向东博客 专注WEB应用 构架之美 --- 构架之美,在于尽态极妍 | 应用之美,在于药到病除
地址:https://jackxiang.com/post/2020/
版权所有。转载时必须以链接形式注明作者和原始出处及本声明!

评论列表
2014-1-12 11:14 | root Email Homepage
1)估计是访问权限的问题,你把你要访问的文件夹权限设置一下2)在phpinfo里查看sqlite是否编译得对,连接路径什么的。
2014-1-7 14:31 | liekkas_zx
您好,我最近尝试在嵌入式开发板上移植Apache+php+sqlite,遇到一些问题,由于php5本身就支持sqlite2,所以我有重新编译了php5,并且配置Apache和php5之后,phpinfo()测试页面通过,但是在php脚本中加入数据库操作,出现服务器内部错误,错误日志:Premature end of script headers: /usr/local/php5-arm/bin/php-cgi,我始终没有解决这个问题,请问你做过相关的试验么,能否给点意见,谢谢~
分页: 1/1 第一页 1 最后页
发表评论

昵称

网址

电邮

打开HTML 打开UBB 打开表情 隐藏 记住我 [登入] [注册]