aboutsummaryrefslogtreecommitdiff
path: root/openmp/runtime
diff options
context:
space:
mode:
authorXing Xue <xingxue@outlook.com>2024-04-30 16:58:47 -0400
committerGitHub <noreply@github.com>2024-04-30 16:58:47 -0400
commit928db7e7edc5ffeaf92e85610068852ee94b26fb (patch)
tree941be1ce1b752e303b0959471abdf2d06d60c782 /openmp/runtime
parent2224dce7e490340717adb3bd864f17b5d7da4421 (diff)
downloadllvm-928db7e7edc5ffeaf92e85610068852ee94b26fb.zip
llvm-928db7e7edc5ffeaf92e85610068852ee94b26fb.tar.gz
llvm-928db7e7edc5ffeaf92e85610068852ee94b26fb.tar.bz2
[OpenMP][AIX] Implement __kmp_is_address_mapped() for AIX (#90516)
This patch implements `__kmp_is_address_mapped()` for AIX by calling `loadquery()` to get the load info of the process and then checking if the address falls within the range of the data segment of one of the loaded modules.
Diffstat (limited to 'openmp/runtime')
-rw-r--r--openmp/runtime/src/z_Linux_util.cpp49
1 files changed, 45 insertions, 4 deletions
diff --git a/openmp/runtime/src/z_Linux_util.cpp b/openmp/runtime/src/z_Linux_util.cpp
index 11ce083..affb577 100644
--- a/openmp/runtime/src/z_Linux_util.cpp
+++ b/openmp/runtime/src/z_Linux_util.cpp
@@ -29,7 +29,9 @@
#include <semaphore.h>
#endif // KMP_OS_LINUX
#include <sys/resource.h>
-#if !KMP_OS_AIX
+#if KMP_OS_AIX
+#include <sys/ldr.h>
+#else
#include <sys/syscall.h>
#endif
#include <sys/time.h>
@@ -2338,9 +2340,48 @@ int __kmp_is_address_mapped(void *addr) {
found = (int)addr < (__builtin_wasm_memory_size(0) * PAGESIZE);
#elif KMP_OS_AIX
- (void)rc;
- // FIXME(AIX): Implement this
- found = 1;
+ uint32_t loadQueryBufSize = 4096u; // Default loadquery buffer size.
+ char *loadQueryBuf;
+
+ for (;;) {
+ loadQueryBuf = (char *)KMP_INTERNAL_MALLOC(loadQueryBufSize);
+ if (loadQueryBuf == NULL) {
+ return 0;
+ }
+
+ rc = loadquery(L_GETXINFO | L_IGNOREUNLOAD, loadQueryBuf, loadQueryBufSize);
+ if (rc < 0) {
+ KMP_INTERNAL_FREE(loadQueryBuf);
+ if (errno != ENOMEM) {
+ return 0;
+ }
+ // errno == ENOMEM; double the size.
+ loadQueryBufSize <<= 1;
+ continue;
+ }
+ // Obtained the load info successfully.
+ break;
+ }
+
+ struct ld_xinfo *curLdInfo = (struct ld_xinfo *)loadQueryBuf;
+
+ // Loop through the load info to find if there is a match.
+ for (;;) {
+ uintptr_t curDataStart = (uintptr_t)curLdInfo->ldinfo_dataorg;
+ uintptr_t curDataEnd = curDataStart + curLdInfo->ldinfo_datasize;
+
+ // The data segment is readable and writable.
+ if (curDataStart <= (uintptr_t)addr && (uintptr_t)addr < curDataEnd) {
+ found = 1;
+ break;
+ }
+ if (curLdInfo->ldinfo_next == 0u) {
+ // Reached the end of load info.
+ break;
+ }
+ curLdInfo = (struct ld_xinfo *)((char *)curLdInfo + curLdInfo->ldinfo_next);
+ }
+ KMP_INTERNAL_FREE(loadQueryBuf);
#else