1 /* 2 * Copyright (C) 2019 The Android Open Source Project 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 17 package android.net.ipsec.ike; 18 19 import android.annotation.NonNull; 20 import android.annotation.SystemApi; 21 22 import com.android.internal.net.ipsec.ike.exceptions.AuthenticationFailedException; 23 24 import java.nio.charset.Charset; 25 import java.security.cert.X509Certificate; 26 import java.util.Objects; 27 28 /** 29 * IkeFqdnIdentification represents an IKE entity identification based on a fully-qualified domain 30 * name (FQDN). An example might be ike.android.com 31 * 32 * @hide 33 */ 34 @SystemApi 35 public class IkeFqdnIdentification extends IkeIdentification { 36 private static final Charset ASCII = Charset.forName("US-ASCII"); 37 38 /** The fully-qualified domain name(FQDN). */ 39 @NonNull public final String fqdn; 40 41 /** 42 * Construct an instance of IkeFqdnIdentification from a decoded inbound packet. 43 * 44 * @param fqdnBytes FQDN in byte array. 45 * @hide 46 */ IkeFqdnIdentification(byte[] fqdnBytes)47 public IkeFqdnIdentification(byte[] fqdnBytes) { 48 super(ID_TYPE_FQDN); 49 fqdn = new String(fqdnBytes, ASCII); 50 } 51 52 /** 53 * Construct an instance of {@link IkeFqdnIdentification} with a fully-qualified domain name. 54 * 55 * @param fqdn the fully-qualified domain name (FQDN). Must contain only US-ASCII characters, 56 * otherwise an IllegalArugmentException will be thrown. 57 */ IkeFqdnIdentification(@onNull String fqdn)58 public IkeFqdnIdentification(@NonNull String fqdn) { 59 super(ID_TYPE_FQDN); 60 if (!ASCII.newEncoder().canEncode(fqdn)) { 61 throw new IllegalArgumentException("Non US-ASCII character set used"); 62 } 63 64 this.fqdn = fqdn; 65 } 66 67 /** @hide */ 68 @Override hashCode()69 public int hashCode() { 70 // idType is also hashed to prevent collisions with other IkeAuthentication subtypes 71 return Objects.hash(idType, fqdn); 72 } 73 74 /** @hide */ 75 @Override equals(Object o)76 public boolean equals(Object o) { 77 if (!(o instanceof IkeFqdnIdentification)) return false; 78 79 // idType already verified based on class type; no need to check again. 80 return fqdn.equals(((IkeFqdnIdentification) o).fqdn); 81 } 82 83 /** @hide */ 84 @Override getIdTypeString()85 public String getIdTypeString() { 86 return "FQDN"; 87 } 88 89 /** @hide */ 90 @Override validateEndCertIdOrThrow(X509Certificate endCert)91 public void validateEndCertIdOrThrow(X509Certificate endCert) 92 throws AuthenticationFailedException { 93 // The corresponding SAN type is DNS Name as per RFC 7296 94 validateEndCertSanOrThrow(endCert, SAN_TYPE_DNS, fqdn); 95 } 96 97 /** 98 * Retrieve the byte-representation of the FQDN. 99 * 100 * @return the byte-representation of the FQDN. 101 * @hide 102 */ 103 @Override getEncodedIdData()104 public byte[] getEncodedIdData() { 105 return fqdn.getBytes(ASCII); 106 } 107 } 108