1 /*
2  * Copyright (C) 2017 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.wifi.hotspot2;
18 
19 import android.annotation.NonNull;
20 import android.annotation.Nullable;
21 import android.annotation.SystemApi;
22 import android.net.Uri;
23 import android.net.wifi.WifiSsid;
24 import android.os.Bundle;
25 import android.os.Parcel;
26 import android.os.Parcelable;
27 import android.text.TextUtils;
28 
29 import java.nio.charset.StandardCharsets;
30 import java.util.ArrayList;
31 import java.util.HashMap;
32 import java.util.List;
33 import java.util.Locale;
34 import java.util.Map;
35 import java.util.Objects;
36 
37 /**
38  * Contained information for a Hotspot 2.0 OSU (Online Sign-Up provider).
39  *
40  * @hide
41  */
42 @SystemApi
43 public final class OsuProvider implements Parcelable {
44     /**
45      * OSU (Online Sign-Up) method: OMA DM (Open Mobile Alliance Device Management).
46      * For more info, refer to Section 8.3 of the Hotspot 2.0 Release 2 Technical Specification.
47      * @hide
48      */
49     public static final int METHOD_OMA_DM = 0;
50 
51     /**
52      * OSU (Online Sign-Up) method: SOAP XML SPP (Subscription Provisioning Protocol).
53      * For more info, refer to Section 8.4 of the Hotspot 2.0 Release 2 Technical Specification.
54      * @hide
55      */
56     public static final int METHOD_SOAP_XML_SPP = 1;
57 
58     /**
59      * SSID of the network to connect for service sign-up.
60      */
61     private WifiSsid mOsuSsid;
62 
63     /**
64      * Map of friendly names expressed as different language for the OSU provider.
65      */
66     private final Map<String, String> mFriendlyNames;
67 
68     /**
69      * Description of the OSU provider.
70      */
71     private final String mServiceDescription;
72 
73     /**
74      * URI to browse to for service sign-up.
75      */
76     private final Uri mServerUri;
77 
78     /**
79      * Network Access Identifier used for authenticating with the OSU network when OSEN is used.
80      */
81     private final String mNetworkAccessIdentifier;
82 
83     /**
84      * List of OSU (Online Sign-Up) method supported.
85      */
86     private final List<Integer> mMethodList;
87 
88     /** @hide */
OsuProvider(String osuSsid, Map<String, String> friendlyNames, String serviceDescription, Uri serverUri, String nai, List<Integer> methodList)89     public OsuProvider(String osuSsid, Map<String, String> friendlyNames,
90             String serviceDescription, Uri serverUri, String nai, List<Integer> methodList) {
91         this(WifiSsid.fromBytes(osuSsid.getBytes(StandardCharsets.UTF_8)),
92                 friendlyNames, serviceDescription, serverUri, nai, methodList);
93     }
94 
95     /** @hide */
OsuProvider(WifiSsid osuSsid, Map<String, String> friendlyNames, String serviceDescription, Uri serverUri, String nai, List<Integer> methodList)96     public OsuProvider(WifiSsid osuSsid, Map<String, String> friendlyNames,
97             String serviceDescription, Uri serverUri, String nai, List<Integer> methodList) {
98         mOsuSsid = osuSsid;
99         mFriendlyNames = friendlyNames;
100         mServiceDescription = serviceDescription;
101         mServerUri = serverUri;
102         mNetworkAccessIdentifier = nai;
103         if (methodList == null) {
104             mMethodList = new ArrayList<>();
105         } else {
106             mMethodList = new ArrayList<>(methodList);
107         }
108     }
109 
110     /**
111      * Copy constructor.
112      *
113      * @param source The source to copy from
114      * @hide
115      */
OsuProvider(OsuProvider source)116     public OsuProvider(OsuProvider source) {
117         if (source == null) {
118             mOsuSsid = null;
119             mFriendlyNames = null;
120             mServiceDescription = null;
121             mServerUri = null;
122             mNetworkAccessIdentifier = null;
123             mMethodList = new ArrayList<>();
124             return;
125         }
126 
127         mOsuSsid = source.mOsuSsid;
128         mFriendlyNames = source.mFriendlyNames;
129         mServiceDescription = source.mServiceDescription;
130         mServerUri = source.mServerUri;
131         mNetworkAccessIdentifier = source.mNetworkAccessIdentifier;
132         if (source.mMethodList == null) {
133             mMethodList = new ArrayList<>();
134         } else {
135             mMethodList = new ArrayList<>(source.mMethodList);
136         }
137     }
138 
139     /** @hide */
getOsuSsid()140     public WifiSsid getOsuSsid() {
141         return mOsuSsid;
142     }
143 
144     /** @hide */
setOsuSsid(WifiSsid osuSsid)145     public void setOsuSsid(WifiSsid osuSsid) {
146         mOsuSsid = osuSsid;
147     }
148 
149     /**
150      * Return the friendly Name for current language from the list of friendly names of OSU
151      * provider.
152      *
153      * The string matching the default locale will be returned if it is found, otherwise the string
154      * in english or the first string in the list will be returned if english is not found.
155      * A null will be returned if the list is empty.
156      *
157      * @return String matching the default locale, null otherwise
158      */
getFriendlyName()159     public @Nullable String getFriendlyName() {
160         if (mFriendlyNames == null || mFriendlyNames.isEmpty()) return null;
161         String lang = Locale.getDefault().getLanguage();
162         String friendlyName = mFriendlyNames.get(lang);
163         if (friendlyName != null) {
164             return friendlyName;
165         }
166         friendlyName = mFriendlyNames.get("en");
167         if (friendlyName != null) {
168             return friendlyName;
169         }
170         return mFriendlyNames.get(mFriendlyNames.keySet().stream().findFirst().get());
171     }
172 
173     /** @hide */
getFriendlyNameList()174     public Map<String, String> getFriendlyNameList() {
175         return mFriendlyNames;
176     }
177 
178     /** @hide */
getServiceDescription()179     public String getServiceDescription() {
180         return mServiceDescription;
181     }
182 
getServerUri()183     public @Nullable Uri getServerUri() {
184         return mServerUri;
185     }
186 
187     /** @hide */
getNetworkAccessIdentifier()188     public String getNetworkAccessIdentifier() {
189         return mNetworkAccessIdentifier;
190     }
191 
192     /** @hide */
getMethodList()193     public List<Integer> getMethodList() {
194         return mMethodList;
195     }
196 
197     @Override
describeContents()198     public int describeContents() {
199         return 0;
200     }
201 
202     @Override
writeToParcel(Parcel dest, int flags)203     public void writeToParcel(Parcel dest, int flags) {
204         dest.writeParcelable(mOsuSsid, flags);
205         dest.writeString(mServiceDescription);
206         dest.writeParcelable(mServerUri, flags);
207         dest.writeString(mNetworkAccessIdentifier);
208         dest.writeList(mMethodList);
209         Bundle bundle = new Bundle();
210         bundle.putSerializable("friendlyNameMap", (HashMap<String, String>) mFriendlyNames);
211         dest.writeBundle(bundle);
212     }
213 
214     @Override
equals(@ullable Object thatObject)215     public boolean equals(@Nullable Object thatObject) {
216         if (this == thatObject) {
217             return true;
218         }
219         if (!(thatObject instanceof OsuProvider)) {
220             return false;
221         }
222         OsuProvider that = (OsuProvider) thatObject;
223         return Objects.equals(mOsuSsid, that.mOsuSsid)
224                 && Objects.equals(mFriendlyNames, that.mFriendlyNames)
225                 && TextUtils.equals(mServiceDescription, that.mServiceDescription)
226                 && Objects.equals(mServerUri, that.mServerUri)
227                 && TextUtils.equals(mNetworkAccessIdentifier, that.mNetworkAccessIdentifier)
228                 && Objects.equals(mMethodList, that.mMethodList);
229     }
230 
231     @Override
hashCode()232     public int hashCode() {
233         return Objects.hash(mOsuSsid, mServiceDescription, mFriendlyNames,
234                 mServerUri, mNetworkAccessIdentifier, mMethodList);
235     }
236 
237     @NonNull
238     @Override
toString()239     public String toString() {
240         return "OsuProvider{mOsuSsid=" + mOsuSsid
241                 + " mFriendlyNames=" + mFriendlyNames
242                 + " mServiceDescription=" + mServiceDescription
243                 + " mServerUri=" + mServerUri
244                 + " mNetworkAccessIdentifier=" + mNetworkAccessIdentifier
245                 + " mMethodList=" + mMethodList;
246     }
247 
248     public static final @android.annotation.NonNull Creator<OsuProvider> CREATOR =
249             new Creator<OsuProvider>() {
250                 @Override
251                 public OsuProvider createFromParcel(Parcel in) {
252                     WifiSsid osuSsid = in.readParcelable(null);
253                     String serviceDescription = in.readString();
254                     Uri serverUri = in.readParcelable(null);
255                     String nai = in.readString();
256                     List<Integer> methodList = new ArrayList<>();
257                     in.readList(methodList, null);
258                     Bundle bundle = in.readBundle();
259                     Map<String, String> friendlyNamesMap = (HashMap) bundle.getSerializable(
260                             "friendlyNameMap");
261                     return new OsuProvider(osuSsid, friendlyNamesMap, serviceDescription,
262                             serverUri, nai, methodList);
263                 }
264 
265             @Override
266             public OsuProvider[] newArray(int size) {
267                 return new OsuProvider[size];
268             }
269         };
270 }
271