Skip to content

Commit

Permalink
Migrate the Ed25519 KeyManagers to use createKeyFromRandomness instea…
Browse files Browse the repository at this point in the history
…d of deriveKey.

PiperOrigin-RevId: 566987074
Change-Id: I9d77ef3e7843db6a5a711481bc1b4622583442e5
  • Loading branch information
tholenst authored and copybara-github committed Sep 20, 2023
1 parent ca962f6 commit ad42346
Show file tree
Hide file tree
Showing 4 changed files with 120 additions and 19 deletions.
16 changes: 16 additions & 0 deletions src/main/java/com/google/crypto/tink/signature/BUILD.bazel
Original file line number Diff line number Diff line change
Expand Up @@ -250,21 +250,29 @@ java_library(
srcs = ["Ed25519PrivateKeyManager.java"],
deps = [
":ed25519_parameters",
":ed25519_private_key",
":ed25519_proto_serialization",
":ed25519_public_key",
":ed25519_public_key_manager",
"//proto:ed25519_java_proto",
"//proto:tink_java_proto",
"//src/main/java/com/google/crypto/tink:accesses_partial_key",
"//src/main/java/com/google/crypto/tink:key_template",
"//src/main/java/com/google/crypto/tink:parameters",
"//src/main/java/com/google/crypto/tink:public_key_sign",
"//src/main/java/com/google/crypto/tink:registry",
"//src/main/java/com/google/crypto/tink:secret_key_access",
"//src/main/java/com/google/crypto/tink/internal:key_type_manager",
"//src/main/java/com/google/crypto/tink/internal:mutable_parameters_registry",
"//src/main/java/com/google/crypto/tink/internal:primitive_factory",
"//src/main/java/com/google/crypto/tink/internal:private_key_type_manager",
"//src/main/java/com/google/crypto/tink/internal:tink_bug_exception",
"//src/main/java/com/google/crypto/tink/internal:util",
"//src/main/java/com/google/crypto/tink/subtle:ed25519_sign",
"//src/main/java/com/google/crypto/tink/subtle:validators",
"//src/main/java/com/google/crypto/tink/util:bytes",
"//src/main/java/com/google/crypto/tink/util:secret_bytes",
"@maven//:com_google_code_findbugs_jsr305",
"@maven//:com_google_protobuf_protobuf_java",
],
)
Expand Down Expand Up @@ -878,21 +886,29 @@ android_library(
srcs = ["Ed25519PrivateKeyManager.java"],
deps = [
":ed25519_parameters-android",
":ed25519_private_key-android",
":ed25519_proto_serialization-android",
":ed25519_public_key-android",
":ed25519_public_key_manager-android",
"//proto:ed25519_java_proto_lite",
"//proto:tink_java_proto_lite",
"//src/main/java/com/google/crypto/tink:accesses_partial_key-android",
"//src/main/java/com/google/crypto/tink:key_template-android",
"//src/main/java/com/google/crypto/tink:parameters-android",
"//src/main/java/com/google/crypto/tink:public_key_sign-android",
"//src/main/java/com/google/crypto/tink:registry-android",
"//src/main/java/com/google/crypto/tink:secret_key_access-android",
"//src/main/java/com/google/crypto/tink/internal:key_type_manager-android",
"//src/main/java/com/google/crypto/tink/internal:mutable_parameters_registry-android",
"//src/main/java/com/google/crypto/tink/internal:primitive_factory-android",
"//src/main/java/com/google/crypto/tink/internal:private_key_type_manager-android",
"//src/main/java/com/google/crypto/tink/internal:tink_bug_exception-android",
"//src/main/java/com/google/crypto/tink/internal:util-android",
"//src/main/java/com/google/crypto/tink/subtle:ed25519_sign-android",
"//src/main/java/com/google/crypto/tink/subtle:validators-android",
"//src/main/java/com/google/crypto/tink/util:bytes-android",
"//src/main/java/com/google/crypto/tink/util:secret_bytes-android",
"@maven//:com_google_code_findbugs_jsr305",
"@maven//:com_google_protobuf_protobuf_javalite",
],
)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,20 +18,25 @@

import static com.google.crypto.tink.internal.TinkBugException.exceptionIsBug;

import com.google.crypto.tink.AccessesPartialKey;
import com.google.crypto.tink.KeyTemplate;
import com.google.crypto.tink.Parameters;
import com.google.crypto.tink.PublicKeySign;
import com.google.crypto.tink.Registry;
import com.google.crypto.tink.SecretKeyAccess;
import com.google.crypto.tink.internal.KeyTypeManager;
import com.google.crypto.tink.internal.MutableParametersRegistry;
import com.google.crypto.tink.internal.PrimitiveFactory;
import com.google.crypto.tink.internal.PrivateKeyTypeManager;
import com.google.crypto.tink.internal.Util;
import com.google.crypto.tink.proto.Ed25519KeyFormat;
import com.google.crypto.tink.proto.Ed25519PrivateKey;
import com.google.crypto.tink.proto.Ed25519PublicKey;
import com.google.crypto.tink.proto.KeyData.KeyMaterialType;
import com.google.crypto.tink.subtle.Ed25519Sign;
import com.google.crypto.tink.subtle.Validators;
import com.google.crypto.tink.util.Bytes;
import com.google.crypto.tink.util.SecretBytes;
import com.google.protobuf.ByteString;
import com.google.protobuf.ExtensionRegistryLite;
import com.google.protobuf.InvalidProtocolBufferException;
Expand All @@ -40,6 +45,7 @@
import java.util.Collections;
import java.util.HashMap;
import java.util.Map;
import javax.annotation.Nullable;

/**
* This instance of {@code KeyManager} generates new {@code Ed25519PrivateKey} keys and produces new
Expand Down Expand Up @@ -123,30 +129,40 @@ public Ed25519PrivateKey createKey(Ed25519KeyFormat format) throws GeneralSecuri
}

@Override
public Ed25519PrivateKey deriveKey(
KeyTypeManager<Ed25519PrivateKey> keyTypeManager,
Ed25519KeyFormat format,
InputStream inputStream)
public com.google.crypto.tink.signature.Ed25519PrivateKey createKeyFromRandomness(
Parameters parameters,
InputStream stream,
@Nullable Integer idRequirement,
SecretKeyAccess access)
throws GeneralSecurityException {
Validators.validateVersion(format.getVersion(), getVersion());

byte[] pseudorandomness = new byte[Ed25519Sign.SECRET_KEY_LEN];
readFully(inputStream, pseudorandomness);
Ed25519Sign.KeyPair keyPair = Ed25519Sign.KeyPair.newKeyPairFromSeed(pseudorandomness);
Ed25519PublicKey publicKey =
Ed25519PublicKey.newBuilder()
.setVersion(getVersion())
.setKeyValue(ByteString.copyFrom(keyPair.getPublicKey()))
.build();
return Ed25519PrivateKey.newBuilder()
.setVersion(getVersion())
.setKeyValue(ByteString.copyFrom(keyPair.getPrivateKey()))
.setPublicKey(publicKey)
.build();
if (parameters instanceof Ed25519Parameters) {
return createEd25519KeyFromRandomness(
(Ed25519Parameters) parameters, stream, idRequirement, access);
}
throw new GeneralSecurityException(
"Unexpected parameters: expected AesFfxFf1Parameters, but got: " + parameters);
}
};
}

@AccessesPartialKey
static com.google.crypto.tink.signature.Ed25519PrivateKey createEd25519KeyFromRandomness(
Ed25519Parameters parameters,
InputStream stream,
@Nullable Integer idRequirement,
SecretKeyAccess access)
throws GeneralSecurityException {
SecretBytes pseudorandomness =
Util.readIntoSecretBytes(stream, Ed25519Sign.SECRET_KEY_LEN, access);
Ed25519Sign.KeyPair keyPair =
Ed25519Sign.KeyPair.newKeyPairFromSeed(pseudorandomness.toByteArray(access));
com.google.crypto.tink.signature.Ed25519PublicKey publicKey =
com.google.crypto.tink.signature.Ed25519PublicKey.create(
parameters.getVariant(), Bytes.copyFrom(keyPair.getPublicKey()), idRequirement);
return com.google.crypto.tink.signature.Ed25519PrivateKey.create(
publicKey, SecretBytes.copyFrom(keyPair.getPrivateKey(), access));
}

private static Map<String, Parameters> namedParameters() throws GeneralSecurityException {
Map<String, Parameters> result = new HashMap<>();
result.put("ED25519", Ed25519Parameters.create(Ed25519Parameters.Variant.TINK));
Expand Down
5 changes: 5 additions & 0 deletions src/test/java/com/google/crypto/tink/signature/BUILD.bazel
Original file line number Diff line number Diff line change
Expand Up @@ -319,6 +319,7 @@ java_test(
deps = [
"//proto:ed25519_java_proto",
"//proto:tink_java_proto",
"//src/main/java/com/google/crypto/tink:insecure_secret_key_access",
"//src/main/java/com/google/crypto/tink:key_template",
"//src/main/java/com/google/crypto/tink:key_templates",
"//src/main/java/com/google/crypto/tink:parameters",
Expand All @@ -327,11 +328,15 @@ java_test(
"//src/main/java/com/google/crypto/tink:registry_cluster",
"//src/main/java/com/google/crypto/tink/internal:key_type_manager",
"//src/main/java/com/google/crypto/tink/signature:ed25519_parameters",
"//src/main/java/com/google/crypto/tink/signature:ed25519_private_key",
"//src/main/java/com/google/crypto/tink/signature:ed25519_private_key_manager",
"//src/main/java/com/google/crypto/tink/signature:ed25519_public_key",
"//src/main/java/com/google/crypto/tink/signature:signature_config",
"//src/main/java/com/google/crypto/tink/subtle:ed25519_verify",
"//src/main/java/com/google/crypto/tink/subtle:hex",
"//src/main/java/com/google/crypto/tink/subtle:random",
"//src/main/java/com/google/crypto/tink/util:bytes",
"//src/main/java/com/google/crypto/tink/util:secret_bytes",
"@maven//:com_google_protobuf_protobuf_java",
"@maven//:com_google_truth_truth",
"@maven//:junit_junit",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,9 @@

import static com.google.common.truth.Truth.assertThat;
import static org.junit.Assert.assertThrows;
import static org.junit.Assert.assertTrue;

import com.google.crypto.tink.InsecureSecretKeyAccess;
import com.google.crypto.tink.KeyTemplate;
import com.google.crypto.tink.KeyTemplates;
import com.google.crypto.tink.KeysetHandle;
Expand All @@ -33,6 +35,8 @@
import com.google.crypto.tink.subtle.Ed25519Verify;
import com.google.crypto.tink.subtle.Hex;
import com.google.crypto.tink.subtle.Random;
import com.google.crypto.tink.util.Bytes;
import com.google.crypto.tink.util.SecretBytes;
import com.google.protobuf.ByteString;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
Expand Down Expand Up @@ -271,4 +275,64 @@ public void testTemplates(@FromDataPoints("templateNames") String templateName)
assertThat(h.getAt(0).getKey().getParameters())
.isEqualTo(KeyTemplates.get(templateName).toParameters());
}

@Test
public void testCreateRawKeyFromRandomness() throws Exception {
byte[] keyMaterial =
Hex.decode(
""
+ "000102030405060708090A0B0C0D0E0F"
+ "101112131415161718191A1B1C1D1E1F"
+ "202122232425262728292A2B2C2D2E2F");
com.google.crypto.tink.signature.Ed25519PrivateKey key =
Ed25519PrivateKeyManager.createEd25519KeyFromRandomness(
Ed25519Parameters.create(Ed25519Parameters.Variant.NO_PREFIX),
new ByteArrayInputStream(keyMaterial),
null,
InsecureSecretKeyAccess.get());
com.google.crypto.tink.signature.Ed25519PublicKey expectedPublicKey =
com.google.crypto.tink.signature.Ed25519PublicKey.create(
Ed25519Parameters.Variant.NO_PREFIX,
Bytes.copyFrom(
Hex.decode("03a107bff3ce10be1d70dd18e74bc09967e4d6309ba50d5f1ddc8664125531b8")),
/* idRequirement= */ null);

com.google.crypto.tink.signature.Ed25519PrivateKey expectedPrivateKey =
com.google.crypto.tink.signature.Ed25519PrivateKey.create(
expectedPublicKey,
SecretBytes.copyFrom(
Hex.decode("000102030405060708090A0B0C0D0E0F101112131415161718191A1B1C1D1E1F"),
InsecureSecretKeyAccess.get()));
assertTrue(key.equalsKey(expectedPrivateKey));
}

@Test
public void testCreateTinkKeyFromRandomness() throws Exception {
byte[] keyMaterial =
Hex.decode(
""
+ "000102030405060708090A0B0C0D0E0F"
+ "101112131415161718191A1B1C1D1E1F"
+ "202122232425262728292A2B2C2D2E2F");
com.google.crypto.tink.signature.Ed25519PrivateKey key =
Ed25519PrivateKeyManager.createEd25519KeyFromRandomness(
Ed25519Parameters.create(Ed25519Parameters.Variant.TINK),
new ByteArrayInputStream(keyMaterial),
2344,
InsecureSecretKeyAccess.get());
com.google.crypto.tink.signature.Ed25519PublicKey expectedPublicKey =
com.google.crypto.tink.signature.Ed25519PublicKey.create(
Ed25519Parameters.Variant.TINK,
Bytes.copyFrom(
Hex.decode("03a107bff3ce10be1d70dd18e74bc09967e4d6309ba50d5f1ddc8664125531b8")),
2344);

com.google.crypto.tink.signature.Ed25519PrivateKey expectedPrivateKey =
com.google.crypto.tink.signature.Ed25519PrivateKey.create(
expectedPublicKey,
SecretBytes.copyFrom(
Hex.decode("000102030405060708090A0B0C0D0E0F101112131415161718191A1B1C1D1E1F"),
InsecureSecretKeyAccess.get()));
assertTrue(key.equalsKey(expectedPrivateKey));
}
}

0 comments on commit ad42346

Please sign in to comment.