summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorstevenjb@chromium.org <stevenjb@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2014-05-16 21:48:35 +0000
committerstevenjb@chromium.org <stevenjb@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2014-05-16 21:48:35 +0000
commit164da42873b70ce025199d15a870ca4650534ac5 (patch)
treea05626c399ecadae950b388e06972a7777d189c7
parentb8787eab8e2ad5ecf3e2a8c0db10c6305ce9e448 (diff)
downloadchromium_src-164da42873b70ce025199d15a870ca4650534ac5.zip
chromium_src-164da42873b70ce025199d15a870ca4650534ac5.tar.gz
chromium_src-164da42873b70ce025199d15a870ca4650534ac5.tar.bz2
Use GUID instead of ServicePath in networkingPrivate API
Currently we pass the service path of networks as the "GUID" in the networkingPrivate implementation on Chrome OS. We should be using the actual GUID (if one exists) or create a GUID if one does not. Note: This change should not break any existing usage since the GUID value should be transparant to the implementation. (This will have the positive side effect of making the GUID consistent across sessions). BUG=284827 For fake_wifi_service.cc: R=asargent@chromium.org, pneubeck@chromium.org TBR=mef@chromium.org Review URL: https://codereview.chromium.org/275543005 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@271106 0039d316-1c4b-4281-b951-d872f2087c98
-rw-r--r--chrome/browser/chromeos/ui_proxy_config_service.cc12
-rw-r--r--chrome/browser/extensions/api/networking_private/networking_private_api_chromeos.cc99
-rw-r--r--chrome/browser/extensions/api/networking_private/networking_private_api_nonchromeos.cc5
-rw-r--r--chrome/browser/extensions/api/networking_private/networking_private_apitest.cc39
-rw-r--r--chrome/browser/extensions/api/networking_private/networking_private_service_client.cc4
-rw-r--r--chrome/browser/ui/webui/options/chromeos/internet_options_handler.cc6
-rw-r--r--chrome/common/extensions/api/networking_private.json14
-rw-r--r--chrome/test/data/extensions/api_test/networking/test.js30
-rw-r--r--chromeos/network/client_cert_resolver.cc3
-rw-r--r--chromeos/network/favorite_state.cc23
-rw-r--r--chromeos/network/favorite_state.h20
-rw-r--r--chromeos/network/managed_network_configuration_handler_impl.cc11
-rw-r--r--chromeos/network/managed_state.h1
-rw-r--r--chromeos/network/network_state.cc4
-rw-r--r--chromeos/network/network_state.h3
-rw-r--r--chromeos/network/network_state_handler.cc89
-rw-r--r--chromeos/network/network_state_handler.h38
-rw-r--r--chromeos/network/network_state_handler_unittest.cc129
-rw-r--r--chromeos/network/network_util.cc27
-rw-r--r--chromeos/network/network_util.h13
-rw-r--r--chromeos/network/shill_property_handler.cc25
-rw-r--r--components/wifi/fake_wifi_service.cc40
22 files changed, 485 insertions, 150 deletions
diff --git a/chrome/browser/chromeos/ui_proxy_config_service.cc b/chrome/browser/chromeos/ui_proxy_config_service.cc
index 66195090..945f4e4 100644
--- a/chrome/browser/chromeos/ui_proxy_config_service.cc
+++ b/chrome/browser/chromeos/ui_proxy_config_service.cc
@@ -81,8 +81,10 @@ void UIProxyConfigService::SetCurrentNetwork(
void UIProxyConfigService::UpdateFromPrefs() {
const FavoriteState* network = NULL;
if (!current_ui_network_.empty()) {
- network = NetworkHandler::Get()->network_state_handler()->GetFavoriteState(
- current_ui_network_);
+ network = NetworkHandler::Get()
+ ->network_state_handler()
+ ->GetFavoriteStateFromServicePath(current_ui_network_,
+ true /* configured_only */);
LOG_IF(ERROR, !network) << "Couldn't find FavoriteState for network "
<< current_ui_network_;
}
@@ -109,8 +111,10 @@ void UIProxyConfigService::SetProxyConfig(const UIProxyConfig& config) {
return;
const FavoriteState* network =
- NetworkHandler::Get()->network_state_handler()->GetFavoriteState(
- current_ui_network_);
+ NetworkHandler::Get()
+ ->network_state_handler()
+ ->GetFavoriteStateFromServicePath(current_ui_network_,
+ true /* configured_only */);
if (!network) {
LOG(ERROR) << "Couldn't find FavoriteState for network "
<< current_ui_network_;
diff --git a/chrome/browser/extensions/api/networking_private/networking_private_api_chromeos.cc b/chrome/browser/extensions/api/networking_private/networking_private_api_chromeos.cc
index 6275bea..8da9206 100644
--- a/chrome/browser/extensions/api/networking_private/networking_private_api_chromeos.cc
+++ b/chrome/browser/extensions/api/networking_private/networking_private_api_chromeos.cc
@@ -15,11 +15,13 @@
#include "chrome/common/extensions/api/networking_private.h"
#include "chromeos/dbus/dbus_thread_manager.h"
#include "chromeos/dbus/shill_manager_client.h"
+#include "chromeos/network/favorite_state.h"
#include "chromeos/network/managed_network_configuration_handler.h"
#include "chromeos/network/network_connection_handler.h"
#include "chromeos/network/network_device_handler.h"
#include "chromeos/network/network_state.h"
#include "chromeos/network/network_state_handler.h"
+#include "chromeos/network/network_util.h"
#include "chromeos/network/onc/onc_signature.h"
#include "chromeos/network/onc/onc_translator.h"
#include "chromeos/network/onc/onc_utils.h"
@@ -30,6 +32,7 @@
namespace api = extensions::api::networking_private;
using chromeos::DBusThreadManager;
+using chromeos::FavoriteState;
using chromeos::ManagedNetworkConfigurationHandler;
using chromeos::NetworkHandler;
using chromeos::NetworkPortalDetector;
@@ -65,6 +68,20 @@ std::string GetUserIdHash(Profile* profile) {
profile_helper()->GetUserIdHashFromProfile(profile);
}
+bool GetServicePathFromGuid(const std::string& guid,
+ std::string* service_path,
+ std::string* error) {
+ const FavoriteState* network =
+ NetworkHandler::Get()->network_state_handler()->GetFavoriteStateFromGuid(
+ guid);
+ if (!network) {
+ *error = "Error.InvalidNetworkGuid";
+ return false;
+ }
+ *service_path = network->path();
+ return true;
+}
+
} // namespace
////////////////////////////////////////////////////////////////////////////////
@@ -78,9 +95,12 @@ bool NetworkingPrivateGetPropertiesFunction::RunAsync() {
scoped_ptr<api::GetProperties::Params> params =
api::GetProperties::Params::Create(*args_);
EXTENSION_FUNCTION_VALIDATE(params);
+ std::string service_path;
+ if (!GetServicePathFromGuid(params->network_guid, &service_path, &error_))
+ return false;
NetworkHandler::Get()->managed_network_configuration_handler()->GetProperties(
- params->network_guid, // service path
+ service_path,
base::Bind(&NetworkingPrivateGetPropertiesFunction::GetPropertiesSuccess,
this),
base::Bind(&NetworkingPrivateGetPropertiesFunction::GetPropertiesFailed,
@@ -91,10 +111,7 @@ bool NetworkingPrivateGetPropertiesFunction::RunAsync() {
void NetworkingPrivateGetPropertiesFunction::GetPropertiesSuccess(
const std::string& service_path,
const base::DictionaryValue& dictionary) {
- base::DictionaryValue* network_properties = dictionary.DeepCopy();
- network_properties->SetStringWithoutPathExpansion(onc::network_config::kGUID,
- service_path);
- SetResult(network_properties);
+ SetResult(dictionary.DeepCopy());
SendResponse(true);
}
@@ -116,13 +133,16 @@ bool NetworkingPrivateGetManagedPropertiesFunction::RunAsync() {
scoped_ptr<api::GetManagedProperties::Params> params =
api::GetManagedProperties::Params::Create(*args_);
EXTENSION_FUNCTION_VALIDATE(params);
+ std::string service_path;
+ if (!GetServicePathFromGuid(params->network_guid, &service_path, &error_))
+ return false;
std::string user_id_hash;
GetUserIdHash(GetProfile());
NetworkHandler::Get()->managed_network_configuration_handler()->
GetManagedProperties(
user_id_hash,
- params->network_guid, // service path
+ service_path,
base::Bind(&NetworkingPrivateGetManagedPropertiesFunction::Success,
this),
base::Bind(&NetworkingPrivateGetManagedPropertiesFunction::Failure,
@@ -133,10 +153,7 @@ bool NetworkingPrivateGetManagedPropertiesFunction::RunAsync() {
void NetworkingPrivateGetManagedPropertiesFunction::Success(
const std::string& service_path,
const base::DictionaryValue& dictionary) {
- base::DictionaryValue* network_properties = dictionary.DeepCopy();
- network_properties->SetStringWithoutPathExpansion(onc::network_config::kGUID,
- service_path);
- SetResult(network_properties);
+ SetResult(dictionary.DeepCopy());
SendResponse(true);
}
@@ -158,13 +175,14 @@ bool NetworkingPrivateGetStateFunction::RunAsync() {
scoped_ptr<api::GetState::Params> params =
api::GetState::Params::Create(*args_);
EXTENSION_FUNCTION_VALIDATE(params);
- // The |network_guid| parameter is storing the service path.
- std::string service_path = params->network_guid;
+ std::string service_path;
+ if (!GetServicePathFromGuid(params->network_guid, &service_path, &error_))
+ return false;
const NetworkState* state = NetworkHandler::Get()->network_state_handler()->
GetNetworkState(service_path);
if (!state) {
- error_ = "Error.InvalidParameter";
+ error_ = "Error.NetworkUnavailable";
return false;
}
@@ -190,12 +208,15 @@ bool NetworkingPrivateSetPropertiesFunction::RunAsync() {
scoped_ptr<api::SetProperties::Params> params =
api::SetProperties::Params::Create(*args_);
EXTENSION_FUNCTION_VALIDATE(params);
+ std::string service_path;
+ if (!GetServicePathFromGuid(params->network_guid, &service_path, &error_))
+ return false;
scoped_ptr<base::DictionaryValue> properties_dict(
params->properties.ToValue());
NetworkHandler::Get()->managed_network_configuration_handler()->SetProperties(
- params->network_guid, // service path
+ service_path,
*properties_dict,
base::Bind(&NetworkingPrivateSetPropertiesFunction::ResultCallback,
this),
@@ -269,30 +290,12 @@ bool NetworkingPrivateGetVisibleNetworksFunction::RunAsync() {
scoped_ptr<api::GetVisibleNetworks::Params> params =
api::GetVisibleNetworks::Params::Create(*args_);
EXTENSION_FUNCTION_VALIDATE(params);
- NetworkTypePattern type = chromeos::onc::NetworkTypePatternFromOncType(
+ NetworkTypePattern pattern = chromeos::onc::NetworkTypePatternFromOncType(
api::GetVisibleNetworks::Params::ToString(params->type));
- NetworkStateHandler::NetworkStateList network_states;
- NetworkHandler::Get()->network_state_handler()->GetNetworkListByType(
- type, &network_states);
-
- base::ListValue* network_properties_list = new base::ListValue;
- for (NetworkStateHandler::NetworkStateList::iterator it =
- network_states.begin();
- it != network_states.end(); ++it) {
- base::DictionaryValue shill_dictionary;
- (*it)->GetStateProperties(&shill_dictionary);
-
- scoped_ptr<base::DictionaryValue> onc_network_part =
- chromeos::onc::TranslateShillServiceToONCPart(
- shill_dictionary, &chromeos::onc::kNetworkWithStateSignature);
- // TODO(stevenjb): Fix this to always use GUID: crbug.com/284827
- onc_network_part->SetStringWithoutPathExpansion(
- onc::network_config::kGUID, (*it)->path());
- network_properties_list->Append(onc_network_part.release());
- }
-
- SetResult(network_properties_list);
+ scoped_ptr<base::ListValue> network_properties_list =
+ chromeos::network_util::TranslateNetworkListToONC(pattern);
+ SetResult(network_properties_list.release());
SendResponse(true);
return true;
}
@@ -433,10 +436,13 @@ bool NetworkingPrivateStartConnectFunction::RunAsync() {
scoped_ptr<api::StartConnect::Params> params =
api::StartConnect::Params::Create(*args_);
EXTENSION_FUNCTION_VALIDATE(params);
+ std::string service_path;
+ if (!GetServicePathFromGuid(params->network_guid, &service_path, &error_))
+ return false;
const bool check_error_state = false;
NetworkHandler::Get()->network_connection_handler()->ConnectToNetwork(
- params->network_guid, // service path
+ service_path,
base::Bind(
&NetworkingPrivateStartConnectFunction::ConnectionStartSuccess,
this),
@@ -469,9 +475,12 @@ bool NetworkingPrivateStartDisconnectFunction::RunAsync() {
scoped_ptr<api::StartDisconnect::Params> params =
api::StartDisconnect::Params::Create(*args_);
EXTENSION_FUNCTION_VALIDATE(params);
+ std::string service_path;
+ if (!GetServicePathFromGuid(params->network_guid, &service_path, &error_))
+ return false;
NetworkHandler::Get()->network_connection_handler()->DisconnectNetwork(
- params->network_guid, // service path
+ service_path,
base::Bind(
&NetworkingPrivateStartDisconnectFunction::DisconnectionStartSuccess,
this),
@@ -530,15 +539,18 @@ bool NetworkingPrivateVerifyAndEncryptCredentialsFunction::RunAsync() {
scoped_ptr<api::VerifyAndEncryptCredentials::Params> params =
api::VerifyAndEncryptCredentials::Params::Create(*args_);
EXTENSION_FUNCTION_VALIDATE(params);
- ShillManagerClient* shill_manager_client =
- DBusThreadManager::Get()->GetShillManagerClient();
+ std::string service_path;
+ if (!GetServicePathFromGuid(params->network_guid, &service_path, &error_))
+ return false;
ShillManagerClient::VerificationProperties verification_properties =
ConvertVerificationProperties(params->properties);
+ ShillManagerClient* shill_manager_client =
+ DBusThreadManager::Get()->GetShillManagerClient();
shill_manager_client->VerifyAndEncryptCredentials(
verification_properties,
- params->guid,
+ service_path,
base::Bind(
&NetworkingPrivateVerifyAndEncryptCredentialsFunction::ResultCallback,
this),
@@ -688,6 +700,9 @@ bool NetworkingPrivateGetCaptivePortalStatusFunction::RunAsync() {
scoped_ptr<api::GetCaptivePortalStatus::Params> params =
api::GetCaptivePortalStatus::Params::Create(*args_);
EXTENSION_FUNCTION_VALIDATE(params);
+ std::string service_path;
+ if (!GetServicePathFromGuid(params->network_guid, &service_path, &error_))
+ return false;
NetworkPortalDetector* detector = NetworkPortalDetector::Get();
if (!detector) {
@@ -696,7 +711,7 @@ bool NetworkingPrivateGetCaptivePortalStatusFunction::RunAsync() {
}
NetworkPortalDetector::CaptivePortalState state =
- detector->GetCaptivePortalState(params->network_path);
+ detector->GetCaptivePortalState(service_path);
SetResult(new base::StringValue(
NetworkPortalDetector::CaptivePortalStatusString(state.status)));
diff --git a/chrome/browser/extensions/api/networking_private/networking_private_api_nonchromeos.cc b/chrome/browser/extensions/api/networking_private/networking_private_api_nonchromeos.cc
index 64d5dbf..9b4ad43 100644
--- a/chrome/browser/extensions/api/networking_private/networking_private_api_nonchromeos.cc
+++ b/chrome/browser/extensions/api/networking_private/networking_private_api_nonchromeos.cc
@@ -87,10 +87,7 @@ bool NetworkingPrivateGetManagedPropertiesFunction::RunAsync() {
void NetworkingPrivateGetManagedPropertiesFunction::Success(
const std::string& network_guid,
const base::DictionaryValue& dictionary) {
- scoped_ptr<base::DictionaryValue> network_properties(dictionary.DeepCopy());
- network_properties->SetStringWithoutPathExpansion(onc::network_config::kGUID,
- network_guid);
- SetResult(network_properties.release());
+ SetResult(dictionary.DeepCopy());
SendResponse(true);
}
diff --git a/chrome/browser/extensions/api/networking_private/networking_private_apitest.cc b/chrome/browser/extensions/api/networking_private/networking_private_apitest.cc
index 583a980..2c56c59 100644
--- a/chrome/browser/extensions/api/networking_private/networking_private_apitest.cc
+++ b/chrome/browser/extensions/api/networking_private/networking_private_apitest.cc
@@ -199,6 +199,19 @@ class ExtensionNetworkingPrivateApiTest
CHECK(!userhash_.empty());
}
+ void AddService(const std::string& service_path,
+ const std::string& name,
+ const std::string& type,
+ const std::string& state) {
+ const bool add_to_watchlist = true;
+ const bool add_to_visible = true;
+ // Tests need a known GUID, so use 'service_path'.
+ service_test_->AddServiceWithIPConfig(
+ service_path, service_path /* guid */, name,
+ type, state, "" /* ipconfig_path */,
+ add_to_visible, add_to_watchlist);
+ }
+
virtual void SetUpOnMainThread() OVERRIDE {
detector_ = new NetworkPortalDetectorTestImpl();
NetworkPortalDetector::InitializeForTesting(detector_);
@@ -246,11 +259,8 @@ class ExtensionNetworkingPrivateApiTest
kCellularDevicePath, shill::kTypeCellular, "stub_cellular_device1");
// Add Services
- const bool add_to_watchlist = true;
- const bool add_to_visible = true;
- service_test_->AddService("stub_ethernet", "eth0",
- shill::kTypeEthernet, shill::kStateOnline,
- add_to_visible, add_to_watchlist);
+ AddService("stub_ethernet", "eth0",
+ shill::kTypeEthernet, shill::kStateOnline);
service_test_->SetServiceProperty(
"stub_ethernet",
shill::kProfileProperty,
@@ -258,9 +268,7 @@ class ExtensionNetworkingPrivateApiTest
profile_test->AddService(ShillProfileClient::GetSharedProfilePath(),
"stub_ethernet");
- service_test_->AddService("stub_wifi1", "wifi1",
- shill::kTypeWifi, shill::kStateOnline,
- add_to_visible, add_to_watchlist);
+ AddService("stub_wifi1", "wifi1", shill::kTypeWifi, shill::kStateOnline);
service_test_->SetServiceProperty("stub_wifi1",
shill::kSecurityProperty,
base::StringValue(shill::kSecurityWep));
@@ -286,9 +294,7 @@ class ExtensionNetworkingPrivateApiTest
shill::kWifiFrequency,
base::FundamentalValue(2400));
- service_test_->AddService("stub_wifi2", "wifi2_PSK",
- shill::kTypeWifi, shill::kStateIdle,
- add_to_visible, add_to_watchlist);
+ AddService("stub_wifi2", "wifi2_PSK", shill::kTypeWifi, shill::kStateIdle);
service_test_->SetServiceProperty("stub_wifi2",
shill::kGuidProperty,
base::StringValue("stub_wifi2"));
@@ -316,10 +322,7 @@ class ExtensionNetworkingPrivateApiTest
base::StringValue(kUser1ProfilePath));
profile_test->AddService(kUser1ProfilePath, "stub_wifi2");
- service_test_->AddService("stub_vpn1", "vpn1",
- shill::kTypeVPN,
- shill::kStateOnline,
- add_to_visible, add_to_watchlist);
+ AddService("stub_vpn1", "vpn1", shill::kTypeVPN, shill::kStateOnline);
manager_test->SortManagerServices();
@@ -537,10 +540,8 @@ IN_PROC_BROWSER_TEST_P(ExtensionNetworkingPrivateApiTest,
#if defined(OS_CHROMEOS)
IN_PROC_BROWSER_TEST_P(ExtensionNetworkingPrivateApiTest,
GetCaptivePortalStatus) {
- service_test_->AddService("stub_cellular1", "cellular1",
- shill::kTypeCellular, shill::kStateIdle,
- true /* add_to_visible */,
- true /* add_to_watchlist */);
+ AddService("stub_cellular1", "cellular1",
+ shill::kTypeCellular, shill::kStateIdle);
service_test_->SetServiceProperty(
"stub_cellular1",
shill::kNetworkTechnologyProperty,
diff --git a/chrome/browser/extensions/api/networking_private/networking_private_service_client.cc b/chrome/browser/extensions/api/networking_private/networking_private_service_client.cc
index fb65df3..781ff74 100644
--- a/chrome/browser/extensions/api/networking_private/networking_private_service_client.cc
+++ b/chrome/browser/extensions/api/networking_private/networking_private_service_client.cc
@@ -61,7 +61,6 @@ class CryptoVerifyImpl : public NetworkingPrivateServiceClient::CryptoVerify {
using api::networking_private::VerifyAndEncryptCredentials::Params;
scoped_ptr<Params> params = Params::Create(*args);
std::string public_key;
- std::string network_guid;
if (!VerifyDestination(params->properties)) {
callback.Run("", "VerifyError");
@@ -76,11 +75,10 @@ class CryptoVerifyImpl : public NetworkingPrivateServiceClient::CryptoVerify {
scoped_ptr<NetworkingPrivateCredentialsGetter> credentials_getter(
NetworkingPrivateCredentialsGetter::Create());
- network_guid = params->guid;
// Start getting credentials. On Windows |callback| will be called
// asynchronously on a different thread after |credentials_getter|
// is deleted.
- credentials_getter->Start(network_guid, public_key, callback);
+ credentials_getter->Start(params->network_guid, public_key, callback);
}
virtual void VerifyAndEncryptData(scoped_ptr<base::ListValue> args,
diff --git a/chrome/browser/ui/webui/options/chromeos/internet_options_handler.cc b/chrome/browser/ui/webui/options/chromeos/internet_options_handler.cc
index 8d18de4..03740a9 100644
--- a/chrome/browser/ui/webui/options/chromeos/internet_options_handler.cc
+++ b/chrome/browser/ui/webui/options/chromeos/internet_options_handler.cc
@@ -303,8 +303,10 @@ bool HasPolicyForFavorite(const FavoriteState* favorite,
bool HasPolicyForNetwork(const NetworkState* network,
const PrefService* profile_prefs) {
const FavoriteState* favorite =
- NetworkHandler::Get()->network_state_handler()->GetFavoriteState(
- network->path());
+ NetworkHandler::Get()
+ ->network_state_handler()
+ ->GetFavoriteStateFromServicePath(network->path(),
+ true /* configured_only */);
if (!favorite)
return false;
return HasPolicyForFavorite(favorite, profile_prefs);
diff --git a/chrome/common/extensions/api/networking_private.json b/chrome/common/extensions/api/networking_private.json
index b9f66e8..db603cc 100644
--- a/chrome/common/extensions/api/networking_private.json
+++ b/chrome/common/extensions/api/networking_private.json
@@ -173,7 +173,7 @@
"type": "function",
"parameters": [
{
- "name": "guid",
+ "name": "networkGuid",
"type": "string"
}
]
@@ -315,7 +315,7 @@
"description": "Properties of the destination to use in verifying that it is a trusted device."
},
{
- "name": "guid",
+ "name": "networkGuid",
"type": "string",
"description": "A string containing the unique identifier of the network to get credentials for."
},
@@ -410,12 +410,12 @@
},
{
"name": "getCaptivePortalStatus",
- "description": "Returns captive portal status for the network with networkGuid.",
+ "description": "Returns captive portal status for the network matching 'guid'.",
"parameters": [
{
- "name": "networkPath",
+ "name": "networkGuid",
"type": "string",
- "description": "The path of the network to get captive portal status."
+ "description": "The guid of the network to get captive portal status."
},
{
"name": "callback",
@@ -459,10 +459,10 @@
{
"name": "onPortalDetectionCompleted",
"type": "function",
- "description": "Fired when a portal detection for a network completes. Sends a name of the network and corresponding captive portal status.",
+ "description": "Fired when a portal detection for a network completes. Sends the guid of the network and the corresponding captive portal status.",
"parameters": [
{
- "name": "networkPath",
+ "name": "networkGuid",
"type": "string"
},
{
diff --git a/chrome/test/data/extensions/api_test/networking/test.js b/chrome/test/data/extensions/api_test/networking/test.js
index 746a89a..c08d962 100644
--- a/chrome/test/data/extensions/api_test/networking/test.js
+++ b/chrome/test/data/extensions/api_test/networking/test.js
@@ -56,12 +56,12 @@ var privateHelpers = {
done();
};
},
- watchForCaptivePortalState: function(expectedNetworkPath,
+ watchForCaptivePortalState: function(expectedGuid,
expectedState,
done) {
var self = this;
- this.onPortalDetectionCompleted = function(networkPath, state) {
- assertEq(expectedNetworkPath, networkPath);
+ this.onPortalDetectionCompleted = function(guid, state) {
+ assertEq(expectedGuid, guid);
assertEq(expectedState, state);
chrome.networkingPrivate.onPortalDetectionCompleted.removeListener(
self.onPortalDetectionCompleted);
@@ -86,17 +86,17 @@ var availableTests = [
function startConnectNonexistent() {
chrome.networkingPrivate.startConnect(
"nonexistent_path",
- callbackFail("configure-failed"));
+ callbackFail("Error.InvalidNetworkGuid"));
},
function startDisconnectNonexistent() {
chrome.networkingPrivate.startDisconnect(
"nonexistent_path",
- callbackFail("not-found"));
+ callbackFail("Error.InvalidNetworkGuid"));
},
function startGetPropertiesNonexistent() {
chrome.networkingPrivate.getProperties(
"nonexistent_path",
- callbackFail("Error.DBusFailed"));
+ callbackFail("Error.InvalidNetworkGuid"));
},
function createNetwork() {
chrome.networkingPrivate.createNetwork(
@@ -243,7 +243,11 @@ var availableTests = [
"Active": "NotConnected",
"Effective": "Unmanaged"
},
- "GUID": "stub_wifi2",
+ "GUID": {
+ "Active": "stub_wifi2",
+ "Effective": "UserPolicy",
+ "UserPolicy": "stub_wifi2"
+ },
"Name": {
"Active": "wifi2_PSK",
"Effective": "UserPolicy",
@@ -292,16 +296,21 @@ var availableTests = [
},
function setProperties() {
var done = chrome.test.callbackAdded();
+ var network_guid = "stub_wifi2";
chrome.networkingPrivate.getProperties(
- "stub_wifi2",
+ network_guid,
callbackPass(function(result) {
+ assertEq(network_guid, result.GUID);
result.WiFi.Security = "WEP-PSK";
chrome.networkingPrivate.setProperties("stub_wifi2", result,
callbackPass(function() {
chrome.networkingPrivate.getProperties(
"stub_wifi2",
callbackPass(function(result) {
+ // Ensure that the property was set.
assertEq("WEP-PSK", result.WiFi.Security);
+ // Ensure that the GUID doesn't change.
+ assertEq(network_guid, result.GUID);
done();
}));
}));
@@ -327,7 +336,7 @@ var availableTests = [
function getStateNonExistent() {
chrome.networkingPrivate.getState(
'non_existent',
- callbackFail('Error.InvalidParameter'));
+ callbackFail('Error.InvalidNetworkGuid'));
},
function onNetworksChangedEventConnect() {
var network = "stub_wifi2";
@@ -367,9 +376,10 @@ var availableTests = [
}));
},
function verifyAndEncryptCredentials() {
+ var network_guid = "stub_wifi2";
chrome.networkingPrivate.verifyAndEncryptCredentials(
verificationProperties,
- "guid",
+ network_guid,
callbackPass(function(result) {
assertEq("encrypted_credentials", result);
}));
diff --git a/chromeos/network/client_cert_resolver.cc b/chromeos/network/client_cert_resolver.cc
index dd66e94..32f7ed7 100644
--- a/chromeos/network/client_cert_resolver.cc
+++ b/chromeos/network/client_cert_resolver.cc
@@ -344,7 +344,8 @@ void ClientCertResolver::PolicyApplied(const std::string& service_path) {
return;
// Compare this network with all certificates.
const FavoriteState* network =
- network_state_handler_->GetFavoriteState(service_path);
+ network_state_handler_->GetFavoriteStateFromServicePath(
+ service_path, true /* configured_only */);
if (!network) {
LOG(ERROR) << "service path '" << service_path << "' unknown.";
return;
diff --git a/chromeos/network/favorite_state.cc b/chromeos/network/favorite_state.cc
index 002ff4f..65b26b3 100644
--- a/chromeos/network/favorite_state.cc
+++ b/chromeos/network/favorite_state.cc
@@ -63,6 +63,8 @@ bool FavoriteState::PropertyChanged(const std::string& key,
NET_LOG_ERROR("Failed to parse " + key, path());
}
return true;
+ } else if (key == shill::kSecurityProperty) {
+ return GetStringValue(key, value, &security_);
}
return false;
}
@@ -79,8 +81,25 @@ void FavoriteState::GetStateProperties(
ui_data_.GetONCSourceAsString());
}
-bool FavoriteState::IsFavorite() const {
- // kTypeEthernetEap is always a favorite. We need this check because it does
+std::string FavoriteState::GetSpecifier() const {
+ if (!update_received()) {
+ NET_LOG_ERROR("GetSpecifier called before update", path());
+ return std::string();
+ }
+ if (type() == shill::kTypeWifi)
+ return name() + "_" + security_;
+ if (!name().empty())
+ return name();
+ return type(); // For unnamed networks such as ethernet.
+}
+
+void FavoriteState::SetGuid(const std::string& guid) {
+ DCHECK(guid_.empty());
+ guid_ = guid;
+}
+
+bool FavoriteState::IsInProfile() const {
+ // kTypeEthernetEap is always saved. We need this check because it does
// not show up in the visible list, but its properties may not be available
// when it first shows up in ServiceCompleteList. See crbug.com/355117.
return !profile_path_.empty() || type() == shill::kTypeEthernetEap;
diff --git a/chromeos/network/favorite_state.h b/chromeos/network/favorite_state.h
index 349b85b..e68f3a3 100644
--- a/chromeos/network/favorite_state.h
+++ b/chromeos/network/favorite_state.h
@@ -19,9 +19,10 @@ namespace chromeos {
// networks).
// Note: NetworkStateHandler will store an entry for each member of
// Manager.ServiceCompleteList, even for visible entries that are not
-// favorites. This is necessary to avoid unnecessarily re-requesting entries,
-// and to limit the code complexity. The IsFavorite() accessor is used to skip
-// entries that are not actually favorites.
+// saved. This is necessary to avoid unnecessarily re-requesting entries,
+// and to limit the code complexity. It is also convenient for tracking the
+// complete list of "known" networks. The IsInProfile() accessor is used to
+// skip entries that are not actually saved in a profile.
class CHROMEOS_EXPORT FavoriteState : public ManagedState {
public:
explicit FavoriteState(const std::string& path);
@@ -40,16 +41,27 @@ class CHROMEOS_EXPORT FavoriteState : public ManagedState {
const std::string& guid() const { return guid_; }
// Returns true if this is a favorite stored in a profile (see note above).
- bool IsFavorite() const;
+ bool IsInProfile() const;
// Returns true if the network properties are stored in a user profile.
bool IsPrivate() const;
+ // Returns a specifier for identifying this network in the absence of a GUID.
+ // This should only be used by NetworkStateHandler for keeping track of
+ // GUIDs assigned to unsaved networks.
+ std::string GetSpecifier() const;
+
+ // Set the GUID. Called exclusively by NetworkStateHandler.
+ void SetGuid(const std::string& guid);
+
private:
std::string profile_path_;
NetworkUIData ui_data_;
std::string guid_;
+ // Keep track of Service.Security. Only used for specifying wifi networks.
+ std::string security_;
+
// TODO(pneubeck): Remove this once (Managed)NetworkConfigurationHandler
// provides proxy configuration. crbug.com/241775
base::DictionaryValue proxy_config_;
diff --git a/chromeos/network/managed_network_configuration_handler_impl.cc b/chromeos/network/managed_network_configuration_handler_impl.cc
index bf7e191..e4bbf77 100644
--- a/chromeos/network/managed_network_configuration_handler_impl.cc
+++ b/chromeos/network/managed_network_configuration_handler_impl.cc
@@ -19,6 +19,7 @@
#include "chromeos/dbus/shill_profile_client.h"
#include "chromeos/dbus/shill_service_client.h"
#include "chromeos/network/device_state.h"
+#include "chromeos/network/favorite_state.h"
#include "chromeos/network/network_configuration_handler.h"
#include "chromeos/network/network_event_log.h"
#include "chromeos/network/network_policy_observer.h"
@@ -50,7 +51,7 @@ const char kPoliciesNotInitialized[] = "PoliciesNotInitialized";
const char kProfileNotInitialized[] = "ProflieNotInitialized";
const char kSetOnUnconfiguredNetwork[] = "SetCalledOnUnconfiguredNetwork";
const char kUnknownProfilePath[] = "UnknownProfilePath";
-const char kUnknownServicePath[] = "UnknownServicePath";
+const char kUnknownNetwork[] = "UnknownNetwork";
std::string ToDebugString(::onc::ONCSource source,
const std::string& userhash) {
@@ -237,11 +238,11 @@ void ManagedNetworkConfigurationHandlerImpl::SetProperties(
const base::DictionaryValue& user_settings,
const base::Closure& callback,
const network_handler::ErrorCallback& error_callback) const {
- const NetworkState* state =
- network_state_handler_->GetNetworkState(service_path);
-
+ const FavoriteState* state =
+ network_state_handler_->GetFavoriteStateFromServicePath(
+ service_path, true /* configured_only */);
if (!state) {
- InvokeErrorCallback(service_path, error_callback, kUnknownServicePath);
+ InvokeErrorCallback(service_path, error_callback, kUnknownNetwork);
return;
}
diff --git a/chromeos/network/managed_state.h b/chromeos/network/managed_state.h
index 8b56394..28e647d 100644
--- a/chromeos/network/managed_state.h
+++ b/chromeos/network/managed_state.h
@@ -79,6 +79,7 @@ class CHROMEOS_EXPORT ManagedState {
update_requested_ = update_requested;
}
+ // Returns true if |type_| matches |pattern|.
bool Matches(const NetworkTypePattern& pattern) const;
static std::string TypeToString(ManagedType type);
diff --git a/chromeos/network/network_state.cc b/chromeos/network/network_state.cc
index f473fcd..a50c7d5 100644
--- a/chromeos/network/network_state.cc
+++ b/chromeos/network/network_state.cc
@@ -252,6 +252,10 @@ std::string NetworkState::GetNetmask() const {
return network_util::PrefixLengthToNetmask(prefix_length_);
}
+void NetworkState::SetGuid(const std::string& guid) {
+ guid_ = guid;
+}
+
bool NetworkState::UpdateName(const base::DictionaryValue& properties) {
std::string updated_name =
shill_property_util::GetNameFromProperties(path(), properties);
diff --git a/chromeos/network/network_state.h b/chromeos/network/network_state.h
index d0ee74a..276c368 100644
--- a/chromeos/network/network_state.h
+++ b/chromeos/network/network_state.h
@@ -99,6 +99,9 @@ class CHROMEOS_EXPORT NetworkState : public ManagedState {
// Converts the prefix length to a netmask string.
std::string GetNetmask() const;
+ // Set the GUID. Called exclusively by NetworkStateHandler.
+ void SetGuid(const std::string& guid);
+
// Helpers (used e.g. when a state or error is cached)
static bool StateIsConnected(const std::string& connection_state);
static bool StateIsConnecting(const std::string& connection_state);
diff --git a/chromeos/network/network_state_handler.cc b/chromeos/network/network_state_handler.cc
index 1f06197..6540a0d 100644
--- a/chromeos/network/network_state_handler.cc
+++ b/chromeos/network/network_state_handler.cc
@@ -6,6 +6,7 @@
#include "base/bind.h"
#include "base/format_macros.h"
+#include "base/guid.h"
#include "base/location.h"
#include "base/logging.h"
#include "base/metrics/histogram.h"
@@ -194,10 +195,10 @@ const FavoriteState* NetworkStateHandler::DefaultFavoriteNetwork() const {
const NetworkState* default_network = DefaultNetwork();
if (!default_network)
return NULL;
- const FavoriteState* default_favorite =
- GetFavoriteState(default_network->path());
- DCHECK(default_network->type() != shill::kTypeWifi ||
- default_favorite) << "No favorite for: " << default_network->path();
+ const FavoriteState* default_favorite = GetFavoriteStateFromServicePath(
+ default_network->path(), true /* configured_only */);
+ DCHECK(default_network->type() != shill::kTypeWifi || default_favorite)
+ << "No favorite for: " << default_network->path();
DCHECK(!default_favorite || default_favorite->update_received())
<< "No update received for: " << default_network->path();
return default_favorite;
@@ -309,26 +310,41 @@ void NetworkStateHandler::GetFavoriteListByType(const NetworkTypePattern& type,
iter != favorite_list_.end(); ++iter) {
const FavoriteState* favorite = (*iter)->AsFavoriteState();
DCHECK(favorite);
- if (favorite->update_received() && favorite->IsFavorite() &&
+ if (favorite->update_received() && favorite->IsInProfile() &&
favorite->Matches(type)) {
list->push_back(favorite);
}
}
}
-const FavoriteState* NetworkStateHandler::GetFavoriteState(
- const std::string& service_path) const {
+const FavoriteState* NetworkStateHandler::GetFavoriteStateFromServicePath(
+ const std::string& service_path,
+ bool configured_only) const {
ManagedState* managed =
GetModifiableManagedState(&favorite_list_, service_path);
if (!managed)
return NULL;
const FavoriteState* favorite = managed->AsFavoriteState();
DCHECK(favorite);
- if (!favorite->update_received() || !favorite->IsFavorite())
+ if (!favorite->update_received() ||
+ (configured_only && !favorite->IsInProfile())) {
return NULL;
+ }
return favorite;
}
+const FavoriteState* NetworkStateHandler::GetFavoriteStateFromGuid(
+ const std::string& guid) const {
+ DCHECK(!guid.empty());
+ for (ManagedStateList::const_iterator iter = favorite_list_.begin();
+ iter != favorite_list_.end(); ++iter) {
+ const FavoriteState* favorite = (*iter)->AsFavoriteState();
+ if (favorite->guid() == guid)
+ return favorite;
+ }
+ return NULL;
+}
+
void NetworkStateHandler::RequestScan() const {
NET_LOG_USER("RequestScan", "");
shill_property_handler_->RequestScan();
@@ -489,7 +505,7 @@ void NetworkStateHandler::UpdateManagedStateProperties(
// A Favorite may not have been created yet if it was added later (e.g.
// through ConfigureService) since ServiceCompleteList updates are not
// emitted. Add and update the state here.
- managed = new FavoriteState(path);
+ managed = ManagedState::Create(type, path);
managed_list->push_back(managed);
}
managed->set_update_received();
@@ -507,6 +523,7 @@ void NetworkStateHandler::UpdateManagedStateProperties(
}
managed->InitialPropertiesReceived(properties);
}
+ UpdateGuid(managed);
managed->set_update_requested(false);
}
@@ -681,7 +698,7 @@ void NetworkStateHandler::ManagedStateListChanged(
for (ManagedStateList::iterator iter = favorite_list_.begin();
iter != favorite_list_.end(); ++iter) {
FavoriteState* favorite = (*iter)->AsFavoriteState();
- if (!favorite->IsFavorite())
+ if (!favorite->IsInProfile())
continue;
if (favorite->IsPrivate())
++unshared;
@@ -728,6 +745,49 @@ void NetworkStateHandler::DefaultNetworkServiceChanged(
//------------------------------------------------------------------------------
// Private methods
+void NetworkStateHandler::UpdateGuid(ManagedState* managed) {
+ if (managed->managed_type() == ManagedState::MANAGED_TYPE_FAVORITE) {
+ FavoriteState* favorite = managed->AsFavoriteState();
+ std::string specifier = favorite->GetSpecifier();
+ if (!favorite->guid().empty()) {
+ // If the favorite is saved in a profile, remove the entry from the map.
+ // Otherwise ensure that the entry matches the specified GUID.
+ if (favorite->IsInProfile())
+ specifier_guid_map_.erase(specifier);
+ else
+ specifier_guid_map_[specifier] = favorite->guid();
+ return;
+ }
+ // Ensure that the FavoriteState has a valid GUID.
+ std::string guid;
+ SpecifierGuidMap::iterator iter = specifier_guid_map_.find(specifier);
+ if (iter != specifier_guid_map_.end()) {
+ guid = iter->second;
+ } else {
+ guid = base::GenerateGUID();
+ specifier_guid_map_[specifier] = guid;
+ }
+ favorite->SetGuid(guid);
+ NetworkState* network = GetModifiableNetworkState(favorite->path());
+ if (network)
+ network->SetGuid(guid);
+ } else if (managed->managed_type() == ManagedState::MANAGED_TYPE_NETWORK) {
+ // If the GUID is not set and a corresponding FavoriteState exists, get the
+ // GUID from the FavoriteState. Otherwise it will get set when the Favorite
+ // is created.
+ NetworkState* network = managed->AsNetworkState();
+ if (!network->guid().empty())
+ return;
+ // ShillPropertyHandler will always call UpdateManagedStateProperties with
+ // type FAVORITE before type NETWORK, so there should always be a
+ // corresponding FavoriteState here.
+ FavoriteState* favorite = GetModifiableFavoriteState(network->path());
+ DCHECK(favorite);
+ if (favorite && !favorite->guid().empty())
+ network->SetGuid(favorite->guid());
+ }
+}
+
void NetworkStateHandler::NotifyDeviceListChanged() {
NET_LOG_DEBUG("NotifyDeviceListChanged",
base::StringPrintf("Size:%" PRIuS, device_list_.size()));
@@ -752,6 +812,15 @@ NetworkState* NetworkStateHandler::GetModifiableNetworkState(
return managed->AsNetworkState();
}
+FavoriteState* NetworkStateHandler::GetModifiableFavoriteState(
+ const std::string& service_path) const {
+ ManagedState* managed =
+ GetModifiableManagedState(&favorite_list_, service_path);
+ if (!managed)
+ return NULL;
+ return managed->AsFavoriteState();
+}
+
ManagedState* NetworkStateHandler::GetModifiableManagedState(
const ManagedStateList* managed_list,
const std::string& path) const {
diff --git a/chromeos/network/network_state_handler.h b/chromeos/network/network_state_handler.h
index 314a975..0d3709e 100644
--- a/chromeos/network/network_state_handler.h
+++ b/chromeos/network/network_state_handler.h
@@ -49,6 +49,21 @@ class NetworkTypePattern;
// keep properties up to date by managing the appropriate Shill observers.
// It will invoke its own more specific observer methods when the specified
// changes occur.
+//
+// Some notes about NetworkState, FavoriteState, and GUIDs:
+// * A FavoriteState exists for all network services stored in a profile, and
+// all "visible" networks (physically connected networks like ethernet and
+// cellular or in-range wifi networks). If the network is stored in a profile,
+// FavoriteState.IsInProfile() will return true.
+// * A NetworkState exists for "visible" networks only. There will always be a
+// corresponding FavoriteState with the same service_path() property.
+// * All networks saved to a profile will have a saved GUID that is persistent
+// across sessions.
+// * Networks that are not saved to a profile will have a GUID assigned when
+// the initial properties are received. The GUID will be consistent for
+// the duration of a session, even if the network drops out and returns.
+// * Both FavoriteState and NetworkState store the GUID. It will always be the
+// same for the same network (i.e. entries with the same service_path()).
class CHROMEOS_EXPORT NetworkStateHandler
: public internal::ShillPropertyHandler::Listener {
@@ -172,8 +187,16 @@ class CHROMEOS_EXPORT NetworkStateHandler
void GetFavoriteListByType(const NetworkTypePattern& type,
FavoriteStateList* list) const;
- // Finds and returns a favorite state by |service_path| or NULL if not found.
- const FavoriteState* GetFavoriteState(const std::string& service_path) const;
+ // Finds and returns the FavoriteState associated with |service_path| or NULL
+ // if not found. If |configured_only| is true, only returns saved entries
+ // (IsInProfile is true).
+ const FavoriteState* GetFavoriteStateFromServicePath(
+ const std::string& service_path,
+ bool configured_only) const;
+
+ // Finds and returns the FavoriteState associated with |guid| or NULL if not
+ // found. This returns all entries (IsInProfile() may be true or false).
+ const FavoriteState* GetFavoriteStateFromGuid(const std::string& guid) const;
// Requests a network scan. This may trigger updates to the network
// list, which will trigger the appropriate observer calls.
@@ -288,6 +311,7 @@ class CHROMEOS_EXPORT NetworkStateHandler
private:
typedef std::list<base::Closure> ScanCallbackList;
typedef std::map<std::string, ScanCallbackList> ScanCompleteCallbackMap;
+ typedef std::map<std::string, std::string> SpecifierGuidMap;
friend class NetworkStateHandlerTest;
FRIEND_TEST_ALL_PREFIXES(NetworkStateHandlerTest, NetworkStateHandlerStub);
@@ -296,6 +320,10 @@ class CHROMEOS_EXPORT NetworkStateHandler
void UpdateNetworkStateProperties(NetworkState* network,
const base::DictionaryValue& properties);
+ // Ensure a valid GUID for FavoriteState and update the NetworkState GUID from
+ // the corresponding FavoriteState if necessary.
+ void UpdateGuid(ManagedState* managed);
+
// Sends DeviceListChanged() to observers and logs an event.
void NotifyDeviceListChanged();
@@ -305,6 +333,8 @@ class CHROMEOS_EXPORT NetworkStateHandler
DeviceState* GetModifiableDeviceState(const std::string& device_path) const;
NetworkState* GetModifiableNetworkState(
const std::string& service_path) const;
+ FavoriteState* GetModifiableFavoriteState(
+ const std::string& service_path) const;
ManagedState* GetModifiableManagedState(const ManagedStateList* managed_list,
const std::string& path) const;
@@ -357,6 +387,10 @@ class CHROMEOS_EXPORT NetworkStateHandler
// Callbacks to run when a scan for the technology type completes.
ScanCompleteCallbackMap scan_complete_callbacks_;
+ // Map of network specifiers to guids. Contains an entry for each
+ // FavoriteState that is not saved in a profile.
+ SpecifierGuidMap specifier_guid_map_;
+
DISALLOW_COPY_AND_ASSIGN(NetworkStateHandler);
};
diff --git a/chromeos/network/network_state_handler_unittest.cc b/chromeos/network/network_state_handler_unittest.cc
index ca167d4..5e0af9c 100644
--- a/chromeos/network/network_state_handler_unittest.cc
+++ b/chromeos/network/network_state_handler_unittest.cc
@@ -17,6 +17,7 @@
#include "chromeos/dbus/shill_manager_client.h"
#include "chromeos/dbus/shill_profile_client.h"
#include "chromeos/dbus/shill_service_client.h"
+#include "chromeos/network/favorite_state.h"
#include "chromeos/network/network_state.h"
#include "chromeos/network/network_state_handler_observer.h"
#include "chromeos/network/shill_property_util.h"
@@ -357,14 +358,38 @@ TEST_F(NetworkStateHandlerTest, ServicePropertyChanged) {
EXPECT_EQ(2, test_observer_->PropertyUpdatesForService(eth1));
}
-TEST_F(NetworkStateHandlerTest, FavoriteState) {
- // Set the profile entry of a service
+TEST_F(NetworkStateHandlerTest, GetState) {
const std::string profile = "/profile/profile1";
- const std::string wifi1 = kShillManagerClientStubDefaultWifi;
+ const std::string wifi_path = kShillManagerClientStubDefaultWifi;
+
+ // Add a wifi service to a Profile.
profile_test_->AddProfile(profile, "" /* userhash */);
- EXPECT_TRUE(profile_test_->AddService(profile, wifi1));
+ EXPECT_TRUE(profile_test_->AddService(profile, wifi_path));
UpdateManagerProperties();
+
+ // Ensure that a NetworkState and corresponding FavoriteState exist.
+ const NetworkState* wifi_network =
+ network_state_handler_->GetNetworkState(wifi_path);
+ ASSERT_TRUE(wifi_network);
+ const FavoriteState* wifi_favorite =
+ network_state_handler_->GetFavoriteStateFromServicePath(
+ wifi_path, true /* configured_only */);
+ ASSERT_TRUE(wifi_favorite);
+ EXPECT_EQ(wifi_network->path(), wifi_favorite->path());
+
+ // Ensure that we are notified that a Favorite was added.
EXPECT_EQ(1u, test_observer_->favorite_count());
+
+ // Test looking up by GUID.
+ ASSERT_FALSE(wifi_favorite->guid().empty());
+ const FavoriteState* wifi_favorite_guid =
+ network_state_handler_->GetFavoriteStateFromGuid(wifi_favorite->guid());
+ EXPECT_EQ(wifi_favorite, wifi_favorite_guid);
+
+ // Remove the service, verify that there is no longer a NetworkState for it.
+ service_test_->RemoveService(wifi_path);
+ UpdateManagerProperties();
+ EXPECT_FALSE(network_state_handler_->GetNetworkState(wifi_path));
}
TEST_F(NetworkStateHandlerTest, NetworkConnectionStateChanged) {
@@ -489,4 +514,100 @@ TEST_F(NetworkStateHandlerTest, RequestUpdate) {
EXPECT_EQ(2, test_observer_->PropertyUpdatesForService(
kShillManagerClientStubDefaultWifi));
}
+
+TEST_F(NetworkStateHandlerTest, NetworkGuidInProfile) {
+ const std::string profile = "/profile/profile1";
+ const std::string wifi_path = "wifi_with_guid";
+ const std::string wifi_guid = "WIFI_GUID";
+ const bool is_service_configured = true;
+
+ // Add a network to the default Profile with a specified GUID.
+ service_test_->AddServiceWithIPConfig(
+ wifi_path,
+ wifi_guid,
+ wifi_path /* name */,
+ shill::kTypeWifi,
+ shill::kStateOnline,
+ "" /* ipconfig_path */,
+ true /* add_to_visible */,
+ true /* add_to_watchlist */);
+ profile_test_->AddProfile(profile, "" /* userhash */);
+ EXPECT_TRUE(profile_test_->AddService(profile, wifi_path));
+ UpdateManagerProperties();
+
+ // Verify that a FavoriteState exists with a matching GUID.
+ const FavoriteState* favorite =
+ network_state_handler_->GetFavoriteStateFromServicePath(
+ wifi_path, is_service_configured);
+ ASSERT_TRUE(favorite);
+ EXPECT_EQ(wifi_guid, favorite->guid());
+
+ // Verify that a NetworkState exists with the same GUID.
+ const NetworkState* network =
+ network_state_handler_->GetNetworkState(wifi_path);
+ ASSERT_TRUE(network);
+ EXPECT_EQ(wifi_guid, network->guid());
+
+ // Remove the service (simulating a network going out of range).
+ service_test_->RemoveService(wifi_path);
+ UpdateManagerProperties();
+ EXPECT_FALSE(network_state_handler_->GetNetworkState(wifi_path));
+
+ // Add the service (simulating a network coming back in range) and verify that
+ // the NetworkState was created with the same GUID.
+ AddService(wifi_path, wifi_path, shill::kTypeWifi, shill::kStateOnline);
+ UpdateManagerProperties();
+ network = network_state_handler_->GetNetworkState(wifi_path);
+ ASSERT_TRUE(network);
+ EXPECT_EQ(wifi_guid, network->guid());
+
+ // Also verify FavoriteState (mostly to test the stub behavior).
+ favorite = network_state_handler_->GetFavoriteStateFromServicePath(
+ wifi_path, is_service_configured);
+ ASSERT_TRUE(favorite);
+ EXPECT_EQ(wifi_guid, favorite->guid());
+}
+
+TEST_F(NetworkStateHandlerTest, NetworkGuidNotInProfile) {
+ const std::string wifi_path = "wifi_with_guid";
+ const bool is_service_configured = false;
+
+ // Add a network without adding it to a profile.
+ AddService(wifi_path, wifi_path, shill::kTypeWifi, shill::kStateOnline);
+ UpdateManagerProperties();
+
+ // Verify that a FavoriteState exists with an assigned GUID.
+ const FavoriteState* favorite =
+ network_state_handler_->GetFavoriteStateFromServicePath(
+ wifi_path, is_service_configured);
+ ASSERT_TRUE(favorite);
+ std::string wifi_guid = favorite->guid();
+ EXPECT_FALSE(wifi_guid.empty());
+
+ // Verify that a NetworkState exists with the same GUID.
+ const NetworkState* network =
+ network_state_handler_->GetNetworkState(wifi_path);
+ ASSERT_TRUE(network);
+ EXPECT_EQ(wifi_guid, network->guid());
+
+ // Remove the service (simulating a network going out of range).
+ service_test_->RemoveService(wifi_path);
+ UpdateManagerProperties();
+ EXPECT_FALSE(network_state_handler_->GetNetworkState(wifi_path));
+
+ // Add the service (simulating a network coming back in range) and verify that
+ // the NetworkState was created with the same GUID.
+ AddService(wifi_path, wifi_path, shill::kTypeWifi, shill::kStateOnline);
+ UpdateManagerProperties();
+ network = network_state_handler_->GetNetworkState(wifi_path);
+ ASSERT_TRUE(network);
+ EXPECT_EQ(wifi_guid, network->guid());
+
+ // Also verify FavoriteState (mostly to test the stub behavior).
+ favorite = network_state_handler_->GetFavoriteStateFromServicePath(
+ wifi_path, is_service_configured);
+ ASSERT_TRUE(favorite);
+ EXPECT_EQ(wifi_guid, favorite->guid());
+}
+
} // namespace chromeos
diff --git a/chromeos/network/network_util.cc b/chromeos/network/network_util.cc
index 1acf6e5..f0d5d6a 100644
--- a/chromeos/network/network_util.cc
+++ b/chromeos/network/network_util.cc
@@ -6,6 +6,11 @@
#include "base/strings/string_tokenizer.h"
#include "base/strings/stringprintf.h"
+#include "chromeos/network/network_state.h"
+#include "chromeos/network/network_state_handler.h"
+#include "chromeos/network/onc/onc_signature.h"
+#include "chromeos/network/onc/onc_translator.h"
+#include "chromeos/network/shill_property_util.h"
#include "third_party/cros_system_api/dbus/service_constants.h"
namespace chromeos {
@@ -122,5 +127,27 @@ bool ParseCellularScanResults(const base::ListValue& list,
return true;
}
+scoped_ptr<base::ListValue> TranslateNetworkListToONC(
+ NetworkTypePattern pattern) {
+ NetworkStateHandler::NetworkStateList network_states;
+ NetworkHandler::Get()->network_state_handler()->GetNetworkListByType(
+ pattern, &network_states);
+
+ scoped_ptr<base::ListValue> network_properties_list(new base::ListValue);
+ for (NetworkStateHandler::NetworkStateList::iterator it =
+ network_states.begin();
+ it != network_states.end();
+ ++it) {
+ base::DictionaryValue shill_dictionary;
+ (*it)->GetStateProperties(&shill_dictionary);
+
+ scoped_ptr<base::DictionaryValue> onc_network_part =
+ TranslateShillServiceToONCPart(
+ shill_dictionary, &onc::kNetworkWithStateSignature);
+ network_properties_list->Append(onc_network_part.release());
+ }
+ return network_properties_list.Pass();
+}
+
} // namespace network_util
} // namespace chromeos
diff --git a/chromeos/network/network_util.h b/chromeos/network/network_util.h
index 7c95238..ebcc811 100644
--- a/chromeos/network/network_util.h
+++ b/chromeos/network/network_util.h
@@ -15,12 +15,19 @@
#include "base/basictypes.h"
#include "base/callback.h"
+#include "base/memory/scoped_ptr.h"
#include "base/time/time.h"
#include "base/values.h"
#include "chromeos/chromeos_export.h"
+namespace base {
+class ListValue;
+}
+
namespace chromeos {
+class NetworkTypePattern;
+
// Struct for passing wifi access point data.
struct CHROMEOS_EXPORT WifiAccessPoint {
WifiAccessPoint();
@@ -79,6 +86,12 @@ CHROMEOS_EXPORT int32 NetmaskToPrefixLength(const std::string& netmask);
CHROMEOS_EXPORT bool ParseCellularScanResults(
const base::ListValue& list, std::vector<CellularScanResult>* scan_results);
+// Retrieves the list of visible network services by passing |pattern| to
+// NetworkStateHandler::GetNetworkListByType() and translates each into a list
+// of ONC dictionaries using TranslateShillServiceToONCPart.
+CHROMEOS_EXPORT scoped_ptr<base::ListValue> TranslateNetworkListToONC(
+ NetworkTypePattern pattern);
+
} // namespace network_util
} // namespace chromeos
diff --git a/chromeos/network/shill_property_handler.cc b/chromeos/network/shill_property_handler.cc
index 13f34c1..219da55 100644
--- a/chromeos/network/shill_property_handler.cc
+++ b/chromeos/network/shill_property_handler.cc
@@ -353,9 +353,15 @@ void ShillPropertyHandler::UpdateProperties(ManagedState::ManagedType type,
(*iter)->GetAsString(&path);
if (path.empty())
continue;
+ // Only request properties once. Favorites that are visible will be updated
+ // when the Network entry is updated. Since 'Services' is always processed
+ // before ServiceCompleteList, only Favorites that are not visible will be
+ // requested here, and GetPropertiesCallback() will only get called with
+ // type == FAVORITE for non-visible Favorites.
if (type == ManagedState::MANAGED_TYPE_FAVORITE &&
- requested_service_updates.count(path) > 0)
- continue; // Update already requested
+ requested_service_updates.count(path) > 0) {
+ continue;
+ }
// We add a special case for devices here to work around an issue in shill
// that prevents it from sending property changed signals for cellular
@@ -477,16 +483,13 @@ void ShillPropertyHandler::GetPropertiesCallback(
base::StringPrintf("%s: %d", path.c_str(), call_status));
return;
}
- // Update Favorite properties for networks in the Services list.
+ // Update Favorite properties for networks in the Services list. Call this
+ // for all networks, regardless of whether or not Profile is set, because
+ // we track all networks in the Favorites list (even if they aren't saved
+ // in a Profile). See notes in UpdateProperties() and favorite_state.h.
if (type == ManagedState::MANAGED_TYPE_NETWORK) {
- // Only networks with a ProfilePath set are Favorites.
- std::string profile_path;
- properties.GetStringWithoutPathExpansion(
- shill::kProfileProperty, &profile_path);
- if (!profile_path.empty()) {
- listener_->UpdateManagedStateProperties(
- ManagedState::MANAGED_TYPE_FAVORITE, path, properties);
- }
+ listener_->UpdateManagedStateProperties(
+ ManagedState::MANAGED_TYPE_FAVORITE, path, properties);
}
listener_->UpdateManagedStateProperties(type, path, properties);
diff --git a/components/wifi/fake_wifi_service.cc b/components/wifi/fake_wifi_service.cc
index 86b6358..87b01a4 100644
--- a/components/wifi/fake_wifi_service.cc
+++ b/components/wifi/fake_wifi_service.cc
@@ -69,11 +69,11 @@ void FakeWiFiService::GetProperties(const std::string& network_guid,
std::string* error) {
WiFiService::NetworkList::iterator network_properties =
FindNetwork(network_guid);
- if (network_properties != networks_.end()) {
- properties->Swap(network_properties->ToValue(false).get());
- } else {
- *error = "Error.DBusFailed";
+ if (network_properties == networks_.end()) {
+ *error = "Error.InvalidNetworkGuid";
+ return;
}
+ properties->Swap(network_properties->ToValue(false).get());
}
void FakeWiFiService::GetManagedProperties(
@@ -90,7 +90,7 @@ void FakeWiFiService::GetState(const std::string& network_guid,
WiFiService::NetworkList::iterator network_properties =
FindNetwork(network_guid);
if (network_properties == networks_.end()) {
- *error = "Error.InvalidParameter";
+ *error = "Error.InvalidNetworkGuid";
return;
}
properties->Swap(network_properties->ToValue(true).get());
@@ -143,29 +143,29 @@ void FakeWiFiService::RequestNetworkScan() {
void FakeWiFiService::StartConnect(const std::string& network_guid,
std::string* error) {
NetworkList::iterator network_properties = FindNetwork(network_guid);
- if (network_properties != networks_.end()) {
- DisconnectAllNetworksOfType(network_properties->type);
- network_properties->connection_state = onc::connection_state::kConnected;
- SortNetworks();
- NotifyNetworkListChanged(networks_);
- NotifyNetworkChanged(network_guid);
- } else {
- *error = "configure-failed";
+ if (network_properties == networks_.end()) {
+ *error = "Error.InvalidNetworkGuid";
+ return;
}
+ DisconnectAllNetworksOfType(network_properties->type);
+ network_properties->connection_state = onc::connection_state::kConnected;
+ SortNetworks();
+ NotifyNetworkListChanged(networks_);
+ NotifyNetworkChanged(network_guid);
}
void FakeWiFiService::StartDisconnect(const std::string& network_guid,
std::string* error) {
WiFiService::NetworkList::iterator network_properties =
FindNetwork(network_guid);
- if (network_properties != networks_.end()) {
- network_properties->connection_state = onc::connection_state::kNotConnected;
- SortNetworks();
- NotifyNetworkListChanged(networks_);
- NotifyNetworkChanged(network_guid);
- } else {
- *error = "not-found";
+ if (network_properties == networks_.end()) {
+ *error = "Error.InvalidNetworkGuid";
+ return;
}
+ network_properties->connection_state = onc::connection_state::kNotConnected;
+ SortNetworks();
+ NotifyNetworkListChanged(networks_);
+ NotifyNetworkChanged(network_guid);
}
void FakeWiFiService::GetKeyFromSystem(const std::string& network_guid,