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 14 using extensions::APIPermission; 15 using extensions::APIPermissionInfo; 16 using extensions::APIPermissionSet; 17 using extensions::Extension; 18 using extensions::Manifest; 19 using extensions::ManifestHandler; 20 using extensions::ManifestPermission; 21 using extensions::ManifestPermissionSet; 22 using extensions::PermissionSet; 23 using extensions::URLPatternSet; 24 25 ExtensionMsg_PermissionSetStruct::ExtensionMsg_PermissionSetStruct() { 26 } 27 28 ExtensionMsg_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 36 ExtensionMsg_PermissionSetStruct::~ExtensionMsg_PermissionSetStruct() { 37 } 38 39 scoped_refptr<const PermissionSet> 40 ExtensionMsg_PermissionSetStruct::ToPermissionSet() const { 41 return new PermissionSet( 42 apis, manifest_permissions, explicit_hosts, scriptable_hosts); 43 } 44 45 ExtensionMsg_Loaded_Params::ExtensionMsg_Loaded_Params() 46 : location(Manifest::INVALID_LOCATION), 47 creation_flags(Extension::NO_FLAGS) {} 48 49 ExtensionMsg_Loaded_Params::~ExtensionMsg_Loaded_Params() {} 50 51 ExtensionMsg_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 63 scoped_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 75 namespace IPC { 76 77 template <> 78 struct 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 98 void ParamTraits<URLPattern>::Write(Message* m, const param_type& p) { 99 WriteParam(m, p.valid_schemes()); 100 WriteParam(m, p.GetAsString()); 101 } 102 103 bool 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 122 void ParamTraits<URLPattern>::Log(const param_type& p, std::string* l) { 123 LogParam(p.GetAsString(), l); 124 } 125 126 void ParamTraits<URLPatternSet>::Write(Message* m, const param_type& p) { 127 WriteParam(m, p.patterns()); 128 } 129 130 bool 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 142 void ParamTraits<URLPatternSet>::Log(const param_type& p, std::string* l) { 143 LogParam(p.patterns(), l); 144 } 145 146 void ParamTraits<APIPermission::ID>::Write( 147 Message* m, const param_type& p) { 148 WriteParam(m, static_cast<int>(p)); 149 } 150 151 bool 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 161 void ParamTraits<APIPermission::ID>::Log( 162 const param_type& p, std::string* l) { 163 LogParam(static_cast<int>(p), l); 164 } 165 166 void 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 177 bool 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 198 void ParamTraits<APIPermissionSet>::Log( 199 const param_type& p, std::string* l) { 200 LogParam(p.map(), l); 201 } 202 203 void 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 214 bool 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 233 void ParamTraits<ManifestPermissionSet>::Log( 234 const param_type& p, std::string* l) { 235 LogParam(p.map(), l); 236 } 237 238 void 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 246 bool 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 255 void 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 263 void 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 273 bool 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 284 void ParamTraits<ExtensionMsg_Loaded_Params>::Log(const param_type& p, 285 std::string* l) { 286 l->append(p.id); 287 } 288 289 } // namespace IPC 290