{"id":2504,"date":"2014-06-10T12:57:08","date_gmt":"2014-06-10T12:57:08","guid":{"rendered":"http:\/\/blog.bachi.net\/?p=2504"},"modified":"2014-06-10T13:06:34","modified_gmt":"2014-06-10T13:06:34","slug":"icmp-echo","status":"publish","type":"post","link":"https:\/\/blog.bachi.net\/?p=2504","title":{"rendered":"ICMP Echo"},"content":{"rendered":"<p><a href=\"http:\/\/www.opensource.apple.com\/source\/network_cmds\/network_cmds-307.0.1\/ping.tproj\/ping.c\">opensource.apple.com: ping.c<\/a><\/p>\n<pre class=\"brush: cpp; title: ping.c; notranslate\" title=\"ping.c\">\r\n\/*\r\n * pinger --\r\n *\tCompose and transmit an ICMP ECHO REQUEST packet.  The IP packet\r\n * will be added on by the kernel.  The ID field is our UNIX process ID,\r\n * and the sequence number is an ascending integer.  The first TIMEVAL_LEN\r\n * bytes of the data portion are used to hold a UNIX &quot;timeval&quot; struct in\r\n * host byte-order, to compute the round-trip time.\r\n *\/\r\nstatic void\r\npinger(void)\r\n{\r\n    &#x5B;...]\r\n    if ((options &amp; F_TIME) || timing) {\r\n        (void)gettimeofday(&amp;now, NULL);\r\n\r\n        if (options &amp; F_TIME)\r\n            icp-&gt;icmp_otime = htonl((now.tv_sec % (24*60*60)) * 1000 + now.tv_usec \/ 1000);\r\n        if (timing)\r\n            bcopy((void *)&amp;now, (void *)&amp;outpack&#x5B;ICMP_MINLEN + phdr_len], sizeof(struct timeval));\r\n    }\r\n    &#x5B;...]\r\n}\r\n<\/pre>\n<pre class=\"brush: cpp; title: \/usr\/include\/netinet\/in_systm.h; notranslate\" title=\"\/usr\/include\/netinet\/in_systm.h\">\r\ntypedef u_int32_t n_time;       \/* ms since 00:00 GMT, byte rev *\/\r\n<\/pre>\n<pre class=\"brush: cpp; title: \/usr\/include\/netinet\/ip_icmp.h; notranslate\" title=\"\/usr\/include\/netinet\/ip_icmp.h\">\r\n#define icmp_otime      icmp_dun.id_ts.its_otime\r\n#define icmp_rtime      icmp_dun.id_ts.its_rtime\r\n#define icmp_ttime      icmp_dun.id_ts.its_ttime\r\n\r\nstruct icmp {\r\n        u_char  icmp_type;              \/* type of message, see below *\/\r\n        u_char  icmp_code;              \/* type sub code *\/\r\n        u_short icmp_cksum;             \/* ones complement cksum of struct *\/\r\n        union {\r\n                u_char ih_pptr;                 \/* ICMP_PARAMPROB *\/\r\n                struct in_addr ih_gwaddr;       \/* ICMP_REDIRECT *\/\r\n                struct ih_idseq {\r\n                        n_short icd_id;\r\n                        n_short icd_seq;\r\n                } ih_idseq;\r\n                int ih_void;\r\n\r\n                \/* ICMP_UNREACH_NEEDFRAG -- Path MTU Discovery (RFC1191) *\/\r\n                struct ih_pmtu {\r\n                        n_short ipm_void;\r\n                        n_short ipm_nextmtu;\r\n                } ih_pmtu;\r\n\r\n                struct ih_rtradv {\r\n                        u_char irt_num_addrs;\r\n                        u_char irt_wpa;\r\n                        u_int16_t irt_lifetime;\r\n                } ih_rtradv;\r\n        } icmp_hun;\r\n        union {\r\n                struct id_ts {                  \/* ICMP Timestamp *\/\r\n                        n_time its_otime;       \/* Originate *\/\r\n                        n_time its_rtime;       \/* Receive *\/\r\n                        n_time its_ttime;       \/* Transmit *\/\r\n                } id_ts;\r\n                struct id_ip  {\r\n                        struct ip idi_ip;\r\n                        \/* options and then 64 bits of data *\/\r\n                } id_ip;\r\n                struct icmp_ra_addr id_radv;\r\n                u_int32_t id_mask;\r\n                char    id_data&#x5B;1];\r\n        } icmp_dun;\r\n};\r\n\r\n<\/pre>\n<p><a href=\"http:\/\/www.wireshark.org\/lists\/wireshark-bugs\/201107\/msg00276.html\">Wireshark-bugs: For ICMP Time Response, In detail pane, Timestamp is incorrectly decoded for MS Windows<\/a><\/p>\n<blockquote><p>\nReference (1):<br \/>\nhttp:\/\/tools.ietf.org\/html\/rfc778<br \/>\n&#8230;<br \/>\n&#8220;The timestamp values are in milliseconds from  midnight<br \/>\nUT and are stored right-justified in the 32-bit fields shown<br \/>\nabove.  Ordinarily,  all  time  calculations  are  performed<br \/>\nmodulo-24 hours in milliseconds.&#8221;\n<\/p><\/blockquote>\n<pre class=\"brush: cpp; title: packet-icmp.c; notranslate\" title=\"packet-icmp.c\">\r\n\r\n\/* Converts a little-endian byte order unsigned long to host byte order. *\/\r\nuint32 LETOHL(uint32 ul);\r\n\r\n\/*\r\n * RFC 792 for basic ICMP.\r\n * RFC 1191 for ICMP_FRAG_NEEDED (with MTU of next hop).\r\n * RFC 1256 for router discovery messages.\r\n * RFC 2002 and 3012 for Mobile IP stuff.\r\n *\/\r\nstatic void\r\ndissect_icmp(tvbuff_t * tvb, packet_info * pinfo, proto_tree * tree)\r\n{\r\n    &#x5B;...]\r\n\r\n    \/* Decode the second 4 bytes of the packet. *\/\r\n    switch (icmp_type) {\r\n    \r\n    &#x5B;...]\r\n    \r\n    case ICMP_ECHOREPLY:\r\n    case ICMP_ECHO:\r\n        \r\n        &#x5B;...]\r\n        \r\n        \/* Interpret the first 8 bytes of the icmp data as a timestamp\r\n         * But only if it does look like it's a timestamp.\r\n         *\r\n         * FIXME:\r\n         *    Timestamps could be in different formats depending on the OS\r\n         *\/\r\n        ts.secs  = tvb_get_ntohl(tvb, 8);\r\n        ts.nsecs = tvb_get_ntohl(tvb, 8 + 4);   \/* Leave at microsec resolution for now *\/\r\n        \r\n        if (abs((guint32) (ts.secs - pinfo-&gt;fd-&gt;abs_ts.secs)) &gt;=\r\n            3600 * 24 || ts.nsecs &gt;= 1000000) {\r\n            \/* Timestamp does not look right in BE, try LE representation *\/\r\n            ts.secs  = tvb_get_letohl(tvb, 8);\r\n            ts.nsecs = tvb_get_letohl(tvb, 8 + 4);  \/* Leave at microsec resolution for now *\/\r\n        }\r\n        if (abs((guint32) (ts.secs - pinfo-&gt;fd-&gt;abs_ts.secs)) &lt; 3600 * 24 &amp;&amp; ts.nsecs &lt; 1000000) {\r\n            ts.nsecs *= 1000;   \/* Convert to nanosec resolution *\/\r\n            proto_tree_add_time(icmp_tree, hf_icmp_data_time,\r\n                                tvb, 8, 8, &amp;ts);\r\n            nstime_delta(&amp;time_relative, &amp;pinfo-&gt;fd-&gt;abs_ts,\r\n                         &amp;ts);\r\n            ti = proto_tree_add_time(icmp_tree,\r\n                                     hf_icmp_data_time_relative,\r\n                                     tvb, 8, 8,\r\n                                     &amp;time_relative);\r\n            PROTO_ITEM_SET_GENERATED(ti);\r\n            call_dissector(data_handle,\r\n                       tvb_new_subset_remaining(tvb,\r\n                                8 + 8),\r\n                       pinfo, icmp_tree);\r\n        } else {\r\n            call_dissector(data_handle,\r\n                       tvb_new_subset_remaining(tvb, 8),\r\n                       pinfo, icmp_tree);\r\n        }\r\n        break;\r\n        \r\n        &#x5B;...]\r\n    }\r\n    \r\n    &#x5B;...]\r\n}\r\n<\/pre>\n","protected":false},"excerpt":{"rendered":"<p>opensource.apple.com: ping.c \/* * pinger &#8212; * Compose and transmit an ICMP ECHO REQUEST packet. The IP packet * will be added on by the kernel. The ID field is our UNIX process ID, * and the sequence number is an ascending integer. The first TIMEVAL_LEN * bytes of the data portion are used to [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[1],"tags":[],"class_list":["post-2504","post","type-post","status-publish","format-standard","hentry","category-uncategorized"],"_links":{"self":[{"href":"https:\/\/blog.bachi.net\/index.php?rest_route=\/wp\/v2\/posts\/2504","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/blog.bachi.net\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/blog.bachi.net\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/blog.bachi.net\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/blog.bachi.net\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=2504"}],"version-history":[{"count":6,"href":"https:\/\/blog.bachi.net\/index.php?rest_route=\/wp\/v2\/posts\/2504\/revisions"}],"predecessor-version":[{"id":2510,"href":"https:\/\/blog.bachi.net\/index.php?rest_route=\/wp\/v2\/posts\/2504\/revisions\/2510"}],"wp:attachment":[{"href":"https:\/\/blog.bachi.net\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=2504"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/blog.bachi.net\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=2504"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/blog.bachi.net\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=2504"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}