Find answer to tcp packet in PCAP with scapy - python

I parse pcap file with scapy python , and there is TCP packet in that pcap that I want to know what is the answer of this pcaket, How can I do that?
For example : client and server TCP stream
client-> server : "hi"
server-> client : "how are you"
When I get "hi" packet (with scapy) how can I get "how are you" ?

Look at the TCP sequence number of the message from the client. Call this SeqC.
Then look for the first message from the client whose TCP acknowledgement sequence is higher than SeqC (usually it will be equal to SeqC plus the size of the client's TCP payload). Call this PacketS1.
Starting with PacketS1, collect the TCP payloads from all packets until you see a packet sent by the server with the TCP PSH (push) flag set. This suggests the end of the application-layer message. Call these payloads PayloadS1 to PayloadSN.
Concatenate PayloadS1 to PayloadSN. This is the likely application-layer response to the client message.

Related

python UDP socket - recvfrom works, but getpeername() gives "Transport endpoint is not connected" error?

I have a udp server in python that i'm testing out by sending packets with netcat -u server_ip server_port
on the udp server, I can receive the packets with
data,addrport = socket.recvfrom(some_number) — I can read the data received and see the other socket's address port with addrport.
But if I try to use socket.getpeername() on the same variable instead it gives the OSError: [Errno 107] Transport endpoint is not connected error.
What causes this? I'm confused as my netcat terminal doesn't close after sending, which I assume means its already connected to my UDP socket.
I can receive the packets with data,addrport = socket.recvfrom(some_number)
recvfrom means that you are working with an unconnected UDP socket, i.e. the case where a single socket could receive packets from various sources and also send data to various sources using sendto. getpeername instead expects a connected socket, i.e. one which will only receive data from a single source (using recv not recvfrom) and only send to a single source (using send not sendto). This is the case with TCP established sockets (the ones returned by accept) but also with UDP socket which are explicitly connected by calling connect.

How does TCP handle a file with large size?

I have two questions about TCP protocol :
Has TCP a limitation on the size of each packet to send them? if yes, what is the largest size of each packet to be sent?
and how does TCP handle files with large size? does it send it at
once time(1 packet) or TCP converts it into smaller packets?
and I use python and socket library.
TCP is a streaming protocol. Which means that you as sender have no control over how many send operations are actually going on in the kernel.
There are several mechanisms at play here. A client can call send many times with only one byte. TCP will try to accumulate these bytes until the MTU of the L2 is filled and only then send it, or sooner if a timeout is reached.
In one send operation you can send 64K approx.
To send a file, you need thus several send operatons until the whole file is sent.
On the receiving side of the TCP, there is no relation to the number of send operations and the number of receive operations. If the sender send 5 times 10 bytes consecutively and fast, very likely they will be received as 50 bytes in one receive operation.
Actually for TCP there is no such thing as a packet. It is called a frame.
Packets are used for UDP, because UDP is not a streaming protocol.
In UDP, if you send 5 bytes, the receiver will receive 5 bytes or nothing because UDP is not connection oriented. Whereas TCP is.
For UDP the max size is approx 64k. This 64k will get chopped to pieces by IP to send it over the wire, and IP will put it back together upon reception. This is all because of the L2 MTU.

Netcat only receiving first UDP packet from Scapy and Python

I'm currently making a DNS tunnel in python using Scapy. I can send packets just fine (according to Wireshark). The problem is, when listening on Netcat on what I'm transmitting the dns packets to, I only receive the first packet.
I've heard that when binding, a UDP "connection" (for lack of better words) locks on a port, and drops all other packets from any other source port. However, I defined a source port, so I'm not sure what is going on.
def sendDns(incomingBytes):
print('sending packet data :\n' + incomingBytes.decode('utf-8'))
incomingBytes = base64.encodebytes(incomingBytes)
send(IP(dst=dnsServer)/UDP(dport=53, sport=12345)/DNS(qd=DNSQR(qname=incomingBytes)))

Python TCP Duplicate Message

I'm working on an in-house TCP Server, and TCP client. When there is 0% packet loss the Server and Client work fine. However, when I have 20% or more packet loss I am seeing duplicate TCP messages. I am receiving something like this....
Client <-- MessageA -- Server
Client -- MessageB --> Server
Client <-- MessageCMessageA -- Server
Is it possible that MessageA is not completely making it to the Client, it times outs, then TCP resends it, and then the original message makes it which is received at a later time by the Client?
My question is if TCP works like that, and if that's a possible scenario with a network containing 20% packet loss or more.
Barebones of how the client and server are sending/receiving data...
socket.recv(1024)
socket.send(1024)
No, it is not possible. TCP guarantees that it will either deliver data exactly once and in the order in which it was sent, or signal an error to the application. Hence, there is probably a bug in your code. The most likely is that your code fails to deal with partial reads.
When you perform a write or send on a TCP socket, the TCP module will segment your data into as many packets as are needed. In the presence of packet loss, it is possible that some packets have arrived successfully but others must be resent. In that case, the corresponding read or recv will only receive part of the data — the remaining data will arrive in a subsequent read or recv. In other words, TCP does not preserve message boundaries.
Your code is probably interpreting such a split message as multiple messages. Make sure that you accumulate a full message in your buffer before attempting to parse it.

python / dpkt: Find out if packet is a tcp packet or a udp packet ,

I have a python scripts that captures the packets on the ethernet using dpkt, but how do i differentiate between which packets are tcp and which ones are for udp.
Eventually i would like to have a list of packets for each tcp connection that was established during the time interval.
my code is:
import dpkt
import pcapy
cap=pcap.open_live('eth0',100000,1,0)
(header,payload)=cap.next()
while header:
eth=dpkt.ethernet.Ethernet(str(payload))
ip=eth.data
tcp=ip.data
# i need to know whether it is a tcp or a udp packet here!!!
(header,payload)=cap.next()
IP header contains field protocol. dpkt should allow you to obtain this value and using it you can guess what is on top of IP. Here is a list of valid protocols numbers http://www.iana.org/assignments/protocol-numbers/protocol-numbers.xml.
UDP is equal to 17 while TCP is 6.
Edit:
I have checked this issue and as I mentioned dpkg provide p properties to access protocol field of IP. So you can check agains it. But it also automatically parse packet and set data property to instance of class that represent upper protocol like UDP or TCP. So you can check type of data property and you recognize this protocol.
from dpkt.ip import IP, IP_PROTO_UDP
from dpkt.udp import UDP
ip = IP('E\x00\x00"\x00\x00\x00\x00#\x11r\xc0\x01\x02\x03\x04\x01\x02\x03\x04\x00o\x00\xde\x00\x0e\xbf5foobar')
#if ip.p == IP_PROTO_UDP: # checking for protocol field in ip header
if type(ip.data) == UDP : # checking of type of data that was recognized by dpkg
udp = ip.data
print udp.sport
else:
print "Not UDP"
A python script that captures the packets on the ethernet adapter eth0 using dpkt, and differentiates between TCP and UDP packets of the IP.
import dpkt
import pcapy
cap=pcapy.open_live('eth0',100000,1,0)
(header,payload)=cap.next()
while header:
eth=dpkt.ethernet.Ethernet(str(payload))
# Check whether IP packets: to consider only IP packets
if eth.type!=dpkt.ethernet.ETH_TYPE_IP:
continue
# Skip if it is not an IP packet
ip=eth.data
if ip.p==dpkt.ip.IP_PROTO_TCP: # Check for TCP packets
TCP=ip.data
# ADD TCP packets Analysis code here
elif ip.p==dpkt.ip.IP_PROTO_UDP: # Check for UDP packets
UDP=ip.data
# UDP packets Analysis code here
(header,payload)=cap.next()

Categories

Resources