<?xml version="1.0" encoding="UTF-8"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
    <title>Hawkheart&#x27;s Site</title>
    <subtitle>Hawkheart&#x27;s personal site</subtitle>
    <link rel="self" type="application/atom+xml" href="https://hawkhe.art/atom.xml"/>
    <link rel="alternate" type="text/html" href="https://hawkhe.art"/>
    <generator uri="https://www.getzola.org/">Zola</generator>
    <updated>2018-09-19T20:29:33-04:00</updated>
    <id>https://hawkhe.art/atom.xml</id>
    <entry xml:lang="en">
        <title>CSAW Quals 2018 - RE 400 - Not Protobuf</title>
        <published>2018-09-19T20:29:33-04:00</published>
        <updated>2018-09-19T20:29:33-04:00</updated>
        
        <author>
          <name>
            
              Unknown
            
          </name>
        </author>
        
        <link rel="alternate" type="text/html" href="https://hawkhe.art/writeups/not-protobuf/"/>
        <id>https://hawkhe.art/writeups/not-protobuf/</id>
        
        <content type="html" xml:base="https://hawkhe.art/writeups/not-protobuf/">&lt;blockquote&gt;
&lt;p&gt;I&#x27;m in this company&#x27;s network and I&#x27;ve MITM&#x27;d this weird protocol between a dev client and server, but I can&#x27;t figure out how it works. Connect to reversing.chal.csaw.io:9002 and I&#x27;ll send the client traffic to you. Forward it on to the dev server at reversing.chal.csaw.io:9001 to figure out what&#x27;s going on. Once you&#x27;re ready, hit up the prod server at reversing.chal.csaw.io:9000 which should have a flag for you.&lt;&#x2F;p&gt;
&lt;&#x2F;blockquote&gt;
&lt;p&gt;&lt;em&gt;Solved with &lt;a rel=&quot;external&quot; href=&quot;https:&#x2F;&#x2F;twitter.com&#x2F;jack7764&quot;&gt;jack2&lt;&#x2F;a&gt; and &lt;a rel=&quot;external&quot; href=&quot;https:&#x2F;&#x2F;twitter.com&#x2F;Plailect&quot;&gt;Plailect&lt;&#x2F;a&gt;!&lt;&#x2F;em&gt;&lt;&#x2F;p&gt;
&lt;p&gt;This was an interesting reverse engineering challenge we solved during the qualification round for CSAW CTF this year. Only one other team, REdefined Behavior, solved the challenge during the 48 hours given. We are given a number of endpoints to connect to – one which provides a &quot;development client&quot;, and two which provide &quot;development&#x2F;production&quot; versions of the server this client is intended to talk to. The challenge description implies that our final goal is to reverse engineer the network protocol well enough to communicate with the prod service.&lt;&#x2F;p&gt;
&lt;p&gt;We began exploring the activity of the service by writing a script that would connect the development services and record a conversation between them (acting as a man-in-the-middle). Simply looking at this traffic doesn&#x27;t reveal much information, though – we can see two plaintext messages (a hello message, and an acknowledgement) before the client initiates TLS.&lt;&#x2F;p&gt;
&lt;p&gt;The one thing we are able to gather from these messages is a bit of the message structure. It appears that each message sent begins with 4 random bytes, and then ends with those same random bytes. For example, the hello message (&lt;code&gt;0x41ca&lt;&#x2F;code&gt;) could be sent as &lt;code&gt;0x0102030441ca04030201&lt;&#x2F;code&gt; and the acknowledgement message (&lt;code&gt;0x0aca&lt;&#x2F;code&gt;) could be encoded &lt;code&gt;0x414243440aca44434241&lt;&#x2F;code&gt;.&lt;&#x2F;p&gt;
&lt;p&gt;We then modified our script to man-in-the-middle the TLS traffic. This was fairly easy to do, as the client&#x2F;servers do not require a valid certificate to function. Using this enhanced script, we captured a number of conversations between the client and the servers.&lt;&#x2F;p&gt;
&lt;p&gt;Forensing of the now-decrypted message traffic allowed us to determine the flow of the application traffic:&lt;&#x2F;p&gt;
&lt;ol&gt;
&lt;li&gt;The client connects to the server and sends a &quot;hello&quot; message.&lt;&#x2F;li&gt;
&lt;li&gt;The server responds with an acknowledgement.&lt;&#x2F;li&gt;
&lt;li&gt;TLS is initiated on the connection between the client&#x2F;server.&lt;&#x2F;li&gt;
&lt;li&gt;The server sends a &quot;hello message.&quot;&lt;&#x2F;li&gt;
&lt;li&gt;The client responds with an acknowledgement.&lt;&#x2F;li&gt;
&lt;li&gt;The client sends a message that appears to contain a username&#x2F;password pair.&lt;&#x2F;li&gt;
&lt;li&gt;The server responds with an acknowledgement on success, or an error message on failure.&lt;&#x2F;li&gt;
&lt;li&gt;The client sends some sort of request.&lt;&#x2F;li&gt;
&lt;li&gt;The server sends a response which is a single null byte followed by some portion of the end of the request.&lt;&#x2F;li&gt;
&lt;li&gt;Repeat &lt;sup&gt;8&lt;&#x2F;sup&gt;⁄&lt;sub&gt;9&lt;&#x2F;sub&gt; until the client has finished.&lt;&#x2F;li&gt;
&lt;li&gt;The client sends a message &lt;code&gt;0xbbca&lt;&#x2F;code&gt; and disconnects.&lt;&#x2F;li&gt;
&lt;&#x2F;ol&gt;
&lt;p&gt;Further investigation of the traffic (and modification of traffic between server&#x2F;client) allowed us to serialize our own messages.&lt;&#x2F;p&gt;
&lt;p&gt;Each message begins with a one-byte message type. The official client uses the following message types:&lt;&#x2F;p&gt;
&lt;ul&gt;
&lt;li&gt;0x00: Value at location&lt;&#x2F;li&gt;
&lt;li&gt;0x0a: Acknowledgement&lt;&#x2F;li&gt;
&lt;li&gt;0x20: Login request&lt;&#x2F;li&gt;
&lt;li&gt;0x41: Hello&lt;&#x2F;li&gt;
&lt;li&gt;0x78: Set value location&lt;&#x2F;li&gt;
&lt;li&gt;0xbb: &quot;Bye-bye&quot;&lt;&#x2F;li&gt;
&lt;li&gt;0xee: Sent by the server on error.&lt;&#x2F;li&gt;
&lt;&#x2F;ul&gt;
&lt;p&gt;The acknowledgement, hello, and goodbye messages all take no arguments, which is serialized as &lt;code&gt;0xca&lt;&#x2F;code&gt;. We found that strings are serialized as a space (&lt;code&gt;0x20&lt;&#x2F;code&gt;) followed by a two byte length prefix, followed by the string itself. Any integers are serialized with a type code of &#x27;0&#x27; followed by a &lt;a rel=&quot;external&quot; href=&quot;https:&#x2F;&#x2F;developers.google.com&#x2F;protocol-buffers&#x2F;docs&#x2F;encoding#varints&quot;&gt;Base 128 varint encoding&lt;&#x2F;a&gt; of the integer.&lt;&#x2F;p&gt;
&lt;p&gt;Most interestingly, though, are the list&#x2F;tuple tuples (beginning with &lt;code&gt;0x00&lt;&#x2F;code&gt; and &lt;code&gt;0x01&lt;&#x2F;code&gt; respectively). These types are serialized with their type code, followed by a series of bytes for the length for the serialized form of each list element. A null byte is used to indicate the end of the list. Following this are the serialized forms of each element in order.&lt;&#x2F;p&gt;
&lt;p&gt;For example, the steps to serialize the tuple &lt;code&gt;(&quot;Hello&quot;, &quot;serialization!&quot;)&lt;&#x2F;code&gt; would be:&lt;&#x2F;p&gt;
&lt;ol&gt;
&lt;li&gt;Serialize the first element of the tuple (&lt;code&gt;0x20000548656c6c6f&lt;&#x2F;code&gt;)&lt;&#x2F;li&gt;
&lt;li&gt;Serialize the second element of the tuple (&lt;code&gt;0x20000e73657269616c697a6174696f6e21&lt;&#x2F;code&gt;)&lt;&#x2F;li&gt;
&lt;li&gt;Serialize the tuple header (&lt;code&gt;0x01081100&lt;&#x2F;code&gt;)&lt;&#x2F;li&gt;
&lt;li&gt;Append the serialized elements to the end of the header to produce the final serialized value.&lt;&#x2F;li&gt;
&lt;&#x2F;ol&gt;
&lt;p&gt;Now that we are able to serialize our own messages, we need to figure out what we need to send the server. Trying all 256 possible message types finds us an interesting message type (&#x27;f&#x27;) which tells us to repeat the request with the value at a given coordinate pair, which is randomized on each connection to the server.&lt;&#x2F;p&gt;
&lt;p&gt;At this point, we were stuck until the third hint was released:&lt;&#x2F;p&gt;
&lt;blockquote&gt;
&lt;p&gt;hint 3: &quot;for the final stage, the server&#x27;s prompt is just trying to confirm that the client has the data that an official client would have. It is referring to what the client sends.&quot;&lt;&#x2F;p&gt;
&lt;&#x2F;blockquote&gt;
&lt;p&gt;With this hint, we figured out that each time the dev client connected to the server, it would set the value of 10 different coordinates. We then wrote a script to gather the values sent by the client for each location on the grid. After gathering a large enough set of values, we retried sending a flag request until the server requested the value of a location we knew the value of. The server then responded with a message containing the flag!&lt;&#x2F;p&gt;
</content>
        
    </entry>
    <entry xml:lang="en">
        <title>HITCON CTF Quals 2017 - Footbook</title>
        <published>2017-11-06T00:00:00+00:00</published>
        <updated>2017-11-06T00:00:00+00:00</updated>
        
        <author>
          <name>
            
              Unknown
            
          </name>
        </author>
        
        <link rel="alternate" type="text/html" href="https://hawkhe.art/writeups/footbook/"/>
        <id>https://hawkhe.art/writeups/footbook/</id>
        
        <content type="html" xml:base="https://hawkhe.art/writeups/footbook/">&lt;blockquote&gt;
&lt;p&gt;Don&#x27;t like Facebook? Try our brand-new social networking service!&lt;&#x2F;p&gt;
&lt;&#x2F;blockquote&gt;
&lt;h2 id=&quot;tl-dr&quot;&gt;tl;dr&lt;&#x2F;h2&gt;
&lt;p&gt;Proxy requests from 127.0.0.1:3000 to the remote server:
&lt;code&gt;socat TCP-LISTEN:3000,fork TCP:13.114.238.13:80&lt;&#x2F;code&gt;&lt;&#x2F;p&gt;
&lt;p&gt;Register a Dropbox account with email address &lt;code&gt;admin+something@footbook.meh&lt;&#x2F;code&gt;&lt;&#x2F;p&gt;
&lt;p&gt;Log in to site at 127.0.0.1:3000 using Dropbox OAuth&lt;&#x2F;p&gt;
&lt;p&gt;Get flag!&lt;&#x2F;p&gt;
&lt;h2 id=&quot;explanation&quot;&gt;explanation&lt;&#x2F;h2&gt;
&lt;p&gt;We are presented with a very simple social media website that allows registered users to make public posts and send messages to other registered users (via their email address).&lt;&#x2F;p&gt;
&lt;p&gt;Email addresses for users who log-in directly via username&#x2F;password are given email addresses of the form &lt;code&gt;username@user.footbook.meh&lt;&#x2F;code&gt;.&lt;&#x2F;p&gt;
&lt;p&gt;An admin user (&lt;code&gt;admin@footbook.meh&lt;&#x2F;code&gt;) can be found by visiting profile ID 1... and they have a post:&lt;&#x2F;p&gt;
&lt;blockquote&gt;
&lt;p&gt;Only I can see the flag ^_&amp;lt;&lt;&#x2F;p&gt;
&lt;&#x2F;blockquote&gt;
&lt;p&gt;So we have our target.&lt;&#x2F;p&gt;
&lt;p&gt;There doesn&#x27;t appear to be anything interesting to do in the actual site, so we return to the login page.&lt;&#x2F;p&gt;
&lt;p&gt;Each of the OAuth login options is disabled (client-side) because our host isn&#x27;t &lt;code&gt;127.0.0.1:3000&lt;&#x2F;code&gt;.
Ignoring that, and visiting the Twitter OAuth login page, we can log-in via Twitter and our user email will be the email on the Twitter account.
Unfortunately, Twitter will only allow us to create&#x2F;log-in with email addresses we control (and we do not control &lt;code&gt;admin@footbook.meh&lt;&#x2F;code&gt;)&lt;&#x2F;p&gt;
&lt;p&gt;The other two OAuth providers (GitHub and Dropbox) reject our login for having a different callback URI than expected, and using plain HTTP for a callback URI on a domain&#x2F;IP other than localhost, respectively.
However, if we proxy requests from 127.0.0.1:3000 to the remote server and access the website using it, both of these login systems begin working.&lt;&#x2F;p&gt;
&lt;p&gt;Examining GitHub and Dropbox, we find that Dropbox does not require you verify control of an email address before using it for OAuth authentication.
Unfortunately, the email address &lt;code&gt;admin@footbook.meh&lt;&#x2F;code&gt; is already taken on Dropbox, so we will have to find another way.&lt;&#x2F;p&gt;
&lt;p&gt;Rereading the JavaScript code for the message-sending code, we see that it only uses data before the first &lt;code&gt;+&lt;&#x2F;code&gt; character in the email username (so sending a message to &lt;code&gt;user+something@user.footbook.meh&lt;&#x2F;code&gt; sends a message to &lt;code&gt;user@user.footbook.meh&lt;&#x2F;code&gt;).
We surmise that the OAuth registration code on the server is doing the same thing (otherwise, no messages can be sent to users with &lt;code&gt;+&lt;&#x2F;code&gt; in their email address) and register a Dropbox account with an email address like &lt;code&gt;admin+something@footbook.meh&lt;&#x2F;code&gt;.&lt;&#x2F;p&gt;
&lt;p&gt;We are able to successfully log-in to the site, and at the top of the page is a box with the flag!&lt;&#x2F;p&gt;
&lt;p&gt;&lt;code&gt;hitcon{mom_said_i_can_trust_oauth_T_T}&lt;&#x2F;code&gt;&lt;&#x2F;p&gt;
</content>
        
    </entry>
</feed>
