Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(165)

Side by Side Diff: chrome/browser/chromeos/cros/onc_network_parser.cc

Issue 10944009: Implementation of ONC signature, validator and normalizer. (Closed) Base URL: http://git.chromium.org/chromium/src.git@gperffix
Patch Set: Completed validator for complete ONC. Integrated into OncNetworkParser. Created 8 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "chrome/browser/chromeos/cros/onc_network_parser.h" 5 #include "chrome/browser/chromeos/cros/onc_network_parser.h"
6 6
7 #include <keyhi.h> 7 #include <keyhi.h>
8 #include <pk11pub.h> 8 #include <pk11pub.h>
9 9
10 #include "base/base64.h" 10 #include "base/base64.h"
11 #include "base/json/json_string_value_serializer.h" 11 #include "base/json/json_string_value_serializer.h"
12 #include "chrome/browser/chromeos/login/user_manager.h" 12 #include "chrome/browser/chromeos/login/user_manager.h"
13 #include "base/json/json_writer.h" // for debug output only. 13 #include "base/json/json_writer.h" // for debug output only.
14 #include "base/stringprintf.h" 14 #include "base/stringprintf.h"
15 #include "base/values.h" 15 #include "base/values.h"
16 #include "chrome/browser/chromeos/cros/certificate_pattern.h" 16 #include "chrome/browser/chromeos/cros/certificate_pattern.h"
17 #include "chrome/browser/chromeos/cros/cros_library.h" 17 #include "chrome/browser/chromeos/cros/cros_library.h"
18 #include "chrome/browser/chromeos/cros/native_network_constants.h" 18 #include "chrome/browser/chromeos/cros/native_network_constants.h"
19 #include "chrome/browser/chromeos/cros/native_network_parser.h" 19 #include "chrome/browser/chromeos/cros/native_network_parser.h"
20 #include "chrome/browser/chromeos/cros/network_library.h" 20 #include "chrome/browser/chromeos/cros/network_library.h"
21 #include "chrome/browser/chromeos/cros/onc_constants.h" 21 #include "chrome/browser/chromeos/cros/onc_constants.h"
22 #include "chrome/browser/chromeos/network_settings/onc_signature.h"
23 #include "chrome/browser/chromeos/network_settings/onc_validator.h"
22 #include "chrome/browser/chromeos/proxy_config_service_impl.h" 24 #include "chrome/browser/chromeos/proxy_config_service_impl.h"
23 #include "chrome/browser/prefs/proxy_config_dictionary.h" 25 #include "chrome/browser/prefs/proxy_config_dictionary.h"
24 #include "chrome/common/net/x509_certificate_model.h" 26 #include "chrome/common/net/x509_certificate_model.h"
25 #include "content/public/browser/browser_thread.h" 27 #include "content/public/browser/browser_thread.h"
26 #include "crypto/encryptor.h" 28 #include "crypto/encryptor.h"
27 #include "crypto/hmac.h" 29 #include "crypto/hmac.h"
28 #include "crypto/scoped_nss_types.h" 30 #include "crypto/scoped_nss_types.h"
29 #include "crypto/symmetric_key.h" 31 #include "crypto/symmetric_key.h"
30 #include "grit/generated_resources.h" 32 #include "grit/generated_resources.h"
31 #include "net/base/crypto_module.h" 33 #include "net/base/crypto_module.h"
(...skipping 94 matching lines...) Expand 10 before | Expand all | Expand 10 after
126 { onc::eap::kUseSystemCAs, PROPERTY_INDEX_EAP_USE_SYSTEM_CAS, TYPE_BOOLEAN }, 128 { onc::eap::kUseSystemCAs, PROPERTY_INDEX_EAP_USE_SYSTEM_CAS, TYPE_BOOLEAN },
127 { onc::eap::kSaveCredentials, PROPERTY_INDEX_SAVE_CREDENTIALS, TYPE_BOOLEAN }, 129 { onc::eap::kSaveCredentials, PROPERTY_INDEX_SAVE_CREDENTIALS, TYPE_BOOLEAN },
128 { NULL } 130 { NULL }
129 }; 131 };
130 132
131 OncValueSignature vpn_signature[] = { 133 OncValueSignature vpn_signature[] = {
132 { onc::vpn::kHost, PROPERTY_INDEX_PROVIDER_HOST, TYPE_STRING }, 134 { onc::vpn::kHost, PROPERTY_INDEX_PROVIDER_HOST, TYPE_STRING },
133 { onc::vpn::kIPsec, PROPERTY_INDEX_ONC_IPSEC, TYPE_DICTIONARY }, 135 { onc::vpn::kIPsec, PROPERTY_INDEX_ONC_IPSEC, TYPE_DICTIONARY },
134 { onc::vpn::kL2TP, PROPERTY_INDEX_ONC_L2TP, TYPE_DICTIONARY }, 136 { onc::vpn::kL2TP, PROPERTY_INDEX_ONC_L2TP, TYPE_DICTIONARY },
135 { onc::vpn::kOpenVPN, PROPERTY_INDEX_ONC_OPENVPN, TYPE_DICTIONARY }, 137 { onc::vpn::kOpenVPN, PROPERTY_INDEX_ONC_OPENVPN, TYPE_DICTIONARY },
136 { onc::vpn::kType, PROPERTY_INDEX_PROVIDER_TYPE, TYPE_STRING }, 138 { onc::kType, PROPERTY_INDEX_PROVIDER_TYPE, TYPE_STRING },
Mattias Nissler (ping if slow) 2012/11/02 10:10:00 Shouldn't this stay onc::vpn::kType? It's the type
pneubeck (no reviews) 2012/11/05 12:04:48 Done.
137 { NULL } 139 { NULL }
138 }; 140 };
139 141
140 OncValueSignature ipsec_signature[] = { 142 OncValueSignature ipsec_signature[] = {
141 { onc::vpn::kAuthenticationType, PROPERTY_INDEX_IPSEC_AUTHENTICATIONTYPE, 143 { onc::vpn::kAuthenticationType, PROPERTY_INDEX_IPSEC_AUTHENTICATIONTYPE,
142 TYPE_STRING }, 144 TYPE_STRING },
143 { onc::vpn::kGroup, PROPERTY_INDEX_L2TPIPSEC_GROUP_NAME, TYPE_STRING }, 145 { onc::vpn::kGroup, PROPERTY_INDEX_L2TPIPSEC_GROUP_NAME, TYPE_STRING },
144 { onc::vpn::kIKEVersion, PROPERTY_INDEX_IPSEC_IKEVERSION, TYPE_INTEGER }, 146 { onc::vpn::kIKEVersion, PROPERTY_INDEX_IPSEC_IKEVERSION, TYPE_INTEGER },
145 { onc::vpn::kClientCertPattern, PROPERTY_INDEX_ONC_CLIENT_CERT_PATTERN, 147 { onc::vpn::kClientCertPattern, PROPERTY_INDEX_ONC_CLIENT_CERT_PATTERN,
146 TYPE_DICTIONARY }, 148 TYPE_DICTIONARY },
(...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after
196 { onc::vpn::kStaticChallenge, PROPERTY_INDEX_OPEN_VPN_STATICCHALLENGE, 198 { onc::vpn::kStaticChallenge, PROPERTY_INDEX_OPEN_VPN_STATICCHALLENGE,
197 TYPE_STRING }, 199 TYPE_STRING },
198 { onc::vpn::kTLSAuthContents, PROPERTY_INDEX_OPEN_VPN_TLSAUTHCONTENTS, 200 { onc::vpn::kTLSAuthContents, PROPERTY_INDEX_OPEN_VPN_TLSAUTHCONTENTS,
199 TYPE_STRING }, 201 TYPE_STRING },
200 { onc::vpn::kTLSRemote, PROPERTY_INDEX_OPEN_VPN_TLSREMOTE, TYPE_STRING }, 202 { onc::vpn::kTLSRemote, PROPERTY_INDEX_OPEN_VPN_TLSREMOTE, TYPE_STRING },
201 { onc::vpn::kUsername, PROPERTY_INDEX_OPEN_VPN_USER, TYPE_STRING }, 203 { onc::vpn::kUsername, PROPERTY_INDEX_OPEN_VPN_USER, TYPE_STRING },
202 { NULL } 204 { NULL }
203 }; 205 };
204 206
205 OncValueSignature proxy_settings_signature[] = { 207 OncValueSignature proxy_settings_signature[] = {
206 { onc::proxy::kType, PROPERTY_INDEX_ONC_PROXY_TYPE, TYPE_STRING }, 208 { onc::kType, PROPERTY_INDEX_ONC_PROXY_TYPE, TYPE_STRING },
Mattias Nissler (ping if slow) 2012/11/02 10:10:00 ditto
pneubeck (no reviews) 2012/11/05 12:04:48 Done.
207 { onc::proxy::kPAC, PROPERTY_INDEX_ONC_PROXY_PAC, TYPE_STRING }, 209 { onc::proxy::kPAC, PROPERTY_INDEX_ONC_PROXY_PAC, TYPE_STRING },
208 { onc::proxy::kManual, PROPERTY_INDEX_ONC_PROXY_MANUAL, TYPE_DICTIONARY }, 210 { onc::proxy::kManual, PROPERTY_INDEX_ONC_PROXY_MANUAL, TYPE_DICTIONARY },
209 { onc::proxy::kExcludeDomains, PROPERTY_INDEX_ONC_PROXY_EXCLUDE_DOMAINS, 211 { onc::proxy::kExcludeDomains, PROPERTY_INDEX_ONC_PROXY_EXCLUDE_DOMAINS,
210 TYPE_LIST }, 212 TYPE_LIST },
211 { NULL }, 213 { NULL },
212 }; 214 };
213 215
214 OncValueSignature proxy_manual_signature[] = { 216 OncValueSignature proxy_manual_signature[] = {
215 { onc::proxy::kHttp, PROPERTY_INDEX_ONC_PROXY_HTTP, TYPE_DICTIONARY }, 217 { onc::proxy::kHttp, PROPERTY_INDEX_ONC_PROXY_HTTP, TYPE_DICTIONARY },
216 { onc::proxy::kHttps, PROPERTY_INDEX_ONC_PROXY_HTTPS, TYPE_DICTIONARY }, 218 { onc::proxy::kHttps, PROPERTY_INDEX_ONC_PROXY_HTTPS, TYPE_DICTIONARY },
(...skipping 80 matching lines...) Expand 10 before | Expand all | Expand 10 after
297 299
298 // Check and see if this is an encrypted ONC file. If so, decrypt it. 300 // Check and see if this is an encrypted ONC file. If so, decrypt it.
299 std::string ciphertext_test; 301 std::string ciphertext_test;
300 if (root_dict_->GetString("Ciphertext", &ciphertext_test)) 302 if (root_dict_->GetString("Ciphertext", &ciphertext_test))
301 root_dict_.reset(Decrypt(passphrase, root_dict_.get())); 303 root_dict_.reset(Decrypt(passphrase, root_dict_.get()));
302 304
303 // Decryption failed, errors will be in parse_error_; 305 // Decryption failed, errors will be in parse_error_;
304 if (!root_dict_.get()) 306 if (!root_dict_.get())
305 return; 307 return;
306 308
309 bool is_managed = onc_source == NetworkUIData::ONC_SOURCE_USER_POLICY ||
310 onc_source == NetworkUIData::ONC_SOURCE_DEVICE_POLICY;
311 // Validate the ONC dictionary. We are liberal and ignore unknown field
312 // names.
Mattias Nissler (ping if slow) 2012/11/02 10:10:00 I think this comment should go before the is_manag
pneubeck (no reviews) 2012/11/05 12:04:48 Done.
313 bool error_on_unknown_field = false;
314 bool error_on_wrong_recommended = false;
Mattias Nissler (ping if slow) 2012/11/02 10:10:00 I don't understand what that means. Better name? C
pneubeck (no reviews) 2012/11/05 12:04:48 Done.
315 bool error_on_missing_field = true;
316 scoped_ptr<onc::Validator> validator(
317 new onc::Validator(error_on_unknown_field, error_on_wrong_recommended,
318 error_on_missing_field, is_managed));
319
320 // Unknown fields are removed from the result.
321 root_dict_ = validator->ValidateAndRepairObject(
322 &onc::kUnencryptedConfigurationSignature,
323 *root_dict_);
324
325 if (!root_dict_.get()) {
326 LOG(WARNING) << "Provided ONC is invalid and couldn't be repaired";
327 return;
328 }
329
307 // At least one of NetworkConfigurations or Certificates is required. 330 // At least one of NetworkConfigurations or Certificates is required.
308 bool has_network_configurations = 331 bool has_network_configurations =
309 root_dict_->GetList("NetworkConfigurations", &network_configs_); 332 root_dict_->GetList("NetworkConfigurations", &network_configs_);
310 bool has_certificates = 333 bool has_certificates =
311 root_dict_->GetList("Certificates", &certificates_); 334 root_dict_->GetList("Certificates", &certificates_);
312 VLOG(2) << "ONC file has " << GetNetworkConfigsSize() << " networks and " 335 VLOG(2) << "ONC file has " << GetNetworkConfigsSize() << " networks and "
313 << GetCertificatesSize() << " certificates"; 336 << GetCertificatesSize() << " certificates";
314 LOG_IF(WARNING, (!has_network_configurations && !has_certificates)) 337 LOG_IF(WARNING, (!has_network_configurations && !has_certificates))
315 << "ONC file has no NetworkConfigurations or Certificates."; 338 << "ONC file has no NetworkConfigurations or Certificates.";
316 } 339 }
(...skipping 750 matching lines...) Expand 10 before | Expand all | Expand 10 after
1067 1090
1068 VLOG(2) << "Successfully imported client certificate at index " 1091 VLOG(2) << "Successfully imported client certificate at index "
1069 << cert_index; 1092 << cert_index;
1070 return cert_result; 1093 return cert_result;
1071 } 1094 }
1072 1095
1073 // static 1096 // static
1074 ClientCertType OncNetworkParser::ParseClientCertType( 1097 ClientCertType OncNetworkParser::ParseClientCertType(
1075 const std::string& type) { 1098 const std::string& type) {
1076 static EnumMapper<ClientCertType>::Pair table[] = { 1099 static EnumMapper<ClientCertType>::Pair table[] = {
1077 { onc::certificate::kNone, CLIENT_CERT_TYPE_NONE }, 1100 { onc::kNone, CLIENT_CERT_TYPE_NONE },
Mattias Nissler (ping if slow) 2012/11/02 10:10:00 same here. I'd prefer clarity of where to find con
pneubeck (no reviews) 2012/11/05 12:04:48 Done.
1078 { onc::certificate::kRef, CLIENT_CERT_TYPE_REF }, 1101 { onc::certificate::kRef, CLIENT_CERT_TYPE_REF },
1079 { onc::certificate::kPattern, CLIENT_CERT_TYPE_PATTERN }, 1102 { onc::certificate::kPattern, CLIENT_CERT_TYPE_PATTERN },
1080 }; 1103 };
1081 CR_DEFINE_STATIC_LOCAL(EnumMapper<ClientCertType>, parser, 1104 CR_DEFINE_STATIC_LOCAL(EnumMapper<ClientCertType>, parser,
1082 (table, arraysize(table), CLIENT_CERT_TYPE_NONE)); 1105 (table, arraysize(table), CLIENT_CERT_TYPE_NONE));
1083 return parser.Get(type); 1106 return parser.Get(type);
1084 } 1107 }
1085 1108
1086 // static 1109 // static
1087 void OncNetworkParser::ListCertsWithNickname(const std::string& label, 1110 void OncNetworkParser::ListCertsWithNickname(const std::string& label,
(...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after
1157 const base::Value& value, 1180 const base::Value& value,
1158 Network* network) { 1181 Network* network) {
1159 VLOG(1) << "Processing ProxySettings: " << ConvertValueToString(value); 1182 VLOG(1) << "Processing ProxySettings: " << ConvertValueToString(value);
1160 1183
1161 // Got "ProxySettings" field. Immediately store the ProxySettings.Type 1184 // Got "ProxySettings" field. Immediately store the ProxySettings.Type
1162 // field value so that we can properly validate fields in the ProxySettings 1185 // field value so that we can properly validate fields in the ProxySettings
1163 // object based on the type. 1186 // object based on the type.
1164 const DictionaryValue* dict = NULL; 1187 const DictionaryValue* dict = NULL;
1165 CHECK(value.GetAsDictionary(&dict)); 1188 CHECK(value.GetAsDictionary(&dict));
1166 std::string proxy_type_string; 1189 std::string proxy_type_string;
1167 if (!dict->GetString(onc::proxy::kType, &proxy_type_string)) { 1190 if (!dict->GetString(onc::kType, &proxy_type_string)) {
1168 VLOG(1) << network->name() << ": ProxySettings.Type is missing"; 1191 VLOG(1) << network->name() << ": ProxySettings.Type is missing";
1169 return false; 1192 return false;
1170 } 1193 }
1171 Network::ProxyOncConfig& config = network->proxy_onc_config(); 1194 Network::ProxyOncConfig& config = network->proxy_onc_config();
1172 config.type = ParseProxyType(proxy_type_string); 1195 config.type = ParseProxyType(proxy_type_string);
1173 1196
1174 // For Direct and WPAD, all other fields are ignored. 1197 // For Direct and WPAD, all other fields are ignored.
1175 // Otherwise, recursively parse the children of ProxySettings dictionary. 1198 // Otherwise, recursively parse the children of ProxySettings dictionary.
1176 if (config.type != PROXY_ONC_DIRECT && config.type != PROXY_ONC_WPAD) { 1199 if (config.type != PROXY_ONC_DIRECT && config.type != PROXY_ONC_WPAD) {
1177 if (!parser->ParseNestedObject(network, 1200 if (!parser->ParseNestedObject(network,
(...skipping 852 matching lines...) Expand 10 before | Expand all | Expand 10 after
2030 // on the value of AuthenticationType. 2053 // on the value of AuthenticationType.
2031 { "L2TP-IPsec", PROVIDER_TYPE_L2TP_IPSEC_PSK }, 2054 { "L2TP-IPsec", PROVIDER_TYPE_L2TP_IPSEC_PSK },
2032 { "OpenVPN", PROVIDER_TYPE_OPEN_VPN }, 2055 { "OpenVPN", PROVIDER_TYPE_OPEN_VPN },
2033 }; 2056 };
2034 CR_DEFINE_STATIC_LOCAL(EnumMapper<ProviderType>, parser, 2057 CR_DEFINE_STATIC_LOCAL(EnumMapper<ProviderType>, parser,
2035 (table, arraysize(table), PROVIDER_TYPE_MAX)); 2058 (table, arraysize(table), PROVIDER_TYPE_MAX));
2036 return parser.Get(type); 2059 return parser.Get(type);
2037 } 2060 }
2038 2061
2039 } // namespace chromeos 2062 } // namespace chromeos
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698