× The internal search function is temporarily non-functional. The current search engine is no longer viable and we are researching alternatives.
As a stop gap measure, we are using Google's custom search engine service.
If you know of an easy to use, open source, search engine ... please contact support@midrange.com.



Hello,

On 10/6/2010 7:17 PM, Alan Campin wrote:
I indicated in one of my previous posts how to reproduce the issue. If you
are in the same program and issue the error there it is not a problem.

For anyone who wants to see what Alan is describing, try the following *SRVPGM. It runs in the TRYAG2 activation group, and deliberately crashes (by sending an *ESCAPE message) -- as Alan describes, this will end the TRYAG2 activation group:

*> CRTRPGMOD TRYAG2 SRCFILE(QRPGLESRC) DBGVIEW(*LIST)
*> CRTSRVPGM TRYAG2 EXPORT(*ALL) ACTGRP(TRYAG2)
H NOMAIN
D TRYAG2 pr
P TRYAG2 b export

D QMHSNDPM PR ExtPgm('QMHSNDPM')
D MessageID 7A Const
D QualMsgF 20A Const
D MsgData 32767A Const options(*varsize)
D MsgDtaLen 10I 0 Const
D MsgType 10A Const
D CallStkEnt 10A Const
D CallStkCnt 10I 0 Const
D MessageKey 4A
D ErrorCode 8192A options(*varsize)

d MsgKey s 4a

d ErrorCode ds
d x 10i 0 inz(0)
d y 10i 0 inz(0)

/free
QMHSNDPM( 'CPF9897'
: 'QCPFMSG *LIBL'
: 'Test'
: 4
: '*ESCAPE'
: '*'
: 0
: MsgKey
: ErrorCode );
/end-free
P e

To see the problem this causes, call it from the following progam... this program runs in a different activation group (TRYAG1.) It calls the preceding service program, and catches the error when it crashes. It then tries to call it again, but this will fail with "Attempt made to reference to an object that no longer exists".

The reason it does this: When RPG called tryag2() the first time, the *SRVPGM was loaded, and a procedure pointer was found that points to the tryag2() procedure. When tryag2() crashed, however, the TRYAG2 activation group ended. When it tries to call it again, it's still trying to use the same pointer (which is no longer valid). What it _should_ do (IMHO) is reactivate the *SRVPGM, and use a new pointer... but it makes no attempt to do that, it just tries to call the old pointer, and fails:

*> CRTRPGMOD TRYAG1 SRCFILE(QRPGLESRC) DBGVIEW(*LIST)
*> CRTPGM TRYAG1 BNDSRVPGM(TRYAG2) ACTGRP(TRYAG1)
D tryag2 pr
/free
monitor;
tryag2();
on-error;
endmon;

tryag2();
*inlr = *on;
/end-free

You could solve the problem by reclaiming the TRYAG1 activation group (this'll cause the pointer to be reset), or by handling the procedure pointer logic manually in your program.

Or (and IMHO this is what Alan _should_ do) code TRYAG2 to catch all errors so that it never crashes.

Note that this error is a bit contrived... normally, you'd code a *SRVPGM with ACTGRP(*CALLER), and in that case, this would never happen.

As an Amazon Associate we earn from qualifying purchases.

This thread ...

Follow-Ups:
Replies:

Follow On AppleNews
Return to Archive home page | Return to MIDRANGE.COM home page

This mailing list archive is Copyright 1997-2024 by midrange.com and David Gibbs as a compilation work. Use of the archive is restricted to research of a business or technical nature. Any other uses are prohibited. Full details are available on our policy page. If you have questions about this, please contact [javascript protected email address].

Operating expenses for this site are earned using the Amazon Associate program and Google Adsense.