[comp.os.vms] Getting DCL prompt within program

l_andenes%avh.unit.uninett@TOR.NTA.NO (Leiv Arild Andenes) (01/10/88)

Hi!
I wonder if anyone out there could tell me if there exists a system
(or Run Time Library) routine to get the DCL prompt string.

I know it can be accomplished in DCL as follows:

  $ prompt_string = F$Environment ("Prompt")

but I want to do it from inside a program (in my case, PASCAL).

Any suggestions?


+-------------------------------------+---------------------------------------+
| Leiv Arild Andenes,                 | Email:                                |
| University of Trondheim/AVH, Norway | l_andenes%avh.unit.uninett@TOR.nta.no |
+-------------------------------------+---------------------------------------+

WEIRAUCH@iravcl.ira.UKa.de ("Stefan Weirauch, IRA, Uni Karlsruhe") (01/11/88)

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

hydrovax@nmtsun.nmt.edu (M. Warner Losh) (01/13/88)

In article <248*l_andenes@avh.unit.uninett>, l_andenes%avh.unit.uninett@TOR.NTA.NO (Leiv Arild Andenes) writes:
> Hi!
> I wonder if anyone out there could tell me if there exists a system
> (or Run Time Library) routine to get the DCL prompt string.
> 

I would also like to know if there is a sanktioned interface to go
through.  Later in this article I give a method to "get the job done".
I posted a request just before Christmas, and haven't seen a single
responce.

Here is a small snipet of MACRO code that is a subroutine to SET the
prompt.  To set your prompt you need CMKRNL priv, but to read it, you
don't.


A brief explination of the code.  It gets the address of the cli data
space.  This is contained in the memory location CTL$AG_CLIDATA that
is defined SOMEWHERE (don't know exactly where).  Then it dereferences
the address with an offset of PPD$Q_CLIREG+4.  This address is places
into R3.  This gives the PRC block for the process.  Now then, the
prompt is contained in two parts.  The first part is it's length, that
is found in PRC_B_PROMPTLEN (offset from R3).  The actual text can be
no longer than 30 characters (in this implementation) and is contained
at the offset PRC_G_PROMPT.

I know that this explination is a bit scketchy, but I stole the code
from a DECUS tape a few years back (fall 1985 I think) and hacked it
so I could use it for a "SD" command that was written in 'C', that
intelligently set your prompt to the current directory.  So I don't
understand all of the implications of the code.

STANDARD DISCLAIMER ABOUT VMS 5.0 : this may break when you upgrade to
5.0, as it is using structures that I couldn't find in the Orange
Binders.  It may not even work at all.  It seems to work correctly on
VMS 4.4 on a VAXstation II.  There don't appear to be (at least to my
eye) any trojan activity going on.  If you find any, LET ME KNOW ASAP.

--------------*<---------------cut here------------>*------------------

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

	.PSECT	DATA RD, WRT, NOEXE, PIC, LONG

ARGS:	.LONG 2
	.ADDRESS LEN
	.ADDRESS BUFF_PTR_PTR
	            
LEN:	.BYTE 	0
BUFF_PTR_PTR: .LONG 0

	.PSECT	CODE RD,NOWRT,EXE,PIC,LONG

;
; Test.  A routine to attempt to set the prompt of the current process.
;
	LENGTH = 4
	NEWPRMT = 8

	.ENTRY NEW_PROMPT ^M<>
	MOVL	LENGTH(AP), LEN
	MOVL	NEWPRMT(AP), BUFF_PTR_PTR
	$CMKRNL_S ROUTIN=SET_PROMPT, ARGLST=ARGS
	$EXIT_S R0
	RET

	.ENTRY SET_PROMPT	^M<R3>
	PUSHR	#^M<R4, R5>
	MOVAB	G^CTL$AG_CLIDATA, R3		; Get cli data space.
	MOVL	PPD$Q_CLIREG+4(R3), R3		; Get address of proc work area
	MOVL	LENGTH(AP), R0			; New prompt length ptr.
	MOVB	(R0), R0			; New prompt length.
	ADDB3	#3, R0, PRC_B_PROMPTLEN(R3)	; Store new prompt length.
	MOVL	NEWPRMT(AP), R1			; Pointer to new prompt.
	MOVL	(R1), R1
	MOVC5	R0, (R1), #32, #32, PRC_G_PROMPT(R3) ; Store new prompt.
	POPR	#^M<R4, R5>
	MOVZWL	#SS$_NORMAL, R0			; Normal exit.
	RET

	.END
--------------*<---------------cut here------------>*------------------

-- 
bitnet:	lush@nmt.csnet			M. Warner Losh
csnet:	warner%hydrovax@nmtsun
uucp:	...{cmcl2, ihnp4}!lanl!unmvax!nmtsun!warner%hydrovax
	...{cmcl2, ihnp4}!lanl!unmvax!nmtsun!hydrovax
Warning:  Hydrovax is both a machine, and an account, so be careful.

u3369429@murdu.OZ (Michael Bednarek) (01/19/88)

In article <1223@nmtsun.nmt.edu> hydrovax@nmtsun.nmt.edu (M. Warner Losh) writes:
>In article <248*l_andenes@avh.unit.uninett>, l_andenes%avh.unit.uninett@TOR.NTA.NO (Leiv Arild Andenes) writes:
>> I wonder if anyone out there could tell me if there exists a system
>> (or Run Time Library) routine to get the DCL prompt string.
>I would also like to know if there is a sanktioned interface to go
>through.  Later in this article I give a method to "get the job done".
>I posted a request just before Christmas, and haven't seen a single
>responce.

In article <8801110532.AA06010@ucbvax.Berkeley.EDU>
WEIRAUCH@iravcl.ira.UKa.de ("Stefan Weirauch, IRA, Uni Karlsruhe")
gave a response.

:Maybe, this little goody is of general interest...
:GET_PROMPT.MAR and DO_CMD.PAS
: [...]
: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.

??? I can't see anything funny about the suggested use of these routines.

> [Explains the MACRO code to get/set the prompt. It needs CMKRNL to set,
>  and may break under future VMS releases.]
>
>so I could use it for a "SD" command that was written in 'C', that
>intelligently set your prompt to the current directory.

I know I'm a bit thick at times, and I'm biased towards DCL, but can
somebody explain why a program would want to change the prompt?
If God wanted programs to change prompts, He had given us `$SET_PROMPT', no?
As it is, we have `SET PROMPT'/ `F$ENVIRONMENT("PROMPT")'.
Why not use the tools He provided?
Why write a `SD' program when the same can be done in DCL?

>                             There don't appear to be (at least to my
>eye) any trojan activity going on.  If you find any, LET ME KNOW ASAP.

Well, think about Weirauch's comment:
:                      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 ? ;-)

Sounds pretty trojan to me.
However, remember that there are several ways to find out whether DCL or
a (simple) Trojan Horse is running:
    o The most obvious: press CTRL/T
    o Try up-arrow (command recall) more than once.
    o Try keys which were defined with `DEFINE/KEY'

Michael Bednarek		
Institute of Applied Economic and Social Research (IAESR)
Melbourne University, Parkville 3052, AUSTRALIA, Phone : +61 3 344 5744
Domain: u3369429@{murdu.oz.au | ucsvc.dn.mu.oz.au}  or  mb@munnari.oz.au
"bang": ...UUNET.UU.NET!munnari!{murdu.oz | ucsvc.dn.mu.oz}!u3369429

"POST NO BILLS."

j_torsmyr%avh.unit.uninett@TOR.NTA.NO (Jo Torsmyr) (01/21/88)

Thank you very much for the response. I want to use the DCL prompt in
a (pascal!) program which is an extension of the DCL recall command.

When you write           $ Recall 3
you get                  $ <some string>


I want to be able to do the same as RECALL.... :-)

I have called my command RETRIEVE, it is based upon an article in
VAX-PROFFESIONAL....

I would appriciate if anyone knows how get the promt in *pascal*!
The RETRIEVE command is installed at our site, and works ok.

                           Jo Torsmyr
                           Some kind of student...