static void print_setsockopt(struct tcb *tcp, int level, int name, long addr, int len) { if (addr && verbose(tcp)) switch (level) { case SOL_SOCKET: switch (name) { #ifdef SO_LINGER case SO_LINGER: print_linger(tcp, addr, len); goto done; #endif } break; case SOL_IP: switch (name) { #ifdef IP_ADD_MEMBERSHIP case IP_ADD_MEMBERSHIP: case IP_DROP_MEMBERSHIP: print_mreq(tcp, addr, len); goto done; #endif /* IP_ADD_MEMBERSHIP */ #ifdef MCAST_JOIN_GROUP case MCAST_JOIN_GROUP: case MCAST_LEAVE_GROUP: print_group_req(tcp, addr, len); goto done; #endif /* MCAST_JOIN_GROUP */ } break; case SOL_IPV6: switch (name) { #ifdef IPV6_ADD_MEMBERSHIP case IPV6_ADD_MEMBERSHIP: case IPV6_DROP_MEMBERSHIP: # ifdef IPV6_JOIN_ANYCAST case IPV6_JOIN_ANYCAST: # endif # ifdef IPV6_LEAVE_ANYCAST case IPV6_LEAVE_ANYCAST: # endif print_mreq6(tcp, addr, len); goto done; #endif /* IPV6_ADD_MEMBERSHIP */ } break; case SOL_PACKET: switch (name) { #ifdef PACKET_RX_RING case PACKET_RX_RING: # ifdef PACKET_TX_RING case PACKET_TX_RING: # endif print_tpacket_req(tcp, addr, len); goto done; #endif /* PACKET_RX_RING */ #ifdef PACKET_ADD_MEMBERSHIP case PACKET_ADD_MEMBERSHIP: case PACKET_DROP_MEMBERSHIP: print_packet_mreq(tcp, addr, len); goto done; #endif /* PACKET_ADD_MEMBERSHIP */ } break; case SOL_RAW: switch (name) { #ifdef ICMP_FILTER case ICMP_FILTER: print_icmp_filter(tcp, addr, len); goto done; #endif } break; } /* default arg printing */ if (verbose(tcp)) { if (len == sizeof(int)) { printnum_int(tcp, addr, "%d"); } else { printstr(tcp, addr, len); } } else { printaddr(addr); } done: tprintf(", %d", len); }
static void print_group_req(struct tcb *tcp, long addr, int len) { struct group_req greq; if (len != sizeof(greq) || umove(tcp, addr, &greq) < 0) { tprintf("%#lx", addr); return; } union { struct sockaddr *sa; struct sockaddr_in *sin; #ifdef HAVE_INET_NTOP struct sockaddr_in6 *sin6; #endif } a = { .sa = (struct sockaddr *) &greq.gr_group }; #ifdef HAVE_INET_NTOP char str[INET6_ADDRSTRLEN]; #endif tprintf("{gr_interface=%u, gr_group={sa_family=", greq.gr_interface); printxval(addrfams, a.sa->sa_family, "AF_???"); switch (a.sa->sa_family) { case AF_INET: tprintf(", sin_port=htons(%u), sin_addr=inet_addr(\"%s\")}}", ntohs(a.sin->sin_port), inet_ntoa(a.sin->sin_addr)); return; #ifdef HAVE_INET_NTOP case AF_INET6: if (!inet_ntop(AF_INET6, &a.sin6->sin6_addr, str, sizeof(str))) break; tprintf(", sin6_port=htons(%u)" ", inet_pton(AF_INET6, \"%s\", &sin6_addr)}}", ntohs(a.sin6->sin6_port), str); return; #endif /* HAVE_INET_NTOP */ } tprints(", sa_data="); print_quoted_string(a.sa->sa_data, sizeof(a.sa->sa_data), 0); tprintf("}}"); } #endif /* MCAST_JOIN_GROUP */ #ifdef PACKET_RX_RING static void print_tpacket_req(struct tcb *tcp, long addr, int len) { struct tpacket_req req; if (len != sizeof(req) || umove(tcp, addr, &req) < 0) { tprintf("%#lx", addr); } else { tprintf("{block_size=%u, block_nr=%u, " "frame_size=%u, frame_nr=%u}", req.tp_block_size, req.tp_block_nr, req.tp_frame_size, req.tp_frame_nr); } } #endif /* PACKET_RX_RING */ #ifdef PACKET_ADD_MEMBERSHIP # include "xlat/packet_mreq_type.h" static void print_packet_mreq(struct tcb *tcp, long addr, int len) { struct packet_mreq mreq; if (len != sizeof(mreq) || umove(tcp, addr, &mreq) < 0) { tprintf("%#lx", addr); } else { unsigned int i; tprintf("{mr_ifindex=%u, mr_type=", mreq.mr_ifindex); printxval(packet_mreq_type, mreq.mr_type, "PACKET_MR_???"); tprintf(", mr_alen=%u, mr_address=", mreq.mr_alen); if (mreq.mr_alen > ARRAY_SIZE(mreq.mr_address)) mreq.mr_alen = ARRAY_SIZE(mreq.mr_address); for (i = 0; i < mreq.mr_alen; ++i) tprintf("%02x", mreq.mr_address[i]); tprints("}"); } } #endif /* PACKET_ADD_MEMBERSHIP */ static void print_setsockopt(struct tcb *tcp, int level, int name, long addr, int len) { if (addr && verbose(tcp)) switch (level) { case SOL_SOCKET: switch (name) { #ifdef SO_LINGER case SO_LINGER: print_linger(tcp, addr, len); goto done; #endif } break; case SOL_IP: switch (name) { #ifdef IP_ADD_MEMBERSHIP case IP_ADD_MEMBERSHIP: case IP_DROP_MEMBERSHIP: print_mreq(tcp, addr, len); goto done; #endif /* IP_ADD_MEMBERSHIP */ #ifdef MCAST_JOIN_GROUP case MCAST_JOIN_GROUP: case MCAST_LEAVE_GROUP: print_group_req(tcp, addr, len); goto done; #endif /* MCAST_JOIN_GROUP */ } break; case SOL_IPV6: switch (name) { #ifdef IPV6_ADD_MEMBERSHIP case IPV6_ADD_MEMBERSHIP: case IPV6_DROP_MEMBERSHIP: # ifdef IPV6_JOIN_ANYCAST case IPV6_JOIN_ANYCAST: # endif # ifdef IPV6_LEAVE_ANYCAST case IPV6_LEAVE_ANYCAST: # endif print_mreq6(tcp, addr, len); goto done; #endif /* IPV6_ADD_MEMBERSHIP */ } break; case SOL_PACKET: switch (name) { #ifdef PACKET_RX_RING case PACKET_RX_RING: # ifdef PACKET_TX_RING case PACKET_TX_RING: # endif print_tpacket_req(tcp, addr, len); goto done; #endif /* PACKET_RX_RING */ #ifdef PACKET_ADD_MEMBERSHIP case PACKET_ADD_MEMBERSHIP: case PACKET_DROP_MEMBERSHIP: print_packet_mreq(tcp, addr, len); goto done; #endif /* PACKET_ADD_MEMBERSHIP */ } break; case SOL_RAW: switch (name) { #ifdef ICMP_FILTER case ICMP_FILTER: print_icmp_filter(tcp, addr, len); goto done; #endif } break; } /* default arg printing */ if (verbose(tcp)) { if (len == sizeof(int)) { printnum_int(tcp, addr, "%d"); } else { printstr(tcp, addr, len); } } else { tprintf("%#lx", addr); } done: tprintf(", %d", len); } SYS_FUNC(setsockopt) { if (entering(tcp)) { print_sockopt_fd_level_name(tcp, tcp->u_arg[0], tcp->u_arg[1], tcp->u_arg[2]); print_setsockopt(tcp, tcp->u_arg[1], tcp->u_arg[2], tcp->u_arg[3], tcp->u_arg[4]); } return 0; }