1c55a96383497a772a307b346368133960b02ad03Eric Laurent/* 2c55a96383497a772a307b346368133960b02ad03Eric Laurent * Copyright (c) 2011 The WebRTC project authors. All Rights Reserved. 3c55a96383497a772a307b346368133960b02ad03Eric Laurent * 4c55a96383497a772a307b346368133960b02ad03Eric Laurent * Use of this source code is governed by a BSD-style license 5c55a96383497a772a307b346368133960b02ad03Eric Laurent * that can be found in the LICENSE file in the root of the source 6c55a96383497a772a307b346368133960b02ad03Eric Laurent * tree. An additional intellectual property rights grant can be found 7c55a96383497a772a307b346368133960b02ad03Eric Laurent * in the file PATENTS. All contributing project authors may 8c55a96383497a772a307b346368133960b02ad03Eric Laurent * be found in the AUTHORS file in the root of the source tree. 9c55a96383497a772a307b346368133960b02ad03Eric Laurent */ 10c55a96383497a772a307b346368133960b02ad03Eric Laurent 11c55a96383497a772a307b346368133960b02ad03Eric Laurent#include "testsupport/fileutils.h" 12c55a96383497a772a307b346368133960b02ad03Eric Laurent 13c55a96383497a772a307b346368133960b02ad03Eric Laurent#ifdef WIN32 14c55a96383497a772a307b346368133960b02ad03Eric Laurent#include <direct.h> 15c55a96383497a772a307b346368133960b02ad03Eric Laurent#define GET_CURRENT_DIR _getcwd 16c55a96383497a772a307b346368133960b02ad03Eric Laurent#else 17c55a96383497a772a307b346368133960b02ad03Eric Laurent#include <unistd.h> 18c55a96383497a772a307b346368133960b02ad03Eric Laurent#define GET_CURRENT_DIR getcwd 19c55a96383497a772a307b346368133960b02ad03Eric Laurent#endif 20c55a96383497a772a307b346368133960b02ad03Eric Laurent 21c55a96383497a772a307b346368133960b02ad03Eric Laurent#include <sys/stat.h> // To check for directory existence. 22c55a96383497a772a307b346368133960b02ad03Eric Laurent#ifndef S_ISDIR // Not defined in stat.h on Windows. 23c55a96383497a772a307b346368133960b02ad03Eric Laurent#define S_ISDIR(mode) (((mode) & S_IFMT) == S_IFDIR) 24c55a96383497a772a307b346368133960b02ad03Eric Laurent#endif 25c55a96383497a772a307b346368133960b02ad03Eric Laurent 26c55a96383497a772a307b346368133960b02ad03Eric Laurent#include <cstdio> 27c55a96383497a772a307b346368133960b02ad03Eric Laurent 28c55a96383497a772a307b346368133960b02ad03Eric Laurent#include "typedefs.h" // For architecture defines 29c55a96383497a772a307b346368133960b02ad03Eric Laurent 30c55a96383497a772a307b346368133960b02ad03Eric Laurentnamespace webrtc { 31c55a96383497a772a307b346368133960b02ad03Eric Laurentnamespace test { 32c55a96383497a772a307b346368133960b02ad03Eric Laurent 33c55a96383497a772a307b346368133960b02ad03Eric Laurent#ifdef WIN32 34c55a96383497a772a307b346368133960b02ad03Eric Laurentstatic const char* kPathDelimiter = "\\"; 35c55a96383497a772a307b346368133960b02ad03Eric Laurent#else 36c55a96383497a772a307b346368133960b02ad03Eric Laurentstatic const char* kPathDelimiter = "/"; 37c55a96383497a772a307b346368133960b02ad03Eric Laurent#endif 38c55a96383497a772a307b346368133960b02ad03Eric Laurent// The file we're looking for to identify the project root dir. 39c55a96383497a772a307b346368133960b02ad03Eric Laurentstatic const char* kProjectRootFileName = "DEPS"; 40c55a96383497a772a307b346368133960b02ad03Eric Laurentstatic const char* kOutputDirName = "out"; 41c55a96383497a772a307b346368133960b02ad03Eric Laurentstatic const char* kFallbackPath = "./"; 42c55a96383497a772a307b346368133960b02ad03Eric Laurentstatic const char* kResourcesDirName = "resources"; 43c55a96383497a772a307b346368133960b02ad03Eric Laurentconst char* kCannotFindProjectRootDir = "ERROR_CANNOT_FIND_PROJECT_ROOT_DIR"; 44c55a96383497a772a307b346368133960b02ad03Eric Laurent 45c55a96383497a772a307b346368133960b02ad03Eric Laurentstd::string ProjectRootPath() { 46c55a96383497a772a307b346368133960b02ad03Eric Laurent std::string working_dir = WorkingDir(); 47c55a96383497a772a307b346368133960b02ad03Eric Laurent if (working_dir == kFallbackPath) { 48c55a96383497a772a307b346368133960b02ad03Eric Laurent return kCannotFindProjectRootDir; 49c55a96383497a772a307b346368133960b02ad03Eric Laurent } 50c55a96383497a772a307b346368133960b02ad03Eric Laurent // Check for our file that verifies the root dir. 51c55a96383497a772a307b346368133960b02ad03Eric Laurent std::string current_path(working_dir); 52c55a96383497a772a307b346368133960b02ad03Eric Laurent FILE* file = NULL; 53c55a96383497a772a307b346368133960b02ad03Eric Laurent int path_delimiter_index = current_path.find_last_of(kPathDelimiter); 54c55a96383497a772a307b346368133960b02ad03Eric Laurent while (path_delimiter_index > -1) { 55c55a96383497a772a307b346368133960b02ad03Eric Laurent std::string root_filename = current_path + kPathDelimiter + 56c55a96383497a772a307b346368133960b02ad03Eric Laurent kProjectRootFileName; 57c55a96383497a772a307b346368133960b02ad03Eric Laurent file = fopen(root_filename.c_str(), "r"); 58c55a96383497a772a307b346368133960b02ad03Eric Laurent if (file != NULL) { 59c55a96383497a772a307b346368133960b02ad03Eric Laurent fclose(file); 60c55a96383497a772a307b346368133960b02ad03Eric Laurent return current_path + kPathDelimiter; 61c55a96383497a772a307b346368133960b02ad03Eric Laurent } 62c55a96383497a772a307b346368133960b02ad03Eric Laurent // Move up one directory in the directory tree. 63c55a96383497a772a307b346368133960b02ad03Eric Laurent current_path = current_path.substr(0, path_delimiter_index); 64c55a96383497a772a307b346368133960b02ad03Eric Laurent path_delimiter_index = current_path.find_last_of(kPathDelimiter); 65c55a96383497a772a307b346368133960b02ad03Eric Laurent } 66c55a96383497a772a307b346368133960b02ad03Eric Laurent // Reached the root directory. 67c55a96383497a772a307b346368133960b02ad03Eric Laurent fprintf(stderr, "Cannot find project root directory!\n"); 68c55a96383497a772a307b346368133960b02ad03Eric Laurent return kCannotFindProjectRootDir; 69c55a96383497a772a307b346368133960b02ad03Eric Laurent} 70c55a96383497a772a307b346368133960b02ad03Eric Laurent 71c55a96383497a772a307b346368133960b02ad03Eric Laurentstd::string OutputPath() { 72c55a96383497a772a307b346368133960b02ad03Eric Laurent std::string path = ProjectRootPath(); 73c55a96383497a772a307b346368133960b02ad03Eric Laurent if (path == kCannotFindProjectRootDir) { 74c55a96383497a772a307b346368133960b02ad03Eric Laurent return kFallbackPath; 75c55a96383497a772a307b346368133960b02ad03Eric Laurent } 76c55a96383497a772a307b346368133960b02ad03Eric Laurent path += kOutputDirName; 77c55a96383497a772a307b346368133960b02ad03Eric Laurent if (!CreateDirectory(path)) { 78c55a96383497a772a307b346368133960b02ad03Eric Laurent return kFallbackPath; 79c55a96383497a772a307b346368133960b02ad03Eric Laurent } 80c55a96383497a772a307b346368133960b02ad03Eric Laurent return path + kPathDelimiter; 81c55a96383497a772a307b346368133960b02ad03Eric Laurent} 82c55a96383497a772a307b346368133960b02ad03Eric Laurent 83c55a96383497a772a307b346368133960b02ad03Eric Laurentstd::string WorkingDir() { 84c55a96383497a772a307b346368133960b02ad03Eric Laurent char path_buffer[FILENAME_MAX]; 85c55a96383497a772a307b346368133960b02ad03Eric Laurent if (!GET_CURRENT_DIR(path_buffer, sizeof(path_buffer))) { 86c55a96383497a772a307b346368133960b02ad03Eric Laurent fprintf(stderr, "Cannot get current directory!\n"); 87c55a96383497a772a307b346368133960b02ad03Eric Laurent return kFallbackPath; 88c55a96383497a772a307b346368133960b02ad03Eric Laurent } else { 89c55a96383497a772a307b346368133960b02ad03Eric Laurent return std::string(path_buffer); 90c55a96383497a772a307b346368133960b02ad03Eric Laurent } 91c55a96383497a772a307b346368133960b02ad03Eric Laurent} 92c55a96383497a772a307b346368133960b02ad03Eric Laurent 93c55a96383497a772a307b346368133960b02ad03Eric Laurentbool CreateDirectory(std::string directory_name) { 94c55a96383497a772a307b346368133960b02ad03Eric Laurent struct stat path_info = {0}; 95c55a96383497a772a307b346368133960b02ad03Eric Laurent // Check if the path exists already: 96c55a96383497a772a307b346368133960b02ad03Eric Laurent if (stat(directory_name.c_str(), &path_info) == 0) { 97c55a96383497a772a307b346368133960b02ad03Eric Laurent if (!S_ISDIR(path_info.st_mode)) { 98c55a96383497a772a307b346368133960b02ad03Eric Laurent fprintf(stderr, "Path %s exists but is not a directory! Remove this " 99c55a96383497a772a307b346368133960b02ad03Eric Laurent "file and re-run to create the directory.\n", 100c55a96383497a772a307b346368133960b02ad03Eric Laurent directory_name.c_str()); 101c55a96383497a772a307b346368133960b02ad03Eric Laurent return false; 102c55a96383497a772a307b346368133960b02ad03Eric Laurent } 103c55a96383497a772a307b346368133960b02ad03Eric Laurent } else { 104c55a96383497a772a307b346368133960b02ad03Eric Laurent#ifdef WIN32 105c55a96383497a772a307b346368133960b02ad03Eric Laurent return _mkdir(directory_name.c_str()) == 0; 106c55a96383497a772a307b346368133960b02ad03Eric Laurent#else 107c55a96383497a772a307b346368133960b02ad03Eric Laurent return mkdir(directory_name.c_str(), S_IRWXU | S_IRWXG | S_IRWXO) == 0; 108c55a96383497a772a307b346368133960b02ad03Eric Laurent#endif 109c55a96383497a772a307b346368133960b02ad03Eric Laurent } 110c55a96383497a772a307b346368133960b02ad03Eric Laurent return true; 111c55a96383497a772a307b346368133960b02ad03Eric Laurent} 112c55a96383497a772a307b346368133960b02ad03Eric Laurent 113c55a96383497a772a307b346368133960b02ad03Eric Laurentbool FileExists(std::string file_name) { 114c55a96383497a772a307b346368133960b02ad03Eric Laurent struct stat file_info = {0}; 115c55a96383497a772a307b346368133960b02ad03Eric Laurent return stat(file_name.c_str(), &file_info) == 0; 116c55a96383497a772a307b346368133960b02ad03Eric Laurent} 117c55a96383497a772a307b346368133960b02ad03Eric Laurent 118c55a96383497a772a307b346368133960b02ad03Eric Laurentstd::string ResourcePath(std::string name, std::string extension) { 119c55a96383497a772a307b346368133960b02ad03Eric Laurent std::string platform = "win"; 120c55a96383497a772a307b346368133960b02ad03Eric Laurent#ifdef WEBRTC_LINUX 121c55a96383497a772a307b346368133960b02ad03Eric Laurent platform = "linux"; 122c55a96383497a772a307b346368133960b02ad03Eric Laurent#endif // WEBRTC_LINUX 123c55a96383497a772a307b346368133960b02ad03Eric Laurent#ifdef WEBRTC_MAC 124c55a96383497a772a307b346368133960b02ad03Eric Laurent platform = "mac"; 125c55a96383497a772a307b346368133960b02ad03Eric Laurent#endif // WEBRTC_MAC 126c55a96383497a772a307b346368133960b02ad03Eric Laurent 127c55a96383497a772a307b346368133960b02ad03Eric Laurent#ifdef WEBRTC_ARCH_64_BITS 128c55a96383497a772a307b346368133960b02ad03Eric Laurent std::string architecture = "64"; 129c55a96383497a772a307b346368133960b02ad03Eric Laurent#else 130c55a96383497a772a307b346368133960b02ad03Eric Laurent std::string architecture = "32"; 131c55a96383497a772a307b346368133960b02ad03Eric Laurent#endif // WEBRTC_ARCH_64_BITS 132c55a96383497a772a307b346368133960b02ad03Eric Laurent 133c55a96383497a772a307b346368133960b02ad03Eric Laurent std::string resources_path = ProjectRootPath() + kResourcesDirName + 134c55a96383497a772a307b346368133960b02ad03Eric Laurent kPathDelimiter; 135c55a96383497a772a307b346368133960b02ad03Eric Laurent std::string resource_file = resources_path + name + "_" + platform + "_" + 136c55a96383497a772a307b346368133960b02ad03Eric Laurent architecture + "." + extension; 137c55a96383497a772a307b346368133960b02ad03Eric Laurent if (FileExists(resource_file)) { 138c55a96383497a772a307b346368133960b02ad03Eric Laurent return resource_file; 139c55a96383497a772a307b346368133960b02ad03Eric Laurent } 140c55a96383497a772a307b346368133960b02ad03Eric Laurent // Try without architecture. 141c55a96383497a772a307b346368133960b02ad03Eric Laurent resource_file = resources_path + name + "_" + platform + "." + extension; 142c55a96383497a772a307b346368133960b02ad03Eric Laurent if (FileExists(resource_file)) { 143c55a96383497a772a307b346368133960b02ad03Eric Laurent return resource_file; 144c55a96383497a772a307b346368133960b02ad03Eric Laurent } 145c55a96383497a772a307b346368133960b02ad03Eric Laurent // Try without platform. 146c55a96383497a772a307b346368133960b02ad03Eric Laurent resource_file = resources_path + name + "_" + architecture + "." + extension; 147c55a96383497a772a307b346368133960b02ad03Eric Laurent if (FileExists(resource_file)) { 148c55a96383497a772a307b346368133960b02ad03Eric Laurent return resource_file; 149c55a96383497a772a307b346368133960b02ad03Eric Laurent } 150c55a96383497a772a307b346368133960b02ad03Eric Laurent // Fall back on name without architecture or platform. 151c55a96383497a772a307b346368133960b02ad03Eric Laurent return resources_path + name + "." + extension; 152c55a96383497a772a307b346368133960b02ad03Eric Laurent} 153c55a96383497a772a307b346368133960b02ad03Eric Laurent 154c55a96383497a772a307b346368133960b02ad03Eric Laurentsize_t GetFileSize(std::string filename) { 155c55a96383497a772a307b346368133960b02ad03Eric Laurent FILE* f = fopen(filename.c_str(), "rb"); 156c55a96383497a772a307b346368133960b02ad03Eric Laurent size_t size = 0; 157c55a96383497a772a307b346368133960b02ad03Eric Laurent if (f != NULL) { 158c55a96383497a772a307b346368133960b02ad03Eric Laurent if (fseek(f, 0, SEEK_END) == 0) { 159c55a96383497a772a307b346368133960b02ad03Eric Laurent size = ftell(f); 160c55a96383497a772a307b346368133960b02ad03Eric Laurent } 161c55a96383497a772a307b346368133960b02ad03Eric Laurent fclose(f); 162c55a96383497a772a307b346368133960b02ad03Eric Laurent } 163c55a96383497a772a307b346368133960b02ad03Eric Laurent return size; 164c55a96383497a772a307b346368133960b02ad03Eric Laurent} 165c55a96383497a772a307b346368133960b02ad03Eric Laurent 166c55a96383497a772a307b346368133960b02ad03Eric Laurent} // namespace test 167c55a96383497a772a307b346368133960b02ad03Eric Laurent} // namespace webrtc 168