Windows NT 4.0 source code leak
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

343 lines
11 KiB

/*++
Copyright (c) 1989 Microsoft Corporation
Module Name:
concreat.c
Abstract:
This module handles the request to create a session form OS2SES.
Author:
Avi Nathan (avin) 17-Jul-1991
Revision History:
--*/
#define INCL_OS2V20_TASKING
#define INCL_OS2V20_ERRORS
#include "os2srv.h"
#define NTOS2_ONLY
#include "sesport.h"
extern ULONG Os2GlobalInfoSeg;
extern HANDLE Os2GlobalInfoSegHandle;
extern HANDLE FirstOs2ProcessHandle;
extern CLIENT_ID FirstOs2ProcessClientId;
NTSTATUS
Os2CreateConSession(
IN OUT PVOID RequestMsg
)
{
PSCREQ_CREATE Create = & ((POS2SESREQUESTMSG)RequestMsg)->d.Create;
OS2_DOSEXECPGM_MSG ExecInfo;
OS2_DOSSTARTSESSION_INFO SessionInfo;
POS2_THREAD NewThread = NULL;
POS2_PROCESS Process;
POS2_SESSION Session, SessionForCreate;
APIRET Rc = 0;
NTSTATUS Status = STATUS_SUCCESS;
BOOLEAN NewSession = FALSE;
ULONG RegionSize = 0, Length;
RtlZeroMemory(&ExecInfo, sizeof( ExecInfo ) );
RtlZeroMemory(&SessionInfo, sizeof( SessionInfo ) );
try
{
Session = (POS2_SESSION)((POS2SESREQUESTMSG)RequestMsg)->Session;
/*
* Set ExecPgm information
*/
ExecInfo.Flags = EXEC_ASYNC;
Length = 1 + strlen(Create->d.In.ApplName);
RtlMoveMemory(
&ExecInfo.ApplName[0],
&Create->d.In.ApplName[0],
Length
);
ExecInfo.ApplNameLength = Length;
RtlInitAnsiString( &ExecInfo.ErrorText, "Default error text");
/*
* Set StartSession information
*/
/* USHORT */ // SessionInfo.FgBg;
/* USHORT */ // SessionInfo.InheritOpt;
/* USHORT */ // SessionInfo.PgmControl;
NewThread = Os2LocateThreadByClientId( NULL, &((POS2SESREQUESTMSG)RequestMsg)->h.ClientId );
if (NewThread == NULL)
{
if( ((POS2SESREQUESTMSG)RequestMsg)->Request != SesCheckPortAndConCreate)
{
//
// Not a root process of a session, still NewThread is NULL - return
// failure
//
#if DBG
KdPrint(("Os2CreateConSession: Process already killed by signal\n"));
#endif
return( STATUS_UNSUCCESSFUL );
}
/*
* create a process for the new session. OS2SS is the parent
* of this process.
*/
ASSERT(Create->d.In.IsNewSession == OS2SS_NEW_SESSION);
SessionForCreate = Session;
NewSession = TRUE;
} else if (OS2SS_IS_PROCESS( Create->d.In.IsNewSession ))
{
/*
* a child process
*/
SessionForCreate = NULL;
} else
{
ASSERT(Create->d.In.IsNewSession == OS2SS_CHILD_SESSION);
/*
* a child session
*/
SessionForCreate = Session;
}
Rc = Os2CreateProcess(
RequestMsg,
NULL, // ParentThread or (POS2_THREAD)Session->Thread,
&ExecInfo,
SessionForCreate,
&NewThread
);
if (FirstOs2ProcessHandle == 0 && Rc == 0) {
//
// First OS/2 application - remember for logoff/shutdown
//
FirstOs2ProcessHandle = NewThread->Process->ProcessHandle;
FirstOs2ProcessClientId = NewThread->Process->ClientId;
}
} except ( EXCEPTION_EXECUTE_HANDLER ){
Rc = (APIRET)STATUS_UNSUCCESSFUL; // BUGBUG!
/*
* fall thru to close the section.
*/
}
if ( Rc == NO_ERROR )
{
Process = NewThread->Process;
if (( Process == NULL ) ||
( Create->d.In.ExitListDispatcher == NULL ) ||
( Create->d.In.InfiniteSleep == NULL) ||
( Create->d.In.SignalDeliverer == NULL ) ||
( Create->d.In.FreezeThread == NULL ) ||
( Create->d.In.UnfreezeThread == NULL ) ||
( Create->d.In.ClientPib == NULL ) ||
( Create->d.In.InitialPebOs2Length !=
Process->InitialPebOs2Data.Length ))
{
Status = STATUS_UNSUCCESSFUL;
} else
{
Process->SignalDeliverer = Create->d.In.SignalDeliverer;
Process->ExitListDispatcher = Create->d.In.ExitListDispatcher;
Process->InfiniteSleep = Create->d.In.InfiniteSleep;
Process->FreezeThread = Create->d.In.FreezeThread;
Process->UnfreezeThread = Create->d.In.UnfreezeThread;
Process->VectorHandler = Create->d.In.VectorHandler;
Process->CritSectionAddr = Create->d.In.CritSectionAddr;
Process->ClientPib = Create->d.In.ClientPib;
NewThread->ClientOs2Tib = Create->d.In.ClientOs2Tib;
Create->d.Out.PibProcessId = (HANDLE)Process->ProcessId;
Create->d.Out.PibParentProcessId = (HANDLE)Process->Parent->ProcessId;
Create->d.Out.PibImageFileHandle = (HANDLE)-1;
Create->d.Out.PibStatus = 0;
if (Process->Flags & OS2_PROCESS_BACKGROUND)
{
Create->d.Out.PibType = PT_DETACHED;
}
else
Create->d.Out.PibType = PT_PM;
Create->d.Out.Os2TibThreadId = (ULONG)NewThread->ThreadId;
Create->d.Out.Os2TibVersion = OS2_VERSION;
Os2SetThreadPriority( NewThread, NewThread->Os2Class, NewThread->Os2Level );
*((PPEB_OS2_DATA)&Create->d.Out.InitialPebOs2Data[0]) = Process->InitialPebOs2Data;
Create->d.Out.BootDrive = Os2BootDrive;
Create->d.Out.SystemDrive = Os2DefaultDrive;
Create->d.Out.SessionNumber = Process->Session->SessionId;
Create->d.Out.GInfoAddr = (PVOID)Os2GlobalInfoSeg;
while (NT_SUCCESS(Status))
{
Status = NtDuplicateObject( NtCurrentProcess(),
Os2DevicesDirectory,
Process->ProcessHandle,
&Create->d.Out.DeviceDirectory,
0,
0,
DUPLICATE_SAME_ACCESS |
DUPLICATE_SAME_ATTRIBUTES
);
if (!NT_SUCCESS(Status) )
{
#if DBG
KdPrint(("Os2CreateConSession: NtDuplicateObject-1 Failed %lx\n",Status));
#endif
break;
}
Status = NtDuplicateObject( NtCurrentProcess(),
Process->Session->ConsolePort,
Process->ProcessHandle,
&Create->d.Out.CtrlPortHandle,
0,
0,
DUPLICATE_SAME_ACCESS |
DUPLICATE_SAME_ATTRIBUTES
);
if (!NT_SUCCESS(Status) )
{
#if DBG
KdPrint(("Os2CreateConSession: NtDuplicateObject-2 Failed %lx\n",Status));
#endif
break;
}
//
// Map view the global info seg into the new client
//
Status = NtMapViewOfSection( Os2GlobalInfoSegHandle,
Process->ProcessHandle,
(PVOID) &Os2GlobalInfoSeg,
0,
0,
NULL,
&RegionSize,
ViewUnmap,
0,
PAGE_READONLY
);
if (!NT_SUCCESS(Status) )
{
#if DBG
KdPrint(("Os2CreateConSession: NtMapViewOfSection Failed %lx\n",Status));
#endif
}
break;
}
}
if (!NT_SUCCESS(Status) )
{
ASSERT( FALSE );
// fall into Os2DereferenceSession
} else if (SessionForCreate)
{
/*
* now that the session is allocated set the console port
* and reply the session handle to OS2SES
*/
OS2SESREQUESTMSG FocusMsg;
ASSERT(NewThread->Process->Session == Session);
//
// Set the new session to be foreground
//
FocusMsg.d.FocusSet = TRUE;
FocusMsg.Session = Session;
Os2SessionFocusSet(&FocusMsg);
return(Status);
} else
{
//
// os2.exe that was created by DosExecPgm
//
return(Status);
}
}
Os2DereferenceSession(Session, NULL, (BOOLEAN)TRUE);
return( STATUS_UNSUCCESSFUL ); // BUGBUG!
}
NTSTATUS
Os2TerminateConSession (
IN POS2_SESSION Session,
IN POS2_TERMINATEPROCESS_MSG a
)
{
HANDLE SessionPort;
NTSTATUS Status;
SCREQUESTMSG Request;
OS2SESREQUESTMSG FocusMsg;
Request.Request = TaskManRequest;
Request.d.Tm.Request = TmExit;
Request.d.Tm.ExitResults = a->ExitResult;
strcpy(&Request.d.Tm.ErrorText[0], &a->ErrorText[0]);
PORT_MSG_TOTAL_LENGTH(Request) = sizeof(SCREQUESTMSG);
PORT_MSG_DATA_LENGTH(Request) = sizeof(SCREQUESTMSG) - sizeof(PORT_MESSAGE);
PORT_MSG_ZERO_INIT(Request) = 0L;
SessionPort = Session->ConsolePort;
Status = NtRequestPort(
SessionPort,
(PPORT_MESSAGE) &Request
);
if ( !NT_SUCCESS( Status )) {
#if DBG
KdPrint(( "OS2SS: Unable to send terminate request - Status == %X\n",
Status
));
#endif
return( Status );
}
//
// Reset foreground session (nop if the terminating session is not in foreground)
//
FocusMsg.d.FocusSet = FALSE;
FocusMsg.Session = Session;
Os2SessionFocusSet(&FocusMsg);
return( STATUS_SUCCESS );
}