Справочник функций

Ваш аккаунт

Войти через: 
Забыли пароль?
Регистрация
Информацию о новых материалах можно получать и без регистрации:

Почтовая рассылка

Подписчиков: -1
Последний выпуск: 19.06.2015

реализация команды cat filename|sort

15K
29 марта 2007 года
K1mi
10 / / 28.10.2006
Нужно написать программу, реализующую аналог команды конвейера cat filename|sort. в программе нужно использовать pipe, fork, dup2, close,execve.
4.9K
29 марта 2007 года
efferson
57 / / 08.12.2005
http://forum.codenet.ru/showthread.php?t=36480

Далее просто copy/paste :)

Если вкратце: создаёшь один канал в родителе, fork'аешь двух потомков. Отрубаешь ненужные тебе концы каналов. Перенаправляешь стандартный вывод первого потомка в писательный конец канала, а стандартный ввод второго в читательный конец канала. Далее exec'ом подменяешь образ соответствующего потомка образом соответствующей команды...
502
29 марта 2007 года
Jail
550 / / 30.01.2007
Цитата:
Если вкратце: создаёшь один канал в родителе, fork'аешь двух потомков. Отрубаешь ненужные тебе концы каналов. Перенаправляешь стандартный вывод первого потомка в писательный конец канала, а стандартный ввод второго в читательный конец канала. Далее exec'ом подменяешь образ соответствующего потомка образом соответствующей команды...


Только один вопрос..........А зачем такие извращения если уже есть один PIPE '|' ???? Если ради познания, то в исходниках UNIX всё есть.

4.9K
30 марта 2007 года
efferson
57 / / 08.12.2005
Это ещё не извращения :) Просто, как я понял, челу нужно было сэмулировать это дело - а тут чем ниже уроень абстракции, тем лучше... :)
502
01 апреля 2007 года
Jail
550 / / 30.01.2007
[LEFT]Идея конечно хорошая, но краткость сестра таланта( а некраткость и есть талант)))) :D
В любой литре по программированию для Linux, описано создание неименнованного канала pipe.
Чтобы создать простой канал на Си, прибегают к использованию системного вызова pipe(). после создания канала, процесс обычно пораждает новый процесс.
 
Код:
SYSTEM CALL: pipe();
  PROTOTYPE: int pipe( int fd[2] );
  RETURNS: 0 в случае успеха
           -1 в случае ошибки:
              errno = EMFILE (нет свободных дескрипторов)
                      EMFILE (системная файловая таблица переполнена)
                      EFAULT (массив fd некорректен)

  NOTES: fd[0] устанавливается для чтения, fd[1] - для записи.
Все данные, проходящие через канал, перемещаются через ядро:
Код:
#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>

main()
{
  int fd[2];

  pipe(fd);
  .
  .
}
Имя массива decays в С это указатель на его первый член. fd это эквивалент &fd[0].
После установки канала делается ответвление потомка:
Код:
#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>

main()
{
  int     fd[2];
  pid_t   childpid;

  pipe(fd);
  if ((childpid = fork()) == -1)
  {
     perror("fork");
     exit(1);
  }
  .
  .
}
Если родитель хочет получить данные от потомка, то он должен закрыть fd1, а потомок должен закрыть fd0. Если родитель хочет послать данные потомку, то он должен закрыть fd0, а потомок - fd1. С тех пор как родитель и потомок делят между собой дескрипторы, нужно всегда быть увереными, что не используемый нами в данный момент конец канала закрыт; EOF никогда не будет возвращен, если ненужные концы канала не закрыты.
Код:
#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>

main()
{
  int     fd[2];
  pid_t   childpid;

  pipe(fd);
  if ((childpid = fork()) == -1)
  {
     perror("fork");
     exit(1);
  }
  if (childpid == 0)
  {
     /* Child process closes up input side of pipe */
     close(fd[0]);
  }
  else
  {
    /* Parent process closes up output side of pipe */
    close(fd[1]);
  }
  .
  .
}
После поднятия канала, файловые дискрипторы могут обрабатываться подобно дескрипторам обычных файлов.
Код:
/**************************************************************************
 Excerpt from "Linux Programmer's Guide - Chapter 6"
 (C)opyright 1994-1995.
 **************************************************************************
 MODULE: pipe.c
 **************************************************************************/
#include <stdio.h>
#include <unistd.h>
#include <sys/types.h>
int main(void)
{
  int     fd[2], nbytes;
  pid_t   childpid;
  char    string[] = "Hello, world!\n";
  char    readbuffer[80];
  pipe(fd);
  if ((childpid = fork()) == -1)
  {
     perror("fork");
     exit(1);
  }
  if (childpid == 0)
  {
     /* Child process closes up input side of pipe */
     close(fd[0]);
     /* Send "string" through the output side of pipe */
     write(fd[1], string, strlen(string));
     exit(0);
  }
  else
  {
    /* Parent process closes up output side of pipe */
    close(fd[1]);
    /* Read in a string from the pipe */
    nbytes = read(fd[0], readbuffer, sizeof(readbuffer));
    printf("Received string: %s", readbuffer);
  }
  return(0);
}
И т.д. и т.п. :)
[/LEFT]
Реклама на сайте | Обмен ссылками | Ссылки | Экспорт (RSS) | Контакты
Добавить статью | Добавить исходник | Добавить хостинг-провайдера | Добавить сайт в каталог