Exemplo n.º 1
0
/*
 * @implemented
 */
NTSTATUS
NTAPI
NtListenPort(IN HANDLE PortHandle,
             OUT PPORT_MESSAGE ConnectMessage)
{
    NTSTATUS Status;
    PAGED_CODE();
    LPCTRACE(LPC_LISTEN_DEBUG, "Handle: %lx\n", PortHandle);

    /* Wait forever for a connection request. */
    for (;;)
    {
        /* Do the wait */
        Status = NtReplyWaitReceivePort(PortHandle,
                                        NULL,
                                        NULL,
                                        ConnectMessage);

        /* Accept only LPC_CONNECTION_REQUEST requests. */
        if ((Status != STATUS_SUCCESS) ||
            (LpcpGetMessageType(ConnectMessage) == LPC_CONNECTION_REQUEST))
        {
            /* Break out */
            break;
        }
    }

    /* Return status */
    return Status;
}
Exemplo n.º 2
0
VOID
SepServerGetNextMessage( VOID )

{

    //
    // Wait for the next message to come in...
    //

    Status = NtReplyWaitReceivePort(
                 EarPort,
                 NULL,
                 NULL,
                 &RequestMessage
                 ); SEASSERT_SUCCESS(Status);

    RequestCount += 1;

    return;
}
Exemplo n.º 3
0
NTSTATUS
NtListenPort (
    __in HANDLE PortHandle,
    __out PPORT_MESSAGE ConnectionRequest
    )

/*++

Routine Description:

    A server thread can listen for connection requests from client threads
    using the NtReplyWaitReceivePort service and looking for an
    LPC_CONNECTION_REQUEST message type.

    This call will loop, calling the NtReplyWaitReceivePort service, and
    return when it sees a message of type LPC_CONNECTION_REQUEST

Arguments:

    PortHandle - Specifies the connection port to listen for connection
        requests to.

    ConnectionRequest - Pointer to a structure that describes the
        connection request the client is making:

Return Value:

    NTSTATUS - An appropriate status value

--*/

{
    NTSTATUS Status;

    PAGED_CODE();

    //
    //  Keep on looping until we get a connection request on the lpc port
    //

    while (TRUE) {

        Status = NtReplyWaitReceivePort( PortHandle,
                                         NULL,
                                         NULL,
                                         ConnectionRequest );

        //
        //  We'll return from this procedure if ever we get back non success
        //  or the message is a connection request.  We still need to protect
        //  the testing of ConnectionRequest because it is a user supplied
        //  buffer.
        //

        try {

            if ((Status != STATUS_SUCCESS) ||
                ((ConnectionRequest->u2.s2.Type & ~LPC_KERNELMODE_MESSAGE) == LPC_CONNECTION_REQUEST)) {

                break;
            }

        } except( EXCEPTION_EXECUTE_HANDLER ) {

            Status = GetExceptionCode();

            break;
        }
    }

    //
    //  And return to our caller
    //

    return Status;
}
Exemplo n.º 4
0
/*++
 * @name CsrSbApiRequestThread
 *
 * The CsrSbApiRequestThread routine handles incoming messages or connection
 * requests on the SM API LPC Port.
 *
 * @param Parameter
 *        System-default user-defined parameter. Unused.
 *
 * @return The thread exit code, if the thread is terminated.
 *
 * @remarks Before listening on the port, the routine will first attempt
 *          to connect to the user subsystem.
 *
 *--*/
VOID
NTAPI
CsrSbApiRequestThread(IN PVOID Parameter)
{
    NTSTATUS Status;
    SB_API_MSG ReceiveMsg;
    PSB_API_MSG ReplyMsg = NULL;
    PVOID PortContext;
    ULONG MessageType;

    /* Start the loop */
    while (TRUE)
    {
        /* Wait for a message to come in */
        Status = NtReplyWaitReceivePort(CsrSbApiPort,
                                        &PortContext,
                                        &ReplyMsg->h,
                                        &ReceiveMsg.h);

        /* Check if we didn't get success */
        if (Status != STATUS_SUCCESS)
        {
            /* If we only got a warning, keep going */
            if (NT_SUCCESS(Status)) continue;

            /* We failed big time, so start out fresh */
            ReplyMsg = NULL;
            DPRINT1("CSRSS: ReceivePort failed - Status == %X\n", Status);
            continue;
        }

        /* Save the message type */
        MessageType = ReceiveMsg.h.u2.s2.Type;

        /* Check if this is a connection request */
        if (MessageType == LPC_CONNECTION_REQUEST)
        {
            /* Handle connection request */
            CsrSbApiHandleConnectionRequest(&ReceiveMsg);

            /* Start over */
            ReplyMsg = NULL;
            continue;
        }

        /* Check if the port died */
        if (MessageType == LPC_PORT_CLOSED)
        {
            /* Close the handle if we have one */
            if (PortContext) NtClose((HANDLE)PortContext);

            /* Client died, start over */
            ReplyMsg = NULL;
            continue;
        }
        else if (MessageType == LPC_CLIENT_DIED)
        {
            /* Client died, start over */
            ReplyMsg = NULL;
            continue;
        }

        /*
         * It's an API Message, check if it's within limits. If it's not, the
         * NT Behaviour is to set this to the Maximum API.
         */
        if (ReceiveMsg.ApiNumber > SbpMaxApiNumber)
        {
            ReceiveMsg.ApiNumber = SbpMaxApiNumber;
            DPRINT1("CSRSS: %lx is invalid Sb ApiNumber\n", ReceiveMsg.ApiNumber);
         }

        /* Reuse the message */
        ReplyMsg = &ReceiveMsg;

        /* Make sure that the message is supported */
        if (ReceiveMsg.ApiNumber < SbpMaxApiNumber)
        {
            /* Call the API */
            if (!CsrServerSbApiDispatch[ReceiveMsg.ApiNumber](&ReceiveMsg))
            {
                /* It failed, so return nothing */
                ReplyMsg = NULL;
            }
        }
        else
        {
            /* We don't support this API Number */
            ReplyMsg->ReturnValue = STATUS_NOT_IMPLEMENTED;
        }
    }
}
Exemplo n.º 5
0
NTSTATUS
SmpApiLoop (
    IN PVOID ThreadParameter
    )

/*++

Routine Description:

    This is the main Session Manager API Loop. It
    services session manager API requests.

Arguments:

    ThreadParameter - Supplies a handle to the API port used
        to receive session manager API requests.

Return Value:

    None.

--*/

{
    PSMAPIMSG SmApiReplyMsg;
    SMMESSAGE_SIZE MsgBuf;

    PSMAPIMSG SmApiMsg;
    NTSTATUS Status;
    HANDLE ConnectionPort;
    PSMP_CLIENT_CONTEXT ClientContext;
    PSMPKNOWNSUBSYS KnownSubSys;


    ConnectionPort = (HANDLE) ThreadParameter;

    SmApiMsg = (PSMAPIMSG)&MsgBuf;
    SmApiReplyMsg = NULL;
    try {
        for(;;) {

            Status = NtReplyWaitReceivePort(
                        ConnectionPort,
                        (PVOID *) &ClientContext,
                        (PPORT_MESSAGE) SmApiReplyMsg,
                        (PPORT_MESSAGE) SmApiMsg
                        );
            if ( !NT_SUCCESS(Status) ) {
                SmApiReplyMsg = NULL;
                continue;
            } else if ( SmApiMsg->h.u2.s2.Type == LPC_CONNECTION_REQUEST ) {
                SmpHandleConnectionRequest( ConnectionPort,
                                            (PSBAPIMSG) SmApiMsg
                                          );
                SmApiReplyMsg = NULL;
            } else if ( SmApiMsg->h.u2.s2.Type == LPC_DEBUG_EVENT ) {
                ASSERT(SmpDbgSsLoaded);
                DbgSsHandleKmApiMsg((PDBGKM_APIMSG)SmApiMsg,NULL);
                SmApiReplyMsg = NULL;
            } else if ( SmApiMsg->h.u2.s2.Type == LPC_PORT_CLOSED ) {
                SmApiReplyMsg = NULL;
            } else {
                KnownSubSys = ClientContext->KnownSubSys;

                SmApiMsg->ReturnedStatus = STATUS_PENDING;

#if DBG && 0
                if (SmApiMsg->ApiNumber >= SmMaxApiNumber ) {
                    SmApiMsg->ApiNumber = SmMaxApiNumber;
                }
                KdPrint(( "SMSS: %s Api Request received from %lx.%lx\n",
                          SmpApiName[ SmApiMsg->ApiNumber ],
                          SmApiMsg->h.ClientId.UniqueProcess,
                          SmApiMsg->h.ClientId.UniqueThread
                       ));
#endif // DBG

                if (SmApiMsg->ApiNumber >= SmMaxApiNumber ) {

                    Status = STATUS_NOT_IMPLEMENTED;

                } else {

                    switch (SmApiMsg->ApiNumber) {
                        case SmExecPgmApi :
                            Status = (SmpApiDispatch[SmApiMsg->ApiNumber])(
                                          SmApiMsg,
                                          ClientContext,
                                          ConnectionPort);
                            break;

                        case SmLoadDeferedSubsystemApi :
                            Status = (SmpApiDispatch[SmApiMsg->ApiNumber])(
                                          SmApiMsg,
                                          ClientContext,
                                          ConnectionPort);
                            break;


                        case SmCreateForeignSessionApi :
                        case SmSessionCompleteApi :
                        case SmTerminateForeignSessionApi :
                            if (!KnownSubSys) {
                                Status = STATUS_INVALID_PARAMETER;
                            } else {

                                Status =
                                    (SmpApiDispatch[SmApiMsg->ApiNumber])(
                                         SmApiMsg,
                                         ClientContext,
                                         ConnectionPort);
                            }
                            break;

                    }

                }

                SmApiMsg->ReturnedStatus = Status;
                SmApiReplyMsg = SmApiMsg;
            }
        }
    } except (DbgpUnhandledExceptionFilter( GetExceptionInformation() )) {
        ;
    }

    //
    // Make the compiler happy
    //

    return STATUS_UNSUCCESSFUL;
}
Exemplo n.º 6
0
int security_reference_monitor_t::run()
{
    const int maxlen = 0x100;
    //dprintf("starting kthread %p p = %p\n", this, process);
    current = static_cast<thread_t*>( this );
    //dprintf("current->process = %p\n", current->process);
    object_attributes_t rm_oa( (PCWSTR) L"\\SeRmCommandPort" );
    HANDLE port = 0, client = 0;
    NTSTATUS r = NtCreatePort( &port, &rm_oa, 0x100, 0x100, 0 );
    if (r == STATUS_THREAD_IS_TERMINATING)
        return 0;
    if (r < STATUS_SUCCESS)
        die("NtCreatePort(SeRmCommandPort) failed r = %08lx\n", r);

    BYTE buf[maxlen];
    LPC_MESSAGE *req = (LPC_MESSAGE*) buf;
    r = NtListenPort( port, req );
    if (r == STATUS_THREAD_IS_TERMINATING)
        return 0;
    if (r < STATUS_SUCCESS)
        die("NtListenPort(SeRmCommandPort) failed r = %08lx\n", r);

    HANDLE conn_port = 0;
    r = NtAcceptConnectPort( &conn_port, 0, req, TRUE, NULL, NULL );
    if (r == STATUS_THREAD_IS_TERMINATING)
        return 0;
    if (r < STATUS_SUCCESS)
        die("NtAcceptConnectPort(SeRmCommandPort) failed r = %08lx\n", r);

    r = NtCompleteConnectPort( conn_port );
    if (r == STATUS_THREAD_IS_TERMINATING)
        return 0;
    if (r < STATUS_SUCCESS)
        die("NtCompleteConnectPort(SeRmCommandPort) failed r = %08lx\n", r);

    unicode_string_t lsa;
    lsa.copy( (PCWSTR) L"\\SeLsaCommandPort" );

    SECURITY_QUALITY_OF_SERVICE qos;
    qos.Length = sizeof(qos);
    qos.ImpersonationLevel = SecurityAnonymous;
    qos.ContextTrackingMode = SECURITY_DYNAMIC_TRACKING;
    qos.EffectiveOnly = TRUE;

    r = NtConnectPort( &client, &lsa, &qos, NULL, NULL, NULL, NULL, NULL );
    if (r == STATUS_THREAD_IS_TERMINATING)
        return 0;
    if (r < STATUS_SUCCESS)
        die("NtConnectPort(SeLsaCommandPort) failed r = %08lx\n", r);

    while (!terminated)
    {
        ULONG client_handle;

        r = NtReplyWaitReceivePort( port, &client_handle, 0, req );
        if (r == STATUS_THREAD_IS_TERMINATING)
            return 0;

        if (r < STATUS_SUCCESS)
            die("NtReplyWaitReceivePort(SeRmCommandPort) failed r = %08lx\n", r);

        dprintf("got message %ld\n", req->MessageId );

        // send something back...
        r = NtReplyPort( port, req );
        if (r == STATUS_THREAD_IS_TERMINATING)
            return 0;

        if (r < STATUS_SUCCESS)
            die("NtReplyPort(SeRmCommandPort) failed r = %08lx\n", r);
    }

    dprintf("done\n");
    return 0;
}
Exemplo n.º 7
0
ULONG
NTAPI
SmpApiLoop(IN PVOID Parameter)
{
    HANDLE SmApiPort = (HANDLE)Parameter;
    NTSTATUS Status;
    PSMP_CLIENT_CONTEXT ClientContext;
    PSM_API_MSG ReplyMsg = NULL;
    SM_API_MSG RequestMsg;
    PROCESS_BASIC_INFORMATION ProcessInformation;
    LARGE_INTEGER Timeout;

    /* Increase the number of API threads for throttling code for later */
    _InterlockedExchangeAdd(&SmTotalApiThreads, 1);

    /* Mark us critical */
    RtlSetThreadIsCritical(TRUE, NULL, TRUE);

    /* Set the PID of the SM process itself for later checking */
    NtQueryInformationProcess(NtCurrentProcess(),
                              ProcessBasicInformation,
                              &ProcessInformation,
                              sizeof(ProcessInformation),
                              NULL);
    SmUniqueProcessId = (HANDLE)ProcessInformation.UniqueProcessId;

    /* Now process incoming messages */
    while (TRUE)
    {
        /* Begin waiting on a request */
        Status = NtReplyWaitReceivePort(SmApiPort,
                                        (PVOID*)&ClientContext,
                                        &ReplyMsg->h,
                                        &RequestMsg.h);
        if (Status == STATUS_NO_MEMORY)
        {
            /* Ran out of memory, so do a little timeout and try again */
            if (ReplyMsg) DPRINT1("SMSS: Failed to reply to calling thread, retrying.\n");
            Timeout.QuadPart = -50000000;
            NtDelayExecution(FALSE, &Timeout);
            continue;
        }

        /* Check what kind of request we received */
        switch (RequestMsg.h.u2.s2.Type)
        {
            /* A new connection */
            case LPC_CONNECTION_REQUEST:
                /* Create the right structures for it */
                SmpHandleConnectionRequest(SmApiPort, (PSB_API_MSG)&RequestMsg);
                ReplyMsg =  NULL;
                break;

            /* A closed connection */
            case LPC_PORT_CLOSED:
                /* Destroy any state we had for this client */
                DPRINT1("Port closed\n");
                //if (ClientContext) SmpPushDeferredClientContext(ClientContext);
                ReplyMsg = NULL;
                break;

            /* An actual API message */
            default:
                if (!ClientContext)
                {
                    ReplyMsg = NULL;
                    break;
                }

                RequestMsg.ReturnValue = STATUS_PENDING;

                /* Check if the API is valid */
                if (RequestMsg.ApiNumber >= SmpMaxApiNumber)
                {
                    /* It isn't, fail */
                    DPRINT1("Invalid API: %lx\n", RequestMsg.ApiNumber);
                    Status = STATUS_NOT_IMPLEMENTED;
                }
                else if ((RequestMsg.ApiNumber <= SmpTerminateForeignSessionApi) &&
                         !(ClientContext->Subsystem))
                {
                    /* It's valid, but doesn't have a subsystem with it */
                    DPRINT1("Invalid session API\n");
                    Status = STATUS_INVALID_PARAMETER;
                }
                else
                {
                    /* It's totally okay, so call the dispatcher for it */
                    Status = SmpApiDispatch[RequestMsg.ApiNumber](&RequestMsg,
                                                                  ClientContext,
                                                                  SmApiPort);
                }

                /* Write the result valud and return the message back */
                RequestMsg.ReturnValue = Status;
                ReplyMsg = &RequestMsg;
                break;
        }
    }
    return STATUS_SUCCESS;
}
Exemplo n.º 8
0
Arquivo: api.c Projeto: GYGit/reactos
/**********************************************************************
 *	ApiPortListener/1
 *
 * DESCRIPTION
 *	The thread to process messages from the \POSIX+\ApiPort
 *	LPC port. Mostly used by PSXDLL.DLL.
 */
VOID STDCALL
ApiPortListener (PVOID pArg)
{
    ULONG            ulIndex = (ULONG) pArg;
    NTSTATUS         Status;
    LPC_TYPE         RequestType;
    ULONG            PortIdentifier;
    PSX_MAX_MESSAGE  Request;
    PPSX_MAX_MESSAGE Reply = NULL;
    BOOL             NullReply = FALSE;

    debug_print (L"PSXSS: ->%s pArg=%d", __FUNCTION__, ulIndex);

    while (TRUE)
    {
        Reply = NULL;
        NullReply = FALSE;
        while (!NullReply)
        {
            Status = NtReplyWaitReceivePort (
                        Server.Port[ulIndex].hObject,
                        0,
                        (PLPC_MESSAGE) Reply,
                        (PLPC_MESSAGE) & Request
                        );
            if (!NT_SUCCESS(Status))
            {
                break;
            }
            RequestType = PORT_MESSAGE_TYPE(Request);
            switch (RequestType)
            {
            case LPC_CONNECTION_REQUEST:
                ProcessConnectionRequest ((PLPC_MAX_MESSAGE) & Request);
                NullReply = TRUE;
                continue;
            case LPC_CLIENT_DIED:
            case LPC_PORT_CLOSED:
            case LPC_DEBUG_EVENT:
            case LPC_ERROR_EVENT:
            case LPC_EXCEPTION:
                NullReply = TRUE;
                continue;
            default:
                if (RequestType != LPC_REQUEST)
                {
                    NullReply = TRUE;
                    continue;
                }
            }
            Reply = & Request;
            Reply->PsxHeader.Status = ProcessRequest (& Request);
            NullReply = FALSE;
        }
        if ((STATUS_INVALID_HANDLE == Status) ||
            (STATUS_OBJECT_TYPE_MISMATCH == Status))
        {
            break;
        }
    }
#ifdef __PSXSS_ON_W32__
    TerminateThread(GetCurrentThread(),Status);
#else
    NtTerminateThread(NtCurrentThread(),Status);
#endif
}
Exemplo n.º 9
0
NTSTATUS AcceptLpcConnect(PLPC_PORT LpcPort, BOOL AcceptConnection, BYTE *reply, WORD replyLength)
{
    NTSTATUS    status;
    LPC_MESSAGE reqMsg, repMsg;
    PSERVER_LPC_PORT   serverPort;
    HANDLE      hPort = INVALID_HANDLE_VALUE;
    PHANDLE     phPort = &hPort;
    BOOL        stopFlag = FALSE;
 
    log("Wait for connection...");
    serverPort = (PSERVER_LPC_PORT) LpcPort;
    
    while (!stopFlag) {
        status = NtReplyWaitReceivePort(
            LpcPort->hPort,
            (PVOID *) &phPort,
            NULL,
            (PLPC_MESSAGE_HEADER) &reqMsg
            );

        log("status: %x\n", status);
        log("Message type: %x\n", reqMsg.header.MessageType);
        switch (reqMsg.header.MessageType) {
        case LPC_CONNECTION_REQUEST:
            status = NtAcceptConnectPort(
                &hPort,
                NULL,
                (PLPC_MESSAGE_HEADER) &reqMsg,
                AcceptConnection,
                NULL,
                NULL
                );

            log("NtAcceptConnectPort: %x\n", status);
            status = NtCompleteConnectPort(hPort);
            log("NtCompleteConnectPort: %x\n", status);
            break;
        case LPC_REQUEST:
        case LPC_DATAGRAM:
            memset(&repMsg, 0, sizeof(repMsg));
            memcpy(&(repMsg.header), &(reqMsg.header), sizeof(repMsg.header));
            memcpy(repMsg.data, reply, replyLength);
            repMsg.header.DataLength = replyLength;
            repMsg.header.TotalLength = replyLength + sizeof(repMsg.header);

            log("SERVER: request: %s\n", reqMsg.data);
            log("SERVER: reply: %s\n", repMsg.data);
            
            status = NtReplyPort(hPort, (PLPC_MESSAGE_HEADER) &repMsg);
            log("NtReplyPort: %x\n", status);
            status = NtCompleteConnectPort(hPort);
            //log("NtCompleteConnectPort: %x\n", status);
            stopFlag = TRUE;
            break;
        case LPC_PORT_CLOSED:
            log("LPC_PORT_CLOSED\n");
            break;
        default:
            break;
        };

    }
    return status;
}
Exemplo n.º 10
0
Arquivo: srm.c Projeto: GYGit/reactos
static
DWORD
WINAPI
LsapRmServerThread(
    PVOID StartContext)
{
    LSAP_RM_API_MESSAGE Message;
    PPORT_MESSAGE ReplyMessage;
    REMOTE_PORT_VIEW RemotePortView;
    HANDLE MessagePort, DummyPortHandle;
    NTSTATUS Status;

    /* Initialize the port message */
    Message.Header.u1.s1.TotalLength = sizeof(Message);
    Message.Header.u1.s1.DataLength = 0;

    /* Listen on the LSA command port */
    Status = NtListenPort(SeLsaCommandPort, &Message.Header);
    if (!NT_SUCCESS(Status))
    {
        ERR("LsapRmServerThread - Port Listen failed 0x%lx\n", Status);
        return Status;
    }

    /* Setup the Port View Structure */
    RemotePortView.Length = sizeof(REMOTE_PORT_VIEW);
    RemotePortView.ViewSize = 0;
    RemotePortView.ViewBase = NULL;

    /* Accept the connection */
    Status = NtAcceptConnectPort(&MessagePort,
                                 0,
                                 &Message.Header,
                                 TRUE,
                                 NULL,
                                 &RemotePortView);
    if (!NT_SUCCESS(Status))
    {
        ERR("LsapRmServerThread - Port Accept Connect failed 0x%lx\n", Status);
        return Status;
    }

    /* Complete the connection */
    Status = NtCompleteConnectPort(MessagePort);
    if (!NT_SUCCESS(Status))
    {
        ERR("LsapRmServerThread - Port Complete Connect failed 0x%lx\n", Status);
        return Status;
    }

    /* No reply yet */
    ReplyMessage = NULL;

    /* Start looping */
    while (TRUE)
    {
        /* Wait for a message */
        Status = NtReplyWaitReceivePort(MessagePort,
                                        NULL,
                                        ReplyMessage,
                                        &Message.Header);
        if (!NT_SUCCESS(Status))
        {
            ERR("LsapRmServerThread - Failed to get message: 0x%lx", Status);
            ReplyMessage = NULL;
            continue;
        }

        /* Check if this is a connection request */
        if (Message.Header.u2.s2.Type == LPC_CONNECTION_REQUEST)
        {
            /* Reject connection request */
            NtAcceptConnectPort(&DummyPortHandle,
                                NULL,
                                &Message.Header,
                                FALSE,
                                NULL,
                                NULL);

            /* Start over */
            ReplyMessage = NULL;
            continue;
        }

        /* Check if this is an actual request */
        if (Message.Header.u2.s2.Type == LPC_REQUEST)
        {
            ReplyMessage = &Message.Header;

            switch (Message.ApiNumber)
            {
                case LsapAdtWriteLogApi:
                    LsapAdtWriteLog(&Message);
                    break;

                case LsapAsyncApi:
                    LsapAsync(&Message);
                    break;

                case LsapComponentTestApi:
                    LsapComponentTest(&Message);
                    break;

                default:
                    ERR("LsapRmServerThread - invalid API number: 0x%lx\n",
                        Message.ApiNumber);
                    ReplyMessage = NULL;
            }

            continue;
        }

        ERR("LsapRmServerThread - unexpected message type: 0x%lx\n",
            Message.Header.u2.s2.Type);

        /* Start over */
        ReplyMessage = NULL;
    }
}
Exemplo n.º 11
0
NTSTATUS PhSvcApiRequestThreadStart(
    __in PVOID Parameter
    )
{
    NTSTATUS status;
    PHSVC_THREAD_CONTEXT threadContext;
    HANDLE portHandle;
    PVOID portContext;
    PHSVC_API_MSG receiveMessage;
    PPHSVC_API_MSG replyMessage;
    CSHORT messageType;
    PPHSVC_CLIENT client;

    threadContext.CurrentClient = NULL;
    threadContext.OldClient = NULL;

    TlsSetValue(PhSvcApiThreadContextTlsIndex, &threadContext);

    portHandle = PhSvcApiPortHandle;
    replyMessage = NULL;

    while (TRUE)
    {
        status = NtReplyWaitReceivePort(
            portHandle,
            &portContext,
            (PPORT_MESSAGE)replyMessage,
            (PPORT_MESSAGE)&receiveMessage
            );

        portHandle = PhSvcApiPortHandle;
        replyMessage = NULL;

        if (!NT_SUCCESS(status))
        {
            // Client probably died.
            continue;
        }

        messageType = receiveMessage.h.u2.s2.Type;

        if (messageType == LPC_CONNECTION_REQUEST)
        {
            PhSvcHandleConnectionRequest(&receiveMessage);
            continue;
        }

        if (!portContext)
            continue;

        client = (PPHSVC_CLIENT)portContext;
        threadContext.CurrentClient = client;

        if (messageType == LPC_REQUEST)
        {
            PhSvcDispatchApiCall(client, &receiveMessage, &replyMessage, &portHandle);
        }
        else if (messageType == LPC_PORT_CLOSED)
        {
            PhDereferenceObject(client);

            if (_InterlockedDecrement(&PhSvcApiNumberOfClients) == 0)
            {
                NtSetEvent(PhSvcTimeoutStandbyEventHandle, NULL);
            }
        }

        assert(!threadContext.OldClient);
    }
}
Exemplo n.º 12
0
UdbgTest1()
{
    NTSTATUS st;
    HANDLE ExitThread, SpinThread, DebugProcess;
    CLIENT_ID ExitClientId, SpinClientId;
    DBGKM_APIMSG m;
    PDBGKM_CREATE_THREAD CreateThreadArgs;
    PDBGKM_CREATE_PROCESS CreateProcessArgs;
    PDBGKM_EXIT_THREAD ExitThreadArgs;
    PDBGKM_EXIT_PROCESS ExitProcessArgs;
    ULONG Psp;

    DbgPrint("UdbgTest1: (1)...\n");

        //
        // Verify that a process can be created with a debug
        // port.
        //

        st = NtCreateProcess(
                &DebugProcess,
                PROCESS_ALL_ACCESS,
                NULL,
                NtCurrentProcess(),
                FALSE,
                NULL,
                DebugPort,
                NULL
                );
        ASSERT(NT_SUCCESS(st));

        st = RtlCreateUserThread(
                DebugProcess,
                NULL,
                TRUE,
                0L,
                0L,
                0L,
                ThreadThatExits,
                (PVOID) STATUS_ABANDONED,
                &ExitThread,
                &ExitClientId
                );
        ASSERT(NT_SUCCESS(st));

        st = RtlCreateUserThread(
                DebugProcess,
                NULL,
                TRUE,
                0L,
                0L,
                0L,
                ThreadThatSpins,
                NULL,
                &SpinThread,
                &SpinClientId
                );
        ASSERT(NT_SUCCESS(st));

    DbgPrint("UdbgTest1: (2)...\n");

        //
        // Verify that CreateProcess Messages Arrive, and that
        // they are correct
        //

        st = NtResumeThread(SpinThread,NULL);
        ASSERT(NT_SUCCESS(st));

        st = NtReplyWaitReceivePort(
                DebugPort,
                NULL,
                NULL,
                (PPORT_MESSAGE)&m
                );
        ASSERT(NT_SUCCESS(st));
        ASSERT(m.ApiNumber == DbgKmCreateProcessApi);

        CreateThreadArgs = &m.u.CreateProcess.InitialThread;
        CreateProcessArgs = &m.u.CreateProcess;
        ASSERT( CreateThreadArgs->SubSystemKey == 0 && CreateThreadArgs->StartAddress == (PVOID)ThreadThatSpins );
        ASSERT( CreateProcessArgs->SubSystemKey == 0);

    DbgPrint("UdbgTest1: (3)...\n");

        //
        // Verify that other threads in the process are properly suspended
        //

        st = NtSuspendThread(ExitThread,&Psp);
        ASSERT(NT_SUCCESS(st) && Psp == 2);

        st = NtResumeThread(ExitThread,&Psp);
        ASSERT(NT_SUCCESS(st) && Psp == 3);

        st = NtReplyPort(DebugPort,(PPORT_MESSAGE)&m);
        ASSERT(NT_SUCCESS(st));


    DbgPrint("UdbgTest1: (4)...\n");

        //
        // Verify that CreateThread Messages Arrive, and that
        // they are correct
        //

        st = NtResumeThread(ExitThread,&Psp);
        ASSERT(NT_SUCCESS(st));

        st = NtReplyWaitReceivePort(
                DebugPort,
                NULL,
                NULL,
                (PPORT_MESSAGE)&m
                );
        ASSERT(NT_SUCCESS(st));
        ASSERT(m.ApiNumber == DbgKmCreateThreadApi);

        CreateThreadArgs = &m.u.CreateThread;
        ASSERT( CreateThreadArgs->SubSystemKey == 0 && CreateThreadArgs->StartAddress == (PVOID)ThreadThatExits );

        st = NtReplyPort(DebugPort,(PPORT_MESSAGE)&m);
        ASSERT(NT_SUCCESS(st));

    DbgPrint("UdbgTest1: (5)...\n");

        //
        // Verify that ExitThread Messages Arrive, and that
        // they are correct
        //

        st = NtReplyWaitReceivePort(
                DebugPort,
                NULL,
                NULL,
                (PPORT_MESSAGE)&m
                );
        ASSERT(NT_SUCCESS(st));
        ASSERT(m.ApiNumber == DbgKmExitThreadApi);

        ExitThreadArgs = &m.u.ExitThread;
        ASSERT( ExitThreadArgs->ExitStatus == STATUS_ABANDONED );

        st = NtReplyPort(DebugPort,(PPORT_MESSAGE)&m);
        ASSERT(NT_SUCCESS(st));

        st = NtWaitForSingleObject(ExitThread,FALSE,NULL);
        ASSERT(NT_SUCCESS(st));

    DbgPrint("UdbgTest1: (6)...\n");

        //
        // Verify that ExitThread Messages Arrive, and that
        // they are correct
        //

        st = NtTerminateProcess(DebugProcess,STATUS_REPARSE);
        ASSERT(NT_SUCCESS(st));

        st = NtReplyWaitReceivePort(
                DebugPort,
                NULL,
                NULL,
                (PPORT_MESSAGE)&m
                );
        ASSERT(NT_SUCCESS(st));
        ASSERT(m.ApiNumber == DbgKmExitThreadApi);

        ExitThreadArgs = &m.u.ExitThread;
        ASSERT( ExitThreadArgs->ExitStatus == STATUS_REPARSE );

        st = NtReplyPort(DebugPort,(PPORT_MESSAGE)&m);
        ASSERT(NT_SUCCESS(st));

    DbgPrint("UdbgTest1: (7)...\n");

        //
        // Verify that ExitProcess Messages Arrive, and that
        // they are correct
        //

        st = NtReplyWaitReceivePort(
                DebugPort,
                NULL,
                NULL,
                (PPORT_MESSAGE)&m
                );
        ASSERT(NT_SUCCESS(st));
        ASSERT(m.ApiNumber == DbgKmExitProcessApi);

        ExitProcessArgs = &m.u.ExitProcess;
        ASSERT( ExitProcessArgs->ExitStatus == STATUS_REPARSE );

        st = NtReplyPort(DebugPort,(PPORT_MESSAGE)&m);
        ASSERT(NT_SUCCESS(st));


        st = NtWaitForSingleObject(ExitThread,FALSE,NULL);
        ASSERT(NT_SUCCESS(st));

        st = NtWaitForSingleObject(DebugProcess,FALSE,NULL);
        ASSERT(NT_SUCCESS(st));

    NtClose(ExitThread);
    NtClose(SpinThread);
    NtClose(DebugProcess);

    DbgPrint("UdbgTest1: END OF TEST ***\n");

}
Exemplo n.º 13
0
UdbgTest2()
{
    NTSTATUS st;
    HANDLE ExceptionThread, DebugProcess;
    DBGKM_APIMSG m;
    PDBGKM_CREATE_THREAD CreateThreadArgs;
    PDBGKM_CREATE_PROCESS CreateProcessArgs;
    PDBGKM_EXIT_THREAD ExitThreadArgs;
    PDBGKM_EXIT_PROCESS ExitProcessArgs;
    PDBGKM_EXCEPTION ExceptionArgs;
    ULONG Psp;

    DbgPrint("UdbgTest2: (1)...\n");

        //
        // Verify that a process can be created with a debug
        // port.
        //

        st = NtCreateProcess(
                &DebugProcess,
                PROCESS_ALL_ACCESS,
                NULL,
                NtCurrentProcess(),
                FALSE,
                NULL,
                DebugPort,
                NULL
                );
        ASSERT(NT_SUCCESS(st));

        st = RtlCreateUserThread(
                DebugProcess,
                NULL,
                TRUE,
                0L,
                0L,
                0L,
                ThreadThatExcepts,
                (PVOID) STATUS_ABANDONED,
                &ExceptionThread,
                NULL
                );
        ASSERT(NT_SUCCESS(st));

    DbgPrint("UdbgTest2: (2)...\n");

        //
        // Verify that CreateThread Messages Arrive, and that
        // they are correct
        //

        st = NtResumeThread(ExceptionThread,NULL);
        ASSERT(NT_SUCCESS(st));

        st = NtReplyWaitReceivePort(
                DebugPort,
                NULL,
                NULL,
                (PPORT_MESSAGE)&m
                );
        ASSERT(NT_SUCCESS(st));
        ASSERT(m.ApiNumber == DbgKmCreateProcessApi);

        CreateThreadArgs = &m.u.CreateProcess.InitialThread;
        CreateProcessArgs = &m.u.CreateProcess;
        ASSERT( CreateThreadArgs->SubSystemKey == 0 && CreateThreadArgs->StartAddress == (PVOID)ThreadThatExcepts );
        ASSERT( CreateProcessArgs->SubSystemKey == 0);

        st = NtReplyPort(DebugPort,(PPORT_MESSAGE)&m);
        ASSERT(NT_SUCCESS(st));

    DbgPrint("UdbgTest2: (3)...\n");

        //
        // Verify that First Chance Exception Messages Arrive, and that
        // they are correct
        //

        st = NtReplyWaitReceivePort(
                DebugPort,
                NULL,
                NULL,
                (PPORT_MESSAGE)&m
                );
        ASSERT(NT_SUCCESS(st));
        ASSERT(m.ApiNumber == DbgKmExceptionApi);

        ExceptionArgs = &m.u.Exception;
        ASSERT( ExceptionArgs->FirstChance == TRUE );

        m.ReturnedStatus = DBG_EXCEPTION_NOT_HANDLED;

        st = NtReplyPort(DebugPort,(PPORT_MESSAGE)&m);
        ASSERT(NT_SUCCESS(st));

    DbgPrint("UdbgTest2: (4)...\n");

        //
        // Verify that First Chance Exception Messages Arrive, and that
        // they are correct
        //

        st = NtReplyWaitReceivePort(
                DebugPort,
                NULL,
                NULL,
                (PPORT_MESSAGE)&m
                );
        ASSERT(NT_SUCCESS(st));
        ASSERT(m.ApiNumber == DbgKmExceptionApi);

        ExceptionArgs = &m.u.Exception;
        ASSERT( ExceptionArgs->FirstChance == FALSE );

        m.ReturnedStatus = DBG_EXCEPTION_HANDLED;
skip4:
        st = NtTerminateProcess(DebugProcess,STATUS_REPARSE);
        ASSERT(NT_SUCCESS(st));

        st = NtReplyPort(DebugPort,(PPORT_MESSAGE)&m);
        ASSERT(NT_SUCCESS(st));

        st = NtReplyWaitReceivePort(
                DebugPort,
                NULL,
                NULL,
                (PPORT_MESSAGE)&m
                );
        ASSERT(NT_SUCCESS(st));
        ASSERT(m.ApiNumber == DbgKmExitThreadApi);

        ExitThreadArgs = &m.u.ExitThread;
        ASSERT( ExitThreadArgs->ExitStatus == STATUS_REPARSE );

        st = NtReplyPort(DebugPort,(PPORT_MESSAGE)&m);
        ASSERT(NT_SUCCESS(st));

    DbgPrint("UdbgTest2: (5)...\n");

        //
        // Verify that ExitProcess Messages Arrive, and that
        // they are correct
        //

        st = NtReplyWaitReceivePort(
                DebugPort,
                NULL,
                NULL,
                (PPORT_MESSAGE)&m
                );
        ASSERT(NT_SUCCESS(st));
        ASSERT(m.ApiNumber == DbgKmExitProcessApi);

        ExitProcessArgs = &m.u.ExitProcess;
        ASSERT( ExitProcessArgs->ExitStatus == STATUS_REPARSE );

        st = NtReplyPort(DebugPort,(PPORT_MESSAGE)&m);
        ASSERT(NT_SUCCESS(st));


        st = NtWaitForSingleObject(ExceptionThread,FALSE,NULL);
        ASSERT(NT_SUCCESS(st));

        st = NtWaitForSingleObject(DebugProcess,FALSE,NULL);
        ASSERT(NT_SUCCESS(st));

    NtClose(ExceptionThread);
    NtClose(DebugProcess);

    DbgPrint("UdbgTest2: END OF TEST ***\n");
}
Exemplo n.º 14
0
/*++
 * @name CsrApiRequestThread
 *
 * The CsrApiRequestThread routine handles incoming messages or connection
 * requests on the CSR API LPC Port.
 *
 * @param Parameter
 *        System-default user-defined parameter. Unused.
 *
 * @return The thread exit code, if the thread is terminated.
 *
 * @remarks Before listening on the port, the routine will first attempt
 *          to connect to the user subsystem.
 *
 *--*/
NTSTATUS
NTAPI
CsrApiRequestThread(IN PVOID Parameter)
{
    PTEB Teb = NtCurrentTeb();
    LARGE_INTEGER TimeOut;
    PCSR_THREAD CurrentThread, CsrThread;
    NTSTATUS Status;
    CSR_REPLY_CODE ReplyCode;
    PCSR_API_MESSAGE ReplyMsg;
    CSR_API_MESSAGE ReceiveMsg;
    PCSR_PROCESS CsrProcess;
    PHARDERROR_MSG HardErrorMsg;
    PVOID PortContext;
    PCSR_SERVER_DLL ServerDll;
    PCLIENT_DIED_MSG ClientDiedMsg;
    PDBGKM_MSG DebugMessage;
    ULONG ServerId, ApiId, MessageType, i;
    HANDLE ReplyPort;

    /* Setup LPC loop port and message */
    ReplyMsg = NULL;
    ReplyPort = CsrApiPort;

    /* Connect to user32 */
    while (!CsrConnectToUser())
    {
        /* Set up the timeout for the connect (30 seconds) */
        TimeOut.QuadPart = -30 * 1000 * 1000 * 10;

        /* Keep trying until we get a response */
        Teb->Win32ClientInfo[0] = 0;
        NtDelayExecution(FALSE, &TimeOut);
    }

    /* Get our thread */
    CurrentThread = Teb->CsrClientThread;

    /* If we got an event... */
    if (Parameter)
    {
        /* Set it, to let stuff waiting on us load */
        Status = NtSetEvent((HANDLE)Parameter, NULL);
        ASSERT(NT_SUCCESS(Status));

        /* Increase the Thread Counts */
        InterlockedIncrementUL(&CsrpStaticThreadCount);
        InterlockedIncrementUL(&CsrpDynamicThreadTotal);
    }

    /* Now start the loop */
    while (TRUE)
    {
        /* Make sure the real CID is set */
        Teb->RealClientId = Teb->ClientId;

        /* Debug check */
        if (Teb->CountOfOwnedCriticalSections)
        {
            DPRINT1("CSRSRV: FATAL ERROR. CsrThread is Idle while holding %lu critical sections\n",
                    Teb->CountOfOwnedCriticalSections);
            DPRINT1("CSRSRV: Last Receive Message %lx ReplyMessage %lx\n",
                    &ReceiveMsg, ReplyMsg);
            DbgBreakPoint();
        }

        /* Wait for a message to come through */
        Status = NtReplyWaitReceivePort(ReplyPort,
                                        &PortContext,
                                        &ReplyMsg->Header,
                                        &ReceiveMsg.Header);

        /* Check if we didn't get success */
        if (Status != STATUS_SUCCESS)
        {
            /* Was it a failure or another success code? */
            if (!NT_SUCCESS(Status))
            {
                /* Check for specific status cases */
                if ((Status != STATUS_INVALID_CID) &&
                    (Status != STATUS_UNSUCCESSFUL) &&
                    ((Status == STATUS_INVALID_HANDLE) || (ReplyPort == CsrApiPort)))
                {
                    /* Notify the debugger */
                    DPRINT1("CSRSS: ReceivePort failed - Status == %X\n", Status);
                    DPRINT1("CSRSS: ReplyPortHandle %lx CsrApiPort %lx\n", ReplyPort, CsrApiPort);
                }

                /* We failed big time, so start out fresh */
                ReplyMsg = NULL;
                ReplyPort = CsrApiPort;
                continue;
            }
            else
            {
                /* A strange "success" code, just try again */
                DPRINT1("NtReplyWaitReceivePort returned \"success\" status 0x%x\n", Status);
                continue;
            }
        }

        /* Use whatever Client ID we got */
        Teb->RealClientId = ReceiveMsg.Header.ClientId;

        /* Get the Message Type */
        MessageType = ReceiveMsg.Header.u2.s2.Type;

        /* Handle connection requests */
        if (MessageType == LPC_CONNECTION_REQUEST)
        {
            /* Handle the Connection Request */
            CsrApiHandleConnectionRequest(&ReceiveMsg);

            ReplyMsg = NULL;
            ReplyPort = CsrApiPort;
            continue;
        }

        /* It's some other kind of request. Get the lock for the lookup */
        CsrAcquireProcessLock();

        /* Now do the lookup to get the CSR_THREAD */
        CsrThread = CsrLocateThreadByClientId(&CsrProcess,
                                              &ReceiveMsg.Header.ClientId);

        /* Did we find a thread? */
        if (!CsrThread)
        {
            /* This wasn't a CSR Thread, release lock */
            CsrReleaseProcessLock();

            /* If this was an exception, handle it */
            if (MessageType == LPC_EXCEPTION)
            {
                ReplyMsg = &ReceiveMsg;
                ReplyPort = CsrApiPort;
                ReplyMsg->Status = DBG_CONTINUE;
            }
            else if (MessageType == LPC_PORT_CLOSED ||
                     MessageType == LPC_CLIENT_DIED)
            {
                /* The Client or Port are gone, loop again */
                ReplyMsg = NULL;
                ReplyPort = CsrApiPort;
            }
            else if (MessageType == LPC_ERROR_EVENT)
            {
                /* If it's a hard error, handle this too */
                HardErrorMsg = (PHARDERROR_MSG)&ReceiveMsg;

                /* Default it to unhandled */
                HardErrorMsg->Response = ResponseNotHandled;

                /* Check if there are free api threads */
                CsrpCheckRequestThreads();
                if (CsrpStaticThreadCount)
                {
                    /* Loop every Server DLL */
                    for (i = 0; i < CSR_SERVER_DLL_MAX; i++)
                    {
                        /* Get the Server DLL */
                        ServerDll = CsrLoadedServerDll[i];

                        /* Check if it's valid and if it has a Hard Error Callback */
                        if ((ServerDll) && (ServerDll->HardErrorCallback))
                        {
                            /* Call it */
                            ServerDll->HardErrorCallback(NULL /* == CsrThread */, HardErrorMsg);

                            /* If it's handled, get out of here */
                            if (HardErrorMsg->Response != ResponseNotHandled) break;
                        }
                    }
                }

                /* Increase the thread count */
                InterlockedIncrementUL(&CsrpStaticThreadCount);

                /* If the response was 0xFFFFFFFF, we'll ignore it */
                if (HardErrorMsg->Response == 0xFFFFFFFF)
                {
                    ReplyMsg = NULL;
                    ReplyPort = CsrApiPort;
                }
                else
                {
                    ReplyMsg = &ReceiveMsg;
                    ReplyPort = CsrApiPort;
                }
            }
            else if (MessageType == LPC_REQUEST)
            {
                /* This is an API Message coming from a non-CSR Thread */
                ReplyMsg = &ReceiveMsg;
                ReplyPort = CsrApiPort;
                ReplyMsg->Status = STATUS_ILLEGAL_FUNCTION;
            }
            else if (MessageType == LPC_DATAGRAM)
            {
                /* This is an API call, get the Server ID */
                ServerId = CSR_API_NUMBER_TO_SERVER_ID(ReceiveMsg.ApiNumber);

                /* Make sure that the ID is within limits, and the Server DLL loaded */
                ServerDll = NULL;
                if ((ServerId >= CSR_SERVER_DLL_MAX) ||
                    (!(ServerDll = CsrLoadedServerDll[ServerId])))
                {
                    /* We are beyond the Maximum Server ID */
                    DPRINT1("CSRSS: %lx is invalid ServerDllIndex (%08x)\n",
                            ServerId, ServerDll);
                    // DbgBreakPoint();

                    ReplyMsg = NULL;
                    ReplyPort = CsrApiPort;
                    continue;
                }

                /* Get the API ID, normalized with our Base ID */
                ApiId = CSR_API_NUMBER_TO_API_ID(ReceiveMsg.ApiNumber) - ServerDll->ApiBase;

                /* Make sure that the ID is within limits, and the entry exists */
                if (ApiId >= ServerDll->HighestApiSupported)
                {
                    /* We are beyond the Maximum API ID, or it doesn't exist */
                    DPRINT1("CSRSS: %lx is invalid ApiTableIndex for %Z\n",
                            CSR_API_NUMBER_TO_API_ID(ReceiveMsg.ApiNumber),
                            &ServerDll->Name);

                    ReplyPort = CsrApiPort;
                    ReplyMsg = NULL;
                    continue;
                }

#ifdef CSR_DBG
                if (CsrDebug & 2)
                {
                    DPRINT1("[%02x] CSRSS: [%02x,%02x] - %s Api called from %08x\n",
                            Teb->ClientId.UniqueThread,
                            ReceiveMsg.Header.ClientId.UniqueProcess,
                            ReceiveMsg.Header.ClientId.UniqueThread,
                            ServerDll->NameTable[ApiId],
                            NULL);
                }
#endif

                /* Assume success */
                ReceiveMsg.Status = STATUS_SUCCESS;

                /* Validation complete, start SEH */
                _SEH2_TRY
                {
                    /* Make sure we have enough threads */
                    CsrpCheckRequestThreads();

                    /* Call the API and get the reply code */
                    ReplyMsg = NULL;
                    ReplyPort = CsrApiPort;
                    ServerDll->DispatchTable[ApiId](&ReceiveMsg, &ReplyCode);

                    /* Increase the static thread count */
                    InterlockedIncrementUL(&CsrpStaticThreadCount);
                }
                _SEH2_EXCEPT(CsrUnhandledExceptionFilter(_SEH2_GetExceptionInformation()))
                {
                    ReplyMsg = NULL;
                    ReplyPort = CsrApiPort;
                }
                _SEH2_END;
            }
            else
            {
Exemplo n.º 15
0
NTSTATUS PhSvcApiRequestThreadStart(
    _In_ PVOID Parameter
    )
{
    PH_AUTO_POOL autoPool;
    NTSTATUS status;
    PHSVC_THREAD_CONTEXT threadContext;
    HANDLE portHandle;
    PVOID portContext;
    SIZE_T messageSize;
    PPORT_MESSAGE receiveMessage;
    PPORT_MESSAGE replyMessage;
    CSHORT messageType;
    PPHSVC_CLIENT client;
    PPHSVC_API_PAYLOAD payload;

    PhInitializeAutoPool(&autoPool);

    threadContext.CurrentClient = NULL;
    threadContext.OldClient = NULL;

    TlsSetValue(PhSvcApiThreadContextTlsIndex, &threadContext);

    portHandle = PhSvcApiPortHandle;
    messageSize = PhIsExecutingInWow64() ? sizeof(PHSVC_API_MSG64) : sizeof(PHSVC_API_MSG);
    receiveMessage = PhAllocate(messageSize);
    replyMessage = NULL;

    while (TRUE)
    {
        status = NtReplyWaitReceivePort(
            portHandle,
            &portContext,
            replyMessage,
            receiveMessage
            );

        portHandle = PhSvcApiPortHandle;
        replyMessage = NULL;

        if (!NT_SUCCESS(status))
        {
            // Client probably died.
            continue;
        }

        messageType = receiveMessage->u2.s2.Type;

        if (messageType == LPC_CONNECTION_REQUEST)
        {
            PhSvcHandleConnectionRequest(receiveMessage);
            continue;
        }

        if (!portContext)
            continue;

        client = portContext;
        threadContext.CurrentClient = client;
        PhWaitForEvent(&client->ReadyEvent, NULL);

        if (messageType == LPC_REQUEST)
        {
            if (PhIsExecutingInWow64())
                payload = &((PPHSVC_API_MSG64)receiveMessage)->p;
            else
                payload = &((PPHSVC_API_MSG)receiveMessage)->p;

            PhSvcDispatchApiCall(client, payload, &portHandle);
            replyMessage = receiveMessage;
        }
        else if (messageType == LPC_PORT_CLOSED)
        {
            PhDereferenceObject(client);

            if (_InterlockedDecrement(&PhSvcApiNumberOfClients) == 0)
            {
                NtSetEvent(PhSvcTimeoutStandbyEventHandle, NULL);
            }
        }

        assert(!threadContext.OldClient);
        PhDrainAutoPool(&autoPool);
    }

    PhDeleteAutoPool(&autoPool);
}
Exemplo n.º 16
0
NTSTATUS
CsrSbApiRequestThread(
    IN PVOID Parameter
    )
{
    NTSTATUS Status;
    SBAPIMSG ReceiveMsg;
    PSBAPIMSG ReplyMsg;

    ReplyMsg = NULL;
    while (TRUE) {
        IF_CSR_DEBUG( LPC ) {
            DbgPrint( "CSRSS: Sb Api Request Thread waiting...\n" );
            }
        Status = NtReplyWaitReceivePort( CsrSbApiPort,
                                         NULL,
                                         (PPORT_MESSAGE)ReplyMsg,
                                         (PPORT_MESSAGE)&ReceiveMsg
                                       );

        if (Status != 0) {
            if (NT_SUCCESS( Status )) {
                continue;       // Try again if alerted or a failure
                }
            else {
                IF_DEBUG {
                    DbgPrint( "CSRSS: ReceivePort failed - Status == %X\n", Status );
                    }
                break;
                }
            }

        //
        // Check to see if this is a connection request and handle
        //

        if (ReceiveMsg.h.u2.s2.Type == LPC_CONNECTION_REQUEST) {
            CsrSbApiHandleConnectionRequest( &ReceiveMsg );
            ReplyMsg = NULL;
            continue;
            }

        if ((ULONG)ReceiveMsg.ApiNumber >= SbMaxApiNumber) {
            IF_DEBUG {
                DbgPrint( "CSRSS: %lx is invalid Sb ApiNumber\n",
                          ReceiveMsg.ApiNumber
                        );
                }

            ReceiveMsg.ApiNumber = SbMaxApiNumber;
            }

#if DBG
        IF_CSR_DEBUG( LPC ) {
            DbgPrint( "CSRSS: %s Sb Api Request received from %lx.%lx\n",
                      CsrServerSbApiName[ ReceiveMsg.ApiNumber ],
                      ReceiveMsg.h.ClientId.UniqueProcess,
                      ReceiveMsg.h.ClientId.UniqueThread
                    );
	    }
#endif // DBG

        ReplyMsg = &ReceiveMsg;
        if (ReceiveMsg.ApiNumber < SbMaxApiNumber) {
            if (!(*CsrServerSbApiDispatch[ ReceiveMsg.ApiNumber ])( &ReceiveMsg )) {
                ReplyMsg = NULL;
                }
            }
        else {
            ReplyMsg->ReturnedStatus = STATUS_NOT_IMPLEMENTED;
            }

#if DBG
	IF_CSR_DEBUG( LPC ) {
            if (ReplyMsg != NULL) {
                DbgPrint( "CSRSS: %s Sb Api sending %lx status reply to %lx.%lx\n",
                          CsrServerSbApiName[ ReceiveMsg.ApiNumber ],
                          ReplyMsg->ReturnedStatus,
                          ReplyMsg->h.ClientId.UniqueProcess,
                          ReplyMsg->h.ClientId.UniqueThread
                        );
                }
	    }
#endif // DBG
        }
Exemplo n.º 17
0
NTSTATUS WINAPI
AuthPortThreadRoutine(PVOID Param)
{
    PLSAP_LOGON_CONTEXT LogonContext;
    PLSA_API_MSG ReplyMsg = NULL;
    LSA_API_MSG RequestMsg;
    NTSTATUS Status;

    TRACE("AuthPortThreadRoutine() called\n");

    Status = STATUS_SUCCESS;

    for (;;)
    {
        TRACE("Reply: %p\n", ReplyMsg);
        Status = NtReplyWaitReceivePort(AuthPortHandle,
                                        (PVOID*)&LogonContext,
                                        (PPORT_MESSAGE)ReplyMsg,
                                        (PPORT_MESSAGE)&RequestMsg);
        if (!NT_SUCCESS(Status))
        {
            TRACE("NtReplyWaitReceivePort() failed (Status %lx)\n", Status);
            break;
        }

        TRACE("Received message\n");

        switch (RequestMsg.h.u2.s2.Type)
        {
            case LPC_CONNECTION_REQUEST:
                TRACE("Port connection request\n");
                Status = LsapHandlePortConnection(&RequestMsg);
                ReplyMsg = NULL;
                break;

            case LPC_PORT_CLOSED:
                TRACE("Port closed\n");
                ReplyMsg = NULL;
                break;

            case LPC_CLIENT_DIED:
                TRACE("Client died\n");
                ReplyMsg = NULL;
                break;

            default:
                TRACE("Received request (ApiNumber: %lu)\n", RequestMsg.ApiNumber);

                switch (RequestMsg.ApiNumber)
                {
                    case LSASS_REQUEST_CALL_AUTHENTICATION_PACKAGE:
                        RequestMsg.Status = LsapCallAuthenticationPackage(&RequestMsg,
                                                                          LogonContext);
                        ReplyMsg = &RequestMsg;
                        break;

                    case LSASS_REQUEST_DEREGISTER_LOGON_PROCESS:

                        ReplyMsg = &RequestMsg;
                        RequestMsg.Status = STATUS_SUCCESS;
                        NtReplyPort(AuthPortHandle,
                                    &ReplyMsg->h);

                        LsapDeregisterLogonProcess(&RequestMsg,
                                                   LogonContext);

                        ReplyMsg = NULL;
                        break;

                    case LSASS_REQUEST_LOGON_USER:
                        RequestMsg.Status = LsapLogonUser(&RequestMsg,
                                                          LogonContext);
                        ReplyMsg = &RequestMsg;
                        break;

                    case LSASS_REQUEST_LOOKUP_AUTHENTICATION_PACKAGE:
                        RequestMsg.Status = LsapLookupAuthenticationPackage(&RequestMsg,
                                                                            LogonContext);
                        ReplyMsg = &RequestMsg;
                        break;

                    case LSASS_REQUEST_ENUM_LOGON_SESSIONS:
                        RequestMsg.Status = LsapEnumLogonSessions(&RequestMsg);
                        ReplyMsg = &RequestMsg;
                        break;

                    case LSASS_REQUEST_GET_LOGON_SESSION_DATA:
                        RequestMsg.Status = LsapGetLogonSessionData(&RequestMsg);
                        ReplyMsg = &RequestMsg;
                        break;

                    case LSASS_REQUEST_POLICY_CHANGE_NOTIFY:
                        RequestMsg.Status = LsapRegisterNotification(&RequestMsg);
                        ReplyMsg = &RequestMsg;
                        break;

                    default:
                        RequestMsg.Status = STATUS_INVALID_SYSTEM_SERVICE;
                        ReplyMsg = &RequestMsg;
                        break;
                }

                break;
        }
    }

    return STATUS_SUCCESS;
}
Exemplo n.º 18
0
NTSTATUS
DbgSspSrvApiLoop(
    IN PVOID ThreadParameter
    )

/*++

Routine Description:

    This loop services Dbg Subsystem server originated messages.

Arguments:

    ThreadParameter - Not used.

Return Value:

    None.

--*/

{
    DBGSRV_APIMSG DbgSrvApiMsg;
    PDBGSS_CONTINUE_KEY ContinueKey;
    NTSTATUS st;

    for(;;) {

        st = NtReplyWaitReceivePort(
                DbgSspApiPort,
                NULL,
                NULL,
                (PPORT_MESSAGE) &DbgSrvApiMsg
                );

        if (!NT_SUCCESS( st )) {
            continue;
            }

        ASSERT(DbgSrvApiMsg.ApiNumber < DbgSrvMaxApiNumber);

        switch (DbgSrvApiMsg.ApiNumber ) {
        case DbgSrvContinueApi :

            //
            // Might want to implement continue status based callout
            // like DBG_TERMINATE_PROCESS/THREAD
            //

            ContinueKey = (PDBGSS_CONTINUE_KEY) DbgSrvApiMsg.ContinueKey;
            ContinueKey->KmApiMsg.ReturnedStatus = DbgSrvApiMsg.ReturnedStatus;

            if ( ContinueKey->ReplyEvent ) {
                st = NtSetEvent(ContinueKey->ReplyEvent,NULL);
            } else {
                st = NtReplyPort(DbgSspKmReplyPort,
                                 (PPORT_MESSAGE) &ContinueKey->KmApiMsg
                                );
            }

            RtlFreeHeap(RtlProcessHeap(), 0, ContinueKey);
            break;
        default :
            ASSERT(FALSE);
        }
    }

    //
    // Make the compiler happy
    //

    return st;
}