// Copyright 2018 The Chromium OS Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include <memory>

#include "shill/eap_credentials.h"

#include <string>
#include <vector>

#include <base/optional.h>
#include <base/stl_util.h>
#include <chromeos/dbus/service_constants.h>
#include <gtest/gtest.h>
#include <libpasswordprovider/fake_password_provider.h>
#include <libpasswordprovider/password.h>
#include <libpasswordprovider/password_provider.h>
#include <libpasswordprovider/password_provider_test_utils.h>

#include "shill/fake_store.h"
#include "shill/key_value_store.h"
#include "shill/mock_certificate_file.h"
#include "shill/mock_log.h"
#include "shill/mock_metrics.h"
#include "shill/supplicant/wpa_supplicant.h"
#include "shill/technology.h"

using testing::_;
using testing::AnyNumber;
using testing::DoAll;
using testing::Mock;
using testing::Return;
using testing::SetArgPointee;

namespace shill {

class EapCredentialsTest : public testing::Test {
 public:
  EapCredentialsTest() = default;
  ~EapCredentialsTest() override = default;

 protected:
  void PopulateSupplicantProperties() {
    eap_.PopulateSupplicantProperties(&certificate_file_, &params_);
  }

  void SetAnonymousIdentity(const std::string& anonymous_identity) {
    eap_.anonymous_identity_ = anonymous_identity;
  }
  void SetCACertPEM(const std::vector<std::string>& ca_cert_pem) {
    eap_.ca_cert_pem_ = ca_cert_pem;
  }
  void SetCertId(const std::string& cert_id) { eap_.cert_id_ = cert_id; }
  void SetCACertId(const std::string& ca_cert_id) {
    eap_.ca_cert_id_ = ca_cert_id;
  }
  void SetEap(const std::string& eap) { eap_.eap_ = eap; }
  void SetIdentity(const std::string& identity) { eap_.identity_ = identity; }
  void SetInnerEap(const std::string& inner_eap) {
    eap_.inner_eap_ = inner_eap;
  }
  void SetTLSVersionMax(const std::string& tls_version_max) {
    eap_.tls_version_max_ = tls_version_max;
  }
  void SetKeyId(const std::string& key_id) { eap_.key_id_ = key_id; }
  const std::string& GetPassword() { return eap_.password_; }
  void SetPassword(const std::string& password) { eap_.password_ = password; }
  void SetPin(const std::string& pin) { eap_.pin_ = pin; }
  void SetUseProactiveKeyCaching(bool use_proactive_key_caching) {
    eap_.use_proactive_key_caching_ = use_proactive_key_caching;
  }
  void SetSubjectAlternativeNameMatch(
      std::vector<std::string> altsubject_match_list) {
    eap_.subject_alternative_name_match_list_ = altsubject_match_list;
  }
  void SetDomainSuffixMatch(std::vector<std::string> domain_suffix_match_list) {
    eap_.domain_suffix_match_list_ = domain_suffix_match_list;
  }
  void SetUseSystemCAs(bool use_system_cas) {
    eap_.use_system_cas_ = use_system_cas;
  }
  void SetUseLoginPassword(bool use_login_password) {
    eap_.use_login_password_ = use_login_password;
  }
  bool IsReset() {
    return eap_.anonymous_identity_.empty() && eap_.cert_id_.empty() &&
           eap_.identity_.empty() && eap_.key_id_.empty() &&
           eap_.password_.empty() && eap_.pin_.empty() &&
           eap_.ca_cert_id_.empty() && eap_.ca_cert_pem_.empty() &&
           eap_.eap_.empty() && eap_.inner_eap_.empty() &&
           eap_.tls_version_max_.empty() && eap_.subject_match_.empty() &&
           eap_.subject_alternative_name_match_list_.empty() &&
           eap_.domain_suffix_match_list_.empty() &&
           eap_.use_system_cas_ == true &&
           eap_.use_proactive_key_caching_ == false &&
           eap_.use_login_password_ == false;
  }

  const std::string& GetKeyManagement() { return eap_.key_management_; }
  bool SetEapPassword(const std::string& password, Error* error) {
    return eap_.SetEapPassword(password, error);
  }

  void SaveLoginPassword(const std::string& password_str) {
    eap_.password_provider_ =
        std::make_unique<password_provider::FakePasswordProvider>();

    auto password = password_provider::test::CreatePassword(password_str);
    ASSERT_TRUE(password);

    eap_.password_provider_->SavePassword(*password);
  }

  EapCredentials eap_;
  MockCertificateFile certificate_file_;
  KeyValueStore params_;
};

TEST_F(EapCredentialsTest, PropertyStore) {
  PropertyStore store;
  eap_.InitPropertyStore(&store);
  const std::string kIdentity("Cross-Eyed Mary");
  Error error;
  EXPECT_TRUE(store.SetStringProperty(kEapIdentityProperty, kIdentity, &error));
  EXPECT_EQ(kIdentity, eap_.identity());
}

TEST_F(EapCredentialsTest, Connectable) {
  // Empty EAP credentials should not make a 802.1x network connectable.
  EXPECT_FALSE(eap_.IsConnectable());

  // Identity alone is not enough.
  SetIdentity("Steel Monkey");
  EXPECT_FALSE(eap_.IsConnectable());

  // Set a password.
  SetPassword("Angry Tapir");

  // Empty "EAP" parameter is treated like "not EAP-TLS", and connectable.
  EXPECT_TRUE(eap_.IsConnectable());

  // Some other non-TLS EAP type.
  SetEap("DodgeBall");
  EXPECT_TRUE(eap_.IsConnectable());

  // EAP-TLS requires certificate parameters, and cares not for passwords.
  SetEap("TLS");
  EXPECT_FALSE(eap_.IsConnectable());

  // Clearing the password won't help.
  SetPassword("");
  EXPECT_FALSE(eap_.IsConnectable());

  // A cert-id + key-id isn't sufficient.
  SetCertId("client-cert-id");
  SetKeyId("client-key-id");
  EXPECT_FALSE(eap_.IsConnectable());

  // We need a PIN for the key id in addition.
  SetPin("pin");
  EXPECT_TRUE(eap_.IsConnectable());

  // If we clear the "EAP" property, a password is required but a client
  // cert is not.
  SetCertId("");
  EXPECT_FALSE(eap_.IsConnectable());

  SetEap("");
  SetPassword("Angry Tapir");
  EXPECT_TRUE(eap_.IsConnectable());
}

TEST_F(EapCredentialsTest, ConnectableUsingPassphrase) {
  EXPECT_FALSE(eap_.IsConnectableUsingPassphrase());

  // No password.
  SetIdentity("TestIdentity");
  EXPECT_FALSE(eap_.IsConnectableUsingPassphrase());

  // Success.
  SetPassword("TestPassword");
  EXPECT_TRUE(eap_.IsConnectableUsingPassphrase());

  // Clear identity.
  SetIdentity("");
  EXPECT_FALSE(eap_.IsConnectableUsingPassphrase());
}

TEST_F(EapCredentialsTest, IsEapAuthenticationProperty) {
  EXPECT_TRUE(EapCredentials::IsEapAuthenticationProperty(
      kEapAnonymousIdentityProperty));
  EXPECT_TRUE(EapCredentials::IsEapAuthenticationProperty(kEapCertIdProperty));
  EXPECT_TRUE(
      EapCredentials::IsEapAuthenticationProperty(kEapIdentityProperty));
  EXPECT_TRUE(EapCredentials::IsEapAuthenticationProperty(kEapKeyIdProperty));
  EXPECT_TRUE(EapCredentials::IsEapAuthenticationProperty(kEapKeyMgmtProperty));
  EXPECT_TRUE(
      EapCredentials::IsEapAuthenticationProperty(kEapPasswordProperty));
  EXPECT_TRUE(EapCredentials::IsEapAuthenticationProperty(kEapPinProperty));
  EXPECT_TRUE(EapCredentials::IsEapAuthenticationProperty(
      kEapUseLoginPasswordProperty));

  // It's easier to test that this function returns TRUE in every situation
  // that it should, than to test all the cases it should return FALSE in.
  EXPECT_FALSE(EapCredentials::IsEapAuthenticationProperty(kEapCaCertProperty));
  EXPECT_FALSE(
      EapCredentials::IsEapAuthenticationProperty(kEapCaCertIdProperty));
  EXPECT_FALSE(
      EapCredentials::IsEapAuthenticationProperty(kEapCaCertPemProperty));
  EXPECT_FALSE(EapCredentials::IsEapAuthenticationProperty(kEapMethodProperty));
  EXPECT_FALSE(
      EapCredentials::IsEapAuthenticationProperty(kEapPhase2AuthProperty));
  EXPECT_FALSE(EapCredentials::IsEapAuthenticationProperty(
      kEapRemoteCertificationProperty));
  EXPECT_FALSE(
      EapCredentials::IsEapAuthenticationProperty(kEapSubjectMatchProperty));
  EXPECT_FALSE(EapCredentials::IsEapAuthenticationProperty(
      kEapUseProactiveKeyCachingProperty));
  EXPECT_FALSE(
      EapCredentials::IsEapAuthenticationProperty(kEapUseSystemCasProperty));
}

TEST_F(EapCredentialsTest, LoadAndSave) {
  FakeStore store;
  const std::string kId("storage-id");
  const std::string kIdentity("Purple Onion");
  store.SetCryptedString(kId, /*deprecated_key=*/"",
                         EapCredentials::kStorageCredentialEapIdentity,
                         kIdentity);
  const std::string kManagement("Shave and a Haircut");
  store.SetString(kId, EapCredentials::kStorageEapKeyManagement, kManagement);
  const std::string kPassword("Two Bits");
  store.SetCryptedString(kId, /*deprecated_key=*/"",
                         EapCredentials::kStorageCredentialEapPassword,
                         kPassword);

  eap_.Load(&store, kId);
  Mock::VerifyAndClearExpectations(&store);

  EXPECT_EQ(kIdentity, eap_.identity());
  EXPECT_EQ(kManagement, eap_.key_management());
  EXPECT_EQ(kPassword, GetPassword());

  // Save with save_credentials=false.
  store.DeleteGroup(kId);
  eap_.Save(&store, kId, /*save_credentials=*/false);
  std::string management;
  EXPECT_TRUE(store.GetString(kId, EapCredentials::kStorageEapKeyManagement,
                              &management));
  EXPECT_EQ(management, kManagement);
  // Authentication properties are deleted from the store if they are empty,
  // so we expect the fields that we haven't set to be deleted.
  EXPECT_FALSE(store.GetString(
      kId, EapCredentials::kStorageCredentialEapIdentity, nullptr));
  EXPECT_FALSE(store.GetString(
      kId, EapCredentials::kStorageCredentialEapPassword, nullptr));

  // Save with save_credentials=true.
  store.DeleteGroup(kId);
  eap_.Save(&store, kId, /*save_credentials=*/true);
  EXPECT_TRUE(store.GetString(kId, EapCredentials::kStorageEapKeyManagement,
                              &management));
  EXPECT_EQ(management, kManagement);
  std::string identity, password;
  EXPECT_TRUE(store.GetString(
      kId, EapCredentials::kStorageCredentialEapIdentity, &identity));
  EXPECT_EQ(identity, kIdentity);
  EXPECT_TRUE(store.GetString(
      kId, EapCredentials::kStorageCredentialEapPassword, &password));
  EXPECT_EQ(password, kPassword);
}

TEST_F(EapCredentialsTest, Load) {
  const std::vector<std::string> kCaCertPem{"first line", "second line"};
  const std::string kMethod("TTLS");
  const std::string kInnerMethod("auth=AnotherMethod");
  const std::string kIdentity("Red Fruit");
  const std::string kPassword("One Time Password");
  const std::string kSubjectNameMatch("domain1.com");
  const std::vector<std::string> kAlternativeNameMatchList{"domain2.com",
                                                           "domain3.com"};
  const std::vector<std::string> kDomainSuffixMatchList{"domain4.com",
                                                        "domain5.com"};

  KeyValueStore store;
  store.Set(kEapCaCertPemProperty, kCaCertPem);
  store.Set(kEapMethodProperty, kMethod);
  store.Set(kEapPhase2AuthProperty, kInnerMethod);
  store.Set(kEapIdentityProperty, kIdentity);
  store.Set(kEapPasswordProperty, kPassword);
  store.Set(kEapSubjectMatchProperty, kSubjectNameMatch);
  store.Set(kEapSubjectAlternativeNameMatchProperty, kAlternativeNameMatchList);
  store.Set(kEapDomainSuffixMatchProperty, kDomainSuffixMatchList);
  eap_.Load(store);

  EXPECT_EQ(kMethod, eap_.method());
  EXPECT_EQ(kInnerMethod, eap_.inner_method());
  EXPECT_EQ(kIdentity, eap_.identity());
  EXPECT_EQ(kPassword, eap_.password_);
  EXPECT_EQ(kCaCertPem, eap_.ca_cert_pem());
  EXPECT_EQ(kSubjectNameMatch, eap_.subject_match());
  EXPECT_EQ(kAlternativeNameMatchList,
            eap_.subject_alternative_name_match_list());
  EXPECT_EQ(kDomainSuffixMatchList, eap_.domain_suffix_match_list());
  // Other fields keep their default value.
  EXPECT_TRUE(eap_.anonymous_identity_.empty());
  EXPECT_TRUE(eap_.cert_id_.empty());
  EXPECT_TRUE(eap_.key_id_.empty());
  EXPECT_TRUE(eap_.pin_.empty());
  EXPECT_TRUE(eap_.ca_cert_id_.empty());
  EXPECT_TRUE(eap_.tls_version_max_.empty());
  EXPECT_TRUE(eap_.use_system_cas());
  EXPECT_FALSE(eap_.use_proactive_key_caching_);
  EXPECT_FALSE(eap_.use_login_password_);

  EapCredentials eap2;
  eap2.Load(eap_);
  EXPECT_EQ(eap_.method(), eap2.method());
  EXPECT_EQ(eap_.inner_method(), eap2.inner_method());
  EXPECT_EQ(eap_.identity(), eap2.identity());
  EXPECT_EQ(eap_.password_, eap2.password_);
  EXPECT_EQ(eap_.ca_cert_pem(), eap2.ca_cert_pem());
  EXPECT_EQ(eap_.subject_match(), eap2.subject_match());
  EXPECT_EQ(eap_.subject_alternative_name_match_list(),
            eap2.subject_alternative_name_match_list());
  EXPECT_EQ(eap_.domain_suffix_match_list(), eap2.domain_suffix_match_list());
  EXPECT_EQ(eap_.anonymous_identity_, eap2.anonymous_identity_);
  EXPECT_EQ(eap_.cert_id_, eap2.cert_id_);
  EXPECT_EQ(eap_.key_id_, eap2.key_id_);
  EXPECT_EQ(eap_.pin_, eap2.pin_);
  EXPECT_EQ(eap_.ca_cert_id_, eap2.ca_cert_id_);
  EXPECT_EQ(eap_.tls_version_max_, eap2.tls_version_max_);
  EXPECT_EQ(eap_.use_system_cas(), eap2.use_system_cas());
  EXPECT_EQ(eap_.use_proactive_key_caching_, eap2.use_proactive_key_caching_);
  EXPECT_EQ(eap_.use_login_password_, eap2.use_login_password_);
}

TEST_F(EapCredentialsTest, OutputConnectionMetrics) {
  Error unused_error;
  SetEap(kEapMethodPEAP);
  SetInnerEap(kEapPhase2AuthPEAPMSCHAPV2);

  MockMetrics metrics;
  EXPECT_CALL(metrics, SendEnumToUMA("Network.Shill.Wifi.EapOuterProtocol",
                                     Metrics::kEapOuterProtocolPeap,
                                     Metrics::kEapOuterProtocolMax));
  EXPECT_CALL(metrics, SendEnumToUMA("Network.Shill.Wifi.EapInnerProtocol",
                                     Metrics::kEapInnerProtocolPeapMschapv2,
                                     Metrics::kEapInnerProtocolMax));
  eap_.OutputConnectionMetrics(&metrics, Technology::kWifi);
}

TEST_F(EapCredentialsTest, PopulateSupplicantProperties) {
  SetIdentity("testidentity");
  SetPin("xxxx");
  PopulateSupplicantProperties();
  // Test that only non-empty 802.1x properties are populated.
  EXPECT_TRUE(params_.Contains<std::string>(
      WPASupplicant::kNetworkPropertyEapIdentity));
  EXPECT_FALSE(
      params_.Contains<std::string>(WPASupplicant::kNetworkPropertyEapKeyId));
  EXPECT_FALSE(
      params_.Contains<std::string>(WPASupplicant::kNetworkPropertyEapCaCert));

  // Test that CA path is set by default.
  EXPECT_TRUE(
      params_.Contains<std::string>(WPASupplicant::kNetworkPropertyCaPath));

  // Test that hardware-backed security arguments are not set, since
  // neither key-id nor cert-id were set.
  EXPECT_FALSE(
      params_.Contains<std::string>(WPASupplicant::kNetworkPropertyEapPin));
  EXPECT_FALSE(
      params_.Contains<uint32_t>(WPASupplicant::kNetworkPropertyEngine));
  EXPECT_FALSE(
      params_.Contains<std::string>(WPASupplicant::kNetworkPropertyEngineId));

  // Test EAP version translation.  The "phase1" supplicant parameter is
  // normally empty, but it will contain a "tls_disable" flag if this
  // service requests an old TLS version.
  EXPECT_FALSE(params_.Contains<std::string>(
      WPASupplicant::kNetworkPropertyEapOuterEap));

  SetTLSVersionMax("1.2");
  PopulateSupplicantProperties();
  EXPECT_FALSE(params_.Contains<std::string>(
      WPASupplicant::kNetworkPropertyEapOuterEap));

  SetTLSVersionMax("1.0");
  PopulateSupplicantProperties();
  EXPECT_TRUE(params_.Contains<std::string>(
      WPASupplicant::kNetworkPropertyEapOuterEap));
  std::string phase1 =
      params_.Get<std::string>(WPASupplicant::kNetworkPropertyEapOuterEap);
  EXPECT_EQ(std::string::npos, phase1.find("disable_tlsv1_0=1"));
  EXPECT_NE(std::string::npos, phase1.find("disable_tlsv1_1=1"));
  EXPECT_NE(std::string::npos, phase1.find("disable_tlsv1_2=1"));

  SetDomainSuffixMatch({"domain1.com", "domain2.com"});
  PopulateSupplicantProperties();
  std::string domain_suffix_match_list = params_.Get<std::string>(
      WPASupplicant::kNetworkPropertyEapDomainSuffixMatch);
  EXPECT_EQ("domain1.com;domain2.com", domain_suffix_match_list);
}

// Test that invalid domains in EAP.DomainSuffixMatch are filtered out.
TEST_F(EapCredentialsTest, DomainSuffixMatch) {
  SetDomainSuffixMatch(
      {"domain1.com", "domain2-.com", "domain3", "domain4.com"});
  PopulateSupplicantProperties();
  std::string domain_suffix_match_list = params_.Get<std::string>(
      WPASupplicant::kNetworkPropertyEapDomainSuffixMatch);
  EXPECT_EQ("domain1.com;domain4.com", domain_suffix_match_list);

  // Expect that if shill doesn't set the value for domain_suffix_match, the
  // parameter is not set to the wpa_supplicant.
  params_.Clear();
  SetDomainSuffixMatch({""});
  PopulateSupplicantProperties();
  EXPECT_FALSE(params_.Contains<std::string>(
      WPASupplicant::kNetworkPropertyEapDomainSuffixMatch));
}

TEST_F(EapCredentialsTest, ValidDomainSuffixMatch) {
  EXPECT_TRUE(EapCredentials::ValidDomainSuffixMatch("com"));
  EXPECT_TRUE(EapCredentials::ValidDomainSuffixMatch("example.com"));
  EXPECT_TRUE(EapCredentials::ValidDomainSuffixMatch("a.b.c.example.com"));
  EXPECT_TRUE(EapCredentials::ValidDomainSuffixMatch("sub-domain.example.com"));
  EXPECT_TRUE(
      EapCredentials::ValidDomainSuffixMatch("1subdomain2.examp7e.com"));
  // False because length = 0.
  EXPECT_FALSE(EapCredentials::ValidDomainSuffixMatch(""));
  // False because starts with hyphen.
  EXPECT_FALSE(EapCredentials::ValidDomainSuffixMatch("-example.com"));
  // False because ends with hyphen.
  EXPECT_FALSE(EapCredentials::ValidDomainSuffixMatch("example-.com"));
  // False because unsupported character.
  EXPECT_FALSE(EapCredentials::ValidDomainSuffixMatch("exam;ple.com"));
  // False because of numerical character in top level domain.
  EXPECT_FALSE(EapCredentials::ValidDomainSuffixMatch("example.com2"));
  // Invalid because label size > 63 characters.
  const std::string invalid_label(64, 'a');
  EXPECT_FALSE(EapCredentials::ValidDomainSuffixMatch(invalid_label + ".com"));
  // Invalid because label size is 0.
  EXPECT_FALSE(EapCredentials::ValidDomainSuffixMatch("..com2"));
}

TEST_F(EapCredentialsTest, PopulateSupplicantPropertiesNoSystemCAs) {
  SetIdentity("testidentity");
  SetUseSystemCAs(false);
  PopulateSupplicantProperties();
  // Test that CA path is not set if use_system_cas is explicitly false.
  EXPECT_FALSE(
      params_.Contains<std::string>(WPASupplicant::kNetworkPropertyCaPath));
}

TEST_F(EapCredentialsTest,
       PopulateSupplicantPropertiesProactiveKeyCachingDisabledByDefault) {
  SetIdentity("testidentity");
  PopulateSupplicantProperties();

  ASSERT_TRUE(params_.Contains<uint32_t>(
      WPASupplicant::kNetworkPropertyEapProactiveKeyCaching));

  const uint32_t kProactiveKeyCachingDisabled(0);

  EXPECT_EQ(kProactiveKeyCachingDisabled,
            params_.Get<uint32_t>(
                WPASupplicant::kNetworkPropertyEapProactiveKeyCaching));
}

TEST_F(EapCredentialsTest,
       PopulateSupplicantPropertiesEnableProactiveKeyCaching) {
  SetIdentity("testidentity");
  SetUseProactiveKeyCaching(true);
  PopulateSupplicantProperties();

  ASSERT_TRUE(params_.Contains<uint32_t>(
      WPASupplicant::kNetworkPropertyEapProactiveKeyCaching));

  const uint32_t kProactiveKeyCachingEnabled(1);

  EXPECT_EQ(kProactiveKeyCachingEnabled,
            params_.Get<uint32_t>(
                WPASupplicant::kNetworkPropertyEapProactiveKeyCaching));
}

TEST_F(EapCredentialsTest,
       PopulateSupplicantPropertiesDisableProactiveKeyCaching) {
  SetIdentity("testidentity");
  SetUseProactiveKeyCaching(false);
  PopulateSupplicantProperties();

  ASSERT_TRUE(params_.Contains<uint32_t>(
      WPASupplicant::kNetworkPropertyEapProactiveKeyCaching));

  const uint32_t kProactiveKeyCachingDisabled(0);

  EXPECT_EQ(kProactiveKeyCachingDisabled,
            params_.Get<uint32_t>(
                WPASupplicant::kNetworkPropertyEapProactiveKeyCaching));
}

TEST_F(EapCredentialsTest, PopulateSupplicantPropertiesUsingHardwareAuth) {
  SetIdentity("testidentity");
  SetKeyId("key_id");
  SetPin("xxxx");
  SetEap("PEAP");
  PopulateSupplicantProperties();
  // Test that EAP engine parameters are not set if the authentication type
  // is not one that accepts a client certificate.
  EXPECT_FALSE(
      params_.Contains<std::string>(WPASupplicant::kNetworkPropertyEapPin));
  EXPECT_FALSE(
      params_.Contains<std::string>(WPASupplicant::kNetworkPropertyEapKeyId));
  EXPECT_FALSE(
      params_.Contains<uint32_t>(WPASupplicant::kNetworkPropertyEngine));
  EXPECT_FALSE(
      params_.Contains<std::string>(WPASupplicant::kNetworkPropertyEngineId));

  // Test that EAP engine parameters are set if key_id is set and the
  // authentication type accepts a client certificate.
  params_.Clear();
  SetEap("TLS");
  PopulateSupplicantProperties();
  EXPECT_TRUE(
      params_.Contains<std::string>(WPASupplicant::kNetworkPropertyEapPin));
  EXPECT_TRUE(
      params_.Contains<std::string>(WPASupplicant::kNetworkPropertyEapKeyId));
  EXPECT_TRUE(
      params_.Contains<uint32_t>(WPASupplicant::kNetworkPropertyEngine));
  EXPECT_TRUE(
      params_.Contains<std::string>(WPASupplicant::kNetworkPropertyEngineId));

  // An empty EAP parameter should be considered to be possibly "TLS".
  params_.Clear();
  SetEap("");
  PopulateSupplicantProperties();
  EXPECT_TRUE(
      params_.Contains<std::string>(WPASupplicant::kNetworkPropertyEapPin));
  EXPECT_TRUE(
      params_.Contains<std::string>(WPASupplicant::kNetworkPropertyEapKeyId));
  EXPECT_TRUE(
      params_.Contains<uint32_t>(WPASupplicant::kNetworkPropertyEngine));
  EXPECT_TRUE(
      params_.Contains<std::string>(WPASupplicant::kNetworkPropertyEngineId));

  // Test that EAP engine parameters are set if ca_cert_id is set even if the
  // authentication type does not accept a client certificate.  However,
  // the client key id should not be provided.
  params_.Clear();
  SetEap("PEAP");
  SetCACertId("certid");
  PopulateSupplicantProperties();
  EXPECT_TRUE(
      params_.Contains<std::string>(WPASupplicant::kNetworkPropertyEapPin));
  EXPECT_FALSE(
      params_.Contains<std::string>(WPASupplicant::kNetworkPropertyEapKeyId));
  EXPECT_TRUE(
      params_.Contains<uint32_t>(WPASupplicant::kNetworkPropertyEngine));
  EXPECT_TRUE(
      params_.Contains<std::string>(WPASupplicant::kNetworkPropertyEngineId));
  EXPECT_TRUE(params_.Contains<std::string>(
      WPASupplicant::kNetworkPropertyEapCaCertId));
}

TEST_F(EapCredentialsTest, PopulateSupplicantPropertiesPEM) {
  const std::vector<std::string> kPemCert{"-pem-certificate-here-"};
  SetCACertPEM(kPemCert);
  const std::string kPEMCertfile("/tmp/pem-cert");
  base::FilePath pem_cert(kPEMCertfile);
  EXPECT_CALL(certificate_file_, CreatePEMFromStrings(kPemCert))
      .WillOnce(Return(pem_cert));

  PopulateSupplicantProperties();
  EXPECT_TRUE(
      params_.Contains<std::string>(WPASupplicant::kNetworkPropertyEapCaCert));
  if (params_.Contains<std::string>(WPASupplicant::kNetworkPropertyEapCaCert)) {
    EXPECT_EQ(kPEMCertfile, params_.Get<std::string>(
                                WPASupplicant::kNetworkPropertyEapCaCert));
  }
}

TEST_F(EapCredentialsTest, Reset) {
  EXPECT_TRUE(IsReset());
  EXPECT_TRUE(GetKeyManagement().empty());
  SetAnonymousIdentity("foo");
  SetCACertId("foo");
  SetCACertPEM(std::vector<std::string>{"foo"});
  SetCertId("foo");
  SetEap("foo");
  SetIdentity("foo");
  SetInnerEap("foo");
  SetKeyId("foo");
  SetPassword("foo");
  SetPin("foo");
  SetUseSystemCAs(false);
  SetUseProactiveKeyCaching(true);
  SetUseLoginPassword(false);
  SetSubjectAlternativeNameMatch(std::vector<std::string>{"foo"});
  SetDomainSuffixMatch(std::vector<std::string>{"foo"});
  eap_.SetKeyManagement("foo", nullptr);
  EXPECT_FALSE(IsReset());
  EXPECT_FALSE(GetKeyManagement().empty());
  eap_.Reset();
  EXPECT_TRUE(IsReset());
  EXPECT_FALSE(GetKeyManagement().empty());
}

TEST_F(EapCredentialsTest, SetKeyManagement) {
  const std::string kKeyManagement0("foo");
  eap_.SetKeyManagement(kKeyManagement0, nullptr);
  EXPECT_EQ(kKeyManagement0, GetKeyManagement());

  const std::string kKeyManagement1("bar");
  eap_.SetKeyManagement(kKeyManagement1, nullptr);
  EXPECT_EQ(kKeyManagement1, GetKeyManagement());

  // We should not be able to set the key management to an empty string.
  eap_.SetKeyManagement("", nullptr);
  EXPECT_EQ(kKeyManagement1, GetKeyManagement());
}

// Custom property setters should return false, and make no changes, if
// the new value is the same as the old value.
TEST_F(EapCredentialsTest, CustomSetterNoopChange) {
  // SetEapKeyManagement
  {
    const std::string kKeyManagement("foo");
    Error error;
    // Set to known value.
    EXPECT_TRUE(eap_.SetKeyManagement(kKeyManagement, &error));
    EXPECT_TRUE(error.IsSuccess());
    // Set to same value.
    EXPECT_FALSE(eap_.SetKeyManagement(kKeyManagement, &error));
    EXPECT_TRUE(error.IsSuccess());
  }

  // SetEapPassword
  {
    const std::string kPassword("foo");
    Error error;
    // Set to known value.
    EXPECT_TRUE(SetEapPassword(kPassword, &error));
    EXPECT_TRUE(error.IsSuccess());
    // Set to same value.
    EXPECT_FALSE(SetEapPassword(kPassword, &error));
    EXPECT_TRUE(error.IsSuccess());
  }
}

TEST_F(EapCredentialsTest, GetPassword) {
  const std::string kPassword("foo");
  Error error;
  EXPECT_TRUE(SetEapPassword(kPassword, &error));
  EXPECT_TRUE(error.IsSuccess());
  std::string set_password = eap_.GetEapPassword(&error);
  EXPECT_TRUE(error.IsSuccess());
  EXPECT_EQ(kPassword, set_password);
}

TEST_F(EapCredentialsTest, GetEmptyPassword) {
  Error error;
  std::string set_password = eap_.GetEapPassword(&error);
  EXPECT_FALSE(error.IsSuccess());
  EXPECT_TRUE(set_password.empty());
}

TEST_F(EapCredentialsTest, GetPasswordEmptyForLoginPassword) {
  SetUseLoginPassword(true);
  Error error;
  std::string password = eap_.GetEapPassword(&error);
  EXPECT_TRUE(password.empty());
  EXPECT_FALSE(error.IsSuccess());
  EXPECT_TRUE(password.empty());
}

TEST_F(EapCredentialsTest, TestUseLoginPassword) {
  const std::string kPasswordStr("thepassword");
  SaveLoginPassword(kPasswordStr);

  SetUseLoginPassword(true);
  PopulateSupplicantProperties();

  EXPECT_TRUE(params_.Contains<std::string>(
      WPASupplicant::kNetworkPropertyEapCaPassword));
  std::string used_password =
      params_.Get<std::string>(WPASupplicant::kNetworkPropertyEapCaPassword);
  EXPECT_EQ(used_password, kPasswordStr);
}

TEST_F(EapCredentialsTest, TestDontUseLoginPassword) {
  const std::string kPasswordStr("thepassword");
  SaveLoginPassword(kPasswordStr);

  SetUseLoginPassword(false);
  PopulateSupplicantProperties();

  EXPECT_FALSE(params_.Contains<std::string>(
      WPASupplicant::kNetworkPropertyEapCaPassword));
}

TEST_F(EapCredentialsTest, TestSubjectAlternativeNameMatchTranslation) {
  const std::vector<std::string> subject_alternative_name_match_list(
      {"{\"Type\":\"EMAIL\",\"Value\":\"my_email_1\"}",
       "{\"Type\":\"EMAIL\",\"Value\":\"my_email_2\"}",
       "{\"Type\":\"EMAIL\",\"Value\":\"my;email\"}",
       "{\"Type\":\"DNS\",\"Value\":\"my_dns\"}",
       "{\"Type\":\"URI\",\"Value\":\"my_uri\"}"});
  std::string expected_translated =
      "EMAIL:my_email_1;EMAIL:my_email_2;EMAIL:my;email;DNS:my_dns;URI:my_uri";
  base::Optional<std::string> altsubject_match =
      EapCredentials::TranslateSubjectAlternativeNameMatch(
          subject_alternative_name_match_list);
  EXPECT_TRUE(altsubject_match.has_value());
  EXPECT_EQ(altsubject_match.value(), expected_translated);
}

TEST_F(EapCredentialsTest, TestSubjectAlternativeNameMatchTranslationFailure) {
  const std::vector<std::string> subject_alternative_name_match_list(
      {"{\"TYPE\":\"EMAIL\",\"Value\":\"my;email\"}"});
  base::Optional<std::string> altsubject_match =
      EapCredentials::TranslateSubjectAlternativeNameMatch(
          subject_alternative_name_match_list);
  EXPECT_FALSE(altsubject_match.has_value());
}

TEST_F(EapCredentialsTest, TestEapInnerAuthMschapv2NoRetryFlag) {
  // If no EAP inner auth is set, no additional  mschapv2_retry flag is added.
  SetInnerEap("");
  PopulateSupplicantProperties();
  EXPECT_FALSE(params_.Contains<std::string>(
      WPASupplicant::kNetworkPropertyEapInnerEap));

  // If an EAP inner auth different than MSCHPAV2 is set, also expect no change.
  SetInnerEap("auth=MD5");
  PopulateSupplicantProperties();
  EXPECT_TRUE(params_.Contains<std::string>(
      WPASupplicant::kNetworkPropertyEapInnerEap));
  {
    const std::string inner_eap =
        params_.Get<std::string>(WPASupplicant::kNetworkPropertyEapInnerEap);
    EXPECT_EQ(inner_eap, "auth=MD5");
  }

  // If EAP inner auth is set to MSCHAPV2, the flag should be added.
  SetInnerEap("auth=MSCHAPV2");
  PopulateSupplicantProperties();
  EXPECT_TRUE(params_.Contains<std::string>(
      WPASupplicant::kNetworkPropertyEapInnerEap));
  {
    const std::string inner_eap =
        params_.Get<std::string>(WPASupplicant::kNetworkPropertyEapInnerEap);
    EXPECT_EQ(inner_eap, "auth=MSCHAPV2 mschapv2_retry=0");
  }
}

}  // namespace shill
