Skip to content

Commit b4f5a9a

Browse files
committed
add askarKeyDeriveEcdhEs, askarKeyFromJwk, askarKeyGetJwkPublic and askarKeyWrapKey
1 parent 1e49b3d commit b4f5a9a

File tree

6 files changed

+304
-116
lines changed

6 files changed

+304
-116
lines changed

lib/askar/askar_native_functions.dart

+14-14
Original file line numberDiff line numberDiff line change
@@ -428,9 +428,9 @@ typedef AskarKeyDeriveEcdhEsNative = Int32 Function(
428428
Pointer<Utf8> alg,
429429
NativeLocalKeyHandle ephem_key,
430430
NativeLocalKeyHandle recip_key,
431-
Pointer<NativeByteBuffer> alg_id,
432-
Pointer<NativeByteBuffer> apu,
433-
Pointer<NativeByteBuffer> apv,
431+
NativeByteBuffer alg_id,
432+
NativeByteBuffer apu,
433+
NativeByteBuffer apv,
434434
Int8 receive,
435435
Pointer<NativeLocalKeyHandle> out,
436436
);
@@ -439,9 +439,9 @@ final int Function(
439439
Pointer<Utf8> alg,
440440
LocalKeyHandle ephem_key,
441441
LocalKeyHandle recip_key,
442-
Pointer<NativeByteBuffer> alg_id,
443-
Pointer<NativeByteBuffer> apu,
444-
Pointer<NativeByteBuffer> apv,
442+
NativeByteBuffer alg_id,
443+
NativeByteBuffer apu,
444+
NativeByteBuffer apv,
445445
int receive,
446446
Pointer<NativeLocalKeyHandle> out,
447447
) nativeAskarKeyDeriveEcdhEs = nativeLib
@@ -547,12 +547,12 @@ final void Function(LocalKeyHandle handle) nativeAskarKeyFree =
547547
nativeLib.lookup<NativeFunction<AskarKeyFreeNative>>('askar_key_free').asFunction();
548548

549549
typedef AskarKeyFromJwkNative = Int32 Function(
550-
Pointer<NativeByteBuffer> jwk,
550+
NativeByteBuffer jwk,
551551
Pointer<NativeLocalKeyHandle> out,
552552
);
553553

554554
final int Function(
555-
Pointer<NativeByteBuffer> jwk,
555+
NativeByteBuffer jwk,
556556
Pointer<NativeLocalKeyHandle> out,
557557
) nativeAskarKeyFromJwk = nativeLib
558558
.lookup<NativeFunction<AskarKeyFromJwkNative>>('askar_key_from_jwk')
@@ -742,18 +742,18 @@ final int Function(
742742
typedef AskarKeyUnwrapKeyNative = Int32 Function(
743743
NativeLocalKeyHandle handle,
744744
Pointer<Utf8> alg,
745-
Pointer<NativeByteBuffer> ciphertext,
746-
Pointer<NativeByteBuffer> nonce,
747-
Pointer<NativeByteBuffer> tag,
745+
NativeByteBuffer ciphertext,
746+
NativeByteBuffer nonce,
747+
NativeByteBuffer tag,
748748
Pointer<NativeLocalKeyHandle> out,
749749
);
750750

751751
final int Function(
752752
LocalKeyHandle handle,
753753
Pointer<Utf8> alg,
754-
Pointer<NativeByteBuffer> ciphertext,
755-
Pointer<NativeByteBuffer> nonce,
756-
Pointer<NativeByteBuffer> tag,
754+
NativeByteBuffer ciphertext,
755+
NativeByteBuffer nonce,
756+
NativeByteBuffer tag,
757757
Pointer<NativeLocalKeyHandle> out,
758758
) nativeAskarKeyUnwrapKey = nativeLib
759759
.lookup<NativeFunction<AskarKeyUnwrapKeyNative>>('askar_key_unwrap_key')

lib/askar/askar_utils.dart

+7-16
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,6 @@ import 'dart:math';
44
import 'dart:typed_data';
55

66
import 'package:ffi/ffi.dart';
7-
import 'package:import_so_libaskar/askar/askar_wrapper.dart';
87

98
import 'askar_native_functions.dart';
109

@@ -38,12 +37,14 @@ Uint8List secretBufferToBytesList(NativeSecretBuffer secretBuffer) {
3837
return dataPointer.asTypedList(length);
3938
}
4039

41-
AskarEncryptedBuffer readNativeEncryptedBuffer(NativeEncryptedBuffer encryptedBuffer) {
42-
int noncePos = encryptedBuffer.nonce_pos;
43-
int tagPos = encryptedBuffer.tag_pos;
40+
int boolToInt(bool value) {
41+
return value ? 1 : 0;
42+
}
4443

45-
return AskarEncryptedBuffer(
46-
secretBufferToBytesList(encryptedBuffer.buffer), tagPos, noncePos);
44+
Uint8List generateRandomSeed() {
45+
final random = Random.secure();
46+
final seed = List<int>.generate(32, (_) => random.nextInt(256));
47+
return Uint8List.fromList(seed);
4748
}
4849

4950
bool intToBool(int value) {
@@ -56,13 +57,3 @@ bool intToBool(int value) {
5657
throw ArgumentError('Invalid bool value: $value');
5758
}
5859
}
59-
60-
int boolToInt(bool value) {
61-
return value ? 1 : 0;
62-
}
63-
64-
Uint8List generateRandomSeed() {
65-
final random = Random.secure();
66-
final seed = List<int>.generate(32, (_) => random.nextInt(256));
67-
return Uint8List.fromList(seed);
68-
}

lib/askar/askar_wrapper.dart

+99-61
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ import 'dart:ffi';
55
import 'package:ffi/ffi.dart';
66
import 'package:flutter/foundation.dart';
77
import 'package:import_so_libaskar/askar/askar_callbacks.dart';
8+
import 'package:import_so_libaskar/askar/crypto/askar_encrypted_buffer.dart';
89
import 'package:import_so_libaskar/askar/enums/askar_entry_operation.dart';
910
import 'package:import_so_libaskar/askar/enums/askar_error_code.dart';
1011
import 'package:import_so_libaskar/askar/enums/askar_key_algorithm.dart';
@@ -27,19 +28,6 @@ final class AskarResult<T> {
2728
}
2829
}
2930

30-
final class AskarEncryptedBuffer {
31-
final Uint8List buffer;
32-
final int tagPos;
33-
final int noncePos;
34-
35-
AskarEncryptedBuffer(this.buffer, this.tagPos, this.noncePos);
36-
37-
@override
38-
String toString() {
39-
return "AskarEncryptedBuffer(tagPos: $tagPos, noncePos: $noncePos, buffer: $buffer)";
40-
}
41-
}
42-
4331
typedef LocalKeyHandle = int;
4432
typedef ScanHandle = int;
4533
typedef StoreHandle = int;
@@ -242,7 +230,7 @@ ErrorCode askarKeyAeadDecrypt(
242230
return ErrorCode.fromInt(result);
243231
}
244232

245-
AskarResult<Uint8List> askarKeyAeadEncrypt(
233+
AskarResult<AskarEncryptedBuffer> askarKeyAeadEncrypt(
246234
LocalKeyHandle localKeyHandle, Uint8List message,
247235
{Uint8List? nonce, Uint8List? aad}) {
248236
final randomNonce = askarKeyAeadRandomNonce(localKeyHandle);
@@ -264,7 +252,9 @@ AskarResult<Uint8List> askarKeyAeadEncrypt(
264252

265253
final errorCode = ErrorCode.fromInt(funcResult);
266254

267-
final encryptedData = secretBufferToBytesList(outPtr.ref.buffer);
255+
final value = (errorCode == ErrorCode.success)
256+
? readNativeEncryptedBuffer(outPtr.ref)
257+
: AskarEncryptedBuffer(Uint8List.fromList([]), 0, 0);
268258

269259
calloc.free(messagePtr.ref.data);
270260
calloc.free(noncePtr.ref.data);
@@ -274,7 +264,7 @@ AskarResult<Uint8List> askarKeyAeadEncrypt(
274264
calloc.free(aadPtr);
275265
calloc.free(outPtr);
276266

277-
return AskarResult(errorCode, encryptedData);
267+
return AskarResult<AskarEncryptedBuffer>(errorCode, value);
278268
}
279269

280270
ErrorCode askarKeyAeadGetPadding(
@@ -447,32 +437,47 @@ ErrorCode askarKeyDeriveEcdh1pu(
447437
return ErrorCode.fromInt(result);
448438
}
449439

450-
ErrorCode askarKeyDeriveEcdhEs(
451-
String alg,
452-
LocalKeyHandle ephemKey,
453-
LocalKeyHandle recipKey,
454-
Pointer<NativeByteBuffer> algId,
455-
Pointer<NativeByteBuffer> apu,
456-
Pointer<NativeByteBuffer> apv,
457-
int receive,
458-
Pointer<NativeLocalKeyHandle> out,
440+
AskarResult<LocalKeyHandle> askarKeyDeriveEcdhEs(
441+
KeyAlgorithm algorithm,
442+
LocalKeyHandle ephemeralKey,
443+
LocalKeyHandle recipientKey,
444+
Uint8List algId,
445+
Uint8List apu,
446+
Uint8List apv,
447+
bool receive,
459448
) {
460-
final algPointer = alg.toNativeUtf8();
449+
Pointer<NativeLocalKeyHandle> outPtr = calloc<NativeLocalKeyHandle>();
461450

462-
final result = nativeAskarKeyDeriveEcdhEs(
451+
final algPointer = algorithm.value.toNativeUtf8();
452+
final algIdByteBufferPtr = bytesListToByteBuffer(algId);
453+
final apuByteBufferPtr = bytesListToByteBuffer(apu);
454+
final apvByteBufferPtr = bytesListToByteBuffer(apv);
455+
456+
final funcResult = nativeAskarKeyDeriveEcdhEs(
463457
algPointer,
464-
ephemKey,
465-
recipKey,
466-
algId,
467-
apu,
468-
apv,
469-
receive,
470-
out,
458+
ephemeralKey,
459+
recipientKey,
460+
algIdByteBufferPtr.ref,
461+
apuByteBufferPtr.ref,
462+
apvByteBufferPtr.ref,
463+
boolToInt(receive),
464+
outPtr,
471465
);
472466

467+
final errorCode = ErrorCode.fromInt(funcResult);
468+
469+
LocalKeyHandle value = (errorCode == ErrorCode.success ? outPtr.value : 0);
470+
471+
calloc.free(algIdByteBufferPtr.ref.data);
472+
calloc.free(algIdByteBufferPtr);
473+
calloc.free(apuByteBufferPtr.ref.data);
474+
calloc.free(apuByteBufferPtr);
475+
calloc.free(apvByteBufferPtr.ref.data);
476+
calloc.free(apvByteBufferPtr);
473477
calloc.free(algPointer);
478+
calloc.free(outPtr);
474479

475-
return ErrorCode.fromInt(result);
480+
return AskarResult<LocalKeyHandle>(errorCode, value);
476481
}
477482

478483
AskarResult<int> askarKeyEntryListCount(KeyEntryListHandle handle) {
@@ -574,10 +579,21 @@ void askarKeyFree(LocalKeyHandle handle) {
574579
nativeAskarKeyFree(handle);
575580
}
576581

577-
ErrorCode askarKeyFromJwk(
578-
Pointer<NativeByteBuffer> jwk, Pointer<NativeLocalKeyHandle> out) {
579-
final result = nativeAskarKeyFromJwk(jwk, out);
580-
return ErrorCode.fromInt(result);
582+
AskarResult<LocalKeyHandle> askarKeyFromJwk(String jwk) {
583+
Pointer<NativeLocalKeyHandle> outPtr = calloc<NativeLocalKeyHandle>();
584+
585+
final jwkByteBufferPtr = stringToByteBuffer(jwk);
586+
587+
final errorCode =
588+
ErrorCode.fromInt(nativeAskarKeyFromJwk(jwkByteBufferPtr.ref, outPtr));
589+
590+
final value = (errorCode == ErrorCode.success ? outPtr.value : 0);
591+
592+
calloc.free(outPtr);
593+
calloc.free(jwkByteBufferPtr.ref.data);
594+
calloc.free(jwkByteBufferPtr);
595+
596+
return AskarResult<LocalKeyHandle>(errorCode, value);
581597
}
582598

583599
ErrorCode askarKeyFromKeyExchange(
@@ -709,22 +725,29 @@ ErrorCode askarKeyGetEphemeral(LocalKeyHandle handle, Pointer<Int8> out) {
709725
return ErrorCode.fromInt(result);
710726
}
711727

712-
ErrorCode askarKeyGetJwkPublic(
728+
AskarResult<String> askarKeyGetJwkPublic(
713729
LocalKeyHandle handle,
714-
String alg,
715-
Pointer<Pointer<Utf8>> out,
730+
KeyAlgorithm algorithm,
716731
) {
717-
final algPointer = alg.toNativeUtf8();
732+
Pointer<Pointer<Utf8>> out = calloc<Pointer<Utf8>>();
733+
734+
final algPtr = algorithm.value.toNativeUtf8();
718735

719-
final result = nativeAskarKeyGetJwkPublic(
736+
final funcResult = nativeAskarKeyGetJwkPublic(
720737
handle,
721-
algPointer,
738+
algPtr,
722739
out,
723740
);
724741

725-
calloc.free(algPointer);
742+
final errorCode = ErrorCode.fromInt(funcResult);
726743

727-
return ErrorCode.fromInt(result);
744+
final String value = (errorCode == ErrorCode.success) ? out.value.toDartString() : "";
745+
746+
calloc.free(algPtr);
747+
calloc.free(out.value);
748+
calloc.free(out);
749+
750+
return AskarResult<String>(errorCode, value);
728751
}
729752

730753
ErrorCode askarKeyGetJwkSecret(
@@ -827,28 +850,43 @@ AskarResult<Uint8List> askarKeySignMessage(
827850
return AskarResult<Uint8List>(errorCode, value);
828851
}
829852

830-
ErrorCode askarKeyUnwrapKey(
853+
AskarResult<LocalKeyHandle> askarKeyUnwrapKey(
831854
LocalKeyHandle handle,
832-
String alg,
833-
Pointer<NativeByteBuffer> ciphertext,
834-
Pointer<NativeByteBuffer> nonce,
835-
Pointer<NativeByteBuffer> tag,
836-
Pointer<NativeLocalKeyHandle> out,
855+
KeyAlgorithm algorithm,
856+
Uint8List ciphertext,
857+
Uint8List nonce,
858+
Uint8List tag,
837859
) {
838-
final algPointer = alg.toNativeUtf8();
860+
Pointer<NativeLocalKeyHandle> out = calloc<NativeLocalKeyHandle>();
861+
862+
final algPtr = algorithm.value.toNativeUtf8();
863+
final cipherByteBufferPtr = bytesListToByteBuffer(ciphertext);
864+
final nonceByteBufferPtr = bytesListToByteBuffer(nonce);
865+
final tagByteBufferPtr = bytesListToByteBuffer(tag);
839866

840-
final result = nativeAskarKeyUnwrapKey(
867+
final funcResult = nativeAskarKeyUnwrapKey(
841868
handle,
842-
algPointer,
843-
ciphertext,
844-
nonce,
845-
tag,
869+
algPtr,
870+
cipherByteBufferPtr.ref,
871+
nonceByteBufferPtr.ref,
872+
tagByteBufferPtr.ref,
846873
out,
847874
);
848875

849-
calloc.free(algPointer);
876+
final errorCode = ErrorCode.fromInt(funcResult);
850877

851-
return ErrorCode.fromInt(result);
878+
final value = (errorCode == ErrorCode.success ? out.value : 0);
879+
880+
calloc.free(cipherByteBufferPtr.ref.data);
881+
calloc.free(cipherByteBufferPtr);
882+
calloc.free(nonceByteBufferPtr.ref.data);
883+
calloc.free(nonceByteBufferPtr);
884+
calloc.free(tagByteBufferPtr.ref.data);
885+
calloc.free(tagByteBufferPtr);
886+
calloc.free(algPtr);
887+
calloc.free(out);
888+
889+
return AskarResult<LocalKeyHandle>(errorCode, value);
852890
}
853891

854892
AskarResult<bool> askarKeyVerifySignature(

0 commit comments

Comments
 (0)