--- old/src/share/vm/c1/c1_GraphBuilder.cpp 2014-07-09 16:46:28.037937151 -0400 +++ new/src/share/vm/c1/c1_GraphBuilder.cpp 2014-07-09 16:46:27.544725197 -0400 @@ -3635,6 +3635,13 @@ case vmIntrinsics::_fullFence : break; + case vmIntrinsics::_cipherBlockChaining_encryptAESCrypt: + case vmIntrinsics::_cipherBlockChaining_decryptAESCrypt: + if (VM_Version::supports_crypto_acceleration_client()) { + return (append_crypto_cbc_aes(callee)); + } + return false; + default : return false; // do not inline } // create intrinsic node @@ -4447,6 +4454,44 @@ return InlineUnsafeOps; } +bool GraphBuilder::append_crypto_cbc_aes(ciMethod* callee) { + + if (!UseAESIntrinsics) return false; + + ciInstanceKlass* inst = callee->holder()->as_instance_klass(); + ciField* cipher = inst->get_field_by_name(ciSymbol::make("embeddedCipher"), ciSymbol::make("Lcom/sun/crypto/provider/SymmetricCipher;"), false); + if (cipher == NULL) return false; + + ciKlass* klass_AESCrypt = inst->find_klass(ciSymbol::make("com/sun/crypto/provider/AESCrypt")); + + // if AESCrypt is not even loaded, we never take the intrinsic fast path + if (klass_AESCrypt == NULL || !klass_AESCrypt->is_loaded()) return false; + + ciInstanceKlass* instklass_AESCrypt = klass_AESCrypt->as_instance_klass(); + + Value recv = state()->stack_at(0); + Value cipher_inst = append(new LoadField(recv, cipher->offset(), cipher, false, copy_state_for_exception(), false /*needs_patching*/)); + + // generate InstanceOf check for further evaluation in LIRAssember + Value insof = append_split(new InstanceOf(instklass_AESCrypt, cipher_inst, copy_state_exhandling())); + + Values* args = state()->pop_arguments(callee->arg_size()); + + args->push(insof); + + // create intrinsic node + ValueType* result_type = as_ValueType(callee->return_type()); + ValueStack* state_before = copy_state_for_exception(); + + Intrinsic* result = new Intrinsic(result_type, callee->intrinsic_id(), args, true /*has_receiver*/, state_before, + true /*preserves_state*/, false /*cantrap*/); + // append instruction & push result + Value value = append_split(result); + push(result_type, value); + + return true; +} + #ifndef PRODUCT void GraphBuilder::print_stats() { vmap()->print();