Вкратце опишу проблему. Есть дочерний процесс, консольный. Ему надо перенаправить вывод stdout в сокет. Очевидно, это делается довольно просто (надо создавать сокет через WSASocket, затем DuplicateHandle, дабы разрешить наследование на 9х, ну а далее все как обычно, используя полученный хендл в качестве stdout при создании дочернего процесса). Это все сделано и работает — как на 9х, так и на NT. Однако в процессе обнаружились следующие моменты — здесь и здесь. Вкратце — если установлены LSP, то DuplicateHandle может вернуть некорректный сокет, причем отследить сам вызов DuplicateHandle в LSP (т.е. каким-либо образом скорректировать проблему), невозможно.
Вопрос в следующем — так ли это? Ну или на крайний случай порекомендуйте, какое либо приложение, которое устанавливает свой LSP, дабы проверить сий прискорбный факт. Ну и еще вопрос вдогонку — как оказалось, создать сокет, подходящий для stdout можно только при помощи WSASocket, либо установкой setsockopt( SO_OPENTYPE) в значение, отличное от нуля (например, SO_SYNCHRONOUS_NONALERT). Причем оба варианта приводят к шваху при использовании LSP (Q189171). Уж очень не хочется принимать stdout в пайп, а затем это все передавать в сокет, уж больно глупо как то... да и сложнее — придется отдельные треды на прием\передачу делать, чего бы не хотелось..
В общем, всем заранее спасибо за советы.
Здравствуйте, Andrew S, Вы писали:
AS>Всем привет.
AS>Вкратце опишу проблему. Есть дочерний процесс, консольный. Ему надо перенаправить вывод stdout в сокет. Очевидно, это делается довольно просто (надо создавать сокет через WSASocket, затем DuplicateHandle, дабы разрешить наследование на 9х, ну а далее все как обычно, используя полученный хендл в качестве stdout при создании дочернего процесса). Это все сделано и работает — как на 9х, так и на NT. Однако в процессе обнаружились следующие моменты — здесь и здесь. Вкратце — если установлены LSP, то DuplicateHandle может вернуть некорректный сокет, причем отследить сам вызов DuplicateHandle в LSP (т.е. каким-либо образом скорректировать проблему), невозможно. AS>Вопрос в следующем — так ли это? Ну или на крайний случай порекомендуйте, какое либо приложение, которое устанавливает свой LSP, дабы проверить сий прискорбный факт. Ну и еще вопрос вдогонку — как оказалось, создать сокет, подходящий для stdout можно только при помощи WSASocket, либо установкой setsockopt( SO_OPENTYPE) в значение, отличное от нуля (например, SO_SYNCHRONOUS_NONALERT). Причем оба варианта приводят к шваху при использовании LSP (Q189171). Уж очень не хочется принимать stdout в пайп, а затем это все передавать в сокет, уж больно глупо как то... да и сложнее — придется отдельные треды на прием\передачу делать, чего бы не хотелось.. AS>В общем, всем заранее спасибо за советы.
LSP фильтры могут создавать дескрипторы двух видов: IFS и non IFS. Первые являются нормальными дескрипторами. Их можно использовать в файловых операциях и можно дублировать с помощью DuplicateHandle. Но в этом случае вызовы ReadFile/WriteFile пойдут мимо LSP фильтра, клиент будет работать напрямую с ядром. Разработчикам LSP фильтров така ситуация не нравится , поэтому они используют обычно non IFS дескрипторы. Это просто числа, они не являются дескрипторами и имеют смысл только для LSP провайдера. В принципе, такие дескриторы можно дублировать с помощью WSADuplicateSocket, но это не решает проблемы — в сокет с non IFS нельзя перенаправить ввод/вывод с консоли.
Могу посоветовать использовать WSASocket c заполненной струтурой WSAPROTOCOL_INFO, где указать флаг XP1_IFS_HANDLES
PS: если поможет, шлите пиво ))))))))))
Да пребудет с тобою сила
Re[2]: Перенаправлени stdio дочернего процесса на сокеты + L
TC>Могу посоветовать использовать WSASocket c заполненной струтурой WSAPROTOCOL_INFO, где указать флаг XP1_IFS_HANDLES
Про IFS\не IFS я уже тоже начитался. А вот перебрать провайдеров и найти подходящего для протокола как то не догадался. Да, по-видимому, только этот вариант. Либо пайпы в качестве промежуточного буфера, чего активно не хочется — там будут как минимум проблемы с прерыванием блокирующих чтений\записей...
TC>PS: если поможет, шлите пиво ))))))))))
Пиво, наверное, не получится, а вот оценку с удовольствием поставлю. Спасибо!
Всем привет еще раз.
Возник еще один вопрос по этой же тематике.
Перенаправление оутпута на IFS сокет вполне работает. Но, оказывается, не всегда. По крайней мере, я не смог добиться работы при следующих условиях
1. Система: Windows 95 osr2 + winsock2.2 update
2. Дочерний процесс: не консольный, однако пишет в stdout
В nt-based системах все работает нормально во всех случаях. Если на 95-эх вместо (2) подсунуть именно консольное приложение (т.е. у которого во флагах PE указано что оно консольное), то все работает и в 95-х. Если вместо сокетов пользовать пайпы, то неконсольное работает и в 95-х.
Есть какие предположения, уже больно странно то, что поведение различается в случае gui и не gui дочернего процесса только на 9х системах, причем на пайпах там работает в обоих случаях нормально.. Я в смятении Q150523 вообще утверждает, что сокеты нальзя ставить как стандартые хендлы для дочерних процессов в Windows 9х, но это явно не так — для консольных приложений все работает...