1// Copyright 2014 The Chromium Authors. All rights reserved. 2// Use of this source code is governed by a BSD-style license that can be 3// found in the LICENSE file. 4 5#include "extensions/common/extension_messages.h" 6 7#include "content/public/common/common_param_traits.h" 8#include "extensions/common/extension.h" 9#include "extensions/common/manifest.h" 10#include "extensions/common/manifest_handler.h" 11#include "extensions/common/permissions/permissions_data.h" 12#include "extensions/common/permissions/permissions_info.h" 13 14using extensions::APIPermission; 15using extensions::APIPermissionInfo; 16using extensions::APIPermissionSet; 17using extensions::Extension; 18using extensions::Manifest; 19using extensions::ManifestHandler; 20using extensions::ManifestPermission; 21using extensions::ManifestPermissionSet; 22using extensions::PermissionSet; 23using extensions::URLPatternSet; 24 25ExtensionMsg_PermissionSetStruct::ExtensionMsg_PermissionSetStruct() { 26} 27 28ExtensionMsg_PermissionSetStruct::ExtensionMsg_PermissionSetStruct( 29 const PermissionSet& permissions) 30 : apis(permissions.apis()), 31 manifest_permissions(permissions.manifest_permissions()), 32 explicit_hosts(permissions.explicit_hosts()), 33 scriptable_hosts(permissions.scriptable_hosts()) { 34} 35 36ExtensionMsg_PermissionSetStruct::~ExtensionMsg_PermissionSetStruct() { 37} 38 39scoped_refptr<const PermissionSet> 40ExtensionMsg_PermissionSetStruct::ToPermissionSet() const { 41 return new PermissionSet( 42 apis, manifest_permissions, explicit_hosts, scriptable_hosts); 43} 44 45ExtensionMsg_Loaded_Params::ExtensionMsg_Loaded_Params() 46 : location(Manifest::INVALID_LOCATION), 47 creation_flags(Extension::NO_FLAGS) {} 48 49ExtensionMsg_Loaded_Params::~ExtensionMsg_Loaded_Params() {} 50 51ExtensionMsg_Loaded_Params::ExtensionMsg_Loaded_Params( 52 const Extension* extension) 53 : manifest(extension->manifest()->value()->DeepCopy()), 54 location(extension->location()), 55 path(extension->path()), 56 active_permissions(*extension->permissions_data()->active_permissions()), 57 withheld_permissions( 58 *extension->permissions_data()->withheld_permissions()), 59 id(extension->id()), 60 creation_flags(extension->creation_flags()) { 61} 62 63scoped_refptr<Extension> ExtensionMsg_Loaded_Params::ConvertToExtension( 64 std::string* error) const { 65 scoped_refptr<Extension> extension = 66 Extension::Create(path, location, *manifest, creation_flags, error); 67 if (extension.get()) { 68 extension->permissions_data()->SetPermissions( 69 active_permissions.ToPermissionSet(), 70 withheld_permissions.ToPermissionSet()); 71 } 72 return extension; 73} 74 75namespace IPC { 76 77template <> 78struct ParamTraits<Manifest::Location> { 79 typedef Manifest::Location param_type; 80 static void Write(Message* m, const param_type& p) { 81 int val = static_cast<int>(p); 82 WriteParam(m, val); 83 } 84 static bool Read(const Message* m, PickleIterator* iter, param_type* p) { 85 int val = 0; 86 if (!ReadParam(m, iter, &val) || 87 val < Manifest::INVALID_LOCATION || 88 val >= Manifest::NUM_LOCATIONS) 89 return false; 90 *p = static_cast<param_type>(val); 91 return true; 92 } 93 static void Log(const param_type& p, std::string* l) { 94 ParamTraits<int>::Log(static_cast<int>(p), l); 95 } 96}; 97 98void ParamTraits<URLPattern>::Write(Message* m, const param_type& p) { 99 WriteParam(m, p.valid_schemes()); 100 WriteParam(m, p.GetAsString()); 101} 102 103bool ParamTraits<URLPattern>::Read(const Message* m, PickleIterator* iter, 104 param_type* p) { 105 int valid_schemes; 106 std::string spec; 107 if (!ReadParam(m, iter, &valid_schemes) || 108 !ReadParam(m, iter, &spec)) 109 return false; 110 111 // TODO(jstritar): We don't want the URLPattern to fail parsing when the 112 // scheme is invalid. Instead, the pattern should parse but it should not 113 // match the invalid patterns. We get around this by setting the valid 114 // schemes after parsing the pattern. Update these method calls once we can 115 // ignore scheme validation with URLPattern parse options. crbug.com/90544 116 p->SetValidSchemes(URLPattern::SCHEME_ALL); 117 URLPattern::ParseResult result = p->Parse(spec); 118 p->SetValidSchemes(valid_schemes); 119 return URLPattern::PARSE_SUCCESS == result; 120} 121 122void ParamTraits<URLPattern>::Log(const param_type& p, std::string* l) { 123 LogParam(p.GetAsString(), l); 124} 125 126void ParamTraits<URLPatternSet>::Write(Message* m, const param_type& p) { 127 WriteParam(m, p.patterns()); 128} 129 130bool ParamTraits<URLPatternSet>::Read(const Message* m, PickleIterator* iter, 131 param_type* p) { 132 std::set<URLPattern> patterns; 133 if (!ReadParam(m, iter, &patterns)) 134 return false; 135 136 for (std::set<URLPattern>::iterator i = patterns.begin(); 137 i != patterns.end(); ++i) 138 p->AddPattern(*i); 139 return true; 140} 141 142void ParamTraits<URLPatternSet>::Log(const param_type& p, std::string* l) { 143 LogParam(p.patterns(), l); 144} 145 146void ParamTraits<APIPermission::ID>::Write( 147 Message* m, const param_type& p) { 148 WriteParam(m, static_cast<int>(p)); 149} 150 151bool ParamTraits<APIPermission::ID>::Read( 152 const Message* m, PickleIterator* iter, param_type* p) { 153 int api_id = -2; 154 if (!ReadParam(m, iter, &api_id)) 155 return false; 156 157 *p = static_cast<APIPermission::ID>(api_id); 158 return true; 159} 160 161void ParamTraits<APIPermission::ID>::Log( 162 const param_type& p, std::string* l) { 163 LogParam(static_cast<int>(p), l); 164} 165 166void ParamTraits<APIPermissionSet>::Write( 167 Message* m, const param_type& p) { 168 APIPermissionSet::const_iterator it = p.begin(); 169 const APIPermissionSet::const_iterator end = p.end(); 170 WriteParam(m, p.size()); 171 for (; it != end; ++it) { 172 WriteParam(m, it->id()); 173 it->Write(m); 174 } 175} 176 177bool ParamTraits<APIPermissionSet>::Read( 178 const Message* m, PickleIterator* iter, param_type* r) { 179 size_t size; 180 if (!ReadParam(m, iter, &size)) 181 return false; 182 for (size_t i = 0; i < size; ++i) { 183 APIPermission::ID id; 184 if (!ReadParam(m, iter, &id)) 185 return false; 186 const APIPermissionInfo* permission_info = 187 extensions::PermissionsInfo::GetInstance()->GetByID(id); 188 if (!permission_info) 189 return false; 190 scoped_ptr<APIPermission> p(permission_info->CreateAPIPermission()); 191 if (!p->Read(m, iter)) 192 return false; 193 r->insert(p.release()); 194 } 195 return true; 196} 197 198void ParamTraits<APIPermissionSet>::Log( 199 const param_type& p, std::string* l) { 200 LogParam(p.map(), l); 201} 202 203void ParamTraits<ManifestPermissionSet>::Write( 204 Message* m, const param_type& p) { 205 ManifestPermissionSet::const_iterator it = p.begin(); 206 const ManifestPermissionSet::const_iterator end = p.end(); 207 WriteParam(m, p.size()); 208 for (; it != end; ++it) { 209 WriteParam(m, it->name()); 210 it->Write(m); 211 } 212} 213 214bool ParamTraits<ManifestPermissionSet>::Read( 215 const Message* m, PickleIterator* iter, param_type* r) { 216 size_t size; 217 if (!ReadParam(m, iter, &size)) 218 return false; 219 for (size_t i = 0; i < size; ++i) { 220 std::string name; 221 if (!ReadParam(m, iter, &name)) 222 return false; 223 scoped_ptr<ManifestPermission> p(ManifestHandler::CreatePermission(name)); 224 if (!p) 225 return false; 226 if (!p->Read(m, iter)) 227 return false; 228 r->insert(p.release()); 229 } 230 return true; 231} 232 233void ParamTraits<ManifestPermissionSet>::Log( 234 const param_type& p, std::string* l) { 235 LogParam(p.map(), l); 236} 237 238void ParamTraits<ExtensionMsg_PermissionSetStruct>::Write(Message* m, 239 const param_type& p) { 240 WriteParam(m, p.apis); 241 WriteParam(m, p.manifest_permissions); 242 WriteParam(m, p.explicit_hosts); 243 WriteParam(m, p.scriptable_hosts); 244} 245 246bool ParamTraits<ExtensionMsg_PermissionSetStruct>::Read(const Message* m, 247 PickleIterator* iter, 248 param_type* p) { 249 return ReadParam(m, iter, &p->apis) && 250 ReadParam(m, iter, &p->manifest_permissions) && 251 ReadParam(m, iter, &p->explicit_hosts) && 252 ReadParam(m, iter, &p->scriptable_hosts); 253} 254 255void ParamTraits<ExtensionMsg_PermissionSetStruct>::Log(const param_type& p, 256 std::string* l) { 257 LogParam(p.apis, l); 258 LogParam(p.manifest_permissions, l); 259 LogParam(p.explicit_hosts, l); 260 LogParam(p.scriptable_hosts, l); 261} 262 263void ParamTraits<ExtensionMsg_Loaded_Params>::Write(Message* m, 264 const param_type& p) { 265 WriteParam(m, p.location); 266 WriteParam(m, p.path); 267 WriteParam(m, *(p.manifest)); 268 WriteParam(m, p.creation_flags); 269 WriteParam(m, p.active_permissions); 270 WriteParam(m, p.withheld_permissions); 271} 272 273bool ParamTraits<ExtensionMsg_Loaded_Params>::Read(const Message* m, 274 PickleIterator* iter, 275 param_type* p) { 276 p->manifest.reset(new base::DictionaryValue()); 277 return ReadParam(m, iter, &p->location) && ReadParam(m, iter, &p->path) && 278 ReadParam(m, iter, p->manifest.get()) && 279 ReadParam(m, iter, &p->creation_flags) && 280 ReadParam(m, iter, &p->active_permissions) && 281 ReadParam(m, iter, &p->withheld_permissions); 282} 283 284void ParamTraits<ExtensionMsg_Loaded_Params>::Log(const param_type& p, 285 std::string* l) { 286 l->append(p.id); 287} 288 289} // namespace IPC 290