| Hi there,
I've a problem when trying to call SMG$CREATE_SUBPROCESS from a
pascal image under VMS V5.0-2.
The pascal program compiles and links fine, but stack dumps when
it reaches the line:
ret_status := smg$create_subprocess(10);
The error that I get is:
%SYSTEM-F-ACCVIO, Access violation .....
%TRACE-F_TRACEBACK, symbolic stack dump follows ....
10 is a valid display id, and return status is of the correct type.
Before I run the program my BYTLM is about 25000, and PRCLM is 2.
Are these quotas high enough or is it worth bumping them up ? and
if that's isn't the problem what is ?
Thanks, in advance,
Rob
This note has also been entered in the SMG notes conference.
|
| Steve,
The 10, is the display-id, which is the identifier of the virtual
display with which the subprocess will be associated. As for the
nature of the passing, I've included the standard definitions:
[INHERIT(
'SYS$LIBRARY:STARLET',
'SYS$LIBRARY:pascal$smg_routines',
'SYS$LIBRARY:pascal$lib_routines')]
although one of these definitions SMG$create_menu is incorrect and
is not used.
Does this help ? Could it be another wrong definition ?
I've also tried using display-ids of other displays on the screen,
but to no avail.
Regards,
Rob
|
| Hi Rob,
what note -.2 was getting at is that if the parameter to the routine
specifies `pass by reference' then passing 10 as the parameter tells the
routine to
`look at memory location 10 for the display-id value'
10 is a reserved memory location (process memory space I think) so the memory
manager goes `can't access that location' or `access violation'!!
To pass a value by reference, put the value in a variable and then pass that
variable name. This will tell the routine that the address of the variable
(e.g. 0A345D67) contains the display-id (10).
In some programming languages (not sure about PASCAL), even a `pass by value'
(i.e. pass the value rather than the memory location of the value) requires
a permanent memory address for the value. Safest thing is to ALWAYS use
variables when talking to external routines or function.
Andy
(P.S. Run down on By Value, By Reference and By Descriptor differences
available if you want a quick chat)
|
| By default, Pascal passes arguments by reference.
Quote from the manual "Developing VAX Pascal Programs on the VAX/VMS System",
section 8.3, page 8-10
"By default VAX PASCAL uses the by reference mechanism to pass all
actual parameters except those that correspond to conformant parameters, in
which case the by descriptor mechanism is used."
This says effectively that anything other than an array will, by
default, be passed by reference. Thus, an argument of (10) will, by default, be
passed by reference and does not necessarily require an explicitly declared
variable. In case you're wondering how this is done, the Pascal (or any other
language) run-time system gets some heap storage (additional memory space) using
a mechanism such as lib$get_vm if necessary, stuffs the literal (10 in your
case) in there, and puts the address on the stack.
At first glance, it looks as if your environment file contains an
incorrect definition. If you have the source, you can check this for yourself.
If you don't, the only way to be sure is to use the debugger to examine the
call frame for the failing routine. If you don't know how to do this, come
and see me.
Don't get too hung up on this parameter passing business, however.
Remember that I said that its a common cause of your problem; it is not the
ONLY possible cause. When you get an access violation in user mode - with
only the last-chance condition handler established, the system will dump the
contents of two arrays on your terminal; the mechanism array and the signal
array. The contents of the signal array are likely to be initially the most
useful and can be interpreted for an ACCVIO as follows:
Longword # Contents Meaning
1 00000005 There are 5 more longwords in this array
2 0000000C Exception code (C = Access Violation)
3 Reason Mask Bit 0 = 1 = Length Violation caused
by instruction at saved PC
Bit 1 = 1 = Attempt to access a
"no access" page
Bit 2 = 1 = Write access
Bit 2 = 0 = Read Access
4 Virtual Adr Virtual address that the failing
instruction tried to reference
5 PC Virtual address of the failing
instruction
6 PSL Processor Status Longword contents
at the time of the exception.
Also, you should be aware that, although argument passing is the most
likely cause, and that the failing argument is probably in the most recent
call prior to the exception, even that latter fact is not guaranteed! You could
have a failing argument that was passed in a previous call and is only now
being used - such as a context variable for example. In other words, if you
used an incorrect mechanism to pass an argument in an earlier call, and the
routine that you called at that time simply read off the contents of the stack
and stored it away to be used in some reference at a later time, you would
only get the access violation at that later time - which may well be just after
you had made some other call, leading you to believe that it was the second
call that you made that was at fault!!!
Isn't life grand??
Steve
|