• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2018 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #include "util/exe_path.h"
6 
7 #include "base/files/file_util.h"
8 #include "base/logging.h"
9 #include "base/strings/string_util.h"
10 #include "util/build_config.h"
11 
12 #if defined(OS_MACOSX)
13 #include <mach-o/dyld.h>
14 #elif defined(OS_WIN)
15 #include <windows.h>
16 
17 #include "base/win/win_util.h"
18 #elif defined(OS_FREEBSD) || defined(OS_NETBSD)
19 #include <limits.h>
20 #include <sys/sysctl.h>
21 #include <sys/types.h>
22 #elif defined(OS_HAIKU)
23 #include <OS.h>
24 #include <image.h>
25 #elif defined(OS_SOLARIS)
26 #include <stdlib.h>
27 #endif
28 
29 #if defined(OS_MACOSX)
30 
GetExePath()31 base::FilePath GetExePath() {
32   // Executable path can have relative references ("..") depending on
33   // how the app was launched.
34   uint32_t executable_length = 0;
35   _NSGetExecutablePath(NULL, &executable_length);
36   DCHECK_GT(executable_length, 1u);
37   std::string executable_path;
38   int rv = _NSGetExecutablePath(
39       base::WriteInto(&executable_path, executable_length), &executable_length);
40   DCHECK_EQ(rv, 0);
41 
42   // _NSGetExecutablePath may return paths containing ./ or ../ which makes
43   // FilePath::DirName() work incorrectly, convert it to absolute path so that
44   // paths such as DIR_SOURCE_ROOT can work, since we expect absolute paths to
45   // be returned here.
46   return base::MakeAbsoluteFilePath(base::FilePath(executable_path));
47 }
48 
49 #elif defined(OS_WIN)
50 
GetExePath()51 base::FilePath GetExePath() {
52   char16_t system_buffer[MAX_PATH];
53   system_buffer[0] = 0;
54   if (GetModuleFileName(NULL, base::ToWCharT(system_buffer), MAX_PATH) == 0) {
55     return base::FilePath();
56   }
57   return base::FilePath(system_buffer);
58 }
59 
60 #elif defined(OS_FREEBSD)
61 
GetExePath()62 base::FilePath GetExePath() {
63   int mib[] = {CTL_KERN, KERN_PROC, KERN_PROC_PATHNAME, -1};
64   char buf[PATH_MAX];
65   size_t buf_size = PATH_MAX;
66   if (sysctl(mib, 4, buf, &buf_size, nullptr, 0) == -1) {
67     return base::FilePath();
68   }
69   return base::FilePath(buf);
70 }
71 
72 #elif defined(OS_NETBSD)
73 
GetExePath()74 base::FilePath GetExePath() {
75   int mib[] = {CTL_KERN, KERN_PROC_ARGS, getpid(), KERN_PROC_PATHNAME};
76   char buf[PATH_MAX];
77   size_t buf_size = PATH_MAX;
78   if (sysctl(mib, 4, buf, &buf_size, nullptr, 0) == -1) {
79     return base::FilePath();
80   }
81   return base::FilePath(buf);
82 }
83 
84 #elif defined(OS_HAIKU)
85 
GetExePath()86 base::FilePath GetExePath() {
87   image_info i_info;
88   int32 image_cookie = 0;
89   while (get_next_image_info(B_CURRENT_TEAM, &image_cookie, &i_info) == B_OK) {
90     if (i_info.type == B_APP_IMAGE) {
91       break;
92     }
93   }
94   return base::FilePath(std::string(i_info.name));
95 }
96 
97 #elif defined(OS_SOLARIS)
98 
GetExePath()99 base::FilePath GetExePath() {
100   const char *raw = getexecname();
101   if (raw == NULL) {
102     return base::FilePath();
103   }
104   return base::FilePath(raw);
105 }
106 
107 #elif defined(OS_ZOS)
108 
GetExePath()109 base::FilePath GetExePath() {
110   char path[PATH_MAX];
111   if (__getexepath(path, sizeof(path), getpid()) != 0) {
112     return base::FilePath();
113   }
114   return base::FilePath(path);
115 }
116 
117 #else
118 
GetExePath()119 base::FilePath GetExePath() {
120   base::FilePath result;
121   const char kProcSelfExe[] = "/proc/self/exe";
122   if (!ReadSymbolicLink(base::FilePath(kProcSelfExe), &result)) {
123     NOTREACHED() << "Unable to resolve " << kProcSelfExe << ".";
124     return base::FilePath();
125   }
126   return result;
127 }
128 
129 #endif
130