diff --git a/src/common/capio/shm.hpp b/src/common/capio/shm.hpp index 3c86741be..6a3fcbe37 100644 --- a/src/common/capio/shm.hpp +++ b/src/common/capio/shm.hpp @@ -25,7 +25,7 @@ #define SHM_CREATE_CHECK(condition, source) \ if (condition) { \ - ERR_EXIT("Unable to open shm: %s", source); \ + ERR_EXIT("Unable to open shm: %s: %s", source, strerror(errno)); \ }; #else @@ -42,7 +42,7 @@ LOG("error while creating %s", source); \ std::cout << CAPIO_SERVER_CLI_LOG_SERVER_ERROR << " [ " << node_name << " ] " \ << "Unable to create shm: " << source << std::endl; \ - ERR_EXIT("Unable to open shm: %s", source); \ + ERR_EXIT("Unable to open shm %s: %s", source, strerror(errno)); \ }; #endif @@ -133,7 +133,12 @@ void *get_shm(const std::string &shm_name) { } void *p = mmap(nullptr, sb.st_size, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0); if (p == MAP_FAILED) { - ERR_EXIT("mmap get_shm %s", shm_name.c_str()); + LOG("ERROR MMAP arg dump:"); + LOG("mmap-size: %ld", sb.st_size); + LOG("mmap-prot: %ld", PROT_READ | PROT_WRITE); + LOG("mmap-flags: %ld", MAP_SHARED); + LOG("mmap-fd: %ld", fd); + ERR_EXIT("ERROR: mmap failed at get_shm(%s): %s", shm_name.c_str(), strerror(errno)); } if (close(fd) == -1) { ERR_EXIT("close"); @@ -151,7 +156,7 @@ void *get_shm_if_exist(const std::string &shm_name) { if (errno == ENOENT) { return nullptr; } - ERR_EXIT("get_shm shm_open %s", shm_name.c_str()); + ERR_EXIT("ERROR: unable to open shared memory %s: %s", shm_name.c_str(), strerror(errno)); } /* Open existing object */ /* Use shared memory object size as length argument for mmap() @@ -161,7 +166,13 @@ void *get_shm_if_exist(const std::string &shm_name) { } void *p = mmap(nullptr, sb.st_size, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0); if (p == MAP_FAILED) { - ERR_EXIT("mmap get_shm %s", shm_name.c_str()); + LOG("ERROR MMAP arg dump:"); + LOG("mmap-size: %ld", sb.st_size); + LOG("mmap-prot: %ld", PROT_READ | PROT_WRITE); + LOG("mmap-flags: %ld", MAP_SHARED); + LOG("mmap-fd: %ld", fd); + ERR_EXIT("ERROR: mmap failed at get_shm_if_exist(%s): %s", shm_name.c_str(), + strerror(errno)); } if (close(fd) == -1) { ERR_EXIT("close"); diff --git a/src/posix/utils/clone.hpp b/src/posix/utils/clone.hpp index 306401f98..81398be32 100644 --- a/src/posix/utils/clone.hpp +++ b/src/posix/utils/clone.hpp @@ -18,13 +18,17 @@ inline bool is_capio_tid(const pid_t tid) { } inline void register_capio_tid(const pid_t tid) { + START_LOG(syscall_no_intercept(SYS_gettid), "call(tid=%ld)", tid); const std::lock_guard lg(clone_mutex); tids->insert(tid); } inline void remove_capio_tid(const pid_t tid) { + START_LOG(syscall_no_intercept(SYS_gettid), "call(tid=%ld)", tid); const std::lock_guard lg(clone_mutex); - tids->erase(tid); + if (tids->find(tid) != tids->end()) { + tids->erase(tid); + } } inline void init_threading_support() { tids = new std::unordered_set{}; } @@ -59,6 +63,21 @@ inline void hook_clone_child() { #ifdef __CAPIO_POSIX syscall_no_intercept_flag = true; + + /* + * This piece of code is aimed at addressing issues with applications that spawn several + * thousand threads that only do computations. When this occurs, under some circumstances CAPIO + * might fail to allocate shared memory objects. As such, if child threads ONLY do computation, + * we can safely ignore them with CAPIO. + */ + thread_local char *skip_child = std::getenv("CAPIO_IGNORE_CHILD_THREADS"); + if (skip_child != nullptr) { + auto skip_child_str = std::string(skip_child); + if (skip_child_str == "ON" || skip_child_str == "TRUE" || skip_child_str == "YES") { + return; + } + } + #endif std::unique_lock lock(clone_mutex); clone_cv.wait(lock, [&tid] { return tids->find(tid) != tids->end(); });