proc_v6.c 1.3 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950
  1. #include "ping.h"
  2. void
  3. proc_v6(char *ptr, ssize_t len, struct msghdr *msg, struct timeval* tvrecv)
  4. {
  5. #ifdef IPV6
  6. double rtt;
  7. struct icmp6_hdr *icmp6;
  8. struct timeval *tvsend;
  9. struct cmsghdr *cmsg;
  10. int hlim;
  11. icmp6 = (struct icmp6_hdr *) ptr;
  12. if (len < 8)
  13. return; /* malformed packet */
  14. if (icmp6->icmp6_type == ICMP6_ECHO_REPLY) {
  15. if (icmp6->icmp6_id != pid)
  16. return; /* not a response to our ECHO_REQUEST */
  17. if (len < 16)
  18. return; /* not enough data to use */
  19. tvsend = (struct timeval *) (icmp6 + 1);
  20. tv_sub(tvrecv, tvsend);
  21. rtt = tvrecv->tv_sec * 1000.0 + tvrecv->tv_usec / 1000.0;
  22. hlim = -1;
  23. for (cmsg = CMSG_FIRSTHDR(msg); cmsg != NULL; cmsg = CMSG_NXTHDR(msg, cmsg)) {
  24. if (cmsg->cmsg_level == IPPROTO_IPV6 &&
  25. cmsg->cmsg_type == IPV6_HOPLIMIT) {
  26. hlim = *(u_int32_t *)CMSG_DATA(cmsg);
  27. break;
  28. }
  29. }
  30. printf("%d bytes from %s: seq=%u, hlim=",
  31. len, Sock_ntop_host(pr->sarecv, pr->salen),
  32. icmp6->icmp6_seq);
  33. if (hlim == -1)
  34. printf("???"); /* ancillary data missing */
  35. else
  36. printf("%d", hlim);
  37. printf(", rtt=%.3f ms\n", rtt);
  38. } else if (verbose) {
  39. printf(" %d bytes from %s: type = %d, code = %d\n",
  40. len, Sock_ntop_host(pr->sarecv, pr->salen),
  41. icmp6->icmp6_type, icmp6->icmp6_code);
  42. }
  43. #endif /* IPV6 */
  44. }