Discussion:
SAVE/RETURN macros in AMODE 64
(too old to reply)
Michel Castelein
2005-09-16 18:28:21 UTC
Permalink
Girls and Boys,

In z/OS V1R3 and using HLASM R4, the following lines of assembler coding:
MAINPGM CSECT
MAINPGM AMODE 64
MAINPGM RMODE ANY
SYSSTATE AMODE64=YES <-- !!!
PROLOG SAVE (14,12)
expand into:
PROLOG DS 0H
STMG 14,12,8(13) <-- !!!
Cf. the Store Multiple "Grande" (STMG) instruction:
Seemingly, the SAVE macro assumes there is a caller-provided 144-byte Format
4 save area available to save the ENTIRE 64-bit contents of R14-R12.

1st question:
For a main program, the caller is the system (z/OS).
What kind of save area is supplied by z/OS V1R3 (and later)?
Is it still a traditional 72-byte "Format 0" save area or is it a new
144-byte Format 4 save area?
Or does the type of save area provided by z/0S depends upon the AMODE of the
(main) program?

In the same assembler source, i.e. still under control of SYSSTATE
AMODE64=YES, the macro call
RETURN (14,12),RC=0
expands into:
LMG 14,12,144(13) <-- !!!
LA 15,0(0,0)
BR 14
Cf. the Load Multiple "Grande" (LMG) instruction:
Seemingly, the RETURN macro also assumes the caller-provided save area to be
of type Format 4.

2nd question:
- The distance 144 used by LMG goes beyond the 144-byte save area!
- 144 happens to be the offset in a (208-byte) Format 5 area used to
save/restore the HIGH HALVES of R0-R15!
What point am I missing (or is it a bug)?

BTW, the LMG is the cause for a S0C4 with reason code 11. Not a surprise to
me.

The complete JCL is:
//ARCIS07X JOB 'HLASM',CLASS=A,MSGCLASS=X,COND=(0,NE),NOTIFY=&SYSUID
//STEP1 EXEC PROC=ASMACLG,PARM.C=ASA HLASM Release 4 - z/OS V1R3
//C.SYSIN DD *
MAINPGM CSECT
MAINPGM AMODE 64
MAINPGM RMODE ANY
SYSSTATE AMODE64=YES
PROLOG SAVE (14,12)
BALR R12,R0
USING *,R12
LA R11,SAVEAREA
ST R11,8(R13)
ST R13,SAVEAREA+4
LR R13,R11
*
EPILOG L R13,SAVEAREA+4
RETURN (14,12),RC=0
SAVEAREA DC 18F'0'
YREGS
END
/*
//L.SYSIN DD DUMMY

TIA for the response.

Michel
--------------------------------------------------
Michel Castelein - Arcis Services
MVS-OS/390-z/OS system engineer & instructor
arcisATadvalvasDOTbe
http://www.geocities.com/michelcastelein/
Steve Comstock
2005-09-16 19:41:17 UTC
Permalink
Michel Castelein wrote:
> Girls and Boys,
>
> In z/OS V1R3 and using HLASM R4, the following lines of assembler coding:
> MAINPGM CSECT
> MAINPGM AMODE 64
> MAINPGM RMODE ANY
> SYSSTATE AMODE64=YES <-- !!!
> PROLOG SAVE (14,12)
> expand into:
> PROLOG DS 0H
> STMG 14,12,8(13) <-- !!!

yes. so?

> Cf. the Store Multiple "Grande" (STMG) instruction:
> Seemingly, the SAVE macro assumes there is a caller-provided 144-byte Format
> 4 save area available to save the ENTIRE 64-bit contents of R14-R12.
>
> 1st question:
> For a main program, the caller is the system (z/OS).
> What kind of save area is supplied by z/OS V1R3 (and later)?
> Is it still a traditional 72-byte "Format 0" save area or is it a new
> 144-byte Format 4 save area?
> Or does the type of save area provided by z/0S depends upon the AMODE of the
> (main) program?

You get a 144-byte save area, regardless of the AMODE,
from z/OS V1R3 and later.

>
> In the same assembler source, i.e. still under control of SYSSTATE
> AMODE64=YES, the macro call
> RETURN (14,12),RC=0
> expands into:
> LMG 14,12,144(13) <-- !!!
> LA 15,0(0,0)
> BR 14
> Cf. the Load Multiple "Grande" (LMG) instruction:
> Seemingly, the RETURN macro also assumes the caller-provided save area to be
> of type Format 4.
>
> 2nd question:
> - The distance 144 used by LMG goes beyond the 144-byte save area!
> - 144 happens to be the offset in a (208-byte) Format 5 area used to
> save/restore the HIGH HALVES of R0-R15!
> What point am I missing (or is it a bug)?
>
> BTW, the LMG is the cause for a S0C4 with reason code 11. Not a surprise to
> me.


see comments below
>
> The complete JCL is:
> //ARCIS07X JOB 'HLASM',CLASS=A,MSGCLASS=X,COND=(0,NE),NOTIFY=&SYSUID
> //STEP1 EXEC PROC=ASMACLG,PARM.C=ASA HLASM Release 4 - z/OS V1R3
> //C.SYSIN DD *
> MAINPGM CSECT
> MAINPGM AMODE 64
> MAINPGM RMODE ANY
> SYSSTATE AMODE64=YES
> PROLOG SAVE (14,12)
> BALR R12,R0
> USING *,R12
> LA R11,SAVEAREA
> ST R11,8(R13)
> ST R13,SAVEAREA+4
> LR R13,R11
> *
> EPILOG L R13,SAVEAREA+4
> RETURN (14,12),RC=0
> SAVEAREA DC 18F'0'
> YREGS
> END
> /*
> //L.SYSIN DD DUMMY

Wait.

1. Why are you using BALR / USING? When you
are entered in in AMOD64, you _must_
user LARL to get your base address

2. Forward and backward chaining are
different if you will be working
in AMODE64 - the 144-byte layout
has different displacements for the
forward and backward pointers.

Try this:

TEST64 CSECT
TEST64 AMODE 64
TEST64 RMODE ANY
SYSSTATE AMODE64=YES
PROLOG SAVE (14,12)
LARL R12,TEST64
USING *,R12
LA R11,SAVEAREA point to my savearea
STG R11,136(R13) save in calling pgm's savearea
STG R13,SAVEAREA+128 save z/os's save area pointer
LGR R13,R11 establish my save area
*
EPILOG LG R13,SAVEAREA+128 pick up z/OS's save area pointer
RETURN (14,12),RC=0 return
SAVEAREA DC 18FD'0'
YREGS
END


<ad>
All this and a lot more is discussed in our
three day course "z/OS Assembler for Applications
Programmers". New hardware instructions, new
operating system linkages, and so on.

Currently reflects all except new z9 instructions
(no POPs yet) and the latest z/OS 1.7 (not much
there, I don't think, but have not had time to
add yet). So we include z990 instructions and
z/OS 1.6 info.

details at:
http://www.trainersfriend.com/Assembler_%20courses/C500descrpt.htm
</ad>

Kind regards,

-Steve Comstock
Edward E. Jaffe
2005-09-16 20:51:59 UTC
Permalink
Steve Comstock wrote:

> LARL R12,TEST64
> USING *,R12


Ignoring the fact that the above USING is wrong, 64-bit programs are
intended to use relative addressing. Thus, the base register would
normally cover constants and literals only (for reentrant code) and the
work area (for non-reentrant code). That is, under normal circumstances,
the LARL would not point to the start of the program. I believe these
examples may be somewhat more typical:

Reentrant code:
| LARL R12,TEST64_Const Point to constants area
| USING TEST64_Const,R12 Synchronize base register
| STORAGE OBTAIN, Acquire the work area
| LENGTH=WKAREA_LEN Acquire work area
| STG R1,136(,R13) Chain save areas
| STG R13,128(,R1) (same)
| LGR R13,R1 Get area address in R13
| USING WKAREA,R13 Synchronize WKAREA
| .
| .
| CNOP 0,8 Align to doubleword
|TEST64_Const DC 0D Begin constants area
| .
| .
| LTORG , Define literals
|
|WKAREA DSECT , Program work area DSECT
| DS 18D Program save area
| .
| .
|WKAREA_LEN EQU *-WKAREA Length of work area


Non-reentrant code:
| LARL R1,TEST64_Const Point to constants area
| STG R1,136(,R13) Chain save areas
| STG R13,128(,R1) (same)
| LGR R13,R1 Get area address in R13
| USING TEST64_Const,R13 Synchronize base register
| .
| .
| CNOP 0,8 Align to doubleword
|TEST64_Const DC 0D Begin constants area
| DC 18D'0' Define program save area
| .
| .
| LTORG , Define literals

--
-----------------------------------------------------------------
| Edward E. Jaffe | |
| Mgr, Research & Development | ***@phoenixsoftware.com |
| Phoenix Software International | Tel: (310) 338-0400 x318 |
| 5200 W Century Blvd, Suite 800 | Fax: (310) 338-0801 |
| Los Angeles, CA 90045 | http://www.phoenixsoftware.com |
-----------------------------------------------------------------
Steve Comstock
2005-09-16 21:00:26 UTC
Permalink
Edward E. Jaffe wrote:
> Steve Comstock wrote:
>
>> LARL R12,TEST64
>> USING *,R12
>
>
>
> Ignoring the fact that the above USING is wrong, 64-bit programs are
> intended to use relative addressing. Thus, the base register would
> normally cover constants and literals only (for reentrant code) and the
> work area (for non-reentrant code). That is, under normal circumstances,
> the LARL would not point to the start of the program. I believe these
> examples may be somewhat more typical:
>
> Reentrant code:
> | LARL R12,TEST64_Const Point to constants area
> | USING TEST64_Const,R12 Synchronize base register
> | STORAGE OBTAIN, Acquire the work area
> | LENGTH=WKAREA_LEN Acquire work area
> | STG R1,136(,R13) Chain save areas
> | STG R13,128(,R1) (same)
> | LGR R13,R1 Get area address in R13
> | USING WKAREA,R13 Synchronize WKAREA
> | .
> | .
> | CNOP 0,8 Align to doubleword
> |TEST64_Const DC 0D Begin constants area
> | .
> | .
> | LTORG , Define literals
> |
> |WKAREA DSECT , Program work area DSECT
> | DS 18D Program save area
> | .
> | .
> |WKAREA_LEN EQU *-WKAREA Length of work area
>
>
> Non-reentrant code:
> | LARL R1,TEST64_Const Point to constants area
> | STG R1,136(,R13) Chain save areas
> | STG R13,128(,R1) (same)
> | LGR R13,R1 Get area address in R13
> | USING TEST64_Const,R13 Synchronize base register
> | .
> | .
> | CNOP 0,8 Align to doubleword
> |TEST64_Const DC 0D Begin constants area
> | DC 18D'0' Define program save area
> | .
> | .
> | LTORG , Define literals


Well, good point. But I focus on using the relative addressing
approach in other places. Just trying to respond to the OP
(but blew it with the USING). Otherwise, there was no
context in his example to tell us what was needed.

[BTW, I thought you only coded reentrant code these days?]

Kind regards,

-Steve
Edward E. Jaffe
2005-09-16 19:38:01 UTC
Permalink
Michel Castelein wrote:

>In z/OS V1R3 and using HLASM R4, the following lines of assembler coding:
> MAINPGM CSECT
> MAINPGM AMODE 64
> MAINPGM RMODE ANY
>
>

FYI. RMODE ANY is deprecated. RMODE 31 is all the rage now!
[snip]

>1st question:
>For a main program, the caller is the system (z/OS).
>What kind of save area is supplied by z/OS V1R3 (and later)?
>Is it still a traditional 72-byte "Format 0" save area or is it a new
>144-byte Format 4 save area?
>Or does the type of save area provided by z/0S depends upon the AMODE of the
>(main) program?
>
>

Depends on program AMODE. Simply follow the recommendations in
http://publibz.boulder.ibm.com/cgi-bin/bookmgr_OS390/BOOKS/IEA2A640/2.1

>2nd question:
>- The distance 144 used by LMG goes beyond the 144-byte save area!
>- 144 happens to be the offset in a (208-byte) Format 5 area used to
>save/restore the HIGH HALVES of R0-R15!
>What point am I missing (or is it a bug)?
>
>

Something is wrong. When I assemble here, I get:

|Stmt Source Statement
| 1 GTEST CSECT ,
| 2 GTEST AMODE 64
| 3 GTEST RMODE 31
| 4 SYSSTATE AMODE64=YES
| 5+* THE VALUE OF SYSSTATE IS NOW SET TO ...
| + VL=2 OSREL=00000000
| 6 SAVE (14,12)
| 8+ DS 0H
| 9+ STMG 14,12,8(13)
| 10 RETURN (14,12),RC=0
| 12+ LMG 14,12,8(13)
| 13+ LA 15,0(0,0)
| 14+ BR 14
| 15 END ,

--
-----------------------------------------------------------------
| Edward E. Jaffe | |
| Mgr, Research & Development | ***@phoenixsoftware.com |
| Phoenix Software International | Tel: (310) 338-0400 x318 |
| 5200 W Century Blvd, Suite 800 | Fax: (310) 338-0801 |
| Los Angeles, CA 90045 | http://www.phoenixsoftware.com |
-----------------------------------------------------------------
McKown, John
2005-09-16 19:54:32 UTC
Permalink
> -----Original Message-----

<snip>

> Try this:
>
> TEST64 CSECT
> TEST64 AMODE 64
> TEST64 RMODE ANY
> SYSSTATE AMODE64=YES
> PROLOG SAVE (14,12)
> LARL R12,TEST64
> USING *,R12

You sure of this instruction? Shouldn't it be
USING TEST64,R12

<snip>

>
> Kind regards,
>
> -Steve Comstock
>

--
John McKown
Senior Systems Programmer
UICI Insurance Center
Information Technology

This message (including any attachments) contains confidential
information intended for a specific individual and purpose, and its'
content is protected by law. If you are not the intended recipient, you
should delete this message and are hereby notified that any disclosure,
copying, or distribution of this transmission, or taking any action
based on it, is strictly prohibited.
Steve Comstock
2005-09-16 20:13:05 UTC
Permalink
McKown, John wrote:
>>-----Original Message-----
>
>
> <snip>
>
>>Try this:
>>
>>TEST64 CSECT
>>TEST64 AMODE 64
>>TEST64 RMODE ANY
>> SYSSTATE AMODE64=YES
>>PROLOG SAVE (14,12)
>> LARL R12,TEST64
>> USING *,R12
>
>
> You sure of this instruction? Shouldn't it be
> USING TEST64,R12
>
> <snip>
>
>
You're right. I moved too fast.

correct code:

TEST64 CSECT
TEST64 AMODE 64
TEST64 RMODE ANY
SYSSTATE AMODE64=YES
PROLOG SAVE (14,12)
LARL R12,TEST64
USING TEST64,R12
LA R11,SAVEAREA point to my savearea
STG R11,136(R13) save in calling pgm's savearea
STG R13,SAVEAREA+128 save z/os's save area pointer
LGR R13,R11 establish my save area
*
EPILOG LG R13,SAVEAREA+128 pick up z/OS's save area pointer
RETURN (14,12),RC=0 return
SAVEAREA DC 18FD'0'
YREGS
END

The previous version compiled, bound, and ran OK; of
course it didn't do anything and I didn't notice.

The above version follows the conventions we teach
in our course.

Good eye.

Kind regards,

-Steve Comstock
john gilmore
2005-09-16 21:12:47 UTC
Permalink
I think it was public-spirited of Ed to provide a non-reentrant example too.
I would not have bothered to do so, in part at least because I'm not sure
I want people who write non-reentrant code using AMODE(64) just yet.

John Gilmore
Ashland, MA 01721
USA





>From: Steve Comstock <***@trainersfriend.com>
>Reply-To: IBM Mainframe Assembler List <ASSEMBLER-***@listserv.uga.edu>
>To: ASSEMBLER-***@LISTSERV.UGA.EDU
>Subject: Re: SAVE/RETURN macros in AMODE 64
>Date: Fri, 16 Sep 2005 15:00:26 -0600
>
>Edward E. Jaffe wrote:
>>Steve Comstock wrote:
>>
>>> LARL R12,TEST64
>>> USING *,R12
>>
>>
>>
>>Ignoring the fact that the above USING is wrong, 64-bit programs are
>>intended to use relative addressing. Thus, the base register would
>>normally cover constants and literals only (for reentrant code) and the
>>work area (for non-reentrant code). That is, under normal circumstances,
>>the LARL would not point to the start of the program. I believe these
>>examples may be somewhat more typical:
>>
>>Reentrant code:
>>| LARL R12,TEST64_Const Point to constants area
>>| USING TEST64_Const,R12 Synchronize base register
>>| STORAGE OBTAIN, Acquire the work area
>>| LENGTH=WKAREA_LEN Acquire work area
>>| STG R1,136(,R13) Chain save areas
>>| STG R13,128(,R1) (same)
>>| LGR R13,R1 Get area address in R13
>>| USING WKAREA,R13 Synchronize WKAREA
>>| .
>>| .
>>| CNOP 0,8 Align to doubleword
>>|TEST64_Const DC 0D Begin constants area
>>| .
>>| .
>>| LTORG , Define literals
>>|
>>|WKAREA DSECT , Program work area DSECT
>>| DS 18D Program save area
>>| .
>>| .
>>|WKAREA_LEN EQU *-WKAREA Length of work area
>>
>>
>>Non-reentrant code:
>>| LARL R1,TEST64_Const Point to constants area
>>| STG R1,136(,R13) Chain save areas
>>| STG R13,128(,R1) (same)
>>| LGR R13,R1 Get area address in R13
>>| USING TEST64_Const,R13 Synchronize base register
>>| .
>>| .
>>| CNOP 0,8 Align to doubleword
>>|TEST64_Const DC 0D Begin constants area
>>| DC 18D'0' Define program save area
>>| .
>>| .
>>| LTORG , Define literals
>
>
>Well, good point. But I focus on using the relative addressing
>approach in other places. Just trying to respond to the OP
>(but blew it with the USING). Otherwise, there was no
>context in his example to tell us what was needed.
>
>[BTW, I thought you only coded reentrant code these days?]
>
>Kind regards,
>
>-Steve

_________________________________________________________________
Express yourself instantly with MSN Messenger! Download today - it's FREE!
http://messenger.msn.click-url.com/go/onm00200471ave/direct/01/
Edward E. Jaffe
2005-09-16 21:24:09 UTC
Permalink
Schiradin,Roland HG-Dir itb-db/dc wrote:

>Yep I agree with the so called baseless programming
>but instead of "hardcoded" offsets I would use
>SYS1.MACLIB(IHASAVER). Also not all engine understand LARL
>while
> BRAS R6,*+8
> DC A(STATIC_AREA)
> L R6,0(R6,0)
> USING STATIC_AREA,R6 Addressebility
>
>works for me.
>
>

Agreed. IHASAVER would have made for a better example.

Re: your other point, the program in question is AMODE(64). That
guarantees LARL hardware support is available.

--
-----------------------------------------------------------------
| Edward E. Jaffe | |
| Mgr, Research & Development | ***@phoenixsoftware.com |
| Phoenix Software International | Tel: (310) 338-0400 x318 |
| 5200 W Century Blvd, Suite 800 | Fax: (310) 338-0801 |
| Los Angeles, CA 90045 | http://www.phoenixsoftware.com |
-----------------------------------------------------------------
Edward E. Jaffe
2005-09-16 22:42:25 UTC
Permalink
Edward E. Jaffe wrote:

> Agreed. IHASAVER would have made for a better example.


In addition, the examples:
1) Should initialize SAVF4SAID in the save area to =C'F4SA'.
2) Do not need the CNOP 0,8 assembler instructions.

--
-----------------------------------------------------------------
| Edward E. Jaffe | |
| Mgr, Research & Development | ***@phoenixsoftware.com |
| Phoenix Software International | Tel: (310) 338-0400 x318 |
| 5200 W Century Blvd, Suite 800 | Fax: (310) 338-0801 |
| Los Angeles, CA 90045 | http://www.phoenixsoftware.com |
-----------------------------------------------------------------
Loading...