Thread overview
Deactivate windows MessageBox dialog on exception
Aug 28, 2019
Andre Pany
Aug 28, 2019
a11e99z
Aug 28, 2019
a11e99z
Aug 28, 2019
Gregor Mückl
Aug 28, 2019
a11e99z
Aug 28, 2019
Gregor Mückl
Aug 28, 2019
Andre Pany
August 28, 2019
Hi,

I call another process using function pipeShell and Redirect.all.

In case the child process(also D application) throws an exception (str to int conversion exception), the child process shows a message box on windows.

I found the source code within DRuntime but I do not see a way to hide this MessageBox.

https://github.com/dlang/druntime/blob/25c8c1506183699758ca3bc323bb2a84a1d93f40/src/rt/dmain2.d#L644

I would like to have the exception text available in stdout or stderr of the pipe.
Why the exception isn't just written to the pipe?

(I do not want to implement a catch all in the source code of the child process).

The actual 2 D applications causing the dialog on windows: https://forum.dlang.org/post/usfmuabytdoludeuldts@forum.dlang.org

Kind regards
Andre
August 28, 2019
On Wednesday, 28 August 2019 at 12:19:54 UTC, Andre Pany wrote:
> Hi,
>
> I call another process using function pipeShell and Redirect.all.
>
> In case the child process(also D application) throws an exception (str to int conversion exception), the child process shows a message box on windows.
>

1) mother process "b" shouldn't terminates/close_pipes early than "a" cuz lines 690 checks stderr is valid, if no then MessageBox is showing.
2) if "a" is wrong or hang just terminate it, result already known.
3) also u can try redirect not all pipes just stdout/stdin, stderr for "a" probably will be working to mother console.
August 28, 2019
On Wednesday, 28 August 2019 at 12:19:54 UTC, Andre Pany wrote:
>

and try to use
https://docs.microsoft.com/en-us/windows/win32/api/errhandlingapi/nf-errhandlingapi-seterrormode     SEM_FAILCRITICALERRORS
for mother process and child process will inherit it


August 28, 2019
On Wednesday, 28 August 2019 at 12:19:54 UTC, Andre Pany wrote:
> Hi,
>
> I call another process using function pipeShell and Redirect.all.
>
> In case the child process(also D application) throws an exception (str to int conversion exception), the child process shows a message box on windows.
>
> I found the source code within DRuntime but I do not see a way to hide this MessageBox.
>
> https://github.com/dlang/druntime/blob/25c8c1506183699758ca3bc323bb2a84a1d93f40/src/rt/dmain2.d#L644
>
> I would like to have the exception text available in stdout or stderr of the pipe.
> Why the exception isn't just written to the pipe?
>
> (I do not want to implement a catch all in the source code of the child process).
>
> The actual 2 D applications causing the dialog on windows: https://forum.dlang.org/post/usfmuabytdoludeuldts@forum.dlang.org
>
> Kind regards
> Andre

The check in druntime could be changed to query the type of file handle that stdout/stderr point to. If they are a console or a file redirection, the error could be written there.

The following stack overflow question gives a possible test whether stdout/stderr exists: https://stackoverflow.com/questions/9021916/how-do-i-check-if-my-delphi-console-app-is-redirected-to-a-file-or-pipe

The documentation for GetStdHandle and GetFileType looks good, but I haven't tried it. I could probably write a quick proof of concept tonight.

An (IMO ugly) alternative would be to extend pipeShell/pipeProcess to launch the child process attached to a console on top of the redirects.

Gregor

August 28, 2019
On Wednesday, 28 August 2019 at 12:19:54 UTC, Andre Pany wrote:
> Hi,
>
> I call another process using function pipeShell and Redirect.all.
>

import std;

void main()
{
    auto p = pipeShell("a.exe", Redirect.all);
    p.stdin.writeln("e1");
    p.stdin.writeln("10");
    p.stdin.writeln("e2");
    p.stdin.writeln("9");

    p.stdin.flush();
    p.stdout.readln.writeln;

    import core.thread: Thread;
    import core.time: seconds;

    Thread.sleep(2.seconds);
    p.stdin.close;
    p.stderr.byLineCopy.writeln;
    Thread.sleep(1.seconds);
    try {
	p.pid.kill; // Windows exception here "Access denied"
    	p.pid.wait; // but no more MessageBox
    } catch (Throwable) { }
}

August 28, 2019
On Wednesday, 28 August 2019 at 13:15:14 UTC, a11e99z wrote:
> On Wednesday, 28 August 2019 at 12:19:54 UTC, Andre Pany wrote:
>> Hi,
>>
>> I call another process using function pipeShell and Redirect.all.
>>
>
> import std;
>
> void main()
> {
>     auto p = pipeShell("a.exe", Redirect.all);
>     p.stdin.writeln("e1");
>     p.stdin.writeln("10");
>     p.stdin.writeln("e2");
>     p.stdin.writeln("9");
>
>     p.stdin.flush();
>     p.stdout.readln.writeln;
>
>     import core.thread: Thread;
>     import core.time: seconds;
>
>     Thread.sleep(2.seconds);
>     p.stdin.close;
>     p.stderr.byLineCopy.writeln;
>     Thread.sleep(1.seconds);
>     try {
> 	p.pid.kill; // Windows exception here "Access denied"
>     	p.pid.wait; // but no more MessageBox
>     } catch (Throwable) { }
> }

This isn't the problem, is it? It's the D runtime throwing up a message box for an uncaught D exception if it doesn't get caught inside main() and there is no console attached.
August 28, 2019
On Wednesday, 28 August 2019 at 13:15:14 UTC, a11e99z wrote:
> On Wednesday, 28 August 2019 at 12:19:54 UTC, Andre Pany wrote:
>> Hi,
>>
>> I call another process using function pipeShell and Redirect.all.
>>
>
> import std;
>
> void main()
> {
>     auto p = pipeShell("a.exe", Redirect.all);
>     p.stdin.writeln("e1");
>     p.stdin.writeln("10");
>     p.stdin.writeln("e2");
>     p.stdin.writeln("9");
>
>     p.stdin.flush();
>     p.stdout.readln.writeln;
>
>     import core.thread: Thread;
>     import core.time: seconds;
>
>     Thread.sleep(2.seconds);
>     p.stdin.close;
>     p.stderr.byLineCopy.writeln;
>     Thread.sleep(1.seconds);
>     try {
> 	p.pid.kill; // Windows exception here "Access denied"
>     	p.pid.wait; // but no more MessageBox
>     } catch (Throwable) { }
> }

Thanks again. This solves my problem.

Kind regards
André