Make sure TempFilePath always generate unique file path
Previously it is possible that the same file path is generated when the function is called consecutively in the same thread. The problem can be re-produced in Windows. Does not seem to be re-producible in Linux and Mac. Fixes #448, #449. Change-Id: Ia0163492e3494eba00f56f4d356aa1010b9660cc
This commit is contained in:
parent
d932153dd7
commit
b4e827e01b
|
@ -19,11 +19,19 @@ namespace shaka {
|
||||||
namespace {
|
namespace {
|
||||||
// Create a temp file name using process id, thread id and current time.
|
// Create a temp file name using process id, thread id and current time.
|
||||||
std::string TempFileName() {
|
std::string TempFileName() {
|
||||||
const int32_t pid = static_cast<int32_t>(base::GetCurrentProcId());
|
const int32_t process_id = static_cast<int32_t>(base::GetCurrentProcId());
|
||||||
const int32_t tid = static_cast<int32_t>(base::PlatformThread::CurrentId());
|
const int32_t thread_id =
|
||||||
|
static_cast<int32_t>(base::PlatformThread::CurrentId());
|
||||||
|
|
||||||
|
// We may need two or more temporary files in the same thread. There might be
|
||||||
|
// name collision if they are requested around the same time, e.g. called
|
||||||
|
// consecutively. Use a thread_local instance to avoid that.
|
||||||
|
static thread_local int32_t instance_id = 0;
|
||||||
|
++instance_id;
|
||||||
|
|
||||||
const int64_t current_time = base::Time::Now().ToInternalValue();
|
const int64_t current_time = base::Time::Now().ToInternalValue();
|
||||||
return base::StringPrintf("packager-tempfile-%x-%x-%" PRIx64, pid, tid,
|
return base::StringPrintf("packager-tempfile-%x-%x-%x-%" PRIx64, process_id,
|
||||||
current_time);
|
thread_id, instance_id, current_time);
|
||||||
}
|
}
|
||||||
} // namespace
|
} // namespace
|
||||||
|
|
||||||
|
|
|
@ -8,15 +8,33 @@
|
||||||
|
|
||||||
#include <gtest/gtest.h>
|
#include <gtest/gtest.h>
|
||||||
|
|
||||||
|
#include "packager/base/logging.h"
|
||||||
|
|
||||||
namespace shaka {
|
namespace shaka {
|
||||||
|
|
||||||
TEST(FileUtilTest, Basic) {
|
TEST(FileUtilTest, TempFilePathInDesignatedDirectory) {
|
||||||
std::string temp_file_path;
|
std::string temp_file_path;
|
||||||
EXPECT_TRUE(TempFilePath("test", &temp_file_path));
|
EXPECT_TRUE(TempFilePath("test", &temp_file_path));
|
||||||
EXPECT_EQ(temp_file_path.find("test"), 0u);
|
EXPECT_EQ(temp_file_path.find("test"), 0u);
|
||||||
|
LOG(INFO) << "temp file path: " << temp_file_path;
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST(FileUtilTest, TempFilePathInSystemTempDirectory) {
|
||||||
|
std::string temp_file_path;
|
||||||
EXPECT_TRUE(TempFilePath("", &temp_file_path));
|
EXPECT_TRUE(TempFilePath("", &temp_file_path));
|
||||||
// temp_file_path should be created in a system specific temp directory.
|
// temp_file_path should be created in a system specific temp directory.
|
||||||
|
LOG(INFO) << "temp file path: " << temp_file_path;
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST(FileUtilTest, TempFilePathCalledTwice) {
|
||||||
|
const char kTempDir[] = "/test/";
|
||||||
|
std::string temp_file_path1;
|
||||||
|
std::string temp_file_path2;
|
||||||
|
ASSERT_TRUE(TempFilePath(kTempDir, &temp_file_path1));
|
||||||
|
ASSERT_TRUE(TempFilePath(kTempDir, &temp_file_path2));
|
||||||
|
ASSERT_NE(temp_file_path1, temp_file_path2);
|
||||||
|
LOG(INFO) << "temp file path1: " << temp_file_path1;
|
||||||
|
LOG(INFO) << "temp file path2: " << temp_file_path2;
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace shaka
|
} // namespace shaka
|
||||||
|
|
Loading…
Reference in New Issue