View Javadoc
1   /*
2    * GordianKnot: Security Suite
3    * Copyright 2012-2026. Tony Washer
4    *
5    * Licensed under the Apache License, Version 2.0 (the "License"); you may not
6    * use this file except in compliance with the License.  You may obtain a copy
7    * of the License at
8    *
9    *   http://www.apache.org/licenses/LICENSE-2.0
10   *
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
13   * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
14   * License for the specific language governing permissions and limitations under
15   * the License.
16   */
17  package io.github.tonywasher.joceanus.gordianknot.api.cipher;
18  
19  import io.github.tonywasher.joceanus.gordianknot.api.base.GordianIdSpec;
20  
21  import java.util.Objects;
22  
23  /**
24   * The StreamCipherSpec class.
25   */
26  public final class GordianStreamCipherSpec
27          extends GordianCipherSpec<GordianStreamKeySpec>
28          implements GordianIdSpec {
29      /**
30       * The Validity.
31       */
32      private final boolean isValid;
33  
34      /**
35       * Is this an AEAD Spec.
36       */
37      private final boolean isAEAD;
38  
39      /**
40       * The String name.
41       */
42      private String theName;
43  
44      /**
45       * Constructor.
46       *
47       * @param pKeySpec the keySpec
48       */
49      public GordianStreamCipherSpec(final GordianStreamKeySpec pKeySpec) {
50          this(pKeySpec, false);
51      }
52  
53      /**
54       * Constructor.
55       *
56       * @param pKeySpec the keySpec
57       * @param pAEAD    is this an AAD cipher?
58       */
59      public GordianStreamCipherSpec(final GordianStreamKeySpec pKeySpec,
60                                     final boolean pAEAD) {
61          super(pKeySpec);
62          isAEAD = pAEAD;
63          isValid = checkValidity();
64      }
65  
66      @Override
67      public boolean needsIV() {
68          return getKeyType().needsIV();
69      }
70  
71      @Override
72      public int getIVLength() {
73          return getKeyType().getIVLength();
74      }
75  
76      /**
77       * Is the keySpec an AEAD cipher mode?
78       *
79       * @return true/false.
80       */
81      public boolean isAEADMode() {
82          return isAEAD;
83      }
84  
85      /**
86       * Is the keySpec an AEAD cipher?
87       *
88       * @return true/false.
89       */
90      public boolean isAEAD() {
91          return isAEAD || getKeyType().isAEAD();
92      }
93  
94      @Override
95      public boolean isValid() {
96          return isValid;
97      }
98  
99      /**
100      * Check spec validity.
101      *
102      * @return valid true/false
103      */
104     private boolean checkValidity() {
105         /* KeyType must be non-null and valid */
106         final GordianStreamKeySpec mySpec = getKeyType();
107         if (mySpec == null
108                 || !mySpec.isValid()) {
109             return false;
110         }
111 
112         /* KeySpec must support AEAD if requested */
113         return !isAEAD || mySpec.supportsAEAD();
114     }
115 
116     @Override
117     public String toString() {
118         /* If we have not yet loaded the name */
119         if (theName == null) {
120             /* If the keySpec is valid */
121             if (isValid) {
122                 /* Load the name */
123                 theName = super.toString();
124                 if (isAEAD) {
125                     theName += "Poly1305";
126                 }
127             } else {
128                 /* Report invalid spec */
129                 theName = "InvalidStreamCipherSpec: " + getKeyType();
130             }
131         }
132 
133         /* return the name */
134         return theName;
135     }
136 
137     @Override
138     public boolean equals(final Object pThat) {
139         /* Handle the trivial cases */
140         if (this == pThat) {
141             return true;
142         }
143         if (pThat == null) {
144             return false;
145         }
146 
147         /* Check KeyType */
148         return pThat instanceof GordianStreamCipherSpec myThat
149                 && getKeyType().equals(myThat.getKeyType())
150                 && isAEAD == myThat.isAEADMode();
151     }
152 
153     @Override
154     public int hashCode() {
155         return Objects.hash(getKeyType(), isAEADMode());
156     }
157 }