blob: 7f6de83fc12fc15c39e34d5f4a5baf61000282e5 [file] [log] [blame]
// Copyright 2016 The Goma 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 "lib/path_util.h"
#include <cctype>
#include "absl/strings/match.h"
#include "absl/strings/string_view.h"
namespace devtools_goma {
bool IsPosixAbsolutePath(absl::string_view path) {
return !path.empty() && path[0] == '/';
}
bool IsWindowsAbsolutePath(absl::string_view path) {
// UNC
if (path.size() > 3 && path[0] == '\\' && path[1] == '\\' &&
path.find('\\', 3) != absl::string_view::npos &&
path.find('/', 3) == absl::string_view::npos) {
return true;
}
// local path.
if (path.size() > 2 && std::isalpha(path[0]) && path[1] == ':' &&
(path[2] == '/' || path[2] == '\\')) {
return true;
}
return false;
}
bool HasPrefixDir(absl::string_view path, absl::string_view prefix) {
#ifdef _WIN32
return HasPrefixDirWithSep(path, prefix, '\\') ||
HasPrefixDirWithSep(path, prefix, '/');
#else
return HasPrefixDirWithSep(path, prefix, '/');
#endif
}
bool HasPrefixDirWithSep(absl::string_view path, absl::string_view prefix,
char pathsep) {
// TODO: do we need to convert path before check on Win path?
// 1. need to make both lower case?
if (!absl::StartsWith(path, prefix)) {
return false;
}
if (path.size() == prefix.size()) {
return true;
}
return path[prefix.size()] == pathsep;
}
absl::string_view GetDirname(absl::string_view filename) {
absl::string_view::size_type last_sep = filename.find_last_of("/\\");
if (last_sep == absl::string_view::npos) {
// Handle the case <drive letter>:
if (filename.size() >= 2 && filename[1] == ':') {
return filename.substr(0, 2);
}
return filename.substr(0, 0);
}
// Handle the case '/'.
if (last_sep == 0) {
return filename.substr(0, 1);
}
// Handle the case <drive letter>:/<something>.
if (last_sep == 2 && filename[1] == ':') {
return filename.substr(0, 3);
}
return filename.substr(0, last_sep);
}
absl::string_view GetBasename(absl::string_view filename) {
absl::string_view::size_type last_sep = filename.find_last_of("/\\");
if (last_sep != absl::string_view::npos) {
filename.remove_prefix(last_sep + 1);
}
return filename;
}
absl::string_view GetExtension(absl::string_view filename) {
filename = GetBasename(filename);
absl::string_view::size_type last_dot = filename.rfind('.');
// Note: .config file should not be path extension.
if (last_dot == absl::string_view::npos || last_dot == 0U) {
return absl::ClippedSubstr(filename, filename.size(), 0);
}
return absl::ClippedSubstr(filename, last_dot + 1);
}
absl::string_view GetStem(absl::string_view filename) {
filename = GetBasename(filename);
absl::string_view::size_type last_dot = filename.rfind('.');
// Note: .config file should not be path extension.
if (last_dot == absl::string_view::npos || last_dot == 0U) {
return filename;
}
return filename.substr(0, last_dot);
}
} // namespace devtools_goma