1 // Copyright (c) 2013 The Chromium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #include "net/android/keystore.h" 6 7 #include <vector> 8 9 #include "base/android/jni_android.h" 10 #include "base/android/jni_array.h" 11 #include "base/logging.h" 12 #include "jni/AndroidKeyStore_jni.h" 13 #include "net/android/android_private_key.h" 14 15 using base::android::AttachCurrentThread; 16 using base::android::HasException; 17 using base::android::JavaByteArrayToByteVector; 18 using base::android::ScopedJavaLocalRef; 19 using base::android::ToJavaByteArray; 20 using base::android::JavaArrayOfByteArrayToStringVector; 21 22 namespace net { 23 namespace android { 24 25 bool GetRSAKeyModulus( 26 jobject private_key_ref, 27 std::vector<uint8>* result) { 28 JNIEnv* env = AttachCurrentThread(); 29 30 ScopedJavaLocalRef<jbyteArray> modulus_ref = 31 Java_AndroidKeyStore_getRSAKeyModulus(env, 32 GetKeyStore(private_key_ref).obj(), 33 private_key_ref); 34 if (modulus_ref.is_null()) 35 return false; 36 37 JavaByteArrayToByteVector(env, modulus_ref.obj(), result); 38 return true; 39 } 40 41 bool GetDSAKeyParamQ(jobject private_key_ref, 42 std::vector<uint8>* result) { 43 JNIEnv* env = AttachCurrentThread(); 44 45 ScopedJavaLocalRef<jbyteArray> q_ref = 46 Java_AndroidKeyStore_getDSAKeyParamQ( 47 env, 48 GetKeyStore(private_key_ref).obj(), 49 private_key_ref); 50 if (q_ref.is_null()) 51 return false; 52 53 JavaByteArrayToByteVector(env, q_ref.obj(), result); 54 return true; 55 } 56 57 bool GetECKeyOrder(jobject private_key_ref, 58 std::vector<uint8>* result) { 59 JNIEnv* env = AttachCurrentThread(); 60 61 ScopedJavaLocalRef<jbyteArray> order_ref = 62 Java_AndroidKeyStore_getECKeyOrder( 63 env, 64 GetKeyStore(private_key_ref).obj(), 65 private_key_ref); 66 67 if (order_ref.is_null()) 68 return false; 69 70 JavaByteArrayToByteVector(env, order_ref.obj(), result); 71 return true; 72 } 73 74 bool GetPrivateKeyEncodedBytes(jobject private_key_ref, 75 std::vector<uint8>* result) { 76 JNIEnv* env = AttachCurrentThread(); 77 78 ScopedJavaLocalRef<jbyteArray> encoded_ref = 79 Java_AndroidKeyStore_getPrivateKeyEncodedBytes( 80 env, 81 GetKeyStore(private_key_ref).obj(), 82 private_key_ref); 83 if (encoded_ref.is_null()) 84 return false; 85 86 JavaByteArrayToByteVector(env, encoded_ref.obj(), result); 87 return true; 88 } 89 90 bool RawSignDigestWithPrivateKey( 91 jobject private_key_ref, 92 const base::StringPiece& digest, 93 std::vector<uint8>* signature) { 94 JNIEnv* env = AttachCurrentThread(); 95 96 // Convert message to byte[] array. 97 ScopedJavaLocalRef<jbyteArray> digest_ref = 98 ToJavaByteArray(env, 99 reinterpret_cast<const uint8*>(digest.data()), 100 digest.length()); 101 DCHECK(!digest_ref.is_null()); 102 103 // Invoke platform API 104 ScopedJavaLocalRef<jbyteArray> signature_ref = 105 Java_AndroidKeyStore_rawSignDigestWithPrivateKey( 106 env, 107 GetKeyStore(private_key_ref).obj(), 108 private_key_ref, 109 digest_ref.obj()); 110 if (HasException(env) || signature_ref.is_null()) 111 return false; 112 113 // Write signature to string. 114 JavaByteArrayToByteVector(env, signature_ref.obj(), signature); 115 return true; 116 } 117 118 PrivateKeyType GetPrivateKeyType(jobject private_key_ref) { 119 JNIEnv* env = AttachCurrentThread(); 120 int type = Java_AndroidKeyStore_getPrivateKeyType( 121 env, 122 GetKeyStore(private_key_ref).obj(), 123 private_key_ref); 124 return static_cast<PrivateKeyType>(type); 125 } 126 127 AndroidEVP_PKEY* GetOpenSSLSystemHandleForPrivateKey(jobject private_key_ref) { 128 JNIEnv* env = AttachCurrentThread(); 129 // Note: the pointer is passed as a jint here because that's how it 130 // is stored in the Java object. Java doesn't have a primitive type 131 // like intptr_t that matches the size of pointers on the host 132 // machine, and Android only runs on 32-bit CPUs. 133 // 134 // Given that this routine shall only be called on Android < 4.2, 135 // this won't be a problem in the far future (e.g. when Android gets 136 // ported to 64-bit environments, if ever). 137 long pkey = Java_AndroidKeyStore_getOpenSSLHandleForPrivateKey( 138 env, 139 GetKeyStore(private_key_ref).obj(), 140 private_key_ref); 141 return reinterpret_cast<AndroidEVP_PKEY*>(pkey); 142 } 143 144 ScopedJavaLocalRef<jobject> GetOpenSSLEngineForPrivateKey( 145 jobject private_key_ref) { 146 JNIEnv* env = AttachCurrentThread(); 147 ScopedJavaLocalRef<jobject> engine = 148 Java_AndroidKeyStore_getOpenSSLEngineForPrivateKey( 149 env, 150 GetKeyStore(private_key_ref).obj(), 151 private_key_ref); 152 return engine; 153 } 154 155 void ReleaseKey(jobject private_key_ref) { 156 JNIEnv* env = AttachCurrentThread(); 157 Java_AndroidKeyStore_releaseKey(env, 158 GetKeyStore(private_key_ref).obj(), 159 private_key_ref); 160 env->DeleteGlobalRef(private_key_ref); 161 } 162 163 bool RegisterKeyStore(JNIEnv* env) { 164 return RegisterNativesImpl(env); 165 } 166 167 } // namespace android 168 } // namespace net 169