mod_fcgid оконные именованные каналы 2-й и последующие запросы

Итак, я создаю интерфейс fastCGI для языка программирования, основанного на времени выполнения и работающего в средах Windows, Linux и UNIX.

Я реализовал протокол fastCGI в программном коде, работающем во время выполнения, но у меня возникла проблема с кодом Windows, который взаимодействует с mod_fcgid. В этом случае я не могу использовать готовые dll для предоставления функций fastCGI, но я могу вызывать большинство функций C из этого языка выполнения. Я не могу изменить среду выполнения, поскольку она принадлежит другой компании... Думайте об этом как о языке, подобном php или perl. То, что я пытаюсь сделать, похоже на создание dll-подобного набора кода (это не dll) для обработки запроса fastCGI. Хотя многие скажут, что я «изобретаю велосипед», у меня нет другого выбора, кроме как использовать чью-то готовую dll для предоставления интерфейса для fastCGI.

Я успешно все реализовал, и я могу получить первоначальный запрос и ответить веб-страницей через мой интерфейс fastCGI. Проблема, с которой я сталкиваюсь, связана со «следующим» запросом при работе под Windows. Мой код при работе под Linux работает потрясающе: я accept() сокет, read() write() для выполнения моей обработки, close() сокет, а затем возвращаюсь и снова accept(), и я получаю следующий запрос и все отлично обрабатывается.

Под Windows mod_fcgid использует именованные каналы. В моем коде я использую GetStdHandle(), чтобы получить дескриптор стандартного ввода, затем использую ReadFile() и WriteFile(), и данные, завернутые в протокол fastCGI, передаются в mod_fcgid, а затем в браузер, когда выполняется запрос, я использую CloseHandle( ), а затем возвращаюсь к GetStdHandle(), чтобы дождаться следующего запроса.

Все отлично работает по первому запросу, браузер получает мой вывод cgi. Тот же код под Linux, использующий сокеты, получает 2-й и последующие запросы и работает как шарм.

Мои проблемы: при работе под Windows после обработки первого запроса я не могу заставить mod_fcgid отправить мне второй запрос. В конечном итоге это убьет мой процесс Windows и запустит новый на его месте. Чего я, конечно, не хочу.

Должно быть, я делаю что-то неправильно между моментом, когда я отправляю fastCGI EndRequest, и когда я зацикливаюсь, чтобы дождаться поступления следующего запроса.

Чтобы получить первоначальный запрос от mod_fcgid, я использую GetStdHandle(), затем я использую ReadFile() и WriteFile() (все из kernel32.dll), и когда я закончил протокол с его EndRequest, я не могу получить правильный код. может получить второй запрос.

Я пробовал fflush() Я пробовал FileFlushBuffers(), я пытался не закрывать дескриптор, полученный от GetStdHandle(), я просто не могу понять, что нужно mod_fcgid от моего приложения Windows, чтобы я мог получить второй и последующие запросы.

После первого запроса, закрывая мой дескриптор, получая дескриптор стандартного ввода из GetStdHandle, а затем сидя на ReadFile, ReadFile() возвращается с 0 байтами, а GetLastError() всегда возвращает 6 (неверный дескриптор).

Я просто не могу понять, какие функции C использовать для очистки после завершения первого запроса и иметь возможность ждать поступления следующего запроса при работе под Windows. Как я уже говорил, код отлично работает под Linux при использовании сокетов вместо Windows, которая использует дескриптор из STDIN, который является именованным каналом.


person user7405204    schedule 11.01.2017    source источник
comment
Вы имеете в виду, что он использует _un_named каналы? Это то, что я ожидал бы, когда используется STDIN/STDOUT.   -  person Ctx    schedule 11.01.2017
comment
Я не могу найти документацию, подтверждающую это, но, основываясь на том, как протокол FastCGI работает через TCP/IP, я ожидаю, что дескриптор, который вам дали, относится к серверному концу именованного канала. . (Мой предыдущий комментарий, теперь удаленный, предполагал, что это был конец клиента; моя ошибка.) Поэтому вместо закрытия дескриптора вы хотите вызвать DisconnectNamedPipe, а затем ConnectNamedPipe (который будет блокироваться, пока не будет готов новый запрос).   -  person Harry Johnston    schedule 12.01.2017
comment
Гарри, спасибо за это. Я считаю, что мне нужно использовать эти функции NamedPipe. Я изучал исходный код mod_fcgi, который включает libfcgi.dll, которую люди могут использовать для включения в свои приложения. Я вижу это с использованием ConnectNamedPipe и DisconnectNamedPipe, а также с использованием некоторого IOCompletion, который я действительно не понимаю, для чего он используется, но я считаю, что вы правы в отношении вызовов NamedPipe. Спасибо.   -  person user7405204    schedule 20.01.2017


Ответы (1)


Гарри, ваш комментарий об использовании функций NamedPipe помог, мне нужно было использовать FileFlushBuffers, за которым следует DisconnectNamedPipe в конце первого запроса, а затем ConnectNamedPipe, чтобы дождаться поступления следующего запроса. Еще раз спасибо.

person user7405204    schedule 22.01.2017