From:	CSBVAX::MRGATE!WEIRAUCH@iravcl.ira.uka.de@SMTP 10-JAN-1988 23:57
To:	ARISIA::EVERHART
Subj:	RE: Getting DCL prompt within program


Received: from RELAY.CS.NET by KL.SRI.COM with TCP; Sun 10 Jan 88 20:10:34-PST
Received: from relay2.cs.net by RELAY.CS.NET id aa07664; 10 Jan 88 23:07 EST
Received: from ira.uka.de by RELAY.CS.NET id aa19459; 10 Jan 88 22:57 EST
Received: from iravcl by iraun1.ira.uka.de. id aa03833; 11 Jan 88 2:14 MET
Date: Mon, 11 Jan 88 02:14 MET
From: "Stefan Weirauch, IRA, Uni Karlsruhe" <WEIRAUCH%iravcl.ira.uka.de@RELAY.CS.NET>
Subject: RE: Getting DCL prompt within program
To: info-vax%kl.sri.com%ira.uka.de@RELAY.CS.NET
X-VMS-To: IN%"info-vax@kl.sri.com",WEIRAUCH

Maybe, this little goody is of general interest...

The Command procedure below creates two files:
GET_PROMPT.MAR and DO_CMD.PAS

First contains a procedure which passes your current DCL prompt string
to the calling program using any valid string descriptor.
It works fine on VMS 4.4, 4.5, 4.6 - not sure, where else...
Unfortunately the offsets into the CLI data region are not documented.
GET_PROMPT does not check whether the descriptor exist and can be accessed.
You might wish to add such checking part.

The example pascal program reads a line with that DCL prompt, and executes it
with lib$do_command - may be, you want to write a program, which takes that
line as password and if it is not correct makes the user think, the program
did nothing ? ;-)

Have fun.

Stefan
------------------------ cut here (ouch) --------------------------------
$!
$!      MAKE_GET_PROMPT.COM
$!
$! create files GET_PROMPT.MAR, DO_CMD.PAS
$! assemble/compile and link them to DO_CMD.EXE
$!
$create get_prompt.mar
        .TITLE  GET_PROMPT      gets prompt from cli-data-region
        .IDENT  /V01-001/

        .LINK   'SYS$SYSTEM:SYS.STB'/SELECTIVE_SEARCH

        .PSECT  DATA,NOEXE,WRT
STR_LEN:
        .BLKL   1

; ATTENTION !!! routine doesnt check parameter for existance or accessability

        .PSECT  CODE,EXE,NOWRT
        .ENTRY  GET_PROMPT,^M<>

        PUSHL   4(AP)                           ; addr. of result-desc.
        PUSHL   #CTL$AG_CLIDATA+^X274           ; address of prompt
        MOVZBL  @#<CTL$AG_CLIDATA+^X270>,STR_LEN; length of prompt + 3
        SUBB2   #3,STR_LEN
        PUSHAL  STR_LEN
        CALLS   #3,G^LIB$SCOPY_R_DX             ; pass result by descriptor
        RET

        .END
$ create do_cmd.pas
program do_command (input, output);

(* this program plays DCL, it shows your prompt and executes a DCL command *)

var   prompt : varying [80] of char;
      inline : varying [512] of char;

procedure get_prompt     ( var string     : varying [u] of char);extern;

procedure lib$get_input  ( var get_str    : varying [u] of char;
                               prompt_str : varying [v] of char);extern;

procedure lib$do_command (     cmd_txt    : varying [u] of char);extern;

begin
   get_prompt (prompt);
   lib$get_input (inline, prompt);
   lib$do_command (inline)
end.
$ macro get_prompt
$ pascal do_cmd
$ link/notraceback/nodebug do_cmd,get_prompt
$ exit
