1 package com.android.server.wifi.hotspot2.anqp; 2 3 import com.android.internal.annotations.VisibleForTesting; 4 5 import java.net.ProtocolException; 6 import java.nio.BufferUnderflowException; 7 import java.nio.ByteBuffer; 8 import java.nio.charset.StandardCharsets; 9 import java.util.ArrayList; 10 import java.util.Collections; 11 import java.util.List; 12 13 /** 14 * The Operator Friendly Name vendor specific ANQP Element, 15 * Wi-Fi Alliance Hotspot 2.0 (Release 2) Technical Specification - Version 5.00, 16 * section 4.3. 17 * 18 * Format: 19 * 20 * | Operator Name Duple #1 (optional) | ... 21 * variable 22 * 23 * | Operator Name Duple #N (optional) | 24 * variable 25 */ 26 public class HSFriendlyNameElement extends ANQPElement { 27 /** 28 * Maximum length for an Operator Name. Refer to Hotspot 2.0 (Release 2) Technical 29 * Specification section 4.3 for more info. 30 */ 31 @VisibleForTesting 32 public static final int MAXIMUM_OPERATOR_NAME_LENGTH = 252; 33 34 private final List<I18Name> mNames; 35 36 @VisibleForTesting 37 public HSFriendlyNameElement(List<I18Name> names) { 38 super(Constants.ANQPElementType.HSFriendlyName); 39 mNames = names; 40 } 41 42 /** 43 * Parse a HSFriendlyNameElement from the given buffer. 44 * 45 * @param payload The buffer to read from 46 * @return {@link HSFriendlyNameElement} 47 * @throws BufferUnderflowException 48 * @throws ProtocolException 49 */ 50 public static HSFriendlyNameElement parse(ByteBuffer payload) 51 throws ProtocolException { 52 List<I18Name> names = new ArrayList<I18Name>(); 53 while (payload.hasRemaining()) { 54 I18Name name = I18Name.parse(payload); 55 // Verify that the number of bytes for the operator name doesn't exceed the max 56 // allowed. 57 int textBytes = name.getText().getBytes(StandardCharsets.UTF_8).length; 58 if (textBytes > MAXIMUM_OPERATOR_NAME_LENGTH) { 59 throw new ProtocolException("Operator Name exceeds the maximum allowed " 60 + textBytes); 61 } 62 names.add(name); 63 } 64 return new HSFriendlyNameElement(names); 65 } 66 67 public List<I18Name> getNames() { 68 return Collections.unmodifiableList(mNames); 69 } 70 71 @Override 72 public boolean equals(Object thatObject) { 73 if (this == thatObject) { 74 return true; 75 } 76 if (!(thatObject instanceof HSFriendlyNameElement)) { 77 return false; 78 } 79 HSFriendlyNameElement that = (HSFriendlyNameElement) thatObject; 80 return mNames.equals(that.mNames); 81 } 82 83 @Override 84 public int hashCode() { 85 return mNames.hashCode(); 86 } 87 88 @Override 89 public String toString() { 90 return "HSFriendlyName{" + 91 "mNames=" + mNames + 92 '}'; 93 } 94 } 95