Search code examples
cnetwork-programminglibpcap

Acknowledgment Number in libpcap


I'm trying to print acknowledgment numbers using libpcap. I do understand that I will get ack numbers different than the ones I see in the pcap file. My problem is that in the pcap file packet number 10 , 11 ,and 12 have different ack numbers and when I print them they all have the same numbers. Can someone please tell me how to print the ack number.

Pcap file: Packets in wireshark

Here is the Output :

num: 10 Timest: 358.312120 tcpACK: 14817 ack_seq: 32784

num: 11 Timest: 358.313252 tcpACK: 14817 ack_seq: 32784

num: 12 Timest: 358.313414 tcpACK: 14817 ack_seq: 32784

Here is some parts of the code :

   struct tcp_hdr {
         u_short th_sport;   // source port 
         u_short th_dport;   // destination port 
         u_int32_t th_seq;       // sequence number 
         u_int32_t th_ack;       // acknowledgement number 
         u_int32_t ack_seq;
         u_char th_offx2;    // data offset, rsvd 
         #define TH_OFF(th)  (((th)->th_offx2 & 0xf0) >> 4)
         u_char th_flags;
         #define TH_FIN 0x01
         #define TH_SYN 0x02
         #define TH_RST 0x04
         #define TH_PUSH 0x08
         #define TH_ACK 0x10
         #define TH_URG 0x20
         #define TH_ECE 0x40
         #define TH_CWR 0x80
         #define TH_FLAGS 
        (TH_FIN|TH_SYN|TH_RST|TH_ACK|TH_URG|TH_ECE|TH_CWR)
        u_short th_win;     // window 
        u_short th_sum;     // checksum 
        u_short th_urp;     // urgent pointer 
                                      };

        if (tcp->th_flags & TH_ACK)
        {
              struct timeval time= header->ts;
              int tcpack = ntohs(tcp->th_ack);
              int seq = ntohs(tcp->th_seq);
              int ack_seq=ntohs(tcp->ack_seq);


             printf("num: %d \n", pcount );  //print packet number 
             printf("Timest: %d.%06d \n",((int)time.tv_sec % 1000),(int)time.tv_usec);  //print packet timestamp
             printf("tcpACK: %d \n", tcpack ); 
             printf("ack_seq: %d \n\n", ack_seq );


        }

Solution

  • First of all, this declaration is not OK:

    u_int32_t ack_seq;
    

    After th_ack you have the offset (4 bits), reserved bits (3 bits), and flags (9 bits). See: https://en.wikipedia.org/wiki/Transmission_Control_Protocol

    Second, you are using conversion macros for short int when the SEQ and ACK are 4-Byte long. You should use ntohl. Third, don't use int because it's signed, use unsigned int and print it as unsigned it.

    unsigned int tcpack = ntohl(tcp->th_ack);
    unsigned int seq = ntohl(tcp->th_seq);
    

    Use unsigned int or uint32_t.

    printf("tcpACK: %u \n", tcpack ); 
    printf("tcpACK: %X \n", tcpack ); 
    printf("seq: %u \n\n", seq );
    printf("seq: %X \n\n", seq );