Zobrazují se příspěvky se štítkemTCP/IP. Zobrazit všechny příspěvky
Zobrazují se příspěvky se štítkemTCP/IP. Zobrazit všechny příspěvky

sobota 14. března 2020

Network scanning, OS fingerprinting part 3



Distinguishing OS detection
If you have read and understood all the lines in the first two blog posts, you can congratulate yourself. You now understand how Nmap performs OS detection, which packets are sent, what are the expected responses to those probes, and how Nmap uses the responses to calculate OS fingerprint and finds the best match in its database.
If you have previously investigated network traffic, you should be able to distinguish between standard, common packets, corrupted ones and nonstandard, unique or rare ones. In this case you could realize that some packets that Nmap sends are quite uncommon or even rare. Let's say that we have discussed 15 core packets that Nmap sends. For example, how often have you seen UPD packet with character 'C' (0x43) repeated 300 times? Or TCP packet with SYN, FIN, URG, PSH flags set? Not very often, right?
We can use our knowledge to create a NGFW, IPS rule, policy or search in network monitoring systems to warn us about Nmap OS scanning. The rule could monitor for the presence of those 15 core packets previously described in (1) that Nmap uses for OS fingerprinting. If we see them within a five-minute period from the same source IP to one destination IP, we can definitively say this destination IP was scanned, and one of the possible responses could be to block the source IP address.
But there is always a mitigating circumstance. The first argument could be that correlating 15 packets together with so many variables is very difficult and therefore, poses a high risk of error. All the mistakes should be discovered during test phase of a rule creation, but the search or test conditions may become quite long, complicated and even confusing. The second argument could be that the correlation of all those 15 packets together with exactly defined variable values can lead to a situation in which  the attacker won't be detected at all even when he performs  a slight change to one of the 15 packets.
As an example and to simplify this, we will only take into account UDP packet with 300 'C' characters described earlier. We can have QRadar or Snort rule like this one:

QRadar
Apply Nmap_OS_scan_UDP_with_C_characters on flows which are detected by the system
and when the IP protocol is one of the following UDP
and when the destination payload matches the regex CCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCC

Snort
alert udp $EXTERNAL_NET any -> $HOME_NET any
(
msg: "Nmap OS scan UDP with 300C detected";
content:"CCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCCC";
sid:1000001;
)
As you can see, having this rule in QRadar is quite inefficient and will likely have considerable performance impact. Also, when using flow data, we are limited with the payload length we can see. For this reason, we have in our rule only 64 'C' characters and not 300. To see the whole payload, we can use full packet capture, which will have additional performance impact. So, it makes sense to move the detection to NGFW or IPS tools like Snort.
If  an attacker changed the number of “C” characters in the UDP packet from 300 to 200, our rule waiting for 300 wouldn't fire. The same applies for cases when you change 'C' character to 'A'. In that case not even the QRadar rule will fire.
The question should be, can I change some Nmap parameters? Yes, you can. Even though it is not seen very often, the Nmap source code is publicly available, and once you understand it, you can adapt the specific file to your needs. What’s more, this UDP packet Nmap only monitors if it is returned the same way as it was sent with the proper packet length. If there was a change in a letter, Nmap still evaluates the response in the same way without any change. If you change the number of letters, then you also need to change the value for expected packet length in response and you are still OK.
So, we can approach it a little bit differently. Monitor only for the most unique packet(s) and for those values that cannot be changed, or their change will require huge intervention in Nmap code and logic of operation. One of my favorite packets to monitor is the ECN one (reserved bit, SYN, ECN, CWR flags, urgent field value of 0xF7F5, window size field=3, TCP options: Window Scale=10; NOP; MSS=1460; SACK permitted; NOP; NOP). In the WireShark display filter example in Figure 3 at part 1, it will filter out all the non-interesting packets. As you can see, we don't need to specify every single parameter (for example, windows size field omitted) in the WireShark and we have still quite good level of certainty that other "standard" packets won't be displayed.

WireShark display filter
(tcp.flags.syn==1 && tcp.flags.cwr==1 && tcp.flags.ecn==1) && (tcp.urgent_pointer == 63477) && (tcp.options.wscale.shift == 10) && (tcp.options.mss == 02:04:05:b4) && (tcp.options.nop == 01)
Personally, I find WireShark a great network investigation tool, but in this case, we won't be using it. We would have traffic dumps (.pcap file) from our environment, and manual investigation of so many files would be very ineffective. I suggest you try it during rule development process. Perform Nmap OS scan on one of your test systems. Dump the traffic, search for the Nmap specific packets and create rules based on the systems and network devices you are using.
But let's assume we have our WireShark search and we want to make a similar rule on our Snort IPS. We will face a challenge how to write a rule that will monitor TCP options and urgent pointer because Snort does not support these options out of the box. We can still use a rule to monitor for the flags, but we can expect a match even when there is no OS scan, because the condition is too generic. You can try it and you will see how common ECN and CWR flags are in your environment. You can use this simple rule and create better and more rules to identify Nmap OS scan:
alert tcp any any -> any any (flags:SCE;)
There is another problem with monitoring scanning attempts on the perimeter or IPS only. Not all devices are protected by IPS.  If an insider is trying to scan your internal network, the communication probably won't flow through a perimeter device. You could monitor endpoints directly. Generally, this is a good idea, but it depends heavily on the endpoint detection possibilities. As an example, we can describe the nature of the problem on  the iptables example in Figure x.

iptables
iptables -I INPUT -p tcp --tcp-flags SYN,RST,ACK,FIN SYN --tcp-option 4 -A LOGGING -j DROP

Here we are monitoring for the presence of SYN flag and TCP option 4, which is Selective ACK. Unfortunately, most of the iptables implementations don’t recognize ECN and CWR flags. That is why we can only focus on SYN out of the all known flags (SYN, RST, ACK, FIN). Also, we can specify only one TCP option.
Here, we have decided to monitor only for Selective ACK, since it is  one of the least used options. Urgent pointer is not usually supported by iptables. That leaves us with a general rule on which we can’t fully rely. I am not saying we can't create useful rules for iptables. It’s just not that easy and straightforward and it requires some development and testing.
Another idea could be to use a SIEM tool to detect Nmap OS scanning and create respective rules. But SIEM tools usually don't go into such packet detail. Even if they can, performance impact will be enormous and applicability throughout whole environment is questionable. We won't be far from the truth to say that there is no effective SIEM detection. Other flow-oriented tools fail when trying to monitor for TCP options and urgent pointer because they are not part of the flow standard.
There is no need to give up yet. Look at the YARA rule in Figure x. In the flags_window parameter, we have hexadecimally encoded header length – offset with reserved bit (88) SYN, CWR, ECN flags (C2) and window size field (00 03). In the pointer_options parameter we can see urgent pointer value (F7 F5) followed by the tcp options (03 03 0A 01 02 04 05 B4 04 02 01 01). Be careful with the order of TCP options, it can differ.. If we follow the condition, we are monitoring for a packet or traffic dump where both parameters are present.

YARA
rule NmapOSdetected
{
strings:
$flags_window = { 88 C2 00 03 }
$pointer_options = { F7 F5 03 03 0A 01 02 04 05 B4 04 02 01 01 }
condition:
$flags_window and $pointer_options
}

You can apply this rule on the endpoints. If you are creating traffic dumps, you can automate the detection by periodically applying the YARA rule on the newly created traffic dumps. Many modern network devices understand and can work with the YARA rules. Be careful with the network devices since some are applying the YARA rules only on the payload and not the protocol headers. If that’s the case, you still need to come up with a solution that fits your environment and tools.
As you can see, there is no silver bullet. It always depends on your tools, their capabilities and where you are able to effectively monitor. But I hope this  series helps you to understand what OS detection is, how it is carried out in terms of Nmap, and what kind of design thinking has to be done to create detection rules.
Now it only depends on you if you choose to rely on single packet or correlate multiple packets together. The solution will differ based on the technology you have available or you are using within your environment. Feel free to come up with your own innovative solution to approach this task. As usual, especially in cyber security, there is no single right answer.

Network scanning, OS fingerprinting part 2

How to decode the NMAP fingerprint
In the first post of the series, we explored what you can find in NMAP fingerprint database. We only covered Class and CPE line. So, let's continue with the most interesting part. Take the below sample and try to decode the values based on the description:
SEQ(SP=F6-100%GCD=1-6%ISR=10B-115%TI=I%CI=I%II=I%SS=S%TS=7)
OPS(O1=M523NW8ST11%O2=M523NW8ST11%O3=M523NW8NNT11%O4=M523NW8ST11%O5=M523NW8ST11%O6=M523ST11)
WIN(W1=2000%W2=2000%W3=2000%W4=2000%W5=2000%W6=2000)

ECN(R=Y%DF=Y%T=7B-85%TG=80%W=2000%O=M523NW8NNS%CC=N%Q=)
T1(R=Y%DF=Y%T=7B-85%TG=80%S=O%A=S+%F=AS%RD=0%Q=)
T2(R=Y%DF=Y%T=7B-85%TG=80%W=0%S=Z%A=S%F=AR%O=%RD=0%Q=)
T3(R=Y%DF=Y%T=7B-85%TG=80%W=0%S=Z%A=O%F=AR%O=%RD=0%Q=)
T4(R=Y%DF=Y%T=7B-85%TG=80%W=0%S=A%A=O%F=R%O=%RD=0%Q=)
T5(R=Y%DF=Y%T=7B-85%TG=80%W=0%S=Z%A=S+%F=AR%O=%RD=0%Q=)
T6(R=Y%DF=Y%T=7B-85%TG=80%W=0%S=A%A=O%F=R%O=%RD=0%Q=)
T7(R=Y%DF=Y%T=7B-85%TG=80%W=0%S=Z%A=S+%F=AR%O=%RD=0%Q=)
U1(DF=N%T=7B-85%TG=80%IPL=164%UN=0%RIPL=G%RID=G%RIPCK=G%RUCK=G%RUD=G)
IE(DFI=N%T=7B-85%TG=80%CD=Z)

SEQ field values
TCP ISN sequence predictability index (SP)
This value measures the ISN (initial sequence number) variability. It roughly estimates how difficult it would be to predict the next ISN from the known sequence of the first six probe responses. This test is only performed if at least four responses were seen.
The calculation uses the difference array (seq_rates) and GCD values discussed in later sections. If you are interested in detailed description how this field is calculated, please see https://nmap.org/book.
Please keep in mind that this test is only done for OS detection purposes and is not a full-blown audit of the target ISN generator. There are many algorithm weaknesses that lead to easy predictability even with a high SP value.

TCP ISN greatest common divisor (GCD)
The SEQ test sends six TCP SYN packets to an open port of the target machine and collects SYN/ACK packets back. Each of these SYN/ACK packets contains a 32-bit initial sequence number (ISN). This test attempts to determine the smallest number by which the target host increments these values. For example, many hosts (especially old ones) always increment the ISN in multiples of 64,000.
The first step in calculating this is creating an array of differences between probe responses. The first element is the difference between the 1st and 2nd probe response ISNs. The second element is the difference between the 2nd and 3rd responses. There are five elements if NMAP receives responses to all six probes. Since the next couple of sections reference this array, we will call it diff1. If an ISN is lower than the previous one, NMAP looks at both numbers and decide if they need to be subtracted or counted up (including wrapping the 32-bit counter back to zero). The smaller of those two values is stored in diff1. So the difference between 0x20000 followed by 0x15000 is 0xB000. The difference between 0xFFFFFF00 and 0xC000 is 0xC0FF. This test value then records the greatest common divisor of all those elements. This GCD is also used for calculating the SP result.

TCP ISN counter rate (ISR)
This value reports the average rate of increase for the returned TCP initial sequence number. Recall that a difference is taken between each two consecutive probe responses and stored in the previously discussed diff1 array. Those differences are each divided by the amount of time elapsed (in seconds—will generally be about 0.1) between sending the two probes which generated them. The result is an array, which we'll call seq_rates containing the rates of ISN counter increases per second. The array has one element for each diff1 value. An average is taken of the array values. If that average is less than one (e.g. a constant ISN is used), ISR is zero. Otherwise, ISR is eight times the binary logarithm (log base-2) of that average value, rounded to the nearest integer.

IP ID sequence generation algorithm (TI, CI, II)
There are three tests that examine the IP header ID field of responses. TI is based on responses to the TCP SEQ probes. CI is from the responses to the three TCP probes sent to a closed port: T5, T6, and T7. II comes from the ICMP responses to the two IE ping probes. For TI, at least three responses must be received for the test to be included; for CI, at least two responses are required; and for II, both ICMP responses must be received.
For each of these tests, the target's IP ID generation algorithm is classified based on the algorithm below. Minor differences between tests are noted. Note that difference values assume that the counter can start over. In that case the difference between an IP ID of 65,100 followed by a value of 700 is 1,136. The difference between 2,000 followed by 1,100 is 64,636. Here are the calculation details:
If all of the ID numbers are zero, the value of the test is Z.
If the IP ID sequence ever increases by at least 20,000, the value is RD (random). This result isn't possible for II because there are not enough samples to support it.
If all of the IP IDs are identical, the test is set to that value in hex.
If any of the differences between two consecutive IDs exceeds 1,000, and is not evenly divisible by 256, the test's value is RI (random positive increments). If the difference is evenly divisible by 256, it must be at least 256,000 to cause this RI result.
If all of the differences are divisible by 256 and no greater than 5,120, the test is set to BI (broken increment). This happens on systems like Microsoft Windows where the IP ID is sent in host byte order (little endian) rather than network byte order (big endian). It works fine and isn't any sort of RFC violation, though it does give away host architecture details which can be useful to attackers.
If all of the differences are less than ten, the value is I (incremental). Nmap allows difference up to ten (rather than requiring sequential ordering) because traffic from other hosts can cause sequence gaps.
If none of the previous steps identify the generation algorithm, the test is omitted from the fingerprint.

Shared IP ID sequence Boolean (SS)
This Boolean value records whether the target shares its IP ID sequence between the TCP and ICMP protocols. If our six TCP IP ID values are 117, 118, 119, 120, 121, and 122, then our ICMP results are 123 and 124, it is clear that not only are both sequences incremental, but they are both part of the same sequence. If, on the other hand, the TCP IP ID values are 117–122 but the ICMP values are 32,917 and 32,918, two different sequences are being used.
This test is only included if II is RI, BI, or I and TI is the same. If SS is included, the result is S if the sequence is shared and O (other) if it is not.
If you are interested in detailed description how this test is calculated, please see https://nmap.org/book.

TCP timestamp option algorithm (TS)
TS is another test which attempts to determine target OS characteristics based on how it generates a series of numbers. This one looks at the TCP timestamp option (if any) in responses to the SEQ probes. It examines the TSval (first four bytes of the option) rather than the echoed TSecr (last four bytes) value. It takes the difference between each consecutive TSval and divides that by the amount of time elapsed between NMAP sending the two probes which generated those responses. The resultant value gives a rate of timestamp increments per second. NMAP computes the average increments per second from all consecutive probes and then calculates the TS as follows:
  1. If any of the responses have no timestamp option, TS is set to U (unsupported).
  2. If any of the timestamp values are zero, TS is set to 0.
  3. If the average increments per second falls within the ranges 0-5.66, 70-150, or 150-350, TS is set to 1, 7, or 8, respectively. These three ranges get special treatment because they correspond to the 2 Hz, 100 Hz, and 200 Hz frequencies used by many hosts.
  4. In all other cases, Nmap records the binary logarithm of the average increments per second, rounded to the nearest integer. Since most hosts use 1,000 Hz frequencies, A is a common result.
OPS field values
TCP options (O, O1–O6)
Some platforms don't implement all options (which are, of course, optional).

Options test values
Option Name
Character
Argument (if any)
End of Options List (EOL)
L

No operation (NOP)
N

Maximum Segment Size (MSS)
M
The value is appended. Many systems echo the value used in the corresponding probe.
Window Scale (WS)
W
The actual value is appended.
Timestamp (TS)
T
The T is followed by two binary characters representing the TSval and TSecr values respectively. 0 if the field is zero and 1 otherwise.
Selective ACK (SACK)
S

As an example, the string M5B4NW3NNT11 means the packet includes the MSS option (value 0x5B4) followed by a NOP. Next comes a window scale option with a value of three, then two more NOPs. The final option is a timestamp, and neither of its two fields (timestamp value, timestamp echo reply) were zero. If there are no TCP options in a response, the test will exist, but the value string will be empty. If no probe was returned, the test is omitted.

WIN field values
Window length of responses for first 6 packets (Packet #1-#6). It is common to see the same value for all six responses.

ECN, T1 – T7, IE field values

Responsiveness (R)
This test simply records whether the target responded to a given probe. Possible values are Y and N. If there is no reply.

IP don't fragment bit (DF)
The IP header contains a single bit which forbids routers from fragmenting a packet. This test records Y if the bit is set, and N if it isn't.

Don't fragment (ICMP) (DFI)
This is simply a modified version of the DF test that is used for the special IE probes. It compares results of the don't fragment bit for the two ICMP echo request probes sent.

DFI test values
Value
Description
N
Neither of the ping responses have the DF bit set.
S
Both responses echo the DF value of the probe.
Y
Both of the response DF bits are set.
O
The one remaining other combination—both responses have the DF bit toggled.

IP initial time-to-live (T)
IP packets contain a field named time-to-live (TTL) which is decremented every time they traverse a router. If the field reaches zero, the packet must be discarded. This prevents packets from looping endlessly. Because operating systems differ on which TTL they start with, it can be used for OS detection. Nmap determines how many hops away it is from the target by examining the ICMP port unreachable response to the U1 probe. That response includes the original IP packet, including the already-decremented TTL field, received by the target. By subtracting that value from our as-sent TTL, we learn how many hops away the machine is. Nmap then adds that hop distance to the probe response TTL to determine what the initial TTL was when that ICMP probe response packet was sent. That initial TTL value is stored in the fingerprint as the T result. Nmap accepts the value within the range specified in fingerprint (for example T=7B-85). In most cases, the expected value will be 0x80 (for our 7B-85 range), but for cases when there are multiple asymmetric routes to the target the calculated value can vary.

IP initial time-to-live guess (TG)
It is not uncommon for Nmap to receive no response to the U1 probe, which prevents Nmap from learning how many hops away a target is. Firewalls and NAT devices love to block unsolicited UDP packets. But since common TTL values are spread well apart and targets are rarely more than 20 hops away, Nmap can make a pretty good guess anyway. Most systems send packets with an initial TTL of 32, 60, 64, 128, or 255. So, the TTL value received in the response is rounded up to the next value out of 32, 64, 128, or 255. Sixty is not in that list because it cannot be reliably distinguished from 64. It is rarely seen anyway. The resulting guess is stored in the TG field. This TTL guess field is not printed in a subject fingerprint if the actual TTL (T) value was discovered.

Explicit congestion notification (CC)
This test is only used for the ECN probe. That probe is a SYN packet which includes the CWR and ECE congestion control flags. When the response SYN/ACK is received, those flags are examined to set the CC (congestion control) test value

CC test values
Value
Description
Y
Only the ECE bit is set (not CWR). This host supports ECN.
N
Neither of these two bits is set. The target does not support ECN.
S
Both bits are set. The target does not support ECN, but it echoes back what it thinks is a reserved bit.
O
The one remaining combination of these two bits (other).

TCP miscellaneous quirks (Q)
This tests for two quirks that a few implementations have in their TCP stack. The first is that the reserved field in the TCP header (right after the header length) is nonzero. This is particularly likely to happen in response to the ECN test as that one sets a reserved bit in the probe. If this is seen in a packet, an "R" is recorded in the Q string.
The other quirk Nmap tests for is a nonzero urgent pointer field value when the URG flag is not set. This is also particularly likely to be seen in response to the ECN probe, which sets a non-zero urgent field. A "U" is appended to the Q string when this is seen.
The Q string must always be generated in alphabetical order. If no quirks are present, the Q test is empty but still shown.

TCP Sequence (S) and Acknowledgement (A)
This test compares the TCP sequence and acknowledgment number from the probe that elicited the response. It then records the appropriate value as shown in the table below.

S and A test values
Value
Description
Z
number is zero.
A
Sequence number is the same as the acknowledgment number in the probe.
A+
Sequence number is the same as the acknowledgment number in the probe plus one.
S
Acknowledgement value is the same as the sequence number in the probe
S+
Acknowledgement value is the same as the sequence number in the probe plus one.
O
number is something else (other).

TCP flags (F)
This field records the TCP flags in the response. Each letter represents one flag, and they occur in the same order as in a TCP packet (from high-bit on the left, to the low ones). The value AS represents the ACK and SYN bits set, while the value SA is illegal (wrong order).

F test values
Character
Flag name
Flag byte value
E
ECN Echo (ECE)
64
U
Urgent Data (URG)
32
A
Acknowledgment (ACK)
16
P
Push (PSH)
8
R
Reset (RST)
4
S
Synchronize (SYN)
2
F
Final (FIN)
1

TCP RST data checksum (RD)
Some operating systems return ASCII data such as error messages in reset packets. When Nmap encounters such data, it performs a CRC32 checksum and reports the results. When there is no data, RD is set to zero. Some of the few operating systems that may return data in their reset packets are HP-UX and versions of Mac OS prior to Mac OS X.

IP total length (IPL)
This test records the total length (in octets) of an IP packet. It is only used for the port unreachable response elicited by the U1 test.

Unused port unreachable field nonzero (UN)
An ICMP port unreachable message header is eight bytes long, but only the first four are used. RFC 792 states that the last four bytes must be zero. A few implementations (mostly ethernet switches and some specialized embedded devices) set it anyway. The value of those last four bytes is recorded in this field.

UDP (U1) related parameters

Returned probe IP total length value (RIPL)
ICMP port unreachable messages (that are sent in response to the U1 probe) are required to include the IP header which generated them. This header should be returned just as they received it, but some implementations send back a corrupted version due to changes they made during IP processing. This test simply records the returned IP total length value. If the correct value of 0x148 (328) is returned, the value G (for good) is stored instead of the actual value.

Returned probe IP ID value (RID)
The U1 probe has a static IP ID value of 0x1042. If that value is returned in the port unreachable message, the value G is stored for this test. Otherwise, the exact value returned is stored. Some systems, such as Solaris, manipulate IP ID values for raw IP packets that Nmap sends. In such cases, this test is skipped

Integrity of returned probe IP checksum value (RIPCK)
The IP checksum is one value that we don't expect to remain the same when returned in a port unreachable message. After all, each network hop during transit changes the checksum as the TTL is decremented. However, the checksum we receive should match the enclosing IP packet. If it does, the value G (good) is stored for this test. If the returned value is zero, then Z is stored. Otherwise, the result is I (invalid).

Integrity of returned probe UDP checksum (RUCK)
The UDP header checksum value should be returned exactly as it was sent. If it is, G is recorded for this test. Otherwise, the value actually returned is recorded.

Integrity of returned UDP data (RUD)
This test checks the integrity of the (possibly truncated) returned UDP payload. If all the payload bytes are the expected 'C' (0x43), or if the payload was truncated to zero length, G is recorded; otherwise, I (invalid) is recorded.

ICMP response code (CD)
The code value of an ICMP echo reply (type zero) packet is supposed to be zero. But some implementations wrongly send other values, particularly if the echo request has a nonzero code (as one of the IE tests does).

CD test values
Value
Description
Z
Both code values are zero.
S
Both code values are the same as in the corresponding probe.
<NN>
When they both use the same non-zero number, it is shown here.
O
Any other combination.
__________________________________________________________________________
In first two parts we have covered the mechanisms around Nmap OS detection and networking protocol basics. In our last part we will be talking about how to monitor those activities. We will discuss pros and cons of different detection methods and as usual you can look forward for a few examples that can be applied on the most common tools used.

Network scanning, OS fingerprinting part 1



One of the  primary challenges you face is  detecting  cyber attacks and cyber threats at their earliest stage.
If you use, the Cybrer Kill Chain framework developed by Lockheed Martin, you will likely find them in the "Reconnaissance" phase, when and intruder first seeks a target and attempts to identify vulnerabilities.
But when it comes to network scanning, this isn’t as simple as it seems. How do you distinguish between "innocent" scans performed by an application flaw or misconfigurations from spoofed IP addresses and serious bad-guy scans whose intention is to weaponize and then deliver some malicious code?
If you respond to every scan by blocking the source IP, then, sooner or later, you will end up with a gigantic blacklist that probably blocks some IPs you actually shouldn't. If those happen to belong to a business partner, customer or cloud application that your organization is using, it may be a while before you realize and fix it. In the case of a business partner or customer, your organization is losing trust and with a cloud application, it is basically a denial of service (DoS) despite the good intention.
So, your goal should be to focus only on those scanning attempts that can be dangerous or worth tracking, instead of blocking them all.  We’ll take a look in this three-part series, starting with a familiar activity.
(subhead) What’s your operating system?
When an attacker wants to scan and determine the operating system (OS), this can be a situation that warrants monitoring and, perhaps, blocking. Why? When an attacker has information about the OS, he can estimate the detection mechanisms he needs to avoid and weaponize the malware.
A very popular, open source tool called Nmap, with option "-O" specified, makes OS detection easier. Nmap is widely used for that purpose, and even the source code and libraries are publicly available and used also by other tools. Let’s look at the OS detection mechanism and see how Nmap creates an OS fingerprint based on the information received from the client.
At the end we will elaborate about effective SIEM detection and give few examples of rules/searches that can help us detect an attacker running Nmap with OS detection against our systems.
To detect the OS, Nmap sends to the target a few specially crafted packets and, based on the received information, it creates an OS “fingerprint.” Because of the different implementation of the TCP/IP stack and respective RFCs by individual vendors, the response to Nmap special packets produced by operating systems varies. The OS fingerprint is really just a record of all the values received from the target, tucked into a database. When the OS scan is performed, Nmap compares the received values with its database and can determine quite precisely the possible operating system.

What do the NMAP database and fingerprint look like?
Based on the system that is running Nmap, the fingerprint database can be located in different places. If you want to see the content of the database, look for a file “Nmap-os-db,” then choose your favorite viewer to open it.
For comparison, we have chosen two fingerprints from this file: Windows 7 and Cisco 19xx router with IOS 15.4. 

Fingerprint Microsoft Windows 7
Class Microsoft | Windows | 7 | general purpose
CPE cpe:/o:microsoft:windows_7
SEQ(SP=F6-100%GCD=1-6%ISR=10B-115%TI=I%CI=I%II=I%SS=S%TS=7)
OPS(O1=M523NW8ST11%O2=M523NW8ST11%O3=M523NW8NNT11%O4=M523NW8ST11%O5=M523NW8ST11%O6=M523ST11)
WIN(W1=2000%W2=2000%W3=2000%W4=2000%W5=2000%W6=2000)
ECN(R=Y%DF=Y%T=7B-85%TG=80%W=2000%O=M523NW8NNS%CC=N%Q=)
T1(R=Y%DF=Y%T=7B-85%TG=80%S=O%A=S+%F=AS%RD=0%Q=)
T2(R=Y%DF=Y%T=7B-85%TG=80%W=0%S=Z%A=S%F=AR%O=%RD=0%Q=)
T3(R=Y%DF=Y%T=7B-85%TG=80%W=0%S=Z%A=O%F=AR%O=%RD=0%Q=)
T4(R=Y%DF=Y%T=7B-85%TG=80%W=0%S=A%A=O%F=R%O=%RD=0%Q=)
T5(R=Y%DF=Y%T=7B-85%TG=80%W=0%S=Z%A=S+%F=AR%O=%RD=0%Q=)
T6(R=Y%DF=Y%T=7B-85%TG=80%W=0%S=A%A=O%F=R%O=%RD=0%Q=)
T7(R=Y%DF=Y%T=7B-85%TG=80%W=0%S=Z%A=S+%F=AR%O=%RD=0%Q=)
U1(DF=N%T=7B-85%TG=80%IPL=164%UN=0%RIPL=G%RID=G%RIPCK=G%RUCK=G%RUD=G)
IE(DFI=N%T=7B-85%TG=80%CD=Z)

Fingerprint Cisco 1900-series router (IOS 15.4)
Class Cisco | IOS | 15.X | router
CPE cpe:/o:cisco:ios:15.4
SEQ(SP=102-10C%GCD=1-6%ISR=106-110%TI=RD%CI=RD|RI%II=RI%TS=U)
OPS(O1=M564%O2=M564%O3=M564%O4=M218%O5=M564%O6=M564)
WIN(W1=1020%W2=1020%W3=1020%W4=1020%W5=1020%W6=1020)
ECN(R=Y%DF=N%T=FB-105%TG=FF%W=1020%O=M564%CC=N%Q=)
T1(R=Y%DF=N%T=FB-105%TG=FF%S=O%A=S+%F=AS%RD=0%Q=)
T2(R=N)
T3(R=N)
T4(R=Y%DF=N%T=FB-105%TG=FF%W=0%S=A%A=Z%F=R%O=%RD=0%Q=)
T5(R=Y%DF=N%T=FB-105%TG=FF%W=0%S=A%A=S+%F=AR%O=%RD=0%Q=)
T6(R=Y%DF=N%T=FB-105%TG=FF%W=0%S=A%A=Z%F=R%O=%RD=0%Q=)
T7(R=Y%DF=N%T=FB-105%TG=FF%W=0%S=A%A=S%F=AR%O=%RD=0%Q=)
U1(DF=N%T=FB-105%TG=FF%IPL=38%UN=0%RIPL=G%RID=G%RIPCK=G%RUCK=G%RUD=G)
IE(DFI=S%T=FB-105%TG=FF%CD=S)

Every fingerprint has one or more Class lines. Each contains four well-defined fields: vendor, OS family, OS generation and device type. The fields are separated by the pipe symbol (|). After the Class line you can see Common Platform Enumeration (CPE) ,the structured naming scheme based on generic syntax for uniform resource identifiers.
Before we will start decoding subsequent rows, let's refresh our knowledge about TCP/IP protocols.

What do the IP header and TCP header look like?
To better understand the whole magic about Nmap OS fingerprinting, we should be familiar with IP, TCP, UDP and ICMP protocols. We’ll focus on the header format of the two most used for OS detection: TCP and IP.

IP header
The IP header format with description can be seen on Figure 1. Nmap during OS detection crafts the IP header and monitors the IP header in response with focus on Identification field (IP ID), Don't fragment bit in IP Flags and Type of Service.
Figure 1- IP header


TCP header
The TCP header format with description can be seen on Figure 2. Nmap during OS detection crafts the TCP header and monitors it in response, with focus on TCP flags, Window field and TCP options.
TCP options can be also referred to by their acronyms: SACK, for Selective ACK; MSS, for Maximum segment size; NOP, for No Operation; EOL, for End of Option List.
Figure 2 - TCP header


On the example in Figure 3, we have open TCP timestamp option (number 8) and from there we can see Timestamp TSval value 4294967295 (0xFFFFFFFF) and TSecr value 0 (0x00000000).

Figure 3 - WireShark output

Now if we know on which parts in our protocol headers we should focus on, we can move onto the explanation of which data or packets  Nmap is sending to detect the target OS. This recap will also help us to monitor the OS detection performed on our devices. Since we know where we should search the variables, it depends whether or not we have the traffic dump, and if we know for which values we are searching. 

What Nmap sends
Let’s see what makes the packets Nmap sends to probe the target  special.
First, Nmap sends six packets. In their TCP header, you can see the following parameters:
Packet #1: window scale (10), NOP, MSS (1460), timestamp (TSval: 0xFFFFFFFF; TSecr: 0), SACK permitted. The window field is 1.
Packet #2: MSS (1400), window scale (0), SACK permitted, timestamp (TSval: 0xFFFFFFFF; TSecr: 0), EOL. The window field is 63.
Packet #3: Timestamp (TSval: 0xFFFFFFFF; TSecr: 0), NOP, NOP, window scale (5), NOP, MSS (640). The window field is 4.
Packet #4: SACK permitted, Timestamp (TSval: 0xFFFFFFFF; TSecr: 0), window scale (10), EOL. The window field is 4.
Packet #5: MSS (536), SACK permitted, Timestamp (TSval: 0xFFFFFFFF; TSecr: 0), window scale (10), EOL. The window field is 16.
Packet #6: MSS (265), SACK permitted, Timestamp (TSval: 0xFFFFFFFF; TSecr: 0). The window field is 512.
From the Packet #1 to #6 following records are derived:
SEQ – Sequence analysis of the probe packet
OPS – TCP options received
WIN – window sizes for the responses of Packet #1-#6
T1 – various test values for packet #1

Then we can see the packet that helps to determine the Explicit Congestion Notification (ECN) values. For this reason, Nmap sends a packet with reserved bit and SYN, ECN, CWR flags set. The urgent field value of 0xF7F5 is used even though the urgent flag is not set. The acknowledgment number is zero, sequence number is random, window size field is three. TCP options are Window Scale (10), NOP, MSS (1460), SACK permitted, NOP, NOP. The probe is sent to an open port.
If we follow the same order as in Nmap fingerprint, we should describe packets corresponding to T2-T7 rows. The packets with corresponding TCP and IP header are:
  • T2 TCP null (no flags set) and a window field of 128. IP DF bit is set. Packet is sent to an open port.
  • T3 TCP packet with SYN, FIN, URG, PSH flags set and a window field of 256 to an open port.
  • T4 TCP ACK packet and a window field of 1024. IP DF bit is set. Packet is sent to an open port.
  • T5 TCP SYN packet and a window field of 31337. IP DF is not set. Packet is sent to a closed port.
  • T6 TCP ACK packet and a window field of 32768. IP DF is set. Packet is sent to a closed port.
  • T7 TCP packet with the FIN, PSH, URG flags set and a window field of 65535. Packet is sent to a closed port.
Now we can move to the U1 row in the Nmap fingerprint. This probe sends a UDP packet to a closed port. In the data field is character 'C' (0x43) repeated 300 times. The IP ID value is set to 0x1042 (4162) for operating systems which allow us to set this. If the port is truly closed and there is no firewall in place, Nmap expects to receive an ICMP port unreachable message in return. That response is then subjected to the R, DF, T, TG, IPL, UN, RIPL, RID, RIPCK, RUCK, and RUD tests that.
Last but not least, we have IE row. The IE test involves sending two ICMP echo request packets to the target. The first one has the IP DF bit set, a type-of-service (TOS) byte value of zero. ICMP type 8 and a code of nine (even though it should be zero or 16 based on RFC792, RFC2780), the ICMP sequence number 295, a random IP ID and 120 bytes of 0x00 as the data payload.
The second ping query is similar, except a TOS of four (IP_TOS_RELIABILITY) is used. The ICMP type is 8 and code is zero. 150 bytes of 0x00 data is sent, and the ICMP request ID and sequence numbers are incremented by one from the previous query values.
The results of both of these probes are combined into an IE line containing the R, DFI, T, TG, and CD tests. The R value is only true (Y) if both probes elicit responses. The T, and CD values are for the response to the first probe only, since they are highly unlikely to differ. DFI is a custom test for this special dual-probe ICMP case.
____________________________________________________________________
In the first part of our article, we have covered the OS detection with Nmap fingerprint examples, refresh our knowledge about TCP and IP headers and explained what Nmap sends. In the next sections we will cover how to decode Nmap fingerprint and talk about detection methods.