Skip to content

Commit a386425

Browse files
committed
Converting absolute paths to relative on client side
1 parent b492412 commit a386425

File tree

6 files changed

+107
-1
lines changed

6 files changed

+107
-1
lines changed

dist-clang.files

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2283,6 +2283,8 @@ src/client/clean_command.hh
22832283
src/client/command.cc
22842284
src/client/command.hh
22852285
src/client/command_test.cc
2286+
src/client/configuration.cc
2287+
src/client/configuration.hh
22862288
src/client/configuration.proto
22872289
src/client/driver_command.cc
22882290
src/client/driver_command.hh

src/base/file_utils.h

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
#pragma once
22

33
#include <base/c_utils.h>
4+
#include <base/string_utils.h>
45

56
#include <stdio.h>
67

@@ -66,5 +67,20 @@ inline Path GetCurrentDir(String* error = nullptr) {
6667
return current_dir;
6768
}
6869

70+
class ScopedCurrentDir {
71+
public:
72+
explicit ScopedCurrentDir(const Path& path): initial_dir_(GetCurrentDir()) {
73+
ChangeCurrentDir(path);
74+
}
75+
~ScopedCurrentDir() {
76+
ChangeCurrentDir(initial_dir_);
77+
}
78+
private:
79+
const Path initial_dir_;
80+
};
81+
82+
83+
String GetRelativePath(const String& current_dir, const String& path);
84+
6985
} // namespace base
7086
} // namespace dist_clang

src/base/file_utils_posix.cc

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -95,5 +95,32 @@ Pair<time_t> GetModificationTime(const String& path, String* error) {
9595
return {time_spec.tv_sec, time_spec.tv_nsec};
9696
}
9797

98+
String GetRelativePath(const String& current_dir, const String& path) {
99+
List<String> current_dir_parts, path_parts;
100+
base::SplitString<'/'>(current_dir, current_dir_parts);
101+
base::SplitString<'/'>(path, path_parts);
102+
103+
auto current_dir_part = current_dir_parts.begin();
104+
auto path_part = path_parts.begin();
105+
while (current_dir_part != current_dir_parts.end() &&
106+
path_part != path_parts.end() &&
107+
*current_dir_part == *path_part) {
108+
++current_dir_part;
109+
++path_part;
110+
}
111+
112+
String result(".");
113+
while (current_dir_part != current_dir_parts.end()) {
114+
result += "/..";
115+
++current_dir_part;
116+
}
117+
118+
while (path_part != path_parts.end()) {
119+
result += "/" + *path_part;
120+
++path_part;
121+
}
122+
return result;
123+
}
124+
98125
} // namespace base
99126
} // namespace dist_clang

src/base/file_utils_test.cc

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -71,5 +71,16 @@ TEST(FileUtilsTest, CreateDirectory) {
7171
}
7272
}
7373

74+
TEST(FileUtilsTest, GetRelativeDirectory) {
75+
const String cur_dir = "/path/to/current/dir";
76+
EXPECT_EQ("./and/more",
77+
base::GetRelativePath(cur_dir, "/path/to/current/dir/and/more"));
78+
EXPECT_EQ("./../../other/dir",
79+
base::GetRelativePath(cur_dir, "/path/to/other/dir"));
80+
EXPECT_EQ("./../../../../absolute/path/to/other/dir",
81+
base::GetRelativePath(cur_dir, "/absolute/path/to/other/dir"));
82+
EXPECT_EQ("./.", base::GetRelativePath("/", "."));
83+
}
84+
7485
} // namespace base
7586
} // namespace dist_clang

src/client/clang_command.cc

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
#include <base/assert.h>
44
#include <base/base.pb.h>
55
#include <base/c_utils.h>
6+
#include <base/file_utils.h>
67
#include <base/logging.h>
78
#include <base/process_impl.h>
89

@@ -64,6 +65,8 @@ bool ClangCommand::FillFlags(base::proto::Flags* flags,
6465
return true;
6566
}
6667

68+
const String current_dir = base::GetCurrentDir();
69+
6770
flags->Clear();
6871

6972
llvm::opt::ArgStringList non_direct_list, non_cached_list, other_list;
@@ -158,8 +161,10 @@ bool ClangCommand::FillFlags(base::proto::Flags* flags,
158161
replaced_command.replace(
159162
pos, self_path.size(),
160163
clang_path.substr(0, clang_path.find_last_of('/')));
164+
const String relative_command =
165+
base::GetRelativePath(current_dir, replaced_command);
161166
non_direct_list.push_back(arg->getSpelling().data());
162-
non_direct_list.push_back(tmp_list.MakeArgString(replaced_command));
167+
non_direct_list.push_back(tmp_list.MakeArgString(relative_command));
163168
LOG(VERBOSE) << "Replaced command: " << non_direct_list.back();
164169
} else {
165170
non_cached_list.push_back(arg->getSpelling().data());

src/client/command_test.cc

Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -264,6 +264,51 @@ TEST(CommandTest, FillFlagsAppendsRewriteIncludes) {
264264
}
265265
}
266266

267+
TEST(CommandTest, RelativeResourceDir) {
268+
String self_path = base::GetCurrentDir();
269+
ASSERT_TRUE(base::GetSelfPath(self_path));
270+
const String input = "/test_file.cc";
271+
const String output = "/tmp/output.o";
272+
const String clang_path = self_path + "/path/to/llvm-build/bin/clang";
273+
const String resource_dir = self_path + "/../lib/1.0.0";
274+
const char* argv[] = {"clang++",
275+
"-Xclang",
276+
"-resource-dir",
277+
"-Xclang",
278+
resource_dir.c_str(),
279+
"-c",
280+
input.c_str(),
281+
"-o",
282+
output.c_str(),
283+
nullptr};
284+
const int argc = 9;
285+
286+
base::ScopedCurrentDir tests_binary_dir(std::move(self_path));
287+
288+
Command::List commands;
289+
ASSERT_TRUE(Command::GenerateFromArgs(argc, argv, commands));
290+
ASSERT_EQ(1u, commands.size());
291+
292+
auto& command = commands.front();
293+
base::proto::Flags flags;
294+
ASSERT_TRUE(command->CanFillFlags());
295+
ASSERT_TRUE(command->FillFlags(&flags, clang_path, "1.0.0", false));
296+
297+
EXPECT_EQ(input, flags.input());
298+
EXPECT_EQ(output, flags.output());
299+
EXPECT_EQ("-emit-obj", flags.action());
300+
EXPECT_EQ("c++", flags.language());
301+
EXPECT_EQ("-cc1", *flags.other().begin());
302+
303+
EXPECT_NE(flags.non_direct().end(),
304+
std::find(flags.non_direct().begin(), flags.non_direct().end(),
305+
"./path/to/llvm-build/bin/../lib/1.0.0"));
306+
307+
if (HasNonfatalFailure()) {
308+
FAIL() << command->RenderAllArgs();
309+
}
310+
}
311+
267312
TEST(CommandTest, AppendCleanTempFilesCommand) {
268313
const String temp_input = base::CreateTempFile(".cc");
269314
const char* argv[] = {"clang++", temp_input.c_str(), nullptr};

0 commit comments

Comments
 (0)