+ if (sock_info->root_handle != -1) {
+ ret = objd_unref(sock_info->root_handle);
+ if (ret) {
+ ERR("Error unref root handle");
+ }
+ sock_info->root_handle = -1;
+ }
+ sock_info->constructor_sem_posted = 0;
+ if (sock_info->wait_shm_mmap) {
+ ret = munmap(sock_info->wait_shm_mmap, sysconf(_SC_PAGE_SIZE));
+ if (ret) {
+ ERR("Error unmapping wait shm");
+ }
+ sock_info->wait_shm_mmap = NULL;
+ }
+}
+
+/*
+ * Using fork to set umask to 0777 in the child process (not
+ * multi-thread safe).
+ */
+static
+int get_wait_shm(struct sock_info *sock_info, size_t mmap_size)
+{
+ int wait_shm_fd, ret;
+ int read_mode;
+ pid_t pid;
+
+ /*
+ * At this point, we should be able to open it for
+ * reading. If it fails, then it's because there is
+ * something wrong: bail out in that case.
+ */
+ read_mode = S_IRUSR | S_IRGRP;
+ if (sock_info->global)
+ read_mode |= S_IROTH;
+
+ /*
+ * Try to open read-only. If it is set read-only, it
+ * means the shm size has been already set with
+ * ftruncate. Note: all processes creating shm need to
+ * call ftruncate on the shm before restricting its
+ * access rights to read-only. The shm should never be
+ * unlinked. It a rogue process try to create a non-accessible
+ * shm or to unlink it, the worse-case scenario is that we don't
+ * use the shm wakeup method and sleep/retry instead.
+ */
+ wait_shm_fd = shm_open(sock_info->wait_shm_path,
+ O_RDONLY, read_mode);
+ if (wait_shm_fd >= 0) {
+ goto end;
+ } else if (wait_shm_fd < 0 && errno != ENOENT) {
+ /*
+ * Real-only open did not work. It's a failure
+ * that prohibits using shm.
+ */
+ ERR("Error opening shm %s", sock_info->wait_shm_path);
+ goto end;
+ }
+
+ /*
+ * If the open failed because the file did not exist, try
+ * creating it ourself.
+ */
+ pid = fork();
+ if (pid > 0) {
+ int status;
+
+ /*
+ * Parent: wait for child to return, in which case the
+ * shared memory map will have been created.
+ */
+ pid = wait(&status);
+ if (!WIFEXITED(status) || WEXITSTATUS(status) != 0) {
+ wait_shm_fd = -1;
+ goto end;
+ }
+ /*
+ * Try to open read-only again after creation.
+ */
+ wait_shm_fd = shm_open(sock_info->wait_shm_path,
+ O_RDONLY, read_mode);
+ if (wait_shm_fd < 0) {
+ /*
+ * Real-only open did not work. It's a failure
+ * that prohibits using shm.
+ */
+ ERR("Error opening shm %s", sock_info->wait_shm_path);
+ goto end;
+ }