425 } |
463 } |
426 } |
464 } |
427 |
465 |
428 #endif // !OS(SYMBIAN) && !OS(WINDOWS) |
466 #endif // !OS(SYMBIAN) && !OS(WINDOWS) |
429 |
467 |
430 } |
468 #if ENABLE(NETSCAPE_PLUGIN_METADATA_CACHE) |
|
469 |
|
470 static void fillBufferWithContentsOfFile(PlatformFileHandle file, Vector<char>& buffer) |
|
471 { |
|
472 size_t bufferSize = 0; |
|
473 size_t bufferCapacity = 1024; |
|
474 buffer.resize(bufferCapacity); |
|
475 |
|
476 do { |
|
477 bufferSize += readFromFile(file, buffer.data() + bufferSize, bufferCapacity - bufferSize); |
|
478 if (bufferSize == bufferCapacity) { |
|
479 if (bufferCapacity < maximumPersistentPluginMetadataCacheSize) { |
|
480 bufferCapacity *= 2; |
|
481 buffer.resize(bufferCapacity); |
|
482 } else { |
|
483 buffer.clear(); |
|
484 return; |
|
485 } |
|
486 } else |
|
487 break; |
|
488 } while (true); |
|
489 |
|
490 buffer.shrink(bufferSize); |
|
491 } |
|
492 |
|
493 static bool readUTF8String(String& resultString, char*& start, const char* end) |
|
494 { |
|
495 if (start >= end) |
|
496 return false; |
|
497 |
|
498 int len = strlen(start); |
|
499 resultString = String::fromUTF8(start, len); |
|
500 start += len + 1; |
|
501 |
|
502 return true; |
|
503 } |
|
504 |
|
505 static bool readTime(time_t& resultTime, char*& start, const char* end) |
|
506 { |
|
507 if (start + sizeof(time_t) >= end) |
|
508 return false; |
|
509 |
|
510 resultTime = *reinterpret_cast<time_t*>(start); |
|
511 start += sizeof(time_t); |
|
512 |
|
513 return true; |
|
514 } |
|
515 |
|
516 static const char schemaVersion = '1'; |
|
517 static const char persistentPluginMetadataCacheFilename[] = "PluginMetadataCache.bin"; |
|
518 |
|
519 void PluginDatabase::loadPersistentMetadataCache() |
|
520 { |
|
521 if (!isPersistentMetadataCacheEnabled() || persistentMetadataCachePath().isEmpty()) |
|
522 return; |
|
523 |
|
524 PlatformFileHandle file; |
|
525 String absoluteCachePath = pathByAppendingComponent(persistentMetadataCachePath(), persistentPluginMetadataCacheFilename); |
|
526 file = openFile(absoluteCachePath, OpenForRead); |
|
527 |
|
528 if (!isHandleValid(file)) |
|
529 return; |
|
530 |
|
531 // Mark cache as loaded regardless of success or failure. If |
|
532 // there's error in the cache, we won't try to load it anymore. |
|
533 m_persistentMetadataCacheIsLoaded = true; |
|
534 |
|
535 Vector<char> fileContents; |
|
536 fillBufferWithContentsOfFile(file, fileContents); |
|
537 closeFile(file); |
|
538 |
|
539 if (fileContents.size() < 2 || fileContents.first() != schemaVersion || fileContents.last() != '\0') { |
|
540 LOG_ERROR("Unable to read plugin metadata cache: corrupt schema"); |
|
541 deleteFile(absoluteCachePath); |
|
542 return; |
|
543 } |
|
544 |
|
545 char* bufferPos = fileContents.data() + 1; |
|
546 char* end = fileContents.data() + fileContents.size(); |
|
547 |
|
548 PluginSet cachedPlugins; |
|
549 HashMap<String, time_t> cachedPluginPathsWithTimes; |
|
550 HashMap<String, RefPtr<PluginPackage> > cachedPluginsByPath; |
|
551 |
|
552 while (bufferPos < end) { |
|
553 String path; |
|
554 time_t lastModified; |
|
555 String name; |
|
556 String desc; |
|
557 String mimeDesc; |
|
558 if (!(readUTF8String(path, bufferPos, end) |
|
559 && readTime(lastModified, bufferPos, end) |
|
560 && readUTF8String(name, bufferPos, end) |
|
561 && readUTF8String(desc, bufferPos, end) |
|
562 && readUTF8String(mimeDesc, bufferPos, end))) { |
|
563 LOG_ERROR("Unable to read plugin metadata cache: corrupt data"); |
|
564 deleteFile(absoluteCachePath); |
|
565 return; |
|
566 } |
|
567 |
|
568 // Skip metadata that points to plugins from directories that |
|
569 // are not part of plugin directory list anymore. |
|
570 String pluginDirectoryName = directoryName(path); |
|
571 if (m_pluginDirectories.find(pluginDirectoryName) == WTF::notFound) |
|
572 continue; |
|
573 |
|
574 RefPtr<PluginPackage> package = PluginPackage::createPackageFromCache(path, lastModified, name, desc, mimeDesc); |
|
575 |
|
576 if (package && cachedPlugins.add(package).second) { |
|
577 cachedPluginPathsWithTimes.add(package->path(), package->lastModified()); |
|
578 cachedPluginsByPath.add(package->path(), package); |
|
579 } |
|
580 } |
|
581 |
|
582 m_plugins.swap(cachedPlugins); |
|
583 m_pluginsByPath.swap(cachedPluginsByPath); |
|
584 m_pluginPathsWithTimes.swap(cachedPluginPathsWithTimes); |
|
585 } |
|
586 |
|
587 static bool writeUTF8String(PlatformFileHandle file, const String& string) |
|
588 { |
|
589 CString utf8String = string.utf8(); |
|
590 int length = utf8String.length() + 1; |
|
591 return writeToFile(file, utf8String.data(), length) == length; |
|
592 } |
|
593 |
|
594 static bool writeTime(PlatformFileHandle file, const time_t& time) |
|
595 { |
|
596 return writeToFile(file, reinterpret_cast<const char*>(&time), sizeof(time_t)) == sizeof(time_t); |
|
597 } |
|
598 |
|
599 void PluginDatabase::updatePersistentMetadataCache() |
|
600 { |
|
601 if (!isPersistentMetadataCacheEnabled() || persistentMetadataCachePath().isEmpty()) |
|
602 return; |
|
603 |
|
604 makeAllDirectories(persistentMetadataCachePath()); |
|
605 String absoluteCachePath = pathByAppendingComponent(persistentMetadataCachePath(), persistentPluginMetadataCacheFilename); |
|
606 deleteFile(absoluteCachePath); |
|
607 |
|
608 if (m_plugins.isEmpty()) |
|
609 return; |
|
610 |
|
611 PlatformFileHandle file; |
|
612 file = openFile(absoluteCachePath, OpenForWrite); |
|
613 |
|
614 if (!isHandleValid(file)) { |
|
615 LOG_ERROR("Unable to open plugin metadata cache for saving"); |
|
616 return; |
|
617 } |
|
618 |
|
619 char localSchemaVersion = schemaVersion; |
|
620 if (writeToFile(file, &localSchemaVersion, 1) != 1) { |
|
621 LOG_ERROR("Unable to write plugin metadata cache schema"); |
|
622 closeFile(file); |
|
623 deleteFile(absoluteCachePath); |
|
624 return; |
|
625 } |
|
626 |
|
627 PluginSet::const_iterator end = m_plugins.end(); |
|
628 for (PluginSet::const_iterator it = m_plugins.begin(); it != end; ++it) { |
|
629 if (!(writeUTF8String(file, (*it)->path()) |
|
630 && writeTime(file, (*it)->lastModified()) |
|
631 && writeUTF8String(file, (*it)->name()) |
|
632 && writeUTF8String(file, (*it)->description()) |
|
633 && writeUTF8String(file, (*it)->fullMIMEDescription()))) { |
|
634 LOG_ERROR("Unable to write plugin metadata to cache"); |
|
635 closeFile(file); |
|
636 deleteFile(absoluteCachePath); |
|
637 return; |
|
638 } |
|
639 } |
|
640 |
|
641 closeFile(file); |
|
642 } |
|
643 |
|
644 bool PluginDatabase::isPersistentMetadataCacheEnabled() |
|
645 { |
|
646 return gPersistentPluginMetadataCacheIsEnabled; |
|
647 } |
|
648 |
|
649 void PluginDatabase::setPersistentMetadataCacheEnabled(bool isEnabled) |
|
650 { |
|
651 gPersistentPluginMetadataCacheIsEnabled = isEnabled; |
|
652 } |
|
653 |
|
654 String PluginDatabase::persistentMetadataCachePath() |
|
655 { |
|
656 return WebCore::persistentPluginMetadataCachePath(); |
|
657 } |
|
658 |
|
659 void PluginDatabase::setPersistentMetadataCachePath(const String& persistentMetadataCachePath) |
|
660 { |
|
661 WebCore::persistentPluginMetadataCachePath() = persistentMetadataCachePath; |
|
662 } |
|
663 #endif |
|
664 } |