1 /*
2  * Copyright 2022 Google LLC
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 package com.google.android.gms.nearby.presence.hazmat;
17 
18 import androidx.annotation.IntDef;
19 
20 /** JNI for a Nearby Presence LDT-XTS-AES128 cipher with the "swap" mix function. */
21 class LdtNpJni {
22 
23   /** Error codes which map to return values on the native side. */
24   @IntDef({
25     DecryptErrorCode.DATA_LEN_ERROR,
26     DecryptErrorCode.JNI_OP_ERROR,
27     DecryptErrorCode.MAC_MISMATCH
28   })
29   public @interface DecryptErrorCode {
30     int DATA_LEN_ERROR = -1;
31     int JNI_OP_ERROR = -2;
32     int MAC_MISMATCH = -3;
33   }
34 
35   /** Error codes which map to return values on the native side. */
36   @IntDef({EncryptErrorCode.DATA_LEN_ERROR, EncryptErrorCode.JNI_OP_ERROR})
37   public @interface EncryptErrorCode {
38     int DATA_LEN_ERROR = -1;
39     int JNI_OP_ERROR = -2;
40   }
41 
42   static {
43     System.loadLibrary("ldt_np_jni");
44   }
45 
46   /**
47    * Create a new LDT-XTS-AES128 Encryption cipher using the "swap" mix function.
48    *
49    * @param keySeed is the 32-byte key material from the Nearby Presence credential from which the
50    *     LDT key will be derived.
51    * @return 0 on error, or a non-zero handle on success.
52    */
createEncryptionCipher(byte[] keySeed)53   static native long createEncryptionCipher(byte[] keySeed);
54 
55   /**
56    * Create a new LDT-XTS-AES128 Decryption cipher using the "swap" mix function.
57    *
58    * @param keySeed is the 32-byte key material from the Nearby Presence credential from which the
59    *     LDT key will be derived.
60    * @param hmacTag is the hmac auth tag calculated on the metadata key used to verify decryption
61    *     was successful.
62    * @return 0 on error, or a non-zero handle on success.
63    */
createDecryptionCipher(byte[] keySeed, byte[] hmacTag)64   static native long createDecryptionCipher(byte[] keySeed, byte[] hmacTag);
65 
66   /**
67    * Close the native resources for an LdtEncryptCipher instance.
68    *
69    * @param ldtEncryptHandle a ldt handle returned from {@link LdtNpJni#createEncryptionCipher}.
70    */
closeEncryptCipher(long ldtEncryptHandle)71   static native void closeEncryptCipher(long ldtEncryptHandle);
72 
73   /**
74    * Close the native resources for an LdtDecryptCipher instance.
75    *
76    * @param ldtDecryptHandle a ldt handle returned from {@link LdtNpJni#createDecryptionCipher}.
77    */
closeDecryptCipher(long ldtDecryptHandle)78   static native void closeDecryptCipher(long ldtDecryptHandle);
79 
80   /**
81    * Encrypt a 16-31 byte buffer in-place.
82    *
83    * @param ldtEncryptHandle a ldt encryption handle returned from {@link
84    *     LdtNpJni#createEncryptionCipher}.
85    * @param salt is the big-endian 2 byte salt that will be used in the Nearby Presence
86    *     advertisement, which will be incorporated into the tweaks LDT uses while encrypting.
87    * @param data 16-31 bytes of plaintext data to be encrypted
88    * @return 0 on success, in which case `buffer` will now contain ciphertext or a non-zero an error
89    *     code on failure
90    */
91   @EncryptErrorCode
encrypt(long ldtEncryptHandle, char salt, byte[] data)92   static native int encrypt(long ldtEncryptHandle, char salt, byte[] data);
93 
94   /**
95    * Decrypt a 16-31 byte buffer in-place and verify the plaintext metadata key matches this item's
96    * MAC, if not the buffer will not be decrypted.
97    *
98    * @param ldtDecryptHandle a ldt encryption handle returned from {@link
99    *     LdtNpJni#createDecryptionCipher}.
100    * @param salt is the big-endian 2 byte salt that will be used in the Nearby Presence
101    *     advertisement, which will be incorporated into the tweaks LDT uses while encrypting.
102    * @param data 16-31 bytes of ciphertext data to be decrypted
103    * @return 0 on success, in which case `buffer` will now contain ciphertext or a non-zero an error
104    *     code on failure, in which case data will remain unchanged.
105    */
106   @DecryptErrorCode
decryptAndVerify(long ldtDecryptHandle, char salt, byte[] data)107   static native int decryptAndVerify(long ldtDecryptHandle, char salt, byte[] data);
108 }
109