高级I/O函数(3)-tee、fcntl函数
tee函数使用
功能描述:tee函数在两个管道文件描述符之间复制数据,也是零拷贝操作.它不消耗数据,因此源文件描述符仍然可以用于后续的操作.
函数原型:
#include <fcntl.h>
ssize_t tee(int fd_in,int fd_out,size_t len,unsigned int flags);
函数参数:fd_in和fd_out必须都是管道文件描述符。
返回值:成功时返回在两个文件描述符之间复制的数据字节数,返回0表示没有复制任何数据.失败时返回-1并设置errno.
下面是利用tee函数和splice函数,实现同时输出数据到终端与文件的程序)的基本功能.
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <assert.h>
#include <errno.h>
#include <fcntl.h> int main(int argc,const char* argv[]){
if(argc<=){
printf("usage:%s <file>\n",argv[]);
exit(-);
} int filefd=open(argv[],O_WRONLY|O_CREAT|O_TRUNC,);
assert(filefd>=); int pipefd_stdout[];
int ret=pipe(pipefd_stdout);
assert(ret!=-); int pipefd_file[];
ret=pipe(pipefd_file);
assert(ret!=-); /*将标准输入内容输入管道文件pipefd_stdout*/
ret=splice(STDIN_FILENO,NULL,pipefd_stdout[],NULL,,SPLICE_F_MORE
|SPLICE_F_MOVE);
assert(ret!=-); /*将管道pipefd_stdout[0]输出复制到管道pipefd_file的输入端*/
ret=tee(pipefd_stdout[],pipefd_file[],,SPLICE_F_NONBLOCK);
assert(ret!=-);
/*将管道pipefd_file的输出定向到文件描述符filefd上*/
ret=splice(pipefd_file[],NULL,filefd,NULL,,SPLICE_F_MORE|
SPLICE_F_MORE);
assert(ret!=-);
/*将管道pipefd_stdout的输出定向到标准输出,其内容与文件中完全一致*/
ret=splice(pipefd_stdout[],NULL,STDOUT_FILENO,NULL,,SPLICE_F_MORE|
SPLICE_F_MOVE);
assert(ret!=-); close(filefd);
close(pipefd_file[]);
close(pipefd_file[]);
close(pipefd_stdout[]);
close(pipefd_stdout[]);
return ;
}
fcntl函数的使用
功能描述:常用于控制文件描述符的属性和行为
函数原型:
#include <fcntl.h>
int fcntl(int fd,int cmd,...);
fd是被操作的文件描述符,cmd参数指定执行何种类型的操作.根据操作类型的不同,该函数可能还需要第三个可选参数.
fcntl支持的常用操作及其参数
操作分类 | 操作 | 含义 | 第三个参数的类型 | 成功时的返回值 |
复制文件描述符 | F_DUPFD | 创建一个新的文件描述符,其值大于或等于arg | long | 新创建的文件描述符的值 |
F_DUPFD_CLOEXEC | 与F_DUPFD相似,不过在创建文件描述符的同时,设置其close_on_exec标志 | long | 新创建的文件描述符的值 | |
获取和设置文件描述符的标志 | F_GETFD | 获取fd的标志 | 无 | fd的标志 |
F_SETFD | 设置fd的标志 | long | 0 | |
获取和设置文件描述符的状态标志 | F_GETFL | 获取fd的状态标志,这些标志包括可由open系统调用设置的标志(O_CREAT、O_APPEND等)和访问模式(O_RDONLY、O_WRONLY和O_RDWR) | void | fd的状态标志 |
F_SETFL | 设置fd的状态标志,但部分标志是不能修改的(比如访问模式标志) | long | 0 | |
管理信号 | F_GETOWN | 获得SIGIO和SIGURG信号的宿主进程的PID或进程组的ID | 无 | 信号的宿主进程或者进程组ID |
F_SETOWN | 设定SIGIO和SIGURG信号的宿主进程的PID和进程组的ID | long | 0 | |
F_GETSIG | 获取当应用程序被通知fd可读或可写时,是哪个信号通知该事件的 | 无 | 信号值 | |
F_SETSIG | 设置当fd可读或可写时,系统应该触发哪个信号来通知应用程序 | long | 0 | |
操作管道容量 | F_SETPIPE | 设置由fd指定的管道的容量 | long | 0 |
F_GETPIPE | 获取由fd指定的管道的容量 | 无 | 管道容量 |
高级I/O函数(3)-tee、fcntl函数的更多相关文章
- UNIX环境高级编程——记录上锁(fcntl函数)以及死锁检测
一.记录锁 record locking 功能:当一个进程正在读或修改文件的某个部分时,它可以阻止其它进程修改同一文件区. 字节范围锁 byte-range locking 二.历史 flock函数, ...
- 文件I/O之fcntl函数
fcntl函数可以改变已打开的文件的性质. #include <fcntl.h> int fcntl( int filedes, int cmd, ... /* int arg */ ); ...
- [Linux]fcntl函数文件锁概述
概述 fcntl函数文件锁有几个比较容易忽视的地方: 1.文件锁是真的进程之间而言的,调用进程绝对不会被自己创建的锁锁住,因为F_SETLK和F_SETLKW命令总是替换调用进程现有的锁(若已存在), ...
- fcntl函数
很多时候,当我们有多个进程要访问同一个文件的时候,为了防止多进程访问导致的不一致,我们就要考虑进程间的同步问题. fcntl是一个很强大的函数,我们可以通过它给文件的某一部分上锁 int fcntl( ...
- Linux文件(区域)锁函数 -- open()、fcntl()
一.什么是文件锁定 对于锁这个字,大家一定不会陌生,因为我们生活中就存在着大量的锁,它们各个方面发挥着它的作用,现在世界中的锁的功能都可归结为一句话,就是阻止某些人做某些事,例如,门锁就是阻止除了屋主 ...
- linxu fcntl 函数用法 【转】
功能描述:根据文件描述词来操作文件的特性. 文件控制函数 fcntl -- file control 头文件: #include <fcntl.h>; i ...
- Linux系统编程(3)——文件与IO之fcntl函数
linux文件I/O用:open.read.write.lseek以及close函数实现了文件的打开.读写等基本操作.fcntl函数可以根据文件描述词来操作文件. 用法: int fcntl(int ...
- Linux下 fcntl 函数用法说明
功能描述:根据文件描述词来操作文件的特性. 文件控制函数 fcntl -- file control LIBRARY Standard C Library (libc, ...
- UNIX网络编程——fcntl函数
fcntl函数提供了与网络编程相关的如下特性: 非阻塞式I/O. 通过使用F_SETFL命令设置O_NONBLOCK文件状态标志,我们可以把一个套接字设置为非阻塞型. 信号驱动式I/O. 通过使用F ...
随机推荐
- javascript(js)中的substring和substr方法
1. substring 方法 定义和用法: substring 方法用于提取字符串中介于两个指定下标之间的字符. 语法: stringObject.substring(start,end) 参数 ...
- Javascript之return
做表单验证的时候,除了错误提示之外,还要做的一点就是避免表单提交. 如果避免表单提交呢? 有一个方法很简单,就是return 我们来看一下代码: $(".make_sure").c ...
- winform登录时,在密码框按下回车,直接登陆
//按回车,焦点跳到密码文本框 private void txtUserName_KeyPress(object sender, KeyPressEventArgs e) { if (e.KeyCha ...
- hdu-3487-Play with Chain-(splay 区间翻转,切割,插入)
题意: 区间翻转,切割,插入 // File Name: ACM/HDU/3487.cpp // Author: Zlbing // Created Time: 2013年08月10日 星期六 21时 ...
- (转载)mysql查询今天、昨天、7天、近30天、本月、上一月数据
(转载)http://blog.163.com/dreamman_yx/blog/static/26526894201053115622827/ 查询 今天 select * from 表名 wher ...
- 数据结构(LCT动态树):BZOJ 1036: [ZJOI2008]树的统计Count
1036: [ZJOI2008]树的统计Count Time Limit: 10 Sec Memory Limit: 162 MBSubmit: 12266 Solved: 4945[Submit ...
- C++ 求阶乘 四种方法
来总结下求阶乘的各种方法哈. 写在最前:①各个代码仅仅是提供了求阶乘的思路,以便在实际须要时再来编码,代码并不健壮!②各个程序都在1到10内測试正确. 代码一: #include<iostrea ...
- 在Quick-cocos2dx中使用云风pbc解析Protocol Buffers,支持win、mac、ios、android
本例主要介绍 如何将 pbc 集成到quick-cocos2dx框架中,让我们的cocos2dx客户端Lua拥有编解码Protocol Buffers能力. 参考: 云风pbc的用法: http:// ...
- Android中的Apk的加固(加壳)原理解析和实现
一.前言 今天又到周末了,憋了好久又要出博客了,今天来介绍一下Android中的如何对Apk进行加固的原理.现阶段.我们知道Android中的反编译工作越来越让人操作熟练,我们辛苦的开发出一个apk, ...
- iOS开发系列之触摸事件
基础知识 三类事件中触摸事件在iOS中是最常用的事件,这里我们首先介绍触摸事件. 在下面的例子中定义一个KCImage,它继承于UIView,在KCImage中指定一个图片作为背景.定义一个视图控制器 ...