|
11 | 11 | #include "lldb/Host/FileSystem.h" |
12 | 12 | #include "lldb/Utility/LLDBLog.h" |
13 | 13 | #include "lldb/Utility/Log.h" |
14 | | - |
15 | 14 | #include "llvm/Support/Threading.h" |
16 | | - |
| 15 | +#include <algorithm> |
17 | 16 | #include <climits> |
18 | 17 | #include <cstdio> |
19 | 18 | #include <cstring> |
| 19 | +#include <mutex> |
20 | 20 | #include <sys/utsname.h> |
21 | 21 | #include <unistd.h> |
22 | 22 |
|
23 | | -#include <algorithm> |
24 | | -#include <mutex> |
25 | | - |
26 | 23 | using namespace lldb_private; |
27 | 24 |
|
28 | | -namespace { |
29 | | -struct HostInfoAIXFields { |
30 | | - llvm::once_flag m_distribution_once_flag; |
31 | | - std::string m_distribution_id; |
32 | | -}; |
33 | | -} // namespace |
34 | | - |
35 | | -static HostInfoAIXFields *g_fields = nullptr; |
36 | | - |
37 | 25 | void HostInfoAIX::Initialize(SharedLibraryDirectoryHelper *helper) { |
38 | 26 | HostInfoPosix::Initialize(helper); |
39 | | - |
40 | | - g_fields = new HostInfoAIXFields(); |
41 | 27 | } |
42 | 28 |
|
43 | | -void HostInfoAIX::Terminate() { |
44 | | - assert(g_fields && "Missing call to Initialize?"); |
45 | | - delete g_fields; |
46 | | - g_fields = nullptr; |
47 | | - HostInfoBase::Terminate(); |
48 | | -} |
49 | | - |
50 | | -llvm::StringRef HostInfoAIX::GetDistributionId() { |
51 | | - assert(g_fields && "Missing call to Initialize?"); |
52 | | - // Try to run 'lbs_release -i', and use that response for the distribution |
53 | | - // id. |
54 | | - llvm::call_once(g_fields->m_distribution_once_flag, []() { |
55 | | - Log *log = GetLog(LLDBLog::Host); |
56 | | - LLDB_LOGF(log, "attempting to determine AIX distribution..."); |
57 | | - |
58 | | - // check if the lsb_release command exists at one of the following paths |
59 | | - const char *const exe_paths[] = {"/bin/lsb_release", |
60 | | - "/usr/bin/lsb_release"}; |
61 | | - |
62 | | - for (size_t exe_index = 0; |
63 | | - exe_index < sizeof(exe_paths) / sizeof(exe_paths[0]); ++exe_index) { |
64 | | - const char *const get_distribution_info_exe = exe_paths[exe_index]; |
65 | | - if (access(get_distribution_info_exe, F_OK)) { |
66 | | - // this exe doesn't exist, move on to next exe |
67 | | - LLDB_LOGF(log, "executable doesn't exist: %s", |
68 | | - get_distribution_info_exe); |
69 | | - continue; |
70 | | - } |
71 | | - |
72 | | - // execute the distribution-retrieval command, read output |
73 | | - std::string get_distribution_id_command(get_distribution_info_exe); |
74 | | - get_distribution_id_command += " -i"; |
75 | | - |
76 | | - FILE *file = popen(get_distribution_id_command.c_str(), "r"); |
77 | | - if (!file) { |
78 | | - LLDB_LOGF(log, |
79 | | - "failed to run command: \"%s\", cannot retrieve " |
80 | | - "platform information", |
81 | | - get_distribution_id_command.c_str()); |
82 | | - break; |
83 | | - } |
84 | | - |
85 | | - // retrieve the distribution id string. |
86 | | - char distribution_id[256] = {'\0'}; |
87 | | - if (fgets(distribution_id, sizeof(distribution_id) - 1, file) != |
88 | | - nullptr) { |
89 | | - LLDB_LOGF(log, "distribution id command returned \"%s\"", |
90 | | - distribution_id); |
91 | | - |
92 | | - const char *const distributor_id_key = "Distributor ID:\t"; |
93 | | - if (strstr(distribution_id, distributor_id_key)) { |
94 | | - // strip newlines |
95 | | - std::string id_string(distribution_id + strlen(distributor_id_key)); |
96 | | - llvm::erase(id_string, '\n'); |
97 | | - |
98 | | - // lower case it and convert whitespace to underscores |
99 | | - std::transform( |
100 | | - id_string.begin(), id_string.end(), id_string.begin(), |
101 | | - [](char ch) { return tolower(isspace(ch) ? '_' : ch); }); |
102 | | - |
103 | | - g_fields->m_distribution_id = id_string; |
104 | | - LLDB_LOGF(log, "distribution id set to \"%s\"", |
105 | | - g_fields->m_distribution_id.c_str()); |
106 | | - } else { |
107 | | - LLDB_LOGF(log, "failed to find \"%s\" field in \"%s\"", |
108 | | - distributor_id_key, distribution_id); |
109 | | - } |
110 | | - } else { |
111 | | - LLDB_LOGF(log, |
112 | | - "failed to retrieve distribution id, \"%s\" returned no" |
113 | | - " lines", |
114 | | - get_distribution_id_command.c_str()); |
115 | | - } |
116 | | - |
117 | | - // clean up the file |
118 | | - pclose(file); |
119 | | - } |
120 | | - }); |
121 | | - |
122 | | - return g_fields->m_distribution_id; |
123 | | -} |
| 29 | +void HostInfoAIX::Terminate() { HostInfoBase::Terminate(); } |
124 | 30 |
|
125 | 31 | FileSpec HostInfoAIX::GetProgramFileSpec() { |
126 | 32 | static FileSpec g_program_filespec; |
127 | | - |
128 | | - if (!g_program_filespec) { |
129 | | - char exe_path[PATH_MAX]; |
130 | | - ssize_t len = readlink("/proc/self/exe", exe_path, sizeof(exe_path) - 1); |
131 | | - if (len > 0) { |
132 | | - exe_path[len] = 0; |
133 | | - g_program_filespec.SetFile(exe_path, FileSpec::Style::native); |
134 | | - } |
135 | | - } |
136 | | - |
137 | 33 | return g_program_filespec; |
138 | 34 | } |
139 | | - |
140 | | -void HostInfoAIX::ComputeHostArchitectureSupport(ArchSpec &arch_32, |
141 | | - ArchSpec &arch_64) { |
142 | | - HostInfoPosix::ComputeHostArchitectureSupport(arch_32, arch_64); |
143 | | - |
144 | | - // On AIX, "unknown" in the vendor slot isn't what we want for the default |
145 | | - // triple. It's probably an artifact of config.guess. |
146 | | - if (arch_32.IsValid()) { |
147 | | - if (arch_32.GetTriple().getVendor() == llvm::Triple::UnknownVendor) |
148 | | - arch_32.GetTriple().setVendorName(llvm::StringRef()); |
149 | | - } |
150 | | - if (arch_64.IsValid()) { |
151 | | - if (arch_64.GetTriple().getVendor() == llvm::Triple::UnknownVendor) |
152 | | - arch_64.GetTriple().setVendorName(llvm::StringRef()); |
153 | | - } |
154 | | -} |
0 commit comments