I want to be able to simulate an incoming packet on a certain physical network interface.
Specifically, given an array of bytes and an interface name, I want to be able to make that interface think a packet containing those bytes arrived from another interface (most likely on another machine).
I've implemented the code that prepares the packet, but I'm unsure what the next step is.
I should point out that I actually need to feed the interface with my bytes, and not use a workaround that might produce a similar results in other machines (I've seen answers to other questions mentioning the loopback interface and external tools). This code is supposed to simulate traffic on a machine that's expecting to receive traffic from certain sources via specific interfaces. Anything else will be ignored by the machine.
I'm going to stick my neck out and say this is not possible without kernel modifications, and possibly driver modifications. Note that:
There are plenty of ways of generating egress packets through a particular interface, including libpcap. But you want to generate ingress packets.
There are plenty of ways of generating ingress packets that are not through a physical interface - this is what tap/tun devices are for.
If you modify the kernel to allow direct injection of packets into a device's receive queue, that may have unexpected effects, and is still not going to be an accurate simulation of the packets arriving in hardware (e.g. they will not be constrained to the same MTU etc). Perhaps you can build an iptables extension that fools the kernel into thinking the packet came from a different interface; I'm not sure that will do what you need though.
If all you need is simulation (and you are happy with a complete simulation), build a tap/tun driver, and rename the tap interface to eth0 or similar.
Depending on which network layer you're trying to simulate, there may be a work-around.
I have had success getting ip packets into the ingress queue with an ethernet 'hairpin'. That is, by setting the source and destination MAC address to the local interface, sending the packet results in it first appearing as an egress packet, then being 'hairpinned' and also appearing as an ingress packet.
This at least works under linux using pcapplusplus (libpcap under the hood), with my wireless interface. Your millage may vary.
This will obviously only suit your needs if you're OK with modifying the ethernet header, ie only simulating a higher layer.
Here is a snippet of c++ where I spoof a rst tcp packet for a local socket:
//always use the actual device source MAC, even if we're spoofing the remote rst
// this produces a 'hairpin' from the egress to the ingress on the interface so the tcp stack actually processes the packet
// required because the tcp stack doesn't process egress packets (at least on a linux wireless interface)
pcpp::EthLayer eth(localMAC,localMAC);
pcpp::IPv4Layer ip(remoteIP, localIP);
pcpp::TcpLayer tcp(remotePort, localPort);
pcpp::Packet pac(60);
ip.getIPv4Header()->timeToLive = 255;
tcp.getTcpHeader()->rstFlag = 1;
tcp.getTcpHeader()->ackFlag = 1;
tcp.getTcpHeader()->ackNumber = pcpp::hostToNet32(src.Ack);
tcp.getTcpHeader()->sequenceNumber = pcpp::hostToNet32(src.Seq);
pac.addLayer(ð);
pac.addLayer(&ip);
pac.addLayer(&tcp);
pac.computeCalculateFields();
dev->sendPacket(&pac);
EDIT: the same code works on windows on an ethernet interface. It doesn't seem to do the same 'hairpin' judging from wireshark, but the tcp stack does process the packets.
Another solution is to create a new dummy network device driver, which will have the same functionality as the loopback interface (i.e. it will be dummy). After that you can wrap up a creation of simple tcp packet and specify in the source and destination addresses the addresses of the two network devices.
It sounds a little hard but it's worth trying - you'll learn a lot for the networking and tcp/ip stack in linux.
Related
if I malfunctioned my computer TCP stack in kernel just commenting out single important line of code or compiling with excluding TCP stack and install. Then What are the steps in I need to take in coding. Do I need to Implement Ethernet (if creates layer 2 Socket in my stack implementation) then do I need to implement IP because that comes with if I am using layer 2 socket then implement TCP (this is what final code will be)
If that's so
Then what are the supported protocols I need to implement to cover ethernet layer, Ip layer and (TCP layer -- that I can know I may have used it in code)
Can anyone please tell the machining protocols with each layer
whats before?-->ethernet --> ip -- tcp --> http <--protocol names please that may be needed
the whole thing is just for as a research thing or learning for my self or just may be programming
I'll assume you want to be able to do something like request https://example.com from a web server.
For this the following procotols are diretly necessary:
HTTPS (i.e. HTTP and TLS), but that's usually already implemented in user space, no change here
DNS to resolve example.com to an IP address. Usually implemented in user space as well, based on UDP
UDP to run DNS on top of. Usually implemented in the kernel on top of IP.
TCP to run HTTPS on top of. Usually implemented in the kernel on top of IP.
IP to run both TCP and UDP on top of. Usually implemented in the kernel on top of Ethernet.
Ethernet to send/receive IP packages. Usually implemented in the kernel, with the help of hardware-specific NIC drivers.
But even if you had implemented those, you wouldn't be done. For example, you wouldn't know what your local IP address is.
To do this, you'd implement DHCP. You could get away without implementing this, if you just configured your IP address to a fixed value (as long as it's within the allowed range of your network and doesn't conflict with other devices, this is not a problem).
But when you try to send your first IP packet to the DNS server, you'd realize that you don't know what Ethernet address you should send that to. So you'd need to implement ARP as well. Again, you could theoretically have a static routing table and "fake" the ARP responses by your router this way, but this could be way trickier than just hard-coding the IP adress.
I may have missed some protocol (and I'm sure comments will pop up, if I did), but that should be roughly everything that you'd need to get going.
Is there a way to view all the IPv4 packets sent to a Linux computer?
I know I can capture the packets at the ethernet level using libpcap. This can work, but I don't really want to defragment the IPv4 packets. Does libpcap provide this functionality and I'm just missing it?
One thing that kinda works is using a tun device. I can capture all the IPv4 traffic by routing all traffic to the tun device via something like ip route add default via $TUN_IP dev $TUNID. This also stops outbound traffic though, which is not what I want.
I just want to see the IPv4 packets, not intercept them. (Or, even better, optionally intercept them.)
Edit: I'm specifically looking for a programmatic interface to do this. E.g. something I can use from within a C program.
Yes, you can see all the packets that arrive at your network interface. There are several options to access or view them. Here a small list of possible solutions, where the first one is the easiest and the last one the hardest to utilize:
Wireshark
I'd say this is pretty much the standard when it comes to protocol analyzers with a GUI (uses libpcap). It has tons of options, a nice GUI, great filtering capabilities and reassembles IP datagrams. It uses libpcap and can also show the raw ethernet frame data. For example it allows you to see layer 2 packets like ARP. Furthermore you can capture the complete data arriving at your network interface in a file that can later be analyzed (also in Wireshark).
tcpdump
Very powerful, similar features like Wireshark but a command line utility, which also uses libpcap. Can also capture/dump the complete interface traffic to a file. You can view the dumped data in Wireshark since the format is compatible.
ngrep
This is known as the "network grep" and is similar to tcpdump but supports regular expressions (regex) to filter the payload data. It allows to save captured data in the file format supported by Wireshark and tcpdump (also uses libpcap).
libnids
Quotation from the official git repository:
"Libnids is a library that provides a functionality of one of NIDS
(Network Intrusion Detection System) components, namely E-component. It means
that libnids code watches all local network traffic [...] and provides convenient information on them to
analyzing modules of NIDS. Libnids performs:
assembly of TCP segments into TCP streams
IP defragmentation
TCP port scan detection"
libpcap
Of course you can also write your own programs by using the library directly. Needless to say, this requires more efforts.
Raw or Packet Sockets
In case you want to do all the dirty work yourself, this is the low level option, which of course also allows you to do everything you want. The tools listed above use them as a common basis. Raw sockets operate on OSI layer 3 and packet sockets on layer 2.
Note: This is not meant to be a complete list of available tools or options. I'm sure there are much more but these are the most common ones I can think of.
Technically you have to make a copy of the received packet via libpcap. To be more specific, what you can do is to get packets with libpcap, that way the packets will be kind of blocked, so you need to re send them to the destination. Lets say that you want to make a Fire-Wall or something, what you should do is to have a layer that can work like getting the package and then send it to the destination, in between you can make a copy of what you got for further processes. In order to make the intercept option, you need to create some predefined rules, i.e. the ones that violates the rules will not be send again to their destination.
But that needs a lot of efforts and I don't think you want to waist your life on it.
Wire-shark as mentioned by #Barmar can do the job already.
If you need some kind of command line interface option I would say that "tcpdump" is one of the best monitoring tools. for example for capturing all ipv4 HTTP packets to and from port 80 the command will be:
tcpdump 'tcp port 80 and (((ip[2:2] - ((ip[0]&0xf)<<2)) - ((tcp[12]&0xf0)>>2)) != 0)'
for more information and options see tcpdump
Please be specific if you need to write a program for it, then we can help about how to do it.
I am working on a project like "openvswitch" --- a linux kernel modules that interfaces with
various network interface cards.
You can bind some network interfaces (like eth0, eth1) to the module, and then packet received from the interfaces will be handled by the kernel module (it may modified the packet header and send the packet from another binding interface).
In a virtual machine environment, I can easily do the development work (kernel space programming often crash the machine) but I can hardly do the testing work. It is difficulty to
send a specific packet to the vm's specific interface. Is there any easy way for this?
Use a traffic generation tool like Scapy on your hypervisor to send traffic to the virtual NICs that are attached to your VM. With qemu/libvirt these interfaces normally come up as "vnet0", "vnet1", etc.
Do not use bridges, but send traffic directly to the vnic. Linux bridges are good at forwarding IP traffic but will not let every ethernet frame go through unmodified.
I believe that my question is:
Is there a simple user-mode TCP stack on PC operating systems that could be used to exchange data over a lossy serial link with a Linux-based device?
Here is more context:
I have a Linux-based device connected via a serial link to a PC. The serial link is lossy so data being sent between the two devices sometimes needs to be retransmitted. Currently the system uses a custom protocol that includes framing, addressing (for routing to different processes within the Linux device), and a not-so-robust retransmission algorithm.
On the Linux device side, it would be convenient to replace the custom protocol, implement SLIP over the serial link and use TCP for all communications. The problem is that on the PC-side, we're not sure how to use the host's TCP stack without pulling in general IP routing that we don't need. If there were a user-mode TCP stack available, it seems like I could integrate that in the PC app. The only TCP stacks that I've found so far are for microcontrollers. They could be ported, but it would be nice if there were something more ready-to-go. Or is there some special way to use the OS's built in TCP stack without needing administrative privileges or risking IP address conflicts with the real Ethernet interfaces.
Lastly, just to keep the solution focused on TCP, yes, there are other solutions to this problem such as using HDLC or just fixing our custom protocol. However, we wanted to explore the TCP route further in case it was an option.
It appears that the comments have already answered your question, but perhaps to clarify; No you can not use TCP without using IP. TCP is built on top of IP, and it isn't going to work any other way.
PPP is a good way of establishing an IP connection over a serial link, but if you do not have administrative access on both sides of the computer this could be difficult. 172.16.x, 10.x, and 192.168.x are defined as being open for local networks, so you should be able to find a set of IP addresses that does not interfere with the network operation of the local computer.
From the point of view of no configuration, no dependencies, comping up with your own framing / re-transmit protocol should not be too hard, and is probably your best choice if you don't need inter-operability. That being said kermit, {z,y,z}modem would provide both better performance and a standard to code against.
Lastly, you may be able to use something like socat to do protocol translation. I.e. connect a serial stream to a TCP port. That wouldn't address data reliability / re-transmission, but it may be the interface you are looking to program against.
I am currently working on a programming assignment. The assignment is to implement a client,network emulator, and server. The client passes packets to a network emulator, and the network emulator passes to the server. Vice-versa applies as well. The prerequisite for the assignment is that I may only use raw sockets. So I will create my own IP and UDP headers. I have tested my packets with wireshark. They are all correct and in the proper format(it reads them properly).
Another requirement is that the emulator, client and server all have specific ports they must be bound to. Now, I do not understand how to bind a raw socket to a specific port. All my raw sockets receive all traffic on the host address they are bound to. According to man pages, and everywhere else on the internet, including "Unix Network Programming" by Richard Stevens, this is how they are supposed to work. My teacher has not responded to any of my emails and I probably will not be able to ask him until Tuesday.I see two options in front of me. First I can use libpcap to filter from a specific device and then output to my raw socket. I feel this is way out of scope for our assignment though. Or I can filter them after I receive them from the socket. This apparently has a lot of overhead because all the packets are being copied/moved through the kernel. At least, that is my understanding(please feel free to correct me if i'm wrong).
So my question is:
Is their an option or something I can set for this? Where the raw socket will bind to a port? Have I missed something obvious?
Thank you for your time.
--
The man page for raw(7) says:
A raw socket can be bound to a specific local address using the bind(2) call. If it isn't bound all packets with the specified IP protocol are received. In addition a RAW socket can be bound to a specific network device using SO_BINDTODEVICE; see socket(7).
Edit: You cannot bind a raw socket to a specific port because "port" is a concept in TCP and UDP, not IP. Look at the header diagrams for those three protocols and it should become obvious: you are working at a lower level, where the concept of port is not known.
I would think you're expected to filter the packets in your software. It sounds like the exercise is to learn what the different components of the IP stack do by recreating a simplified piece of it in user space. Normally in the kernel, the IP code would process all packets, verify the IP headers, reassemble fragments, and check the protocol field. If the protocol field is 17 (udp), then it passes it to the UDP code (every UDP packet). It's up to the UDP code to then validate the UDP header and determine if any applications are interested in them based on the destination port.
I imagine your project is expected to more or less mimic this process. Obviously none of it will be as efficient as doing it in the kernel, but since the assignment is to write (part of) an IP stack in user-space, I'd guess efficiency isn't the point of the exercise.