11
2月
2020

popenとpclose

パイプのopenとclose.
popenとpclose
読み込む
書き出す

popenとpclose

popenとpcloseは指定したsystem関数にパイプ機能を加えた感じで使用できる.実際shell経由で引数のコマンドを渡すので,オーバーヘッドは大きいがワイルドカードなどを使用できる.で,パイプを使用すると,あるコマンドの出力を別のコマンドの入力に使用できる.例えば
dmesg | head
では,dmesgの出力がheadの入力となりそしてそのheadの出力が端末に出力される.

読み込む

popenはファイルストリームを開く.pcloseは閉じる.popenではファイルストリームが読み込み用か書き込み用かどちらかを選択する.読むか書くかと聞かれたら,なんとなくまずは読んでみたい気がするのは私だけだろうか.読み込み用で開く場合,popenしたプロセスはコマンドラインでは|の右側ということになる.以下,popenで読み込み用パイプストリームを開いた場合のサンプル.

#include <stdlib.h>
#include <stdio.h>

#define BUFSIZE 100

/* �����Ѵؿ� */
int output(char *buffer);

int main(void)
{
  /* �ɤ߹����ѥѥ��� */
  FILE *in_pipe;
  /* �ɤ߹����ѥХåե� */
  char buffer[BUFSIZE + 1];
  int readed_num;

  /* �Хåե������� */
  memset(buffer,'\0',sizeof(buffer));

  /* �ѥ��פ��ɤ߹��ߥ⡼�ɤdz��� */
  in_pipe = popen("date","r");

  /* �������̾�Υե����륹�ȥ꡼���Ʊ�ͤ˰����� */
  if(in_pipe != NULL){
    readed_num = fread(buffer,sizeof(char),BUFSIZE,in_pipe);
    while(readed_num > 0){
      output(buffer);
      readed_num = fread(buffer,sizeof(char),BUFSIZE,in_pipe);
    }
    /* ˺�줺���Ĥ��� */
    pclose(in_pipe);
    exit(EXIT_SUCCESS);
  }
  exit(EXIT_FAILURE);
}

/* �����Ѵؿ� */
int output(char *buffer)
{
  while(*buffer != '\0'){
    if(*buffer == ' '){
      fprintf(stdout,"\n");
      buffer++;
    }else{
      fprintf(stdout,"%c",*buffer++);
    }
  }
  return 0;
}

popenの第二引数に”r”を指定すると読み込みモードでパイプをオープンする.そしてこのとき読み込みようのファイルストリームが返る.失敗するとNULLを返す.以下実行結果.
2003年

4月
10日
木曜日
21:50:48
JST

書き出す

読んだら書きたい.書き込み用でパイプをオープンしたプロセスはコマンドラインでは|の左側ということになる.以下サンプル.

#include <stdlib.h>
#include <stdio.h>

#define BUFSIZE 100
/* �ѥ��פ���񤭽Ф���å����� */
#define MESSAGE "hoge"

int main(void)
{
  /* �񤭹����ѥѥ��� */
  FILE *out_pipe;
  /* �񤭹����ѥХåե� */
  char buffer[BUFSIZE + 1];
  int written_num;

  /* �Хåե������� */
  memset(buffer,'\0',sizeof(buffer));
  sprintf(buffer,MESSAGE);

  /* �ѥ��פ�񤭹��ߥ⡼�ɤdz��� */
  out_pipe = popen("banner -w 30","w");

  /* �������̾�Υե����륹�ȥ꡼���Ʊ�ͤ˰����� */
  if(out_pipe != NULL){
    written_num = fwrite(buffer,sizeof(char),BUFSIZE,out_pipe);
    while(written_num > 0){
      written_num = fread(buffer,sizeof(char),BUFSIZE,out_pipe);
    }
    /* ˺�줺���Ĥ��� */
    pclose(out_pipe);
    exit(EXIT_SUCCESS);
  }
  exit(EXIT_FAILURE);
}

popenの第二引数に”w”を指定するとパイプを書き込みモードでオープンする.そして書き込みようのファイルストリームを返す.失敗するとNULLを返す.以下実行結果.
Message: # #
#####################
#####################
#
##
#############
############
#
####
#########
## ##
# #
# ##
## ##
#########
####
## ##
## #### ######
# ####### ##
# ### # #
# ### # ##
####### #######
### #### ##
#
####
#########
## # ##
# # #
# # ##
# # ###
# #####

これは
echo “hoge” | banner -w 30
と同じ結果である.

You may also like...