/** @brief retrieve the arguments of recvfrom syscall */ void get_args_recvfrom(process_descriptor_t * proc, reg_s * reg, syscall_arg_u * sysarg) { recvfrom_arg_t arg = &(sysarg->recvfrom); arg->ret = reg->ret; arg->sockfd = (int) reg->arg1; arg->len = (int) reg->arg3; arg->flags = (int) reg->arg4; int domain = get_domain_socket(proc, arg->sockfd); pid_t child = proc->pid; if (reg->arg5 != 0) { // syscall "send" doesn't exist on x86_64, it's sendto with struct sockaddr=NULL and addrlen=0 arg->is_addr = 1; if (domain == 2) // PF_INET ptrace_cpy(child, &arg->sai, (void *) reg->arg5, sizeof(struct sockaddr_in), "recvfrom"); if (domain == 1) // PF_UNIX ptrace_cpy(child, &arg->sau, (void *) reg->arg5, sizeof(struct sockaddr_in), "recvfrom"); if (domain == 16) // PF_NETLINK ptrace_cpy(child, &arg->snl, (void *) reg->arg5, sizeof(struct sockaddr_in), "recvfrom"); } else arg->is_addr = 0; arg->dest = (void *) reg->arg2; socklen_t len = 0; if (reg->arg5 != 0) { // syscall "recv" doesn't exist on x86_64, it's recvfrom with struct sockaddr=NULL and addrlen=0 ptrace_cpy(child, &len, (void *) reg->arg6, sizeof(socklen_t), "recvfrom"); } arg->addrlen = len; }
/** @brief retrieve the arguments of sendto syscall */ void get_args_sendto(process_descriptor_t * proc, reg_s * reg, syscall_arg_u * sysarg) { sendto_arg_t arg = &(sysarg->sendto); pid_t pid = proc->pid; arg->ret = reg->ret; arg->sockfd = (int) reg->arg1; arg->len = (int) reg->arg3; arg->flags = (int) reg->arg4; int domain = get_domain_socket(proc, arg->sockfd); if (reg->arg5 != 0) { // syscall "send" doesn't exist on x86_64, it's sendto with struct sockaddr=NULL and addrlen=0 arg->is_addr = 1; if (domain == 2) // PF_INET ptrace_cpy(pid, &arg->sai, (void *) reg->arg5, sizeof(struct sockaddr_in), "sendto"); if (domain == 1) // PF_UNIX ptrace_cpy(pid, &arg->sau, (void *) reg->arg5, sizeof(struct sockaddr_in), "sendto"); if (domain == 16) // PF_NETLINK ptrace_cpy(pid, &arg->snl, (void *) reg->arg5, sizeof(struct sockaddr_in), "sendto"); } else arg->is_addr = 0; #ifndef address_translation arg->data = malloc(arg->len); ptrace_cpy(pid, arg->data, (void *) reg->arg2, arg->len, "sendto"); #endif if (reg->arg5 != 0) { // syscall "send" doesn't exist on x86_64, it's sendto with struct sockaddr=NULL and addrlen=0 arg->addrlen = (socklen_t) reg->arg6; } else arg->addrlen = 0; }
/** @brief print a strace-like log of recvfrom syscall */ void print_recvfrom_syscall(process_descriptor_t * proc, syscall_arg_u * sysarg) { recvfrom_arg_t arg = &(sysarg->recvfrom); int domain = get_domain_socket(proc, arg->sockfd); // fprintf(proc->strace_out,"[%d] recvfrom(", pid); fprintf(proc->strace_out, "recvfrom("); #ifndef address_translation if (arg->ret) { char buff[500]; if (arg->ret <= 500) { memcpy(buff, arg->data, arg->ret); buff[arg->ret] = '\0'; fprintf(proc->strace_out, "%d, \"%s\" , %d, ", arg->sockfd, buff, arg->len); } else { memcpy(buff, arg->data, 500); buff[499] = '\0'; fprintf(proc->strace_out, "%d, \"%s...\" , %d, ", arg->sockfd, buff, arg->len); } if (arg->flags > 0) { print_flags_send(proc, arg->flags); } else fprintf(proc->strace_out, "0, "); } else fprintf(proc->strace_out, "%d, \"\" , %d, ", arg->sockfd, arg->len); #else fprintf(proc->strace_out, "%d, \"...\" , %d, ", arg->sockfd, arg->len); #endif if (domain == 2) { // PF_INET if (arg->is_addr) { fprintf(proc->strace_out, "{sa_family=AF_INET, sin_port=htons(%d), sin_addr=inet_addr(\"%s\")}, ", ntohs(arg->sai.sin_port), inet_ntoa(arg->sai.sin_addr)); } else fprintf(proc->strace_out, "NULL, "); } else if (domain == 1) { //PF_UNIX if (arg->is_addr) { fprintf(proc->strace_out, "{sa_family=AF_UNIX, sun_path=\"%s\"}, ", arg->sau.sun_path); } else fprintf(proc->strace_out, "NULL, "); } else if (domain == 16) { //PF_NETLINK if (arg->is_addr) { fprintf(proc->strace_out, "{sa_family=AF_NETLINK, pid=%d, groups=%u}, ", arg->snl.nl_pid, arg->snl.nl_groups); } else fprintf(proc->strace_out, "NULL, "); } else { fprintf(proc->strace_out, "{sockaddr unknown}, "); } fprintf(proc->strace_out, "%d", (int) arg->addrlen); fprintf(proc->strace_out, ") = %d\n", arg->ret); }
/** @brief retrieve the arguments of bind and connect syscalls */ void get_args_bind_connect(process_descriptor_t * proc, reg_s * reg, syscall_arg_u * sysarg) { connect_arg_t arg = &(sysarg->connect); arg->ret = (int) reg->ret; if (arg->ret == -EINPROGRESS) /* EINPROGRESS 115 Operation now in progress */ arg->ret = 0; arg->sockfd = (int) reg->arg1; int domain = get_domain_socket(proc, arg->sockfd); pid_t child = proc->pid; arg->addrlen = (socklen_t) reg->arg3; const char *sysname = "bind ou connect"; if (domain == 2) // PF_INET ptrace_cpy(child, &arg->sai, (void *) reg->arg2, sizeof(struct sockaddr_in), sysname); if (domain == 1) // PF_UNIX ptrace_cpy(child, &arg->sau, (void *) reg->arg2, sizeof(struct sockaddr_in), sysname); if (domain == 16) // PF_NETLINK ptrace_cpy(child, &arg->sau, (void *) reg->arg2, sizeof(struct sockaddr_in), sysname); }
/** @brief retrieve the arguments of accept syscall */ void get_args_accept(process_descriptor_t * proc, reg_s * reg, syscall_arg_u * sysarg) { accept_arg_t arg = &(sysarg->accept); arg->ret = reg->ret; arg->sockfd = (int) reg->arg1; XBT_DEBUG("Socket for accepting %lu", reg->arg1); int domain = get_domain_socket(proc, arg->sockfd); pid_t child = proc->pid; if (domain == 2) // PF_INET ptrace_cpy(child, &arg->sai, (void *) reg->arg2, sizeof(struct sockaddr_in), "accept"); if (domain == 1) // PF_UINX ptrace_cpy(child, &arg->sau, (void *) reg->arg2, sizeof(struct sockaddr_in), "accept"); if (domain == 16) // PF_NETLINK ptrace_cpy(child, &arg->snl, (void *) reg->arg2, sizeof(struct sockaddr_in), "accept"); ptrace_cpy(child, &arg->addrlen, (void *) reg->arg3, sizeof(socklen_t), "accept"); arg->addr_dest = (void *) reg->arg2; arg->len_dest = (void *) reg->arg3; }
/** @brief print a strace-like log of bind syscall */ void print_bind_syscall(process_descriptor_t * proc, syscall_arg_u * sysarg) { bind_arg_t arg = &(sysarg->bind); int domain = get_domain_socket(proc, arg->sockfd); // fprintf(proc->strace_out,"[%d] bind(", pid); fprintf(proc->strace_out, "bind("); fprintf(proc->strace_out, "%d, ", arg->sockfd); if (domain == 2) { fprintf(proc->strace_out, "{sa_family=AF_INET, sin_port=htons(%d), sin_addr=inet_addr(\"%s\")}, ", ntohs(arg->sai.sin_port), inet_ntoa(arg->sai.sin_addr)); } else if (domain == 1) { //PF_UNIX fprintf(proc->strace_out, "{sa_family=AF_UNIX, sun_path=\"%s\"}, ", arg->sau.sun_path); } else if (domain == 16) { //PF_NETLINK fprintf(proc->strace_out, "{sa_family=AF_NETLINK, pid=%d, groups=%u}, ", arg->snl.nl_pid, arg->snl.nl_groups); } else { fprintf(proc->strace_out, "{sockaddr unknown}, "); } fprintf(proc->strace_out, "%d", arg->addrlen); fprintf(proc->strace_out, ") = %d\n", arg->ret); }