Home | History | Annotate | Download | only in 1.2
      1 /*
      2  * hidl interface for wpa_supplicant daemon
      3  * Copyright (c) 2004-2016, Jouni Malinen <j (at) w1.fi>
      4  * Copyright (c) 2004-2016, Roshan Pius <rpius (at) google.com>
      5  *
      6  * This software may be distributed under the terms of the BSD license.
      7  * See README for more details.
      8  */
      9 
     10 #include <algorithm>
     11 #include <regex>
     12 
     13 #include "hidl_manager.h"
     14 #include "misc_utils.h"
     15 
     16 extern "C" {
     17 #include "scan.h"
     18 #include "src/eap_common/eap_sim_common.h"
     19 }
     20 
     21 namespace {
     22 using android::hardware::hidl_array;
     23 using namespace android::hardware::wifi::supplicant::V1_2;
     24 
     25 constexpr uint8_t kWfdDeviceInfoLen = 6;
     26 // GSM-AUTH:<RAND1>:<RAND2>[:<RAND3>]
     27 constexpr char kGsmAuthRegex2[] = "GSM-AUTH:([0-9a-f]+):([0-9a-f]+)";
     28 constexpr char kGsmAuthRegex3[] =
     29     "GSM-AUTH:([0-9a-f]+):([0-9a-f]+):([0-9a-f]+)";
     30 // UMTS-AUTH:<RAND>:<AUTN>
     31 constexpr char kUmtsAuthRegex[] = "UMTS-AUTH:([0-9a-f]+):([0-9a-f]+)";
     32 constexpr size_t kGsmRandLenBytes = GSM_RAND_LEN;
     33 constexpr size_t kUmtsRandLenBytes = EAP_AKA_RAND_LEN;
     34 constexpr size_t kUmtsAutnLenBytes = EAP_AKA_AUTN_LEN;
     35 constexpr u8 kZeroBssid[6] = {0, 0, 0, 0, 0, 0};
     36 /**
     37  * Check if the provided |wpa_supplicant| structure represents a P2P iface or
     38  * not.
     39  */
     40 constexpr bool isP2pIface(const struct wpa_supplicant *wpa_s)
     41 {
     42 	return (wpa_s->global->p2p_init_wpa_s == wpa_s);
     43 }
     44 
     45 /**
     46  * Creates a unique key for the network using the provided |ifname| and
     47  * |network_id| to be used in the internal map of |ISupplicantNetwork| objects.
     48  * This is of the form |ifname|_|network_id|. For ex: "wlan0_1".
     49  *
     50  * @param ifname Name of the corresponding interface.
     51  * @param network_id ID of the corresponding network.
     52  */
     53 const std::string getNetworkObjectMapKey(
     54     const std::string &ifname, int network_id)
     55 {
     56 	return ifname + "_" + std::to_string(network_id);
     57 }
     58 
     59 /**
     60  * Add callback to the corresponding list after linking to death on the
     61  * corresponding hidl object reference.
     62  */
     63 template <class CallbackType>
     64 int registerForDeathAndAddCallbackHidlObjectToList(
     65     const android::sp<CallbackType> &callback,
     66     const std::function<void(const android::sp<CallbackType> &)>
     67 	&on_hidl_died_fctor,
     68     std::vector<android::sp<CallbackType>> &callback_list)
     69 {
     70 #if 0   // TODO(b/31632518): HIDL object death notifications.
     71 	auto death_notifier = new CallbackObjectDeathNotifier<CallbackType>(
     72 	    callback, on_hidl_died_fctor);
     73 	// Use the |callback.get()| as cookie so that we don't need to
     74 	// store a reference to this |CallbackObjectDeathNotifier| instance
     75 	// to use in |unlinkToDeath| later.
     76 	// NOTE: This may cause an immediate callback if the object is already
     77 	// dead, so add it to the list before we register for callback!
     78 	if (android::hardware::IInterface::asBinder(callback)->linkToDeath(
     79 		death_notifier, callback.get()) != android::OK) {
     80 		wpa_printf(
     81 		    MSG_ERROR,
     82 		    "Error registering for death notification for "
     83 		    "supplicant callback object");
     84 		callback_list.erase(
     85 		    std::remove(
     86 			callback_list.begin(), callback_list.end(), callback),
     87 		    callback_list.end());
     88 		return 1;
     89 	}
     90 #endif  // TODO(b/31632518): HIDL object death notifications.
     91 	callback_list.push_back(callback);
     92 	return 0;
     93 }
     94 
     95 template <class ObjectType>
     96 int addHidlObjectToMap(
     97     const std::string &key, const android::sp<ObjectType> object,
     98     std::map<const std::string, android::sp<ObjectType>> &object_map)
     99 {
    100 	// Return failure if we already have an object for that |key|.
    101 	if (object_map.find(key) != object_map.end())
    102 		return 1;
    103 	object_map[key] = object;
    104 	if (!object_map[key].get())
    105 		return 1;
    106 	return 0;
    107 }
    108 
    109 template <class ObjectType>
    110 int removeHidlObjectFromMap(
    111     const std::string &key,
    112     std::map<const std::string, android::sp<ObjectType>> &object_map)
    113 {
    114 	// Return failure if we dont have an object for that |key|.
    115 	const auto &object_iter = object_map.find(key);
    116 	if (object_iter == object_map.end())
    117 		return 1;
    118 	object_iter->second->invalidate();
    119 	object_map.erase(object_iter);
    120 	return 0;
    121 }
    122 
    123 template <class CallbackType>
    124 int addIfaceCallbackHidlObjectToMap(
    125     const std::string &ifname, const android::sp<CallbackType> &callback,
    126     const std::function<void(const android::sp<CallbackType> &)>
    127 	&on_hidl_died_fctor,
    128     std::map<const std::string, std::vector<android::sp<CallbackType>>>
    129 	&callbacks_map)
    130 {
    131 	if (ifname.empty())
    132 		return 1;
    133 
    134 	auto iface_callback_map_iter = callbacks_map.find(ifname);
    135 	if (iface_callback_map_iter == callbacks_map.end())
    136 		return 1;
    137 	auto &iface_callback_list = iface_callback_map_iter->second;
    138 
    139 	// Register for death notification before we add it to our list.
    140 	return registerForDeathAndAddCallbackHidlObjectToList<CallbackType>(
    141 	    callback, on_hidl_died_fctor, iface_callback_list);
    142 }
    143 
    144 template <class CallbackType>
    145 int addNetworkCallbackHidlObjectToMap(
    146     const std::string &ifname, int network_id,
    147     const android::sp<CallbackType> &callback,
    148     const std::function<void(const android::sp<CallbackType> &)>
    149 	&on_hidl_died_fctor,
    150     std::map<const std::string, std::vector<android::sp<CallbackType>>>
    151 	&callbacks_map)
    152 {
    153 	if (ifname.empty() || network_id < 0)
    154 		return 1;
    155 
    156 	// Generate the key to be used to lookup the network.
    157 	const std::string network_key =
    158 	    getNetworkObjectMapKey(ifname, network_id);
    159 	auto network_callback_map_iter = callbacks_map.find(network_key);
    160 	if (network_callback_map_iter == callbacks_map.end())
    161 		return 1;
    162 	auto &network_callback_list = network_callback_map_iter->second;
    163 
    164 	// Register for death notification before we add it to our list.
    165 	return registerForDeathAndAddCallbackHidlObjectToList<CallbackType>(
    166 	    callback, on_hidl_died_fctor, network_callback_list);
    167 }
    168 
    169 template <class CallbackType>
    170 int removeAllIfaceCallbackHidlObjectsFromMap(
    171     const std::string &ifname,
    172     std::map<const std::string, std::vector<android::sp<CallbackType>>>
    173 	&callbacks_map)
    174 {
    175 	auto iface_callback_map_iter = callbacks_map.find(ifname);
    176 	if (iface_callback_map_iter == callbacks_map.end())
    177 		return 1;
    178 #if 0   // TODO(b/31632518): HIDL object death notifications.
    179 	const auto &iface_callback_list = iface_callback_map_iter->second;
    180 	for (const auto &callback : iface_callback_list) {
    181 		if (android::hardware::IInterface::asBinder(callback)
    182 			->unlinkToDeath(nullptr, callback.get()) !=
    183 		    android::OK) {
    184 			wpa_printf(
    185 			    MSG_ERROR,
    186 			    "Error deregistering for death notification for "
    187 			    "iface callback object");
    188 		}
    189 	}
    190 #endif  // TODO(b/31632518): HIDL object death notifications.
    191 	callbacks_map.erase(iface_callback_map_iter);
    192 	return 0;
    193 }
    194 
    195 template <class CallbackType>
    196 int removeAllNetworkCallbackHidlObjectsFromMap(
    197     const std::string &network_key,
    198     std::map<const std::string, std::vector<android::sp<CallbackType>>>
    199 	&callbacks_map)
    200 {
    201 	auto network_callback_map_iter = callbacks_map.find(network_key);
    202 	if (network_callback_map_iter == callbacks_map.end())
    203 		return 1;
    204 #if 0   // TODO(b/31632518): HIDL object death notifications.
    205 	const auto &network_callback_list = network_callback_map_iter->second;
    206 	for (const auto &callback : network_callback_list) {
    207 		if (android::hardware::IInterface::asBinder(callback)
    208 			->unlinkToDeath(nullptr, callback.get()) !=
    209 		    android::OK) {
    210 			wpa_printf(
    211 			    MSG_ERROR,
    212 			    "Error deregistering for death "
    213 			    "notification for "
    214 			    "network callback object");
    215 		}
    216 	}
    217 #endif  // TODO(b/31632518): HIDL object death notifications.
    218 	callbacks_map.erase(network_callback_map_iter);
    219 	return 0;
    220 }
    221 
    222 template <class CallbackType>
    223 void removeIfaceCallbackHidlObjectFromMap(
    224     const std::string &ifname, const android::sp<CallbackType> &callback,
    225     std::map<const std::string, std::vector<android::sp<CallbackType>>>
    226 	&callbacks_map)
    227 {
    228 	if (ifname.empty())
    229 		return;
    230 
    231 	auto iface_callback_map_iter = callbacks_map.find(ifname);
    232 	if (iface_callback_map_iter == callbacks_map.end())
    233 		return;
    234 
    235 	auto &iface_callback_list = iface_callback_map_iter->second;
    236 	iface_callback_list.erase(
    237 	    std::remove(
    238 		iface_callback_list.begin(), iface_callback_list.end(),
    239 		callback),
    240 	    iface_callback_list.end());
    241 }
    242 
    243 template <class CallbackType>
    244 void removeNetworkCallbackHidlObjectFromMap(
    245     const std::string &ifname, int network_id,
    246     const android::sp<CallbackType> &callback,
    247     std::map<const std::string, std::vector<android::sp<CallbackType>>>
    248 	&callbacks_map)
    249 {
    250 	if (ifname.empty() || network_id < 0)
    251 		return;
    252 
    253 	// Generate the key to be used to lookup the network.
    254 	const std::string network_key =
    255 	    getNetworkObjectMapKey(ifname, network_id);
    256 
    257 	auto network_callback_map_iter = callbacks_map.find(network_key);
    258 	if (network_callback_map_iter == callbacks_map.end())
    259 		return;
    260 
    261 	auto &network_callback_list = network_callback_map_iter->second;
    262 	network_callback_list.erase(
    263 	    std::remove(
    264 		network_callback_list.begin(), network_callback_list.end(),
    265 		callback),
    266 	    network_callback_list.end());
    267 }
    268 
    269 template <class CallbackType>
    270 void callWithEachIfaceCallback(
    271     const std::string &ifname,
    272     const std::function<
    273 	android::hardware::Return<void>(android::sp<CallbackType>)> &method,
    274     const std::map<const std::string, std::vector<android::sp<CallbackType>>>
    275 	&callbacks_map)
    276 {
    277 	if (ifname.empty())
    278 		return;
    279 
    280 	auto iface_callback_map_iter = callbacks_map.find(ifname);
    281 	if (iface_callback_map_iter == callbacks_map.end())
    282 		return;
    283 	const auto &iface_callback_list = iface_callback_map_iter->second;
    284 	for (const auto &callback : iface_callback_list) {
    285 		if (!method(callback).isOk()) {
    286 			wpa_printf(
    287 			    MSG_ERROR, "Failed to invoke HIDL iface callback");
    288 		}
    289 	}
    290 }
    291 
    292 template <class CallbackTypeV1_0, class CallbackTypeV1_1>
    293 void callWithEachIfaceCallback_1_1(
    294     const std::string &ifname,
    295     const std::function<
    296 	android::hardware::Return<void>(android::sp<CallbackTypeV1_1>)> &method,
    297     const std::map<
    298 	const std::string, std::vector<android::sp<CallbackTypeV1_0>>>
    299 	&callbacks_map)
    300 {
    301 	if (ifname.empty())
    302 		return;
    303 
    304 	auto iface_callback_map_iter = callbacks_map.find(ifname);
    305 	if (iface_callback_map_iter == callbacks_map.end())
    306 		return;
    307 	const auto &iface_callback_list = iface_callback_map_iter->second;
    308 	for (const auto &callback : iface_callback_list) {
    309 		android::sp<CallbackTypeV1_1> callback_1_1 =
    310 		    CallbackTypeV1_1::castFrom(callback);
    311 		if (callback_1_1 == nullptr)
    312 			continue;
    313 
    314 		if (!method(callback_1_1).isOk()) {
    315 			wpa_printf(
    316 			    MSG_ERROR, "Failed to invoke HIDL iface callback");
    317 		}
    318 	}
    319 }
    320 
    321 template <class CallbackTypeV1_0, class CallbackTypeV1_2>
    322 void callWithEachIfaceCallback_1_2(
    323     const std::string &ifname,
    324     const std::function<
    325 	android::hardware::Return<void>(android::sp<CallbackTypeV1_2>)> &method,
    326     const std::map<
    327 	const std::string, std::vector<android::sp<CallbackTypeV1_0>>>
    328 	&callbacks_map)
    329 {
    330 	if (ifname.empty())
    331 		return;
    332 
    333 	auto iface_callback_map_iter = callbacks_map.find(ifname);
    334 	if (iface_callback_map_iter == callbacks_map.end())
    335 		return;
    336 	const auto &iface_callback_list = iface_callback_map_iter->second;
    337 	for (const auto &callback : iface_callback_list) {
    338 		android::sp<CallbackTypeV1_2> callback_1_2 =
    339 		    CallbackTypeV1_2::castFrom(callback);
    340 		if (callback_1_2 == nullptr)
    341 			continue;
    342 
    343 		if (!method(callback_1_2).isOk()) {
    344 			wpa_printf(
    345 			    MSG_ERROR, "Failed to invoke HIDL iface callback");
    346 		}
    347 	}
    348 }
    349 
    350 template <class CallbackType>
    351 void callWithEachNetworkCallback(
    352     const std::string &ifname, int network_id,
    353     const std::function<
    354 	android::hardware::Return<void>(android::sp<CallbackType>)> &method,
    355     const std::map<const std::string, std::vector<android::sp<CallbackType>>>
    356 	&callbacks_map)
    357 {
    358 	if (ifname.empty() || network_id < 0)
    359 		return;
    360 
    361 	// Generate the key to be used to lookup the network.
    362 	const std::string network_key =
    363 	    getNetworkObjectMapKey(ifname, network_id);
    364 	auto network_callback_map_iter = callbacks_map.find(network_key);
    365 	if (network_callback_map_iter == callbacks_map.end())
    366 		return;
    367 	const auto &network_callback_list = network_callback_map_iter->second;
    368 	for (const auto &callback : network_callback_list) {
    369 		if (!method(callback).isOk()) {
    370 			wpa_printf(
    371 			    MSG_ERROR,
    372 			    "Failed to invoke HIDL network callback");
    373 		}
    374 	}
    375 }
    376 
    377 int parseGsmAuthNetworkRequest(
    378     const std::string &params_str,
    379     std::vector<hidl_array<uint8_t, kGsmRandLenBytes>> *out_rands)
    380 {
    381 	std::smatch matches;
    382 	std::regex params_gsm_regex2(kGsmAuthRegex2);
    383 	std::regex params_gsm_regex3(kGsmAuthRegex3);
    384 	if (!std::regex_match(params_str, matches, params_gsm_regex3) &&
    385 	    !std::regex_match(params_str, matches, params_gsm_regex2)) {
    386 		return 1;
    387 	}
    388 	for (uint32_t i = 1; i < matches.size(); i++) {
    389 		hidl_array<uint8_t, kGsmRandLenBytes> rand;
    390 		const auto &match = matches[i];
    391 		WPA_ASSERT(match.size() >= 2 * rand.size());
    392 		if (hexstr2bin(match.str().c_str(), rand.data(), rand.size())) {
    393 			wpa_printf(
    394 			    MSG_ERROR, "Failed to parse GSM auth params");
    395 			return 1;
    396 		}
    397 		out_rands->push_back(rand);
    398 	}
    399 	return 0;
    400 }
    401 
    402 int parseUmtsAuthNetworkRequest(
    403     const std::string &params_str,
    404     hidl_array<uint8_t, kUmtsRandLenBytes> *out_rand,
    405     hidl_array<uint8_t, kUmtsAutnLenBytes> *out_autn)
    406 {
    407 	std::smatch matches;
    408 	std::regex params_umts_regex(kUmtsAuthRegex);
    409 	if (!std::regex_match(params_str, matches, params_umts_regex)) {
    410 		return 1;
    411 	}
    412 	WPA_ASSERT(matches[1].size() >= 2 * out_rand->size());
    413 	if (hexstr2bin(
    414 		matches[1].str().c_str(), out_rand->data(), out_rand->size())) {
    415 		wpa_printf(MSG_ERROR, "Failed to parse UMTS auth params");
    416 		return 1;
    417 	}
    418 	WPA_ASSERT(matches[2].size() >= 2 * out_autn->size());
    419 	if (hexstr2bin(
    420 		matches[2].str().c_str(), out_autn->data(), out_autn->size())) {
    421 		wpa_printf(MSG_ERROR, "Failed to parse UMTS auth params");
    422 		return 1;
    423 	}
    424 	return 0;
    425 }
    426 }  // namespace
    427 
    428 namespace android {
    429 namespace hardware {
    430 namespace wifi {
    431 namespace supplicant {
    432 namespace V1_2 {
    433 namespace implementation {
    434 
    435 using namespace android::hardware::wifi::supplicant::V1_2;
    436 using V1_0::ISupplicantStaIfaceCallback;
    437 
    438 HidlManager *HidlManager::instance_ = NULL;
    439 
    440 HidlManager *HidlManager::getInstance()
    441 {
    442 	if (!instance_)
    443 		instance_ = new HidlManager();
    444 	return instance_;
    445 }
    446 
    447 void HidlManager::destroyInstance()
    448 {
    449 	if (instance_)
    450 		delete instance_;
    451 	instance_ = NULL;
    452 }
    453 
    454 int HidlManager::registerHidlService(struct wpa_global *global)
    455 {
    456 	// Create the main hidl service object and register it.
    457 	supplicant_object_ = new Supplicant(global);
    458 	if (supplicant_object_->registerAsService() != android::NO_ERROR) {
    459 		return 1;
    460 	}
    461 	return 0;
    462 }
    463 
    464 /**
    465  * Register an interface to hidl manager.
    466  *
    467  * @param wpa_s |wpa_supplicant| struct corresponding to the interface.
    468  *
    469  * @return 0 on success, 1 on failure.
    470  */
    471 int HidlManager::registerInterface(struct wpa_supplicant *wpa_s)
    472 {
    473 	if (!wpa_s)
    474 		return 1;
    475 
    476 	if (isP2pIface(wpa_s)) {
    477 		if (addHidlObjectToMap<P2pIface>(
    478 			wpa_s->ifname,
    479 			new P2pIface(wpa_s->global, wpa_s->ifname),
    480 			p2p_iface_object_map_)) {
    481 			wpa_printf(
    482 			    MSG_ERROR,
    483 			    "Failed to register P2P interface with HIDL "
    484 			    "control: %s",
    485 			    wpa_s->ifname);
    486 			return 1;
    487 		}
    488 		p2p_iface_callbacks_map_[wpa_s->ifname] =
    489 		    std::vector<android::sp<ISupplicantP2pIfaceCallback>>();
    490 	} else {
    491 		if (addHidlObjectToMap<StaIface>(
    492 			wpa_s->ifname,
    493 			new StaIface(wpa_s->global, wpa_s->ifname),
    494 			sta_iface_object_map_)) {
    495 			wpa_printf(
    496 			    MSG_ERROR,
    497 			    "Failed to register STA interface with HIDL "
    498 			    "control: %s",
    499 			    wpa_s->ifname);
    500 			return 1;
    501 		}
    502 		sta_iface_callbacks_map_[wpa_s->ifname] =
    503 		    std::vector<android::sp<ISupplicantStaIfaceCallback>>();
    504 		// Turn on Android specific customizations for STA interfaces
    505 		// here!
    506 		//
    507 		// Turn on scan mac randomization only if driver supports.
    508 		if (wpa_s->mac_addr_rand_supported & MAC_ADDR_RAND_SCAN) {
    509 			if (wpas_mac_addr_rand_scan_set(
    510 				wpa_s, MAC_ADDR_RAND_SCAN, nullptr, nullptr)) {
    511 				wpa_printf(
    512 				    MSG_ERROR,
    513 				    "Failed to enable scan mac randomization");
    514 			}
    515 		}
    516 	}
    517 
    518 	// Invoke the |onInterfaceCreated| method on all registered callbacks.
    519 	callWithEachSupplicantCallback(std::bind(
    520 	    &ISupplicantCallback::onInterfaceCreated, std::placeholders::_1,
    521 	    wpa_s->ifname));
    522 	return 0;
    523 }
    524 
    525 /**
    526  * Unregister an interface from hidl manager.
    527  *
    528  * @param wpa_s |wpa_supplicant| struct corresponding to the interface.
    529  *
    530  * @return 0 on success, 1 on failure.
    531  */
    532 int HidlManager::unregisterInterface(struct wpa_supplicant *wpa_s)
    533 {
    534 	if (!wpa_s)
    535 		return 1;
    536 
    537 	// Check if this interface is present in P2P map first, else check in
    538 	// STA map.
    539 	// Note: We can't use isP2pIface() here because interface
    540 	// pointers (wpa_s->global->p2p_init_wpa_s == wpa_s) used by the helper
    541 	// function is cleared by the core before notifying the HIDL interface.
    542 	bool success =
    543 	    !removeHidlObjectFromMap(wpa_s->ifname, p2p_iface_object_map_);
    544 	if (success) {  // assumed to be P2P
    545 		success = !removeAllIfaceCallbackHidlObjectsFromMap(
    546 		    wpa_s->ifname, p2p_iface_callbacks_map_);
    547 	} else {  // assumed to be STA
    548 		success = !removeHidlObjectFromMap(
    549 		    wpa_s->ifname, sta_iface_object_map_);
    550 		if (success) {
    551 			success = !removeAllIfaceCallbackHidlObjectsFromMap(
    552 			    wpa_s->ifname, sta_iface_callbacks_map_);
    553 		}
    554 	}
    555 	if (!success) {
    556 		wpa_printf(
    557 		    MSG_ERROR,
    558 		    "Failed to unregister interface with HIDL "
    559 		    "control: %s",
    560 		    wpa_s->ifname);
    561 		return 1;
    562 	}
    563 
    564 	// Invoke the |onInterfaceRemoved| method on all registered callbacks.
    565 	callWithEachSupplicantCallback(std::bind(
    566 	    &ISupplicantCallback::onInterfaceRemoved, std::placeholders::_1,
    567 	    wpa_s->ifname));
    568 	return 0;
    569 }
    570 
    571 /**
    572  * Register a network to hidl manager.
    573  *
    574  * @param wpa_s |wpa_supplicant| struct corresponding to the interface on which
    575  * the network is added.
    576  * @param ssid |wpa_ssid| struct corresponding to the network being added.
    577  *
    578  * @return 0 on success, 1 on failure.
    579  */
    580 int HidlManager::registerNetwork(
    581     struct wpa_supplicant *wpa_s, struct wpa_ssid *ssid)
    582 {
    583 	if (!wpa_s || !ssid)
    584 		return 1;
    585 
    586 	// Generate the key to be used to lookup the network.
    587 	const std::string network_key =
    588 	    getNetworkObjectMapKey(wpa_s->ifname, ssid->id);
    589 
    590 	if (isP2pIface(wpa_s)) {
    591 		if (addHidlObjectToMap<P2pNetwork>(
    592 			network_key,
    593 			new P2pNetwork(wpa_s->global, wpa_s->ifname, ssid->id),
    594 			p2p_network_object_map_)) {
    595 			wpa_printf(
    596 			    MSG_ERROR,
    597 			    "Failed to register P2P network with HIDL "
    598 			    "control: %d",
    599 			    ssid->id);
    600 			return 1;
    601 		}
    602 		p2p_network_callbacks_map_[network_key] =
    603 		    std::vector<android::sp<ISupplicantP2pNetworkCallback>>();
    604 		// Invoke the |onNetworkAdded| method on all registered
    605 		// callbacks.
    606 		callWithEachP2pIfaceCallback(
    607 		    wpa_s->ifname,
    608 		    std::bind(
    609 			&ISupplicantP2pIfaceCallback::onNetworkAdded,
    610 			std::placeholders::_1, ssid->id));
    611 	} else {
    612 		if (addHidlObjectToMap<StaNetwork>(
    613 			network_key,
    614 			new StaNetwork(wpa_s->global, wpa_s->ifname, ssid->id),
    615 			sta_network_object_map_)) {
    616 			wpa_printf(
    617 			    MSG_ERROR,
    618 			    "Failed to register STA network with HIDL "
    619 			    "control: %d",
    620 			    ssid->id);
    621 			return 1;
    622 		}
    623 		sta_network_callbacks_map_[network_key] =
    624 		    std::vector<android::sp<ISupplicantStaNetworkCallback>>();
    625 		// Invoke the |onNetworkAdded| method on all registered
    626 		// callbacks.
    627 		callWithEachStaIfaceCallback(
    628 		    wpa_s->ifname,
    629 		    std::bind(
    630 			&ISupplicantStaIfaceCallback::onNetworkAdded,
    631 			std::placeholders::_1, ssid->id));
    632 	}
    633 	return 0;
    634 }
    635 
    636 /**
    637  * Unregister a network from hidl manager.
    638  *
    639  * @param wpa_s |wpa_supplicant| struct corresponding to the interface on which
    640  * the network is added.
    641  * @param ssid |wpa_ssid| struct corresponding to the network being added.
    642  *
    643  * @return 0 on success, 1 on failure.
    644  */
    645 int HidlManager::unregisterNetwork(
    646     struct wpa_supplicant *wpa_s, struct wpa_ssid *ssid)
    647 {
    648 	if (!wpa_s || !ssid)
    649 		return 1;
    650 
    651 	// Generate the key to be used to lookup the network.
    652 	const std::string network_key =
    653 	    getNetworkObjectMapKey(wpa_s->ifname, ssid->id);
    654 
    655 	if (isP2pIface(wpa_s)) {
    656 		if (removeHidlObjectFromMap(
    657 			network_key, p2p_network_object_map_)) {
    658 			wpa_printf(
    659 			    MSG_ERROR,
    660 			    "Failed to unregister P2P network with HIDL "
    661 			    "control: %d",
    662 			    ssid->id);
    663 			return 1;
    664 		}
    665 		if (removeAllNetworkCallbackHidlObjectsFromMap(
    666 			network_key, p2p_network_callbacks_map_))
    667 			return 1;
    668 
    669 		// Invoke the |onNetworkRemoved| method on all registered
    670 		// callbacks.
    671 		callWithEachP2pIfaceCallback(
    672 		    wpa_s->ifname,
    673 		    std::bind(
    674 			&ISupplicantP2pIfaceCallback::onNetworkRemoved,
    675 			std::placeholders::_1, ssid->id));
    676 	} else {
    677 		if (removeHidlObjectFromMap(
    678 			network_key, sta_network_object_map_)) {
    679 			wpa_printf(
    680 			    MSG_ERROR,
    681 			    "Failed to unregister STA network with HIDL "
    682 			    "control: %d",
    683 			    ssid->id);
    684 			return 1;
    685 		}
    686 		if (removeAllNetworkCallbackHidlObjectsFromMap(
    687 			network_key, sta_network_callbacks_map_))
    688 			return 1;
    689 
    690 		// Invoke the |onNetworkRemoved| method on all registered
    691 		// callbacks.
    692 		callWithEachStaIfaceCallback(
    693 		    wpa_s->ifname,
    694 		    std::bind(
    695 			&ISupplicantStaIfaceCallback::onNetworkRemoved,
    696 			std::placeholders::_1, ssid->id));
    697 	}
    698 	return 0;
    699 }
    700 
    701 /**
    702  * Notify all listeners about any state changes on a particular interface.
    703  *
    704  * @param wpa_s |wpa_supplicant| struct corresponding to the interface on which
    705  * the state change event occured.
    706  */
    707 int HidlManager::notifyStateChange(struct wpa_supplicant *wpa_s)
    708 {
    709 	if (!wpa_s)
    710 		return 1;
    711 
    712 	if (sta_iface_object_map_.find(wpa_s->ifname) ==
    713 	    sta_iface_object_map_.end())
    714 		return 1;
    715 
    716 	// Invoke the |onStateChanged| method on all registered callbacks.
    717 	uint32_t hidl_network_id = UINT32_MAX;
    718 	std::vector<uint8_t> hidl_ssid;
    719 	if (wpa_s->current_ssid) {
    720 		hidl_network_id = wpa_s->current_ssid->id;
    721 		hidl_ssid.assign(
    722 		    wpa_s->current_ssid->ssid,
    723 		    wpa_s->current_ssid->ssid + wpa_s->current_ssid->ssid_len);
    724 	}
    725 	uint8_t *bssid;
    726 	// wpa_supplicant sets the |pending_bssid| field when it starts a
    727 	// connection. Only after association state does it update the |bssid|
    728 	// field. So, in the HIDL callback send the appropriate bssid.
    729 	if (wpa_s->wpa_state <= WPA_ASSOCIATED) {
    730 		bssid = wpa_s->pending_bssid;
    731 	} else {
    732 		bssid = wpa_s->bssid;
    733 	}
    734 	callWithEachStaIfaceCallback(
    735 	    wpa_s->ifname, std::bind(
    736 			       &ISupplicantStaIfaceCallback::onStateChanged,
    737 			       std::placeholders::_1,
    738 			       static_cast<ISupplicantStaIfaceCallback::State>(
    739 				   wpa_s->wpa_state),
    740 			       bssid, hidl_network_id, hidl_ssid));
    741 	return 0;
    742 }
    743 
    744 /**
    745  * Notify all listeners about a request on a particular network.
    746  *
    747  * @param wpa_s |wpa_supplicant| struct corresponding to the interface on which
    748  * the network is present.
    749  * @param ssid |wpa_ssid| struct corresponding to the network.
    750  * @param type type of request.
    751  * @param param addition params associated with the request.
    752  */
    753 int HidlManager::notifyNetworkRequest(
    754     struct wpa_supplicant *wpa_s, struct wpa_ssid *ssid, int type,
    755     const char *param)
    756 {
    757 	if (!wpa_s || !ssid)
    758 		return 1;
    759 
    760 	const std::string network_key =
    761 	    getNetworkObjectMapKey(wpa_s->ifname, ssid->id);
    762 	if (sta_network_object_map_.find(network_key) ==
    763 	    sta_network_object_map_.end())
    764 		return 1;
    765 
    766 	if (type == WPA_CTRL_REQ_EAP_IDENTITY) {
    767 		callWithEachStaNetworkCallback(
    768 		    wpa_s->ifname, ssid->id,
    769 		    std::bind(
    770 			&ISupplicantStaNetworkCallback::
    771 			    onNetworkEapIdentityRequest,
    772 			std::placeholders::_1));
    773 		return 0;
    774 	}
    775 	if (type == WPA_CTRL_REQ_SIM) {
    776 		std::vector<hidl_array<uint8_t, 16>> gsm_rands;
    777 		hidl_array<uint8_t, 16> umts_rand;
    778 		hidl_array<uint8_t, 16> umts_autn;
    779 		if (!parseGsmAuthNetworkRequest(param, &gsm_rands)) {
    780 			ISupplicantStaNetworkCallback::
    781 			    NetworkRequestEapSimGsmAuthParams hidl_params;
    782 			hidl_params.rands = gsm_rands;
    783 			callWithEachStaNetworkCallback(
    784 			    wpa_s->ifname, ssid->id,
    785 			    std::bind(
    786 				&ISupplicantStaNetworkCallback::
    787 				    onNetworkEapSimGsmAuthRequest,
    788 				std::placeholders::_1, hidl_params));
    789 			return 0;
    790 		}
    791 		if (!parseUmtsAuthNetworkRequest(
    792 			param, &umts_rand, &umts_autn)) {
    793 			ISupplicantStaNetworkCallback::
    794 			    NetworkRequestEapSimUmtsAuthParams hidl_params;
    795 			hidl_params.rand = umts_rand;
    796 			hidl_params.autn = umts_autn;
    797 			callWithEachStaNetworkCallback(
    798 			    wpa_s->ifname, ssid->id,
    799 			    std::bind(
    800 				&ISupplicantStaNetworkCallback::
    801 				    onNetworkEapSimUmtsAuthRequest,
    802 				std::placeholders::_1, hidl_params));
    803 			return 0;
    804 		}
    805 	}
    806 	return 1;
    807 }
    808 
    809 /**
    810  * Notify all listeners about the end of an ANQP query.
    811  *
    812  * @param wpa_s |wpa_supplicant| struct corresponding to the interface.
    813  * @param bssid BSSID of the access point.
    814  * @param result Result of the operation ("SUCCESS" or "FAILURE").
    815  * @param anqp |wpa_bss_anqp| ANQP data fetched.
    816  */
    817 void HidlManager::notifyAnqpQueryDone(
    818     struct wpa_supplicant *wpa_s, const u8 *bssid, const char *result,
    819     const struct wpa_bss_anqp *anqp)
    820 {
    821 	if (!wpa_s || !bssid || !result || !anqp)
    822 		return;
    823 
    824 	if (sta_iface_object_map_.find(wpa_s->ifname) ==
    825 	    sta_iface_object_map_.end())
    826 		return;
    827 
    828 	ISupplicantStaIfaceCallback::AnqpData hidl_anqp_data;
    829 	ISupplicantStaIfaceCallback::Hs20AnqpData hidl_hs20_anqp_data;
    830 	if (std::string(result) == "SUCCESS") {
    831 		hidl_anqp_data.venueName =
    832 		    misc_utils::convertWpaBufToVector(anqp->venue_name);
    833 		hidl_anqp_data.roamingConsortium =
    834 		    misc_utils::convertWpaBufToVector(anqp->roaming_consortium);
    835 		hidl_anqp_data.ipAddrTypeAvailability =
    836 		    misc_utils::convertWpaBufToVector(
    837 			anqp->ip_addr_type_availability);
    838 		hidl_anqp_data.naiRealm =
    839 		    misc_utils::convertWpaBufToVector(anqp->nai_realm);
    840 		hidl_anqp_data.anqp3gppCellularNetwork =
    841 		    misc_utils::convertWpaBufToVector(anqp->anqp_3gpp);
    842 		hidl_anqp_data.domainName =
    843 		    misc_utils::convertWpaBufToVector(anqp->domain_name);
    844 
    845 		hidl_hs20_anqp_data.operatorFriendlyName =
    846 		    misc_utils::convertWpaBufToVector(
    847 			anqp->hs20_operator_friendly_name);
    848 		hidl_hs20_anqp_data.wanMetrics =
    849 		    misc_utils::convertWpaBufToVector(anqp->hs20_wan_metrics);
    850 		hidl_hs20_anqp_data.connectionCapability =
    851 		    misc_utils::convertWpaBufToVector(
    852 			anqp->hs20_connection_capability);
    853 		hidl_hs20_anqp_data.osuProvidersList =
    854 		    misc_utils::convertWpaBufToVector(
    855 			anqp->hs20_osu_providers_list);
    856 	}
    857 
    858 	callWithEachStaIfaceCallback(
    859 	    wpa_s->ifname, std::bind(
    860 			       &ISupplicantStaIfaceCallback::onAnqpQueryDone,
    861 			       std::placeholders::_1, bssid, hidl_anqp_data,
    862 			       hidl_hs20_anqp_data));
    863 }
    864 
    865 /**
    866  * Notify all listeners about the end of an HS20 icon query.
    867  *
    868  * @param wpa_s |wpa_supplicant| struct corresponding to the interface.
    869  * @param bssid BSSID of the access point.
    870  * @param file_name Name of the icon file.
    871  * @param image Raw bytes of the icon file.
    872  * @param image_length Size of the the icon file.
    873  */
    874 void HidlManager::notifyHs20IconQueryDone(
    875     struct wpa_supplicant *wpa_s, const u8 *bssid, const char *file_name,
    876     const u8 *image, u32 image_length)
    877 {
    878 	if (!wpa_s || !bssid || !file_name || !image)
    879 		return;
    880 
    881 	if (sta_iface_object_map_.find(wpa_s->ifname) ==
    882 	    sta_iface_object_map_.end())
    883 		return;
    884 
    885 	callWithEachStaIfaceCallback(
    886 	    wpa_s->ifname,
    887 	    std::bind(
    888 		&ISupplicantStaIfaceCallback::onHs20IconQueryDone,
    889 		std::placeholders::_1, bssid, file_name,
    890 		std::vector<uint8_t>(image, image + image_length)));
    891 }
    892 
    893 /**
    894  * Notify all listeners about the reception of HS20 subscription
    895  * remediation notification from the server.
    896  *
    897  * @param wpa_s |wpa_supplicant| struct corresponding to the interface.
    898  * @param url URL of the server.
    899  * @param osu_method OSU method (OMA_DM or SOAP_XML_SPP).
    900  */
    901 void HidlManager::notifyHs20RxSubscriptionRemediation(
    902     struct wpa_supplicant *wpa_s, const char *url, u8 osu_method)
    903 {
    904 	if (!wpa_s || !url)
    905 		return;
    906 
    907 	if (sta_iface_object_map_.find(wpa_s->ifname) ==
    908 	    sta_iface_object_map_.end())
    909 		return;
    910 
    911 	ISupplicantStaIfaceCallback::OsuMethod hidl_osu_method = {};
    912 	if (osu_method & 0x1) {
    913 		hidl_osu_method =
    914 		    ISupplicantStaIfaceCallback::OsuMethod::OMA_DM;
    915 	} else if (osu_method & 0x2) {
    916 		hidl_osu_method =
    917 		    ISupplicantStaIfaceCallback::OsuMethod::SOAP_XML_SPP;
    918 	}
    919 	callWithEachStaIfaceCallback(
    920 	    wpa_s->ifname,
    921 	    std::bind(
    922 		&ISupplicantStaIfaceCallback::onHs20SubscriptionRemediation,
    923 		std::placeholders::_1, wpa_s->bssid, hidl_osu_method, url));
    924 }
    925 
    926 /**
    927  * Notify all listeners about the reception of HS20 immient deauth
    928  * notification from the server.
    929  *
    930  * @param wpa_s |wpa_supplicant| struct corresponding to the interface.
    931  * @param code Deauth reason code sent from server.
    932  * @param reauth_delay Reauthentication delay in seconds sent from server.
    933  * @param url URL of the server.
    934  */
    935 void HidlManager::notifyHs20RxDeauthImminentNotice(
    936     struct wpa_supplicant *wpa_s, u8 code, u16 reauth_delay, const char *url)
    937 {
    938 	if (!wpa_s || !url)
    939 		return;
    940 
    941 	if (sta_iface_object_map_.find(wpa_s->ifname) ==
    942 	    sta_iface_object_map_.end())
    943 		return;
    944 
    945 	callWithEachStaIfaceCallback(
    946 	    wpa_s->ifname,
    947 	    std::bind(
    948 		&ISupplicantStaIfaceCallback::onHs20DeauthImminentNotice,
    949 		std::placeholders::_1, wpa_s->bssid, code, reauth_delay, url));
    950 }
    951 
    952 /**
    953  * Notify all listeners about the reason code for disconnection from the
    954  * currently connected network.
    955  *
    956  * @param wpa_s |wpa_supplicant| struct corresponding to the interface on which
    957  * the network is present.
    958  */
    959 void HidlManager::notifyDisconnectReason(struct wpa_supplicant *wpa_s)
    960 {
    961 	if (!wpa_s)
    962 		return;
    963 
    964 	if (sta_iface_object_map_.find(wpa_s->ifname) ==
    965 	    sta_iface_object_map_.end())
    966 		return;
    967 
    968 	const u8 *bssid = wpa_s->bssid;
    969 	if (is_zero_ether_addr(bssid)) {
    970 		bssid = wpa_s->pending_bssid;
    971 	}
    972 
    973 	callWithEachStaIfaceCallback(
    974 	    wpa_s->ifname,
    975 	    std::bind(
    976 		&ISupplicantStaIfaceCallback::onDisconnected,
    977 		std::placeholders::_1, bssid, wpa_s->disconnect_reason < 0,
    978 		static_cast<ISupplicantStaIfaceCallback::ReasonCode>(
    979 		    abs(wpa_s->disconnect_reason))));
    980 }
    981 
    982 /**
    983  * Notify all listeners about association reject from the access point to which
    984  * we are attempting to connect.
    985  *
    986  * @param wpa_s |wpa_supplicant| struct corresponding to the interface on which
    987  * the network is present.
    988  */
    989 void HidlManager::notifyAssocReject(struct wpa_supplicant *wpa_s)
    990 {
    991 	if (!wpa_s)
    992 		return;
    993 
    994 	if (sta_iface_object_map_.find(wpa_s->ifname) ==
    995 	    sta_iface_object_map_.end())
    996 		return;
    997 
    998 	const u8 *bssid = wpa_s->bssid;
    999 	if (is_zero_ether_addr(bssid)) {
   1000 		bssid = wpa_s->pending_bssid;
   1001 	}
   1002 
   1003 	callWithEachStaIfaceCallback(
   1004 	    wpa_s->ifname,
   1005 	    std::bind(
   1006 		&ISupplicantStaIfaceCallback::onAssociationRejected,
   1007 		std::placeholders::_1, bssid,
   1008 		static_cast<ISupplicantStaIfaceCallback::StatusCode>(
   1009 		    wpa_s->assoc_status_code),
   1010 		wpa_s->assoc_timed_out == 1));
   1011 }
   1012 
   1013 void HidlManager::notifyAuthTimeout(struct wpa_supplicant *wpa_s)
   1014 {
   1015 	if (!wpa_s)
   1016 		return;
   1017 
   1018 	const std::string ifname(wpa_s->ifname);
   1019 	if (sta_iface_object_map_.find(ifname) == sta_iface_object_map_.end())
   1020 		return;
   1021 
   1022 	const u8 *bssid = wpa_s->bssid;
   1023 	if (is_zero_ether_addr(bssid)) {
   1024 		bssid = wpa_s->pending_bssid;
   1025 	}
   1026 	callWithEachStaIfaceCallback(
   1027 	    wpa_s->ifname,
   1028 	    std::bind(
   1029 		&ISupplicantStaIfaceCallback::onAuthenticationTimeout,
   1030 		std::placeholders::_1, bssid));
   1031 }
   1032 
   1033 void HidlManager::notifyBssidChanged(struct wpa_supplicant *wpa_s)
   1034 {
   1035 	if (!wpa_s)
   1036 		return;
   1037 
   1038 	const std::string ifname(wpa_s->ifname);
   1039 	if (sta_iface_object_map_.find(ifname) == sta_iface_object_map_.end())
   1040 		return;
   1041 
   1042 	// wpa_supplicant does not explicitly give us the reason for bssid
   1043 	// change, but we figure that out from what is set out of |wpa_s->bssid|
   1044 	// & |wpa_s->pending_bssid|.
   1045 	const u8 *bssid;
   1046 	ISupplicantStaIfaceCallback::BssidChangeReason reason;
   1047 	if (is_zero_ether_addr(wpa_s->bssid) &&
   1048 	    !is_zero_ether_addr(wpa_s->pending_bssid)) {
   1049 		bssid = wpa_s->pending_bssid;
   1050 		reason =
   1051 		    ISupplicantStaIfaceCallback::BssidChangeReason::ASSOC_START;
   1052 	} else if (
   1053 	    !is_zero_ether_addr(wpa_s->bssid) &&
   1054 	    is_zero_ether_addr(wpa_s->pending_bssid)) {
   1055 		bssid = wpa_s->bssid;
   1056 		reason = ISupplicantStaIfaceCallback::BssidChangeReason::
   1057 		    ASSOC_COMPLETE;
   1058 	} else if (
   1059 	    is_zero_ether_addr(wpa_s->bssid) &&
   1060 	    is_zero_ether_addr(wpa_s->pending_bssid)) {
   1061 		bssid = wpa_s->pending_bssid;
   1062 		reason =
   1063 		    ISupplicantStaIfaceCallback::BssidChangeReason::DISASSOC;
   1064 	} else {
   1065 		wpa_printf(MSG_ERROR, "Unknown bssid change reason");
   1066 		return;
   1067 	}
   1068 
   1069 	callWithEachStaIfaceCallback(
   1070 	    wpa_s->ifname, std::bind(
   1071 			       &ISupplicantStaIfaceCallback::onBssidChanged,
   1072 			       std::placeholders::_1, reason, bssid));
   1073 }
   1074 
   1075 void HidlManager::notifyWpsEventFail(
   1076     struct wpa_supplicant *wpa_s, uint8_t *peer_macaddr, uint16_t config_error,
   1077     uint16_t error_indication)
   1078 {
   1079 	if (!wpa_s || !peer_macaddr)
   1080 		return;
   1081 
   1082 	if (sta_iface_object_map_.find(wpa_s->ifname) ==
   1083 	    sta_iface_object_map_.end())
   1084 		return;
   1085 
   1086 	callWithEachStaIfaceCallback(
   1087 	    wpa_s->ifname,
   1088 	    std::bind(
   1089 		&ISupplicantStaIfaceCallback::onWpsEventFail,
   1090 		std::placeholders::_1, peer_macaddr,
   1091 		static_cast<ISupplicantStaIfaceCallback::WpsConfigError>(
   1092 		    config_error),
   1093 		static_cast<ISupplicantStaIfaceCallback::WpsErrorIndication>(
   1094 		    error_indication)));
   1095 }
   1096 
   1097 void HidlManager::notifyWpsEventSuccess(struct wpa_supplicant *wpa_s)
   1098 {
   1099 	if (!wpa_s)
   1100 		return;
   1101 
   1102 	if (sta_iface_object_map_.find(wpa_s->ifname) ==
   1103 	    sta_iface_object_map_.end())
   1104 		return;
   1105 
   1106 	callWithEachStaIfaceCallback(
   1107 	    wpa_s->ifname, std::bind(
   1108 			       &ISupplicantStaIfaceCallback::onWpsEventSuccess,
   1109 			       std::placeholders::_1));
   1110 }
   1111 
   1112 void HidlManager::notifyWpsEventPbcOverlap(struct wpa_supplicant *wpa_s)
   1113 {
   1114 	if (!wpa_s)
   1115 		return;
   1116 
   1117 	if (sta_iface_object_map_.find(wpa_s->ifname) ==
   1118 	    sta_iface_object_map_.end())
   1119 		return;
   1120 
   1121 	callWithEachStaIfaceCallback(
   1122 	    wpa_s->ifname,
   1123 	    std::bind(
   1124 		&ISupplicantStaIfaceCallback::onWpsEventPbcOverlap,
   1125 		std::placeholders::_1));
   1126 }
   1127 
   1128 void HidlManager::notifyP2pDeviceFound(
   1129     struct wpa_supplicant *wpa_s, const u8 *addr,
   1130     const struct p2p_peer_info *info, const u8 *peer_wfd_device_info,
   1131     u8 peer_wfd_device_info_len)
   1132 {
   1133 	if (!wpa_s || !addr || !info)
   1134 		return;
   1135 
   1136 	if (p2p_iface_object_map_.find(wpa_s->ifname) ==
   1137 	    p2p_iface_object_map_.end())
   1138 		return;
   1139 
   1140 	std::array<uint8_t, kWfdDeviceInfoLen> hidl_peer_wfd_device_info{};
   1141 	if (peer_wfd_device_info) {
   1142 		if (peer_wfd_device_info_len != kWfdDeviceInfoLen) {
   1143 			wpa_printf(
   1144 			    MSG_ERROR, "Unexpected WFD device info len: %d",
   1145 			    peer_wfd_device_info_len);
   1146 		} else {
   1147 			os_memcpy(
   1148 			    hidl_peer_wfd_device_info.data(),
   1149 			    peer_wfd_device_info, kWfdDeviceInfoLen);
   1150 		}
   1151 	}
   1152 
   1153 	callWithEachP2pIfaceCallback(
   1154 	    wpa_s->ifname,
   1155 	    std::bind(
   1156 		&ISupplicantP2pIfaceCallback::onDeviceFound,
   1157 		std::placeholders::_1, addr, info->p2p_device_addr,
   1158 		info->pri_dev_type, info->device_name, info->config_methods,
   1159 		info->dev_capab, info->group_capab, hidl_peer_wfd_device_info));
   1160 }
   1161 
   1162 void HidlManager::notifyP2pDeviceLost(
   1163     struct wpa_supplicant *wpa_s, const u8 *p2p_device_addr)
   1164 {
   1165 	if (!wpa_s || !p2p_device_addr)
   1166 		return;
   1167 
   1168 	if (p2p_iface_object_map_.find(wpa_s->ifname) ==
   1169 	    p2p_iface_object_map_.end())
   1170 		return;
   1171 
   1172 	callWithEachP2pIfaceCallback(
   1173 	    wpa_s->ifname, std::bind(
   1174 			       &ISupplicantP2pIfaceCallback::onDeviceLost,
   1175 			       std::placeholders::_1, p2p_device_addr));
   1176 }
   1177 
   1178 void HidlManager::notifyP2pFindStopped(struct wpa_supplicant *wpa_s)
   1179 {
   1180 	if (!wpa_s)
   1181 		return;
   1182 
   1183 	if (p2p_iface_object_map_.find(wpa_s->ifname) ==
   1184 	    p2p_iface_object_map_.end())
   1185 		return;
   1186 
   1187 	callWithEachP2pIfaceCallback(
   1188 	    wpa_s->ifname, std::bind(
   1189 			       &ISupplicantP2pIfaceCallback::onFindStopped,
   1190 			       std::placeholders::_1));
   1191 }
   1192 
   1193 void HidlManager::notifyP2pGoNegReq(
   1194     struct wpa_supplicant *wpa_s, const u8 *src_addr, u16 dev_passwd_id,
   1195     u8 /* go_intent */)
   1196 {
   1197 	if (!wpa_s || !src_addr)
   1198 		return;
   1199 
   1200 	if (p2p_iface_object_map_.find(wpa_s->ifname) ==
   1201 	    p2p_iface_object_map_.end())
   1202 		return;
   1203 
   1204 	callWithEachP2pIfaceCallback(
   1205 	    wpa_s->ifname,
   1206 	    std::bind(
   1207 		&ISupplicantP2pIfaceCallback::onGoNegotiationRequest,
   1208 		std::placeholders::_1, src_addr,
   1209 		static_cast<ISupplicantP2pIfaceCallback::WpsDevPasswordId>(
   1210 		    dev_passwd_id)));
   1211 }
   1212 
   1213 void HidlManager::notifyP2pGoNegCompleted(
   1214     struct wpa_supplicant *wpa_s, const struct p2p_go_neg_results *res)
   1215 {
   1216 	if (!wpa_s || !res)
   1217 		return;
   1218 
   1219 	if (p2p_iface_object_map_.find(wpa_s->ifname) ==
   1220 	    p2p_iface_object_map_.end())
   1221 		return;
   1222 
   1223 	callWithEachP2pIfaceCallback(
   1224 	    wpa_s->ifname,
   1225 	    std::bind(
   1226 		&ISupplicantP2pIfaceCallback::onGoNegotiationCompleted,
   1227 		std::placeholders::_1,
   1228 		static_cast<ISupplicantP2pIfaceCallback::P2pStatusCode>(
   1229 		    res->status)));
   1230 }
   1231 
   1232 void HidlManager::notifyP2pGroupFormationFailure(
   1233     struct wpa_supplicant *wpa_s, const char *reason)
   1234 {
   1235 	if (!wpa_s || !reason)
   1236 		return;
   1237 
   1238 	if (p2p_iface_object_map_.find(wpa_s->ifname) ==
   1239 	    p2p_iface_object_map_.end())
   1240 		return;
   1241 
   1242 	callWithEachP2pIfaceCallback(
   1243 	    wpa_s->ifname,
   1244 	    std::bind(
   1245 		&ISupplicantP2pIfaceCallback::onGroupFormationFailure,
   1246 		std::placeholders::_1, reason));
   1247 }
   1248 
   1249 void HidlManager::notifyP2pGroupStarted(
   1250     struct wpa_supplicant *wpa_group_s, const struct wpa_ssid *ssid,
   1251     int persistent, int client)
   1252 {
   1253 	if (!wpa_group_s || !wpa_group_s->parent || !ssid)
   1254 		return;
   1255 
   1256 	// For group notifications, need to use the parent iface for callbacks.
   1257 	struct wpa_supplicant *wpa_s = wpa_group_s->parent;
   1258 	if (p2p_iface_object_map_.find(wpa_s->ifname) ==
   1259 	    p2p_iface_object_map_.end())
   1260 		return;
   1261 
   1262 	uint32_t hidl_freq = wpa_group_s->current_bss
   1263 				 ? wpa_group_s->current_bss->freq
   1264 				 : wpa_group_s->assoc_freq;
   1265 	std::array<uint8_t, 32> hidl_psk;
   1266 	if (ssid->psk_set) {
   1267 		os_memcpy(hidl_psk.data(), ssid->psk, 32);
   1268 	}
   1269 	bool hidl_is_go = (client == 0 ? true : false);
   1270 	bool hidl_is_persistent = (persistent == 1 ? true : false);
   1271 
   1272 	callWithEachP2pIfaceCallback(
   1273 	    wpa_s->ifname,
   1274 	    std::bind(
   1275 		&ISupplicantP2pIfaceCallback::onGroupStarted,
   1276 		std::placeholders::_1, wpa_group_s->ifname, hidl_is_go,
   1277 		std::vector<uint8_t>{ssid->ssid, ssid->ssid + ssid->ssid_len},
   1278 		hidl_freq, hidl_psk, ssid->passphrase, wpa_group_s->go_dev_addr,
   1279 		hidl_is_persistent));
   1280 }
   1281 
   1282 void HidlManager::notifyP2pGroupRemoved(
   1283     struct wpa_supplicant *wpa_group_s, const struct wpa_ssid *ssid,
   1284     const char *role)
   1285 {
   1286 	if (!wpa_group_s || !wpa_group_s->parent || !ssid || !role)
   1287 		return;
   1288 
   1289 	// For group notifications, need to use the parent iface for callbacks.
   1290 	struct wpa_supplicant *wpa_s = wpa_group_s->parent;
   1291 	if (p2p_iface_object_map_.find(wpa_s->ifname) ==
   1292 	    p2p_iface_object_map_.end())
   1293 		return;
   1294 
   1295 	bool hidl_is_go = (std::string(role) == "GO");
   1296 
   1297 	callWithEachP2pIfaceCallback(
   1298 	    wpa_s->ifname,
   1299 	    std::bind(
   1300 		&ISupplicantP2pIfaceCallback::onGroupRemoved,
   1301 		std::placeholders::_1, wpa_group_s->ifname, hidl_is_go));
   1302 }
   1303 
   1304 void HidlManager::notifyP2pInvitationReceived(
   1305     struct wpa_supplicant *wpa_s, const u8 *sa, const u8 *go_dev_addr,
   1306     const u8 *bssid, int id, int op_freq)
   1307 {
   1308 	if (!wpa_s || !sa || !go_dev_addr || !bssid)
   1309 		return;
   1310 
   1311 	if (p2p_iface_object_map_.find(wpa_s->ifname) ==
   1312 	    p2p_iface_object_map_.end())
   1313 		return;
   1314 
   1315 	SupplicantNetworkId hidl_network_id;
   1316 	if (id < 0) {
   1317 		hidl_network_id = UINT32_MAX;
   1318 	}
   1319 	hidl_network_id = id;
   1320 
   1321 	callWithEachP2pIfaceCallback(
   1322 	    wpa_s->ifname,
   1323 	    std::bind(
   1324 		&ISupplicantP2pIfaceCallback::onInvitationReceived,
   1325 		std::placeholders::_1, sa, go_dev_addr, bssid, hidl_network_id,
   1326 		op_freq));
   1327 }
   1328 
   1329 void HidlManager::notifyP2pInvitationResult(
   1330     struct wpa_supplicant *wpa_s, int status, const u8 *bssid)
   1331 {
   1332 	if (!wpa_s)
   1333 		return;
   1334 
   1335 	if (p2p_iface_object_map_.find(wpa_s->ifname) ==
   1336 	    p2p_iface_object_map_.end())
   1337 		return;
   1338 
   1339 	callWithEachP2pIfaceCallback(
   1340 	    wpa_s->ifname,
   1341 	    std::bind(
   1342 		&ISupplicantP2pIfaceCallback::onInvitationResult,
   1343 		std::placeholders::_1, bssid ? bssid : kZeroBssid,
   1344 		static_cast<ISupplicantP2pIfaceCallback::P2pStatusCode>(
   1345 		    status)));
   1346 }
   1347 
   1348 void HidlManager::notifyP2pProvisionDiscovery(
   1349     struct wpa_supplicant *wpa_s, const u8 *dev_addr, int request,
   1350     enum p2p_prov_disc_status status, u16 config_methods,
   1351     unsigned int generated_pin)
   1352 {
   1353 	if (!wpa_s || !dev_addr)
   1354 		return;
   1355 
   1356 	if (p2p_iface_object_map_.find(wpa_s->ifname) ==
   1357 	    p2p_iface_object_map_.end())
   1358 		return;
   1359 
   1360 	std::string hidl_generated_pin;
   1361 	if (generated_pin > 0) {
   1362 		hidl_generated_pin =
   1363 		    misc_utils::convertWpsPinToString(generated_pin);
   1364 	}
   1365 	bool hidl_is_request = (request == 1 ? true : false);
   1366 
   1367 	callWithEachP2pIfaceCallback(
   1368 	    wpa_s->ifname,
   1369 	    std::bind(
   1370 		&ISupplicantP2pIfaceCallback::onProvisionDiscoveryCompleted,
   1371 		std::placeholders::_1, dev_addr, hidl_is_request,
   1372 		static_cast<ISupplicantP2pIfaceCallback::P2pProvDiscStatusCode>(
   1373 		    status),
   1374 		config_methods, hidl_generated_pin));
   1375 }
   1376 
   1377 void HidlManager::notifyP2pSdResponse(
   1378     struct wpa_supplicant *wpa_s, const u8 *sa, u16 update_indic,
   1379     const u8 *tlvs, size_t tlvs_len)
   1380 {
   1381 	if (!wpa_s || !sa || !tlvs)
   1382 		return;
   1383 
   1384 	if (p2p_iface_object_map_.find(wpa_s->ifname) ==
   1385 	    p2p_iface_object_map_.end())
   1386 		return;
   1387 
   1388 	callWithEachP2pIfaceCallback(
   1389 	    wpa_s->ifname,
   1390 	    std::bind(
   1391 		&ISupplicantP2pIfaceCallback::onServiceDiscoveryResponse,
   1392 		std::placeholders::_1, sa, update_indic,
   1393 		std::vector<uint8_t>{tlvs, tlvs + tlvs_len}));
   1394 }
   1395 
   1396 void HidlManager::notifyApStaAuthorized(
   1397     struct wpa_supplicant *wpa_s, const u8 *sta, const u8 *p2p_dev_addr)
   1398 {
   1399 	if (!wpa_s || !wpa_s->parent || !sta)
   1400 		return;
   1401 	if (p2p_iface_object_map_.find(wpa_s->parent->ifname) ==
   1402 	    p2p_iface_object_map_.end())
   1403 		return;
   1404 	callWithEachP2pIfaceCallback(
   1405 	    wpa_s->parent->ifname,
   1406 	    std::bind(
   1407 		&ISupplicantP2pIfaceCallback::onStaAuthorized,
   1408 		std::placeholders::_1, sta,
   1409 		p2p_dev_addr ? p2p_dev_addr : kZeroBssid));
   1410 }
   1411 
   1412 void HidlManager::notifyApStaDeauthorized(
   1413     struct wpa_supplicant *wpa_s, const u8 *sta, const u8 *p2p_dev_addr)
   1414 {
   1415 	if (!wpa_s || !wpa_s->parent || !sta)
   1416 		return;
   1417 	if (p2p_iface_object_map_.find(wpa_s->parent->ifname) ==
   1418 	    p2p_iface_object_map_.end())
   1419 		return;
   1420 
   1421 	callWithEachP2pIfaceCallback(
   1422 	    wpa_s->parent->ifname,
   1423 	    std::bind(
   1424 		&ISupplicantP2pIfaceCallback::onStaDeauthorized,
   1425 		std::placeholders::_1, sta,
   1426 		p2p_dev_addr ? p2p_dev_addr : kZeroBssid));
   1427 }
   1428 
   1429 void HidlManager::notifyExtRadioWorkStart(
   1430     struct wpa_supplicant *wpa_s, uint32_t id)
   1431 {
   1432 	if (!wpa_s)
   1433 		return;
   1434 
   1435 	if (sta_iface_object_map_.find(wpa_s->ifname) ==
   1436 	    sta_iface_object_map_.end())
   1437 		return;
   1438 
   1439 	callWithEachStaIfaceCallback(
   1440 	    wpa_s->ifname,
   1441 	    std::bind(
   1442 		&ISupplicantStaIfaceCallback::onExtRadioWorkStart,
   1443 		std::placeholders::_1, id));
   1444 }
   1445 
   1446 void HidlManager::notifyExtRadioWorkTimeout(
   1447     struct wpa_supplicant *wpa_s, uint32_t id)
   1448 {
   1449 	if (!wpa_s)
   1450 		return;
   1451 
   1452 	if (sta_iface_object_map_.find(wpa_s->ifname) ==
   1453 	    sta_iface_object_map_.end())
   1454 		return;
   1455 
   1456 	callWithEachStaIfaceCallback(
   1457 	    wpa_s->ifname,
   1458 	    std::bind(
   1459 		&ISupplicantStaIfaceCallback::onExtRadioWorkTimeout,
   1460 		std::placeholders::_1, id));
   1461 }
   1462 
   1463 void HidlManager::notifyEapError(struct wpa_supplicant *wpa_s, int error_code)
   1464 {
   1465 	typedef V1_1::ISupplicantStaIfaceCallback::EapErrorCode EapErrorCode;
   1466 
   1467 	if (!wpa_s)
   1468 		return;
   1469 
   1470 	switch (static_cast<EapErrorCode>(error_code)) {
   1471 	case EapErrorCode::SIM_GENERAL_FAILURE_AFTER_AUTH:
   1472 	case EapErrorCode::SIM_TEMPORARILY_DENIED:
   1473 	case EapErrorCode::SIM_NOT_SUBSCRIBED:
   1474 	case EapErrorCode::SIM_GENERAL_FAILURE_BEFORE_AUTH:
   1475 	case EapErrorCode::SIM_VENDOR_SPECIFIC_EXPIRED_CERT:
   1476 		break;
   1477 	default:
   1478 		return;
   1479 	}
   1480 
   1481 	callWithEachStaIfaceCallback_1_1(
   1482 	    wpa_s->ifname,
   1483 	    std::bind(
   1484 		&V1_1::ISupplicantStaIfaceCallback::onEapFailure_1_1,
   1485 		std::placeholders::_1, static_cast<EapErrorCode>(error_code)));
   1486 }
   1487 
   1488 /**
   1489  * Notify listener about a new DPP configuration received success event
   1490  *
   1491  * @param ifname Interface name
   1492  * @param config Configuration object
   1493  */
   1494 void HidlManager::notifyDppConfigReceived(struct wpa_supplicant *wpa_s,
   1495 		struct wpa_ssid *config)
   1496 {
   1497 	DppAkm securityAkm;
   1498 	char *password;
   1499 	std::string hidl_ifname = wpa_s->ifname;
   1500 
   1501 	if ((config->key_mgmt & WPA_KEY_MGMT_SAE) &&
   1502 			(wpa_s->drv_flags & WPA_DRIVER_FLAGS_SAE)) {
   1503 		securityAkm = DppAkm::SAE;
   1504 	} else if (config->key_mgmt & WPA_KEY_MGMT_PSK) {
   1505 			securityAkm = DppAkm::PSK;
   1506 	} else {
   1507 		/* Unsupported AKM */
   1508 		wpa_printf(MSG_ERROR, "DPP: Error: Unsupported AKM 0x%X",
   1509 				config->key_mgmt);
   1510 		notifyDppFailure(wpa_s, DppFailureCode::NOT_SUPPORTED);
   1511 		return;
   1512 	}
   1513 
   1514 	password = config->passphrase;
   1515 	std::vector < uint8_t > hidl_ssid;
   1516 	hidl_ssid.assign(config->ssid, config->ssid + config->ssid_len);
   1517 
   1518 	/* At this point, the network is already registered, notify about new
   1519 	 * received configuration
   1520 	 */
   1521 	callWithEachStaIfaceCallback_1_2(hidl_ifname,
   1522 			std::bind(
   1523 					&V1_2::ISupplicantStaIfaceCallback::onDppSuccessConfigReceived,
   1524 					std::placeholders::_1, hidl_ssid, password, config->psk,
   1525 					securityAkm));
   1526 }
   1527 
   1528 /**
   1529  * Notify listener about a DPP configuration sent success event
   1530  *
   1531  * @param ifname Interface name
   1532  */
   1533 void HidlManager::notifyDppConfigSent(struct wpa_supplicant *wpa_s)
   1534 {
   1535 	std::string hidl_ifname = wpa_s->ifname;
   1536 
   1537 	callWithEachStaIfaceCallback_1_2(hidl_ifname,
   1538 			std::bind(&V1_2::ISupplicantStaIfaceCallback::onDppSuccessConfigSent,
   1539 					std::placeholders::_1));
   1540 }
   1541 
   1542 /**
   1543  * Notify listener about a DPP failure event
   1544  *
   1545  * @param ifname Interface name
   1546  * @param code Status code
   1547  */
   1548 void HidlManager::notifyDppFailure(struct wpa_supplicant *wpa_s, DppFailureCode code)
   1549 {
   1550 	std::string hidl_ifname = wpa_s->ifname;
   1551 
   1552 	callWithEachStaIfaceCallback_1_2(hidl_ifname,
   1553 			std::bind(&V1_2::ISupplicantStaIfaceCallback::onDppFailure,
   1554 					std::placeholders::_1, code));
   1555 }
   1556 
   1557 /**
   1558  * Notify listener about a DPP progress event
   1559  *
   1560  * @param ifname Interface name
   1561  * @param code Status code
   1562  */
   1563 void HidlManager::notifyDppProgress(struct wpa_supplicant *wpa_s, DppProgressCode code)
   1564 {
   1565 	std::string hidl_ifname = wpa_s->ifname;
   1566 
   1567 	callWithEachStaIfaceCallback_1_2(hidl_ifname,
   1568 			std::bind(&V1_2::ISupplicantStaIfaceCallback::onDppProgress,
   1569 					std::placeholders::_1, code));
   1570 }
   1571 
   1572 /**
   1573  * Retrieve the |ISupplicantP2pIface| hidl object reference using the provided
   1574  * ifname.
   1575  *
   1576  * @param ifname Name of the corresponding interface.
   1577  * @param iface_object Hidl reference corresponding to the iface.
   1578  *
   1579  * @return 0 on success, 1 on failure.
   1580  */
   1581 int HidlManager::getP2pIfaceHidlObjectByIfname(
   1582     const std::string &ifname, android::sp<ISupplicantP2pIface> *iface_object)
   1583 {
   1584 	if (ifname.empty() || !iface_object)
   1585 		return 1;
   1586 
   1587 	auto iface_object_iter = p2p_iface_object_map_.find(ifname);
   1588 	if (iface_object_iter == p2p_iface_object_map_.end())
   1589 		return 1;
   1590 
   1591 	*iface_object = iface_object_iter->second;
   1592 	return 0;
   1593 }
   1594 
   1595 /**
   1596  * Retrieve the |ISupplicantStaIface| hidl object reference using the provided
   1597  * ifname.
   1598  *
   1599  * @param ifname Name of the corresponding interface.
   1600  * @param iface_object Hidl reference corresponding to the iface.
   1601  *
   1602  * @return 0 on success, 1 on failure.
   1603  */
   1604 int HidlManager::getStaIfaceHidlObjectByIfname(
   1605     const std::string &ifname, android::sp<ISupplicantStaIface> *iface_object)
   1606 {
   1607 	if (ifname.empty() || !iface_object)
   1608 		return 1;
   1609 
   1610 	auto iface_object_iter = sta_iface_object_map_.find(ifname);
   1611 	if (iface_object_iter == sta_iface_object_map_.end())
   1612 		return 1;
   1613 
   1614 	*iface_object = iface_object_iter->second;
   1615 	return 0;
   1616 }
   1617 
   1618 /**
   1619  * Retrieve the |ISupplicantP2pNetwork| hidl object reference using the provided
   1620  * ifname and network_id.
   1621  *
   1622  * @param ifname Name of the corresponding interface.
   1623  * @param network_id ID of the corresponding network.
   1624  * @param network_object Hidl reference corresponding to the network.
   1625  *
   1626  * @return 0 on success, 1 on failure.
   1627  */
   1628 int HidlManager::getP2pNetworkHidlObjectByIfnameAndNetworkId(
   1629     const std::string &ifname, int network_id,
   1630     android::sp<ISupplicantP2pNetwork> *network_object)
   1631 {
   1632 	if (ifname.empty() || network_id < 0 || !network_object)
   1633 		return 1;
   1634 
   1635 	// Generate the key to be used to lookup the network.
   1636 	const std::string network_key =
   1637 	    getNetworkObjectMapKey(ifname, network_id);
   1638 
   1639 	auto network_object_iter = p2p_network_object_map_.find(network_key);
   1640 	if (network_object_iter == p2p_network_object_map_.end())
   1641 		return 1;
   1642 
   1643 	*network_object = network_object_iter->second;
   1644 	return 0;
   1645 }
   1646 
   1647 /**
   1648  * Retrieve the |ISupplicantStaNetwork| hidl object reference using the provided
   1649  * ifname and network_id.
   1650  *
   1651  * @param ifname Name of the corresponding interface.
   1652  * @param network_id ID of the corresponding network.
   1653  * @param network_object Hidl reference corresponding to the network.
   1654  *
   1655  * @return 0 on success, 1 on failure.
   1656  */
   1657 int HidlManager::getStaNetworkHidlObjectByIfnameAndNetworkId(
   1658     const std::string &ifname, int network_id,
   1659     android::sp<ISupplicantStaNetwork> *network_object)
   1660 {
   1661 	if (ifname.empty() || network_id < 0 || !network_object)
   1662 		return 1;
   1663 
   1664 	// Generate the key to be used to lookup the network.
   1665 	const std::string network_key =
   1666 	    getNetworkObjectMapKey(ifname, network_id);
   1667 
   1668 	auto network_object_iter = sta_network_object_map_.find(network_key);
   1669 	if (network_object_iter == sta_network_object_map_.end())
   1670 		return 1;
   1671 
   1672 	*network_object = network_object_iter->second;
   1673 	return 0;
   1674 }
   1675 
   1676 /**
   1677  * Add a new |ISupplicantCallback| hidl object reference to our
   1678  * global callback list.
   1679  *
   1680  * @param callback Hidl reference of the |ISupplicantCallback| object.
   1681  *
   1682  * @return 0 on success, 1 on failure.
   1683  */
   1684 int HidlManager::addSupplicantCallbackHidlObject(
   1685     const android::sp<ISupplicantCallback> &callback)
   1686 {
   1687 	// Register for death notification before we add it to our list.
   1688 	auto on_hidl_died_fctor = std::bind(
   1689 	    &HidlManager::removeSupplicantCallbackHidlObject, this,
   1690 	    std::placeholders::_1);
   1691 	return registerForDeathAndAddCallbackHidlObjectToList<
   1692 	    ISupplicantCallback>(
   1693 	    callback, on_hidl_died_fctor, supplicant_callbacks_);
   1694 }
   1695 
   1696 /**
   1697  * Add a new iface callback hidl object reference to our
   1698  * interface callback list.
   1699  *
   1700  * @param ifname Name of the corresponding interface.
   1701  * @param callback Hidl reference of the callback object.
   1702  *
   1703  * @return 0 on success, 1 on failure.
   1704  */
   1705 int HidlManager::addP2pIfaceCallbackHidlObject(
   1706     const std::string &ifname,
   1707     const android::sp<ISupplicantP2pIfaceCallback> &callback)
   1708 {
   1709 	const std::function<void(
   1710 	    const android::sp<ISupplicantP2pIfaceCallback> &)>
   1711 	    on_hidl_died_fctor = std::bind(
   1712 		&HidlManager::removeP2pIfaceCallbackHidlObject, this, ifname,
   1713 		std::placeholders::_1);
   1714 	return addIfaceCallbackHidlObjectToMap(
   1715 	    ifname, callback, on_hidl_died_fctor, p2p_iface_callbacks_map_);
   1716 }
   1717 
   1718 /**
   1719  * Add a new iface callback hidl object reference to our
   1720  * interface callback list.
   1721  *
   1722  * @param ifname Name of the corresponding interface.
   1723  * @param callback Hidl reference of the callback object.
   1724  *
   1725  * @return 0 on success, 1 on failure.
   1726  */
   1727 int HidlManager::addStaIfaceCallbackHidlObject(
   1728     const std::string &ifname,
   1729     const android::sp<ISupplicantStaIfaceCallback> &callback)
   1730 {
   1731 	const std::function<void(
   1732 	    const android::sp<ISupplicantStaIfaceCallback> &)>
   1733 	    on_hidl_died_fctor = std::bind(
   1734 		&HidlManager::removeStaIfaceCallbackHidlObject, this, ifname,
   1735 		std::placeholders::_1);
   1736 	return addIfaceCallbackHidlObjectToMap(
   1737 	    ifname, callback, on_hidl_died_fctor, sta_iface_callbacks_map_);
   1738 }
   1739 
   1740 /**
   1741  * Add a new network callback hidl object reference to our network callback
   1742  * list.
   1743  *
   1744  * @param ifname Name of the corresponding interface.
   1745  * @param network_id ID of the corresponding network.
   1746  * @param callback Hidl reference of the callback object.
   1747  *
   1748  * @return 0 on success, 1 on failure.
   1749  */
   1750 int HidlManager::addP2pNetworkCallbackHidlObject(
   1751     const std::string &ifname, int network_id,
   1752     const android::sp<ISupplicantP2pNetworkCallback> &callback)
   1753 {
   1754 	const std::function<void(
   1755 	    const android::sp<ISupplicantP2pNetworkCallback> &)>
   1756 	    on_hidl_died_fctor = std::bind(
   1757 		&HidlManager::removeP2pNetworkCallbackHidlObject, this, ifname,
   1758 		network_id, std::placeholders::_1);
   1759 	return addNetworkCallbackHidlObjectToMap(
   1760 	    ifname, network_id, callback, on_hidl_died_fctor,
   1761 	    p2p_network_callbacks_map_);
   1762 }
   1763 
   1764 /**
   1765  * Add a new network callback hidl object reference to our network callback
   1766  * list.
   1767  *
   1768  * @param ifname Name of the corresponding interface.
   1769  * @param network_id ID of the corresponding network.
   1770  * @param callback Hidl reference of the callback object.
   1771  *
   1772  * @return 0 on success, 1 on failure.
   1773  */
   1774 int HidlManager::addStaNetworkCallbackHidlObject(
   1775     const std::string &ifname, int network_id,
   1776     const android::sp<ISupplicantStaNetworkCallback> &callback)
   1777 {
   1778 	const std::function<void(
   1779 	    const android::sp<ISupplicantStaNetworkCallback> &)>
   1780 	    on_hidl_died_fctor = std::bind(
   1781 		&HidlManager::removeStaNetworkCallbackHidlObject, this, ifname,
   1782 		network_id, std::placeholders::_1);
   1783 	return addNetworkCallbackHidlObjectToMap(
   1784 	    ifname, network_id, callback, on_hidl_died_fctor,
   1785 	    sta_network_callbacks_map_);
   1786 }
   1787 
   1788 /**
   1789  * Removes the provided |ISupplicantCallback| hidl object reference
   1790  * from our global callback list.
   1791  *
   1792  * @param callback Hidl reference of the |ISupplicantCallback| object.
   1793  */
   1794 void HidlManager::removeSupplicantCallbackHidlObject(
   1795     const android::sp<ISupplicantCallback> &callback)
   1796 {
   1797 	supplicant_callbacks_.erase(
   1798 	    std::remove(
   1799 		supplicant_callbacks_.begin(), supplicant_callbacks_.end(),
   1800 		callback),
   1801 	    supplicant_callbacks_.end());
   1802 }
   1803 
   1804 /**
   1805  * Removes the provided iface callback hidl object reference from
   1806  * our interface callback list.
   1807  *
   1808  * @param ifname Name of the corresponding interface.
   1809  * @param callback Hidl reference of the callback object.
   1810  */
   1811 void HidlManager::removeP2pIfaceCallbackHidlObject(
   1812     const std::string &ifname,
   1813     const android::sp<ISupplicantP2pIfaceCallback> &callback)
   1814 {
   1815 	return removeIfaceCallbackHidlObjectFromMap(
   1816 	    ifname, callback, p2p_iface_callbacks_map_);
   1817 }
   1818 
   1819 /**
   1820  * Removes the provided iface callback hidl object reference from
   1821  * our interface callback list.
   1822  *
   1823  * @param ifname Name of the corresponding interface.
   1824  * @param callback Hidl reference of the callback object.
   1825  */
   1826 void HidlManager::removeStaIfaceCallbackHidlObject(
   1827     const std::string &ifname,
   1828     const android::sp<ISupplicantStaIfaceCallback> &callback)
   1829 {
   1830 	return removeIfaceCallbackHidlObjectFromMap(
   1831 	    ifname, callback, sta_iface_callbacks_map_);
   1832 }
   1833 
   1834 /**
   1835  * Removes the provided network callback hidl object reference from
   1836  * our network callback list.
   1837  *
   1838  * @param ifname Name of the corresponding interface.
   1839  * @param network_id ID of the corresponding network.
   1840  * @param callback Hidl reference of the callback object.
   1841  */
   1842 void HidlManager::removeP2pNetworkCallbackHidlObject(
   1843     const std::string &ifname, int network_id,
   1844     const android::sp<ISupplicantP2pNetworkCallback> &callback)
   1845 {
   1846 	return removeNetworkCallbackHidlObjectFromMap(
   1847 	    ifname, network_id, callback, p2p_network_callbacks_map_);
   1848 }
   1849 
   1850 /**
   1851  * Removes the provided network callback hidl object reference from
   1852  * our network callback list.
   1853  *
   1854  * @param ifname Name of the corresponding interface.
   1855  * @param network_id ID of the corresponding network.
   1856  * @param callback Hidl reference of the callback object.
   1857  */
   1858 void HidlManager::removeStaNetworkCallbackHidlObject(
   1859     const std::string &ifname, int network_id,
   1860     const android::sp<ISupplicantStaNetworkCallback> &callback)
   1861 {
   1862 	return removeNetworkCallbackHidlObjectFromMap(
   1863 	    ifname, network_id, callback, sta_network_callbacks_map_);
   1864 }
   1865 
   1866 /**
   1867  * Helper function to invoke the provided callback method on all the
   1868  * registered |ISupplicantCallback| callback hidl objects.
   1869  *
   1870  * @param method Pointer to the required hidl method from
   1871  * |ISupplicantCallback|.
   1872  */
   1873 void HidlManager::callWithEachSupplicantCallback(
   1874     const std::function<Return<void>(android::sp<ISupplicantCallback>)> &method)
   1875 {
   1876 	for (const auto &callback : supplicant_callbacks_) {
   1877 		if (!method(callback).isOk()) {
   1878 			wpa_printf(MSG_ERROR, "Failed to invoke HIDL callback");
   1879 		}
   1880 	}
   1881 }
   1882 
   1883 /**
   1884  * Helper fucntion to invoke the provided callback method on all the
   1885  * registered iface callback hidl objects for the specified
   1886  * |ifname|.
   1887  *
   1888  * @param ifname Name of the corresponding interface.
   1889  * @param method Pointer to the required hidl method from
   1890  * |ISupplicantIfaceCallback|.
   1891  */
   1892 void HidlManager::callWithEachP2pIfaceCallback(
   1893     const std::string &ifname,
   1894     const std::function<Return<void>(android::sp<ISupplicantP2pIfaceCallback>)>
   1895 	&method)
   1896 {
   1897 	callWithEachIfaceCallback(ifname, method, p2p_iface_callbacks_map_);
   1898 }
   1899 
   1900 /**
   1901  * Helper function to invoke the provided callback method on all the
   1902  * registered V1.1 interface callback hidl objects for the specified
   1903  * |ifname|.
   1904  *
   1905  * @param ifname Name of the corresponding interface.
   1906  * @param method Pointer to the required hidl method from
   1907  * |V1_1::ISupplicantIfaceCallback|.
   1908  */
   1909 void HidlManager::callWithEachStaIfaceCallback_1_1(
   1910     const std::string &ifname,
   1911     const std::function<
   1912 	Return<void>(android::sp<V1_1::ISupplicantStaIfaceCallback>)> &method)
   1913 {
   1914 	callWithEachIfaceCallback_1_1(ifname, method, sta_iface_callbacks_map_);
   1915 }
   1916 
   1917 /**
   1918  * Helper function to invoke the provided callback method on all the
   1919  * registered V1.2 interface callback hidl objects for the specified
   1920  * |ifname|.
   1921  *
   1922  * @param ifname Name of the corresponding interface.
   1923  * @param method Pointer to the required hidl method from
   1924  * |V1_2::ISupplicantIfaceCallback|.
   1925  */
   1926 void HidlManager::callWithEachStaIfaceCallback_1_2(
   1927     const std::string &ifname,
   1928     const std::function<
   1929 	Return<void>(android::sp<V1_2::ISupplicantStaIfaceCallback>)> &method)
   1930 {
   1931 	callWithEachIfaceCallback_1_2(ifname, method, sta_iface_callbacks_map_);
   1932 }
   1933 
   1934 /**
   1935  * Helper function to invoke the provided callback method on all the
   1936  * registered interface callback hidl objects for the specified
   1937  * |ifname|.
   1938  *
   1939  * @param ifname Name of the corresponding interface.
   1940  * @param method Pointer to the required hidl method from
   1941  * |ISupplicantIfaceCallback|.
   1942  */
   1943 void HidlManager::callWithEachStaIfaceCallback(
   1944     const std::string &ifname,
   1945     const std::function<Return<void>(android::sp<ISupplicantStaIfaceCallback>)>
   1946 	&method)
   1947 {
   1948 	callWithEachIfaceCallback(ifname, method, sta_iface_callbacks_map_);
   1949 }
   1950 
   1951 /**
   1952  * Helper function to invoke the provided callback method on all the
   1953  * registered network callback hidl objects for the specified
   1954  * |ifname| & |network_id|.
   1955  *
   1956  * @param ifname Name of the corresponding interface.
   1957  * @param network_id ID of the corresponding network.
   1958  * @param method Pointer to the required hidl method from
   1959  * |ISupplicantP2pNetworkCallback| or |ISupplicantStaNetworkCallback| .
   1960  */
   1961 void HidlManager::callWithEachP2pNetworkCallback(
   1962     const std::string &ifname, int network_id,
   1963     const std::function<
   1964 	Return<void>(android::sp<ISupplicantP2pNetworkCallback>)> &method)
   1965 {
   1966 	callWithEachNetworkCallback(
   1967 	    ifname, network_id, method, p2p_network_callbacks_map_);
   1968 }
   1969 
   1970 /**
   1971  * Helper function to invoke the provided callback method on all the
   1972  * registered network callback hidl objects for the specified
   1973  * |ifname| & |network_id|.
   1974  *
   1975  * @param ifname Name of the corresponding interface.
   1976  * @param network_id ID of the corresponding network.
   1977  * @param method Pointer to the required hidl method from
   1978  * |ISupplicantP2pNetworkCallback| or |ISupplicantStaNetworkCallback| .
   1979  */
   1980 void HidlManager::callWithEachStaNetworkCallback(
   1981     const std::string &ifname, int network_id,
   1982     const std::function<
   1983 	Return<void>(android::sp<ISupplicantStaNetworkCallback>)> &method)
   1984 {
   1985 	callWithEachNetworkCallback(
   1986 	    ifname, network_id, method, sta_network_callbacks_map_);
   1987 }
   1988 }  // namespace implementation
   1989 }  // namespace V1_2
   1990 }  // namespace supplicant
   1991 }  // namespace wifi
   1992 }  // namespace hardware
   1993 }  // namespace android
   1994