int bot_unix_fini(void) { bz(global_info.fd_unix_path); safe_event_del(&global_info.ev_unix); if (global_info.fd_unix) safe_close(global_info.fd_unix); global_info.fd_unix = 0; bz2(global_info.ev_unix); return 0; }
int bot_unix_fd_send(bot_t * bot, int fd, bot_gmod_elm_t * gmod) { char tag[132]; char cmsg_buf[sizeof(struct cmsghdr) + sizeof(long)]; struct sockaddr_un un; struct cmsghdr *cmsg; struct msghdr msg; struct iovec iov[2]; int sock; int op; if (!bot) return -1; debug(NULL, "bot_unix_fd_send: Entered: %s\n", gi->fd_unix_path); if (!_sNULL(global_info.fd_unix_path) || fd < 0) return -1; bz2(un); strlcpy_buf(un.sun_path, global_info.fd_unix_path); un.sun_family = AF_UNIX; sock = socket(AF_UNIX, SOCK_STREAM, 0); if (sock < 0) { perror("socket "); return -1; } if (connect(sock, (struct sockaddr *)&un, sizeof(un)) < 0) { perror("connect "); goto cleanup; } op = BOT_UNIX_OP_FDPASS; iov[0].iov_len = sizeof(int); iov[0].iov_base = &op; bz(tag); snprintf_buf(tag, "%s,%i", bot->tag, bot->ID); if (gmod) { if (_sNULL(gmod->trigger_ext)) { strlcatfmt_buf(tag, ",%s", gmod->trigger_ext); } } iov[1].iov_len = sizeof(tag); iov[1].iov_base = tag; msg.msg_name = 0; msg.msg_namelen = 0; msg.msg_control = cmsg_buf; msg.msg_controllen = sizeof cmsg_buf; msg.msg_iov = (struct iovec *)&iov; msg.msg_iovlen = 2; msg.msg_flags = 0; cmsg = (struct cmsghdr *)cmsg_buf; cmsg->cmsg_level = SOL_SOCKET; cmsg->cmsg_type = SCM_RIGHTS; msg.msg_controllen = cmsg->cmsg_len = sizeof(struct cmsghdr) + sizeof(long); *(int *)((void *)cmsg + sizeof(struct cmsghdr)) = fd; sleep(1); if (sendmsg(sock, &msg, 0) < 0) { perror("sendmsg "); goto cleanup; } safe_close(sock); return 0; cleanup: if (sock) safe_close(sock); return -1; }
void bot_evhook_unix_read(int fd, short event, void *arg) { dlist_t *dptr; bot_unix_node_t *bun; struct cmsghdr *hdr; struct msghdr msg; char cmsg_buf[sizeof(struct cmsghdr) + sizeof(long)]; struct iovec iov[2]; int passed_fd; int op; char tag[132]; if (!arg) { safe_close(fd); return; } dptr = (dlist_t *) arg; if (!dptr->data) { safe_close(fd); return; } bun = (bot_unix_node_t *) dlist_data(dptr); debug(NULL, "bot_evhook_unix_read: Entered\n"); bz2(msg); iov[0].iov_base = &op; iov[0].iov_len = sizeof(op); iov[1].iov_base = &tag; iov[1].iov_len = sizeof(tag); msg.msg_iov = (struct iovec *)&iov; msg.msg_iovlen = 2; msg.msg_control = cmsg_buf; msg.msg_controllen = sizeof(cmsg_buf); errno = 0; if (recvmsg(fd, &msg, 0) < 0) { perror("recvmsg: Entered "); bot_unix_node_destroy(dptr); return; } bz2(iov); if (msg.msg_iovlen > 0) { if (op == BOT_UNIX_OP_FDPASS || BOT_UNIX_OP_TAG) { strlcpy_buf(bun->tag, tag); bun->op = op; } else if (op == BOT_UNIX_OP_CLOSE) { } } if (op == BOT_UNIX_OP_FDPASS) { hdr = CMSG_FIRSTHDR(&msg); if (!hdr) { goto fdpass_cleanup; } if (hdr->cmsg_level != SOL_SOCKET || hdr->cmsg_type != SCM_RIGHTS) { goto fdpass_cleanup; } passed_fd = *(int *)CMSG_DATA(hdr); bun->passed_fd = passed_fd; bot_find_and_set_fd(bun->tag, bun->passed_fd); fdpass_cleanup: bot_unix_node_destroy(dptr); } sleep(1); return; }
gcException IPCToolMain::installTool(gcRefPtr<UserCore::ToolInfo> info) { gcString exe(info->getExe()); gcString args(info->getArgs()); if (!UTIL::FS::isValidFile(exe.c_str())) return gcException(ERR_INVALIDFILE); if (exe.size() > 0 && args == "GAME_LIBRARY") { size_t pos = exe.find_last_of(".bz2"); if (pos == (exe.size()-1)) { UTIL::FS::Path pd(exe.c_str(), "", true); pd += UTIL::FS::File(info->getName()); gcString dest = pd.getFullPath(); uint64 size = UTIL::FS::getFileSize(exe.c_str()); try { UTIL::FS::FileHandle srcFh(exe.c_str(), UTIL::FS::FILE_READ); UTIL::FS::FileHandle destFh(dest.c_str(), UTIL::FS::FILE_WRITE); UTIL::MISC::BZ2Worker bz2(UTIL::MISC::BZ2_DECOMPRESS); srcFh.read(size, [&bz2, &destFh](const unsigned char* buff, uint32 size) -> bool { UTIL::FS::FileHandle *pDest = &destFh; bz2.write((const char*)buff, size, [&pDest](const unsigned char* buff, uint32 size) -> bool { pDest->write((const char*)buff, size); return false; }); return false; }); } catch (gcException &e) { return e; } info->overridePath(dest.c_str()); UTIL::FS::delFile(exe.c_str()); } else { info->overridePath(exe.c_str()); } } else if (args.find("PRECHECK_") == 0) { info->setInstalled(); } else { return gcException(ERR_TOOLINSTALL, gcString("Un-supported tool install [{0}]", info->getName())); } return gcException(ERR_COMPLETED); }