附录A 函数原型
把全书函数原型按头文件、参数类型、返回约定和功能族组织成接口查验表。 覆盖1个正式目录层级。
为什么从接口合同开始
、、、、共同构成本页坐标。把全书函数原型按头文件、参数类型、返回约定和功能族组织成接口查验表。
APUE第3版面向SUSv4/POSIX.1-2008,并以Solaris 10、Mac OS X 10.6.8、FreeBSD 8.0和Ubuntu 12.04为主要验证平台。正文先还原书中标准合同与实现差异;Linux当前行为只能作为显式现代对照,不能悄悄覆盖原书的版本边界。
六阶段可重放链
1. 定位功能族
围绕函数原型记录平台、功能测试宏、输入、描述符/对象表、返回值、errno和预期状态。进入“确认头文件”前保存第一条偏离,清理与恢复也写入结果。
2. 确认头文件
围绕头文件记录平台、功能测试宏、输入、描述符/对象表、返回值、errno和预期状态。进入“展开宏条件”前保存第一条偏离,清理与恢复也写入结果。
3. 展开宏条件
围绕参数类型记录平台、功能测试宏、输入、描述符/对象表、返回值、errno和预期状态。进入“核对原型”前保存第一条偏离,清理与恢复也写入结果。
4. 核对原型
围绕返回约定记录平台、功能测试宏、输入、描述符/对象表、返回值、errno和预期状态。进入“编译告警”前保存第一条偏离,清理与恢复也写入结果。
5. 编译告警
围绕功能测试宏记录平台、功能测试宏、输入、描述符/对象表、返回值、errno和预期状态。进入“记录平台差异”前保存第一条偏离,清理与恢复也写入结果。
6. 记录平台差异
围绕函数原型记录平台、功能测试宏、输入、描述符/对象表、返回值、errno和预期状态。进入“定位功能族”前保存第一条偏离,清理与恢复也写入结果。
机制、所有权与失败模型
把全书函数原型按头文件、参数类型、返回约定和功能族组织成接口查验表。
本页核心不变量是:调用点所见声明来自正确头文件与功能测试宏;整数宽度、指针限定和返回类型不靠隐式声明猜测。 它必须同时约束正常、边界、故障和恢复样本。接口返回成功只是证据之一,还要检查短计数、EINTR/EAGAIN、对象继承、并发时序、缓冲与异步清理。
实验台账至少包含平台与版本、编译宏、入口参数、对象所有者、描述符或ID、预期返回、实际返回、errno、首个状态分叉、原始轨迹和清理结果十一列。性能样本还需固定预热、CPU放置、输入规模、采样窗口与分位数;信号/线程样本必须记录掩码、取消状态和处理上下文。
附录使用法:从查表到可执行证据
附录不是正文之外的速查碎片。第一次使用附录A 函数原型时,先从当前问题反向定位函数原型与头文件,抄录标准声明、所需头文件、功能测试宏和返回约定;然后回到对应正文章节确认对象由谁创建、谁继承、谁关闭。这样能避免只记函数名却丢失标准条件,也能发现同名接口在C库封装、系统调用和不同UNIX实现之间的责任差异。
第二步建立最小构建。创建只包含一个入口、一个成功样本和一个失败样本的小目录,开启C11、全部常见告警并把告警视为错误。编译输出必须保存编译器版本、宏展开结果、链接符号和运行平台;如果需要apue.h或公共错误例程,只链接同一份实现,不能通过复制粘贴制造多个略有差异的版本。此时重点不是“程序能跑”,而是声明、定义、调用约定和错误报告能互相对上。
第三步验证失败合同。分别制造不存在的路径、权限不足、短输入、信号中断、容量耗尽和并发关闭,只保留与当前接口相关的一个变量。记录原始返回值后立刻保存errno,随后再格式化诊断;否则后续库调用可能覆盖真正首错。对于返回指针、描述符、PID或线程ID的接口,还要写清失败前后所有权是否发生转移,以及清理函数在部分初始化状态下能否安全执行。
第四步做实现对照。至少比较标准文本保证、书中四个平台观察和当前Linux实测三列:标准未规定的行为标为“实现选择”,运行时可查询的限制保留查询结果,编译期选项保留宏值。不能因为两台Linux机器结果相同就把它提升为POSIX规则,也不能因为历史平台接口仍可编译就假设它适合新代码。
第五步把答案接回正文证据链。定位功能族、确认头文件、展开宏条件、核对原型、编译告警、记录平台差异不是六个孤立动作,而是一条从前提到恢复的闭环。每个结论都附最小程序、构建命令、原始标准输出/错误、系统调用轨迹、资源清单和清理结果;复核者无需依赖作者机器的隐藏状态即可得到相同基线,并能在单变量故障下看到相同第一处分叉。
最后做反例审查:删掉一个头文件、改变一个功能测试宏、让一个调用返回短计数、在错误打印前插入会改errno的函数、或让子进程在exec前走一条不安全路径。若测试仍然“通过”,说明断言只检查了最终文本而没有约束接口合同。修正断言后关闭描述符、join线程、wait子进程、删除IPC名字并恢复信号与终端属性,再以同一输入重放;只有无残留地回到基线,附录知识才真正进入工程能力。
最后再做一次陌生环境复核:清空构建产物与临时环境变量,在新shell或最小容器中仅按记录执行。若仍需口头补充路径、权限、输入文件或清理顺序,说明实验合同尚不完整;把这些隐含前提写入台账,重新抓取原始输出并核对资源数归零。
可重放命令骨架
cc -std=c11 -Wall -Wextra -Werror -Iinclude src/*.c -o probenm -g probe | sort
readelf -Ws probe | sed -n '1,20p'make clean && make check
find . -type f -name '*.o' -delete正式目录逐项讲解
附录A 函数原型
“附录A 函数原型”不是孤立API名词。把函数原型、前置条件、成功返回、失败errno、可中断性和资源转移逐项列出,禁止把一次成功调用当成完整合同。在本章中,它通过“函数原型”服务于“定位功能族”:先固定平台、编译宏、输入与初始资源表,再记录原始返回值和系统可见状态。
验证时只改变一个长度、容量、时序、权限、信号或失败点,并在进入“确认头文件”前停住第一条返回值、errno、系统调用轨迹、对象计数或状态分叉。最后关闭描述符、回收进程/线程、删除命名对象并恢复终端或信号掩码;同输入重放回到基线,结论才成立。
分步视觉验证
先预测对象、返回值和状态,再动手试一试;若结果不同,停在第一条系统调用或对象状态分叉。
常见误区
四类样本与验收
| 样本 | 只改变什么 | 必查证据 | 通过条件 |
|---|---|---|---|
| 基线 | 平台、宏与固定输入 | 返回值、errno、对象与轨迹 | 与预测一致 |
| 边界 | 长度、容量、权限或时序 | 短计数、拒绝或阻塞点 | 边界可解释 |
| 故障 | 一个信号、断开或失败注入 | 首错与责任层 | 故障可定位 |
| 恢复 | 关闭、回收、删除与属性还原 | 残留对象和同输入重放 | 回到基线 |
练习
小结
- 函数原型:连接“定位功能族”的接口合同与运行证据。
- 头文件:连接“确认头文件”的接口合同与运行证据。
- 参数类型:连接“展开宏条件”的接口合同与运行证据。
- 返回约定:连接“核对原型”的接口合同与运行证据。
- 功能测试宏:连接“编译告警”的接口合同与运行证据。
- 本页1个正式目录层级全部进入可重放实验链。