• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2023 Google LLC
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 //      http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14 //
15 ////////////////////////////////////////////////////////////////////////////////
16 
17 package com.google.crypto.tink.keyderivation;
18 
19 import com.google.crypto.tink.AccessesPartialKey;
20 import com.google.crypto.tink.Key;
21 import com.google.crypto.tink.prf.PrfKey;
22 import com.google.errorprone.annotations.RestrictedApi;
23 import java.security.GeneralSecurityException;
24 import java.util.Objects;
25 import javax.annotation.Nullable;
26 
27 /**
28  * Represents a Derivation key which is based on a PRF.
29  *
30  * <p>An object of this class represents the map which 1) uses the given PRF (as specified by {@link
31  * #getPrfKey}) to get sufficient key material from the salt, then 2) creates a key for the
32  * parameters as specified in {@code getParameters().getDerivedKeyParameters()}.
33  */
34 public final class PrfBasedKeyDerivationKey extends KeyDerivationKey {
35   @RestrictedApi(
36       explanation = "Accessing parts of keys can produce unexpected incompatibilities, annotate the function with @AccessesPartialKey",
37       link = "https://developers.google.com/tink/design/access_control#accessing_partial_keys",
38       allowedOnPath = ".*Test\\.java",
39       allowlistAnnotations = {AccessesPartialKey.class})
create( PrfBasedKeyDerivationParameters parameters, PrfKey prfKey, @Nullable Integer idRequirement)40   public static PrfBasedKeyDerivationKey create(
41       PrfBasedKeyDerivationParameters parameters, PrfKey prfKey, @Nullable Integer idRequirement)
42       throws GeneralSecurityException {
43     if (!parameters.getPrfParameters().equals(prfKey.getParameters())) {
44       throw new GeneralSecurityException(
45           "PrfParameters of passed in PrfBasedKeyDerivationParameters and passed in prfKey"
46               + " parameters object must match. DerivationParameters gave: "
47               + parameters.getPrfParameters()
48               + ", key gives: "
49               + prfKey.getParameters());
50     }
51     if (parameters.getDerivedKeyParameters().hasIdRequirement()) {
52       if (idRequirement == null) {
53         throw new GeneralSecurityException(
54             "Derived key has an ID requirement, but no idRequirement was passed in on creation of"
55                 + " this key");
56       }
57     }
58     if (!parameters.getDerivedKeyParameters().hasIdRequirement()) {
59       if (idRequirement != null) {
60         throw new GeneralSecurityException(
61             "Derived key has no ID requirement, but idRequirement was passed in on creation of"
62                 + " this key");
63       }
64     }
65     return new PrfBasedKeyDerivationKey(parameters, prfKey, idRequirement);
66   }
67 
68   private final PrfBasedKeyDerivationParameters parameters;
69   private final PrfKey prfKey;
70   private final Integer idRequirementOrNull;
71 
PrfBasedKeyDerivationKey( PrfBasedKeyDerivationParameters parameters, PrfKey prfKey, @Nullable Integer idRequirement)72   private PrfBasedKeyDerivationKey(
73       PrfBasedKeyDerivationParameters parameters, PrfKey prfKey, @Nullable Integer idRequirement) {
74     this.parameters = parameters;
75     this.prfKey = prfKey;
76     this.idRequirementOrNull = idRequirement;
77   }
78 
79   @RestrictedApi(
80       explanation = "Accessing parts of keys can produce unexpected incompatibilities, annotate the function with @AccessesPartialKey",
81       link = "https://developers.google.com/tink/design/access_control#accessing_partial_keys",
82       allowedOnPath = ".*Test\\.java",
83       allowlistAnnotations = {AccessesPartialKey.class})
getPrfKey()84   public PrfKey getPrfKey() {
85     return prfKey;
86   }
87 
88   @Override
getParameters()89   public PrfBasedKeyDerivationParameters getParameters() {
90     return parameters;
91   }
92 
93   @Override
94   @Nullable
getIdRequirementOrNull()95   public Integer getIdRequirementOrNull() {
96     return idRequirementOrNull;
97   }
98 
99   @Override
equalsKey(Key other)100   public boolean equalsKey(Key other) {
101     if (!(other instanceof PrfBasedKeyDerivationKey)) {
102       return false;
103     }
104 
105     PrfBasedKeyDerivationKey otherKey = (PrfBasedKeyDerivationKey) other;
106     return otherKey.getParameters().equals(getParameters())
107         && otherKey.prfKey.equalsKey(prfKey)
108         && Objects.equals(otherKey.idRequirementOrNull, idRequirementOrNull);
109   }
110 }
111