< prev index next >

src/cpu/s390/vm/stubGenerator_s390.cpp

Print this page




 274       //
 275       // Stack on exit from frame manager / native entry:
 276       //
 277       //     F0      [ABI]
 278       //             ...
 279       //             [ENTRY_FRAME_LOCALS]
 280       //     F1      [C_FRAME]
 281       //             ...
 282       //
 283       // Just pop the topmost frame ...
 284       //
 285 
 286       Label ret_is_object;
 287       Label ret_is_long;
 288       Label ret_is_float;
 289       Label ret_is_double;
 290 
 291       // Restore frame pointer.
 292       __ z_lg(r_entryframe_fp, _z_abi(callers_sp), Z_SP);
 293       // Pop frame. Done here to minimize stalls.
 294       __ z_lg(Z_SP, _z_abi(callers_sp), Z_SP);
 295 
 296       // Reload some volatile registers which we've spilled before the call
 297       // to frame manager / native entry.
 298       // Access all locals via frame pointer, because we know nothing about
 299       // the topmost frame's size.
 300       __ z_lg(r_arg_result_addr, result_address_offset, r_entryframe_fp);
 301       __ z_lg(r_arg_result_type, result_type_offset, r_entryframe_fp);
 302 
 303       // Restore non-volatiles.
 304       __ z_lmg(Z_R6, Z_R14, 16, Z_SP);
 305       __ z_ld(Z_F8, 96, Z_SP);
 306       __ z_ld(Z_F9, 104, Z_SP);
 307       __ z_ld(Z_F10, 112, Z_SP);
 308       __ z_ld(Z_F11, 120, Z_SP);
 309       __ z_ld(Z_F12, 128, Z_SP);
 310       __ z_ld(Z_F13, 136, Z_SP);
 311       __ z_ld(Z_F14, 144, Z_SP);
 312       __ z_ld(Z_F15, 152, Z_SP);
 313       BLOCK_COMMENT("} restore");
 314 


1660   //   Therefore, we need the original, not the expanded key here.
1661   //   Luckily, the first n bits of an AES-<n> expanded key are formed
1662   //   by the original key itself. That takes us out of trouble. :-)
1663   //   The key length (in bytes) relation is as follows:
1664   //     original    expanded   rounds  key bit     keylen
1665   //    key bytes   key bytes            length   in words
1666   //           16         176       11      128         44
1667   //           24         208       13      192         52
1668   //           32         240       15      256         60
1669   //
1670   // The crypto instructions used in the AES* stubs have some specific register requirements.
1671   //   Z_R0   holds the crypto function code. Please refer to the KM/KMC instruction
1672   //          description in the "z/Architecture Principles of Operation" manual for details.
1673   //   Z_R1   holds the parameter block address. The parameter block contains the cryptographic key
1674   //          (KM instruction) and the chaining value (KMC instruction).
1675   //   dst    must designate an even-numbered register, holding the address of the output message.
1676   //   src    must designate an even/odd register pair, holding the address/length of the original message
1677 
1678   // Helper function which generates code to
1679   //  - load the function code in register fCode (== Z_R0)
1680   //  - load the data block length (depends on cipher function) in register srclen if requested.
1681   //  - is_decipher switches between cipher/decipher function codes
1682   //  - set_len requests (if true) loading the data block length in register srclen
1683   void generate_load_AES_fCode(Register keylen, Register fCode, Register srclen, bool is_decipher) {
1684 
1685     BLOCK_COMMENT("Set fCode {"); {
1686       Label fCode_set;
1687       int   mode = is_decipher ? VM_Version::CipherMode::decipher : VM_Version::CipherMode::cipher;
1688       bool  identical_dataBlk_len =  (VM_Version::Cipher::_AES128_dataBlk == VM_Version::Cipher::_AES192_dataBlk)
1689                                   && (VM_Version::Cipher::_AES128_dataBlk == VM_Version::Cipher::_AES256_dataBlk);
1690       // Expanded key length is 44/52/60 * 4 bytes for AES-128/AES-192/AES-256.
1691       __ z_cghi(keylen, 52);

1692       __ z_lghi(fCode, VM_Version::Cipher::_AES256 + mode);
1693       if (!identical_dataBlk_len) {
1694         __ z_lghi(srclen, VM_Version::Cipher::_AES256_dataBlk);
1695       }
1696       __ z_brh(fCode_set);  // keyLen >  52: AES256
1697 
1698       __ z_lghi(fCode, VM_Version::Cipher::_AES192 + mode);
1699       if (!identical_dataBlk_len) {
1700         __ z_lghi(srclen, VM_Version::Cipher::_AES192_dataBlk);
1701       }
1702       __ z_bre(fCode_set);  // keyLen == 52: AES192
1703 
1704       __ z_lghi(fCode, VM_Version::Cipher::_AES128 + mode);
1705       if (!identical_dataBlk_len) {
1706         __ z_lghi(srclen, VM_Version::Cipher::_AES128_dataBlk);
1707       }
1708       // __ z_brl(fCode_set);  // keyLen <  52: AES128           // fallthru

1709       __ bind(fCode_set);
1710       if (identical_dataBlk_len) {
1711         __ z_lghi(srclen, VM_Version::Cipher::_AES128_dataBlk);
1712       }
1713     }
1714     BLOCK_COMMENT("} Set fCode");
1715   }
1716 
1717   // Push a parameter block for the cipher/decipher instruction on the stack.
1718   // NOTE:
1719   //   Before returning, the stub has to copy the chaining value from
1720   //   the parmBlk, where it was updated by the crypto instruction, back
1721   //   to the chaining value array the address of which was passed in the cv argument.
1722   //   As all the available registers are used and modified by KMC, we need to save
1723   //   the key length across the KMC instruction. We do so by spilling it to the stack,
1724   //   just preceding the parmBlk (at (parmBlk - 8)).
1725   void generate_push_parmBlk(Register keylen, Register fCode, Register parmBlk, Register key, Register cv, bool is_decipher) {
1726     const int AES_parmBlk_align    = 32;
1727     const int AES_parmBlk_addspace = AES_parmBlk_align; // Must be multiple of AES_parmblk_align.
1728     int       cv_len, key_len;




 274       //
 275       // Stack on exit from frame manager / native entry:
 276       //
 277       //     F0      [ABI]
 278       //             ...
 279       //             [ENTRY_FRAME_LOCALS]
 280       //     F1      [C_FRAME]
 281       //             ...
 282       //
 283       // Just pop the topmost frame ...
 284       //
 285 
 286       Label ret_is_object;
 287       Label ret_is_long;
 288       Label ret_is_float;
 289       Label ret_is_double;
 290 
 291       // Restore frame pointer.
 292       __ z_lg(r_entryframe_fp, _z_abi(callers_sp), Z_SP);
 293       // Pop frame. Done here to minimize stalls.
 294       __ pop_frame();
 295 
 296       // Reload some volatile registers which we've spilled before the call
 297       // to frame manager / native entry.
 298       // Access all locals via frame pointer, because we know nothing about
 299       // the topmost frame's size.
 300       __ z_lg(r_arg_result_addr, result_address_offset, r_entryframe_fp);
 301       __ z_lg(r_arg_result_type, result_type_offset, r_entryframe_fp);
 302 
 303       // Restore non-volatiles.
 304       __ z_lmg(Z_R6, Z_R14, 16, Z_SP);
 305       __ z_ld(Z_F8, 96, Z_SP);
 306       __ z_ld(Z_F9, 104, Z_SP);
 307       __ z_ld(Z_F10, 112, Z_SP);
 308       __ z_ld(Z_F11, 120, Z_SP);
 309       __ z_ld(Z_F12, 128, Z_SP);
 310       __ z_ld(Z_F13, 136, Z_SP);
 311       __ z_ld(Z_F14, 144, Z_SP);
 312       __ z_ld(Z_F15, 152, Z_SP);
 313       BLOCK_COMMENT("} restore");
 314 


1660   //   Therefore, we need the original, not the expanded key here.
1661   //   Luckily, the first n bits of an AES-<n> expanded key are formed
1662   //   by the original key itself. That takes us out of trouble. :-)
1663   //   The key length (in bytes) relation is as follows:
1664   //     original    expanded   rounds  key bit     keylen
1665   //    key bytes   key bytes            length   in words
1666   //           16         176       11      128         44
1667   //           24         208       13      192         52
1668   //           32         240       15      256         60
1669   //
1670   // The crypto instructions used in the AES* stubs have some specific register requirements.
1671   //   Z_R0   holds the crypto function code. Please refer to the KM/KMC instruction
1672   //          description in the "z/Architecture Principles of Operation" manual for details.
1673   //   Z_R1   holds the parameter block address. The parameter block contains the cryptographic key
1674   //          (KM instruction) and the chaining value (KMC instruction).
1675   //   dst    must designate an even-numbered register, holding the address of the output message.
1676   //   src    must designate an even/odd register pair, holding the address/length of the original message
1677 
1678   // Helper function which generates code to
1679   //  - load the function code in register fCode (== Z_R0)
1680   //  - load the data block length (depends on cipher function) into register srclen if requested.
1681   //  - is_decipher switches between cipher/decipher function codes
1682   //  - set_len requests (if true) loading the data block length in register srclen
1683   void generate_load_AES_fCode(Register keylen, Register fCode, Register srclen, bool is_decipher) {
1684 
1685     BLOCK_COMMENT("Set fCode {"); {
1686       Label fCode_set;
1687       int   mode = is_decipher ? VM_Version::CipherMode::decipher : VM_Version::CipherMode::cipher;
1688       bool  identical_dataBlk_len =  (VM_Version::Cipher::_AES128_dataBlk == VM_Version::Cipher::_AES192_dataBlk)
1689                                   && (VM_Version::Cipher::_AES128_dataBlk == VM_Version::Cipher::_AES256_dataBlk);
1690       // Expanded key length is 44/52/60 * 4 bytes for AES-128/AES-192/AES-256.
1691       __ z_cghi(keylen, 52);
1692 
1693       __ z_lghi(fCode, VM_Version::Cipher::_AES256 + mode);
1694       if (!identical_dataBlk_len) {
1695         __ z_lghi(srclen, VM_Version::Cipher::_AES256_dataBlk);
1696       }
1697       __ z_brh(fCode_set);  // keyLen >  52: AES256
1698 
1699       __ z_lghi(fCode, VM_Version::Cipher::_AES192 + mode);
1700       if (!identical_dataBlk_len) {
1701         __ z_lghi(srclen, VM_Version::Cipher::_AES192_dataBlk);
1702       }
1703       __ z_bre(fCode_set);  // keyLen == 52: AES192
1704 
1705       __ z_lghi(fCode, VM_Version::Cipher::_AES128 + mode);
1706       if (!identical_dataBlk_len) {
1707         __ z_lghi(srclen, VM_Version::Cipher::_AES128_dataBlk);
1708       }
1709       // __ z_brl(fCode_set);  // keyLen <  52: AES128           // fallthru
1710 
1711       __ bind(fCode_set);
1712       if (identical_dataBlk_len) {
1713         __ z_lghi(srclen, VM_Version::Cipher::_AES128_dataBlk);
1714       }
1715     }
1716     BLOCK_COMMENT("} Set fCode");
1717   }
1718 
1719   // Push a parameter block for the cipher/decipher instruction on the stack.
1720   // NOTE:
1721   //   Before returning, the stub has to copy the chaining value from
1722   //   the parmBlk, where it was updated by the crypto instruction, back
1723   //   to the chaining value array the address of which was passed in the cv argument.
1724   //   As all the available registers are used and modified by KMC, we need to save
1725   //   the key length across the KMC instruction. We do so by spilling it to the stack,
1726   //   just preceding the parmBlk (at (parmBlk - 8)).
1727   void generate_push_parmBlk(Register keylen, Register fCode, Register parmBlk, Register key, Register cv, bool is_decipher) {
1728     const int AES_parmBlk_align    = 32;
1729     const int AES_parmBlk_addspace = AES_parmBlk_align; // Must be multiple of AES_parmblk_align.
1730     int       cv_len, key_len;


< prev index next >