This document should give a straight forward guidline in
"how to analyse session-IDs" you find in Webaplications.
This document was written by Florian Walther
You can download this project in either zip or tar formats.
You can also clone the project with Git by running:
$ git clone git://github.com/scusi/SessionIDAnalysis
Web applications use session management to maintain context during client interaction. Once a user logs in, that user is associated with a particular session and the client is marked as authenticated. To prevent having to send authentication credentials with each request from the client, most session management systems use a session identifier. The session identifier is basically a token that associates incoming requests with the server's stored session. The goal of an attacker is to steal or guess a valid session ID for a user. Therefore a session ID must be secured during transmission, should be not predictable and it should be long enough to withstand brute force attacks.
A differential analysis is a form of an attack in which the differences between values is used to gain additional knowledge about the system and maybe also about its implementation.
Phase Space is an n-dimensional space that fully describes the space of an n-variable system. An attractor is a shape that is specific to the given Pseudo-Random Number Generator (PRNG) function, and reveals the complex nature of dependencies between subsequent results generated by the implementation. We wanted to generate a clean, three-dimensional representation of the one-dimensional input data. The method used is known as "delayed coordinates", and is well known and widely used in the analysis of dynamic systems, especially nonlinear systems and deterministic chaos. This method assumes that we can reconstruct missing dimensions using previous, delayed function values as additional coordinates. Instead of using function values, we will calculate the first-order difference for the input data to generate more suggestive and useful results to show the function dynamics.So if "s" stands for the input set, and "x", "y" and "z" are the point coordinates we are looking for, the equations are:
x[n] = s[n-2] - s[n-3]NOTE: This function does not predict values, it only hints at how difficult it would be to predict a value.
The analysis can be described in four Steps:
The first thing we have to do is to collect data on which to base the analysis. Normally SessionIDs will be set via cookies at the loginpage to the webapplication uses that SessionID. We assume that you have a valid login to the application in order to login and collect those cookies contain the SessionID. To do this we can use the gather_cookie.sh Script is described in the "Tools to use" Section of this document. gather_cookies.sh will repeatedly login into the application to gather cookies that contain the SessionID.
We assume you have a valid login, let's say User="test" and Password="testpasswd" Start @stake WebProxy, configure your browser to use webproxy and point your browser to the loginpage of the target webapplication. After login succesfully to the application go into the requestcache of webproxy and look for the last request you send to the Server before the Server sends back the cookie contains the sessionID. The Request could look like:
------------------------------ 01 POST /path-to/login HTTP/1.0 02 User-Agent: Mozilla/4.75 [en] (X11; U; OpenBSD 3.1 i386; Nav) 03 Host: mytest.server.com:443 04 Accept: image/gif, image/x-xbitmap, image/jpeg, image/pjpeg, image/png, */* 05 Accept-Encoding: gzip 06 Accept-Language: de, en 07 Accept-Charset: iso-8859-1,*,utf-8 08 Cookie: test=1; host=; folders=; HostName=test-domain 09 Content-type: application/x-www-form-urlencoded 10 Connection: close 11 Content-length: 96 12 13 User=test&Password=testpasswd&RequestType=LoginRequest&Domain=test-domain -------------------------------
The Server Response (the Cookie) could look like:
------------------------------- 01 HTTP/1.1 302 Found 02 Date:03 Server: Apache/1.3.26 (Unix) mod_ssl/2.8.10 OpenSSL/0.96 04 Set-Cookie: SESSIONID=51917721 05 Location: /path-to/login 06 Connection: close 07 Content-type: text/html; charset=iso-8859-1 -------------------------------
if you found both, take the browser-Request and put it in a text file (poststuff.txt). This text file we will use as input data for our cookie collecting script (gather_cookies.sh) in order to login. Basically "gather_cooies.sh" just posts the input (our request is now in poststuff.txt) to the given webserver and logs the respons in another log file. In order to have enough data to base our analysis on, we should collect at least 10.000 Cookies.
NOTE: repeatendly logins to a webserver can cause kind of a dinial of service condition if the webserver is not performant enough to handle all the requests we generate in addition to the "normal" traffic.
The data we collected by the shell script in step 1 contains much more information than needed for the specific analysis. We have to extract and condens the data down to what is relevant for us.
Step 1 produced a logfile with all the responses from the Webserver. The only thing we are interested in is the value of the SESSIONID Cookie (which is 51917721 in the example above). I leave it up to you how to cut away all the other data, i did it with the subtract command in vi, but you can also do it in Perl or with sed and gawk or what ever you want to use. (Just by Hand is a bit boring ;-)) After you cut out all the stuff we don't need you should have a file looks like:
------------------------------- 51917721 52792087 53667222 00511487 01386398 02495651 03386901 04245317 05120733 05979877 06839779 07698167 -------------------------------
Save the values to a file. Now we are ready for step 3.
In order to be able to do phase space analysis, the delayed coordinates are calculated with the existing cookie values. we will use a custom-developed Perl script (seq.pl) to accomplish this step.
What we do now is we use seq.pl (which is in the Tools Section of this document) to calculate our delayed coordinates from the inputdata (the cookie values we extracted in Step 2). In order to do this we just have to run seq.pl with the input data as argument. You have to call seq.pl with a comand line like this:
cat step2-output.txt | ./seq.pl > 3d.dat
The above command line will print the cookie values we extracted in step 2 and pipe them to seq.pl (which is doing the actual calculations). The output will be written to 3d.dat. The Script will produce a *.dat file (3d.dat) with the delayed coordinates. The .dat file could look like:
------------------------------- 891250 1109253 874911 858416 891250 1109253 875416 858416 891250 859144 875416 858416 859902 859144 875416 858388 859902 859144 860174 858388 859902 858751 860174 858388 859330 858751 860174 874704 859330 858751 875725 874704 859330 859341 875725 874704 859364 859341 875725 -------------------------------
If you have the datfile you are ready for Step 4.
The data gathered in Step 3 was put into a mathematical plot program to generate the display graph (Fig.1). we will use 'GNUplot' to achieve this effort.
What we do now is we feed the delayed coordinates into GNUplot to visualize the
data, in order to be able to analise the results. We need to have GNUplot instaled
and running. GNUplot can be downloaded at:
http://www.gnuplot.info/
An introduction to GNUplot you can find here:
http://www.cs.uni.edu/Help/gnuplot/
Start GNUplot with gnuplot
. U will get a gnuplot command line looks like:
------------------------------- gnuplot> -------------------------------
In the following table you will find the commands you really need.
GNUplot Command: | Description: |
gnuplot> splot "step3output.dat" |
Will load and plot the data we got out of step 3. |
gnuplot> set output "output.ps" |
redirects the output to a file with the filename output.ps |
gnuplot> set terminal postscript |
Sets the terminal mode to postscript, will produce postscript output. |
gnuplot> set terminal postscript color |
produces also Postscript, but in color. |
gnuplot> replot |
replots the whole stuff. If you changed the terminal and output this will be used now. |
This Postscript file you can also convert into .jpg or a .gif picture, which you can put into your report. The result could look like the examples in Interpreting results
A high degree of randomness in the session ID would generate a wide distribution cloud with evenly spread values and no patterns.
The following figure shows a good randomness. It was produced by this script.
Click on the image to Zoom in.
A poor degree of randomness in the session ID would generate a clear concentration of values along the three vectors.
The folowing graph shows a poor randomness.
Click on the image to Zoom in.
In the following figure you can see how a SessionID which is based on seconds and microseconds since the epoch is
shown in a phase-space analysis.
Click on the image to Zoom in.
The Script i wrote to generate these values is availible here
The relevant parts of the script looks like:
#!/usr/bin/perl -w # [...] use Time::HiRes qw( usleep ualarm gettimeofday tv_interval ); use Math::Random; for ($i=0; $i<$count;$i++) { $random = random_uniform(); $randsub = substr($random, 2, 6); ($seconds, $microseconds) = gettimeofday; $s = substr($seconds, 8, 2); uslgather_cookies.sheep $randsub; $time = $s . $microseconds; print ("$time\n"); } exit;
In this Section you will learn about the Tools you need to do all this.
To collect the cookies we have gather_cookies.sh and gather_cookies-ssl.sh.
gather_cookies.sh is a Sellscript for colecting cookies from normal webservers (http).
gather_goocies-ssl.sh is a script to collect cookies from https Servers.
The Syntax of the script is:
./gather_cookies.sh www.victim.com | tee cookies.txt
The Code looks like:
#!/bin/sh # gather.sh while [ 1 ] do echo -e "GET / HTTP/1.0\n\n" | \ nc -vv $1 80 | \ grep ASPSESSIONID done
The Syntax for gather_cookies-ssl.sh is the same as for gather_cookies.sh.
The Code for gather_cookies-ssl.sh looks like this:
gather_cookies.sh: ================== 01 #!/bin/sh 02 # 03 # gather_cookies-ssl.sh 04 # written by <flow@atstake.com> 05 # 06 # Shell script to gather Cookies from a Server to analyze them. 07 # 08 ########################################################## 09 while [ 1 ] 10 do 11 cat poststuff.txt| \ 12 openssl s_client -quiet -no_tls1 -connect $1:443 2>/dev/null | \ 13 grep 1 14 done
poststuff.txt is the request we post to the server in order to login and getting a cookie with the SessionID.
poststuff.txt ============== POST /path-to/login HTTP/1.0 User-Agent: Mozilla/4.75 [en] (X11; U; OpenBSD 3.1 i386; Nav) Host: mytest.server.com:443 Accept: image/gif, image/x-xbitmap, image/jpeg, image/pjpeg, image/png, */* Accept-Encoding: gzip Accept-Language: de, en Accept-Charset: iso-8859-1,*,utf-8 Cookie: test=1; host=; folders=; HostName=test-domain Content-type: application/x-www-form-urlencoded Connection: close Content-length: 96 User=test&Password=testpasswd&RequestType=LoginRequest&u=&STD=lm%3D1%26&Domain=test-domain
seq.pl is the Perlscript which calculates the delayed coordinates for the Cookie Values you collected.
seq.pl: ======= 01 ############################################ 02 #!/usr/bin/perl -w 03 # 04 # seq.pl 05 # Script to calculate "delayed coordinates". 06 ############################################ 07 08 @seq = (); 09 @x = @y = @z = (); 10 while(<>) { 11 chomp($val = $_); 12 push(@seq, $val); 13 14 } 15 for ($i = 3; $i < $#seq; $i++) { 16 push(@x, $seq[$i] - $seq[$i - 1]); 17 push(@y, $seq[$i - 1] - $seq[$i - 2]); 18 push(@z, $seq[$i - 2] - $seq[$i - 3]); 19 } 20 for ($i = 0; $i < $#seq; $i++) { 21 print $x[$i] . " " . $y[$i] . " " . $z[$i] . "\n"; 22 } 23 ############################################
Thanks to:
If you have any constructive comment on the above please drop a mail to: scusi@snurn.de. I will try to add your stuff to the current version of the document and/or correct the stuff you found that is not right or not clear.
© by Florian 'scusi' Walther September 2002 | [ back to top ] |