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

Side by Side Diff: webkit/plugins/npapi/plugin_list.cc

Issue 5699005: Policy: Re-enabled plugin still disabled (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Whitespace fixes only. Trybot happiness still applies. Created 9 years, 11 months 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 | Annotate | Revision Log
« no previous file with comments | « webkit/plugins/npapi/plugin_list.h ('k') | webkit/plugins/npapi/plugin_list_mac.mm » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2010 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 "webkit/plugins/npapi/plugin_list.h" 5 #include "webkit/plugins/npapi/plugin_list.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 8
9 #include "base/command_line.h" 9 #include "base/command_line.h"
10 #include "base/lazy_instance.h" 10 #include "base/lazy_instance.h"
11 #include "base/logging.h" 11 #include "base/logging.h"
12 #include "base/stl_util-inl.h"
13 #include "base/string_split.h" 12 #include "base/string_split.h"
14 #include "base/string_util.h" 13 #include "base/string_util.h"
15 #include "base/sys_string_conversions.h" 14 #include "base/sys_string_conversions.h"
16 #include "base/utf_string_conversions.h" 15 #include "base/utf_string_conversions.h"
17 #include "googleurl/src/gurl.h" 16 #include "googleurl/src/gurl.h"
18 #include "net/base/mime_util.h" 17 #include "net/base/mime_util.h"
19 #include "webkit/glue/webkit_glue.h" 18 #include "webkit/glue/webkit_glue.h"
20 #include "webkit/plugins/npapi/plugin_constants_win.h" 19 #include "webkit/plugins/npapi/plugin_constants_win.h"
21 #include "webkit/plugins/npapi/plugin_lib.h" 20 #include "webkit/plugins/npapi/plugin_lib.h"
22 #include "webkit/plugins/plugin_switches.h" 21 #include "webkit/plugins/plugin_switches.h"
(...skipping 204 matching lines...) Expand 10 before | Expand all | Expand 10 after
227 void PluginList::RegisterInternalPlugin(const FilePath& filename, 226 void PluginList::RegisterInternalPlugin(const FilePath& filename,
228 const std::string& name, 227 const std::string& name,
229 const std::string& description, 228 const std::string& description,
230 const std::string& mime_type_str, 229 const std::string& mime_type_str,
231 const PluginEntryPoints& entry_points) { 230 const PluginEntryPoints& entry_points) {
232 InternalPlugin plugin; 231 InternalPlugin plugin;
233 plugin.info.path = filename; 232 plugin.info.path = filename;
234 plugin.info.name = ASCIIToUTF16(name); 233 plugin.info.name = ASCIIToUTF16(name);
235 plugin.info.version = ASCIIToUTF16("1"); 234 plugin.info.version = ASCIIToUTF16("1");
236 plugin.info.desc = ASCIIToUTF16(description); 235 plugin.info.desc = ASCIIToUTF16(description);
237 plugin.info.enabled = true; 236 plugin.info.enabled = WebPluginInfo::USER_ENABLED_POLICY_UNMANAGED;
238 237
239 WebPluginMimeType mime_type; 238 WebPluginMimeType mime_type;
240 mime_type.mime_type = mime_type_str; 239 mime_type.mime_type = mime_type_str;
241 plugin.info.mime_types.push_back(mime_type); 240 plugin.info.mime_types.push_back(mime_type);
242 241
243 plugin.entry_points = entry_points; 242 plugin.entry_points = entry_points;
244 243
245 base::AutoLock lock(lock_); 244 base::AutoLock lock(lock_);
246 internal_plugins_.push_back(plugin); 245 internal_plugins_.push_back(plugin);
247 } 246 }
(...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after
317 316
318 parsed_mime_types->push_back(mime_type); 317 parsed_mime_types->push_back(mime_type);
319 } 318 }
320 319
321 return true; 320 return true;
322 } 321 }
323 322
324 PluginList::PluginList() 323 PluginList::PluginList()
325 : plugins_loaded_(false), 324 : plugins_loaded_(false),
326 plugins_need_refresh_(false), 325 plugins_need_refresh_(false),
327 disable_outdated_plugins_(false), 326 disable_outdated_plugins_(false) {
328 next_priority_(0) {
329 PlatformInit(); 327 PlatformInit();
330 AddHardcodedPluginGroups(); 328 AddHardcodedPluginGroups();
331 } 329 }
332 330
333 bool PluginList::ShouldDisableGroup(const string16& group_name) { 331 void PluginList::LoadPluginsInternal(ScopedVector<PluginGroup>* plugin_groups) {
334 base::AutoLock lock(lock_);
335 if (PluginGroup::IsPluginNameDisabledByPolicy(group_name)) {
336 disabled_groups_.insert(group_name);
337 return true;
338 }
339 return disabled_groups_.count(group_name) > 0;
340 }
341
342 void PluginList::LoadPlugins(bool refresh) {
343 // Don't want to hold the lock while loading new plugins, so we don't block 332 // Don't want to hold the lock while loading new plugins, so we don't block
344 // other methods if they're called on other threads. 333 // other methods if they're called on other threads.
345 std::vector<FilePath> extra_plugin_paths; 334 std::vector<FilePath> extra_plugin_paths;
346 std::vector<FilePath> extra_plugin_dirs; 335 std::vector<FilePath> extra_plugin_dirs;
347 std::vector<InternalPlugin> internal_plugins; 336 std::vector<InternalPlugin> internal_plugins;
348 { 337 {
349 base::AutoLock lock(lock_); 338 base::AutoLock lock(lock_);
350 if (plugins_loaded_ && !refresh && !plugins_need_refresh_)
351 return;
352
353 // Clear the refresh bit now, because it might get set again before we 339 // Clear the refresh bit now, because it might get set again before we
354 // reach the end of the method. 340 // reach the end of the method.
355 plugins_need_refresh_ = false; 341 plugins_need_refresh_ = false;
356 extra_plugin_paths = extra_plugin_paths_; 342 extra_plugin_paths = extra_plugin_paths_;
357 extra_plugin_dirs = extra_plugin_dirs_; 343 extra_plugin_dirs = extra_plugin_dirs_;
358 internal_plugins = internal_plugins_; 344 internal_plugins = internal_plugins_;
359 } 345 }
360 346
361 std::vector<WebPluginInfo> new_plugins;
362 std::set<FilePath> visited_plugins; 347 std::set<FilePath> visited_plugins;
363 348
364 std::vector<FilePath> directories_to_scan; 349 std::vector<FilePath> directories_to_scan;
365 GetPluginDirectories(&directories_to_scan); 350 GetPluginDirectories(&directories_to_scan);
366 351
367 // Load internal plugins first so that, if both an internal plugin and a 352 // Load internal plugins first so that, if both an internal plugin and a
368 // "discovered" plugin want to handle the same type, the internal plugin 353 // "discovered" plugin want to handle the same type, the internal plugin
369 // will have precedence. 354 // will have precedence.
370 for (size_t i = 0; i < internal_plugins.size(); ++i) { 355 for (size_t i = 0; i < internal_plugins.size(); ++i) {
371 if (internal_plugins[i].info.path.value() == kDefaultPluginLibraryName) 356 if (internal_plugins[i].info.path.value() == kDefaultPluginLibraryName)
372 continue; 357 continue;
373 LoadPlugin(internal_plugins[i].info.path, &new_plugins); 358 LoadPlugin(internal_plugins[i].info.path, plugin_groups);
374 } 359 }
375 360
376 for (size_t i = 0; i < extra_plugin_paths.size(); ++i) { 361 for (size_t i = 0; i < extra_plugin_paths.size(); ++i) {
377 const FilePath& path = extra_plugin_paths[i]; 362 const FilePath& path = extra_plugin_paths[i];
378 if (visited_plugins.find(path) != visited_plugins.end()) 363 if (visited_plugins.find(path) != visited_plugins.end())
379 continue; 364 continue;
380 LoadPlugin(path, &new_plugins); 365 LoadPlugin(path, plugin_groups);
381 visited_plugins.insert(path); 366 visited_plugins.insert(path);
382 } 367 }
383 368
384 for (size_t i = 0; i < extra_plugin_dirs.size(); ++i) { 369 for (size_t i = 0; i < extra_plugin_dirs.size(); ++i) {
385 LoadPluginsFromDir(extra_plugin_dirs[i], &new_plugins, &visited_plugins); 370 LoadPluginsFromDir(
371 extra_plugin_dirs[i], plugin_groups, &visited_plugins);
386 } 372 }
387 373
388 for (size_t i = 0; i < directories_to_scan.size(); ++i) { 374 for (size_t i = 0; i < directories_to_scan.size(); ++i) {
389 LoadPluginsFromDir(directories_to_scan[i], &new_plugins, &visited_plugins); 375 LoadPluginsFromDir(
376 directories_to_scan[i], plugin_groups, &visited_plugins);
390 } 377 }
391 378
392 #if defined(OS_WIN) 379 #if defined(OS_WIN)
393 LoadPluginsFromRegistry(&new_plugins, &visited_plugins); 380 LoadPluginsFromRegistry(plugin_groups, &visited_plugins);
394 #endif 381 #endif
395 382
396 // Load the default plugin last. 383 // Load the default plugin last.
397 if (webkit_glue::IsDefaultPluginEnabled()) 384 if (webkit_glue::IsDefaultPluginEnabled())
398 LoadPlugin(FilePath(kDefaultPluginLibraryName), &new_plugins); 385 LoadPlugin(FilePath(kDefaultPluginLibraryName), plugin_groups);
386 }
399 387
388 void PluginList::LoadPlugins(bool refresh) {
389 {
390 base::AutoLock lock(lock_);
391 if (plugins_loaded_ && !refresh && !plugins_need_refresh_)
392 return;
393 }
394
395 ScopedVector<PluginGroup> new_plugin_groups;
396 // Do the actual loading of the plugins.
397 LoadPluginsInternal(&new_plugin_groups);
398
399 base::AutoLock lock(lock_);
400 // Grab all plugins that were found before to copy enabled statuses.
401 std::vector<WebPluginInfo> old_plugins;
402 for (size_t i = 0; i < plugin_groups_.size(); ++i) {
403 const std::vector<WebPluginInfo>& gr_plugins =
404 plugin_groups_[i]->web_plugins_info();
405 old_plugins.insert(old_plugins.end(), gr_plugins.begin(), gr_plugins.end());
406 }
400 // Disable all of the plugins and plugin groups that are disabled by policy. 407 // Disable all of the plugins and plugin groups that are disabled by policy.
401 // There's currenly a bug that makes it impossible to correctly re-enable 408 for (size_t i = 0; i < new_plugin_groups.size(); ++i) {
402 // plugins or plugin-groups to their original, "pre-policy" state, so 409 PluginGroup* group = new_plugin_groups[i];
403 // plugins and groups are only changed to a more "safe" state after a policy
404 // change, i.e. from enabled to disabled. See bug 54681.
405 for (PluginGroup::PluginMap::iterator it = plugin_groups_.begin();
406 it != plugin_groups_.end(); ++it) {
407 PluginGroup* group = it->second;
408 string16 group_name = group->GetGroupName(); 410 string16 group_name = group->GetGroupName();
409 if (ShouldDisableGroup(group_name)) { 411
410 group->Enable(false); 412 std::vector<WebPluginInfo>& gr_plugins = group->GetPluginsContainer();
413 for (size_t j = 0; j < gr_plugins.size(); ++j) {
414 int plugin_found = -1;
415 for (size_t k = 0; k < old_plugins.size(); ++k) {
416 if (gr_plugins[j].path == old_plugins[k].path) {
417 plugin_found = k;
418 break;
419 }
420 }
421 if (plugin_found >= 0)
422 gr_plugins[j].enabled = old_plugins[plugin_found].enabled;
423 // Set the disabled flag of all plugins scheduled for disabling.
424 if (plugins_to_disable_.find(gr_plugins[j].path) !=
425 plugins_to_disable_.end()) {
426 group->DisablePlugin(gr_plugins[j].path);
427 }
428 }
429 if (group->IsEmpty()) {
430 if (!group->Enabled())
431 groups_to_disable_.insert(group->GetGroupName());
432 new_plugin_groups.erase(new_plugin_groups.begin() + i);
433 --i;
434 continue;
411 } 435 }
412 436
413 if (disable_outdated_plugins_) { 437 group->EnforceGroupPolicy();
438 if (disable_outdated_plugins_)
414 group->DisableOutdatedPlugins(); 439 group->DisableOutdatedPlugins();
415 }
416 if (!group->Enabled()) {
417 base::AutoLock lock(lock_);
418 disabled_groups_.insert(group_name);
419 }
420 } 440 }
441 // We flush the list of prematurely disabled plugins after the load has
442 // finished. If for some reason a plugin reappears on a second load it is
443 // going to be loaded normally. This is only true for non-policy controlled
444 // plugins though.
445 plugins_to_disable_.clear();
421 446
422 // Only update the data now since loading plugins can take a while. 447 plugin_groups_.swap(new_plugin_groups);
423 base::AutoLock lock(lock_);
424
425 plugins_ = new_plugins;
426 plugins_loaded_ = true; 448 plugins_loaded_ = true;
427 } 449 }
428 450
429 void PluginList::LoadPlugin(const FilePath& path, 451 void PluginList::LoadPlugin(const FilePath& path,
430 std::vector<WebPluginInfo>* plugins) { 452 ScopedVector<PluginGroup>* plugin_groups) {
431 LOG_IF(ERROR, PluginList::DebugPluginLoading()) 453 LOG_IF(ERROR, PluginList::DebugPluginLoading())
432 << "Loading plugin " << path.value(); 454 << "Loading plugin " << path.value();
433
434 WebPluginInfo plugin_info; 455 WebPluginInfo plugin_info;
435 const PluginEntryPoints* entry_points; 456 const PluginEntryPoints* entry_points;
436 457
437 if (!ReadPluginInfo(path, &plugin_info, &entry_points)) 458 if (!ReadPluginInfo(path, &plugin_info, &entry_points))
438 return; 459 return;
439 460
440 if (!ShouldLoadPlugin(plugin_info, plugins)) 461 if (!ShouldLoadPlugin(plugin_info, plugin_groups))
441 return; 462 return;
442 463
443 if (path.value() != kDefaultPluginLibraryName 464 if (path.value() != kDefaultPluginLibraryName
444 #if defined(OS_WIN) && !defined(NDEBUG) 465 #if defined(OS_WIN) && !defined(NDEBUG)
445 && path.BaseName().value() != L"npspy.dll" // Make an exception for NPSPY 466 && path.BaseName().value() != L"npspy.dll" // Make an exception for NPSPY
446 #endif 467 #endif
447 ) { 468 ) {
448 for (size_t i = 0; i < plugin_info.mime_types.size(); ++i) { 469 for (size_t i = 0; i < plugin_info.mime_types.size(); ++i) {
449 // TODO: don't load global handlers for now. 470 // TODO: don't load global handlers for now.
450 // WebKit hands to the Plugin before it tries 471 // WebKit hands to the Plugin before it tries
451 // to handle mimeTypes on its own. 472 // to handle mimeTypes on its own.
452 const std::string &mime_type = plugin_info.mime_types[i].mime_type; 473 const std::string &mime_type = plugin_info.mime_types[i].mime_type;
453 if (mime_type == "*" ) 474 if (mime_type == "*" )
454 return; 475 return;
455 } 476 }
456 } 477 }
457 478
458 // Mark disabled plugins as such. (This has to happen before calling 479 AddToPluginGroups(plugin_info, plugin_groups);
459 // |AddToPluginGroups(plugin_info)|.)
460 if (disabled_plugins_.count(plugin_info.path)) {
461 plugin_info.enabled = false;
462 } else {
463 plugin_info.enabled = true;
464 }
465
466 base::AutoLock lock(lock_);
467 plugins->push_back(plugin_info);
468 AddToPluginGroups(plugin_info);
469 } 480 }
470 481
471 bool PluginList::SupportsType(const WebPluginInfo& info,
472 const std::string &mime_type,
473 bool allow_wildcard) {
474 // Webkit will ask for a plugin to handle empty mime types.
475 if (mime_type.empty())
476 return false;
477
478 for (size_t i = 0; i < info.mime_types.size(); ++i) {
479 const WebPluginMimeType& mime_info = info.mime_types[i];
480 if (net::MatchesMimeType(mime_info.mime_type, mime_type)) {
481 if (!allow_wildcard && mime_info.mime_type == "*") {
482 continue;
483 }
484 return true;
485 }
486 }
487 return false;
488 }
489
490 bool PluginList::SupportsExtension(const WebPluginInfo& info,
491 const std::string &extension,
492 std::string* actual_mime_type) {
493 for (size_t i = 0; i < info.mime_types.size(); ++i) {
494 const WebPluginMimeType& mime_type = info.mime_types[i];
495 for (size_t j = 0; j < mime_type.file_extensions.size(); ++j) {
496 if (mime_type.file_extensions[j] == extension) {
497 if (actual_mime_type)
498 *actual_mime_type = mime_type.mime_type;
499 return true;
500 }
501 }
502 }
503
504 return false;
505 }
506
507
508 void PluginList::GetPlugins(bool refresh, std::vector<WebPluginInfo>* plugins) { 482 void PluginList::GetPlugins(bool refresh, std::vector<WebPluginInfo>* plugins) {
509 LoadPlugins(refresh); 483 LoadPlugins(refresh);
510 484
511 base::AutoLock lock(lock_); 485 base::AutoLock lock(lock_);
512 *plugins = plugins_; 486 for (size_t i = 0; i < plugin_groups_.size(); ++i) {
487 const std::vector<WebPluginInfo>& gr_plugins =
488 plugin_groups_[i]->web_plugins_info();
489 plugins->insert(plugins->end(), gr_plugins.begin(), gr_plugins.end());
490 }
513 } 491 }
514 492
515 void PluginList::GetEnabledPlugins(bool refresh, 493 void PluginList::GetEnabledPlugins(bool refresh,
516 std::vector<WebPluginInfo>* plugins) { 494 std::vector<WebPluginInfo>* plugins) {
517 LoadPlugins(refresh); 495 LoadPlugins(refresh);
518 496
519 plugins->clear(); 497 plugins->clear();
520 base::AutoLock lock(lock_); 498 base::AutoLock lock(lock_);
521 for (std::vector<WebPluginInfo>::const_iterator it = plugins_.begin(); 499 for (size_t i = 0; i < plugin_groups_.size(); ++i) {
522 it != plugins_.end(); 500 const std::vector<WebPluginInfo>& gr_plugins =
523 ++it) { 501 plugin_groups_[i]->web_plugins_info();
524 if (it->enabled) 502 for (size_t i = 0; i < gr_plugins.size(); ++i) {
525 plugins->push_back(*it); 503 if (IsPluginEnabled(gr_plugins[i]))
504 plugins->push_back(gr_plugins[i]);
505 }
526 } 506 }
527 } 507 }
528 508
529 void PluginList::GetPluginInfoArray( 509 void PluginList::GetPluginInfoArray(
530 const GURL& url, 510 const GURL& url,
531 const std::string& mime_type, 511 const std::string& mime_type,
532 bool allow_wildcard, 512 bool allow_wildcard,
533 std::vector<WebPluginInfo>* info, 513 std::vector<WebPluginInfo>* info,
534 std::vector<std::string>* actual_mime_types) { 514 std::vector<std::string>* actual_mime_types) {
535 DCHECK(mime_type == StringToLowerASCII(mime_type)); 515 DCHECK(mime_type == StringToLowerASCII(mime_type));
536 DCHECK(info); 516 DCHECK(info);
537 517
538 LoadPlugins(false); 518 LoadPlugins(false);
539 base::AutoLock lock(lock_); 519 base::AutoLock lock(lock_);
540 info->clear(); 520 info->clear();
541 if (actual_mime_types) 521 if (actual_mime_types)
542 actual_mime_types->clear(); 522 actual_mime_types->clear();
543 523
544 std::set<FilePath> visited_plugins; 524 std::set<FilePath> visited_plugins;
545 525
546 // Add in enabled plugins by mime type. 526 // Add in enabled plugins by mime type.
547 WebPluginInfo default_plugin; 527 WebPluginInfo default_plugin;
548 for (size_t i = 0; i < plugins_.size(); ++i) { 528 for (size_t i = 0; i < plugin_groups_.size(); ++i) {
549 if (plugins_[i].enabled && 529 const std::vector<WebPluginInfo>& plugins =
550 SupportsType(plugins_[i], mime_type, allow_wildcard)) { 530 plugin_groups_[i]->web_plugins_info();
551 FilePath path = plugins_[i].path; 531 for (size_t i = 0; i < plugins.size(); ++i) {
552 if (path.value() != kDefaultPluginLibraryName && 532 if (IsPluginEnabled(plugins[i]) && SupportsType(plugins[i],
553 visited_plugins.insert(path).second) { 533 mime_type, allow_wildcard)) {
554 info->push_back(plugins_[i]); 534 FilePath path = plugins[i].path;
555 if (actual_mime_types) 535 if (path.value() != kDefaultPluginLibraryName &&
556 actual_mime_types->push_back(mime_type); 536 visited_plugins.insert(path).second) {
537 info->push_back(plugins[i]);
538 if (actual_mime_types)
539 actual_mime_types->push_back(mime_type);
540 }
557 } 541 }
558 } 542 }
559 } 543 }
560 544
561 // Add in enabled plugins by url. 545 // Add in enabled plugins by url.
562 std::string path = url.path(); 546 std::string path = url.path();
563 std::string::size_type last_dot = path.rfind('.'); 547 std::string::size_type last_dot = path.rfind('.');
564 if (last_dot != std::string::npos) { 548 if (last_dot != std::string::npos) {
565 std::string extension = StringToLowerASCII(std::string(path, last_dot+1)); 549 std::string extension = StringToLowerASCII(std::string(path, last_dot+1));
566 std::string actual_mime_type; 550 std::string actual_mime_type;
567 for (size_t i = 0; i < plugins_.size(); ++i) { 551 for (size_t i = 0; i < plugin_groups_.size(); ++i) {
568 if (plugins_[i].enabled && 552 const std::vector<WebPluginInfo>& plugins =
569 SupportsExtension(plugins_[i], extension, &actual_mime_type)) { 553 plugin_groups_[i]->web_plugins_info();
570 FilePath path = plugins_[i].path; 554 for (size_t i = 0; i < plugins.size(); ++i) {
571 if (path.value() != kDefaultPluginLibraryName && 555 if (IsPluginEnabled(plugins[i]) &&
572 visited_plugins.insert(path).second) { 556 SupportsExtension(plugins[i], extension, &actual_mime_type)) {
573 info->push_back(plugins_[i]); 557 FilePath path = plugins[i].path;
574 if (actual_mime_types) 558 if (path.value() != kDefaultPluginLibraryName &&
575 actual_mime_types->push_back(actual_mime_type); 559 visited_plugins.insert(path).second) {
560 info->push_back(plugins[i]);
561 if (actual_mime_types)
562 actual_mime_types->push_back(actual_mime_type);
563 }
576 } 564 }
577 } 565 }
578 } 566 }
579 } 567 }
580 568
581 // Add in disabled plugins by mime type. 569 // Add in disabled plugins by mime type.
582 for (size_t i = 0; i < plugins_.size(); ++i) { 570 for (size_t i = 0; i < plugin_groups_.size(); ++i) {
583 if (!plugins_[i].enabled && 571 const std::vector<WebPluginInfo>& plugins =
584 SupportsType(plugins_[i], mime_type, allow_wildcard)) { 572 plugin_groups_[i]->web_plugins_info();
585 FilePath path = plugins_[i].path; 573 for (size_t i = 0; i < plugins.size(); ++i) {
586 if (path.value() != kDefaultPluginLibraryName && 574 if (!IsPluginEnabled(plugins[i]) &&
587 visited_plugins.insert(path).second) { 575 SupportsType(plugins[i], mime_type, allow_wildcard)) {
588 info->push_back(plugins_[i]); 576 FilePath path = plugins[i].path;
589 if (actual_mime_types) 577 if (path.value() != kDefaultPluginLibraryName &&
590 actual_mime_types->push_back(mime_type); 578 visited_plugins.insert(path).second) {
579 info->push_back(plugins[i]);
580 if (actual_mime_types)
581 actual_mime_types->push_back(mime_type);
582 }
591 } 583 }
592 } 584 }
593 } 585 }
594 586
595 // Add the default plugin at the end if it supports the mime type given, 587 // Add the default plugin at the end if it supports the mime type given,
596 // and the default plugin is enabled. 588 // and the default plugin is enabled.
597 if (!plugins_.empty() && webkit_glue::IsDefaultPluginEnabled()) { 589 for (size_t i = 0; i < plugin_groups_.size(); ++i) {
598 const WebPluginInfo& default_info = plugins_.back(); 590 #if defined(OS_WIN)
599 if (SupportsType(default_info, mime_type, allow_wildcard)) { 591 if (plugin_groups_[i]->identifier().compare(
600 info->push_back(default_info); 592 WideToUTF8(kDefaultPluginLibraryName)) == 0) {
601 if (actual_mime_types) 593 #else
602 actual_mime_types->push_back(mime_type); 594 if (plugin_groups_[i]->identifier().compare(
595 kDefaultPluginLibraryName) == 0) {
596 #endif
597 DCHECK_NE(0U, plugin_groups_[i]->web_plugins_info().size());
598 const WebPluginInfo& default_info =
599 plugin_groups_[i]->web_plugins_info()[0];
600 if (SupportsType(default_info, mime_type, allow_wildcard)) {
601 info->push_back(default_info);
602 if (actual_mime_types)
603 actual_mime_types->push_back(mime_type);
604 }
603 } 605 }
604 } 606 }
605 } 607 }
606 608
607 bool PluginList::GetPluginInfo(const GURL& url, 609 bool PluginList::GetPluginInfo(const GURL& url,
608 const std::string& mime_type, 610 const std::string& mime_type,
609 bool allow_wildcard, 611 bool allow_wildcard,
610 WebPluginInfo* info, 612 WebPluginInfo* info,
611 std::string* actual_mime_type) { 613 std::string* actual_mime_type) {
612 DCHECK(info); 614 DCHECK(info);
(...skipping 17 matching lines...) Expand all
630 return true; 632 return true;
631 } 633 }
632 } 634 }
633 return false; 635 return false;
634 } 636 }
635 637
636 bool PluginList::GetPluginInfoByPath(const FilePath& plugin_path, 638 bool PluginList::GetPluginInfoByPath(const FilePath& plugin_path,
637 WebPluginInfo* info) { 639 WebPluginInfo* info) {
638 LoadPlugins(false); 640 LoadPlugins(false);
639 base::AutoLock lock(lock_); 641 base::AutoLock lock(lock_);
640 for (size_t i = 0; i < plugins_.size(); ++i) { 642 for (size_t i = 0; i < plugin_groups_.size(); ++i) {
641 if (plugins_[i].path == plugin_path) { 643 const std::vector<WebPluginInfo>& plugins =
642 *info = plugins_[i]; 644 plugin_groups_[i]->web_plugins_info();
643 return true; 645 for (size_t i = 0; i < plugins.size(); ++i) {
646 if (plugins[i].path == plugin_path) {
647 *info = plugins[i];
648 return true;
649 }
644 } 650 }
645 } 651 }
646 652
647 return false; 653 return false;
648 } 654 }
649 655
650 void PluginList::GetPluginGroups( 656 void PluginList::GetPluginGroups(
651 bool load_if_necessary, 657 bool load_if_necessary,
652 std::vector<PluginGroup>* plugin_groups) { 658 std::vector<PluginGroup>* plugin_groups) {
653 if (load_if_necessary) 659 if (load_if_necessary)
654 LoadPlugins(false); 660 LoadPlugins(false);
661 base::AutoLock lock(lock_);
655 plugin_groups->clear(); 662 plugin_groups->clear();
656 for (PluginGroup::PluginMap::const_iterator it = plugin_groups_.begin(); 663 for (size_t i = 0; i < plugin_groups_.size(); ++i) {
657 it != plugin_groups_.end(); ++it) { 664 // In some unit tests we can get confronted with empty groups but in real
658 if (!it->second->IsEmpty()) 665 // world code this if should never be false here.
659 plugin_groups->push_back(*it->second); 666 if (!plugin_groups_[i]->IsEmpty())
667 plugin_groups->push_back(*plugin_groups_[i]);
660 } 668 }
661 } 669 }
662 670
663 const PluginGroup* PluginList::GetPluginGroup( 671 const PluginGroup* PluginList::GetPluginGroup(
664 const WebPluginInfo& web_plugin_info) { 672 const WebPluginInfo& web_plugin_info) {
665 base::AutoLock lock(lock_); 673 base::AutoLock lock(lock_);
666 return AddToPluginGroups(web_plugin_info); 674 return AddToPluginGroups(web_plugin_info, &plugin_groups_);
667 } 675 }
668 676
669 string16 PluginList::GetPluginGroupName(std::string identifier) { 677 string16 PluginList::GetPluginGroupName(const std::string& identifier) {
670 PluginGroup::PluginMap::iterator it = plugin_groups_.find(identifier); 678 for (size_t i = 0; i < plugin_groups_.size(); ++i) {
671 if (it == plugin_groups_.end()) { 679 if (plugin_groups_[i]->identifier() == identifier)
672 return string16(); 680 return plugin_groups_[i]->GetGroupName();
673 } 681 }
674 return it->second->GetGroupName(); 682 return string16();
675 } 683 }
676 684
677 std::string PluginList::GetPluginGroupIdentifier( 685 std::string PluginList::GetPluginGroupIdentifier(
678 const WebPluginInfo& web_plugin_info) { 686 const WebPluginInfo& web_plugin_info) {
679 base::AutoLock lock(lock_); 687 base::AutoLock lock(lock_);
680 PluginGroup* group = AddToPluginGroups(web_plugin_info); 688 PluginGroup* group = AddToPluginGroups(web_plugin_info, &plugin_groups_);
681 return group->identifier(); 689 return group->identifier();
682 } 690 }
683 691
684 void PluginList::AddHardcodedPluginGroups() { 692 void PluginList::AddHardcodedPluginGroups() {
685 base::AutoLock lock(lock_); 693 base::AutoLock lock(lock_);
686 const PluginGroupDefinition* definitions = GetPluginGroupDefinitions(); 694 const PluginGroupDefinition* definitions = GetPluginGroupDefinitions();
687 for (size_t i = 0; i < GetPluginGroupDefinitionsSize(); ++i) { 695 for (size_t i = 0; i < GetPluginGroupDefinitionsSize(); ++i) {
688 PluginGroup* definition_group = PluginGroup::FromPluginGroupDefinition( 696 PluginGroup* definition_group = PluginGroup::FromPluginGroupDefinition(
689 definitions[i]); 697 definitions[i]);
690 std::string identifier = definition_group->identifier(); 698 plugin_groups_.push_back(definition_group);
691 DCHECK(plugin_groups_.find(identifier) == plugin_groups_.end());
692 plugin_groups_.insert(std::make_pair(identifier, definition_group));
693 } 699 }
694 } 700 }
695 701
696 PluginGroup* PluginList::AddToPluginGroups( 702 PluginGroup* PluginList::AddToPluginGroups(
697 const WebPluginInfo& web_plugin_info) { 703 const WebPluginInfo& web_plugin_info,
704 ScopedVector<PluginGroup>* plugin_groups) {
698 PluginGroup* group = NULL; 705 PluginGroup* group = NULL;
699 for (PluginGroup::PluginMap::iterator it = plugin_groups_.begin(); 706 for (size_t i = 0; i < plugin_groups->size(); ++i) {
700 it != plugin_groups_.end(); ++it) { 707 if ((*plugin_groups)[i]->Match(web_plugin_info)) {
701 if (it->second->Match(web_plugin_info)) 708 group = (*plugin_groups)[i];
702 group = it->second; 709 break;
710 }
703 } 711 }
704 if (!group) { 712 if (!group) {
705 group = PluginGroup::FromWebPluginInfo(web_plugin_info); 713 group = PluginGroup::FromWebPluginInfo(web_plugin_info);
714 // If group is scheduled for disabling do that now and remove it from the
715 // list.
716 if (groups_to_disable_.find(group->GetGroupName()) !=
717 groups_to_disable_.end()) {
718 group->EnableGroup(false);
719 groups_to_disable_.erase(group->GetGroupName());
720 }
706 std::string identifier = group->identifier(); 721 std::string identifier = group->identifier();
707 // If the identifier is not unique, use the full path. This means that we 722 // If the identifier is not unique, use the full path. This means that we
708 // probably won't be able to search for this group by identifier, but at 723 // probably won't be able to search for this group by identifier, but at
709 // least it's going to be in the set of plugin groups, and if there 724 // least it's going to be in the set of plugin groups, and if there
710 // is already a plug-in with the same filename, it's probably going to 725 // is already a plug-in with the same filename, it's probably going to
711 // handle the same MIME types (and it has a higher priority), so this one 726 // handle the same MIME types (and it has a higher priority), so this one
712 // is not going to run anyway. 727 // is not going to run anyway.
713 if (plugin_groups_.find(identifier) != plugin_groups_.end()) 728 for (size_t i = 0; i < plugin_groups->size(); ++i) {
714 identifier = PluginGroup::GetLongIdentifier(web_plugin_info); 729 if ((*plugin_groups)[i]->identifier() == identifier) {
715 DCHECK(plugin_groups_.find(identifier) == plugin_groups_.end()); 730 group->set_identifier(PluginGroup::GetLongIdentifier(web_plugin_info));
716 plugin_groups_.insert(std::make_pair(identifier, group)); 731 break;
732 }
733 }
734 plugin_groups->push_back(group);
717 } 735 }
718 group->AddPlugin(web_plugin_info, next_priority_++); 736 group->AddPlugin(web_plugin_info);
719 return group; 737 return group;
720 } 738 }
721 739
722 bool PluginList::EnablePlugin(const FilePath& filename) { 740 bool PluginList::EnablePlugin(const FilePath& filename) {
723 base::AutoLock lock(lock_); 741 base::AutoLock lock(lock_);
724 742 for (size_t i = 0; i < plugin_groups_.size(); ++i) {
725 bool did_enable = false; 743 if (plugin_groups_[i]->ContainsPlugin(filename))
726 744 return plugin_groups_[i]->EnablePlugin(filename);
727 std::set<FilePath>::iterator entry = disabled_plugins_.find(filename);
728 if (entry == disabled_plugins_.end())
729 return did_enable; // Early exit if plugin not in disabled list.
730
731 disabled_plugins_.erase(entry); // Remove from disabled list.
732
733 // Set enabled flags if necessary.
734 for (std::vector<WebPluginInfo>::iterator it = plugins_.begin();
735 it != plugins_.end();
736 ++it) {
737 if (it->path == filename) {
738 DCHECK(!it->enabled); // Should have been disabled.
739 it->enabled = true;
740 did_enable = true;
741 }
742 } 745 }
743 746 // Non existing plugin is being enabled. Check if it has been disabled before
744 return did_enable; 747 // and remove it.
748 return (plugins_to_disable_.erase(filename) != 0);
745 } 749 }
746 750
747 bool PluginList::DisablePlugin(const FilePath& filename) { 751 bool PluginList::DisablePlugin(const FilePath& filename) {
748 base::AutoLock lock(lock_); 752 base::AutoLock lock(lock_);
753 for (size_t i = 0; i < plugin_groups_.size(); ++i) {
754 if (plugin_groups_[i]->ContainsPlugin(filename))
755 return plugin_groups_[i]->DisablePlugin(filename);
756 }
757 // Non existing plugin is being disabled. Queue the plugin so that on the next
758 // load plugins call they will be disabled.
759 // Check if we already have this one to avoid double inclusion.
760 plugins_to_disable_.insert(filename);
761 return true;
762 }
749 763
750 bool did_disable = false; 764 bool PluginList::EnableGroup(bool enable, const string16& group_name) {
751 765 base::AutoLock lock(lock_);
752 if (disabled_plugins_.find(filename) != disabled_plugins_.end()) 766 PluginGroup* group = NULL;
753 return did_disable; // Early exit if plugin already in disabled list. 767 for (size_t i = 0; i < plugin_groups_.size(); ++i) {
754 768 if (plugin_groups_[i]->GetGroupName().find(group_name) != string16::npos) {
755 disabled_plugins_.insert(filename); // Add to disabled list. 769 group = plugin_groups_[i];
756 770 break;
757 // Unset enabled flags if necessary. 771 }
758 for (std::vector<WebPluginInfo>::iterator it = plugins_.begin(); 772 }
759 it != plugins_.end(); 773 if (!group) {
760 ++it) { 774 // Non existing group is being enabled. Queue the group so that on the next
761 if (it->path == filename) { 775 // load plugins call they will be disabled.
762 DCHECK(it->enabled); // Should have been enabled. 776 if (!enable) {
763 it->enabled = false; 777 groups_to_disable_.insert(group_name);
764 did_disable = true; 778 return true;
779 } else {
780 return (groups_to_disable_.erase(group_name) != 0);
765 } 781 }
766 } 782 }
767 783
768 return did_disable; 784 return group->EnableGroup(enable);
769 } 785 }
770 786
771 bool PluginList::EnableGroup(bool enable, const string16& group_name) { 787 bool PluginList::SupportsType(const WebPluginInfo& plugin,
772 bool did_change = false; 788 const std::string& mime_type,
773 { 789 bool allow_wildcard) {
774 base::AutoLock lock(lock_); 790 // Webkit will ask for a plugin to handle empty mime types.
791 if (mime_type.empty())
792 return false;
775 793
776 std::set<string16>::iterator entry = disabled_groups_.find(group_name); 794 for (size_t i = 0; i < plugin.mime_types.size(); ++i) {
777 if (enable) { 795 const WebPluginMimeType& mime_info = plugin.mime_types[i];
778 if (entry == disabled_groups_.end()) 796 if (net::MatchesMimeType(mime_info.mime_type, mime_type)) {
779 return did_change; // Early exit if group not in disabled list. 797 if (!allow_wildcard && mime_info.mime_type == "*")
780 disabled_groups_.erase(entry); // Remove from disabled list. 798 continue;
781 } else { 799 return true;
782 if (entry != disabled_groups_.end())
783 return did_change; // Early exit if group already in disabled list.
784 disabled_groups_.insert(group_name);
785 } 800 }
786 } 801 }
802 return false;
803 }
787 804
788 for (PluginGroup::PluginMap::iterator it = plugin_groups_.begin(); 805 bool PluginList::SupportsExtension(const WebPluginInfo& plugin,
789 it != plugin_groups_.end(); ++it) { 806 const std::string& extension,
790 if (it->second->GetGroupName() == group_name) { 807 std::string* actual_mime_type) {
791 if (it->second->Enabled() != enable) { 808 for (size_t i = 0; i < plugin.mime_types.size(); ++i) {
792 it->second->Enable(enable); 809 const WebPluginMimeType& mime_type = plugin.mime_types[i];
793 did_change = true; 810 for (size_t j = 0; j < mime_type.file_extensions.size(); ++j) {
794 break; 811 if (mime_type.file_extensions[j] == extension) {
812 if (actual_mime_type)
813 *actual_mime_type = mime_type.mime_type;
814 return true;
795 } 815 }
796 } 816 }
797 } 817 }
798 818 return false;
799 return did_change;
800 } 819 }
801 820
802 void PluginList::DisableOutdatedPluginGroups() { 821 void PluginList::DisableOutdatedPluginGroups() {
803 disable_outdated_plugins_ = true; 822 disable_outdated_plugins_ = true;
804 } 823 }
805 824
806 PluginList::~PluginList() { 825 PluginList::~PluginList() {
807 Shutdown();
808 } 826 }
809 827
810 void PluginList::Shutdown() {
811 STLDeleteContainerPairSecondPointers(plugin_groups_.begin(),
812 plugin_groups_.end());
813 }
814 828
815 } // namespace npapi 829 } // namespace npapi
816 } // namespace webkit 830 } // namespace webkit
OLDNEW
« no previous file with comments | « webkit/plugins/npapi/plugin_list.h ('k') | webkit/plugins/npapi/plugin_list_mac.mm » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698