Lighttpd CGI配置:404错误排查实录

article/2025/8/1 17:36:55

目录

引言

编写测试程序

前端代码

后端代码

配置CGI模块(mod_cgi)

如何检查404错误

测试结果

​编辑

结语


引言

在前面的测试中,我们将lighttpd移植到x210开发板中,今天学生报告说她在进行CGI程序测试时总是遭遇404错误。所谓404错误,就是服务器在处理CGI程序时总是找不到对应的脚本文件。针对这个问题进行了一番测试,介绍一下处理方法。

编写测试程序

前端代码

前端测试代码是这样的,用于调用 CGI 脚本:

<html>
<head><title>CGI测试页面</title><meta charset="UTF-8">
</head>
<body><h1>Lighttpd CGI测试</h1><h2>测试CGI脚本</h2><p><a href="/cgi-bin/test.cgi">运行测试CGI脚本</a></p><h2>带参数测试</h2><form action="/cgi-bin/test.cgi" method="get"><label>姓名: <input type="text" name="name"></label><label>年龄: <input type="number" name="age"></label><input type="submit" value="提交"></form><h2>POST方法测试</h2><form action="/cgi-bin/test.cgi" method="post"><label>消息: <textarea name="message"></textarea></label><input type="submit" value="发送"></form>
</body>
</html>

将这个 HTML 页面保存为/var/lighttpd/htdocs/test-cgi.html。 

后端代码

下面是一个基于 Bash 的测试 CGI 脚本,它会输出当前环境变量和请求信息:

#!/bin/bash# 输出HTTP头部
echo "Content-Type: text/html"
echo ""# 输出HTML页面
cat << EOF
<!DOCTYPE html>
<html>
<head><title>CGI测试</title><meta charset="UTF-8">
</head>
<body><h1>CGI脚本测试成功!</h1><p>当前时间: $(date)</p><h2>环境变量</h2><pre>
$(env | sort)</pre><h2>请求信息</h2><p>请求方法: $REQUEST_METHOD</p><p>请求URI: $REQUEST_URI</p><p>查询字符串: $QUERY_STRING</p>
</body>
</html>
EOF

把上述脚本保存为/var/lighttpd/cgi-bin/test.cgi(这里的路径有问题,后面会详细讲),并赋予执行权限: 

chmod +x /var/lighttpd/cgi-bin/test.cgi

配置CGI模块(mod_cgi)

使用CGI功能,要对 lighttpd 进行配置,使其支持 CGI 功能。找到并编辑 lighttpd 的modules配置文件,我们的配置为/var/lighttpd/config/modules.conf,取消include "conf.d/cgi.conf"这行前面的注释:

这样修改之后就可以激活mod_cgi。

然后修改/var/lighttpd/config/conf.d/cgi.conf文件,以指定 Bash 脚本作为 CGI 处理程序。

#######################################################################
##
##  CGI modules
## ---------------
##
## http://www.lighttpd.net/documentation/cgi.html
##
server.modules += ( "mod_cgi" )##
## Plain old CGI handling
##
## For PHP don't forget to set cgi.fix_pathinfo = 1 in the php.ini.
##
cgi.assign                 = ( ".pl"  => "/usr/bin/perl",".cgi" => "/bin/bash",".rb"  => "/usr/bin/ruby",".erb" => "/usr/bin/eruby",".py"  => "/usr/bin/python" )

保存设置后,启动lighttpd。如果先前已经启动了lighttpd ,需要先用kill杀掉lighttpd进程。

如何检查404错误

不过如果安装上述配置运行测试程序,会报告404文件错误,就是学生遇到的问题。

为了解决这个问题,我使用strace程序。这是一个强大的 Linux 系统调用跟踪工具,它能够监控和记录程序执行时所发起的系统调用以及收到的信号。

使用如下命令:

 strace  -e trace=file ./sbin/lighttpd -f config/lighttpd.conf -D

其中-e trace=file参数只跟踪与文件操作相关的系统调用,像 openreadwrite 等。 而-D参数是lighttpd的参数,表示程序不会切换到后台。程序运行后会输出下面的log:


stat64("/var/lighttpd/htdocs", {st_mode=S_IFDIR|0777, st_size=1024, ...}) = 0
open("/var/lighttpd/lib/mod_indexfile.so", O_RDONLY|O_CLOEXEC) = 3
fstat64(3, {st_mode=S_IFREG|0755, st_size=32008, ...}) = 0
open("/var/lighttpd/lib/mod_access.so", O_RDONLY|O_CLOEXEC) = 3
fstat64(3, {st_mode=S_IFREG|0755, st_size=30268, ...}) = 0
open("/var/lighttpd/lib/mod_cgi.so", O_RDONLY|O_CLOEXEC) = 3
fstat64(3, {st_mode=S_IFREG|0755, st_size=73015, ...}) = 0
open("/var/lighttpd/lib/mod_accesslog.so", O_RDONLY|O_CLOEXEC) = 3
fstat64(3, {st_mode=S_IFREG|0755, st_size=51523, ...}) = 0
open("/var/lighttpd/lib/mod_dirlisting.so", O_RDONLY|O_CLOEXEC) = 3
fstat64(3, {st_mode=S_IFREG|0755, st_size=59028, ...}) = 0
open("/var/lighttpd/lib/mod_staticfile.so", O_RDONLY|O_CLOEXEC) = 3
fstat64(3, {st_mode=S_IFREG|0755, st_size=42913, ...}) = 0
open("/var/lighttpd/lighttpd.pid", O_WRONLY|O_CREAT|O_EXCL|O_TRUNC|O_LARGEFILE, 0644) = 3
open("/var/lighttpd/log/error.log", O_WRONLY|O_CREAT|O_APPEND|O_LARGEFILE, 0644) = 3
open("/etc/localtime", O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)
open("/var/lighttpd/log/access.log", O_WRONLY|O_CREAT|O_APPEND|O_LARGEFILE, 0644) = 5
open("/dev/null", O_RDONLY|O_LARGEFILE) = 7
stat64("/var/lighttpd/htdocs/cgi-bin/test.cgi", 0xbed491b0) = -1 ENOENT (No such file or directory)

我发现,当运行test.cgi时,lighttpd去照相的文件是/var/lighttpd/htdocs/cgi-bin/test.cgi,而不是前面所想象的/var/lighttpd/cgi-bin/test.cgi。出现这个问题的原始是我们没有使能mod_alias,也没有在配置文件中将/cgi-bin指向/var/lighttpd/cgi-bin目录。所以lighttpd会去寻找var/lighttpd/htdocs/cgi-bin/test.cgi。如果不想修改配置文件,就需要将test.cgi放置到var/lighttpd/htdocs/cgi-bin/目录中。

测试结果

修改文件路径后,再次测试,程序可以正常运行了。

结语

通过上述排查与实践可见,在嵌入式开发板中调试 Lighttpd 的 CGI 功能时,路径配置的准确性与模块启用状态是关键突破口。从最初因未正确配置mod_alias导致服务器误读脚本路径,到借助strace工具精准定位文件查找逻辑,这一系列过程不仅体现了系统调用跟踪工具在底层调试中的价值,也再次印证了嵌入式环境下配置细节对功能实现的直接影响。

希望本文的解决过程能为嵌入式 Web 服务开发提供参考,帮助开发者在面对类似路径解析或模块冲突问题时,能更系统地分析与解决。如需进一步探讨 Lighttpd 在嵌入式场景中的优化策略或其他调试技巧,欢迎在评论区交流!


http://www.hkcw.cn/article/kvEtGqEvoI.shtml

相关文章

卢昌海 | 质量的起源

注&#xff1a;本文为卢昌海 | 质量的起源五篇合辑。 公式巨多&#xff0c;未一一校排。 如有内容异常&#xff0c;请看原文。 卢昌海 | 质量的起源 &#xff08;一&#xff09; 一、引言 物理学是一门试图在最基本层次上理解自然的古老科学&#xff0c;其早期曾是哲学的一部…

5、设置时区、链接wifi

一、修改时区&#xff1a; 输入以下命名打开raspbian系统的设置界面 sudo raspi-config 如下图&#xff0c;通过键盘上下键&#xff0c;移动到第 5 步“localisation Options”&#xff0c;回车进入。 注:每个系统版本不一样&#xff0c;选择就不一样&#xff0c;我的是在第…

81、使用DTU控制水下灯光控制

基本思想:记录调试济南有人DTU控制水下灯光控制 一、首先连接dtu设备,进行供电模块的链接和RS-485控制水下探照灯 线头链接方方式示意图,供电线接入之后,要保证设备处于工作状态,如果设备在供电不处于工作状态,那可能火线和零线接反了,请重新接入; 将红色的线接入RS-4…

【js逆向】易车网某车辆对比信息X-sign

目标网址&#xff1a;aHR0cHM6Ly9jYXIueWljaGUuY29tL2JpeWFkaWUyL3BlaXpoaS8 f12刷新网页查看数据接口 断点调试&#xff1a; 我们的目标网址是 param/get_param_details, 用条件断点 e.url.includes(param/get_param/details) 向上跟栈&#xff0c;这里X-Sign已经生成&#x…

基于TMC5160堵转检测技术的夹紧力控制系统设计与实现

点击下面图片带您领略全新的嵌入式学习路线 &#x1f525;爆款热榜 90万阅读 1.6万收藏 一、技术背景与系统原理 在工业自动化领域&#xff0c;夹紧力控制是精密装配、机床夹具等场景的核心需求。传统方案多采用压力传感器伺服电机的闭环控制方式&#xff0c;但存在系统复杂…

青岛红狮主教练马永康下课 球队保级压力增大

北京时间5月31日晚,2025赛季中甲第11轮多场比赛展开,广西平果在主场迎战青岛红狮。比赛前,两队分别位于中甲积分榜的倒数第一和第二位。上半场马特乌斯为广西平果打破僵局,下半场双方均未能改写比分。最终,广西平果以1-0战胜青岛红狮,取得联赛首胜并保持了两轮不败,而青…

Maven(黑马)

Maven 是一个强大的项目管理和构建自动化工具&#xff0c;主要用于 Java 项目的构建、依赖管理和文档生成。它通过使用 POM&#xff08;Project Object Model&#xff09;文件来管理项目的配置和依赖关系&#xff0c;从而实现项目的自动化构建和管理。以下是 Maven 的一些核心概…

项目练习:element ui 的icon放在button的右侧

文章目录 一、需求描述二、左侧实现三、右侧实现 一、需求描述 我们知道&#xff0c;element ui的button一般都会配置一个icon 这个icon默认是放在左侧的。 如何让它放在右侧了&#xff1f; 二、左侧实现 <el-buttontype"primary"plainicon"el-icon-d-arr…

大连一景区日撒1000斤蚬子 吸引游客赶海乐

近两日,多名网友分享了在辽宁省大连市夏家河子海滨浴场偶遇工作人员开着铲车、三轮车给游客撒蚬子赶海的情景。景区回应称,在沙滩上撒蚬子是为了让赶海的游客都能挖到东西。这两天,景区每天需要撒约1000斤的蚬子。此外,还有巴掌大的鲍鱼和海螺,如果游客捡到可以兑换礼品。…

位运算 #常见位运算总结 #题解

系列文章目录 leetcode - 双指针问题_leetcode双指针题目-CSDN博客 leetcode - 滑动窗口问题集_leetcode 滑动窗口-CSDN博客 高效掌握二分查找&#xff1a;从基础到进阶-CSDN博客 leetcode - 前缀和_前缀和的题目-CSDN博客 动态规划 - 斐波那契数列模型-CSDN博客 目录 系…

openpnp - 给M4x0.7mm的直油嘴加油的工具选择

文章目录 openpnp - 给M4x0.7mm的直油嘴加油的工具选择概述如果换上带卡口的M4x0.7直油嘴END openpnp - 给M4x0.7mm的直油嘴加油的工具选择 概述 X导轨用了一个HG15的滑块 滑块上的注油口的黄油嘴是M4x0.7mm的直油嘴。 外表面是6边形的柱子&#xff0c;没有可以卡住加油嘴工…

SSL/TLS 协议详解:安全通信的基石

一、概述 SSL&#xff08;Secure Sockets Layer&#xff09; 及其继任者 TLS&#xff08;Transport Layer Security&#xff09; 是位于 传输层&#xff08;TCP&#xff09;与应用层之间 的加密协议&#xff0c;用于在网络通信中实现 机密性、身份认证和数据完整性。 核心目标…

象棋里的卧槽马、侧面虎、金钩马的方位与解析

在中国象棋里&#xff0c;根据马的方位&#xff0c;有不同的称谓&#xff0c;比如卧槽马、侧面虎、金钩马&#xff1b;车也是一样&#xff0c;比如有肋车、沉底车、相位车等。     按照《象棋攻防与口诀》的"边炮车砍象&#xff0c;三七马肋车"口诀&#xff0c;这里…

内存管理 : 05 内存换入-请求调页

操作系统内存换入 - 请求调页讲解 这一讲主要内容是内存的换入&#xff0c;下一讲要讲内存的换出&#xff08;swap out&#xff09;&#xff0c;这两讲合在一起就是内存的换入换出。讲完内存的换入换出&#xff0c;操作系统关于内存管理这部分内容&#xff0c;也就是我们课程里…

任务23:创建天气信息大屏Django项目

任务描述 知识点&#xff1a; Django 重 点&#xff1a; Django创建项目Django视图函数Django路由Django静态文件Django渲染模板 内 容&#xff1a; 使用PyCharm创建大屏项目渲染大屏主页 任务指导 1. 使用PyCharm创建大屏项目。 创建weather项目配置虚拟环境创建ch…

回溯算法!!

只要有递归就会有回溯&#xff0c;回溯隐藏在递归函数的下面 回溯算法是回溯搜索算法&#xff0c;是纯暴力的搜索算法 一般用于解决以下问题 组合问题&#xff1a;N个数里面按一定规则找出k个数的集合&#xff0c;组合是不强调元素顺序的&#xff0c;排列是强调元素顺序。切…

算法学习--持续更新

算法 2025年5月24日 完成&#xff1a;快速排序、快速排序基数优化、尾递归优化 快排 public class QuickSort {public void sort(int[] nums, int left, int right) {if(left>right){return;}int partiton quickSort(nums,left,right);sort(nums,left,partiton-1);sort(nu…

类和对象(4)

&#xff08;本文是《类和对象》的收尾&#xff09; 一.构造函数初始化的逻辑 1.构造函数的初始化列表使用说明 初始化列表是以冒号开头、逗号分隔成员变量的初始化方式&#xff0c;格式为&#xff1a; 构造函数() : 成员1(初始值), 成员2(表达式…

大规模真实场景 WiFi 感知基准数据集

一段话总结 本文提出CSI-Bench,首个大规模真实场景WiFi感知基准数据集,覆盖26个室内环境、35名用户、16种商用设备,包含461小时有效数据,支持跌倒检测、呼吸监测、定位、运动源识别等单任务及用户身份、活动、 proximity联合标注的多任务学习。通过标准化评估协议和基线模…

io流2——字节输入流,文件拷贝

!基本代码演示&#xff1a; 读取&#xff1a; 到程序中不是a&#xff0c;而是a的asicc码对应的数字 继续读读到最后&#xff1a; 不想看到数字&#xff0c;还想看abcde: 再继续读&#xff1a; 如果读不到了&#xff0c;就会返回-1 细节 细节一 细节2 字节输入流循环读取 …