Home | Info | Community | Development | myReactOS | Contact Us
ReactOS Development > Doxygenhandle.c
Go to the documentation of this file.
00001 /* 00002 * COPYRIGHT: See COPYING in the top level directory 00003 * PROJECT: ReactOS WinSock 2 DLL 00004 * FILE: include/ws2_32.h 00005 * PURPOSE: WinSock 2 DLL header 00006 */ 00007 00008 /* INCLUDES ******************************************************************/ 00009 00010 #include "precomp.h" 00011 00012 /* DATA **********************************************************************/ 00013 00014 typedef struct _WSH_HELPER_CONTEXT 00015 { 00016 HANDLE FileHandle; 00017 HANDLE ThreadHandle; 00018 HANDLE DllHandle; 00019 } WSH_HELPER_CONTEXT, *PWAH_HELPER_CONTEXT; 00020 00021 LPFN_WSASEND pWSASend; 00022 LPFN_WSARECV pWSARecv; 00023 LPFN_WSASENDTO pWSASendTo; 00024 LPFN_WSARECVFROM pWSARecvFrom; 00025 LPFN_WSAGETLASTERROR pWSAGetLastError; 00026 LPFN_WSACANCELBLOCKINGCALL pWSACancelBlockingCall; 00027 LPFN_WSASETBLOCKINGHOOK pWSASetBlockingHook; 00028 LPFN_SELECT pSelect; 00029 LPFN_WSASTARTUP pWSAStartup; 00030 LPFN_WSACLEANUP pWSACleanup; 00031 LPFN_GETSOCKOPT pGetSockOpt; 00032 LPFN_WSAIOCTL pWSAIoctl; 00033 00034 #define APCH (HANDLE)'SOR ' 00035 00036 /* FUNCTIONS *****************************************************************/ 00037 00038 VOID 00039 CALLBACK 00040 ApcThread(ULONG_PTR Context) 00041 { 00042 00043 } 00044 00045 NTSTATUS 00046 WINAPI 00047 DoSocketCancel(PVOID Context1, 00048 PVOID Context2, 00049 PVOID Context3) 00050 { 00051 return STATUS_SUCCESS; 00052 } 00053 00054 NTSTATUS 00055 WINAPI 00056 DoSocketRequest(PVOID Context1, 00057 PVOID Context2, 00058 PVOID Context3) 00059 { 00060 return STATUS_SUCCESS; 00061 } 00062 00063 VOID 00064 CALLBACK 00065 ExitThreadApc(ULONG_PTR Context) 00066 { 00067 PWAH_HELPER_CONTEXT HelperContext = (PWAH_HELPER_CONTEXT)Context; 00068 HMODULE DllHandle = HelperContext->DllHandle; 00069 00070 /* Close the file handle */ 00071 CloseHandle(HelperContext->FileHandle); 00072 00073 /* Free the context */ 00074 HeapFree(GlobalHeap, 0, HelperContext); 00075 00076 /* Exit the thread and library */ 00077 FreeLibraryAndExitThread(DllHandle, ERROR_SUCCESS); 00078 } 00079 00080 DWORD 00081 WINAPI 00082 WahCloseHandleHelper(IN HANDLE HelperHandle) 00083 { 00084 DWORD ErrorCode; 00085 PWAH_HELPER_CONTEXT Context = HelperHandle; 00086 00087 /* Enter the prolog, make sure we're initialized */ 00088 ErrorCode = WS2HELP_PROLOG(); 00089 if (ErrorCode != ERROR_SUCCESS) return ErrorCode; 00090 00091 /* Validate the handle */ 00092 if (!Context) return ERROR_INVALID_PARAMETER; 00093 00094 /* Queue an APC to exit the thread */ 00095 if (QueueUserAPC(ExitThreadApc, Context->ThreadHandle, (ULONG_PTR)Context)) 00096 { 00097 /* Done */ 00098 return ERROR_SUCCESS; 00099 } 00100 else 00101 { 00102 /* We failed somewhere */ 00103 return ERROR_GEN_FAILURE; 00104 } 00105 } 00106 00107 DWORD 00108 WINAPI 00109 WahCloseSocketHandle(IN HANDLE HelperHandle, 00110 IN SOCKET Socket) 00111 { 00112 DWORD ErrorCode; 00113 PWAH_HELPER_CONTEXT Context = HelperHandle; 00114 00115 /* Enter the prolog, make sure we're initialized */ 00116 ErrorCode = WS2HELP_PROLOG(); 00117 if (ErrorCode != ERROR_SUCCESS) return ErrorCode; 00118 00119 /* Validate the handle */ 00120 if (!(Context) || (Socket == INVALID_SOCKET) || !(Socket)) 00121 { 00122 /* Invalid handle and/or socket */ 00123 return ERROR_INVALID_PARAMETER; 00124 } 00125 00126 /* Just close the handle and return */ 00127 CloseHandle((HANDLE)Socket); 00128 return ERROR_SUCCESS; 00129 } 00130 00131 DWORD 00132 WINAPI 00133 WahCreateSocketHandle(IN HANDLE HelperHandle, 00134 OUT SOCKET *Socket) 00135 { 00136 DWORD ErrorCode; 00137 INT OpenType; 00138 DWORD Size = sizeof(OpenType); 00139 DWORD CreateOptions = 0; 00140 UNICODE_STRING Name; 00141 OBJECT_ATTRIBUTES ObjectAttributes; 00142 PFILE_FULL_EA_INFORMATION Ea; 00143 PWAH_EA_DATA EaData; 00144 CHAR EaBuffer[sizeof(*Ea) + sizeof(*EaData)]; 00145 NTSTATUS Status; 00146 IO_STATUS_BLOCK IoStatusBlock; 00147 PWAH_HELPER_CONTEXT Context = (PWAH_HELPER_CONTEXT)HelperHandle; 00148 00149 /* Enter the prolog, make sure we're initialized */ 00150 ErrorCode = WS2HELP_PROLOG(); 00151 if (ErrorCode != ERROR_SUCCESS) return ErrorCode; 00152 00153 /* Validate the handle and pointer */ 00154 if (!(Context) || !(Socket)) 00155 { 00156 /* Invalid handle and/or socket */ 00157 return ERROR_INVALID_PARAMETER; 00158 } 00159 00160 /* Set pointer to EA */ 00161 Ea = (PFILE_FULL_EA_INFORMATION)EaBuffer; 00162 00163 /* Get the open type to determine the create options */ 00164 if ((pGetSockOpt(INVALID_SOCKET, 00165 SOL_SOCKET, 00166 SO_OPENTYPE, 00167 (PCHAR)&OpenType, 00168 (INT FAR*)&Size) == ERROR_SUCCESS) && (OpenType)) 00169 { 00170 /* This is a sync open */ 00171 CreateOptions = FILE_SYNCHRONOUS_IO_NONALERT; 00172 } 00173 00174 /* Initialize the attributes for the driver */ 00175 RtlInitUnicodeString(&Name, L"\\Device\\WS2IFSL\\NifsSct"); 00176 InitializeObjectAttributes(&ObjectAttributes, 00177 &Name, 00178 0, 00179 NULL, 00180 NULL); 00181 00182 /* Set up the EA */ 00183 Ea->NextEntryOffset = 0; 00184 Ea->Flags = 0; 00185 Ea->EaNameLength = sizeof("NifsSct"); 00186 Ea->EaValueLength = sizeof(*EaData); 00187 RtlCopyMemory(Ea->EaName, "NifsSct", Ea->EaNameLength); 00188 00189 /* Get our EA data */ 00190 EaData = (PWAH_EA_DATA)(Ea + 1); 00191 00192 /* Write the EA Data */ 00193 EaData->FileHandle = Context->FileHandle; 00194 EaData->Context = NULL; 00195 00196 /* Call the driver */ 00197 Status = NtCreateFile((PHANDLE)Socket, 00198 FILE_ALL_ACCESS, 00199 &ObjectAttributes, 00200 &IoStatusBlock, 00201 NULL, 00202 FILE_ATTRIBUTE_NORMAL, 00203 0, 00204 FILE_OPEN_IF, 00205 CreateOptions, 00206 Ea, 00207 sizeof(*Ea) + sizeof(*EaData)); 00208 00209 /* Check for success */ 00210 if (NT_SUCCESS(Status)) 00211 { 00212 /* Write the socket handle */ 00213 EaData->Context =(HANDLE)*Socket; 00214 00215 /* Tell the driver about it */ 00216 if (DeviceIoControl((HANDLE)*Socket, 00217 IOCTL_WS2IFSL_SET_HANDLE, 00218 &EaData, 00219 sizeof(WSH_EA_DATA), 00220 NULL, 00221 0, 00222 &Size, 00223 NULL)) 00224 { 00225 /* Set success */ 00226 ErrorCode = NO_ERROR; 00227 } 00228 else 00229 { 00230 /* We failed. Get the error and close the socket */ 00231 ErrorCode = GetLastError(); 00232 CloseHandle((HANDLE)*Socket); 00233 *Socket = 0; 00234 } 00235 } 00236 else 00237 { 00238 /* Create file failed, conver error code */ 00239 ErrorCode = RtlNtStatusToDosError(Status); 00240 } 00241 00242 /* Return to caller */ 00243 return ErrorCode; 00244 } 00245 00246 INT 00247 WINAPI 00248 WahDisableNonIFSHandleSupport(VOID) 00249 { 00250 DWORD ErrorCode; 00251 SC_HANDLE ServiceMgrHandle, Ws2IfsHandle; 00252 00253 /* Enter the prolog, make sure we're initialized */ 00254 ErrorCode = WS2HELP_PROLOG(); 00255 if (ErrorCode != ERROR_SUCCESS) return ErrorCode; 00256 00257 /* Open the service DB */ 00258 ServiceMgrHandle = OpenSCManager(NULL, 00259 SERVICES_ACTIVE_DATABASE, 00260 SC_MANAGER_CREATE_SERVICE); 00261 if (!ServiceMgrHandle) return GetLastError(); 00262 00263 /* Open the service */ 00264 Ws2IfsHandle = OpenService(ServiceMgrHandle, "WS2IFSL", SERVICE_ALL_ACCESS); 00265 00266 /* Disable the servce */ 00267 ChangeServiceConfig(Ws2IfsHandle, 00268 SERVICE_NO_CHANGE, 00269 SERVICE_DISABLED, 00270 SERVICE_NO_CHANGE, 00271 NULL, 00272 NULL, 00273 NULL, 00274 NULL, 00275 NULL, 00276 NULL, 00277 NULL); 00278 00279 /* Close the handles and return */ 00280 CloseServiceHandle(ServiceMgrHandle); 00281 CloseServiceHandle(Ws2IfsHandle); 00282 return ERROR_SUCCESS; 00283 } 00284 00285 INT 00286 WINAPI 00287 WahEnableNonIFSHandleSupport(VOID) 00288 { 00289 return 0; 00290 } 00291 00292 DWORD 00293 WINAPI 00294 WahOpenHandleHelper(OUT PHANDLE HelperHandle) 00295 { 00296 DWORD ErrorCode; 00297 HINSTANCE hWs2_32; 00298 UNICODE_STRING Name; 00299 OBJECT_ATTRIBUTES ObjectAttributes; 00300 PFILE_FULL_EA_INFORMATION Ea; 00301 PWAH_EA_DATA2 EaData; 00302 CHAR EaBuffer[sizeof(*Ea) + sizeof(*EaData)]; 00303 NTSTATUS Status; 00304 IO_STATUS_BLOCK IoStatusBlock; 00305 DWORD Tid; 00306 PWAH_HELPER_CONTEXT Context; 00307 00308 /* Enter the prolog, make sure we're initialized */ 00309 ErrorCode = WS2HELP_PROLOG(); 00310 if (ErrorCode != ERROR_SUCCESS) return ErrorCode; 00311 00312 /* Validate the pointer */ 00313 if (!HelperHandle) 00314 { 00315 /* Invalid handle and/or socket */ 00316 return ERROR_INVALID_PARAMETER; 00317 } 00318 00319 /* Get ws2_32.dll's handle. We don't load it: it MUST be here */ 00320 hWs2_32 = GetModuleHandle ("WS2_32.DLL"); 00321 if (!hWs2_32) return WSASYSCALLFAILURE; 00322 00323 /* Dynamically load all its APIs */ 00324 if (!((pGetSockOpt = (LPFN_GETSOCKOPT)GetProcAddress(hWs2_32, "getsockopt"))) || 00325 !((pSelect = (LPFN_SELECT)GetProcAddress(hWs2_32, "select"))) || 00326 !((pWSACancelBlockingCall = (LPFN_WSACANCELBLOCKINGCALL)GetProcAddress(hWs2_32, "WSACancelBlockingCall"))) || 00327 !((pWSACleanup = (LPFN_WSACLEANUP)GetProcAddress(hWs2_32, "WSACleanup"))) || 00328 !((pWSAGetLastError = (LPFN_WSAGETLASTERROR)GetProcAddress(hWs2_32, "WSAGetLastError"))) || 00329 !((pWSASetBlockingHook = (LPFN_WSASETBLOCKINGHOOK)GetProcAddress(hWs2_32, "WSASetBlockingHook"))) || 00330 !((pWSARecv = (LPFN_WSARECV)GetProcAddress(hWs2_32, "WSARecv"))) || 00331 !((pWSASend = (LPFN_WSASEND)GetProcAddress(hWs2_32, "WSASend"))) || 00332 !((pWSASendTo = (LPFN_WSASENDTO)GetProcAddress(hWs2_32, "WSASendTo"))) || 00333 !((pWSAStartup = (LPFN_WSASTARTUP)GetProcAddress(hWs2_32, "WSAStartup"))) || 00334 !((pWSARecvFrom = (LPFN_WSARECVFROM)GetProcAddress(hWs2_32, "WSARecvFrom"))) || 00335 !((pWSAIoctl = (LPFN_WSAIOCTL)GetProcAddress(hWs2_32, "WSAIoctl")))) 00336 { 00337 /* Uh, guess we failed somewhere */ 00338 return WSASYSCALLFAILURE; 00339 } 00340 00341 /* Set pointer EA structure */ 00342 Ea = (PFILE_FULL_EA_INFORMATION)EaBuffer; 00343 00344 /* Create the helper context */ 00345 Context = HeapAlloc(GlobalHeap, 0, sizeof(WSH_HELPER_CONTEXT)); 00346 if (Context) 00347 { 00348 /* Create the special request thread */ 00349 Context->ThreadHandle = CreateThread(NULL, 00350 0, 00351 (PVOID)ApcThread, 00352 Context, 00353 CREATE_SUSPENDED, 00354 &Tid); 00355 if (Context->ThreadHandle) 00356 { 00357 /* Create the attributes for the driver open */ 00358 RtlInitUnicodeString(&Name, L"\\Device\\WS2IFSL\\NifsPvd"); 00359 InitializeObjectAttributes(&ObjectAttributes, 00360 &Name, 00361 0, 00362 NULL, 00363 NULL); 00364 00365 /* Setup the EA */ 00366 Ea->NextEntryOffset = 0; 00367 Ea->Flags = 0; 00368 Ea->EaNameLength = sizeof("NifsPvd"); 00369 Ea->EaValueLength = sizeof(*EaData); 00370 RtlCopyMemory(Ea->EaName, "NifsPvd", Ea->EaNameLength); 00371 00372 /* Get our EA data */ 00373 EaData = (PWAH_EA_DATA2)(Ea + 1); 00374 00375 /* Fill out the EA Data */ 00376 EaData->ThreadHandle = Context->ThreadHandle; 00377 EaData->RequestRoutine = DoSocketRequest; 00378 EaData->CancelRoutine = DoSocketCancel; 00379 EaData->ApcContext = Context; 00380 EaData->Reserved = 0; 00381 00382 /* Call the driver */ 00383 Status = NtCreateFile(&Context->FileHandle, 00384 FILE_ALL_ACCESS, 00385 &ObjectAttributes, 00386 &IoStatusBlock, 00387 NULL, 00388 FILE_ATTRIBUTE_NORMAL, 00389 0, 00390 FILE_OPEN_IF, 00391 0, 00392 Ea, 00393 sizeof(*Ea) + sizeof(*EaData)); 00394 00395 /* Check for success */ 00396 if (NT_SUCCESS(Status)) 00397 { 00398 /* Resume the thread and return a handle to the context */ 00399 ResumeThread(Context->ThreadHandle); 00400 *HelperHandle = (HANDLE)Context; 00401 return ERROR_SUCCESS; 00402 } 00403 else 00404 { 00405 /* Get the error code */ 00406 ErrorCode = RtlNtStatusToDosError(Status); 00407 } 00408 00409 /* We failed, mark us as such */ 00410 Context->FileHandle = NULL; 00411 ResumeThread(Context->ThreadHandle); 00412 } 00413 else 00414 { 00415 /* Get the error code */ 00416 ErrorCode = GetLastError(); 00417 } 00418 00419 /* If we got here, we failed, so free the context */ 00420 HeapFree(GlobalHeap, 0, Context); 00421 } 00422 else 00423 { 00424 /* Get the errror code */ 00425 ErrorCode = GetLastError(); 00426 } 00427 00428 /* Return to caller */ 00429 return ErrorCode; 00430 } 00431 00432 DWORD 00433 WINAPI 00434 WahCompleteRequest(IN HANDLE HelperHandle, 00435 IN SOCKET Socket, 00436 IN LPWSAOVERLAPPED lpOverlapped, 00437 IN DWORD ErrorCode, 00438 IN DWORD BytesTransferred) 00439 { 00440 UNREFERENCED_PARAMETER(HelperHandle); 00441 UNREFERENCED_PARAMETER(Socket); 00442 UNREFERENCED_PARAMETER(lpOverlapped); 00443 UNREFERENCED_PARAMETER(ErrorCode); 00444 UNREFERENCED_PARAMETER(BytesTransferred); 00445 return ERROR_SUCCESS; 00446 } 00447 00448 /* EOF */ Generated on Mon May 28 2012 04:24:06 for ReactOS by
1.7.6.1
|