I am stuck on create new console window for my console application, for logger. That code works fine for GUI apps, but not work for console, and they require: CreateProcess function with the DETACHED_PROCESS flag.
Logger Log;
DWORD PiD;
void __stdcall LoggerCore(PVOID pVoid)
{
AllocConsole();
while(true)
{
SetConsoleTitleA(Log.LoggerTittle());
Sleep(5000);
}
_endthread();
}
char* Logger::LoggerTittle()
{
static char Tittle[55];
sprintf(Tittle, "Debug Logger");
return Tittle;
}
void Logger::LoggerInit()
{
CreateThread( 0 , 0 , (LPTHREAD_START_ROUTINE) LoggerCore , 0 , 0 , &PiD );
}
And that code, create a new console when app is GUI, and display "Log.ConsoleOutPut(1, c_Green,t_Default,"Debug Logger: SomeInfo");" in new console window. But all of that, not work for console application. So, how i can make a second console window in console application by using CreateProcess? Thanks for advice!
So, i am try to re-write it, but nothing... that is not works for me.
#include logger.h
char Message[1024];
Logger Log;
DWORD PiD;
/*
void __stdcall LoggerCore(PVOID pVoid)
{
AllocConsole();
while(true)
{
SetConsoleTitleA(Log.LoggerTittle());
Sleep(5000);
}
_endthread();
}
char* Logger::LoggerTittle()
{
static char Tittle[55];
sprintf(Tittle, "Debug Logger");
return Tittle;
}
*/
void Logger::LoggerInit()
{
SECURITY_ATTRIBUTES sa;
sa.nLength=sizeof(SECURITY_ATTRIBUTES);
sa.bInheritHandle=1;
sa.lpSecurityDescriptor=0;
SetHandleInformation(this->near_end,HANDLE_FLAG_INHERIT,0);
PROCESS_INFORMATION pi;
STARTUPINFO si;
ZeroMemory(&pi,sizeof(pi));
ZeroMemory(&si,sizeof(si));
si.cb=sizeof(STARTUPINFO);
si.dwFlags|=STARTF_USESTDHANDLES;
TCHAR program[]=TEXT("???");//need type something here.
TCHAR arguments[100];
if (!CreateProcess(program,arguments,0,0,1,CREATE_NEW_CONSOLE,0,0,&si,&pi))
printf( "CreateProcess failed (%d).\n", GetLastError() );
return;
// Wait until child process exits.
WaitForSingleObject( pi.hProcess, INFINITE );
this->process=pi.hProcess;
CloseHandle(pi.hThread);
// CreateThread( 0 , 0 , (LPTHREAD_START_ROUTINE) LoggerCore , 0 , 0 , &PiD );
}
void Logger::CheckProcent(char* message)
{
for (UINT i = 0; i <= strlen(message); i++)
{
if(message[i] == '%')
{
for(UINT j = strlen(message); j >= i; j--)
message[j+1] = message[j];
i++;
}
}
}
void Logger::ConsoleOutPut(int WOL, sColor Color, sLogType Type, const char* Format, ...)
{
SYSTEMTIME t;
GetLocalTime(&t);
DWORD dwBytesWritten;
HANDLE Handle = GetStdHandle(STD_OUTPUT_HANDLE);
HANDLE hStdin;
hStdin = GetStdHandle(STD_INPUT_HANDLE);
if (hStdin == INVALID_HANDLE_VALUE)
ExitProcess(1);
va_list pArguments;
va_start(pArguments, Format);
sprintf(Message,Format, pArguments);
CheckProcent(Message); // "%" Bug Fix
va_end(pArguments);
char currdate[11] = {0};
char outputmsg[2048];
if(WOL == 1)
{
sprintf(currdate, "(%02d:%02d:%02d)", t.wHour, t.wMinute, t.wSecond);
sprintf(outputmsg,"%s %s\n", currdate,Message);
}
else
sprintf(outputmsg,"%s\n", Message);
switch(Color)
{
case c_BoldGreen:
SetConsoleTextAttribute(this->Handle(FALSE),FOREGROUND_GREEN | FOREGROUND_INTENSITY | BACKGROUND_RED | BACKGROUND_INTENSITY);
break;
case c_BoldRed:
SetConsoleTextAttribute(this->Handle(FALSE),FOREGROUND_GREEN | FOREGROUND_INTENSITY | BACKGROUND_RED );
break;
case c_Red:
SetConsoleTextAttribute(this->Handle(FALSE),FOREGROUND_RED | FOREGROUND_INTENSITY);
break;
case c_Green:
SetConsoleTextAttribute(this->Handle(FALSE),FOREGROUND_GREEN | FOREGROUND_INTENSITY);
break;
case c_Blue:
SetConsoleTextAttribute(this->Handle(FALSE),FOREGROUND_BLUE | FOREGROUND_INTENSITY);
break;
case c_Cyan:
SetConsoleTextAttribute(this->Handle(FALSE),FOREGROUND_GREEN | FOREGROUND_BLUE | FOREGROUND_INTENSITY);
break;
case c_Yellow:
SetConsoleTextAttribute(this->Handle(FALSE),FOREGROUND_RED | FOREGROUND_GREEN | FOREGROUND_INTENSITY);
break;
case c_Magenta:
SetConsoleTextAttribute(this->Handle(FALSE),FOREGROUND_BLUE | FOREGROUND_RED | FOREGROUND_INTENSITY);
break;
case c_Grey:
SetConsoleTextAttribute(this->Handle(FALSE), FOREGROUND_RED | FOREGROUND_GREEN | FOREGROUND_BLUE | FOREGROUND_INTENSITY);
break;
}
CreateLog(Type,outputmsg);
WriteFile(this->Handle(FALSE), outputmsg, strlen(outputmsg), &dwBytesWritten, NULL);
SetConsoleTextAttribute(this->Handle(FALSE), FOREGROUND_RED | FOREGROUND_GREEN | FOREGROUND_BLUE);
return;
}
HANDLE Logger::Handle(BOOL Input)
{
if(Input==TRUE)
return GetStdHandle(STD_INPUT_HANDLE);
else
return GetStdHandle(STD_OUTPUT_HANDLE);
}
void Logger::CreateLog(sLogType Type,const char* Format, ...)
{
SYSTEMTIME now;
GetLocalTime(&now);
char ConsoleLog[55];
char CommandsLog[55];
char ErrorLog[55];
char Date[55];
char SqlLog[55];
char TestLog[55];
sprintf(Date, ".\\Logger\\%02d-%02d-%02d\\", now.wDay, now.wMonth, now.wYear);
CreateDirectory(Date,NULL);
sprintf(CommandsLog, ".\\Logger\\%02d-%02d-%02d\\Commands.log", now.wDay, now.wMonth, now.wYear);
sprintf(ConsoleLog, ".\\Logger\\%02d-%02d-%02d\\CONSOLE.log", now.wDay, now.wMonth, now.wYear);
sprintf(ErrorLog, ".\\Logger\\%02d-%02d-%02d\\Error.log", now.wDay, now.wMonth, now.wYear);
sprintf(SqlLog, ".\\Logger\\%02d-%02d-%02d\\Sql.log", now.wDay, now.wMonth, now.wYear);
sprintf(TestLog, ".\\Logger\\%02d-%02d-%02d\\Test.log", now.wDay, now.wMonth, now.wYear);
va_list pArguments1;
va_start(pArguments1, Format);
sprintf(Message,Format, pArguments1);
va_end(pArguments1);
switch (Type)
{
case t_NULL:
break;
case t_Error:
{
SaveFile(ErrorLog, Message);
}
break;
case t_Default:
{
SaveFile(ConsoleLog,Message);
}
break;
case t_COMMANDS:
{
SaveFile(ConsoleLog,Message);
SaveFile(CommandsLog,Message);
}
break;
case t_SQL:
{
SaveFile(ConsoleLog,Message);
SaveFile(SqlLog,Message);
}
break;
case t_TEST:
{
SaveFile(TestLog,Message);
}
break;
}
}
void Logger::SaveFile(char *logString,char *Message)
{
FILE *stream;
stream=fopen(logString, "a+" );
fprintf(stream, "%s", Message);
fclose(stream);
}
So, now my problem is - CreateProcess failed <2>, and when i am set TCHAR program[]=TEXT("application.exe"); - they launch many copies of that program, when i am set param in NULL - they return me <87> error... And they send logs to primary console window (app window).
CreateProcessfails, callGetLastError()to get error information. That will help you determine why it's failing.LoggerInit. You only want to call that one time in your application. If you want to send log information from one application to another, you need to set up some kind of interprocess communication like a named pipe.