|
#include <windows.h>
#include <stdlib.h>
#include <iostream>
using namespace std;
#pragma comment(lib, "user32")
int main(int argc, char *argv[], char *envp[])
{
DWORD idThread;
MSG Msg;
if (argc == 2)
{
idThread = atoi(argv[1]);
if (!PostThreadMessage(idThread, WM_COMMAND, (WPARAM)0, (LPARAM)0))
cout << GetLastError() << " PostThreadMessage error\n";
return 0;
}
cout << GetCurrentThreadId() << " thread id\n";
while (GetMessage(&Msg, NULL, 0, WM_USER))
{
if (Msg.message == WM_COMMAND)
cout << "WM_COMMAND\n";
else
cout << "Message: " << Msg.message << endl;
}
return 0;
}
|
|
|
|
|
|
If you have access to the console app source code, and you go to the trouble of adding the message pump, you may as well add code to create a message-only window, no?
The difficult we do right away...
...the impossible takes slightly longer.
|
|
|
|
|
Hi Richard,
Richard Andrew x64 wrote: you may as well add code to create a message-only window, no?
It doesn't really matter to me how you decide to implement IPC between console applications. As Rajesh suggested you could use sockets, pipes or as Carlo Pallini suggested you could use STDIN/STDOUT/STDERR or as you suggested a hidden window or the option I have suggested; PostThreadMessage. It is great to have so many options put on the table.
Best Wishes,
-David Delaune
|
|
|
|
|
Yep, definitely not impossible (people get too used to the framework doing magic)... I think it's just a bit of a hassle more than anything else. Good job pointing this out!
|
|
|
|
|
It is not possible but you can cheat. Reverse engineer it.
Create a Windows app (win32 or MFC) and redirect messages to a console window.
But once you add a window, your app will no longer be a console app.
So it is still not possible.
See [this].
More reversed console apps [here] and [here].
|
|
|
|
|
Here is another example, to go along with Carlos'.
"One man's wage rise is another man's price increase." - Harold Wilson
"Fireproof doesn't mean the fire will never come. It means when the fire comes that you will be able to withstand it." - Michael Simmons
"Show me a community that obeys the Ten Commandments and I'll show you a less crowded prison system." - Anonymous
|
|
|
|
|
Hi,
I have gotten arount Most of the security challenges around the New Windows Model.
One issue remains a challenge. I created a derrived MFC Control: 'CMultiColumListBox', derived from MFC-'CListBox'. It in turn, is used as a Baseclass for various data tabulations. it all works to perfection under Win 95/98. Win NT, and Windows XP. With Vista and Windows 7, the Header Button listtakes up about 80% of the width of the CListbox Window, the Text Colums take up even Less.
One part of the creation process sets up the display Geometry parameters. I must have missed a Translation Somewhere.
The Salient part of the control that does this is as follows:-
BOOL CMultiColumListBox::RegisterControl(CDialog * pDialog)
{
if(!m_bDrawButtons)return TRUE;
ASSERT(pDialog->IsKindOf( RUNTIME_CLASS(CWnd) ) );
ASSERT(::IsWindow(pDialog->m_hWnd));
CDC* pDC=pDialog->GetDC();
ASSERT(pDC);
m_pParentDialog=pDialog;
CRect CtrlRect,DlgWndRect,DlgClientRect,BnRect;
GetWindowRect(&CtrlRect); pDialog->GetWindowRect(&DlgWndRect);
pDialog->GetClientRect(&DlgClientRect);
int BorderWidth=DlgWndRect.Width() - DlgClientRect.Width();
int TitleBarHeight=DlgWndRect.Height() -
DlgClientRect.Height()-BorderWidth;
BorderWidth/=2;
int Base_x,Base_y,BaseWidth;
Base_x=CtrlRect.left-1;
Base_y=CtrlRect.top;
BaseWidth=CtrlRect.Width();
for(int i=0;i<m_nNrOfColumns;i++){
CWnd* pWnd=pDialog->GetDlgItem(m_nColumList[i].n_ID);
ASSERT(pWnd);
pWnd->ShowWindow(SW_NORMAL);
int Width=m_nColumList[i].width;
if(i==m_nNrOfColumns-1)Width=BaseWidth;
if(Width>BaseWidth)Width=BaseWidth;
BnRect.left=Base_x-DlgWndRect.left-BorderWidth;
BnRect.right=Base_x+Width-DlgWndRect.left-BorderWidth;
BnRect.top=Base_y-m_nItemHeight*2-TitleBarHeight-DlgWndRect.top-1;
BnRect.bottom=Base_y-TitleBarHeight-DlgWndRect.top-1;
pWnd->MoveWindow(&BnRect); Base_x+=Width;
BaseWidth-=Width;
char* p=m_nColumList[i].lpcstrColumHeader;
if(p)pWnd->SetWindowText(p);
}
return TRUE;
}
This function would Typicaly be called from OnInitDialog()from the Dlg that contains it. It sets the Parameters for subsequent Drawing and Painting.
Any Idea about DlgToScreen() ScreenToDlg(),etc tha should have been used here
Bram van Kampen
|
|
|
|
|
i have a character arry in C
hello hi soidjosdc
kcopsdkcpok cjsdp
dskcoksdpc ocsdkcpd
i want to read it line by line and store it in another array....please help
|
|
|
|
|
please give any suggestions
|
|
|
|
|
Okay, I'll byte..
In essence, you have a string that you have to cut up into smaller pieces.
The cut-points are clearly defined - the string is to be cut at the end of each line of text.
So, we need
1) knowledge of the number of lines
2) memory to hold each of the lines
3) to copy each of the lines to the memory allocated in step 2.
Sooo, you'll need to know what your line-ending character(or sequence) is. You'll need to count the number of instances of the of line terminators, and for ease and simplicity, add 1 to this number - this is the number of lines you have - mLineCount.
You can then create an array of mLineCount elements of char*
You can then copy each line, storing the address of the new text into the appropriate array element.
Two functions you'll likely make use of are strdup and strtok. I advise you read the documentation for these two functions carefully, there are a few gotchas or things to watch for with strtok - Particularly, the fact that it modifies the input string. This precludes the use of the function on const char* strings.
For example, while the intention below is to split "some text" into two separate strings, it will fail since strtok can't modify myString.
char *myString = "some text", *delims = ",. ";
char *curToken;
curToken = strtok(myString, delims);
|
|
|
|
|
I and others already answered a similar query below. If you still don't understand string parsing then you need to spend a lot of time reading the MSDN documentation and sample code on the functions I recommended to you.
Unrequited desire is character building. OriginalGriff
I'm sitting here giving you a standing ovation - Len Goodman
|
|
|
|
|
You may hand-craft it, for instance:
#include <stdio.h>
#include <stdlib.h>
#include <assert.h>
int main()
{
int n, count;
int item, lastindex;
char ** b;
const char a[] = "hello hi soidjosdc\nkcopsdkcpok cjsdp\ndskcoksdpc ocsdkcpd";
const int LEN = sizeof(a);
for (n=0, count = 0; n<LEN; n++)
{
if (a[n] =='\n' || a[n] == '\0')
count++;
}
b = (char **) malloc( count * sizeof(char *));
assert(b);
for (n=0, item=0, lastindex = 0; n<LEN; n++)
{
if (a[n] =='\n' || a[n]=='\0')
{
int k, len;
len = n-lastindex;
b[item] = (char *) malloc(len+1);
assert(b[item]);
for (k=0; k<len;k++)
{
b[item][k] = a[lastindex+k];
}
b[item][k] = '\0';
lastindex = n+1;
item++;
}
}
for (item=0; item<count; item++)
{
printf("%s\n", b[item]);
}
for (item=0; item<count; item++)
{
free(b[item]);
}
free(b);
return 0;
}
If the Lord God Almighty had consulted me before embarking upon the Creation, I would have recommended something simpler.
-- Alfonso the Wise, 13th Century King of Castile.
This is going on my arrogant assumptions. You may have a superb reason why I'm completely wrong.
-- Iain Clarke
[My articles]
|
|
|
|
|
That's what I'm talkin' about.
I love your cruel avoidance of the simplifying (though functionality hiding) strdup and strtok.
|
|
|
|
|
enhzflep wrote: That's what I'm talkin' about.
In fact I just spoon-fed the OP with your method.
enhzflep wrote: I love your cruel avoidance of the simplifying (though functionality hiding) strdup and strtok.
Yes, that's my own departure: why should we use a function when we've the 'metal'?
If the Lord God Almighty had consulted me before embarking upon the Creation, I would have recommended something simpler.
-- Alfonso the Wise, 13th Century King of Castile.
This is going on my arrogant assumptions. You may have a superb reason why I'm completely wrong.
-- Iain Clarke
[My articles]
|
|
|
|
|
I want to run a do loop, for cosmetic purposes while WaitForSingleObjectEx is monitoring the ShellExecuteEx Thread.
I'm looking for something to grab onto, for the while statement to monitor, and then release to close the handle.
The hProcess !- NULL, is not working well, or I'm calling the code in the wrong order or something.
exit_Code = ShellExecuteEx(&lpExecInfo);
if (lpExecInfo.hProcess != NULL) {
DWORD iWait = WaitForSingleObjectEx(lpExecInfo.hProcess, INFINITE, TRUE);
int ndx = 0;
do {
ndx++;
} while ( lpExecInfo.hProcess !=NULL );*/
CloseHandle(lpExecInfo.hProcess);
|
|
|
|
|
Your loop is unnecessary. The call to WaitForSingleObjectEx() is going to block unitl the process you are monitoring is complete.
Chris Meech
I am Canadian. [heard in a local bar]
In theory there is no difference between theory and practice. In practice there is. [Yogi Berra]
posting about Crystal Reports here is like discussing gay marriage on a catholic church’s website.[Nishant Sivakumar]
|
|
|
|
|
Your right about that. It's one or the other.
|
|
|
|
|
Hi,
As Chris pointed out... by the time your do-while loop has started the processes will have ended. I would also recommend that you use CreateProcess rather than ShellExecute.
STARTUPINFO si;
PROCESS_INFORMATION pi;
memset(&si, 0, sizeof(si));
memset(&pi, 0, sizeof(pi));
si.cb = sizeof(si);
if(CreateProcess(lpApplicationpath,lpCommandline, NULL, NULL, FALSE, CREATE_DEFAULT_ERROR_MODE|NORMAL_PRIORITY_CLASS, 0, lpCurrentdirectory, &si, &pi))
{
int index = 0;
do
{
++index;
} while (WAIT_OBJECT_0 = WaitForSingleObject(pi.hProcess,10););
}
Best Wishes,
-David Delaune
|
|
|
|
|
The program takes 30 minutes to run, I'll give create process a whirl
|
|
|
|
|
Here's what I use
int CWelcomeWizardDlg::RunAppAndWait(char *cmd)
{
PROCESS_INFORMATION ProcInfo;
STARTUPINFO StartInfo;
int exit_status = 0;
memset(&StartInfo, 0, sizeof(StartInfo));
StartInfo.cb = sizeof(StartInfo);
if (CreateProcess(NULL, cmd, NULL, NULL, FALSE, 0, NULL, NULL, &StartInfo, &ProcInfo))
{
WaitForSingleObject(ProcInfo.hProcess, INFINITE);
GetExitCodeProcess(ProcInfo.hProcess, (unsigned long *)&exit_status);
CloseHandle(ProcInfo.hProcess);
CloseHandle(ProcInfo.hThread);
return exit_status;
}
return 1;
}
|
|
|
|
|
Thanks Chuck. Let's see what create process does.
|
|
|
|
|
And as Chuck will attest, put the waitforsingleobject into a seperate thread otherwise you risk blocking your windows messaging.
==============================
Nothing to say.
|
|
|
|
|
I tried Randor's Do Loop with WaitForSingleOject, but it didn't work out.
So I said heck with it, and changed the programs unattended mode to run automatic but visible.
Does the CloseHandle delete the memset, or do I have to do that manually?
|
|
|
|
|
jkirkerx wrote: I tried Randor's Do Loop with WaitForSingleOject, but it didn't work out.
What type of problem were you having? The do/while loop sample was given because that appeared to be what you were trying to accomplish in your original post.
jkirkerx wrote: Does the CloseHandle delete the memset, or do I have to do that manually?
The question does not make any sense. If you are referring to the variables si and pi in my code sample... they are local variables created on the stack and you do not need to perform any clean-up. The memset call is required because the STARTUPINFO struct needs to be initialized to zero to avoid passing garbage to the CreateProcess function. The only cleanup you would need to do is close the handles in the PROCESS_INFORMATION struct.
If you are looking for a complete function to copy and paste that will launch a process and wait for it to complete... the post by Chuck O'Toole will do just fine. Something tells me there is more your not telling us... but when I consult my magic 8 ball it says 'Ask again later'.
Best Wishes,
-David Delaune
|
|
|
|
|