Why does the following code work to send commands to a console application in Windows NT and not in Win 98?
//---------------------------------------------------------------------------
#include <vcl.h>
#include <fstream.h>
#pragma hdrstop
#include "Project.h"
#include "Unit2.h"
//---------------------------------------------------------------------------
#pragma package(smart_init)
#pragma resource "*.dfm"
TForm1 *Form1;
HANDLE conin,conout;
int status;
SECURITY_ATTRIBUTES security;
STARTUPINFO si = {0};
PROCESS_INFORMATION pi = {0};
int send(char[]);
//---------------------------------------------------------------------------
__fastcall TForm1::TForm1(TComponent* Owner)
: TForm(Owner)
{
AllocConsole();
security.nLength = sizeof(SECURITY_ATTRIBUTES);
security.lpSecurityDescriptor = NULL;
security.bInheritHandle = TRUE;
// Get handle to console input
conin = CreateFile("CONIN$",
GENERIC_WRITE,
FILE_SHARE_WRITE, /* share with cmd.*/
&security,
CREATE_ALWAYS, /* open already created console */
FILE_ATTRIBUTE_NORMAL, /* normal file open */
NULL);
if(conin == INVALID_HANDLE_VALUE)
MessageBox(NULL, "Invalid input handle!", "Error", MB_OK);
// Get handle to console output
conout = CreateFile("CONOUT$",
GENERIC_READ | GENERIC_WRITE,
FILE_SHARE_READ | FILE_SHARE_WRITE, /* share with cmd.*/
&security,
OPEN_EXISTING, /* open already created console */
0, /*normal file open */
NULL);
if(conout == INVALID_HANDLE_VALUE)
MessageBox(NULL, "Invalid output handle!", "Error", MB_OK);
/* Set up members of STARTUPINFO structure. */
si.cb = sizeof(STARTUPINFO);
si.dwFlags = STARTF_USESTDHANDLES;
si.hStdInput = conin;
si.hStdOutput = conout;
si.hStdError = conout;
si.wShowWindow = SW_SHOWDEFAULT;
/* Create the child process. */
CreateProcess(NULL,
"c:\\running.exe", /* command line */
NULL, /* process security attributes */
NULL, /* primary thread security attributes */
TRUE, /* handles are inherited */
CREATE_NEW_PROCESS_GROUP,
NULL, /* use parent's environment */
NULL, /* use parent's current directory */
&si, /* STARTUPINFO pointer */
&pi); /* receives PROCESS_INFORMATION */
//WaitForSingleObject( pi.hProcess, INFINITE );
AllocConsole();
}
//---------------------------------------------------------------------------
void __fastcall TForm1::Runner1Click(TObject *Sender)
{
Runner->ShowModal();
}
//---------------------------------------------------------------------------
void __fastcall TForm1::Exit1Click(TObject *Sender)
{
Close();
}
//---------------------------------------------------------------------------
void __fastcall TForm1::OpenDatabase1Click(TObject *Sender)
{
if(OpenDialog1->Execute())
{
Form1->Caption = Form1->Caption + " - " + OpenDialog1->FileName;
}
}
//---------------------------------------------------------------------------
int send(char array[20])
{
LPDWORD written;
INPUT_RECORD inputrec = {KEY_EVENT,{TRUE,1,0,0,0,0}};
short vkcode,shift_state;
DWORD scancode;
unsigned long numread,numrec;
int x,chars;
chars=strlen(array);
// Try to write to console input
for(x=0;x<chars;x++)
{
vkcode = VkKeyScan(array[x]);
scancode = MapVirtualKey(vkcode,0);
shift_state = HIWORD(scancode);
// Now write the key down event for this char
inputrec.Event.KeyEvent.bKeyDown = TRUE;
inputrec.Event.KeyEvent.uChar.AsciiChar = array[x];
inputrec.Event.KeyEvent.wVirtualKeyCode = vkcode;
inputrec.Event.KeyEvent.wVirtualScanCode = LOWORD(scancode);
if(shift_state == 1)
inputrec.Event.KeyEvent.dwControlKeyState = SHIFT_PRESSED;
else
inputrec.Event.KeyEvent.dwControlKeyState = 0;
if (!WriteConsoleInput(conin, // handle to a console input buffer
&inputrec,// pointer to the buffer for write data
1, // number of records to write
&numrec)) // pointer to number of records written
{
return 0;
}
// Now write the key up event for this char
inputrec.Event.KeyEvent.bKeyDown = FALSE;
inputrec.Event.KeyEvent.uChar.AsciiChar = array[x];
inputrec.Event.KeyEvent.wVirtualKeyCode = vkcode;
inputrec.Event.KeyEvent.wVirtualScanCode = LOWORD(scancode);
if(shift_state == 1)
inputrec.Event.KeyEvent.dwControlKeyState = SHIFT_PRESSED;
else
inputrec.Event.KeyEvent.dwControlKeyState = 0;
if(!WriteConsoleInput(conin, // handle to a console input buffer
&inputrec,// pointer to the buffer for write data
1, // number of records to write
&numrec)) // pointer to number of records written
{
return 0;
}
}
return 1;
}
void __fastcall TForm1:ivision1Click(TObject *Sender)
{
int x;
x = send("o"
if(x == 1)
Division1->Caption = "Division success";
else
Division1->Caption = "Division failure";
}
//---------------------------------------------------------------------------
#include <vcl.h>
#include <fstream.h>
#pragma hdrstop
#include "Project.h"
#include "Unit2.h"
//---------------------------------------------------------------------------
#pragma package(smart_init)
#pragma resource "*.dfm"
TForm1 *Form1;
HANDLE conin,conout;
int status;
SECURITY_ATTRIBUTES security;
STARTUPINFO si = {0};
PROCESS_INFORMATION pi = {0};
int send(char[]);
//---------------------------------------------------------------------------
__fastcall TForm1::TForm1(TComponent* Owner)
: TForm(Owner)
{
AllocConsole();
security.nLength = sizeof(SECURITY_ATTRIBUTES);
security.lpSecurityDescriptor = NULL;
security.bInheritHandle = TRUE;
// Get handle to console input
conin = CreateFile("CONIN$",
GENERIC_WRITE,
FILE_SHARE_WRITE, /* share with cmd.*/
&security,
CREATE_ALWAYS, /* open already created console */
FILE_ATTRIBUTE_NORMAL, /* normal file open */
NULL);
if(conin == INVALID_HANDLE_VALUE)
MessageBox(NULL, "Invalid input handle!", "Error", MB_OK);
// Get handle to console output
conout = CreateFile("CONOUT$",
GENERIC_READ | GENERIC_WRITE,
FILE_SHARE_READ | FILE_SHARE_WRITE, /* share with cmd.*/
&security,
OPEN_EXISTING, /* open already created console */
0, /*normal file open */
NULL);
if(conout == INVALID_HANDLE_VALUE)
MessageBox(NULL, "Invalid output handle!", "Error", MB_OK);
/* Set up members of STARTUPINFO structure. */
si.cb = sizeof(STARTUPINFO);
si.dwFlags = STARTF_USESTDHANDLES;
si.hStdInput = conin;
si.hStdOutput = conout;
si.hStdError = conout;
si.wShowWindow = SW_SHOWDEFAULT;
/* Create the child process. */
CreateProcess(NULL,
"c:\\running.exe", /* command line */
NULL, /* process security attributes */
NULL, /* primary thread security attributes */
TRUE, /* handles are inherited */
CREATE_NEW_PROCESS_GROUP,
NULL, /* use parent's environment */
NULL, /* use parent's current directory */
&si, /* STARTUPINFO pointer */
&pi); /* receives PROCESS_INFORMATION */
//WaitForSingleObject( pi.hProcess, INFINITE );
AllocConsole();
}
//---------------------------------------------------------------------------
void __fastcall TForm1::Runner1Click(TObject *Sender)
{
Runner->ShowModal();
}
//---------------------------------------------------------------------------
void __fastcall TForm1::Exit1Click(TObject *Sender)
{
Close();
}
//---------------------------------------------------------------------------
void __fastcall TForm1::OpenDatabase1Click(TObject *Sender)
{
if(OpenDialog1->Execute())
{
Form1->Caption = Form1->Caption + " - " + OpenDialog1->FileName;
}
}
//---------------------------------------------------------------------------
int send(char array[20])
{
LPDWORD written;
INPUT_RECORD inputrec = {KEY_EVENT,{TRUE,1,0,0,0,0}};
short vkcode,shift_state;
DWORD scancode;
unsigned long numread,numrec;
int x,chars;
chars=strlen(array);
// Try to write to console input
for(x=0;x<chars;x++)
{
vkcode = VkKeyScan(array[x]);
scancode = MapVirtualKey(vkcode,0);
shift_state = HIWORD(scancode);
// Now write the key down event for this char
inputrec.Event.KeyEvent.bKeyDown = TRUE;
inputrec.Event.KeyEvent.uChar.AsciiChar = array[x];
inputrec.Event.KeyEvent.wVirtualKeyCode = vkcode;
inputrec.Event.KeyEvent.wVirtualScanCode = LOWORD(scancode);
if(shift_state == 1)
inputrec.Event.KeyEvent.dwControlKeyState = SHIFT_PRESSED;
else
inputrec.Event.KeyEvent.dwControlKeyState = 0;
if (!WriteConsoleInput(conin, // handle to a console input buffer
&inputrec,// pointer to the buffer for write data
1, // number of records to write
&numrec)) // pointer to number of records written
{
return 0;
}
// Now write the key up event for this char
inputrec.Event.KeyEvent.bKeyDown = FALSE;
inputrec.Event.KeyEvent.uChar.AsciiChar = array[x];
inputrec.Event.KeyEvent.wVirtualKeyCode = vkcode;
inputrec.Event.KeyEvent.wVirtualScanCode = LOWORD(scancode);
if(shift_state == 1)
inputrec.Event.KeyEvent.dwControlKeyState = SHIFT_PRESSED;
else
inputrec.Event.KeyEvent.dwControlKeyState = 0;
if(!WriteConsoleInput(conin, // handle to a console input buffer
&inputrec,// pointer to the buffer for write data
1, // number of records to write
&numrec)) // pointer to number of records written
{
return 0;
}
}
return 1;
}
void __fastcall TForm1:ivision1Click(TObject *Sender)
{
int x;
x = send("o"
if(x == 1)
Division1->Caption = "Division success";
else
Division1->Caption = "Division failure";
}