wpa_supplicant(hidl): Add network param getters
Add getters for all the enterprise network params. These are useful only
for reading out network configs from wpa_supplicant.con for migrating
config store data from N to O. Otherwise, wpa_supplicant should only be
a sink and should only need setter methods.
While there,
Fixed a bug with the eap phase2 method string construction in the HIDL
interface.
Bug: 33583001
Bug: 31497348
Test: Will add gtests for these soon.
Change-Id: I1fe802638b1db96870d0eaf76252b2a35b307523
diff --git a/wpa_supplicant/hidl/sta_network.cpp b/wpa_supplicant/hidl/sta_network.cpp
index 15e628f..226c1bd 100644
--- a/wpa_supplicant/hidl/sta_network.cpp
+++ b/wpa_supplicant/hidl/sta_network.cpp
@@ -48,6 +48,8 @@
static_cast<uint32_t>(ISupplicantStaNetwork::EapPhase2Method::GTC) + 1;
constexpr char const *kEapPhase2MethodStrings[kEapPhase2MethodMax] = {
"NULL", "PAP", "MSCHAP", "MSCHAPV2", "GTC"};
+constexpr char kEapPhase2AuthPrefix[] = "auth=";
+constexpr char kEapPhase2AuthEapPrefix[] = "autheap=";
} // namespace
namespace android {
@@ -394,6 +396,107 @@
&StaNetwork::getRequirePmfInternal, _hidl_cb);
}
+Return<void> StaNetwork::getEapMethod(getEapMethod_cb _hidl_cb)
+{
+ return validateAndCall(
+ this, SupplicantStatusCode::FAILURE_NETWORK_INVALID,
+ &StaNetwork::getEapMethodInternal, _hidl_cb);
+}
+
+Return<void> StaNetwork::getEapPhase2Method(getEapPhase2Method_cb _hidl_cb)
+{
+ return validateAndCall(
+ this, SupplicantStatusCode::FAILURE_NETWORK_INVALID,
+ &StaNetwork::getEapPhase2MethodInternal, _hidl_cb);
+}
+
+Return<void> StaNetwork::getEapIdentity(getEapIdentity_cb _hidl_cb)
+{
+ return validateAndCall(
+ this, SupplicantStatusCode::FAILURE_NETWORK_INVALID,
+ &StaNetwork::getEapIdentityInternal, _hidl_cb);
+}
+
+Return<void> StaNetwork::getEapAnonymousIdentity(
+ getEapAnonymousIdentity_cb _hidl_cb)
+{
+ return validateAndCall(
+ this, SupplicantStatusCode::FAILURE_NETWORK_INVALID,
+ &StaNetwork::getEapAnonymousIdentityInternal, _hidl_cb);
+}
+
+Return<void> StaNetwork::getEapPassword(getEapPassword_cb _hidl_cb)
+{
+ return validateAndCall(
+ this, SupplicantStatusCode::FAILURE_NETWORK_INVALID,
+ &StaNetwork::getEapPasswordInternal, _hidl_cb);
+}
+
+Return<void> StaNetwork::getEapCACert(getEapCACert_cb _hidl_cb)
+{
+ return validateAndCall(
+ this, SupplicantStatusCode::FAILURE_NETWORK_INVALID,
+ &StaNetwork::getEapCACertInternal, _hidl_cb);
+}
+
+Return<void> StaNetwork::getEapCAPath(getEapCAPath_cb _hidl_cb)
+{
+ return validateAndCall(
+ this, SupplicantStatusCode::FAILURE_NETWORK_INVALID,
+ &StaNetwork::getEapCAPathInternal, _hidl_cb);
+}
+
+Return<void> StaNetwork::getEapClientCert(getEapClientCert_cb _hidl_cb)
+{
+ return validateAndCall(
+ this, SupplicantStatusCode::FAILURE_NETWORK_INVALID,
+ &StaNetwork::getEapClientCertInternal, _hidl_cb);
+}
+
+Return<void> StaNetwork::getEapPrivateKey(getEapPrivateKey_cb _hidl_cb)
+{
+ return validateAndCall(
+ this, SupplicantStatusCode::FAILURE_NETWORK_INVALID,
+ &StaNetwork::getEapPrivateKeyInternal, _hidl_cb);
+}
+
+Return<void> StaNetwork::getEapSubjectMatch(getEapSubjectMatch_cb _hidl_cb)
+{
+ return validateAndCall(
+ this, SupplicantStatusCode::FAILURE_NETWORK_INVALID,
+ &StaNetwork::getEapSubjectMatchInternal, _hidl_cb);
+}
+
+Return<void> StaNetwork::getEapAltSubjectMatch(
+ getEapAltSubjectMatch_cb _hidl_cb)
+{
+ return validateAndCall(
+ this, SupplicantStatusCode::FAILURE_NETWORK_INVALID,
+ &StaNetwork::getEapSubjectMatchInternal, _hidl_cb);
+}
+
+Return<void> StaNetwork::getEapEngine(getEapEngine_cb _hidl_cb)
+{
+ return validateAndCall(
+ this, SupplicantStatusCode::FAILURE_NETWORK_INVALID,
+ &StaNetwork::getEapEngineInternal, _hidl_cb);
+}
+
+Return<void> StaNetwork::getEapEngineID(getEapEngineID_cb _hidl_cb)
+{
+ return validateAndCall(
+ this, SupplicantStatusCode::FAILURE_NETWORK_INVALID,
+ &StaNetwork::getEapEngineIDInternal, _hidl_cb);
+}
+
+Return<void> StaNetwork::getEapDomainSuffixMatch(
+ getEapDomainSuffixMatch_cb _hidl_cb)
+{
+ return validateAndCall(
+ this, SupplicantStatusCode::FAILURE_NETWORK_INVALID,
+ &StaNetwork::getEapDomainSuffixMatchInternal, _hidl_cb);
+}
+
Return<void> StaNetwork::enable(bool no_connect, enable_cb _hidl_cb)
{
return validateAndCall(
@@ -662,10 +765,16 @@
SupplicantStatus StaNetwork::setEapMethodInternal(
ISupplicantStaNetwork::EapMethod method)
{
+ uint32_t eap_method_idx = static_cast<
+ std::underlying_type<ISupplicantStaNetwork::EapMethod>::type>(
+ method);
+ if (eap_method_idx >= kEapMethodMax) {
+ return {SupplicantStatusCode::FAILURE_ARGS_INVALID, ""};
+ }
+
struct wpa_ssid *wpa_ssid = retrieveNetworkPtr();
int retrieved_vendor, retrieved_method;
- const char *method_str =
- kEapMethodStrings[static_cast<uint32_t>(method)];
+ const char *method_str = kEapMethodStrings[eap_method_idx];
// This string lookup is needed to check if the device supports the
// corresponding EAP type.
retrieved_method = eap_peer_get_type(method_str, &retrieved_vendor);
@@ -709,10 +818,34 @@
SupplicantStatus StaNetwork::setEapPhase2MethodInternal(
ISupplicantStaNetwork::EapPhase2Method method)
{
+ uint32_t eap_phase2_method_idx = static_cast<
+ std::underlying_type<ISupplicantStaNetwork::EapPhase2Method>::type>(
+ method);
+ if (eap_phase2_method_idx >= kEapPhase2MethodMax) {
+ return {SupplicantStatusCode::FAILURE_ARGS_INVALID, ""};
+ }
+
struct wpa_ssid *wpa_ssid = retrieveNetworkPtr();
+ // EAP method needs to be set for us to construct the eap
+ // phase 2 method string.
+ SupplicantStatus status;
+ ISupplicantStaNetwork::EapMethod eap_method;
+ std::tie(status, eap_method) = getEapMethodInternal();
+ if (status.code != SupplicantStatusCode::SUCCESS) {
+ return {SupplicantStatusCode::FAILURE_UNKNOWN,
+ "EAP method not set"};
+ }
+ std::string eap_phase2_str;
+ if (eap_method == ISupplicantStaNetwork::EapMethod::TTLS &&
+ method == ISupplicantStaNetwork::EapPhase2Method::GTC) {
+ eap_phase2_str = kEapPhase2AuthEapPrefix;
+ } else {
+ eap_phase2_str = kEapPhase2AuthPrefix;
+ }
+ eap_phase2_str += kEapPhase2MethodStrings[eap_phase2_method_idx];
if (setStringFieldAndResetState(
- kEapPhase2MethodStrings[static_cast<uint32_t>(method)],
- &(wpa_ssid->eap.phase2), "eap phase2")) {
+ eap_phase2_str.c_str(), &(wpa_ssid->eap.phase2),
+ "eap phase2")) {
return {SupplicantStatusCode::FAILURE_UNKNOWN, ""};
}
return {SupplicantStatusCode::SUCCESS, ""};
@@ -950,10 +1083,201 @@
(wpa_ssid->ieee80211w == MGMT_FRAME_PROTECTION_REQUIRED)};
}
+std::pair<SupplicantStatus, ISupplicantStaNetwork::EapMethod>
+StaNetwork::getEapMethodInternal()
+{
+ struct wpa_ssid *wpa_ssid = retrieveNetworkPtr();
+ if (!wpa_ssid->eap.eap_methods) {
+ return {{SupplicantStatusCode::FAILURE_UNKNOWN, ""}, {}};
+ }
+ // wpa_supplicant can support setting multiple eap methods for each
+ // network. But, this is not really used by Android. So, just reading
+ // the first EAP method for each network.
+ const std::string eap_method_str = eap_get_name(
+ wpa_ssid->eap.eap_methods[0].vendor,
+ static_cast<EapType>(wpa_ssid->eap.eap_methods[0].method));
+ size_t eap_method_idx =
+ std::find(
+ std::begin(kEapMethodStrings), std::end(kEapMethodStrings),
+ eap_method_str) -
+ std::begin(kEapMethodStrings);
+ if (eap_method_idx >= kEapMethodMax) {
+ return {{SupplicantStatusCode::FAILURE_UNKNOWN, ""}, {}};
+ }
+ return {{SupplicantStatusCode::SUCCESS, ""},
+ static_cast<ISupplicantStaNetwork::EapMethod>(eap_method_idx)};
+}
+
+std::pair<SupplicantStatus, ISupplicantStaNetwork::EapPhase2Method>
+StaNetwork::getEapPhase2MethodInternal()
+{
+ struct wpa_ssid *wpa_ssid = retrieveNetworkPtr();
+ if (!wpa_ssid->eap.phase2) {
+ return {{SupplicantStatusCode::FAILURE_UNKNOWN, ""}, {}};
+ }
+ const std::string eap_phase2_method_str_with_prefix =
+ wpa_ssid->eap.phase2;
+ std::string eap_phase2_method_str;
+ // Strip out the phase 2 method prefix before doing a reverse lookup
+ // of phase 2 string to the Eap Phase 2 type.
+ if (eap_phase2_method_str_with_prefix.find(kEapPhase2AuthPrefix) == 0) {
+ eap_phase2_method_str =
+ eap_phase2_method_str_with_prefix.substr(
+ strlen(kEapPhase2AuthPrefix),
+ eap_phase2_method_str_with_prefix.size());
+ } else if (
+ eap_phase2_method_str_with_prefix.find(kEapPhase2AuthEapPrefix) ==
+ 0) {
+ eap_phase2_method_str =
+ eap_phase2_method_str_with_prefix.substr(
+ strlen(kEapPhase2AuthEapPrefix),
+ eap_phase2_method_str_with_prefix.size());
+ }
+ size_t eap_phase2_method_idx =
+ std::find(
+ std::begin(kEapPhase2MethodStrings),
+ std::end(kEapPhase2MethodStrings), eap_phase2_method_str) -
+ std::begin(kEapPhase2MethodStrings);
+ if (eap_phase2_method_idx >= kEapPhase2MethodMax) {
+ return {{SupplicantStatusCode::FAILURE_UNKNOWN, ""}, {}};
+ }
+ return {{SupplicantStatusCode::SUCCESS, ""},
+ static_cast<ISupplicantStaNetwork::EapPhase2Method>(
+ eap_phase2_method_idx)};
+}
+
+std::pair<SupplicantStatus, std::vector<uint8_t>>
+StaNetwork::getEapIdentityInternal()
+{
+ struct wpa_ssid *wpa_ssid = retrieveNetworkPtr();
+ if (!wpa_ssid->eap.identity) {
+ return {{SupplicantStatusCode::FAILURE_UNKNOWN, ""}, {}};
+ }
+ return {{SupplicantStatusCode::SUCCESS, ""},
+ std::vector<uint8_t>(
+ wpa_ssid->eap.identity,
+ wpa_ssid->eap.identity + wpa_ssid->eap.identity_len)};
+}
+
+std::pair<SupplicantStatus, std::vector<uint8_t>>
+StaNetwork::getEapAnonymousIdentityInternal()
+{
+ struct wpa_ssid *wpa_ssid = retrieveNetworkPtr();
+ if (!wpa_ssid->eap.anonymous_identity) {
+ return {{SupplicantStatusCode::FAILURE_UNKNOWN, ""}, {}};
+ }
+ return {{SupplicantStatusCode::SUCCESS, ""},
+ std::vector<uint8_t>(
+ wpa_ssid->eap.anonymous_identity,
+ wpa_ssid->eap.anonymous_identity +
+ wpa_ssid->eap.anonymous_identity_len)};
+}
+
+std::pair<SupplicantStatus, std::vector<uint8_t>>
+StaNetwork::getEapPasswordInternal()
+{
+ struct wpa_ssid *wpa_ssid = retrieveNetworkPtr();
+ if (!wpa_ssid->eap.password) {
+ return {{SupplicantStatusCode::FAILURE_UNKNOWN, ""}, {}};
+ }
+ return {{SupplicantStatusCode::SUCCESS, ""},
+ std::vector<uint8_t>(
+ wpa_ssid->eap.password,
+ wpa_ssid->eap.password + wpa_ssid->eap.password_len)};
+}
+
+std::pair<SupplicantStatus, std::string> StaNetwork::getEapCACertInternal()
+{
+ struct wpa_ssid *wpa_ssid = retrieveNetworkPtr();
+ if (!wpa_ssid->eap.ca_cert) {
+ return {{SupplicantStatusCode::FAILURE_UNKNOWN, ""}, {}};
+ }
+ return {{SupplicantStatusCode::SUCCESS, ""},
+ reinterpret_cast<char *>(wpa_ssid->eap.ca_cert)};
+}
+
+std::pair<SupplicantStatus, std::string> StaNetwork::getEapCAPathInternal()
+{
+ struct wpa_ssid *wpa_ssid = retrieveNetworkPtr();
+ if (!wpa_ssid->eap.ca_path) {
+ return {{SupplicantStatusCode::FAILURE_UNKNOWN, ""}, {}};
+ }
+ return {{SupplicantStatusCode::SUCCESS, ""},
+ reinterpret_cast<char *>(wpa_ssid->eap.ca_path)};
+}
+
+std::pair<SupplicantStatus, std::string> StaNetwork::getEapClientCertInternal()
+{
+ struct wpa_ssid *wpa_ssid = retrieveNetworkPtr();
+ if (!wpa_ssid->eap.client_cert) {
+ return {{SupplicantStatusCode::FAILURE_UNKNOWN, ""}, {}};
+ }
+ return {{SupplicantStatusCode::SUCCESS, ""},
+ reinterpret_cast<char *>(wpa_ssid->eap.client_cert)};
+}
+
+std::pair<SupplicantStatus, std::string> StaNetwork::getEapPrivateKeyInternal()
+{
+ struct wpa_ssid *wpa_ssid = retrieveNetworkPtr();
+ if (!wpa_ssid->eap.private_key) {
+ return {{SupplicantStatusCode::FAILURE_UNKNOWN, ""}, {}};
+ }
+ return {{SupplicantStatusCode::SUCCESS, ""},
+ reinterpret_cast<char *>(wpa_ssid->eap.private_key)};
+}
+
+std::pair<SupplicantStatus, std::string>
+StaNetwork::getEapSubjectMatchInternal()
+{
+ struct wpa_ssid *wpa_ssid = retrieveNetworkPtr();
+ if (!wpa_ssid->eap.subject_match) {
+ return {{SupplicantStatusCode::FAILURE_UNKNOWN, ""}, {}};
+ }
+ return {{SupplicantStatusCode::SUCCESS, ""},
+ reinterpret_cast<char *>(wpa_ssid->eap.subject_match)};
+}
+
+std::pair<SupplicantStatus, std::string>
+StaNetwork::getEapAltSubjectMatchInternal()
+{
+ struct wpa_ssid *wpa_ssid = retrieveNetworkPtr();
+ if (!wpa_ssid->eap.altsubject_match) {
+ return {{SupplicantStatusCode::FAILURE_UNKNOWN, ""}, {}};
+ }
+ return {{SupplicantStatusCode::SUCCESS, ""},
+ reinterpret_cast<char *>(wpa_ssid->eap.altsubject_match)};
+}
+
+std::pair<SupplicantStatus, bool> StaNetwork::getEapEngineInternal()
+{
+ struct wpa_ssid *wpa_ssid = retrieveNetworkPtr();
+ return {{SupplicantStatusCode::SUCCESS, ""}, wpa_ssid->eap.engine == 1};
+}
+
+std::pair<SupplicantStatus, std::string> StaNetwork::getEapEngineIDInternal()
+{
+ struct wpa_ssid *wpa_ssid = retrieveNetworkPtr();
+ if (!wpa_ssid->eap.engine_id) {
+ return {{SupplicantStatusCode::FAILURE_UNKNOWN, ""}, {}};
+ }
+ return {{SupplicantStatusCode::SUCCESS, ""}, {wpa_ssid->eap.engine_id}};
+}
+
+std::pair<SupplicantStatus, std::string>
+StaNetwork::getEapDomainSuffixMatchInternal()
+{
+ struct wpa_ssid *wpa_ssid = retrieveNetworkPtr();
+ if (!wpa_ssid->eap.domain_suffix_match) {
+ return {{SupplicantStatusCode::FAILURE_UNKNOWN, ""}, {}};
+ }
+ return {{SupplicantStatusCode::SUCCESS, ""},
+ {wpa_ssid->eap.domain_suffix_match}};
+}
+
SupplicantStatus StaNetwork::enableInternal(bool no_connect)
{
struct wpa_ssid *wpa_ssid = retrieveNetworkPtr();
- if (wpa_ssid->disabled != 0) {
+ if (wpa_ssid->disabled == 2) {
return {SupplicantStatusCode::FAILURE_UNKNOWN, ""};
}
struct wpa_supplicant *wpa_s = retrieveIfacePtr();
@@ -1118,8 +1442,7 @@
*/
struct wpa_supplicant *StaNetwork::retrieveIfacePtr()
{
- return wpa_supplicant_get_iface(
- (struct wpa_global *)wpa_global_, ifname_.c_str());
+ return wpa_supplicant_get_iface(wpa_global_, ifname_.c_str());
}
/**
diff --git a/wpa_supplicant/hidl/sta_network.h b/wpa_supplicant/hidl/sta_network.h
index f35f230..68ab139 100644
--- a/wpa_supplicant/hidl/sta_network.h
+++ b/wpa_supplicant/hidl/sta_network.h
@@ -131,6 +131,25 @@
uint32_t key_idx, getWepKey_cb _hidl_cb) override;
Return<void> getWepTxKeyIdx(getWepTxKeyIdx_cb _hidl_cb) override;
Return<void> getRequirePmf(getRequirePmf_cb _hidl_cb) override;
+ Return<void> getEapMethod(getEapMethod_cb _hidl_cb) override;
+ Return<void> getEapPhase2Method(
+ getEapPhase2Method_cb _hidl_cb) override;
+ Return<void> getEapIdentity(getEapIdentity_cb _hidl_cb) override;
+ Return<void> getEapAnonymousIdentity(
+ getEapAnonymousIdentity_cb _hidl_cb) override;
+ Return<void> getEapPassword(getEapPassword_cb _hidl_cb) override;
+ Return<void> getEapCACert(getEapCACert_cb _hidl_cb) override;
+ Return<void> getEapCAPath(getEapCAPath_cb _hidl_cb) override;
+ Return<void> getEapClientCert(getEapClientCert_cb _hidl_cb) override;
+ Return<void> getEapPrivateKey(getEapPrivateKey_cb _hidl_cb) override;
+ Return<void> getEapSubjectMatch(
+ getEapSubjectMatch_cb _hidl_cb) override;
+ Return<void> getEapAltSubjectMatch(
+ getEapAltSubjectMatch_cb _hidl_cb) override;
+ Return<void> getEapEngine(getEapEngine_cb _hidl_cb) override;
+ Return<void> getEapEngineID(getEapEngineID_cb _hidl_cb) override;
+ Return<void> getEapDomainSuffixMatch(
+ getEapDomainSuffixMatch_cb _hidl_cb) override;
Return<void> enable(bool no_connect, enable_cb _hidl_cb) override;
Return<void> disable(disable_cb _hidl_cb) override;
Return<void> select(select_cb _hidl_cb) override;
@@ -201,6 +220,27 @@
uint32_t key_idx);
std::pair<SupplicantStatus, uint32_t> getWepTxKeyIdxInternal();
std::pair<SupplicantStatus, bool> getRequirePmfInternal();
+ std::pair<SupplicantStatus, ISupplicantStaNetwork::EapMethod>
+ getEapMethodInternal();
+ std::pair<SupplicantStatus, ISupplicantStaNetwork::EapPhase2Method>
+ getEapPhase2MethodInternal();
+ std::pair<SupplicantStatus, std::vector<uint8_t>>
+ getEapIdentityInternal();
+ std::pair<SupplicantStatus, std::vector<uint8_t>>
+ getEapAnonymousIdentityInternal();
+ std::pair<SupplicantStatus, std::vector<uint8_t>>
+ getEapPasswordInternal();
+ std::pair<SupplicantStatus, std::string> getEapCACertInternal();
+ std::pair<SupplicantStatus, std::string> getEapCAPathInternal();
+ std::pair<SupplicantStatus, std::string> getEapClientCertInternal();
+ std::pair<SupplicantStatus, std::string> getEapPrivateKeyInternal();
+ std::pair<SupplicantStatus, std::string> getEapSubjectMatchInternal();
+ std::pair<SupplicantStatus, std::string>
+ getEapAltSubjectMatchInternal();
+ std::pair<SupplicantStatus, bool> getEapEngineInternal();
+ std::pair<SupplicantStatus, std::string> getEapEngineIDInternal();
+ std::pair<SupplicantStatus, std::string>
+ getEapDomainSuffixMatchInternal();
SupplicantStatus enableInternal(bool no_connect);
SupplicantStatus disableInternal();
SupplicantStatus selectInternal();
@@ -237,7 +277,7 @@
// Reference to the global wpa_struct. This is assumed to be valid
// for the lifetime of the process.
- const struct wpa_global* wpa_global_;
+ struct wpa_global* wpa_global_;
// Name of the iface this network belongs to.
const std::string ifname_;
// Id of the network this hidl object controls.