Функция WSPStartup (ws2spi.h)
Функция WSPStartup инициирует использование клиентом интерфейса поставщика сокетов Windows (SPI).
Синтаксис
int WSPStartup(
[in] WORD wVersionRequested,
[out] LPWSPDATA lpWSPData,
[in] LPWSAPROTOCOL_INFOW lpProtocolInfo,
[in] WSPUPCALLTABLE UpcallTable,
[out] LPWSPPROC_TABLE lpProcTable
);
Параметры
[in] wVersionRequested
Самая высокая версия поддержки SPI сокетов Windows, которую может использовать вызывающий объект. Байт высокого порядка указывает дополнительный номер версии (редакции); Байт нижнего порядка указывает номер основной версии.
[out] lpWSPData
Указатель на структуру данных WSPDATA , которая получает сведения о поставщике службы Сокетов Windows.
[in] lpProtocolInfo
Указатель на структуру WSAProtocol_Info , которая определяет характеристики требуемого протокола. Это особенно полезно, если одна библиотека DLL поставщика может создавать экземпляры нескольких разных поставщиков служб.
[in] UpcallTable
Таблица отправки winsock 2 DLL (Ws2_32.dll) представляет собой структуру WSPUpCallTable .
[out] lpProcTable
Указатель на таблицу указателей функций SPI. Эта таблица возвращается в виде структуры WSPProc_Table .
Возвращаемое значение
Функция WSPStartup возвращает ноль в случае успешного выполнения. В противном случае возвращается один из приведенных ниже кодов ошибок.
Код ошибки | Значение |
---|---|
Сетевая подсистема недоступна. Эта ошибка возвращается, если реализация сокетов Windows не может работать в настоящее время, так как базовая система, использующаяся для предоставления сетевых служб, в настоящее время недоступна. | |
Версия Winsock.dll выходит за пределы диапазона. Эта ошибка возвращается, если запрошенная версия поддержки SPI сокетов Windows не предоставляется этим поставщиком службы Сокетов Windows. | |
Выполняется блокировка сокетов Windows 1.1. | |
Достигнуто ограничение на количество задач, поддерживаемых реализацией сокетов Windows. | |
Недопустимый параметр lpWSPData или lpProcTable . |
Комментарии
Поставщики транспортных служб Windows Sockets 2 — это библиотеки DLL с одной экспортируемой точкой входа процедуры WSPStartup, используемой для функции инициализации поставщика услуг. Все остальные функции поставщика услуг становятся доступными для библиотеки DLL Winsock 2 через таблицу диспетчеризации поставщика услуг, переданную в параметре lpProcTable в функцию WSPStartup . Библиотеки DLL поставщика услуг загружаются в память библиотекой DLL WinSock 2 только при необходимости и выгружаются, когда их службы больше не требуются.
Интерфейс поставщика услуг также определяет несколько ситуаций, когда поставщик транспортных служб вызывает библиотеку DLL Winsock 2 (реплики) для получения служб поддержки DLL. Поставщику транспортных служб возвращается таблица диспетчеризации для библиотеки DLL Winsock 2 в параметре Реплика, переданном в функцию WSPStartup .
Функция WSPStartup должна быть первой функцией SPI Сокетов Windows, вызываемой клиентом Windows Sockets SPI на основе каждого процесса. Он позволяет клиенту указать требуемую версию SPI сокетов Windows и предоставить таблицу отправки для него. Все функции с префиксом WPU, созданные поставщиком услуг Сокетов Windows, вызываются через таблицу диспетчеризации для всех клиентов. Эта функция также позволяет клиенту получать сведения о конкретной реализации поставщика услуг Сокетов Windows. Клиент Windows Sockets SPI может выдавать дополнительные функции SPI сокетов Windows только после успешного вызова WSPStartup . Таблица указателей на остальные функции SPI извлекается с помощью параметра lpProcTable , который возвращает структуру WSPProc_Table .
Библиотека DLL Winsock 2 загружает библиотеку DLL интерфейса поставщика услуг в систему с помощью стандартных механизмов загрузки динамической библиотеки Windows и инициализирует ее, вызывая функцию WSPStartup . Обычно это активируется приложением, вызывающим функцию сокета или WSASocket для создания нового сокета, который должен быть связан с поставщиком услуг, библиотека DLL интерфейса которого в настоящее время не загружается в память.
Для поддержки будущих версий windows Sockets SPI и Ws2_32.dll, которые могут иметь функциональные отличия от текущего spi сокетов Windows, согласование выполняется в WSPStartup. Вызывающий объект WSPStartup (Ws2_32.dll или многоуровневый протокол) и поставщик служб Сокетов Windows указывают друг другу на самую высокую версию сокетов Windows, которую они могут поддерживать, и каждый из них подтверждает, что самая высокая версия другого пользователя является приемлемой. При входе в WSPStartup поставщик службы Сокетов Windows проверяет версию, запрошенную клиентом. Если эта версия равна или выше самой низкой версии, поддерживаемой поставщиком услуг, вызов выполняется успешно, и поставщик служб возвращает в элементе wHighVersion структуры WSPDATA самую высокую поддерживаемую версию, а в элементе wVersion — минимальную версию и версию, указанную в параметре wVersionRequested . Затем поставщик службы Сокетов Windows предполагает, что клиент WINDOWS Sockets SPI будет использовать версию сокетов Windows, указанную в элементе wVersion . Если член wVersion структуры WSPDATA неприемлем для вызывающего объекта, он должен вызвать LPWSPCleanup и либо найти другого поставщика служб Сокетов Windows, либо не выполнить инициализацию.
Это согласование позволяет поставщику услуг Windows Sockets и клиенту SPI Windows Sockets поддерживать ряд версий сокетов Windows. Клиент может успешно использовать поставщик службы Сокетов Windows, если диапазоны версий перекрываются.
Текущая версия спецификации сокетов Windows — версия 2.2. Текущая библиотека DLL Winsock ,Ws2_32.dll, поддерживает приложения, запрашивающие любую из следующих версий спецификации сокетов Windows:
- 1,0
- 1,1
- 2.0
- 2.1
- 2.2
Чтобы получить полный доступ к новому синтаксису более поздней версии спецификации Сокетов Windows, приложение должно согласовать эту более позднюю версию. В этом случае параметру wVersionRequested следует задать запрос версии 2.2. Приложение также должно полностью соответствовать этой более поздней версии спецификации сокета Windows, например компиляция по соответствующему файлу заголовка, связывание с новой библиотекой или другие особые случаи. Файл заголовка Winsock2.h для поддержки Winsock 2 входит в состав microsoft пакет средств разработки программного обеспечения для Windows (SDK).
Сокеты Windows версии 2.2 поддерживаются в Windows Server 2008, Windows Vista, Windows Server 2003, Windows XP, Windows 2000, Windows NT 4.0 с пакетом обновления 4 (SP4) и более поздних версий, Windows Me, Windows 98 и Windows 95 OSR2.
Сокеты Windows версии 2.2 также поддерживаются в
Windows 95 с обновлением сокета Windows 2. Приложения на этих платформах обычно запрашивают Winsock 2.2, задавая соответствующий параметр wVersionRequested .
В Windows 95 и версиях Windows NT 3.51 и более ранних версий сокеты Windows версии 1.1 являются самой высокой поддерживаемой версией спецификации сокетов Windows.
Для успешного согласования этой более ранней версии с помощью функции WSPStartup в приложении или библиотеке DLL, написанной на записи, можно использовать более раннюю версию спецификации сокетов Windows, поддерживаемую библиотекой DLL Winsock. Например, приложение может запросить версию 1.1 в параметре wVersionRequested, переданном функции WSPStartup на платформе с библиотекой DLL Winsock 2.2. В этом случае приложение должно полагаться только на функции, которые соответствуют запрошенной версии. Не следует использовать новые коды Ioctl, новое поведение существующих функций и новые функции. Согласование версий, предоставляемое WSPStartup, в основном использовалось для того, чтобы старые приложения Winsock 1.1, разработанные для Windows 95 и Windows NT 3.51 и более ранних версий, запускались с таким же поведением в более поздних версиях Windows. Файл заголовка Winsock.h для поддержки Winsock 1.1 входит в состав Windows SDK.
На следующей диаграмме приведены примеры работы WSPStartup в сочетании с различными версиями WS2_32.DLL и windows Sockets Service Provider (SP).
DLL |
SP |
wVersionRequested | wVersion | wHighVersion | Конечный результат |
---|---|---|---|---|---|
1.1 | 1.1 | 1.1 | 1.1 | 1,1 | use 1.1 |
1.0 1.1 | 1,0 | 1,1 | 1.0 | 1.0 | use 1.0 |
1,0 | 1.0 1.1 | 1.0 | 1.0 | 1,1 | use 1.0 |
1,1 | 1.0 1.1 | 1.1 | 1.1 | 1,1 | use 1.1 |
1,1 | 1.0 | 1,1 | 1.0 | 1.0 | Сбой библиотеки DLL |
1,0 | 1,1 | 1.0 | --- | --- | WSAVERNOTSUPPORTED |
1.0 1.1 | 1.0 1.1 | 1.1 | 1.1 | 1,1 | use 1.1 |
1.0 1.1 2.0 | 1,1 | 2,0 | 1,1 | 1,1 | use 1.1 |
1.0 1.1 2.0 | 2.0 | 2.0 | 2.0 | 2.0 | use 2.0 |
1.0 1.1 2.0 2.1 2.2 | 2.2 | 2.2 | 2.2 | 2.2 | use 2.2 |
В следующем фрагменте кода показано, как клиент Windows Sockets SPI, поддерживающий только версию 2 windows Sockets SPI, выполняет вызов WSPStartup :
WORD wVersionRequested;
WSPDATA WSPData;
int err;
WSPUPCALLTABLE upcallTable =
{
/* initialize upcallTable with function pointers */
};
LPWSPPROC_TABLE lpProcTable =
{
/* allocate memory for the ProcTable */
};
wVersionRequested = MAKEWORD( 2, 2 );
err = WSPStartup( wVersionRequested, &WSPData, lpProtocolBuffer, upcallTable, lpProcTable );
if ( err != 0 ) {
/* Tell the user that we could not find a usable */
/* Windows Sockets service provider. */
return;
}
/* Confirm that the Windows Sockets service provider supports 2.2.*/
/* Note that if the service provider supports versions */
/* greater than 2.2 in addition to 2.2, it will still */
/* return 2.2 in wVersion since that is the version we */
/* requested. */
if ( LOBYTE( WSPData.wVersion ) != 2 ||
HIBYTE( WSPData.wVersion ) != 2 ) {
/* Tell the user that we could not find a usable */
/* Windows Sockets service provider. */
LPWSPCleanup( );
return;
}
/* The Windows Sockets service provider is acceptable. Proceed. */
В этом фрагменте кода показано, как поставщик служб Windows Sockets, поддерживающий только версию 2.2, выполняет согласование WSPStartup :
/* Make sure that the version requested is >= 2.2. */
/* The low byte is the major version and the high */
/* byte is the minor version. */
if ( (LOBYTE( wVersionRequested ) < 2) ||
((LOBYTE( wVersionRequested ) == 2) &&
(HIBYTE( wVersionRequested ) < 2))) {
return WSAVERNOTSUPPORTED;
}
/* Since we only support 2.2, set both wVersion and */
/* wHighVersion to 2.2. */
lpWSPData->wVersion = MAKEWORD( 2, 2 );
lpWSPData->wHighVersion = MAKEWORD( 2, 2 );
После успешного вызова WSPStartup клиент Windows Sockets SPI может при необходимости выполнить другие вызовы SPI сокетов Windows. Завершив использование служб поставщика сокетов Windows, клиент должен вызвать LPWSPCleanup , чтобы позволить поставщику службы Сокетов Windows освободить все ресурсы, выделенные для клиента.
Функция WSPStartup должна вызываться по крайней мере один раз каждым клиентским процессом и может вызываться несколько раз библиотекой DLL Winsock 2 или другими сущностями. Для каждого успешного вызова WSPStartup необходимо вызывать соответствующую функцию LPWSPCleanup. Поставщик услуг должен поддерживать количество ссылок для каждого процесса. При каждом вызове WSPStartup вызывающий объект может указать любой номер версии, поддерживаемый библиотекой DLL поставщика услуг.
Поставщик услуг должен хранить указатель на таблицу отправки на клиенте, которая получается функцией WSPStartup в качестве параметра "Всесхватка", для каждого процесса. Если данный процесс вызывает WSPStartup несколько раз, поставщик услуг должен использовать только последний предоставленный указатель на таблицу отправки.
Клиент Windows Sockets SPI может вызывать WSPStartup несколько раз, если ему требуется получить сведения о структуре WSPDATA несколько раз. При каждом таком вызове клиент может указать любой номер версии, поддерживаемый поставщиком.
Должен быть один вызов LPWSPCleanup , соответствующий каждому успешному вызову WSPStartup , чтобы сторонние библиотеки DLL могли использовать поставщик сокетов Windows. Это означает, например, что если WSPStartup вызывается три раза, соответствующий вызов LPWSPCleanup должен выполняться три раза. Первые два вызова LPWSPCleanup не выполняют никаких действий, кроме уменьшения внутреннего счетчика; последний вызов LPWSPCleanup выполняет все необходимые действия по освобождению ресурсов.
Эту функцию (и большинство других функций поставщика услуг) можно вызывать в потоке, который запускается как 16-разрядный процесс, если клиент является 16-разрядным клиентом Windows Sockets 1.1. Одним из важных ограничений 16-разрядных процессов является то, что 16-разрядный процесс не может создавать потоки. Это важно для разработчиков поставщиков услуг, которые планируют использовать внутренний поток службы в рамках реализации.
К счастью, обычно существуют только две области, в которых условия для потока службы являются надежными:
- В реализации перекрывающегося завершения ввода-вывода.
- В реализации LPWSPEventSelect.
Обе эти области доступны только с помощью новых функций Windows Sockets 2, которые могут вызываться только 32-разрядными процессами.
Поток службы можно безопасно использовать при тщательном соблюдении этих двух правил проектирования:
- Используйте поток службы только для функций, недоступных для 16-разрядных клиентов Windows Sockets 1.1.
- Создавайте поток службы только по запросу.
Несколько других предостережений применяются к использованию внутренних потоков службы. Во-первых, потоки обычно имеют некоторое снижение производительности. Используйте как можно меньше и избегайте переходов потоков везде, где это возможно. Во-вторых, код всегда должен проверка ошибок при создании потоков и корректно и информативно (например, при использовании WSAEOPNOTSUPP) на случай, если какое-то событие выполнения, которое не ожидало, приведет к 16-разрядному процессу, выполняющем путь кода, которому требуются потоки.
Многоуровневый поставщик служб предоставляет реализацию этой функции, но он также является клиентом этой функции при вызове WSPStartup для инициализации следующего уровня в цепочке протоколов. Вызов WSPStartup следующего слоя может произойти во время выполнения WSPStartup этого слоя или может быть отложен и вызван по запросу, например при вызове LPWSPSocket . В любом случае некоторые особые рекомендации относятся к параметру lpProtocolInfo этой функции, так как он распространяется вниз по уровням цепочки протоколов.
Многоуровневый поставщик выполняет поиск в ProtocolChain структуры, на которую ссылается lpProtocolInfo , чтобы определить собственное расположение в цепочке (путем поиска собственного идентификатора записи каталога слоя) и идентификатор следующего элемента в цепочке. Если следующий элемент является другим слоем, то при вызове WSPStartup следующего слоя этот слой должен передать следующему слою lpProtocolInfo , который ссылается на ту же неизмененную структуру WSAProtocol_Info с теми же неизмененные сведениями о цепочке. Однако если следующим уровнем является базовый протокол (т. е. последний элемент в цепочке), этот слой выполняет подстановку при вызове WSPStartup базового поставщика. В этом случае на структуру WSAPROTOCOL_INFO базового поставщика следует ссылаться с помощью параметра lpProtocolInfo .
Одним из важнейших преимуществ этой политики является то, что поставщики базовых служб не должны знать о цепочках протоколов.
Эта же политика распространения применяется при распространении структуры WSAPROTOCOL_INFO через многоуровневую последовательность других функций, таких как LPWSPAddressToString, LPWSPDuplicateSocket, LPWSPSocket или LPWSPStringToAddress.
Требования
Требование | Значение |
---|---|
Минимальная версия клиента | Windows 2000 Professional [только классические приложения] |
Минимальная версия сервера | Windows 2000 Server [только классические приложения] |
Целевая платформа | Windows |
Header | ws2spi.h |