diff --git a/base/services/dhcpcsvc/CMakeLists.txt b/base/services/dhcpcsvc/CMakeLists.txt index 1726d94bd09..41494771e53 100644 --- a/base/services/dhcpcsvc/CMakeLists.txt +++ b/base/services/dhcpcsvc/CMakeLists.txt @@ -1,5 +1,9 @@ -include_directories(include) +include_directories(include ${REACTOS_SOURCE_DIR}/sdk/include/reactos/idl) + +add_rpc_file(client ${REACTOS_SOURCE_DIR}/sdk/include/reactos/idl/dhcpcsvc.idl PREFIX_CLIENT Client_ PREFIX_SERVER Server_) +add_rpc_file(server ${REACTOS_SOURCE_DIR}/sdk/include/reactos/idl/dhcpcsvc.idl PREFIX_CLIENT Client_ PREFIX_SERVER Server_) + spec2def(dhcpcsvc.dll dhcpcsvc.spec ADD_IMPORTLIB) list(APPEND SOURCE @@ -11,13 +15,14 @@ list(APPEND SOURCE dhcp/dispatch.c dhcp/hash.c dhcp/options.c - dhcp/pipe.c dhcp/socket.c dhcp/tables.c dhcp/util.c dhcpcsvc.c) list(APPEND PCH_SKIP_SOURCE + ${CMAKE_CURRENT_BINARY_DIR}/dhcpcsvc_c.c + ${CMAKE_CURRENT_BINARY_DIR}/dhcpcsvc_s.c ${CMAKE_CURRENT_BINARY_DIR}/dhcpcsvc_stubs.c) add_library(dhcpcsvc MODULE @@ -26,8 +31,8 @@ add_library(dhcpcsvc MODULE dhcpcsvc.rc ${CMAKE_CURRENT_BINARY_DIR}/dhcpcsvc.def) -target_link_libraries(dhcpcsvc oldnames) set_module_type(dhcpcsvc win32dll) -add_importlibs(dhcpcsvc ws2_32 iphlpapi advapi32 msvcrt kernel32 ntdll) +target_link_libraries(dhcpcsvc oldnames ${PSEH_LIB}) +add_importlibs(dhcpcsvc ws2_32 rpcrt4 iphlpapi advapi32 msvcrt kernel32 ntdll) add_pch(dhcpcsvc include/rosdhcp.h "${PCH_SKIP_SOURCE}") add_cd_file(TARGET dhcpcsvc DESTINATION reactos/system32 FOR all) diff --git a/base/services/dhcpcsvc/dhcp/api.c b/base/services/dhcpcsvc/dhcp/api.c index 5ed64d3ac03..e294cb72798 100644 --- a/base/services/dhcpcsvc/dhcp/api.c +++ b/base/services/dhcpcsvc/dhcp/api.c @@ -31,32 +31,73 @@ VOID ApiFree() { DeleteCriticalSection( &ApiCriticalSection ); } +DWORD +WINAPI +RpcThreadRoutine( + LPVOID lpParameter) +{ + RPC_STATUS Status; + + Status = RpcServerUseProtseqEpW(L"ncacn_np", 20, L"\\pipe\\dhcpcsvc", NULL); + if (Status != RPC_S_OK) + { + DPRINT1("RpcServerUseProtseqEpW() failed (Status %lx)\n", Status); + return 0; + } + + Status = RpcServerRegisterIf(Server_dhcpcsvc_v0_0_s_ifspec, NULL, NULL); + if (Status != RPC_S_OK) + { + DPRINT1("RpcServerRegisterIf() failed (Status %lx)\n", Status); + return 0; + } + + Status = RpcServerListen(1, RPC_C_LISTEN_MAX_CALLS_DEFAULT, FALSE); + if (Status != RPC_S_OK) + { + DPRINT1("RpcServerListen() failed (Status %lx)\n", Status); + } + + return 0; +} + +HANDLE +InitRpc(VOID) +{ + return CreateThread( NULL, 0, RpcThreadRoutine, (LPVOID)NULL, 0, NULL); +} + +VOID +ShutdownRpc(VOID) +{ + RpcMgmtStopServerListening(NULL); +} + /* This represents the service portion of the DHCP client API */ +/* Function 0 */ DWORD -DSAcquireParams( - _In_ PipeSendFunc Send, - _In_ HANDLE CommPipe, - _Out_ COMM_DHCP_REQ *Req) +__stdcall +Server_AcquireParameters( + _In_ PDHCP_SERVER_NAME ServerName, + _In_ LPWSTR AdapterName) { - COMM_DHCP_REPLY Reply; PDHCP_ADAPTER Adapter; struct protocol* proto; + DWORD ret = ERROR_SUCCESS; - DPRINT1("DSAcquireParams()\n"); - - Reply.Reply = ERROR_SUCCESS; + DPRINT("Server_AcquireParameters()\n"); ApiLock(); - Adapter = AdapterFindName(Req->Body.AcquireParams.AdapterName); + Adapter = AdapterFindName(AdapterName); if (Adapter == NULL || Adapter->DhclientState.state == S_STATIC) { - Reply.Reply = ERROR_FILE_NOT_FOUND; + ret = ERROR_FILE_NOT_FOUND; goto done; } - DPRINT1("Adapter: %p\n", Adapter); + DPRINT("Adapter: %p\n", Adapter); proto = find_protocol_by_adapter(&Adapter->DhclientInfo); if (proto) @@ -75,34 +116,33 @@ DSAcquireParams( done: ApiUnlock(); - return Send(CommPipe, &Reply); + return ret; } +/* Function 1 */ DWORD -DSReleaseParams( - _In_ PipeSendFunc Send, - _In_ HANDLE CommPipe, - _Out_ COMM_DHCP_REQ *Req) +__stdcall +Server_ReleaseParameters( + _In_ PDHCP_SERVER_NAME ServerName, + _In_ LPWSTR AdapterName) { - COMM_DHCP_REPLY Reply; PDHCP_ADAPTER Adapter; struct protocol* proto; + DWORD ret = ERROR_SUCCESS; - DPRINT1("DSReleaseParams()\n"); - - Reply.Reply = ERROR_SUCCESS; + DPRINT("Server_ReleaseParameters()\n"); ApiLock(); - Adapter = AdapterFindName(Req->Body.AcquireParams.AdapterName); + Adapter = AdapterFindName(AdapterName); if (Adapter == NULL) { - Reply.Reply = ERROR_FILE_NOT_FOUND; + ret = ERROR_FILE_NOT_FOUND; goto done; } - DPRINT1("Adapter: %p\n", Adapter); + DPRINT("Adapter: %p\n", Adapter); if (Adapter->NteContext) { @@ -128,71 +168,98 @@ DSReleaseParams( done: ApiUnlock(); - return Send(CommPipe, &Reply); + return ret; } -DWORD DSQueryHWInfo( PipeSendFunc Send, HANDLE CommPipe, COMM_DHCP_REQ *Req ) { - COMM_DHCP_REPLY Reply; +/* Function 2 */ +DWORD +__stdcall +Server_QueryHWInfo( + _In_ PDHCP_SERVER_NAME ServerName, + _In_ DWORD AdapterIndex, + _Out_ PDWORD MediaType, + _Out_ PDWORD Mtu, + _Out_ PDWORD Speed) +{ PDHCP_ADAPTER Adapter; + DWORD ret = ERROR_SUCCESS; + + DPRINT("Server_QueryHWInfo()\n"); ApiLock(); - Adapter = AdapterFindIndex( Req->AdapterIndex ); - - Reply.Reply = Adapter ? 1 : 0; - - if (Adapter) { - Reply.QueryHWInfo.AdapterIndex = Req->AdapterIndex; - Reply.QueryHWInfo.MediaType = Adapter->IfMib.dwType; - Reply.QueryHWInfo.Mtu = Adapter->IfMib.dwMtu; - Reply.QueryHWInfo.Speed = Adapter->IfMib.dwSpeed; + Adapter = AdapterFindIndex(AdapterIndex); + if (Adapter == NULL) + { + ret = ERROR_FILE_NOT_FOUND; + goto done; } + DPRINT("Adapter: %p\n", Adapter); + + *MediaType = Adapter->IfMib.dwType; + *Mtu = Adapter->IfMib.dwMtu; + *Speed = Adapter->IfMib.dwSpeed; + +done: ApiUnlock(); - return Send(CommPipe, &Reply ); + return ret; } -DWORD DSStaticRefreshParams( PipeSendFunc Send, HANDLE CommPipe, COMM_DHCP_REQ *Req ) { - NTSTATUS Status; - COMM_DHCP_REPLY Reply; +/* Function 3 */ +DWORD +__stdcall +Server_StaticRefreshParams( + _In_ PDHCP_SERVER_NAME ServerName, + _In_ DWORD AdapterIndex, + _In_ DWORD Address, + _In_ DWORD Netmask) +{ PDHCP_ADAPTER Adapter; struct protocol* proto; + DWORD ret = ERROR_SUCCESS; + + DPRINT("Server_StaticRefreshParams()\n"); ApiLock(); - Adapter = AdapterFindIndex( Req->AdapterIndex ); - - Reply.Reply = Adapter ? 1 : 0; - - if( Adapter ) { - if (Adapter->NteContext) - { - DeleteIPAddress( Adapter->NteContext ); - Adapter->NteContext = 0; - } - if (Adapter->RouterMib.dwForwardNextHop) - { - DeleteIpForwardEntry( &Adapter->RouterMib ); - Adapter->RouterMib.dwForwardNextHop = 0; - } - - Adapter->DhclientState.state = S_STATIC; - proto = find_protocol_by_adapter( &Adapter->DhclientInfo ); - if (proto) - remove_protocol(proto); - Status = AddIPAddress( Req->Body.StaticRefreshParams.IPAddress, - Req->Body.StaticRefreshParams.Netmask, - Req->AdapterIndex, - &Adapter->NteContext, - &Adapter->NteInstance ); - Reply.Reply = NT_SUCCESS(Status); - - if (hAdapterStateChangedEvent != NULL) - SetEvent(hAdapterStateChangedEvent); + Adapter = AdapterFindIndex(AdapterIndex); + if (Adapter == NULL) + { + ret = ERROR_FILE_NOT_FOUND; + goto done; } + DPRINT("Adapter: %p\n", Adapter); + + if (Adapter->NteContext) + { + DeleteIPAddress(Adapter->NteContext); + Adapter->NteContext = 0; + } + if (Adapter->RouterMib.dwForwardNextHop) + { + DeleteIpForwardEntry(&Adapter->RouterMib); + Adapter->RouterMib.dwForwardNextHop = 0; + } + + Adapter->DhclientState.state = S_STATIC; + proto = find_protocol_by_adapter(&Adapter->DhclientInfo); + if (proto) + remove_protocol(proto); + + ret = AddIPAddress(Address, + Netmask, + AdapterIndex, + &Adapter->NteContext, + &Adapter->NteInstance); + + if (hAdapterStateChangedEvent != NULL) + SetEvent(hAdapterStateChangedEvent); + +done: ApiUnlock(); - return Send(CommPipe, &Reply ); + return ret; } diff --git a/base/services/dhcpcsvc/dhcp/pipe.c b/base/services/dhcpcsvc/dhcp/pipe.c deleted file mode 100644 index 795fe4f9434..00000000000 --- a/base/services/dhcpcsvc/dhcp/pipe.c +++ /dev/null @@ -1,419 +0,0 @@ -/* - * COPYRIGHT: See COPYING in the top level directory - * PROJECT: ReactOS kernel - * FILE: subsys/system/dhcp/pipe.c - * PURPOSE: DHCP client pipe - * PROGRAMMER: arty - */ - -#include - -#define NDEBUG -#include - -#define COMM_PIPE_OUTPUT_BUFFER sizeof(COMM_DHCP_REQ) -#define COMM_PIPE_INPUT_BUFFER sizeof(COMM_DHCP_REPLY) -#define COMM_PIPE_DEFAULT_TIMEOUT 1000 - -DWORD PipeSend( HANDLE CommPipe, COMM_DHCP_REPLY *Reply ) { - DWORD Written = 0; - OVERLAPPED Overlapped = {0}; - BOOL Success = - WriteFile( CommPipe, - Reply, - sizeof(*Reply), - &Written, - &Overlapped); - if (!Success) - { - WaitForSingleObject(CommPipe, INFINITE); - Success = GetOverlappedResult(CommPipe, - &Overlapped, - &Written, - TRUE); - } - - return Success ? Written : -1; -} - -/** - * @brief - * Creates a security descriptor for the DHCP pipe - * service. - * - * @param[out] SecurityDescriptor - * A pointer to an allocated security descriptor - * for the DHCP pipe. - * - * @return - * ERROR_SUCCESS is returned if the function has - * successfully created the descriptor otherwise - * a Win32 error code is returned. - * - * @remarks - * Both admins and local system are given full power - * over the DHCP pipe whereas authenticated users - * and network operators can only read over this pipe. - * They can also execute it. - */ -DWORD CreateDhcpPipeSecurity( PSECURITY_DESCRIPTOR *SecurityDescriptor ) { - DWORD ErrCode; - PACL Dacl; - ULONG DaclSize, RelSDSize = 0; - PSECURITY_DESCRIPTOR AbsSD = NULL, RelSD = NULL; - PSID AuthenticatedUsersSid = NULL, NetworkOpsSid = NULL, AdminsSid = NULL, SystemSid = NULL; - static SID_IDENTIFIER_AUTHORITY NtAuthority = {SECURITY_NT_AUTHORITY}; - - if (!AllocateAndInitializeSid(&NtAuthority, - 1, - SECURITY_AUTHENTICATED_USER_RID, - 0, 0, 0, 0, 0, 0, 0, - &AuthenticatedUsersSid)) - { - DPRINT1("CreateDhcpPipeSecurity(): Failed to create Authenticated Users SID (error code %d)\n", GetLastError()); - return GetLastError(); - } - - if (!AllocateAndInitializeSid(&NtAuthority, - 2, - SECURITY_BUILTIN_DOMAIN_RID, - DOMAIN_ALIAS_RID_NETWORK_CONFIGURATION_OPS, - 0, 0, 0, 0, 0, 0, - &NetworkOpsSid)) - { - DPRINT1("CreateDhcpPipeSecurity(): Failed to create Network Ops SID (error code %d)\n", GetLastError()); - ErrCode = GetLastError(); - goto Quit; - } - - if (!AllocateAndInitializeSid(&NtAuthority, - 2, - SECURITY_BUILTIN_DOMAIN_RID, - DOMAIN_ALIAS_RID_ADMINS, - 0, 0, 0, 0, 0, 0, - &AdminsSid)) - { - DPRINT1("CreateDhcpPipeSecurity(): Failed to create Admins SID (error code %d)\n", GetLastError()); - ErrCode = GetLastError(); - goto Quit; - } - - if (!AllocateAndInitializeSid(&NtAuthority, - 1, - SECURITY_LOCAL_SYSTEM_RID, - 0, 0, 0, 0, 0, 0, 0, - &SystemSid)) - { - DPRINT1("CreateDhcpPipeSecurity(): Failed to create Local System SID (error code %d)\n", GetLastError()); - ErrCode = GetLastError(); - goto Quit; - } - - AbsSD = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(SECURITY_DESCRIPTOR)); - if (!AbsSD) - { - DPRINT1("CreateDhcpPipeSecurity(): Failed to allocate absolute security descriptor!\n"); - ErrCode = ERROR_OUTOFMEMORY; - goto Quit; - } - - if (!InitializeSecurityDescriptor(AbsSD, SECURITY_DESCRIPTOR_REVISION)) - { - DPRINT1("CreateDhcpPipeSecurity(): Failed to initialize absolute security descriptor (error code %d)\n", GetLastError()); - ErrCode = GetLastError(); - goto Quit; - } - - DaclSize = sizeof(ACL) + - sizeof(ACCESS_ALLOWED_ACE) + GetLengthSid(AuthenticatedUsersSid) + - sizeof(ACCESS_ALLOWED_ACE) + GetLengthSid(NetworkOpsSid) + - sizeof(ACCESS_ALLOWED_ACE) + GetLengthSid(AdminsSid) + - sizeof(ACCESS_ALLOWED_ACE) + GetLengthSid(SystemSid); - - Dacl = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, DaclSize); - if (!Dacl) - { - DPRINT1("CreateDhcpPipeSecurity(): Failed to allocate DACL!\n"); - ErrCode = ERROR_OUTOFMEMORY; - goto Quit; - } - - if (!InitializeAcl(Dacl, DaclSize, ACL_REVISION)) - { - DPRINT1("CreateDhcpPipeSecurity(): Failed to initialize DACL (error code %d)\n", GetLastError()); - ErrCode = GetLastError(); - goto Quit; - } - - if (!AddAccessAllowedAce(Dacl, - ACL_REVISION, - GENERIC_READ | GENERIC_EXECUTE, - AuthenticatedUsersSid)) - { - DPRINT1("CreateDhcpPipeSecurity(): Failed to set up ACE for Authenticated Users SID (error code %d)\n", GetLastError()); - ErrCode = GetLastError(); - goto Quit; - } - - if (!AddAccessAllowedAce(Dacl, - ACL_REVISION, - GENERIC_READ | GENERIC_EXECUTE, - NetworkOpsSid)) - { - DPRINT1("CreateDhcpPipeSecurity(): Failed to set up ACE for Network Ops SID (error code %d)\n", GetLastError()); - ErrCode = GetLastError(); - goto Quit; - } - - if (!AddAccessAllowedAce(Dacl, - ACL_REVISION, - GENERIC_ALL, - AdminsSid)) - { - DPRINT1("CreateDhcpPipeSecurity(): Failed to set up ACE for Admins SID (error code %d)\n", GetLastError()); - ErrCode = GetLastError(); - goto Quit; - } - - if (!AddAccessAllowedAce(Dacl, - ACL_REVISION, - GENERIC_ALL, - SystemSid)) - { - DPRINT1("CreateDhcpPipeSecurity(): Failed to set up ACE for Local System SID (error code %d)\n", GetLastError()); - ErrCode = GetLastError(); - goto Quit; - } - - if (!SetSecurityDescriptorDacl(AbsSD, TRUE, Dacl, FALSE)) - { - DPRINT1("CreateDhcpPipeSecurity(): Failed to set up DACL to absolute security descriptor (error code %d)\n", GetLastError()); - ErrCode = GetLastError(); - goto Quit; - } - - if (!SetSecurityDescriptorOwner(AbsSD, AdminsSid, FALSE)) - { - DPRINT1("CreateDhcpPipeSecurity(): Failed to set up owner to absolute security descriptor (error code %d)\n", GetLastError()); - ErrCode = GetLastError(); - goto Quit; - } - - if (!SetSecurityDescriptorGroup(AbsSD, SystemSid, FALSE)) - { - DPRINT1("CreateDhcpPipeSecurity(): Failed to set up group to absolute security descriptor (error code %d)\n", GetLastError()); - ErrCode = GetLastError(); - goto Quit; - } - - if (!MakeSelfRelativeSD(AbsSD, NULL, &RelSDSize) && GetLastError() != ERROR_INSUFFICIENT_BUFFER) - { - DPRINT1("CreateDhcpPipeSecurity(): Unexpected error code (error code %d -- must be ERROR_INSUFFICIENT_BUFFER)\n", GetLastError()); - ErrCode = GetLastError(); - goto Quit; - } - - RelSD = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, RelSDSize); - if (RelSD == NULL) - { - DPRINT1("CreateDhcpPipeSecurity(): Failed to allocate relative SD!\n"); - ErrCode = ERROR_OUTOFMEMORY; - goto Quit; - } - - if (!MakeSelfRelativeSD(AbsSD, RelSD, &RelSDSize) && GetLastError() == ERROR_INSUFFICIENT_BUFFER) - { - DPRINT1("CreateDhcpPipeSecurity(): Failed to allocate relative SD, buffer too smal (expected size %lu)\n", RelSDSize); - ErrCode = ERROR_INSUFFICIENT_BUFFER; - goto Quit; - } - - *SecurityDescriptor = RelSD; - ErrCode = ERROR_SUCCESS; - -Quit: - if (ErrCode != ERROR_SUCCESS) - { - if (RelSD) - { - HeapFree(GetProcessHeap(), 0, RelSD); - } - } - - if (AuthenticatedUsersSid) - { - FreeSid(AuthenticatedUsersSid); - } - - if (NetworkOpsSid) - { - FreeSid(NetworkOpsSid); - } - - if (AdminsSid) - { - FreeSid(AdminsSid); - } - - if (SystemSid) - { - FreeSid(SystemSid); - } - - if (Dacl) - { - HeapFree(GetProcessHeap(), 0, Dacl); - } - - if (AbsSD) - { - HeapFree(GetProcessHeap(), 0, AbsSD); - } - - return ErrCode; -} - -DWORD WINAPI PipeThreadProc( LPVOID Parameter ) { - DWORD BytesRead; - COMM_DHCP_REQ Req; - COMM_DHCP_REPLY Reply; - BOOL Result, Connected; - HANDLE Events[2]; - HANDLE CommPipe; - OVERLAPPED Overlapped = {0}; - DWORD dwError; - SECURITY_ATTRIBUTES SecurityAttributes; - PSECURITY_DESCRIPTOR DhcpPipeSD = NULL; - - DPRINT("PipeThreadProc(%p)\n", Parameter); - - dwError = CreateDhcpPipeSecurity(&DhcpPipeSD); - if (dwError != ERROR_SUCCESS) - { - DbgPrint("DHCP: Could not create security descriptor for pipe\n"); - return FALSE; - } - - SecurityAttributes.nLength = sizeof(SECURITY_ATTRIBUTES); - SecurityAttributes.lpSecurityDescriptor = DhcpPipeSD; - SecurityAttributes.bInheritHandle = FALSE; - - CommPipe = CreateNamedPipeW - ( DHCP_PIPE_NAME, - PIPE_ACCESS_DUPLEX | FILE_FLAG_FIRST_PIPE_INSTANCE | FILE_FLAG_OVERLAPPED, - PIPE_TYPE_MESSAGE | PIPE_READMODE_MESSAGE | PIPE_WAIT, - 1, - COMM_PIPE_OUTPUT_BUFFER, - COMM_PIPE_INPUT_BUFFER, - COMM_PIPE_DEFAULT_TIMEOUT, - &SecurityAttributes ); - HeapFree(GetProcessHeap(), 0, DhcpPipeSD); - if (CommPipe == INVALID_HANDLE_VALUE) - { - DbgPrint("DHCP: Could not create named pipe\n"); - return FALSE; - } - - Events[0] = (HANDLE)Parameter; - Events[1] = CommPipe; - - while( TRUE ) - { - Connected = ConnectNamedPipe(CommPipe, &Overlapped); - if (!Connected) - { - dwError = GetLastError(); - if (dwError == ERROR_IO_PENDING) - { - dwError = WaitForMultipleObjects(2, Events, FALSE, INFINITE); - DPRINT("WaitForMultipleObjects() returned %lu\n", dwError); - if (dwError == WAIT_OBJECT_0 + 1) - { - Connected = GetOverlappedResult(CommPipe, - &Overlapped, - &BytesRead, - TRUE); - } - else if (dwError == WAIT_OBJECT_0) - { - CancelIo(CommPipe); - CloseHandle(CommPipe); - CommPipe = INVALID_HANDLE_VALUE; - break; - } - } - } - - if (!Connected) { - DbgPrint("DHCP: Could not connect named pipe\n"); - CloseHandle( CommPipe ); - CommPipe = INVALID_HANDLE_VALUE; - break; - } - - Result = ReadFile(CommPipe, &Req, sizeof(Req), &BytesRead, &Overlapped); - if (!Result) - { - dwError = GetLastError(); - if (dwError == ERROR_IO_PENDING) - { - dwError = WaitForMultipleObjects(2, Events, FALSE, INFINITE); - DPRINT("WaitForMultipleObjects() returned %lu\n", dwError); - if (dwError == WAIT_OBJECT_0 + 1) - { - Result = GetOverlappedResult(CommPipe, - &Overlapped, - &BytesRead, - TRUE); - } - else if (dwError == WAIT_OBJECT_0) - { - CancelIo(CommPipe); - DisconnectNamedPipe( CommPipe ); - CloseHandle(CommPipe); - CommPipe = INVALID_HANDLE_VALUE; - break; - } - } - } - - if( Result ) - { - switch( Req.Type ) - { - case DhcpReqAcquireParams: - DSAcquireParams(PipeSend, CommPipe, &Req); - break; - - case DhcpReqReleaseParams: - DSReleaseParams(PipeSend, CommPipe, &Req); - break; - - case DhcpReqQueryHWInfo: - DSQueryHWInfo(PipeSend, CommPipe, &Req); - break; - - case DhcpReqStaticRefreshParams: - DSStaticRefreshParams( PipeSend, CommPipe, &Req ); - break; - - default: - DPRINT1("Unrecognized request type %d\n", Req.Type); - ZeroMemory( &Reply, sizeof( COMM_DHCP_REPLY ) ); - Reply.Reply = 0; - PipeSend(CommPipe, &Reply ); - break; - } - } - DisconnectNamedPipe( CommPipe ); - } - - DPRINT("Pipe thread stopped!\n"); - - return TRUE; -} - -HANDLE PipeInit(HANDLE hStopEvent) -{ - return CreateThread( NULL, 0, PipeThreadProc, (LPVOID)hStopEvent, 0, NULL); -} diff --git a/base/services/dhcpcsvc/dhcpcsvc.c b/base/services/dhcpcsvc/dhcpcsvc.c index 55577b2586a..b2b0a16430f 100644 --- a/base/services/dhcpcsvc/dhcpcsvc.c +++ b/base/services/dhcpcsvc/dhcpcsvc.c @@ -19,59 +19,88 @@ SERVICE_STATUS ServiceStatus; HANDLE hStopEvent = NULL; HANDLE hAdapterStateChangedEvent = NULL; -static HANDLE PipeHandle = INVALID_HANDLE_VALUE; extern SOCKET DhcpSocket; -DWORD APIENTRY -DhcpCApiInitialize(LPDWORD Version) + +void __RPC_FAR * __RPC_USER MIDL_user_allocate(SIZE_T len) { - DWORD PipeMode; + return HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, len); +} - /* Wait for the pipe to be available */ - if (!WaitNamedPipeW(DHCP_PIPE_NAME, NMPWAIT_USE_DEFAULT_WAIT)) +void __RPC_USER MIDL_user_free(void __RPC_FAR * ptr) +{ + HeapFree(GetProcessHeap(), 0, ptr); +} + +handle_t __RPC_USER +PDHCP_SERVER_NAME_bind( + _In_ PDHCP_SERVER_NAME pszServerName) +{ + handle_t hBinding = NULL; + LPWSTR pszStringBinding; + RPC_STATUS status; + + DPRINT("PDHCP_SERVER_NAME_bind() called\n"); + + status = RpcStringBindingComposeW(NULL, + L"ncacn_np", + pszServerName, + L"\\pipe\\dhcpcsvc", + NULL, + &pszStringBinding); + if (status) { - /* No good, we failed */ - return GetLastError(); + DPRINT1("RpcStringBindingCompose returned 0x%x\n", status); + return NULL; } - /* It's available, let's try to open it */ - PipeHandle = CreateFileW(DHCP_PIPE_NAME, - GENERIC_READ | GENERIC_WRITE, - FILE_SHARE_READ | FILE_SHARE_WRITE, - NULL, - OPEN_EXISTING, - 0, - NULL); - - /* Check if we succeeded in opening the pipe */ - if (PipeHandle == INVALID_HANDLE_VALUE) + /* Set the binding handle that will be used to bind to the server. */ + status = RpcBindingFromStringBindingW(pszStringBinding, + &hBinding); + if (status) { - /* We didn't */ - return GetLastError(); + DPRINT1("RpcBindingFromStringBinding returned 0x%x\n", status); } - /* Change the pipe into message mode */ - PipeMode = PIPE_READMODE_MESSAGE; - if (!SetNamedPipeHandleState(PipeHandle, &PipeMode, NULL, NULL)) + status = RpcStringFreeW(&pszStringBinding); + if (status) { - /* Mode change failed */ - CloseHandle(PipeHandle); - PipeHandle = INVALID_HANDLE_VALUE; - return GetLastError(); + DPRINT1("RpcStringFree returned 0x%x\n", status); } - else + + return hBinding; +} + +void __RPC_USER +PDHCP_SERVER_NAME_unbind( + _In_ PDHCP_SERVER_NAME pszServerName, + _In_ handle_t hBinding) +{ + RPC_STATUS status; + + DPRINT("PDHCP_SERVER_NAME_unbind() called\n"); + + status = RpcBindingFree(&hBinding); + if (status) { - /* We're good to go */ - *Version = 2; - return NO_ERROR; + DPRINT1("RpcBindingFree returned 0x%x\n", status); } } -VOID APIENTRY + +DWORD +APIENTRY +DhcpCApiInitialize( + _Out_ LPDWORD Version) +{ + *Version = 2; + return NO_ERROR; +} + +VOID +APIENTRY DhcpCApiCleanup(VOID) { - CloseHandle(PipeHandle); - PipeHandle = INVALID_HANDLE_VALUE; } DWORD @@ -79,29 +108,21 @@ APIENTRY DhcpAcquireParameters( _In_ PWSTR AdapterName) { - COMM_DHCP_REQ Req; - COMM_DHCP_REPLY Reply; - DWORD BytesRead; - BOOL Result; + DWORD ret; - DPRINT1("DhcpAcquireParameters(%S)\n", AdapterName); + DPRINT("DhcpAcquireParameters(%S)\n", AdapterName); - ASSERT(PipeHandle != INVALID_HANDLE_VALUE); - - Req.Type = DhcpReqAcquireParams; - wcscpy(Req.Body.AcquireParams.AdapterName, AdapterName); - - Result = TransactNamedPipe(PipeHandle, - &Req, sizeof(Req), - &Reply, sizeof(Reply), - &BytesRead, NULL); - if (!Result) + RpcTryExcept { - /* Pipe transaction failed */ - return GetLastError(); + ret = Client_AcquireParameters(NULL, AdapterName); } + RpcExcept(EXCEPTION_EXECUTE_HANDLER) + { + ret = I_RpcMapWin32Status(RpcExceptionCode()); + } + RpcEndExcept; - return Reply.Reply; + return ret; } DWORD @@ -109,29 +130,21 @@ APIENTRY DhcpReleaseParameters( _In_ PWSTR AdapterName) { - COMM_DHCP_REQ Req; - COMM_DHCP_REPLY Reply; - DWORD BytesRead; - BOOL Result; + DWORD ret; - DPRINT1("DhcpReleaseParameters(%S)\n", AdapterName); + DPRINT("DhcpReleaseParameters(%S)\n", AdapterName); - ASSERT(PipeHandle != INVALID_HANDLE_VALUE); - - Req.Type = DhcpReqReleaseParams; - wcscpy(Req.Body.AcquireParams.AdapterName, AdapterName); - - Result = TransactNamedPipe(PipeHandle, - &Req, sizeof(Req), - &Reply, sizeof(Reply), - &BytesRead, NULL); - if (!Result) + RpcTryExcept { - /* Pipe transaction failed */ - return GetLastError(); + ret = Client_ReleaseParameters(NULL, AdapterName); } + RpcExcept(EXCEPTION_EXECUTE_HANDLER) + { + ret = I_RpcMapWin32Status(RpcExceptionCode()); + } + RpcEndExcept; - return Reply.Reply; + return ret; } DWORD @@ -167,63 +180,44 @@ DhcpQueryHWInfo(DWORD AdapterIndex, PDWORD Mtu, PDWORD Speed) { - COMM_DHCP_REQ Req; - COMM_DHCP_REPLY Reply; - DWORD BytesRead; - BOOL Result; + DWORD ret; - ASSERT(PipeHandle != INVALID_HANDLE_VALUE); + DPRINT("DhcpQueryHWInfo()\n"); - Req.Type = DhcpReqQueryHWInfo; - Req.AdapterIndex = AdapterIndex; - - Result = TransactNamedPipe(PipeHandle, - &Req, sizeof(Req), - &Reply, sizeof(Reply), - &BytesRead, NULL); - if (!Result) + RpcTryExcept { - /* Pipe transaction failed */ - return 0; + ret = Client_QueryHWInfo(NULL, AdapterIndex, MediaType, Mtu, Speed); } + RpcExcept(EXCEPTION_EXECUTE_HANDLER) + { + ret = I_RpcMapWin32Status(RpcExceptionCode()); + } + RpcEndExcept; - if (Reply.Reply == 0) - return 0; - - *MediaType = Reply.QueryHWInfo.MediaType; - *Mtu = Reply.QueryHWInfo.Mtu; - *Speed = Reply.QueryHWInfo.Speed; - return 1; + return (ret == ERROR_SUCCESS) ? 1 : 0; } -DWORD APIENTRY +DWORD +APIENTRY DhcpStaticRefreshParams(DWORD AdapterIndex, DWORD Address, DWORD Netmask) { - COMM_DHCP_REQ Req; - COMM_DHCP_REPLY Reply; - DWORD BytesRead; - BOOL Result; + DWORD ret; - ASSERT(PipeHandle != INVALID_HANDLE_VALUE); + DPRINT("DhcpStaticRefreshParams()\n"); - Req.Type = DhcpReqStaticRefreshParams; - Req.AdapterIndex = AdapterIndex; - Req.Body.StaticRefreshParams.IPAddress = Address; - Req.Body.StaticRefreshParams.Netmask = Netmask; - - Result = TransactNamedPipe(PipeHandle, - &Req, sizeof(Req), - &Reply, sizeof(Reply), - &BytesRead, NULL); - if (!Result) + RpcTryExcept { - /* Pipe transaction failed */ - return 0; + ret = Client_StaticRefreshParams(NULL, AdapterIndex, Address, Netmask); } + RpcExcept(EXCEPTION_EXECUTE_HANDLER) + { + ret = I_RpcMapWin32Status(RpcExceptionCode()); + } + RpcEndExcept; - return Reply.Reply; + return (ret == ERROR_SUCCESS) ? 1 : 0; } /*! @@ -378,7 +372,7 @@ ServiceMain(DWORD argc, LPWSTR* argv) UpdateServiceStatus(SERVICE_START_PENDING); - hPipeThread = PipeInit(hStopEvent); + hPipeThread = InitRpc(); if (hPipeThread == INVALID_HANDLE_VALUE) { DbgPrint("DHCPCSVC: PipeInit() failed!\n"); @@ -393,6 +387,7 @@ ServiceMain(DWORD argc, LPWSTR* argv) if (hDiscoveryThread == INVALID_HANDLE_VALUE) { DbgPrint("DHCPCSVC: StartAdapterDiscovery() failed!\n"); + ShutdownRpc(); stop_client(); CloseHandle(hAdapterStateChangedEvent); CloseHandle(hStopEvent); @@ -411,6 +406,7 @@ ServiceMain(DWORD argc, LPWSTR* argv) DH_DbgPrint(MID_TRACE,("DHCPCSVC: DHCP service is shutting down\n")); + ShutdownRpc(); stop_client(); DPRINT("Wait for pipe thread to close! %p\n", hPipeThread); diff --git a/base/services/dhcpcsvc/include/rosdhcp.h b/base/services/dhcpcsvc/include/rosdhcp.h index 7233e18bed9..162a06818a2 100644 --- a/base/services/dhcpcsvc/include/rosdhcp.h +++ b/base/services/dhcpcsvc/include/rosdhcp.h @@ -13,7 +13,9 @@ #define NTOS_MODE_USER #include #include -#include +#include +#include +#include #include "debug.h" @@ -76,8 +78,6 @@ typedef struct _DHCP_ADAPTER { unsigned char recv_buf[1]; } DHCP_ADAPTER, *PDHCP_ADAPTER; -typedef DWORD (*PipeSendFunc)(HANDLE CommPipe, COMM_DHCP_REPLY *Reply ); - #define random rand #define srandom srand @@ -93,16 +93,12 @@ extern PDHCP_ADAPTER AdapterFindIndex( unsigned int AdapterIndex ); extern PDHCP_ADAPTER AdapterFindName(const WCHAR *name); extern PDHCP_ADAPTER AdapterFindInfo( struct interface_info *info ); extern PDHCP_ADAPTER AdapterFindByHardwareAddress( u_int8_t haddr[16], u_int8_t hlen ); -extern HANDLE PipeInit(HANDLE hStopEvent); +extern HANDLE InitRpc(VOID); +extern VOID ShutdownRpc(VOID); extern VOID ApiInit(VOID); extern VOID ApiFree(VOID); extern VOID ApiLock(VOID); extern VOID ApiUnlock(VOID); -extern DWORD DSAcquireParams(PipeSendFunc Send, HANDLE CommPipe, COMM_DHCP_REQ *Req); -extern DWORD DSReleaseParams(PipeSendFunc Send, HANDLE CommPipe, COMM_DHCP_REQ *Req); -extern DWORD DSQueryHWInfo( PipeSendFunc Send, HANDLE CommPipe, COMM_DHCP_REQ *Req ); -extern DWORD DSStaticRefreshParams( PipeSendFunc Send, HANDLE CommPipe, COMM_DHCP_REQ *Req ); -extern DWORD DSGetAdapterInfo( PipeSendFunc Send, HANDLE CommPipe, COMM_DHCP_REQ *Req ); extern int inet_aton(const char *s, struct in_addr *addr); int warn( char *format, ... ); diff --git a/base/services/dhcpcsvc/include/rosdhcp_pipe.h b/base/services/dhcpcsvc/include/rosdhcp_pipe.h deleted file mode 100644 index 7b41417655d..00000000000 --- a/base/services/dhcpcsvc/include/rosdhcp_pipe.h +++ /dev/null @@ -1,50 +0,0 @@ -#ifndef ROSDHCP_PIPE_H -#define ROSDHCP_PIPE_H - -enum { - DhcpReqAcquireParams, - DhcpReqReleaseParams, - DhcpReqQueryHWInfo, - DhcpReqStaticRefreshParams, -}; - -typedef struct _COMM_DHCP_REQ { - UINT Type; - DWORD AdapterIndex; - union - { - struct - { - WCHAR AdapterName[45]; - } AcquireParams; - struct { - BOOL Inserted; - } PnpEvent; - struct { - LPWSTR AdapterName; - DHCPCAPI_PARAMS_ARRAY Params; - } RegisterParamChange; - struct { - LPWSTR AdapterName; - LPWSTR RequestId; - } RequestParams, UndoRequestParams; - struct { - DWORD IPAddress; - DWORD Netmask; - } StaticRefreshParams; - } Body; -} COMM_DHCP_REQ; - -typedef union _COMM_DHCP_REPLY { - DWORD Reply; - struct { - DWORD AdapterIndex; - DWORD MediaType; - DWORD Mtu; - DWORD Speed; - } QueryHWInfo; -} COMM_DHCP_REPLY; - -#define DHCP_PIPE_NAME L"\\\\.\\pipe\\dhcpclient" - -#endif/*ROSDHCP_PIPE_H*/ diff --git a/sdk/include/reactos/idl/dhcpcsvc.idl b/sdk/include/reactos/idl/dhcpcsvc.idl new file mode 100644 index 00000000000..5bbdef30f39 --- /dev/null +++ b/sdk/include/reactos/idl/dhcpcsvc.idl @@ -0,0 +1,55 @@ +/* + * DHCP Client service interface definition + */ + +#include + +typedef [handle] wchar_t *PDHCP_SERVER_NAME; + +[ + uuid(6BFFD098-A112-3610-9833-012892020162), + version(0.0), + pointer_default(unique), +#ifdef __midl + ms_union, +#endif + endpoint("ncacn_np:[\\pipe\\dhcpcsvc]") +#ifndef __midl + ,explicit_handle +#endif +] +interface dhcpcsvc +{ + /* Function 0 */ + DWORD + __stdcall + AcquireParameters( + [in, string, unique] PDHCP_SERVER_NAME ServerName, + [in, string] LPWSTR AdapterName); + + /* Function 1 */ + DWORD + __stdcall + ReleaseParameters( + [in, string, unique] PDHCP_SERVER_NAME ServerName, + [in, string] LPWSTR AdapterName); + + /* Function 2 */ + DWORD + __stdcall + QueryHWInfo( + [in, string, unique] PDHCP_SERVER_NAME ServerName, + [in] DWORD AdapterIndex, + [out] PDWORD MediaType, + [out] PDWORD Mtu, + [out] PDWORD Speed); + + /* Function 3 */ + DWORD + __stdcall + StaticRefreshParams( + [in, string, unique] PDHCP_SERVER_NAME ServerName, + [in] DWORD AdapterIndex, + [in] DWORD Address, + [in] DWORD Netmask); +}