Rational Developer for System z
PL/I for Windows, Version 8.0, プログラミング・ガイド

パラメーターの受け渡し例

以下の例は、わかりやすく例示するためにのみ記載されたものであり、最適化されていません。これらの例では、ユーザーがアセンブラーのプログラミングに習熟している ことが前提になっています。各例では、スタックはページの下方へ伸びていきます。また、ESP は常に、スタックの上部を指します。

規格合致パラメーターのルーチンへの受け渡し

以下の例は、関数 FUNC1 に対する呼び出しのときの、コード・シーケンスおよびスタックの図を示しています。このプログラムは、PREFIX(NOFIXEDOVERFLOW) オプションでコンパイルされることが前提になっています。

 dcl func1 entry( char(1),
                  fixed bin(15),
                  fixed bin(31),
                  fixed bin(31) )
     returns( fixed bin(31) )
     options( byvalue nodescriptor );

 dcl x fixed bin(15);
 dcl y fixed bin(31);

 y = func1('A', x, y+x, y);

caller's Code Up Until Call:

              PUSH     y           ; Push p4 onto the 80386 stack
              SUB      ESP, 12     ; Allocate stack space for
                                   ;  register parameters
              MOV      AL, 'A'     ; Put p1 into AL
              MOV      DX,  x      ; Put p2 into DX
              MOVSX    ECX, DX     ; Sign-extend x to long
              ADD      ECX, y      ; Calculate p3 and put it into ECX
              CALL     FUNC1       ; Make call

             呼び出し直後のスタック          呼び出し直後のレジスター設定

            ・                        ・          *--------------------*
            |   呼び出し側の Local    |      EAX  |      未定義   | p1 |
            *-------------------------*           *--------------------*
            |        p4               |      EBX  |   呼び出し側の EBX |
            *-------------------------*           *--------------------*
            | p3 のブランク・スロット |      ECX  |        p3     |    |
            *-------------------------*           *--------------------*
            | p2 のブランク・スロット |      EDX  |   未定義 |    p2   |
            *-------------------------*           *--------------------*
            | p1 のブランク・スロット |      EDI  |   呼び出し側の EDI |
            *-------------------------*           *--------------------*
            |  呼び出し側の EIP       |      ESI  |   呼び出し側の ESI |
 ESP -->    *-------------------------*           *--------------------*

callee's Prolog Code:

            PUSH     EBP                      ; Save caller's EBP
            MOV      EBP, ESP                 ; Set up callee's EBP
            SUB      ESP, callee's local size ; Allocate callee's Local
            PUSH     EBX                      ; Save preserved registers -
            PUSH     EDI                      ;  will optimize to save
            PUSH     ESI                      ;  only registers callee uses

             
                Prolog 後のスタック           Prolog 後のレジスター設定

             ・                       ・          *--------------------*
             |  呼び出し側の Local    |       EAX |      未定義   | p1 |
             *------------------------*           *--------------------*
             |        p4              |       EBX |      未定義        |
             *------------------------*           *--------------------*
             | p3 のブランク・スロット|       ECX |          p3        |
             *------------------------*           *--------------------*
             | p2 のブランク・スロット|       EDX |未定義    |   p2    |
             *------------------------*           *--------------------*
             | p1 のブランク・スロット|       EDI |      未定義        |
             *------------------------*           *--------------------*
             |   呼び出し側の EIP     |       ESI |      未定義        |
             *------------------------*           *--------------------*
             |   呼び出し側の EBP     |
             *------------------------*       レジスター EBX、EDI、および
             |                        |       ESI における「未定義」と
             .                        .       いう用語は、FUNC1 のコード
             .  呼び出し側の Local    .       で安全に上書きできることを
             .                        .       意味します。
             |                        | 
             *------------------------*
             |     保管 EBX           |
             *------------------------*
             |     保管 EDI           |
             *------------------------|
             |     保管 ESI           |
  ESP -->    *------------------------*

callee's Epilog Code:

              MOV       EAX, RetVal ; Put return value in EAX
              POP       ESI         ; Restore preserved registers
              POP       EDI
              POP       EBX
              MOV       ESP, EBP    ; Deallocate callee's local
              POP       EBP         ; Restore caller's EBP
              RET                   ; Return to caller

                 Epilog 後のスタック           Epilog 後のレジスター設定

             ・                        ・           *------------------*
             | 呼び出し側の Local      |       EAX  |     戻り値       |
             *-------------------------*            *------------------*
             |        p4               |       EBX  | 呼び出し側の EBX |
             *-------------------------*            *------------------*
             | p3 のブランク・スロット |       ECX  |     未定義       |
             *-------------------------*            *------------------*
             | p2 のブランク・スロット |       EDX  |     未定義       |
             *-------------------------*            *------------------*
             | p1 のブランク・スロット |       EDI  | 呼び出し側の EDI |
             |                         |            *------------------*
 ESP -->     *-------------------------*       ESI  | 呼び出し側の ESI |
                                                    *------------------*

caller's Code Just After Call:

              ADD      ESP, 16      ; Remove parameters from stack
              MOV      y,   EAX     ; Use return value.

              クリーンアップ後のスタック    クリーンアップ後のレジスター設定

               ・                   ・             *------------------*
               | 呼び出し側の Local |        EAX  |     戻り値      |
   ESP -->     *--------------------*              *------------------*
                                              EBX  | 呼び出し側の EBX |
                                                   *------------------*
                                              ECX  |      未定義      |
                                                   *------------------*
                                              EDX  |      未定義      |
                                                   *------------------*
                                              EDI  | 呼び出し側の EDI |
                                                   *------------------*
                                              ESI  | 呼び出し側の ESI |
                                                   *------------------*
浮動小数点パラメーターのルーチンへの受け渡し

以下の例は、ルーチン FUNC2 に対する呼び出しのときの、コード・シーケンス、80386 のスタック・レイアウト、および浮動小数点レジスター・スタック の状態を示しています。単純にするために、汎用レジスターは示しません。このプログラムは、IMPRECISE オプションでコンパイルされることが前提になっています。

 dcl func2 entry( float bin(21),
                  float bin(53),
                  float bin(64),
                  float bin(21),
                  float bin(53) )
     returns( float bin(53) )
     options( byvalue nodescriptor );

 dcl (a, b, c) float bin(53);
 dcl (d, e) float bin(21);

 a = b + func2(a, d, prec(a + c, 53), e, c);

caller's Code Up Until Call:

      PUSH    2ND DWORD OF c       ; Push upper 4 bytes of c onto stack
      PUSH    1ST DWORD OF c       ; Push lower 4 bytes of c onto stack
      FLD     DWORD_PTR e          ; Load e into 80387, promotion
                                   ;  requires no conversion code
      FLD     QWORD_PTR a          ; Load a to calculate p3
      FADD    ST(0), QWORD_PTR c   ; Calculate p3, result is float bin(64)
                                   ;  from nature of 80387 hardware
      FLD     QWORD_PTR d          ; Load d, no conversion necessary
      FLD     QWORD_PTR a          ; Load a, demotion requires conversion
      FSTP    DWORD_PTR [EBP - T1] ; Store to a temp (T1) to convert to float
      FLD     DWORD_PTR [EBP - T1] ; Load converted value from temp (T1)
      SUB     ESP, 32              ; Allocate the stack space for
                                   ; parameter list
      CALL    FUNC2                ; Make call

            呼び出し直後のスタック      呼び出し直後の 80387 レジスター設定

            *                      *            *-------------------*
            |   呼び出し側の Local |     ST(7)  |       空         |
            *----------------------*            *------------------*
            | p5 の Upper Dword    |     ST(6)  |        空        |
            *- - - - - - - - - - - *            *------------------*
            | p5 の Lower Dword    |     ST(5)  |        空         |
            *----------------------*            **------------------*
            | p4 の Blank Dword    |     ST(4)  |        空         |
            *----------------------*            **------------------*
            |       Four           |     ST(3)  |      p4 (e)       |
            *- -- -- -- -- -- -- --*            **------------------*
            |       ブランク       |     ST(2)  |    p3 (a + c)     |
            *- -- -- -- -- -- -- --*            **------------------*
            |       Dwords         |     ST(1)  |      p2 (d)       |
            *- -- -- -- -- -- -- --*            **------------------*
            |       for p3         |     ST(0)  |      p1 (a)       |
            *----------------------*            *------------------*
            |     2 つのブランク   |
            *- -- -- -- -- -- -- --*
            |   p2 の Dwords       |
            *----------------------*
            | p1 の Blank Dword    |
            *----------------------*
            |    呼び出し側の EIP  |
 ESP --->   *----------------------*

callee's Prolog Code:

            PUSH     EBP                      ; Save caller's EBP
            MOV      EBP, ESP                 ; Set up callee's EBP
            SUB      ESP, callee's local size ; Allocate callee's Local
            PUSH     EBX                      ; Save preserved registers -
            PUSH     EDI                      ;  will optimize to save
            PUSH     ESI                      ;  only registers callee uses

             
              Prolog 後のスタック       Prolog 後の 80387 レジスター設定

            ・                    ・              *-----------------*
            |  呼び出し側の Local  |      ST(7)   |       空        |
            *-----------------------*              *------------------*
            | p5 の Upper Dword    |      ST(6)   |       空        |
            *-- -- -- -- -- -- -- --*              *------------------*
            | p5 の Lower Dword    |      ST(5)   |       空        |
            *-----------------------*              *------------------*
            | p4 の Blank Dword    |      ST(4)   |       空        |
            *-----------------------*              *------------------*
            |       Four           |      ST(3)   |       p4        |
            *-- -- -- -- -- -- -- --*              *------------------*
            |       ブランク       |      ST(2)   |       p3        |
            *-- -- -- -- -- -- -- --*              *------------------*
            |       Dwords         |      ST(1)   |       p2        |
            *-- -- -- -- -- -- -- --*              *------------------*
            |       for p3         |      ST(0)   |       p1        |
            *-----------------------*              *-----------------*
            |     2 つのブランク   |
            *-- -- -- -- -- -- -- --*
            |   p2 の Dwords       |
            *-----------------------*
            | p1 の Blank Dword    |
            *-----------------------*
            |    呼び出し側の EIP  |
            *-----------------------*
            |    呼び出し側の EBP  |
            *-----------------------*
            |                      |
            .                      .
            .   呼び出し先の Local .
            .                      .
            |                      |
            *-----------------------*
            |      保管 EBX        |
            *-----------------------*
            |      保管 EDI        |
            *-----------------------*
            |      保管 ESI        |
 ESP --->   *----------------------*

callee's Epilog Code:

    FLD       RETVAL      ; Load return value onto floating-point stack
    POP       ESI         ; Restore preserved registers
    POP       EDI
    POP       EBX
    MOV       ESP, EBP    ; Deallocate callee's local
    POP       EBP         ; Restore caller's EBP
    RET                   ; Return to caller

             Epilog 後のスタック     Epilog 後の 80387 レジスター設定

            ・                     ・            *------------------*
            |  呼び出し側の Local  |     ST(7)   |        空        |
            *-----------------------*             *-------------------*
            | p5 の Upper Dword    |     ST(6)   |        空        |
            *-- -- -- -- -- -- -- --*             *-------------------*
            | p5 の Lower Dword    |     ST(5)   |        空        |
            *-----------------------*             *-------------------*
            | p4 の Blank Dword    |     ST(4)   |        空        |
            *-----------------------*             *-------------------*
            |       Four           |     ST(3)   |        空        |
            *-- -- -- -- -- -- -- --*             *-------------------*
            |       ブランク       |     ST(2)   |        空        |
            *-- -- -- -- -- -- -- --*             *-------------------*
            |       Dwords         |     ST(1)   |        空        |
            *-- -- -- -- -- -- -- --*             *-------------------*
            |       for p3         |     ST(0)   |      戻り値      |
            *-----------------------*             *------------------*
            |     2 つのブランク   |
            *-- -- -- -- -- -- -- --*
            |   p2 の Dwords       |
            *-----------------------*
            | p1 の Blank Dword    |
 ESP --->   *----------------------*

caller's Code Just After Call:

              ADD      ESP, 40      ; Remove parameters from stack
              FADD     QWORD_PTR b  ; Use return value
              FSTP     QWORD_PTR a  ; Store expression to variable a

            
          クリーンアップ後のスタック   クリーンアップ後の 80387 レジスター設定

            ・                    ・              *--------------------*
            |  呼び出し側の Local |        ST(7)  |         空         |
            |                     |               *---------------------*
 ESP --->  *---------------------*        ST(6)  |         空         |
                                                  *---------------------*
                                           ST(5)  |         空         |
                                                  *---------------------*
                                           ST(4)  |         空         |
                                                  *---------------------*
                                           ST(3)  |         空         |
                                                  *---------------------*
                                           ST(2)  |         空         |
                                                  *---------------------*
                                           ST(1)  |         空         |
                                                  *---------------------*
                                           ST(0)  |       戻り値       |
                                                  *--------------------*

Terms of use | Feedback

This information center is powered by Eclipse technology. (http://www.eclipse.org)