Leaked source code of windows server 2003
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.
 
 
 
 
 
 

219 lines
6.1 KiB

//
// ConsoleCom.cpp : Defines the entry point for the console application.
//
#include "stdafx.h"
#include "ConsoleCom.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#endif
//
// The one and only application object
//
CWinApp theApp;
HANDLE coutPipe, cinPipe, cerrPipe;
#define CONNECTIMEOUT 1000
//
// Create named pipes for stdin, stdout and stderr
// Parameter: process id
//
BOOL CreateNamedPipes(DWORD pid)
{
TCHAR name[256];
_stprintf(name, _T("\\\\.\\pipe\\%dcout"), pid);
if (INVALID_HANDLE_VALUE == (coutPipe = CreateNamedPipe(name,
PIPE_ACCESS_INBOUND,
PIPE_TYPE_BYTE | PIPE_READMODE_BYTE,
1,
1024,
1024,
CONNECTIMEOUT,
NULL)))
return 0;
_stprintf(name, _T("\\\\.\\pipe\\%dcin"), pid);
if (INVALID_HANDLE_VALUE == (cinPipe = CreateNamedPipe(name,
PIPE_ACCESS_OUTBOUND,
PIPE_TYPE_BYTE | PIPE_READMODE_BYTE,
1,
1024,
1024,
CONNECTIMEOUT,
NULL)))
return 0;
_stprintf(name, _T("\\\\.\\pipe\\%dcerr"), pid);
if (INVALID_HANDLE_VALUE == (cerrPipe = CreateNamedPipe(name,
PIPE_ACCESS_INBOUND,
PIPE_TYPE_BYTE | PIPE_READMODE_BYTE,
1,
1024,
1024,
CONNECTIMEOUT,
NULL)))
return 0;
return 1;
}
//
// Close all named pipes
//
void CloseNamedPipes()
{
CloseHandle(coutPipe);
CloseHandle(cerrPipe);
CloseHandle(cinPipe);
}
//
// Thread function that handles incoming bytesreams to be outputed
// on stdout
//
void __cdecl OutPipeTh(void*)
{
TCHAR buffer[1024];
DWORD count = 0;
ConnectNamedPipe(coutPipe, NULL);
while(ReadFile(coutPipe, buffer, 1024, &count, NULL))
{
buffer[count] = 0;
cout << buffer << flush;
}
}
//
// Thread function that handles incoming bytesreams to be outputed
// on stderr
//
void __cdecl ErrPipeTh(void*)
{
TCHAR buffer[1024];
DWORD count = 0;
ConnectNamedPipe(cerrPipe, NULL);
while(ReadFile(cerrPipe, buffer, 1024, &count, NULL))
{
buffer[count] = 0;
cerr << buffer << flush;
}
}
//
// Thread function that handles incoming bytesreams from stdin
//
void __cdecl InPipeTh(void*)
{
TCHAR buffer[1024];
DWORD countr = 0;
DWORD countw = 0;
ConnectNamedPipe(cinPipe, NULL);
for(;;)
{
if (!ReadFile(GetStdHandle(STD_INPUT_HANDLE),
buffer,
1024,
&countr,
NULL))
break;
if (!WriteFile(cinPipe,
buffer,
countr,
&countw,
NULL))
break;
}
}
//
// Start handler pipe handler threads
//
void RunPipeThreads()
{
_beginthread(InPipeTh, 0, NULL);
_beginthread(OutPipeTh, 0, NULL);
_beginthread(ErrPipeTh, 0, NULL);
}
int __cdecl _tmain(int argc, TCHAR* argv[], TCHAR* envp[])
{
ULONG nRetCode = 0;
//
// initialize MFC and print and error on failure
//
if (!AfxWinInit(::GetModuleHandle(NULL), NULL, ::GetCommandLine(), 0))
{
_tprintf(_T("Fatal Error: MFC initialization failed\n"));
nRetCode = 1;
} else {
//
// create command line string based on program name
//
TCHAR drive[_MAX_DRIVE];
TCHAR dir[_MAX_DIR];
TCHAR fname[_MAX_FNAME];
TCHAR ext[_MAX_EXT];
_tsplitpath(argv[0], drive, dir, fname, ext);
TCHAR cParams[1024];
_tcscpy(cParams, GetCommandLine() + _tcslen(argv[0]) + 1);
TCHAR cLine[2028];
_stprintf(cLine, _T("%s%s%s.exe %s"), drive, dir, fname, cParams);
//
// create process in suspended mode
//
PROCESS_INFORMATION pInfo;
STARTUPINFO sInfo;
memset(&sInfo, 0, sizeof(STARTUPINFO));
sInfo.cb = sizeof(STARTUPINFO);
//cout << "Calling " << cLine << endl;
if (!CreateProcess(NULL,
cLine,
NULL,
NULL,
FALSE,
CREATE_SUSPENDED,
NULL,
NULL,
&sInfo,
&pInfo))
{
cerr << _T("ERROR: Could not create process.") << endl;
return 1;
}
if (!CreateNamedPipes(pInfo.dwProcessId))
{
cerr << _T("ERROR: Could not create named pipes.") << endl;
return 1;
}
RunPipeThreads();
//
// resume process
//
ResumeThread(pInfo.hThread);
WaitForSingleObject(pInfo.hProcess, INFINITE);
CloseNamedPipes();
GetExitCodeProcess(pInfo.hProcess, (ULONG*)&nRetCode);
}
return (int)nRetCode;
}