5
$\begingroup$

I have a long loop in a C WSTP process, within which I intermittently check for abort messages sent by the front-end:

void checkIfUserAborted() {
  
    if (WSMessageReady(stdlink)) {

        int code, arg;
        WSGetMessage(stdlink, &code, &arg);

        if (code == WSTerminateMessage || code == WSInterruptMessage || 
            code == WSAbortMessage     || code == WSImDyingMessage) {
                
            // throw error
        }
    }
}
void myWSTPFunc() {

    try {

        for (big loop) {

            checkIfUserAborted();

            // do task
        }

    } catch ... {

        // handle abort
    }
}

This code was adapted from this great but very outdated doc, which uses the defunct MLAbort (for which the replacement WSAbort somehow went missing). This code previously worked in version 11 of Mathematica on MacOS, allowing me to detect and handle the abort during myWSTPFunc(), as invoked by the user clicking Evaluation > Abort Evaluation in their notebook.

As of Mathematica v13 however, this process no longer works. Invoking Evaluation > Abort Evaluation no longer triggers a WSAbortMessage discoverable by checkIfUserAborted().

I managed to get LinkSnooper working as per this post, but all it logs during my abort invocation is

****** Message FE ---> K:  on Main: 3

I hence have two questions:

  • How can I use LinkSnooper to see the specific message my Abort induced?
  • Is there an updated way to listen for aborts in WSTP? Is LinkInterrupt relevant?
$\endgroup$
7
  • $\begingroup$ Can you show a complete minimal example where checking MLAbort does not work? $\endgroup$
    – Szabolcs
    Jul 22, 2022 at 7:16
  • $\begingroup$ ML-named functions are not "defunct". They work fine, and should be completely equivalent to the WS-ones. If there is any difference whatsoever, it's a bug and you should report it to Wolfram. $\endgroup$
    – Szabolcs
    Jul 22, 2022 at 7:18
  • $\begingroup$ @Szabolcs MLAbort is undefined, and WSAbort is undeclared. It doesn't get more defunct than that. $\endgroup$
    – Anti Earth
    Jul 26, 2022 at 0:11
  • $\begingroup$ MLAbort works perfectly fine here. $\endgroup$
    – Szabolcs
    Jul 26, 2022 at 6:04
  • $\begingroup$ Can you show a complete minimal example that demonstrates that MLAbort and WSAbort do not work? $\endgroup$
    – Szabolcs
    Jul 26, 2022 at 6:09

1 Answer 1

3
+25
$\begingroup$

I looked into this and it seems that there are two situations we need to distinguish: writing an installable MathLink program or setting up the communication loop manually.

First, ML and WS functions should behave equivalently, you just need to make sure that you consistently stick to either the ML versions or the WS versions throughout your program. In this answer I will use the ML names.

Installable MathLink program

MLAbort is only available when you are writing an installable MathLink program. In this case you will have a .tm template file which is translated to C code with mprep. It is in the output of mprep that MLAbort is defined (although it is declared in mathlink.h). This code needs to be compiled and linked into your executable, otherwise you will see a linker error that MLAbort is not found.

Manual communication

If you are writing your own main loop to communicate through a MathLink connection, you can emulate what is done in installable MathLink programs, and set up your own MLAbort. It seems that this is done by setting up a message handler, like so:

int MLAbort = 0;

...

void MLDefaultHandler( MLINK mlp, int message, int n)
{
    switch (message){
    case MLTerminateMessage:
        MLDone = 1;
    case MLInterruptMessage:
    case MLAbortMessage:
        MLAbort = 1;
    default:
        return;
    }
}

Then the message handler is registered using MLSetMessageHandler(mlp, MLDefaultHandler);

I am assuming that the message handler will be called from a parallel thread, thus in your main code you will be able to simply use if (MLAbort) ... as usual, without needing to worry about MLAbort getting updated in a timely manner.

Note that the above code was copied directly from the source file generated by mprep and contains other details not relevant to the question such as MLDone.

If you set up your own communication loop, it would be a good idea to look carefully at how this works in installable MathLink programs (the output of mprep) as the documentation is rather sparse on this. So far I have not had the need to do this.

$\endgroup$
2
  • $\begingroup$ I am creating an installable ML program using a template file compiled with mprep, and I am not writing my own main loop. The project is QuESTlink and my message-checking workaround to the undefined MLAbort is viewable here, though which no longer works. What OS and Mathematica version provide your mprep and wstp.h? $\endgroup$
    – Anti Earth
    Jul 27, 2022 at 0:07
  • $\begingroup$ (I can also confirm that the C file output by mprep of the templates file contains no definitions of either MLAbort nor WSAbort) $\endgroup$
    – Anti Earth
    Jul 27, 2022 at 0:51

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.