0

I have a DCL script where I need to call a Perl function located in a Perl script. How do I do that and capture the output of that Perl function in the DCL script?

I know I can probably call the Perl script as follows:

$ perl my_perl_script.pl

But I want to call a specific function in a Perl module and be able to use the return value from that function in my DCL script.

Golam Kawsar
  • 760
  • 1
  • 8
  • 21

3 Answers3

1

The VMS::DCLsym module has been part of the Perl core distribution for many years and makes it easy to store the return value of a function (or anything else) in a DCL symbol. Here's an example:

$ perl -"MVMS::DCLsym" -e "$x = sprintf('0x%x', 99); VMS::DCLsym->setsym('X', $x, 'GLOBAL');"
$ show symbol x
  X == "0x63"

Also, by default, the %ENV hash is mapped to supervisor-mode process logical names, meaning they persist after Perl exits. So here's another way to leave something behind for the CLI when Perl exits:

$ perl -e "$ENV{'X'} = sprintf('0x%x', 99);"
$ show logical x
  "X" = "0x63" (LNM$PROCESS_TABLE)
$ x = f$trnlnm("X")
$ show symbol x
  X = "0x63"

If the only thing you want to pass back to DCL is an integer value, you can just exit Perl with that value and retrieve it from the $STATUS symbol that is always available in DCL:

$ perl -e "exit 99;"
$ show symbol $status
  $STATUS == "%X00000063"

But there are complications here, since the CLI will interpret that value as success (odd values) or failure (even values), in the latter case invoking any relevant warning or error handlers you have set up and attempting to retrieve message text, if there is any. In other words, exit statuses are expected to actually mean something to DCL, such as in this famous Easter Egg:

$ perl -e "exit 2928;"
%SYSTEM-W-FISH, my hovercraft is full of eels

You can suppress the printing of the message with the "vmsish 'hushed'" pragma, and while you're at it you'll want to also use the "vmsish 'exit'" pragma to prevent the mapping of 0 to a generic success value and 1 to a generic failure value, assuming those are in the range of numbers you might be returning. So that would look something like:

$ perl -e "use vmsish 'hushed','exit'; exit 2928;"
$ show symbol $status
  $STATUS == "%X10000B70"

Note that handlers may still be invoked for even-numbered exit values.

0

If it's a module and if you can access the shell with a system() function (or something similar), then you can just do

perl -MMy::Module -e 'My::Module->new->method;';echo $?

where My::Module is the name of your module and method is the name of the method that you want to call. The echo $? command (assuming that you're on a Linux/Unix system) will tell you the return value from the method call as received by the shell.

That's about as specific of an answer as you're going to get without posting your code.

0

There are a couple of possibilities that I can think of (never having actually done it before).

Write a Perl script to call the function and output the result to STDOUT. Then in DCL script, you could capture that output to a file and read it back in to use it. Alternatively, perhaps, capture the output via PIPE and handle it. Depends what the output is and what you want to do with it, I guess.

Alternatively, there appears to be some OpenVMS modules out there for Perl which allow you to get and set symbols. If you can locate one of these, then your Perl script can set a symbol to be used from that point on in the DCL command file.

I tend to favour the latter option.

I don't believe there is a way to call the Perl function directly from DCL - any more than there is a way to call a function from any other language at the DCL level.

ChrisB
  • 96
  • 2
  • Just noticed this http://stackoverflow.com/questions/4431757/how-to-assign-the-output-of-a-program-to-a-variable-in-a-dcl-com-script-on-vms which has a good example of how do do it in my first alternative. – ChrisB Mar 19 '12 at 01:36