用户可能要对现有程序(如 /usr/bin/cat)使用 exec(2) 来建立传输连接,以便处理通过该连接收到的数据。现有程序使用 read(2) 和 write(2)。XTI/TLI 并不直接支持传输提供器的读/写接口,但是有一个接口可用。利用该接口,可以在数据传送阶段通过传输连接发出 read(2) 和 write(2) 调用。本节介绍 XTI/TLI 连接模式服务的读/写接口。该接口不适用于无连接模式服务。
#include <stropts.h> . ./* Same local management and connection establishment steps. */ . if (ioctl(fd, I_PUSH, "tirdwr") == -1) { perror(“I_PUSH of tirdwr failed”); exit(5); } close(0); dup(fd); execl(“/usr/bin/cat”, “/usr/bin/cat”, (char *) 0); perror(“exec of /usr/bin/cat failed”); exit(6); }
客户机通过将 tirdwr 推送到与传输端点关联的流来调用读/写接口。有关 I_PUSH 的说明,请参见 streamio(7I) 手册页。tirdwr 模块将位于传输提供器之上的 XTI/TLI 转换为纯读/写接口。使用该模块后,客户机将调用 close(2) 和 dup(2) 来建立传输端点作为其标准输入文件,并使用 /usr/bin/cat 来处理输入。
将 tirdwr 推送到传输提供器会强制 XTI/TLI 使用 read(2) 和 write(2) 语义。使用 read 和 write 语义时,XTI/TLI 不保留消息边界。请从传输提供器弹出 tirdwr 以恢复 XTI/TLI 语义(有关 I_POP 的说明,请参见 streamio(7I) 手册页)。
仅当传输端点位于数据传送阶段时,才将 tirdwr 模块推送到流。推送该模块之后,用户不能调用任何 XTI/TLI 例程。如果用户调用 XTI/TLI 例程,则 tirdwr 会在流上生成致命的协议错误 EPROTO,表明该例程不可用。如果随后将 tirdwr 模块弹出该流,则该传输连接将异常中止。有关 I_POP 的说明,请参见 streamio(7I) 手册页。
使用 write(2) 通过传输连接发送数据之后,tirdwr 将数据传递到传输提供器。如果发送的数据包长度为零(该机制允许),则 tirdwr 会放弃该消息。如果传输连接异常中止,则会在流上产生挂起状态,后续 write(2) 调用将失败,并且 errno 被设置为 ENXIO。例如,远程用户使用 t_snddis(3NSL) 异常中止连接时可能出现此问题。挂起之后,仍可以检索任何可用数据。
使用 read(2) 接收到达传输连接的数据。tirdwr 传递来自传输提供器的数据。tirdwr 模块可处理从提供器传递至用户的任何其他事件或请求,如下所示:
read(2) 无法识别发送给用户的加速数据。如果 read(2) 接收到加速数据请求,则 tirdwr 将在流上生成一个致命的协议错误 EPROTO。该错误将导致后续系统调用失败。请勿使用 read(2) 接收加速数据。
tirdwr 会放弃异常断开请求并在流上生成挂起状态。后续 read(2) 调用检索所有剩余数据,然后针对所有后续调用返回零值,指示文件结束。
tirdwr 会放弃顺序释放请求并向用户发送一条长度为零的消息。如 read(2) 手册页中所述,该消息通过返回 0 来通知用户文件结束。
如果 read(2) 接收到任何其他 XTI/TLI 请求,则 tirdwr 将在流上生成一个致命的协议错误 EPROTO。该错误将导致后续系统调用失败。如果用户在连接建立之后将 tirdwr 推送到流,则 tirdwr 不会生成请求。
利用流上的 tirdwr,在连接有效期间内,可以通过传输连接发送和接收数据。用户可通过关闭与传输端点关联的文件描述符来终止连接,也可通过将 tirdwr 模块弹出流来终止连接。在上述任一情况下,tirdwr 都会执行以下操作:
如果 tirdwr 接收到顺序释放请求,则将该请求传递到传输提供器以完成该连接的顺序释放。数据传送完成后,启动顺序释放过程的远程用户将接收到预期请求。
如果 tirdwr 接收到断开请求,则不执行任何特殊操作。
如果 tirdwr 接收到的既不是顺序释放请求,也不是断开请求,则会将一个断开请求传递到传输提供器以异常中止该连接。
如果流上发生错误,并且 tirdwr 未接收到断开请求,则会将一个断开请求传递到传输提供器。
将 tirdwr 推送到流之后,进程便不能启动顺序释放。如果位于传输连接另一端的用户启动了顺序释放,tirdwr 将处理该释放。如果该部分中的客户机与服务器程序进行通信,则该服务器会使用顺序释放请求终止数据的传送。然后,该服务器将等待客户机的相应请求。此时,该客户机将退出并关闭传输端点。关闭文件描述符之后,tirdwr 便会启动来自连接客户端的顺序释放请求。该释放会生成阻塞服务器的请求。
某些协议(如 TCP)要求此顺序释放以确保数据完整地传送。