CodeGuru Home VC++ / MFC / C++ .NET / C# Visual Basic VB Forums Developer.com
Results 1 to 3 of 3
  1. #1
    Join Date
    Feb 2009
    Posts
    252

    [RESOLVED] Writing to a named pipe coming from a service (session 0) without admin rights

    Greetings

    I'm trying to write to a named pipe created by a service, as we all know the session 0 isolation implemented in vista and forward makes this task a bit complicated.

    well at this point i managed to make almost all to work but my real problem comes when i try to write on the named pipe from my GUI application with no administrator rights

    If i run the GUI application with admin rights it works 100% but, I don't need that application to require the user admin rights and for security reasons i rather to leave it without admin...

    so i started my research and i found that there is a way to achieve this by calling CreateNamedPipe() with a low integrity security attributes...

    well it was kind a pain in the *** to implement but i finally made it, the problem is that it gets worse than passing null security attributes, it works with admin rights with NULL security attributes, but when i pass the low integrity security attributes it gives "access denied" even when using admin rights, so i guess im passing the wrong security attributes but to be honest i have no idea how to manually create the security descriptor string.


    this is the code:

    Service (session0) SERVER

    Code:
            DWORD WINAPI PipeThreadRSVS(void* pParameter){
    	LPTSTR _PIPE_NAME = "\\\\.\\pipe\\RSVHPipeIn";
    	bool Break=false;
    	char Received_Buffer[BlockSize+16];
    	DWORD BytesRead = 0;
    
    
    
    	//DYNAMIC CALL
           ConvertStringSecurityDescriptorToSecurityDescriptorT DConvertStringSecurityDescriptorToSecurityDescriptor;
    
    	HMODULE hAdvapi32=LoadLibrary("Advapi32.dll");
    
    	DConvertStringSecurityDescriptorToSecurityDescriptor=(ConvertStringSecurityDescriptorToSecurityDescriptorT)GetProcAddress(hAdvapi32, "ConvertStringSecurityDescriptorToSecurityDescriptorA");
    
    
        //
    
        //SECURIRY DECRIPTOR
        #define LOW_INTEGRITY_SDDL_SACL       "S:(ML;;NW;;;LW)"
        PSECURITY_DESCRIPTOR pSD;
        DConvertStringSecurityDescriptorToSecurityDescriptor(LOW_INTEGRITY_SDDL_SACL,1,&pSD,NULL);
    
        SECURITY_ATTRIBUTES  sa; 
        sa.nLength = sizeof(sa);   
        sa.lpSecurityDescriptor = pSD;
        sa.bInheritHandle = TRUE; 
    
    
    
            //hPIPEInRSVS = CreateNamedPipe(_PIPE_NAME,PIPE_ACCESS_INBOUND,PIPE_TYPE_MESSAGE |PIPE_READMODE_MESSAGE | PIPE_WAIT,PIPE_UNLIMITED_INSTANCES,1024,1024,10000,&sa);
    
    	hPIPEInRSVS = CreateNamedPipe(_PIPE_NAME,PIPE_ACCESS_INBOUND,PIPE_TYPE_MESSAGE |PIPE_READMODE_MESSAGE | PIPE_WAIT,PIPE_UNLIMITED_INSTANCES,1024,1024,10000,NULL);
    
    
    	if ( hPIPEInRSVS != INVALID_HANDLE_VALUE ){
    		//OVERLAPPED *Overlapped;
    
    		int Connected = 0;
    		Connected = ConnectNamedPipe(hPIPEInRSVS, NULL);
    		while(!Break){
    
    			if ( Connected == 1 ){
    				BOOL bRead = ReadFile(hPIPEInRSVS, Received_Buffer, BlockSize+16, &BytesRead, NULL ); 
    
    				if (bRead != 0){
    					Received_Buffer[7]=0;
    					PipeRSV* IncPck=(PipeRSV*)&Received_Buffer;
    					if(strncmp(IncPck->Sig,"EndPCOm",7)==0){//Detenemos la comunicacion
    					   Break=true;
    					}
    					PipeMessagesRSVS(IncPck->Sig,IncPck->Data,IncPck->PckSize,IncPck->BlockPos);
    				  //FlushFileBuffers(hPIPE); 
    					
    				}else{
    				    Fncs.Loguear("ReadFile: Failed Server PipeIn");
                        Break=true;
    				}
    			}else{
    				Fncs.Loguear("ConnectedNamePipe() Has been Disconected");
    				Break=true;
    			}
    		}//while
    	}else{
    		Fncs.Loguear("SERVER FAILED ON CreateNamedPipe()");
    	}//Luego del Break desconectamos y cerramos el handle
    
    	Fncs.Loguear("Disconecting... Server PipeIn");
        DisconnectNamedPipe(hPIPEInRSVS); 
    	CloseHandle(hPIPEInRSVS);
    	return 0;
    
    }

    CLIENT WITH NO ADMIN RIGHTS
    Code:
    BOOL SendPipeMsgRSVC(char* Sig,char* Message,DWORD BlockPos,int Len){
    	if(hPIPEOutRSVC==INVALID_HANDLE_VALUE){
    		Fncs.Loguear("CLIENT: The Pipe Hasnt been started!");
    		RsvStopFlag=true;
    		return FALSE;
    	}
    
    	BOOL bWrite = false;
    	DWORD BYTESWRITTEN = 0;
    
    	char buffer[BlockSize+16];
    	PipeRSV* SendPck=(PipeRSV*)&buffer;
    	//copy string into buffer and fill with terminating null characters
    	memcpy(SendPck->Sig,Sig,8);
    	SendPck->BlockPos=BlockPos;
        SendPck->PckSize=(DWORD)Len;
    	memcpy(SendPck->Data,Message,Len);
    	
    	if ( hPIPEOutRSVC != INVALID_HANDLE_VALUE ){
    		//Write char array "buffer" to the pipe handle held in hPIPE
    		bWrite = WriteFile( hPIPEOutRSVC, buffer, sizeof(buffer), &BYTESWRITTEN, NULL );
    
    		if ( bWrite == FALSE ){
    			Fncs.Loguear("WriteFile() Error:",GetLastError());
    			RsvStopFlag=true; //we exit every thread
    		}
    		return bWrite;
    	}else{
    		Fncs.Loguear("CREATEFILE FAILED!",GetLastError());;
    		RsvStopFlag=true;
    		CloseHandle(hPIPEOutRSVC);
    		return FALSE;
    	}
    
    
    }
    
    
    BOOL StartPipeRSVC(){
    	LPCTSTR _PIPE_NAME = "\\\\.\\pipe\\RSVHPipeIn";
    	hPIPEOutRSVC = CreateFile(_PIPE_NAME, GENERIC_WRITE,0, NULL, OPEN_EXISTING,0, NULL);
    	if(hPIPEOutRSVC==INVALID_HANDLE_VALUE){
    					
    		    char B[80];
    			sprintf(B, "Client:Pipe Coulnt Be Started: %d", GetLastError());
    			OutputDebugString(B);
    
    		Fncs.Loguear("Client:Pipe Coulnt Be Started",GetLastError());
    		RsvStopFlag=true;
    		return FALSE;
    	}else{
            return TRUE;
    	}
    Thx in advance
    Last edited by Alphadan; December 9th, 2014 at 11:08 AM.

  2. #2
    Join Date
    Nov 2000
    Location
    Voronezh, Russia
    Posts
    6,620

    Re: Writing to a named pipe coming from a service (session 0) without admin rights

    Your service application may create the proper pipe with explicit all-access security descriptor.

    Code:
       PSECURITY_DESCRIPTOR psd = NULL;
       BYTE  sd[SECURITY_DESCRIPTOR_MIN_LENGTH];
       psd = (PSECURITY_DESCRIPTOR)sd;
       InitializeSecurityDescriptor(psd, SECURITY_DESCRIPTOR_REVISION);
       SetSecurityDescriptorDacl(psd, TRUE, (PACL)NULL, FALSE);
       SECURITY_ATTRIBUTES sa = {sizeof(sa), psd, FALSE};
    Sample for reading from service attached.
    Attached Files Attached Files
    Last edited by Igor Vartanov; December 10th, 2014 at 12:45 AM.
    Best regards,
    Igor

  3. #3
    Join Date
    Feb 2009
    Posts
    252

    Re: [RESOLVED] Writing to a named pipe coming from a service (session 0) without admi

    Thx a lot Igor your solution was very accurate and easy to implement, added reputation for you again thx alot!!!

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  





Click Here to Expand Forum to Full Width

Featured