banner

[Rule] Rules  [Home] Main Forum  [Portal] Portal  
[Members] Member Listing  [Statistics] Statistics  [Search] Search  [Reading Room] Reading Room 
[Register] Register  
[Login] Loginhttp  | https  ]
 
Forum Index Thảo luận mạng và thiết bị mạng Về việc gửi và bắt gói tin sử dụng thư viện libcap.  XML
  [Question]   Về việc gửi và bắt gói tin sử dụng thư viện libcap. 20/03/2012 00:02:52 (+0700) | #1 | 259329
[Avatar]
chiro8x
Member

[Minus]    0    [Plus]
Joined: 26/09/2010 00:38:37
Messages: 661
Location: /home/chiro8x
Offline
[Profile] [PM] [Yahoo!]
Em đang viết một module cho server sử dụng thư viện libcap, xữ lý các gói tin ở tầng data link. Điều em phân vân chuẩn giao tiếp ở tầng data link ở các server có khác với chuẩn dành cho pc không.

Code:
#define ETH_ALEN 6
........
/* 10Mb/s ethernet header */
struct ether_header
{
  u_int8_t  ether_dhost[ETH_ALEN];	/* destination eth addr	*/
  u_int8_t  ether_shost[ETH_ALEN];	/* source ether addr	*/
  u_int16_t ether_type;		        /* packet type ID field	*/
} __attribute__ ((__packed__));


Đoạn mã trên em trích từ file /usr/include/ethernet.h.

Em dân lập trình kiến thức về mạng dốt lắm, ai biết xin chỉ giáo.

p/s: khổ nổi là người ta bắt em làm module trên server mà không cho em sở xem thế nào.
while(1){}
[Up] [Print Copy]
  [Question]   Về việc gửi và bắt gói tin sử dụng thư viện libcap. 20/03/2012 05:53:18 (+0700) | #2 | 259340
[Avatar]
conmale
Administrator

Joined: 07/05/2004 23:43:15
Messages: 9353
Location: down under
Offline
[Profile] [PM]

chiro8x wrote:
Em đang viết một module cho server sử dụng thư viện libcap, xữ lý các gói tin ở tầng data link. Điều em phân vân chuẩn giao tiếp ở tầng data link ở các server có khác với chuẩn dành cho pc không.

Code:
#define ETH_ALEN 6
........
/* 10Mb/s ethernet header */
struct ether_header
{
  u_int8_t  ether_dhost[ETH_ALEN];	/* destination eth addr	*/
  u_int8_t  ether_shost[ETH_ALEN];	/* source ether addr	*/
  u_int16_t ether_type;		        /* packet type ID field	*/
} __attribute__ ((__packed__));


Đoạn mã trên em trích từ file /usr/include/ethernet.h.

Em dân lập trình kiến thức về mạng dốt lắm, ai biết xin chỉ giáo.

p/s: khổ nổi là người ta bắt em làm module trên server mà không cho em sở xem thế nào. 


---> vấn đề là ở hệ điều hành và implementation của từng hệ điều hành chớ không lệ thuộc vào "server" hay "PC".
What bringing us together is stronger than what pulling us apart.
[Up] [Print Copy]
  [Question]   Về việc gửi và bắt gói tin sử dụng thư viện libcap. 20/03/2012 09:49:17 (+0700) | #3 | 259354
vd_
Member

[Minus]    0    [Plus]
Joined: 06/03/2010 03:05:09
Messages: 124
Offline
[Profile] [PM]
@chiro8x

Bạn phải biết bạn viết cho ethernet, FDDI hay 802.11 để xác định các header field cho packet tương ứng -> từ đó cast struct cho đúng. PC có sử dụng cả ethernet và 802.11. Server có lẽ chủ yếu trên nền ethernet.

Bạn dùng wireshark, lưu ý các nó display capture data như là 1 series những struct lồng trong struct để thể hiện mô hình lớp của mạng: layer ở dưới add thêm header (hoặc wrap trong header/footer) vào packet của lớp trên.
[Up] [Print Copy]
  [Question]   Về việc gửi và bắt gói tin sử dụng thư viện libcap. 25/03/2012 20:54:34 (+0700) | #4 | 259824
[Avatar]
chiro8x
Member

[Minus]    0    [Plus]
Joined: 26/09/2010 00:38:37
Messages: 661
Location: /home/chiro8x
Offline
[Profile] [PM] [Yahoo!]
Việc gửi gói tin sử dụng libcap bắt gói tin và phân tích thì ổn rồi. Em sử dụng các file trong thư viện netinet.

Đôi lúc cần thêm đoạn mã sau để enable một số thứ như struct tcphdr.
Code:
#define __FAVOR_BSD 1;


Em thử viết một chương trình gửi một gói SYN nhưng thất bại mặc dù checksum và toàn bộ thông tin em đã hợp lệ nhưng không thấy gói SYN/ACK ném lại. Gói SYN của em liệu có vấn đề gì không ?.

Code:
No.     Time        Source                Destination           Protocol Length Info
      1 0.000000    192.168.1.2           120.138.69.100        TCP      74     38418 > http [SYN] Seq=0 Win=14600 Len=0 MSS=1460 SACK_PERM=1 TSval=279373 TSecr=0 WS=16

Frame 1: 74 bytes on wire (592 bits), 74 bytes captured (592 bits)
Ethernet II, Src: Electros_36:01:95 (00:e0:aa:36:01:95), Dst: D-Link_10:4b:bd (00:1b:11:10:4b:bd)
Internet Protocol Version 4, Src: 192.168.1.2 (192.168.1.2), Dst: 120.138.69.100 (120.138.69.100)
Transmission Control Protocol, Src Port: 38418 (38418), Dst Port: http (80), Seq: 0, Len: 0
    Source port: 38418 (38418)
    Destination port: http (80)
    [Stream index: 0]
    Sequence number: 0    (relative sequence number)
    Header length: 40 bytes
    Flags: 0x02 (SYN)
    Window size value: 14600
    [Calculated window size: 14600]
    Checksum: 0x7fc7 [validation disabled]
        [Good Checksum: False]
        [Bad Checksum: False]
    Options: (20 bytes)
        Maximum segment size: 1460 bytes
        TCP SACK Permitted Option: True
        Timestamps: TSval 279373, TSecr 0
        No-Operation (NOP)
        Window scale: 4 (multiply by 16)


0000   00 1b 11 10 4b bd 00 e0 aa 36 01 95 08 00 45 10  ....K....6....E.
0010   00 3c e9 80 40 00 40 06 d1 92 c0 a8 01 02 78 8a  .<..@.@.......x.
0020   45 64 96 12 00 50 db 22 aa cd 00 00 00 00 a0 02  Ed...P."........
0030   39 08 7f c7 00 00 02 04 05 b4 04 02 08 0a 00 04  9...............
0040   43 4d 00 00 00 00 01 03 03 04                    CM........


À em bắt gói tin này và phần tích từ ngày hôm trước hôm sau em mới lấy gói tin này để thử nghiệm.

Cảm ơn anh conmale và bạn _vd đã giúp đỡ.
while(1){}
[Up] [Print Copy]
  [Question]   Về việc gửi và bắt gói tin sử dụng thư viện libcap. 26/03/2012 09:19:11 (+0700) | #5 | 259854
[Avatar]
chiro8x
Member

[Minus]    0    [Plus]
Joined: 26/09/2010 00:38:37
Messages: 661
Location: /home/chiro8x
Offline
[Profile] [PM] [Yahoo!]
Em tìm ra nguyên nhân rồi ! checksum của gói tin bị sai, hàm tính checksum em đang phải viết lại. Tiện đây em post luôn các links giúp ích cho em rất nhiều. Mong lần sau nếu có bạn nào tìm hiểu về cái này cũng dễ dàng hơn.

http://www.networksorcery.com/enp/protocol/ip.htm
http://www.alhem.net/project/ex10/index.html

Code:
//Checksum
uint16_t cal_checksum(const uint16_t* buf, size_t len)
{
  uint32_t sum = 0;

  for (; nbytes > 1; nbytes -= 2)
  {
    sum += *buf++;
  }

  if (nbytes == 1)
  {
    sum += *(unsigned char*) buf;
  }

  sum  = (sum >> 16) + (sum & 0xFFFF);
  sum += (sum >> 16);

  return ~sum;
}

//cách dùng hàm checksum
    ipcs_ptr = new uint16_t[sizeof(iphdr)];
    memcpy(ipcs_ptr, &hdr_ip, sizeof(iphdr));
    hdr_ip.check = cal_checksum(ipcs_ptr,sizeof(iphdr));
    delete ipcs_ptr;
/*
Trom đó mấy con trỏ động đóng vai trò là bộ đệm để chuyển từ struct iphdr.
*/
while(1){}
[Up] [Print Copy]
  [Question]   Về việc gửi và bắt gói tin sử dụng thư viện libcap. 27/03/2012 08:40:29 (+0700) | #6 | 259939
[Avatar]
chiro8x
Member

[Minus]    0    [Plus]
Joined: 26/09/2010 00:38:37
Messages: 661
Location: /home/chiro8x
Offline
[Profile] [PM] [Yahoo!]
Em đã cố gắng tìm đọc nhiều rồi nhưng vướng mắc về phần TCP / ICMP checksum vẫn chưa thể tháo bỏ được.

Để tính TCP checksum cần tính cả Pseudo Header.
Để tính ICMP checksum cần tính cả data field.

Chương trình em tính toán đúng, đối chiếu với HPING và NMAP vẫn đúng, vậy sao kết quả cuối lại sai. Ai đó giúp em gỡ rối với ! giờ em cảm thấy rất bí.

TCP checksum:
Code:
//......
struct pseudo_header
{
    unsigned int   s_addr;
    unsigned int   d_addr;
    char           reserved;
    unsigned char  protocol;
    unsigned short length;
};
//......
    memset(&hdr_ip, 0x00, sizeof(hdr_ip));

    hdr_ip.version = 4;
    hdr_ip.ihl = 5;
    hdr_ip.tos = 0;
    hdr_ip.tot_len = htons(sizeof(iphdr)+sizeof(icmp_echo_request) + 56);
    hdr_ip.id = 0x0000;
    hdr_ip.frag_off = 0x0040;
    hdr_ip.ttl = 67;
    hdr_ip.protocol = 1;
    hdr_ip.check = 0;
    hdr_ip.saddr = inet_addr("192.168.1.3");
    hdr_ip.daddr = inet_addr("192.168.1.1");
//.....
    pseudo_header hdr_psd;

    hdr_psd.s_addr = hdr_ip.saddr;
    hdr_psd.d_addr = hdr_ip.daddr;
    hdr_psd.reserved = 0x00;
    hdr_psd.protocol = hdr_ip.protocol;
    hdr_psd.length = sizeof(icmphdr);
//......
    uint16_t *pointer;
    pointer = new uint16_t [sizeof(tcphdr)+sizeof(pseudo_header)]; //<-- đây là gói tin SYN không có datafield.
    memcpy(pointer,&hdr_psd, sizeof(pseudo_header));
    memcpy(pointer + sizeof(psedo_header),&hdr_tcp, sizeof(tcphdr));
    hdr_tcp.check = checksum(pointer, sizeof(tcphdr)+sizeof(pseudo_header));
    delete pointer; // em tính đúng như người ta làm nhưng kết quả vẫn sai, chỉ có IP checksum là đúng

Với ICMP checksum:
Code:
memset(&hdr_icmp, 0x00, sizeof(hdr_icmp));
    hdr_icmp.type = 0x08;
    hdr_icmp.code = 0x00;
    hdr_icmp.checksum = 0x00;
    hdr_icmp.un.echo.id = 1087;//random();
    hdr_icmp.un.echo.sequence = htons(11);


char dat[] = {0x32, 0x4b, 0x6f, 0x4f, 0xf1, 0x06,
0x08, 0x00, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d,
0x0e, 0x0f, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15,
0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d,
0x1e, 0x1f, 0x20, 0x21, 0x22, 0x23, 0x24, 0x25,
0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d,
0x2e, 0x2f, 0x30, 0x31, 0x32, 0x33, 0x34, 0x35,
0x36, 0x37 };
    icmpcs_ptr = new uint16_t[sizeof(icmphdr)+56];

    memcpy(icmpcs_ptr, &hdr_icmp, sizeof(icmphdr));
    memcpy(icmpcs_ptr+sizeof(icmphdr), &dat, 56);
    hdr_icmp.checksum = checksum(icmpcs_ptr, sizeof(icmphdr)+56);
    cout << hex << (int)hdr_icmp.checksum << endl;

    delete icmpcs_ptr;
while(1){}
[Up] [Print Copy]
[digg] [delicious] [google] [yahoo] [technorati] [reddit] [stumbleupon]
Go to: 
 Users currently in here 
1 Anonymous

Powered by JForum - Extended by HVAOnline
 hvaonline.net  |  hvaforum.net  |  hvazone.net  |  hvanews.net  |  vnhacker.org
1999 - 2013 © v2012|0504|218|