Читаем Linux API. Исчерпывающее руководство полностью

Подобную проверку всегда следует проводить в программах, запускающих произвольные команды на основе пользовательского ввода, используя функции popen() (или system()). Как вариант символы, которые не нужно проверять, можно было бы заключить в кавычки — таким образом командная оболочка не стала бы их интерпретировать.

44.6. Каналы и буферизация стандартного ввода/вывода

Поскольку указатель на файловый поток, возвращаемый вызовом popen(), не ссылается на терминал, библиотека stdio применяет к данному потоку блочную буферизацию (см. раздел 13.2). Это значит, что по умолчанию при выполнении функции popen() в режиме w вывод передается дочернему процессу на другом конце канала только после заполнения буфера или закрытия самого канала с помощью вызова pclose(). Во многих случаях это не вызывает никаких проблем. Однако если нужно, чтобы потомок получал данные из канала немедленно, то есть два варианта: можно периодически вызывать fflush() или отключить буферизацию, используя вызов setbuf(fp, NULL). То же самое можно сделать, если мы создаем канал, задействуя системный вызов pipe(), а затем применяем fdopen() для получения потока стандартного вывода, связанного с записывающим концом канала.

Но все может оказаться сложнее, если процесс, вызывающий popen(), читает из канала (то есть при указании режима r). В таком случае, если потомок использует библиотеку stdio (и при этом не делает вызовов fflush() или setbuf()), то его вывод дойдет до вызывающего процесса либо после заполнения буфера, либо в результате вызова fclose(). (То же самое относится к ситуации, когда мы читаем из канала, созданного с помощью вызова pipe(), а процесс на другом конце записывает данные, применяя библиотеку stdio.) Если такое поведение вас не устраивает, исправить его почти невозможно — разве что можно отредактировать исходный код программы, выполняющейся в дочернем процессе, и добавить туда вызов setbuf() или fflush().

Если у вас нет доступа к исходному коду, канал можно заменить псевдотерминалом — IPC-каналом, один конец которого подключается к процессу и ведет себя как терминал. В итоге библиотека stdio будет буферизировать вывод построчно. Псевдотерминалы будут описаны в главе 60.

44.7. Очереди FIFO

С точки зрения семантики очередь FIFO похожа на канал. Ее принципиальное отличие заключается в том, что у нее есть имя в рамках файловой системы и ее можно открывать так же, как обычный файл. Это позволяет использовать очереди FIFO для взаимодействия процессов, не имеющих отношения друг к другу (например, между клиентом и сервером).

Для работы с открытой очередью FIFO служат те же системные вызовы, что и в случае с каналами и другими файлами (то есть read(), write() и close()). По аналогии с каналами очередь FIFO имеет записывающий и считывающий конец, а данные, которые из них читаются, поступают в том же порядке, в каком они были записаны. На этом и основывается название FIFO — «первым пришел — первым ушел» (англ. first in, first out). Такие очереди иногда называют именованными каналами.

Как и в случае с каналами, данные внутри очереди FIFO теряются при закрытии последнего дескриптора, который на нее ссылается.

Очередь FIFO можно создать, задействуя консольную команду mkfifo:

$ mkfifo [-m mode] pathname

где pathname — имя создаваемой очереди, а параметр — m используется, чтобы задать режим доступа (так же как это делается в команде chmod).

Функции fstat() и stat(), если их применить к очереди FIFO (или каналу), возвращают в поле st_mode структуры stat (см. раздел 15.1) тип файла S_IFIFO. При выводе с помощью команды ls — l очередь FIFO содержит в первом столбце тип p, а команда ls — F добавляет к ее имени символ канала (|).

Функция mkfifo() позволяет создать очередь FIFO с заданным именем.

#include

int mkfifo(const char *pathname, mode_t mode);

Возвращает 0 при успешном завершении или -1 при ошибке

Аргумент mode задает права доступа к новой очереди FIFO. Они состоят из констант, к которым применяется побитовое ИЛИ (см. табл. 15.4). Как и к обычным правам доступа, к ним применяется атрибут umask (см. подраздел 15.4.6).

Изначально очереди FIFO создавались с помощью системного вызова mknod(pathname, S_IFIFO, 0), который позволяет создавать различные виды файлов, включая файлы устройств (в стандарте SUSv3 применение mknod() ограничивается созданием очередей FIFO). В стандарте POSIX.1-1990 появился более простой, хотя и менее универсальный программный интерфейс, mkfifo(). В большинстве UNIX-систем он реализован в виде обертки вокруг mknod().

Новую очередь FIFO может открыть любой процесс, имеющий соответствующие права доступа (см. подраздел 15.4.3).

Перейти на страницу:

Похожие книги

1С: Бухгалтерия 8 с нуля
1С: Бухгалтерия 8 с нуля

Книга содержит полное описание приемов и методов работы с программой 1С:Бухгалтерия 8. Рассматривается автоматизация всех основных участков бухгалтерии: учет наличных и безналичных денежных средств, основных средств и НМА, прихода и расхода товарно-материальных ценностей, зарплаты, производства. Описано, как вводить исходные данные, заполнять справочники и каталоги, работать с первичными документами, проводить их по учету, формировать разнообразные отчеты, выводить данные на печать, настраивать программу и использовать ее сервисные функции. Каждый урок содержит подробное описание рассматриваемой темы с детальным разбором и иллюстрированием всех этапов.Для широкого круга пользователей.

Алексей Анатольевич Гладкий

Программирование, программы, базы данных / Программное обеспечение / Бухучет и аудит / Финансы и бизнес / Книги по IT / Словари и Энциклопедии
1С: Управление торговлей 8.2
1С: Управление торговлей 8.2

Современные торговые предприятия предлагают своим клиентам широчайший ассортимент товаров, который исчисляется тысячами и десятками тысяч наименований. Причем многие позиции могут реализовываться на разных условиях: предоплата, отсрочка платежи, скидка, наценка, объем партии, и т.д. Клиенты зачастую делятся на категории – VIP-клиент, обычный клиент, постоянный клиент, мелкооптовый клиент, и т.д. Товарные позиции могут комплектоваться и разукомплектовываться, многие товары подлежат обязательной сертификации и гигиеническим исследованиям, некондиционные позиции необходимо списывать, на складах периодически должна проводиться инвентаризация, каждая компания должна иметь свою маркетинговую политику и т.д., вообщем – современное торговое предприятие представляет живой организм, находящийся в постоянном движении.Очевидно, что вся эта кипучая деятельность требует автоматизации. Для решения этой задачи существуют специальные программные средства, и в этой книге мы познакомим вам с самым популярным продуктом, предназначенным для автоматизации деятельности торгового предприятия – «1С Управление торговлей», которое реализовано на новейшей технологической платформе версии 1С 8.2.

Алексей Анатольевич Гладкий

Финансы / Программирование, программы, базы данных