Network subsystem in the OS

For future students of the course “Network engineer” and all those interested have prepared a useful article.

We also invite you to an open webinar on the topic “NAT is not a Firewall”… Participants of the webinar, together with an expert, will discuss NAT and its use, why NAT! = Firewall, as well as different types of configurations for different situations.


In this article, a study of the network subsystem of Windows and Linux OS will be carried out, as well as a plan for studying the operating system subsystems. The main task of the research is to understand what the network subsystem consists of; what protocols it supports out of the box; what additional mechanisms it uses in its work.

Disclamer: The article describes data that, from the point of view of the author, will help to understand how operating systems work with the TCP / IP model, and does not claim to be complete.

Research tools and method

To study the operating system, we will use the following tools:

  • Linux operating system:

    • git;

    • Visual Stuio Code;

  • Windows operating system:

    • strings.exe;

    • radare2;

    • hxD Editor;

    • Python;

    • Process Explorer.

The tools are selected in such a way that you can cover the maximum number of file formats that can be found in the OS. For the source code, the main tool is the editor, which allows you to conveniently switch from source to source for parsing the code.

In our study, we will be guided by two rules:

  1. We use all the information from the operating system documentation;

  2. We check the veracity of the described data. For data structures:

    • In Windows, we examine the dll and sys files corresponding to the functionality;

    • In Linux, we explore the source codes and individual branches kernels;

Now let’s define the problems that are likely to haunt us throughout the study.

Linux OS research problems

The main functionality of the subsystem is entirely in the kernel. Fortunately, the source code is available online. Examining the source code of such large projects is always a challenge. Its complexity can be influenced by several factors:

  1. Subjective:

    • each researcher has a different level of expertise in the programming language used in the source code;

    • each researcher has his own approach to interpreting the information received.

  2. Objective:

    • limited research time;

    • source code size;

    • accepted project coding rules.

How to minimize the number of actions of a researcher in order to get as much useful and interesting information as possible? A properly configured workplace plays a huge role. In our case, the correct setting is determined by the set of tools, which we described in the section “Tools and research method”. You can also apply a little life hack and not look at every line of the kernel source, but consider only high-level elements. This will save time on learning the programming language and will give you the opportunity to figure out what’s what. Let’s try to apply this tactic in practice.

Linux networking subsystem

Let’s start our research with this interesting picture:

The picture represents the directory structure of the Linux kernel source code. It shows that the networking subsystem is not at all the largest part of the operating system. In truth, you can build a kernel without this part. Today it is only an option for embeded systems, in general it is difficult to imagine Linux without a network.

The code for the networking subsystem is in the “net” directory. Let’s see what it consists of.

The source code is compiled for the tasks to be performed. For basic elements, you can refer to the core directory:

In the picture, the names of the files are highlighted, which describe the basic structures for working with the network. This is the creation of sockets, storage of transmitted data and work with the filtering subsystem. bfp… It is this code that is reused for the rest of the networking subsystem.

The remaining files in the “net” directory describe how the kernel works with various protocols. An interesting point here is that the filtering subsystem has some files only in some protocols and subsystems:

The rectangles mark those protocols and subsystems that contain files netfilter… As you can see from the picture, the traffic filtering mechanism does not work with all protocols. It is also interesting that it is present not only in protocols, but also in a higher-level abstraction – bridge… Now it is clear why the bridge from Linux can be configured so flexibly and control the data sent.

What’s the bottom line? In total, based on 4 pictures of the structure of the kernel source codes, we already have information about which protocols are supported in the Linux kernel, which mechanisms are integrated into the protocols for control and filtering, and where to find the basic elements that allow using the network. Let’s try to find this information in Windows.

Windows OS: networking subsystem

It will not work to study the network subsystem of this OS as easily as in the Linux OS. The biggest sticking point is closed source. However, let’s try to recover information about how the network subsystem works within this OS. We will use what we found in Linux as targets:

  • Where is the code for creating and working with sockets located;

  • What mechanism is used for filtering;

  • How protocols are implemented.

    The network subsystem, according to documentation built on the principle of the OSI model. And also a description is given of what technologies and file types are used to implement the work of individual levels of the model.

Implementation of the OSI model in an operating system starts at well-defined levels. In this case, everything starts at the “Channel” level and ends at the “Transport” level. Implementation at each level is different:

  • Link layer – consists of MAC and LLC, respectively, and there should be two parts of the implementation:

    • MAC – miniportdriver is a driver that controls the network interface;

    • LLC – protocol driver – a driver used to process data from network devices;

  • Network layer – protocol driver – driver used to process data from network devices;

  • Transport layer – protocol (transport) driver;

So the fundamental difference between Windows and Linux was revealed – the entire logic of the network subsystem is broken down into many elements. Every device, every protocol and abstraction is not implemented in the kernel, but in a kernel module – a driver that can be loaded by the kernel on demand. What does this mean for us? We do not have the source code for these drivers, which means we cannot use the approach that we used to study Linux OS.

How to be? When developing exploits, researchers use an open source project as a starting point for rebuilding structures within the Windows kernel – ReactOS… Let’s try to do the same. Let’s find parts of the subsystem and then project the information we find onto a real Windows OS.

The screen below is a snapshot of the main drivers directory for the networking subsystem:

Let’s try to find the same files in a real OS. Let’s look into the “% Windows%” directory. As the system under study, we take Windows 7

Some of the files actually have file names that are present in the real OS.

One way to test the functionality of an already compiled application is to read the strings it uses. For this we can use the strings.exe utility to tcpip.sys:

It seems that data on working with the network subsystem can be found in this driver. Let’s look for functions that allow us to filter traffic. How do you identify them?

In the Windows operating system for the entire time of its existence, there were 2 technical specifications on the basis of which drivers for network communication were created: TDI and WinSock… And all these specifications used a separate driver in order to be able to collect all the functionality – NDIS… This means that most of the functions are concentrated in these drivers:

  • netio.sys

  • tcpip.sys

  • tdi.sys

  • ndis.sys

But they still lack features that could filter traffic. Why is that? The fact is that before Windows 7, traffic filtering as such was implemented in separate drivers that were configured using the Windows interface. Since Windows 7, the so-called Windows Filtering Platform, which has identified some of the drivers in a special category, which is designed to filter traffic.

Some of these filters can be found by a regular search in the OS directories:

 Get-ChildItem "C:WINDOWSSystem32" FWPKCLNT.SYS -Recurse | Select-Object FullName
 Get-ChildItem "C:WINDOWSSystem32" wfplwf.sys -Recurse | Select-Object FullName

We use the strings.exe utility for files FWPKCLNT.SYS and wfplwf.sys:

Above is some of the lines that were found in the file FWPKCLNT.sys, file wfplwf.sys contained only function names. Why then are they here together? The fact is that in imports wfplwf.sys there is a function that is taken from a file FWPKCLNT.sys:

Eventually:

  1. Implementation of all objects and mechanisms in the kernel for working with protocols – files from the directory %Windows%System32Drivers… The main ones are netio.sys, ndis.sys, tdi.sys.

  2. Filtering is handled by WFP drivers: FWPKCLNT.sys, wfplwf.sys

  3. They are implemented through separate files of the same name, for example: tcpip.sys

In Linux, we didn’t think about how applications access kernel structures and interact with the network. Everything is more or less obvious there and only one step to functions, but for Windows everything works on the principle of Callbacks. Therefore, there will most likely be several wrappers for interaction. Let’s try to find these files.

You can use the following method to find files that are used as a wrapper library. To do this, we will create a mini application that will work with sockets, receive and send data. Application source code:

import socket

HOST = '127.0.0.1'  
PORT = 10000        

with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as s:
    s.bind((HOST, PORT))
    s.listen()
    conn, addr = s.accept()
    with conn:
        print('Connected by', addr)
        while True:
            data = conn.recv(1024)
            if not data:
                break
            conn.sendall(data)

We launch the file in the OS, if there are no errors, then it is necessary to run the Process Explorer tool in parallel. With this tool, we can see what the thread is doing while it is waiting for a connection. The picture below shows all the described actions:

On the left is a stack of function calls that are involved in setting up a socket and putting it into bind state. This set of files – mswinsock.dll (Win Sock 2 Service) and WS2_32.dll(Windows Socket 2). These libraries are used to provide socket functions to applications in Windows.

It is worth noting that the sequence of functions that are called to operate the socket in the OS is not visible in Process Explorer. If you need to recover this data too, you need to use the kernel debugger.

Thus, it is possible to conduct a study of subsystems of any OS and their mechanisms with or without source code – it is enough to choose the required set of tools, as well as available methods, sources of knowledge.


Learn more about the course “Network engineer”.

Register for the open webinar on the topic “NAT is not a Firewall”.

Similar Posts

Leave a Reply

Your email address will not be published. Required fields are marked *