Board logo

标题: Linux 多线程同步-命名管道 [打印本页]

作者: yuyang911220    时间: 2017-6-11 16:03     标题: Linux 多线程同步-命名管道

命名管道(FIFO)既可用于进程间通信,也可用于线程间通信;  FIFO是一种文件类型,一般文件I/O函数(close,read,write,unlink等)都适用于FIFO
  一、管道创建:
  #include <sys/stat.h>
  int mkfifo( const char* pathname,  mode_t mode );
  //成功返回0;否则返回-1
  //mode为读写文件| 是否阻塞
  二、管道默认读写——阻塞
  a. 管道读取:如果没有线程进行写管道操作,读线程将一直阻塞,直到有线程往里面写为止
  b. 管道写:   如果没有线程进行读操作,写线程将一直阻塞,直到有线程读数据为止
  三、设置管道读写——不阻塞(O_NONBLOCK)
  a、管道读:如果没有线程进行写管道操作,读线程将立即返回
  b、 管道写:如果没有线程进行读操作,写线程将立即返回,返回错误码-1;errno: ENXIO
  示例代码:获取vmstat的参数
  #include <stdio.h>
  #include <sys/types.h>
  #include <sys/stat.h>
  #include <errno.h>
  #include <fcntl.h>
  #include <stdio.h>
  #include <stdlib.h>
  #include <string.h>
  #include <assert.h>
  #include <ctype.h>
  /*定义FIFO路径*/
  #define FIFO "myfifo"
  #define FILE_PATH "conf.log"
  int ncnt = 0;
  int get_siso( char* str, int* si, int* so ){
  assert( str != NULL );
  char* sub_str;
  FILE* fp = fopen( FILE_PATH, "ab+" );
  sub_str = strtok( str, " " );
  //ncnt = 0;
  while( sub_str ){
  if( sub_str != NULL && isdigit( sub_str[0] ) ){
  fprintf( fp, "  %s  \t", sub_str );
  printf( "substr[%d] = %d \n", ncnt, atoi(sub_str) );
  ncnt++;
  }
  if( ncnt == 16 ){
  ncnt = 0;
  }
  sub_str = strtok( NULL, " " );
  //sleep(0.3);
  }
  fclose( fp );
  printf( "nCnt is %d\n\n\n", ncnt );
  return 1;
  }
int mf(){
  char buf_r[1025];
  int  fd;
  int  nread;
  printf("Preparing for reading bytes...\n");
  memset(buf_r,0,sizeof(buf_r));
  //system( "vmstat 2 > myfifo" );
  /*打开FIFO管道,不阻塞方式*/
  //fd=open(FIFO,O_RDONLY|O_NONBLOCK,0);
  fd=open(FIFO,O_RDONLY,0);
  if(fd==-1)
  {
  perror("open");
  exit(1);
  }
  while(1)
  {
  memset(buf_r,0,sizeof(buf_r));
  if((nread=read(fd,buf_r,1024))==-1){
  if(errno==EAGAIN)
  printf("no data yet\n");
  }
  sleep(2);
  printf("\n\n%s\n",buf_r);
  get_siso( buf_r, NULL, NULL );
  //sleep(1);
  }
  pause();
  return 1;
  }
  void thr_get(){
  pthread_detach( pthread_self() );
  system( "vmstat 2 > myfifo" );
  pthread_exit(0);
  }
  void thr_read(){
  pthread_detach( pthread_self() );
  pthread_t cthd;
  int stat = pthread_create( &cthd, NULL, thr_get, NULL );
  mf();
  pthread_exit(0);
  }
  int main(int argc,char** argv)
  {
  int pid;
  pthread_t cthd, dthd;
  void* tret;
  /*创建FIFO管道*/
  if((mkfifo(FIFO,O_CREAT|O_EXCL)<0)&&(errno!=EEXIST)){
  printf("cannot create fifoserver\n");
  }
  system( "chmod 777 myfifo" );
  int tsts = pthread_create( &dthd, NULL, thr_read, NULL );
  pthread_join( dthd, &tret );
  printf( "tsts is %d\n", tsts );
  sleep( 60 );
  unlink(FIFO);




欢迎光临 电子技术论坛_中国专业的电子工程师学习交流社区-中电网技术论坛 (http://bbs.eccn.com/) Powered by Discuz! 7.0.0