// Copyright 2014 The Chromium Authors. All rights reserved. // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. #include "net/base/filename_util.h" #include "base/bind.h" #include "base/files/file_path.h" #include "base/i18n/file_util_icu.h" #include "base/strings/string16.h" #include "net/base/filename_util_internal.h" class GURL; namespace net { bool IsSafePortablePathComponent(const base::FilePath& component) { base::string16 component16; base::FilePath::StringType sanitized = component.value(); SanitizeGeneratedFileName(&sanitized, true); base::FilePath::StringType extension = component.Extension(); if (!extension.empty()) extension.erase(extension.begin()); // Erase preceding '.'. return !component.empty() && (component == component.BaseName()) && (component == component.StripTrailingSeparators()) && FilePathToString16(component, &component16) && base::i18n::IsFilenameLegal(component16) && !IsShellIntegratedExtension(extension) && (sanitized == component.value()) && !IsReservedName(component.value()); } bool IsSafePortableRelativePath(const base::FilePath& path) { if (path.empty() || path.IsAbsolute() || path.EndsWithSeparator()) return false; std::vector components; path.GetComponents(&components); if (components.empty()) return false; for (size_t i = 0; i < components.size() - 1; ++i) { if (!IsSafePortablePathComponent(base::FilePath(components[i]))) return false; } return IsSafePortablePathComponent(path.BaseName()); } base::string16 GetSuggestedFilename(const GURL& url, const std::string& content_disposition, const std::string& referrer_charset, const std::string& suggested_name, const std::string& mime_type, const std::string& default_name) { return GetSuggestedFilenameImpl( url, content_disposition, referrer_charset, suggested_name, mime_type, default_name, base::Bind(&base::i18n::ReplaceIllegalCharactersInPath)); } base::FilePath GenerateFileName(const GURL& url, const std::string& content_disposition, const std::string& referrer_charset, const std::string& suggested_name, const std::string& mime_type, const std::string& default_file_name) { base::FilePath generated_name(GenerateFileNameImpl( url, content_disposition, referrer_charset, suggested_name, mime_type, default_file_name, base::Bind(&base::i18n::ReplaceIllegalCharactersInPath))); #if defined(OS_CHROMEOS) // When doing file manager operations on ChromeOS, the file paths get // normalized in WebKit layer, so let's ensure downloaded files have // normalized names. Otherwise, we won't be able to handle files with NFD // utf8 encoded characters in name. base::i18n::NormalizeFileNameEncoding(&generated_name); #endif DCHECK(!generated_name.empty()); return generated_name; } } // namespace net