<?xml version="1.0" encoding="utf-8" standalone="yes"?>
<rss version="2.0"
     xmlns:atom="http://www.w3.org/2005/Atom"
     xmlns:content="http://purl.org/rss/1.0/modules/content/"
     xmlns:media="http://search.yahoo.com/mrss/">
  <channel>

    <title>Posts on less on sec</title>
    <link>https://lessonsec.com/posts/</link>
    <description>
      Recent content in Postson less on sec
    </description>

    <generator>Hugo -- gohugo.io</generator>
    <language>en</language>
    <lastBuildDate>Thu, 04 Sep 2025 21:41:00 &#43;0200</lastBuildDate>
    <atom:link href="https://lessonsec.com/posts/index.xml" rel="self" type="application/rss&#43;xml" /><item>
        <title>nRF51 RBPCONF bypass for firmware dumping</title>
        <link>https://lessonsec.com/posts/nrf51-bypass/</link>
        <guid isPermaLink="true">https://lessonsec.com/posts/nrf51-bypass/</guid>
        <pubDate>Thu, 04 Sep 2025 21:41:00 &#43;0200</pubDate><description>A while ago I read about the firmware dumping technique proposed by Include Security to bypass RBPCONF (Readback Protection) on nRF51 family MCUs. Recently I could spend some time attempting to replicate the effects of their research.</description>
	<content:encoded>&lt;p&gt;A while ago I read about the &lt;a href=&#34;https://blog.includesecurity.com/2015/11/firmware-dumping-technique-for-an-arm-cortex-m0-soc/&#34;&gt;firmware dumping technique proposed by Include Security&lt;/a&gt; to bypass RBPCONF (Readback Protection) on nRF51 family MCUs. Recently I could spend some time attempting to replicate the effects of their research.&lt;/p&gt;
&lt;p&gt;The nRF51 series is Nordic Semiconductor’s family of low-power SoCs built around an ARM Cortex-M0. If you’ve played with Bluetooth Low Energy (BLE) gadgets from a few years back such as beacons, smart locks or fitness trackers there’s a good chance they had an nRF51 inside.&lt;/p&gt;
&lt;p&gt;This technique is significant because retrieving the firmware is almost always the first step before any meaningful reverse engineering. Once the binary is available, an attacker can perform static or dynamic analysis to uncover hardcoded secrets, or look for exploitable bugs that could compromise the security of the system. For connected products such as smart locks, wearables, and IoT sensors, the impact of such access can be substantial.&lt;/p&gt;
&lt;p&gt;What makes this bypass interesting is its non-invasive nature. Other approaches often involve some type of glitching, manipulating reset lines, or even destructive decapsulation, all of which risk damaging the device and require specialized equipment. In this case, the attack relies only on software manipulation through standard debugging interfaces. The target remains fully functional while its memory is exfiltrated, making the method practical and appealing.&lt;/p&gt;
&lt;p&gt;So I decided to visit Aliexpress, bought two of the cheapest board I could find featuring an nRF51822 and went to work.&lt;/p&gt;
&lt;h2 id=&#34;nrf51-security-in-a-nutshell&#34;&gt;nRF51 security in a nutshell&lt;/h2&gt;
&lt;p&gt;As numerous other MCUs, the nRF51 family offers some way to prevent final users of the device from reading the flash memory of the MCU and recover the firmware. Much of the device’s security posture is controlled through a set of non-volatile registers called &lt;strong&gt;User Information Configuration Registers (UICR)&lt;/strong&gt; located at address &lt;code&gt;0x10001000&lt;/code&gt;. This registers are what allows for enabling protections on this devices family.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/nrf51/uicr.png#center&#34; alt=&#34;UICR overview&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;UICR overview&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;Registers inside UICR we are going to focus onto are: &lt;code&gt;CLENR0&lt;/code&gt; and &lt;code&gt;RBPCONF&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;Register &lt;code&gt;CLENR0&lt;/code&gt; is what allows dividing code flash in two areas: Code Region 0 (CR0) and Code Region 1 (CR1). CR0 always starts at &lt;code&gt;0x00000000&lt;/code&gt;, and its size is defined by the &lt;code&gt;CLENR0&lt;/code&gt; register. Everything above that boundary falls into CR1. If &lt;code&gt;CLENR0&lt;/code&gt; is left untouched (&lt;code&gt;0xFFFFFFFF&lt;/code&gt;), the whole flash is simply treated as CR1.&lt;/p&gt;
&lt;p&gt;sThere are a few differences between CR0 and CR1:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Code running in CR0 cannot be modified by code running in CR1.&lt;/li&gt;
&lt;li&gt;Pages of CR0 cannot be erased, CR0 is erasable only via chip-wide wipe (&lt;code&gt;ERASEALL&lt;/code&gt;)&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Generally speaking, this renders CR0 a more secure memory area suitable for critical software components or sensitive data storage.&lt;/p&gt;
&lt;h3 id=&#34;understanding-rbpconf&#34;&gt;Understanding RBPCONF&lt;/h3&gt;
&lt;p&gt;An nRF51 device can be configured with three different security configurations based on &lt;code&gt;RBPCONF&lt;/code&gt;: no protection, &lt;code&gt;PR0&lt;/code&gt; protection and &lt;code&gt;PALL&lt;/code&gt; protection.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/nrf51/rbpconf.png#center&#34; alt=&#34;RBCONF Register&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;RBCONF overview&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;&lt;code&gt;PR0&lt;/code&gt; register allows for locking CR0 memory area. This protection, when enabled, prevents firmware running from CR1 from reading CR0 memory as well as locking the read-back on CR0 area from SWD debugger.&lt;/p&gt;
&lt;p&gt;The nRF51 also exposes the &lt;code&gt;PALL&lt;/code&gt; protection, which locks down all code memory (both CR0 and CR1). Once &lt;code&gt;PALL&lt;/code&gt; is enabled, no external debugger reads are possible. The only way to disable this protection is to perform a full chip erase (&lt;code&gt;ERASEALL&lt;/code&gt;), which wipes both application and configuration data, protecting the firmware from exfiltration. The &lt;code&gt;PALL&lt;/code&gt; mechanism is intended as &amp;ldquo;production lock&amp;rdquo; and is the strongest protection mechanism available in these MCUs.&lt;/p&gt;
&lt;p&gt;One security measure other SoCs offer, is to completely disable debugger accesses. However this is not a possibility with the nRF51 and even though the debugger won&amp;rsquo;t be able to access flash memory directly, this poses a risk to the device and it is exactly the weakness we are abusing to access the whole memory.&lt;/p&gt;
&lt;h3 id=&#34;exploiting-rbpconf&#34;&gt;Exploiting RBPCONF&lt;/h3&gt;
&lt;p&gt;The protection mechanisms in place allow only code already present in the CR0 to read flash memory.&lt;/p&gt;
&lt;p&gt;External debuggers are blocked from issuing flash memory reads directly. So, in order to extract data from the protected memory we will abuse the execution environment against itself. The register state, unlike the flash, remains observable and editable through the debugger interface.&lt;/p&gt;
&lt;p&gt;The &lt;code&gt;RBPCONF&lt;/code&gt; bypass is based on the fact that, being able to control CPU registers, it would be possible to halt and single step the CPU executing the firmware and change the behavior of instructions by altering generic purpose CPU registers values. This way it is possible to hijack instructions already residing in CR0 memory area.
With this knowledge available it&amp;rsquo;s just a matter of finding a load instruction that will take an address from one of the registers and puts the value from that address back to one of the registers.&lt;/p&gt;
&lt;p&gt;Nordic’s model assumes that isolating CR0 and requiring ERASEALL for modification is sufficient to protect sensitive firmware. However, the lack of debugger lockout means these guarantees can be bypassed.&lt;/p&gt;
&lt;h2 id=&#34;the-setup&#34;&gt;The Setup&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;Hardware:&lt;/strong&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;nRF51822 dev board&lt;/li&gt;
&lt;li&gt;SEGGER J-Link&lt;/li&gt;
&lt;li&gt;Linux host machine&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;&lt;strong&gt;Software:&lt;/strong&gt;&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;www.segger.com/products/development-tools/embedded-studio/&#34;&gt;SEGGER Embedded Studio&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://openocd.org/&#34;&gt;OpenOCD&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.nordicsemi.com/Products/Development-tools/nrf-command-line-tools/download&#34;&gt;nRF Command Line Tools&lt;/a&gt; (not strictly required, but handy for enabling protections &amp;amp; restoring a locked device)&lt;/li&gt;
&lt;li&gt;arm-none-eabi-gdb + Python for automation&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;The board I&amp;rsquo;m using is this one:&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/nrf51/board.png#center&#34; alt=&#34;nRF51 board&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;nRF51822 dev board&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;Fortunately SWD pins (SWDIO, SWDCLK) are exposed and it was possible to attempt opening a debug interface straight away. However pin distancing was not compatible with any breakout or breadboard I had at home, so I resorted to using some integrated circuit hooks and these ended up working just as fine.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/nrf51/setup.png#center&#34; alt=&#34;nRF51 board connected&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;Dev board connected to debugger&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;Once board&amp;rsquo;s pins VCC, GND, SWDIO and SWDCLK are connected to J-Link&amp;rsquo;s corresponding pins it was possible to obtain SWD debug access both with J-Link suite tools and with OpenOCD using the commands:&lt;/p&gt;
&lt;p&gt;&lt;code&gt;openocd -f /usr/share/openocd/scripts/interface/jlink.cfg -c &amp;quot;transport select swd&amp;quot; -f /usr/share/openocd/scripts/target/nrf51.cfg&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;&lt;code&gt;JLinkGDBServer -device nrf51822_XXAA -if SWD&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;Personally I&amp;rsquo;m more keen on using OpenOCD for this exploitation specifically because J-Link suite wouldn&amp;rsquo;t allow opening  a GDB connection to nRF51 if the &lt;code&gt;PALL&lt;/code&gt; protection is enabled.&lt;/p&gt;
&lt;p&gt;Once the SWD connection is achieved, we need to flash the device with a custom firmware, to do so I used SEGGER Embedded Studio as it was the fastest way to setup the SDK and toolchain for our target device.&lt;/p&gt;
&lt;p&gt;For this demo a firmware containing a single &lt;code&gt;printf(&amp;quot;SECRET&amp;quot;)&lt;/code&gt; is used and the objective will be to confirm whether the string can still be retrieved with &lt;code&gt;PALL&lt;/code&gt; protection enabled.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/nrf51/firmware.png#center&#34; alt=&#34;firmware&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;Dummy firmware&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;Once the firmware is flashed, we can perform a few tests without protection enabled in order to better understand the differences in the behavior of the debugger when the protection is OFF and when it is ON.&lt;/p&gt;
&lt;p&gt;With the GDB server running, we can attempt connecting and reading some memory:&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/nrf51/noprotection.png#center&#34; alt=&#34;no_protection&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;Memory read demo - no protection&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;As it is possible to see, bytes are correctly read back from flash memory.
In addition notice how we also read  &lt;code&gt;0xE000ED00 (CPUID)&lt;/code&gt; this register will always be populated with &lt;code&gt;0x410CC200&lt;/code&gt; on nRF51 and the value is readable when &lt;code&gt;PALL&lt;/code&gt; protection is in place as well, rendering it a good reference value for future experiments.&lt;/p&gt;
&lt;p&gt;At this point we can enable the &lt;code&gt;PALL&lt;/code&gt; protection with command &lt;code&gt;nrfjprog --rbp ALL&lt;/code&gt;, reboot the target device and attempt performing the same operations again.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/nrf51/protection.png#center&#34; alt=&#34;protection_on&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;Memory read demo - with protection&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;We note how the same addresses come back as &lt;code&gt;0x00000000&lt;/code&gt; when read back.&lt;/p&gt;
&lt;h2 id=&#34;dumping-the-firmware&#34;&gt;Dumping the firmware&lt;/h2&gt;
&lt;p&gt;The exploitation of the vulnerability goes through 2 steps: locating a load instruction and abusing it to read protected memory.&lt;/p&gt;
&lt;p&gt;To achieve the first, it is possible to use GDB to set each register to address &lt;code&gt;0xE000ED00&lt;/code&gt; since it contains a known value. If the instruction PC is pointing is a load, we should find the expected value (&lt;code&gt;0x410CC200&lt;/code&gt;) in one of the registers.&lt;/p&gt;
&lt;p&gt;We will simply need to issue commands:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; style=&#34;color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-shell&#34; data-lang=&#34;shell&#34;&gt;set $r0&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r1&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r2&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r3&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r4&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r5&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r6&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r7&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r8&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r9&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r10&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r11&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r12&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;0xE000ED00
stepi
info registers
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;And we will monitor the output of &lt;code&gt;info registers&lt;/code&gt; to see if any of the register gets populated with the expected value.&lt;/p&gt;
&lt;p&gt;That&amp;rsquo;s exactly what happens after a few iterations of this:&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/nrf51/manual_read.png#center&#34; alt=&#34;manual load&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;Load instruction found&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;We can see that after the execution of instruction at &lt;code&gt;PC=0x82&lt;/code&gt; we have our expected value in register &lt;code&gt;r0&lt;/code&gt;.
Once the load instruction is located, it is necessary to attempt reading bytes from the protected memory.&lt;/p&gt;
&lt;p&gt;So now we populate registers with value &lt;code&gt;0x00000000&lt;/code&gt; and attempt reading that word.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/nrf51/prot_mem_read.png#center&#34; alt=&#34;protected memory read&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;Value read from CR0&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;and as expected we are able to read the first byte of protected memory.&lt;/p&gt;
&lt;p&gt;Now it&amp;rsquo;s time to render the exploit practical and to automate the firmware extraction and we can achieve this in several ways, I&amp;rsquo;ve decided to simply script the interaction with GDB commands.
Depending on the exact MCU you&amp;rsquo;re working with, you may encounter different flash sizes. In this case we are working with an &lt;code&gt;nRF51822_XXAA&lt;/code&gt; which is the most commonly available variant of nRF51822 around and features 256kB of flash memory.&lt;/p&gt;
&lt;p&gt;The extraction script will look something like this:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; style=&#34;color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-shell&#34; data-lang=&#34;shell&#34;&gt;set $i &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;0&lt;/span&gt;
set $end &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; 0x3FFFF
&lt;span style=&#34;color:#66d9ef&#34;&gt;while&lt;/span&gt; $i &amp;lt;&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; $end
  set $pc&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;0x82

  set $r0&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r1&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r2&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r3&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r4&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r5&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r6&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r7&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r8&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r9&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r10&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r11&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$r12&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$i
  stepi

  printf &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;0x%08x\n&amp;#34;&lt;/span&gt;, $r0
  set $i&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;$i+4
end
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;and the output on the terminal when the script is executed looks like this:&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/nrf51/auto_read.png#center&#34; alt=&#34;scripted read&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;Scripted memory read&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;After letting it run the script will have gone through the entire code space. A simple parser will then be used to cleanup the retrieved data and rebuild the binary file.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;For ease of use I&amp;rsquo;ve decided to write a more usable script capable of automatically detecting the load function, dump the firmware and reassemble it to generate a binary output.&lt;/p&gt;
&lt;p&gt;You can find it at: &lt;a href=&#34;https://github.com/0xless/nRF51-RBPCONF-Bypass&#34;&gt;https://github.com/0xless/nRF51-RBPCONF-Bypass&lt;/a&gt;&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;Once the script has finished running, in under 54 minutes, we get &lt;code&gt;firmware.bin&lt;/code&gt; file:&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/nrf51/time.png#center&#34; alt=&#34;dump complete&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;Dump completed in 54 minutes&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;And performing &lt;code&gt;xxd&lt;/code&gt; on the extracted firmware allow us to recover out &lt;code&gt;SECRET&lt;/code&gt; value.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/nrf51/extracted_secret.png#center&#34; alt=&#34;secret extracted&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;Secret value recovered from firmware&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;This proves the functioning of the exploit and the practicality of this attack.&lt;/p&gt;
&lt;p&gt;The PoC script developed for this attack is far from perfect, it takes a lot of time to execute and the GDB + Python interaction is a bit &amp;ldquo;hacky&amp;rdquo;.  A huge improvement it is possible to make is to aim to find instructions that load more bytes of flash memory to registers; an example would be &lt;code&gt;LDMIA Rn!, {Rlist}&lt;/code&gt; that allow up to 32 bytes loads in a single step. When reading the memory, it is easy to evaluate the OPCODE of the instruction just read, if it&amp;rsquo;s a &lt;code&gt;LDMIA&lt;/code&gt; instruction, then we can edit the PC register value to jump there and attempt exfiltrating memory at higher speed.&lt;/p&gt;
&lt;p&gt;I&amp;rsquo;ve attempted sketching this using GDB scripting, but as the complexity of the project increased I realized this scripting language was not the tool for the job. For future developments I want to rewrite the whole script in python using library &lt;code&gt;pyswd&lt;/code&gt; which looks promising in handling SWD interactions directly via python, however it is compatible with ST-Link debuggers only (which I don&amp;rsquo;t own).&lt;/p&gt;
&lt;h2 id=&#34;conclusions&#34;&gt;Conclusions&lt;/h2&gt;
&lt;p&gt;The nRF51’s RBPCONF was designed to keep firmware safe, but not allowing final users to disable debugger access weakens the model. Even under PALL protection, careful register manipulation and instruction reuse make full extraction possible with modest tools.&lt;/p&gt;
&lt;p&gt;In this post we demonstrated how it is possible to do so and walked all the steps needed to discover the issue and replicate the attack.&lt;/p&gt;
</content:encoded>

      </item><item>
        <title>I hacked the Dutch government and all I got was this lousy t-shirt</title>
        <link>https://lessonsec.com/posts/dutch_government_bounty/</link>
        <guid isPermaLink="true">https://lessonsec.com/posts/dutch_government_bounty/</guid>
        <pubDate>Thu, 02 Nov 2023 23:25:14 &#43;0100</pubDate><description>Recently, I was awarded a cool t-shirt from the Dutch government for disclosing and reporting a vulnerability under their National Cyber Security Centre responsible disclosure program.
        Lousy t-shirt    I was able to discover a vulnerability in one of the government&amp;rsquo;s websites.</description>
	<content:encoded>&lt;p&gt;Recently, I was awarded a cool t-shirt from the &lt;strong&gt;Dutch government&lt;/strong&gt; for disclosing and reporting a vulnerability under their &lt;strong&gt;National Cyber Security Centre&lt;/strong&gt; &lt;a href=&#34;https://www.government.nl/topics/cybercrime/fighting-cybercrime-in-the-netherlands/responsible-disclosure&#34;&gt;responsible disclosure program&lt;/a&gt;.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/dutch_government_bounty/tshirt.jpeg#center&#34; alt=&#34;Lousy t-shirt&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;Lousy t-shirt&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;I was able to discover a vulnerability in one of the government&amp;rsquo;s websites.
The platform allows users to compile a survey and offers the possibility to save progress and receive a link via email to resume the it in a second time.&lt;/p&gt;
&lt;p&gt;Testing this functionality I was able to find the parameter responsible for setting the URL to resume the survey in a POST request. This parameter was also not subject to sanification, and so it was possible to inject HTML code into email sent from &lt;code&gt;noreply@[governmentdomain].nl&lt;/code&gt; effectively allowing unauthenticated users to send emails with forged contents to arbitrary addresses, impersonating the Dutch government.&lt;/p&gt;
&lt;p&gt;As a proof of concept, consider this POST request:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; style=&#34;color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-http&#34; data-lang=&#34;http&#34;&gt;&lt;span style=&#34;color:#a6e22e&#34;&gt;POST&lt;/span&gt; /[endpoint] &lt;span style=&#34;color:#66d9ef&#34;&gt;HTTP&lt;/span&gt;&lt;span style=&#34;color:#f92672&#34;&gt;/&lt;/span&gt;&lt;span style=&#34;color:#ae81ff&#34;&gt;1.1&lt;/span&gt;
Host&lt;span style=&#34;color:#f92672&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;[governmentdomain].nl&lt;/span&gt;
User-Agent&lt;span style=&#34;color:#f92672&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;Mozilla/5.0(X11; Linux x86_64; rv: 108.0) Gecko/20100101 Firefox/108.0&lt;/span&gt;
Accept&lt;span style=&#34;color:#f92672&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;application/json, text/javascript, */*; q=0.01&lt;/span&gt;
Accept-Language&lt;span style=&#34;color:#f92672&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;en-US,en;q=0.5&lt;/span&gt;
Accept-Encoding&lt;span style=&#34;color:#f92672&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;gzip, deflate, br&lt;/span&gt;
Referer&lt;span style=&#34;color:#f92672&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;[...]&lt;/span&gt;
Content-Type&lt;span style=&#34;color:#f92672&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;application/x-www-form-urlencoded; charset=UTF-8&lt;/span&gt;
X-Requested-With&lt;span style=&#34;color:#f92672&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;XMLHttpRequest&lt;/span&gt;
Content-Length&lt;span style=&#34;color:#f92672&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;191&lt;/span&gt;
Origin&lt;span style=&#34;color:#f92672&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;https://[governmentdomain].nl&lt;/span&gt;
Connection&lt;span style=&#34;color:#f92672&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;keep-alive&lt;/span&gt;
Cookie&lt;span style=&#34;color:#f92672&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;[...]&lt;/span&gt;
Sec-Fetch-Dest&lt;span style=&#34;color:#f92672&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;empty&lt;/span&gt;
Sec-Fetch-Mode&lt;span style=&#34;color:#f92672&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;cors&lt;/span&gt;
Sec-Fetch-Site&lt;span style=&#34;color:#f92672&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;same-origin&lt;/span&gt;
Pragma&lt;span style=&#34;color:#f92672&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;no-cache&lt;/span&gt;
Cache-Control&lt;span style=&#34;color:#f92672&#34;&gt;:&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;no-cache&lt;/span&gt;

[...]
link=https%3A%2F%2Fexample.org&amp;lt;h1&amp;gt;hack&amp;lt;/h1&amp;gt;
[...]
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;With the received email looking like this:&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/dutch_government_bounty/poc.jpg#center&#34; alt=&#34;poc email&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;PoC email with injected HTML code&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;At this point I stopped testing in accordance to the rules of the responsible disclosure program and reported the issue.&lt;/p&gt;
&lt;p&gt;Thanks to the Dutch National Cyber Security Centre for promptly fixing the issue and awarding me the t-shirt. It&amp;rsquo;s great to see a government taking proactive steps towards improving their cybersecurity posture and promoting responsible disclosure.&lt;/p&gt;
</content:encoded>

      </item><item>
        <title>Attacking RKE: How to hack a car open</title>
        <link>https://lessonsec.com/posts/attacking_rke_how_to_hack_a_car_open/</link>
        <guid isPermaLink="true">https://lessonsec.com/posts/attacking_rke_how_to_hack_a_car_open/</guid>
        <pubDate>Fri, 30 Dec 2022 22:30:14 &#43;0100</pubDate><description>I&amp;rsquo;ve always found cybersecurity to be more interesting when implications reflect in the &amp;ldquo;real world&amp;rdquo; and this is the reason hacking physical devices is fun to me. Well, it turns out that the more the hack is controversial, the funnier it is to carry out!</description>
	<content:encoded>&lt;p&gt;I&amp;rsquo;ve always found cybersecurity to be more interesting when  implications reflect in the &amp;ldquo;real world&amp;rdquo; and this is the reason hacking  physical devices is fun to me. Well, it turns out that the more the hack is controversial, the funnier it is to carry out!  For this reason I  got into remote controlled devices hacking, and in particular into car  remotes hacking. A while ago I got all the hardware needed to attempt  attacking these devices, so I could finally attempt some attacks.&lt;/p&gt;
</content:encoded>

      </item><item>
        <title>Walkthrough: BLE CTF</title>
        <link>https://lessonsec.com/posts/walkthrough-ble-ctf/</link>
        <guid isPermaLink="true">https://lessonsec.com/posts/walkthrough-ble-ctf/</guid>
        <pubDate>Sun, 17 Apr 2022 14:08:32 &#43;0200</pubDate><description>This CTF has been in my todo list for a good while, finally I had the time to solve it and to publish a walkthrough article on it! The challenge is available at: https://github.</description>
	<content:encoded>&lt;p&gt;This CTF has been in my todo list for a good while, finally I had the time to solve it and to publish a walkthrough article on it!
The challenge is available at: &lt;a href=&#34;https://github.com/hackgnar/ble_ctf&#34;&gt;https://github.com/hackgnar/ble_ctf&lt;/a&gt; and is an awesome tool to learn about BLE and get your feet wet.&lt;/p&gt;
&lt;p&gt;To be fair I expected the CTF to be a bit more security oriented, but I learned way more than I expected, both on BLE technologies and on the tools used to interact with those.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;em&gt;&lt;strong&gt;Disclaimer&lt;/strong&gt;&lt;/em&gt;&lt;br&gt;
I&amp;rsquo;m not a fan of walkthrough articles that ignore the request of the creators not to post those.
The reasons I&amp;rsquo;m publishing this article are that:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;No request by the creator has been made not to post the solutions&lt;/li&gt;
&lt;li&gt;There are plenty of walkthrough articles on this CTF that don&amp;rsquo;t really teach anything and barely explain the solutions&lt;/li&gt;
&lt;li&gt;The CTF is self-hosted and is more of a teaching tool than a proper challenge&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Of course I strongly recommend trying to solve the challenges on your own before checking the solutions here!
Anyway I suggest reading the first part of the articles to gather some useful information about the technologies involved in the challenge.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;Without further ado, let&amp;rsquo;s get started!&lt;/p&gt;
&lt;h2 id=&#34;how-does-this-ctf-works&#34;&gt;How does this CTF works?&lt;/h2&gt;
&lt;p&gt;The CTF is composed of a series of challenges hosted on an ESP32 board.
The software required to setup the challenge is in fact a firmware to be installed on the board. I won&amp;rsquo;t enter in details about the installation in this article, but you can find detailed instructions here: &lt;a href=&#34;https://github.com/hackgnar/ble_ctf/blob/master/docs/setup.md&#34;&gt;https://github.com/hackgnar/ble_ctf/blob/master/docs/setup.md&lt;/a&gt;&lt;/p&gt;
&lt;p&gt;When the firmware is installed, the ESP32 will host a GATT server with which we can interact to solve the challenges and gather the flags.&lt;/p&gt;
&lt;h3 id=&#34;whats-a-gatt-server&#34;&gt;What&amp;rsquo;s a GATT server&lt;/h3&gt;
&lt;p&gt;GATT is the name of a protocol that is used to exchange data between two Bluetooth Low Energy devices.
This is developed on top of the Attribute Protocol (ATT) and manages device interactions following the advertising and pairing processes.
A GATT Server is a device that stores attribute data locally and provides data access methods to a remote GATT Client paired via BLE.  A client, on the other hand, is a device that access data on a remote GATT Server. When two devices are paired, each can function as both a GATT Server and a GATT Client.&lt;/p&gt;
&lt;p&gt;GATT lists a device’s characteristics, descriptors, and services in a table as either 16 or 32-bits values.
A characteristic is a data value sent between the server and the client.&lt;/p&gt;
&lt;p&gt;These characteristics can have descriptors that provide additional information about them.
Characteristics are often grouped in services if they have purposes related to each other. Services can have several characteristics.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/BLE_CTF/gatt_server.jpg#center&#34; alt=&#34;GATT server layout&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;GATT Server content layout &lt;br /&gt;Credits - Practical IoT Hacking: The Definitive Guide to Attacking the Internet of Things&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;h3 id=&#34;attgatt-basics&#34;&gt;ATT/GATT basics&lt;/h3&gt;
&lt;p&gt;It is possible to interact with a GATT server, by interacting with each of the characteristics available.
It is possible to do that using handles, or UUID: handles define the address of a characteristic, while the UUID works as an identifier, but also gives the user some indication about the content of a characteristic. In general, handles are to be preferred to reference to a particular characteristic, this is because UUID can vary depending on the GATT implementation, while handles are expected to remain immutable for each device.&lt;/p&gt;
&lt;p&gt;As anticipated, UUID contain info about the service or characteristic. These are useful because they are defined by profiles: standards that use known UUID to serve specific information, profiles can be found here: &lt;a href=&#34;https://www.bluetooth.com/specifications/specs/&#34;&gt;https://www.bluetooth.com/specifications/specs/&lt;/a&gt;
While UUID vary depending on the device functionality some UUID remains the same, for example: 0x2800, around which service discovery is built. This UUID allows GATT servers to understand service boundaries without having to know the exact standard the device is following.&lt;/p&gt;
&lt;p&gt;Finally, there are characteristic properties. Properties indicate how to interact with a characteristic and what to expect from it.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/BLE_CTF/properties.jpg#center&#34; alt=&#34;properties&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;GATT chatateristic proprieties  &lt;br /&gt;Credits - devzone.nordicsemi.com&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;Properties are defined as an hex value and work as bitmasks, so using bitwise operations it is possible reveal the properties of a characteristic starting from its properties value.&lt;/p&gt;
&lt;p&gt;Properties need to be interpreted knowing Attribute Protocol Packets, these are:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;Commands         	    (Client -&amp;gt; Server, no response required)&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Requests            	     (Client -&amp;gt; Server, response required)&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Responses         	    (Server -&amp;gt; Client, it&amp;rsquo;s the response to a request)&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Notifications      	    (Server -&amp;gt; Client, no response required - Signal the fact that a&lt;/p&gt;
&lt;p&gt;                 characteristic&amp;rsquo;s value has changed)&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Indications        	     (Server -&amp;gt; Client, ACK response required by the client - Similar to&lt;/p&gt;
&lt;p&gt;                notifications)&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Confirmations   	    (Client -&amp;gt; Server, it&amp;rsquo;s the response to an indication)&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;As indicated in the image, the &lt;code&gt;Read&lt;/code&gt; and &lt;code&gt;Write&lt;/code&gt; properties are like permissions, and allow the reading and writing of the characteristic if set.
The other properties are an indication of the behavior of a characteristic in response of an action by the client.&lt;/p&gt;
&lt;p&gt;Actions performed by the client are limited to read and write operations.
While read operations are requests by nature, write operations can either be commands or requests.&lt;/p&gt;
&lt;h2 id=&#34;ctf&#34;&gt;CTF&lt;/h2&gt;
&lt;p&gt;The tools that will be employed for this challenge are: gatttool and hcitool.
There are other tools that can be used, in particular bettercap, which is a bit more user friendly but lacks some functionalities, or libraries that implement GATT operations, that were avoided to allow familiarizing with the tools available on a standard linux system.
I think this &amp;ldquo;Living off the Land&amp;rdquo; approach helps better understanding GATT operations and also leads to a more generally employable approach to solve BLE related tasks. Of course you&amp;rsquo;re free to use the tools you prefer for this challenge.&lt;/p&gt;
&lt;p&gt;Before starting, I suggest familiarizing with the challenge page and to understand how to operate actions relative to the challenge, like reading the score and submitting a flag. The list of the flags at the bottom of the page is really useful, as understanding exactly what to do can be tricky.
There are also hints there, don&amp;rsquo;t be afraid to check those out. None of the hints gives away too much and in certain cases those are needed to understand the challenge and to get the flag.&lt;/p&gt;
&lt;p&gt;NOTE: the score is reset each time the ESP32 is powered off! Keep that in mind.&lt;/p&gt;
&lt;hr&gt;
&lt;p&gt;Let&amp;rsquo;s begin! First thing first, we need to retrieve the device BT MAC address and we can do that using hcitool:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ sudo hcitool lescan
LE Scan ...
78:21:84:80:A2:22 BLECTF
[...]
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Now we know the address for my board is: &lt;code&gt;78:21:84:80:A2:22&lt;/code&gt;, it will vary on yours.&lt;/p&gt;
&lt;p&gt;Once we have the address we can start enumerating services on the GATT server.
The first thing to do is to connect to the board, we will do that using &lt;code&gt;gatttool&lt;/code&gt; and its interactive mode:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ gatttool -I
[                 ][LE]&amp;gt; connect 78:21:84:80:A2:22
Attempting to connect to 78:21:84:80:A2:22
Connection successful
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Now we need to enumerate the services, we can do that using the &lt;code&gt;primary&lt;/code&gt; command or by reading the UUID 0x2800.&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;[78:21:84:80:A2:22][LE]&amp;gt; primary
attr handle: 0x0001, end grp handle: 0x0005 uuid: 00001801-0000-1000-8000-00805f9b34fb
attr handle: 0x0014, end grp handle: 0x001c uuid: 00001800-0000-1000-8000-00805f9b34fb
attr handle: 0x0028, end grp handle: 0xffff uuid: 000000ff-0000-1000-8000-00805f9b34fb
[78:21:84:80:A2:22][LE]&amp;gt; char-read-uuid 0x2800
handle: 0x0001 	 value: 01 18 
handle: 0x0014 	 value: 00 18 
handle: 0x0028 	 value: ff 00 
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;And in both cases we retrieve services boundaries. The first two services are standard, and contain info about the server itself, while the third is the one we want to work with.&lt;/p&gt;
&lt;p&gt;Now we can enumerate the characteristic of each service. This can be done using the command &lt;code&gt;characteristics&lt;/code&gt; and using the boundaries found as upper and lower limits:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;[78:21:84:80:A2:22][LE]&amp;gt; characteristics 0x0001 0x0014
handle: 0x0002, char properties: 0x20, char value handle: 0x0003, uuid: 00002a05-0000-1000-8000-00805f9b34fb
[78:21:84:80:A2:22][LE]&amp;gt; characteristics 0x0014 0x0028
handle: 0x0015, char properties: 0x02, char value handle: 0x0016, uuid: 00002a00-0000-1000-8000-00805f9b34fb
handle: 0x0017, char properties: 0x02, char value handle: 0x0018, uuid: 00002a01-0000-1000-8000-00805f9b34fb
handle: 0x0019, char properties: 0x02, char value handle: 0x001a, uuid: 00002aa6-0000-1000-8000-00805f9b34fb
[78:21:84:80:A2:22][LE]&amp;gt; characteristics 0x0028 0x00ff
handle: 0x0029, char properties: 0x02, char value handle: 0x002a, uuid: 0000ff01-0000-1000-8000-00805f9b34fb
handle: 0x002b, char properties: 0x0a, char value handle: 0x002c, uuid: 0000ff02-0000-1000-8000-00805f9b34fb
handle: 0x002d, char properties: 0x02, char value handle: 0x002e, uuid: 0000ff03-0000-1000-8000-00805f9b34fb
handle: 0x002f, char properties: 0x02, char value handle: 0x0030, uuid: 0000ff04-0000-1000-8000-00805f9b34fb
handle: 0x0031, char properties: 0x0a, char value handle: 0x0032, uuid: 0000ff05-0000-1000-8000-00805f9b34fb
handle: 0x0033, char properties: 0x0a, char value handle: 0x0034, uuid: 0000ff06-0000-1000-8000-00805f9b34fb
handle: 0x0035, char properties: 0x0a, char value handle: 0x0036, uuid: 0000ff07-0000-1000-8000-00805f9b34fb
handle: 0x0037, char properties: 0x02, char value handle: 0x0038, uuid: 0000ff08-0000-1000-8000-00805f9b34fb
handle: 0x0039, char properties: 0x08, char value handle: 0x003a, uuid: 0000ff09-0000-1000-8000-00805f9b34fb
handle: 0x003b, char properties: 0x0a, char value handle: 0x003c, uuid: 0000ff0a-0000-1000-8000-00805f9b34fb
handle: 0x003d, char properties: 0x02, char value handle: 0x003e, uuid: 0000ff0b-0000-1000-8000-00805f9b34fb
handle: 0x003f, char properties: 0x1a, char value handle: 0x0040, uuid: 0000ff0c-0000-1000-8000-00805f9b34fb
handle: 0x0041, char properties: 0x02, char value handle: 0x0042, uuid: 0000ff0d-0000-1000-8000-00805f9b34fb
handle: 0x0043, char properties: 0x2a, char value handle: 0x0044, uuid: 0000ff0e-0000-1000-8000-00805f9b34fb
handle: 0x0045, char properties: 0x1a, char value handle: 0x0046, uuid: 0000ff0f-0000-1000-8000-00805f9b34fb
handle: 0x0047, char properties: 0x02, char value handle: 0x0048, uuid: 0000ff10-0000-1000-8000-00805f9b34fb
handle: 0x0049, char properties: 0x2a, char value handle: 0x004a, uuid: 0000ff11-0000-1000-8000-00805f9b34fb
handle: 0x004b, char properties: 0x02, char value handle: 0x004c, uuid: 0000ff12-0000-1000-8000-00805f9b34fb
handle: 0x004d, char properties: 0x02, char value handle: 0x004e, uuid: 0000ff13-0000-1000-8000-00805f9b34fb
handle: 0x004f, char properties: 0x0a, char value handle: 0x0050, uuid: 0000ff14-0000-1000-8000-00805f9b34fb
handle: 0x0051, char properties: 0x0a, char value handle: 0x0052, uuid: 0000ff15-0000-1000-8000-00805f9b34fb
handle: 0x0053, char properties: 0x9b, char value handle: 0x0054, uuid: 0000ff16-0000-1000-8000-00805f9b34fb
handle: 0x0055, char properties: 0x02, char value handle: 0x0056, uuid: 0000ff17-0000-1000-8000-00805f9b34fb
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;And just like that we retrieved every characteristic available, their value and their properties.&lt;/p&gt;
&lt;p&gt;At this point it is useful to define utility functions to work with the handles:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; style=&#34;color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-bash&#34; data-lang=&#34;bash&#34;&gt;mac&lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;78:21:84:80:A2:22&amp;#34;&lt;/span&gt; &lt;span style=&#34;color:#75715e&#34;&gt;#change the value to match your board&amp;#39;s MAC&lt;/span&gt;

&lt;span style=&#34;color:#75715e&#34;&gt;# HEX encode&lt;/span&gt;
encode&lt;span style=&#34;color:#f92672&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;{&lt;/span&gt;
        echo -n $1 | xxd -ps;
&lt;span style=&#34;color:#f92672&#34;&gt;}&lt;/span&gt;

&lt;span style=&#34;color:#75715e&#34;&gt;# HEX decode&lt;/span&gt;
decode&lt;span style=&#34;color:#f92672&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;{&lt;/span&gt;
        echo $1 | tr -d &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;&amp;#34;&lt;/span&gt; | xxd -r -p; echo
&lt;span style=&#34;color:#f92672&#34;&gt;}&lt;/span&gt;

&lt;span style=&#34;color:#75715e&#34;&gt;# Write flag to handle 0x002c&lt;/span&gt;
submit_flag&lt;span style=&#34;color:#f92672&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;{&lt;/span&gt;
        gatttool -b $mac --char-write-req -a 0x002c -n &lt;span style=&#34;color:#e6db74&#34;&gt;`&lt;/span&gt;encode &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;&lt;/span&gt;$1&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;`&lt;/span&gt;
&lt;span style=&#34;color:#f92672&#34;&gt;}&lt;/span&gt;

&lt;span style=&#34;color:#75715e&#34;&gt;# Read handle 0x002a to get the score&lt;/span&gt;
get_score&lt;span style=&#34;color:#f92672&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;{&lt;/span&gt;
        read_hnd 0x002a
&lt;span style=&#34;color:#f92672&#34;&gt;}&lt;/span&gt;

&lt;span style=&#34;color:#75715e&#34;&gt;# Read values from handle and decode it&lt;/span&gt;
read_hnd&lt;span style=&#34;color:#f92672&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;{&lt;/span&gt;
        decode &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;`gatttool -b &lt;/span&gt;$mac&lt;span style=&#34;color:#e6db74&#34;&gt; --char-read -a &lt;/span&gt;$1&lt;span style=&#34;color:#e6db74&#34;&gt; | awk -F&amp;#39;:&amp;#39; &amp;#39;{print &lt;/span&gt;$2&lt;span style=&#34;color:#e6db74&#34;&gt;}&amp;#39;`&amp;#34;&lt;/span&gt;
&lt;span style=&#34;color:#f92672&#34;&gt;}&lt;/span&gt;

&lt;span style=&#34;color:#75715e&#34;&gt;# List properties from hex property value&lt;/span&gt;
get_properties&lt;span style=&#34;color:#f92672&#34;&gt;()&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;{&lt;/span&gt;
		&lt;span style=&#34;color:#66d9ef&#34;&gt;if&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;((&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;(&lt;/span&gt;$1 &amp;amp; 0x1&lt;span style=&#34;color:#f92672&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;==&lt;/span&gt; 0x1 &lt;span style=&#34;color:#f92672&#34;&gt;))&lt;/span&gt;; &lt;span style=&#34;color:#66d9ef&#34;&gt;then&lt;/span&gt; echo &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;Broadcast&amp;#34;&lt;/span&gt;; &lt;span style=&#34;color:#66d9ef&#34;&gt;fi&lt;/span&gt;
        &lt;span style=&#34;color:#66d9ef&#34;&gt;if&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;((&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;(&lt;/span&gt;$1 &amp;amp; 0x2&lt;span style=&#34;color:#f92672&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;==&lt;/span&gt; 0x2 &lt;span style=&#34;color:#f92672&#34;&gt;))&lt;/span&gt;; &lt;span style=&#34;color:#66d9ef&#34;&gt;then&lt;/span&gt; echo &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;Read&amp;#34;&lt;/span&gt;; &lt;span style=&#34;color:#66d9ef&#34;&gt;fi&lt;/span&gt;
        &lt;span style=&#34;color:#66d9ef&#34;&gt;if&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;((&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;(&lt;/span&gt;$1 &amp;amp; 0x4&lt;span style=&#34;color:#f92672&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;==&lt;/span&gt; 0x4 &lt;span style=&#34;color:#f92672&#34;&gt;))&lt;/span&gt;; &lt;span style=&#34;color:#66d9ef&#34;&gt;then&lt;/span&gt; echo &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;Write without response&amp;#34;&lt;/span&gt;; &lt;span style=&#34;color:#66d9ef&#34;&gt;fi&lt;/span&gt;
        &lt;span style=&#34;color:#66d9ef&#34;&gt;if&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;((&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;(&lt;/span&gt;$1 &amp;amp; 0x8&lt;span style=&#34;color:#f92672&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;==&lt;/span&gt; 0x8 &lt;span style=&#34;color:#f92672&#34;&gt;))&lt;/span&gt;; &lt;span style=&#34;color:#66d9ef&#34;&gt;then&lt;/span&gt; echo &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;Write&amp;#34;&lt;/span&gt;; &lt;span style=&#34;color:#66d9ef&#34;&gt;fi&lt;/span&gt;
        &lt;span style=&#34;color:#66d9ef&#34;&gt;if&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;((&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;(&lt;/span&gt;$1 &amp;amp; 0x10&lt;span style=&#34;color:#f92672&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;==&lt;/span&gt; 0x10 &lt;span style=&#34;color:#f92672&#34;&gt;))&lt;/span&gt;; &lt;span style=&#34;color:#66d9ef&#34;&gt;then&lt;/span&gt; echo &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;Notify&amp;#34;&lt;/span&gt;; &lt;span style=&#34;color:#66d9ef&#34;&gt;fi&lt;/span&gt;
        &lt;span style=&#34;color:#66d9ef&#34;&gt;if&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;((&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;(&lt;/span&gt;$1 &amp;amp; 0x20&lt;span style=&#34;color:#f92672&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;==&lt;/span&gt; 0x20 &lt;span style=&#34;color:#f92672&#34;&gt;))&lt;/span&gt;; &lt;span style=&#34;color:#66d9ef&#34;&gt;then&lt;/span&gt; echo &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;Indicate&amp;#34;&lt;/span&gt;; &lt;span style=&#34;color:#66d9ef&#34;&gt;fi&lt;/span&gt;
        &lt;span style=&#34;color:#66d9ef&#34;&gt;if&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;((&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;(&lt;/span&gt;$1 &amp;amp; 0x40&lt;span style=&#34;color:#f92672&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;==&lt;/span&gt; 0x40 &lt;span style=&#34;color:#f92672&#34;&gt;))&lt;/span&gt;; &lt;span style=&#34;color:#66d9ef&#34;&gt;then&lt;/span&gt; echo &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;Authenticated Signed Writes&amp;#34;&lt;/span&gt;; &lt;span style=&#34;color:#66d9ef&#34;&gt;fi&lt;/span&gt;
        &lt;span style=&#34;color:#66d9ef&#34;&gt;if&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;((&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;(&lt;/span&gt;$1 &amp;amp; 0x80&lt;span style=&#34;color:#f92672&#34;&gt;)&lt;/span&gt; &lt;span style=&#34;color:#f92672&#34;&gt;==&lt;/span&gt; 0x80 &lt;span style=&#34;color:#f92672&#34;&gt;))&lt;/span&gt;; &lt;span style=&#34;color:#66d9ef&#34;&gt;then&lt;/span&gt; echo &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;Extended Properties&amp;#34;&lt;/span&gt;; &lt;span style=&#34;color:#66d9ef&#34;&gt;fi&lt;/span&gt;
&lt;span style=&#34;color:#f92672&#34;&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;p&gt;NOTE: properties for each characteristic of interest are listed in the challenge description, so the &lt;code&gt;get_properties&lt;/code&gt; function won&amp;rsquo;t be used explicitly.&lt;/p&gt;
&lt;hr&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Flag #1&lt;/strong&gt;
To get this flag we need to use the &lt;a href=&#34;https://github.com/hackgnar/ble_ctf/blob/master/docs/hints/flag1.md&#34;&gt;hint&lt;/a&gt;!&lt;/li&gt;
&lt;/ul&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ gatttool -b 78:21:84:80:A2:22 --char-write-req -a 0x002c -n $(echo -n &amp;quot;12345678901234567890&amp;quot;|xxd -ps)
Characteristic value was written successfully
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Now, reading the handle 0x002a confirms we got the first flag.&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ get_score
Score:1 /20
&lt;/code&gt;&lt;/pre&gt;&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Flag 0x002e&lt;/strong&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;Properties: Read&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;To get this flag we simply need to read the handle 0x002e.&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ read_hnd 0x002e
d205303e099ceff44835
less@machine:~$ submit_flag d205303e099ceff44835
less@machine:~$ get_score
Score:2 /20
&lt;/code&gt;&lt;/pre&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Flag 0x0030&lt;/strong&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&amp;ldquo;MD5 of Device Name&amp;rdquo;&lt;/p&gt;
&lt;p&gt;Properties: Read&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;So for this flag we need to submit the MD5 of the Device Name.
Note: the MD5 hash needs to be truncated to 20 characters as suggested in the README of the CTF project.&lt;/p&gt;
&lt;p&gt;We already know the device name as we encountered it connecting to the device:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ sudo hcitool lescan
LE Scan ...
78:21:84:80:A2:22 BLECTF
[...]
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Now we only need to get the MD5 digest of the name, cut and submit it:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ echo -n &amp;quot;BLECTF&amp;quot; | md5sum | cut -c 1-20
5cd56d74049ae40f442e
less@machine:~$ submit_flag 5cd56d74049ae40f442e
Characteristic value was written successfully
less@machine:~$ get_score 
Score:3 /20
&lt;/code&gt;&lt;/pre&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Flag 0x0016&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;This is a particular challenge, the hint says:&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&amp;ldquo;Bluetooth GATT services provide some extra device attributes.  Try finding the value of the Generic Access -&amp;gt; Device Name.&amp;rdquo;&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;But the name of the challenge is &amp;ldquo;Flag 0x0016&amp;rdquo;, so it gives it away!&lt;/p&gt;
&lt;p&gt;Reading the handle we get the flag:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ read_hnd 0x0016
2b00042f7481c7b056c4b410d28f33cf
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Of course we need to cut it before submitting it (as it is a name and the README clearly states that names and digests need to be cut to the 20th character):&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ echo 2b00042f7481c7b056c4b410d28f33cf | cut -c 1-20
2b00042f7481c7b056c4
less@machine:~$  submit_flag 2b00042f7481c7b056c4
Characteristic value was written successfully
less@machine:~$  get_score 
Score:4 /20
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;But it is important to understand the reason why this flag is there.
We already talked about profiles and standard UUID, these include an UUID that corresponds to the Device Name, this UUID is: 0x2A00.&lt;/p&gt;
&lt;p&gt;Using &lt;code&gt;gatttool&lt;/code&gt;, we can read the UUID and note that the handle is indeed 0x0016:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ gatttool -b 78:21:84:80:A2:22 --char-read -u 0x2A00
handle: 0x0016 	 value: 32 62 30 30 30 34 32 66 37 34 38 31 63 37 62 30 35 36 63 
&lt;/code&gt;&lt;/pre&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Flag 0x0032&lt;/strong&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;The content of the handle is: &amp;ldquo;Write anything here&amp;rdquo;&lt;/p&gt;
&lt;p&gt;Properties: Read, Write&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;To get the flag we need to write &amp;ldquo;anything&amp;rdquo; to the 0x0032 handle.&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ gatttool -b 78:21:84:80:A2:22 --char-write-req -a 0x0032 -n `encode &amp;quot;anything&amp;quot;`
Characteristic value was written successfully
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Now, we can read the handle a second time and it will reveal the flag&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ read_hnd 0x0032
3873c0270763568cf7aa
less@machine:~$ submit_flag 3873c0270763568cf7aa
Characteristic value was written successfully
less@machine:~$ get_score 
Score:5 /20
&lt;/code&gt;&lt;/pre&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Flag 0x0034&lt;/strong&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;The content of the handle is: &amp;ldquo;Write the ascii value &amp;ldquo;yo&amp;rdquo; here&amp;rdquo;&lt;/p&gt;
&lt;p&gt;Properties: Read, Write&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;The task is similar to the last one, but this time we don&amp;rsquo;t have to hex encode the string&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ gatttool -b 78:21:84:80:A2:22 --char-write-req -a 0x0034 -n `encode &amp;quot;yo&amp;quot;`
Characteristic value was written successfully
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Now, we can get the flag reading the handle again&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ read_hnd 0x0034
c55c6314b3db0a6128af
less@machine:~$ submit_flag c55c6314b3db0a6128af
Characteristic value was written successfully
less@machine:~$ get_score 
Score:6 /20
&lt;/code&gt;&lt;/pre&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Flag 0x0036&lt;/strong&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;The content of the handle is: &amp;ldquo;Write the hex value 0x07 here&amp;rdquo;&lt;/p&gt;
&lt;p&gt;Properties: Read, Write&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;This task is not different from the previous ones, but since the default encoding used in BLE communications is hex, and the value is to be sent in hex, no encoding needs to be used&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ gatttool -b 78:21:84:80:A2:22 --char-write-req -a 0x0036 -n 07
Characteristic value was written successfully
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Now the flag should be available at the same handle&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ read_hnd 0x0036
1179080b29f8da16ad66
less@machine:~$ submit_flag 1179080b29f8da16ad66
Characteristic value was written successfully
less@machine:~$ get_score 
Score:7 /20
&lt;/code&gt;&lt;/pre&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Flag 0x0038&lt;/strong&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;The content of the handle is: &amp;ldquo;Write 0xC9 to handle 58&amp;rdquo;&lt;/p&gt;
&lt;p&gt;Properties: Read
Handle 58 properties: Write&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;First off we need to convert 58 in hex to get the hex value for the handle, &lt;code&gt;hex(58)&lt;/code&gt; is 0x3A.
Now we need to write the hex value 0xC9 to the handle, this can be done exactly like we did for the last challenge:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ gatttool -b 78:21:84:80:A2:22 --char-write-req -a 0x003A -n C9
Characteristic value was written successfully
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Now reading the handle 0x0038 again reveals the flag&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ read_hnd 0x0038
f8b136d937fad6a2be9f
less@machine:~$ submit_flag f8b136d937fad6a2be9f
Characteristic value was written successfully
less@machine:~$ get_score 
Score:8 /20
&lt;/code&gt;&lt;/pre&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Flag 0x003C&lt;/strong&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;The content of the handle is: &amp;ldquo;Brute force my value 00 to ff&amp;rdquo;&lt;/p&gt;
&lt;p&gt;Properties: Read, Write&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;This can be achieved in multiple ways, but for consistency &lt;code&gt;gatttool&lt;/code&gt; and a bit of bash scripting will be used.&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ for i in {0..255};
&amp;gt; do gatttool -b 78:21:84:80:A2:22 --char-write-req -a 0x003c -n $(printf &#39;%02x\n&#39; $i) &amp;gt; /dev/null;
&amp;gt; done;
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;This script iterates through every value from 0 to 255 (which is FF in hex) and writes such value in the handle 0x003C. The &lt;code&gt;$(printf &#39;%02x\n&#39; $i);&lt;/code&gt; command converts the value to write from decimal to hex.&lt;/p&gt;
&lt;p&gt;Once the script has finished, it&amp;rsquo;s possible to read the handle 0x003C again to get the flag&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ read_hnd 0x003c
933c1fcfa8ed52d2ec05
less@machine:~$ submit_flag 933c1fcfa8ed52d2ec05
Characteristic value was written successfully
less@machine:~$ get_score 
Score:9 /20
&lt;/code&gt;&lt;/pre&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Flag 0x003E&lt;/strong&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;The content of the handle is: &amp;ldquo;Read me 1000 times&amp;rdquo;&lt;/p&gt;
&lt;p&gt;Properties: Read&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;This can be done simply modifying the script used in the previous challenge&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ for i in {0..1000}; 
&amp;gt; do gatttool -b 78:21:84:80:A2:22 --char-read -a 0x003e;
&amp;gt; done;
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;This command will print out the content of the reads, and after a while you&amp;rsquo;ll notice that the output changes like in the example here:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;[...]
Characteristic value/descriptor: 52 65 61 64 20 6d 65 20 31 30 30 30 20 74 69 6d 65 73 
Characteristic value/descriptor: 52 65 61 64 20 6d 65 20 31 30 30 30 20 74 69 6d 65 73 
Characteristic value/descriptor: 52 65 61 64 20 6d 65 20 31 30 30 30 20 74 69 6d 65 73 
Characteristic value/descriptor: 36 66 66 63 64 32 31 34 66 66 65 62 64 63 30 64 30 36 39 65 
Characteristic value/descriptor: 36 66 66 63 64 32 31 34 66 66 65 62 64 63 30 64 30 36 39 65 
Characteristic value/descriptor: 36 66 66 63 64 32 31 34 66 66 65 62 64 63 30 64 30 36 39 65 
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;The values printed after the variation represent the flag!&lt;/p&gt;
&lt;p&gt;So we just need to submit it to complete this challenge&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ decode &amp;quot;36 66 66 63 64 32 31 34 66 66 65 62 64 63 30 64 30 36 39 65&amp;quot;
6ffcd214ffebdc0d069e
less@machine:~$ submit_flag 6ffcd214ffebdc0d069e
Characteristic value was written successfully
less@machine:~$ get_score 
Score:10/20 
&lt;/code&gt;&lt;/pre&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Flag 0x0040&lt;/strong&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;The content of the handle is: &amp;ldquo;Listen to me for a single notification&amp;rdquo;&lt;/p&gt;
&lt;p&gt;Properties: Read, Write, Notify&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;To listen for a notification, we first need to send a write request, but we will have to listen to the notification, this can be achieved with the following command:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ gatttool -b 78:21:84:80:A2:22 --char-write-req --handle=0x0040 --value=dummy --listen
Characteristic value was written successfully
Notification handle = 0x0040 value: 35 65 63 33 37 37 32 62 63 64 30 30 63 66 30 36 64 38 65 62 
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;The notification value is the flag!&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ decode &amp;quot;35 65 63 33 37 37 32 62 63 64 30 30 63 66 30 36 64 38 65 62&amp;quot;
5ec3772bcd00cf06d8eb
less@machine:~$ submit_flag 5ec3772bcd00cf06d8eb
Characteristic value was written successfully
less@machine:~$ get_score 
Score:11/20 
&lt;/code&gt;&lt;/pre&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Flag 0x0042&lt;/strong&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;The content of the handle is: &amp;ldquo;Listen to handle 0x0044 for a single indication&amp;rdquo;&lt;/p&gt;
&lt;p&gt;Properties: Read&lt;/p&gt;
&lt;p&gt;Handle 0x0044 Properties: Read, Write, Indicate&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;This flag can be obtained just like the last one:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ gatttool -b 78:21:84:80:A2:22 --char-write-req --handle=0x0044 --value=ffff --listen
Characteristic value was written successfully
Indication   handle = 0x0044 value: 63 37 62 38 36 64 64 31 32 31 38 34 38 63 37 37 63 31 31 33 
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Once the notification value is retrieved we can decode and submit it:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ decode &amp;quot;63 37 62 38 36 64 64 31 32 31 38 34 38 63 37 37 63 31 31 33&amp;quot;
c7b86dd121848c77c113
less@machine:~$ submit_flag c7b86dd121848c77c113
Characteristic value was written successfully
less@machine:~$ get_score 
Score:12/20 
&lt;/code&gt;&lt;/pre&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Flag 0x0046&lt;/strong&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;The content of the handle is: &amp;ldquo;Listen to me for multi notifications&amp;rdquo;&lt;/p&gt;
&lt;p&gt;Properties: Read, Write, Notify&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;And with the same command we can get this flag too!&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ gatttool -b 78:21:84:80:A2:22 --char-write-req --handle=0x0046 --value=ffff --listen
Characteristic value was written successfully
Notification handle = 0x0046 value: 55 20 6e 6f 20 77 61 6e 74 20 74 68 69 73 20 6d 73 67 00 00 
Notification handle = 0x0046 value: 63 39 34 35 37 64 65 35 66 64 38 63 61 66 65 33 34 39 66 64 
Notification handle = 0x0046 value: 63 39 34 35 37 64 65 35 66 64 38 63 61 66 65 33 34 39 66 64 
Notification handle = 0x0046 value: 63 39 34 35 37 64 65 35 66 64 38 63 61 66 65 33 34 39 66 64 
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;After the first notification, we get the content of the flag! (The decoded content of the first notification is &amp;ldquo;U no want this msg&amp;rdquo;).&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ decode &amp;quot;63 39 34 35 37 64 65 35 66 64 38 63 61 66 65 33 34 39 66 64&amp;quot;
c9457de5fd8cafe349fd
less@machine:~$ submit_flag c9457de5fd8cafe349fd
Characteristic value was written successfully
less@machine:~$ get_score 
Score:13/20 
&lt;/code&gt;&lt;/pre&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Flag 0x0048&lt;/strong&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;The content of the handle is: &amp;ldquo;Listen to handle 0x004a for multi indications&amp;rdquo;&lt;/p&gt;
&lt;p&gt;Properties: Read&lt;/p&gt;
&lt;p&gt;Handle 0x004a Properties: Read, Write, Indicate&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;Once again the same command is the key to the flag!&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ gatttool -b 78:21:84:80:A2:22 --char-write-req --handle=0x004a --value=ffff --listen
Characteristic value was written successfully
Indication   handle = 0x004a value: 55 20 6e 6f 20 77 61 6e 74 20 74 68 69 73 20 6d 73 67 00 00 
Indication   handle = 0x004a value: 62 36 66 33 61 34 37 66 32 30 37 64 33 38 65 31 36 66 66 61 
Indication   handle = 0x004a value: 62 36 66 33 61 34 37 66 32 30 37 64 33 38 65 31 36 66 66 61 
Indication   handle = 0x004a value: 62 36 66 33 61 34 37 66 32 30 37 64 33 38 65 31 36 66 66 61 
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Now we can decode and submit the flag like always.&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ decode &amp;quot;62 36 66 33 61 34 37 66 32 30 37 64 33 38 65 31 36 66 66 61&amp;quot;
b6f3a47f207d38e16ffa
less@machine:~$ submit_flag b6f3a47f207d38e16ffa
Characteristic value was written successfully
less@machine:~$ get_score 
Score:14/20 
&lt;/code&gt;&lt;/pre&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Flag 0x004c&lt;/strong&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;The content of the handle is: &amp;ldquo;Connect with BT MAC address 11:22:33:44:55:66&amp;rdquo;&lt;/p&gt;
&lt;p&gt;Properties: Read&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;Now, this challenge depends on the BT card you&amp;rsquo;re using. I&amp;rsquo;m using a raspberry pi 3b+ and I could solve the challenge in the following way:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ sudo hcitool cmd 0x3f 0x001 0x66 0x55 0x44 0x33 0x22 0x11
&amp;lt; HCI Command: ogf 0x3f, ocf 0x0001, plen 6
  66 55 44 33 22 11 
&amp;gt; HCI Event: 0x0e plen 4
  01 01 FC 00 
less@machine:~$ sudo hciconfig hci0 reset
less@machine:~$ systemctl restart bluetooth.service
Authentication is required to restart &#39;bluetooth.service&#39;.
Authenticating as: ,,, (less)
Password: 
==== AUTHENTICATION COMPLETE ===
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;At this point we can confirm our BT MAC address executing &lt;code&gt;hciconfig&lt;/code&gt;:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ hciconfig
hci0:	Type: Primary  Bus: UART
	BD Address: 11:22:33:44:55:66  ACL MTU: 1021:8  SCO MTU: 64:1
	UP RUNNING 
	RX bytes:13820 acl:117 sco:0 events:824 errors:0
	TX bytes:16604 acl:108 sco:0 commands:606 errors:0
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;And of course now, reading the handle gives us the flag:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ read_hnd 0x004c
aca16920583e42bdcf5f
less@machine:~$ submit_flag aca16920583e42bdcf5f
Characteristic value was written successfully
less@machine:~$ get_score 
Score:15/20
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Check out these resources for more info on this solution:
&lt;a href=&#34;https://www.lisha.ufsc.br/teaching/shi/ine5346-2003-1/work/bluetooth/hci_commands.html&#34;&gt;https://www.lisha.ufsc.br/teaching/shi/ine5346-2003-1/work/bluetooth/hci_commands.html&lt;/a&gt; and &lt;a href=&#34;https://raspberrypi.stackexchange.com/a/124117&#34;&gt;https://raspberrypi.stackexchange.com/a/124117&lt;/a&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Flag 0x004e&lt;/strong&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;The content of the handle is: &amp;ldquo;Set your connection MTU to 444&amp;rdquo;&lt;/p&gt;
&lt;p&gt;Properties: Read&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;Even if there is the option to do that (-m), I can&amp;rsquo;t seem to get the flag without using the interactive mode of gatttools, so my solution to this flag is:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ gatttool -I
[                 ][LE]&amp;gt; connect 78:21:84:80:A2:22
Attempting to connect to 78:21:84:80:A2:22
Connection successful
[78:21:84:80:A2:22][LE]&amp;gt; mtu 444
MTU was exchanged successfully: 444
[78:21:84:80:A2:22][LE]&amp;gt; char-read-hnd 0x004e
Characteristic value/descriptor: 62 31 65 34 30 39 65 35 61 34 65 61 66 39 66 65 35 31 35 38 
[78:21:84:80:A2:22][LE]&amp;gt; exit
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;And just like that we got the flag&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ decode &amp;quot;62 31 65 34 30 39 65 35 61 34 65 61 66 39 66 65 35 31 35 38 &amp;quot;
b1e409e5a4eaf9fe5158
less@machine:~$ submit_flag b1e409e5a4eaf9fe5158
Characteristic value was written successfully
less@machine:~$ get_score 
Score:16/20
&lt;/code&gt;&lt;/pre&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Flag 0x0050&lt;/strong&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;The content of the handle is: &amp;ldquo;Write+resp &amp;lsquo;hello&amp;rsquo; &amp;quot;&lt;/p&gt;
&lt;p&gt;Properties: Read, Write&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;I suggest checking the hint for this challenge! The key is in correctly handling the ACK response from the write instruction, this is the reason&lt;/p&gt;
&lt;p&gt;&lt;code&gt;--char-write-req&lt;/code&gt; needs to be used.&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ gatttool -b 78:21:84:80:A2:22 --char-write-req --handle=0x0050 --value=`encode hello`
Characteristic value was written successfully
less@machine:~$ read_hnd 0x0050
d41d8cd98f00b204e980
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Now we only need to submit the flag.&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ submit_flag d41d8cd98f00b204e980
Characteristic value was written successfully
less@machine:~$ get_score 
Score:17/20
&lt;/code&gt;&lt;/pre&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Flag 0x0052&lt;/strong&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;The content of the handle is: &amp;ldquo;No notifications here! really?&amp;rdquo;&lt;/p&gt;
&lt;p&gt;Properties: Read, Write&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;In fact even if there is no notification property set&amp;hellip;&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ gatttool -b 78:21:84:80:A2:22 --char-write-req --handle=0x0052 --value=`encode hello` --listen
Characteristic value was written successfully
Notification handle = 0x0052 value: 66 63 39 32 30 63 36 38 62 36 30 30 36 31 36 39 34 37 37 62 
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;The flag is revealed through a notification!
Now we can decode and submit it.&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ decode &amp;quot;66 63 39 32 30 63 36 38 62 36 30 30 36 31 36 39 34 37 37 62&amp;quot;
fc920c68b6006169477b
less@machine:~$ submit_flag fc920c68b6006169477b
Characteristic value was written successfully
less@machine:~$ get_score 
Score:18/20
&lt;/code&gt;&lt;/pre&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Flag 0x0054&lt;/strong&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;The content of the handle is: &amp;ldquo;So many properties!&amp;rdquo;&lt;/p&gt;
&lt;p&gt;Properties: Broadcast, Read, Write, Notify, Extended properties&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;&amp;hellip;and to be fair this handle has &amp;ldquo;Broadcast, Read, Write, Notify, Extended properties&amp;rdquo; properties. It&amp;rsquo;s a bit of a mess!&lt;/p&gt;
&lt;p&gt;But getting the flag is fairly simple. The first half can be retrieved simply listening for a notification:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ gatttool -b 78:21:84:80:A2:22 --char-write-req --handle=0x0054 --value=ffff --listen
Characteristic value was written successfully
Notification handle = 0x0054 value: 30 37 65 34 61 30 63 63 34 38 
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;For the second half we need to read the handle once more:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ read_hnd 0x0054
fbb966958f
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Now we just need to put the two halves together and submit the flag (the second half of the flag goes first!):&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ submit_flag fbb966958f07e4a0cc48
Characteristic value was written successfully
less@machine:~$ get_score 
Score:19/20
&lt;/code&gt;&lt;/pre&gt;&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;Flag 0x0056&lt;/strong&gt;&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;The content of the handle is: &amp;ldquo;md5 of author&amp;rsquo;s twitter handle&amp;rdquo;.&lt;/p&gt;
&lt;p&gt;Properties: Read&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;So we need to do a bit of OSINT to solve this challenge!&lt;/p&gt;
&lt;p&gt;The starting point is the github page of the challenge: &lt;a href=&#34;https://github.com/hackgnar/ble_ctf&#34;&gt;https://github.com/hackgnar/ble_ctf&lt;/a&gt;
Luckily in the README.md file we can find a twitter follow button, this leads us to: &lt;a href=&#34;https://twitter.com/hackgnar&#34;&gt;https://twitter.com/hackgnar&lt;/a&gt;
And now we know the handle is: @hackgnar&lt;/p&gt;
&lt;p&gt;Now we can get the MD5 digest of the handle and cut it to 20 chars:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ echo -n &amp;quot;@hackgnar&amp;quot; | md5sum | cut -c 1-20
d953bfb9846acc2e15ee
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;We can now submit it as a flag&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;less@machine:~$ submit_flag d953bfb9846acc2e15ee
Characteristic value was written successfully
less@machine:~$ get_score 
Score:20/20
&lt;/code&gt;&lt;/pre&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;hr&gt;
&lt;h2 id=&#34;conclusions&#34;&gt;Conclusions&lt;/h2&gt;
&lt;p&gt;Hope this article is useful to anyone who&amp;rsquo;s stuck on one of these challenges or to anyone who&amp;rsquo;s trying to learn about BLE technologies.
Writing this article has helped me formalizing most of the things I learned solving these challenges and my main takeaways are an improved understanding of BLE, GATT and ATT, but also the ability to use the tools needed to work with these technologies.&lt;/p&gt;
&lt;p&gt;In future I&amp;rsquo;ll try working with GATT libraries to programmatically interact with GATT servers!&lt;/p&gt;
&lt;hr&gt;
&lt;p&gt;Resources:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://epxx.co/artigos/bluetooth_gatt.html&#34;&gt;https://epxx.co/artigos/bluetooth_gatt.html&lt;/a&gt; (ATT/GATT basics)&lt;/li&gt;
&lt;li&gt;Practical IoT Hacking: The Definitive Guide to Attacking the Internet of Things (General BLE introduction)&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://axodyne.com/2020/08/ble-uuids/&#34;&gt;https://axodyne.com/2020/08/ble-uuids/&lt;/a&gt;  (Explanation on standard UUIDS)&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://learn.adafruit.com/introduction-to-bluetooth-low-energy/gatt&#34;&gt;https://learn.adafruit.com/introduction-to-bluetooth-low-energy/gatt&lt;/a&gt; (Profiles and services)&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://devzone.nordicsemi.com/guides/short-range-guides/b/bluetooth-low-energy/posts/ble-characteristics-a-beginners-tutorial&#34;&gt;https://devzone.nordicsemi.com/guides/short-range-guides/b/bluetooth-low-energy/posts/ble-characteristics-a-beginners-tutorial&lt;/a&gt; (Properties)&lt;/li&gt;
&lt;/ul&gt;
</content:encoded>

      </item><item>
        <title>Email spoofing 101</title>
        <link>https://lessonsec.com/posts/email-spoofing-101/</link>
        <guid isPermaLink="true">https://lessonsec.com/posts/email-spoofing-101/</guid>
        <pubDate>Sat, 05 Feb 2022 16:40:50 &#43;0100</pubDate><description>Email spoofing is a technique mostly linked to malicious activities including phishing and spamming. From a formal(ish) standpoint, email spoofing is the act of sending an email with a forged sender address.</description>
	<content:encoded>&lt;p&gt;Email spoofing is a technique mostly linked to malicious activities including phishing and spamming.
From a formal(ish) standpoint, email spoofing is the act of sending an email with a forged sender address.&lt;/p&gt;
&lt;p&gt;I got interested in this technique in the last few days, so I decided to experiment a bit with it.&lt;/p&gt;
&lt;h2 id=&#34;email-spoofing-basics&#34;&gt;Email spoofing basics&lt;/h2&gt;
&lt;p&gt;This technique is as old as emails are, in fact original transmission protocols (such as SMTP) don&amp;rsquo;t have authentication methods, and while security measures have been adopted these are &lt;a href=&#34;https://labs.bishopfox.com/tech-blog/2017/05/how-we-can-stop-email-spoofing&#34;&gt;not widely employed yet&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;An email is composed of three different parts:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;Envelope&lt;/strong&gt;: data about sender and receiver addresses.
This part of message is destined to the server, it&amp;rsquo;s generally not shown to the user by the client.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Header&lt;/strong&gt;: meta-data of the email. Contains information like the subject of the email, the date and some info about sending/receiving addresses.&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;Body&lt;/strong&gt;: the content of the email.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;To get a bit more into details, the SMTP protocol specify two addresses in the envelope addressing part of the message:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;MAIL FROM&lt;/code&gt;: it specifies the &amp;ldquo;return address&amp;rdquo; in case an email bounces.&lt;/li&gt;
&lt;li&gt;&lt;code&gt;RCPT TO&lt;/code&gt;: address to which the email will be delivered.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Other headers are often present, this set of information represent what the receiver will see when reading the email inside of a client.
The addresses in each header will be present in the form of: &lt;code&gt;Foo Bar &amp;lt;foobar@spam.com&amp;gt;&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;In particular, these headers are: &lt;code&gt;From:&lt;/code&gt;, &lt;code&gt;Reply-to:&lt;/code&gt;, &lt;code&gt;Sender:&lt;/code&gt;. Each of these headers represents the address visible to the receiving part.&lt;/p&gt;
&lt;p&gt;In general, it&amp;rsquo;s important to notice the difference between the envelope &lt;code&gt;MAIL FROM&lt;/code&gt; or &lt;a href=&#34;https://datatracker.ietf.org/doc/html/rfc5321&#34;&gt;RFC5321&lt;/a&gt;.MailFrom and the header &lt;code&gt;From:&lt;/code&gt;or &lt;a href=&#34;https://datatracker.ietf.org/doc/html/rfc5322&#34;&gt;RFC5322&lt;/a&gt;.From since the latter is shown to the user and can be easily spoofed and it&amp;rsquo;s shown to the recipient of the email by the client.&lt;/p&gt;
&lt;p&gt;As anticipated, SMTP doesn&amp;rsquo;t check whether an user is authorized or not to use a particular address in these fields and this is the reason why it&amp;rsquo;s so easy to spoof emails. The only reliable information we can harvest from a spoofed email is the IP from which the email was sent.&lt;/p&gt;
&lt;h2 id=&#34;available-security-measures&#34;&gt;Available security measures&lt;/h2&gt;
&lt;p&gt;There are three main security measured against email spoofing:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;&lt;a href=&#34;https://datatracker.ietf.org/doc/html/rfc7208&#34;&gt;Sender Policy Framework&lt;/a&gt; (SPF)&lt;/strong&gt;
This method allows the detection of forged sender addresses and it&amp;rsquo;s based on envelope information.
In particular SPF information are contained inside a &lt;code&gt;TXT&lt;/code&gt; DNS record. These info specify which IP addresses are allowed to send emails on the behalf of the  domain. Allowed senders can be listed explicitly specifying authorized IP ranges, or checking if &lt;code&gt;A&lt;/code&gt;, &lt;code&gt;AAAA&lt;/code&gt; or &lt;code&gt;MX&lt;/code&gt; records resolve to the sender&amp;rsquo;s address.&lt;/p&gt;
&lt;p&gt;SPF also use 4 qualifiers, these represent the status of the SPF validation.
Qualifiers can be:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;PASS (+) : if the check is passed. The email can be accepted.&lt;/li&gt;
&lt;li&gt;NEUTRAL (?) : if no policy is in use.&lt;/li&gt;
&lt;li&gt;FAIL (-) : if the check wasn&amp;rsquo;t successful. The email should be rejected.&lt;/li&gt;
&lt;li&gt;SOFTFAIL (~) : like fail, but used for debugging. In general emails with SOFTFAIL qualifier are accepted but flagged.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;The SPF &lt;code&gt;TXT&lt;/code&gt; DNS record is composed of SPF version (specified with the tag &lt;code&gt;v=&lt;/code&gt; &lt;a href=&#34;http://www.open-spf.org/SPF_vs_Sender_ID/#0.1.3&#34;&gt;it can only be followed by the value &lt;code&gt;spf1&lt;/code&gt;&lt;/a&gt;) and one of more &lt;em&gt;mechanisms&lt;/em&gt;.
Mechanisms are used to specify if a domain can send the email. Mechanisms include specifying IPv4/IPv6 address ranges or checking if A, MX or PTR records resolve to the domain. Other mechanisms exist but are rarely used.&lt;/p&gt;
&lt;p&gt;SPF alone is not enough to detect email forging because it checks envelope information only, it would still be possible to keep the original sender in the envelope information and forge only the headers that are interpreted by the client and can&amp;rsquo;t be checked with SPF.
Usually a failed SPF check is enough to mark the email as spam or even reject it.
It&amp;rsquo;s worth noting that SPF policies could cause troubles in case of email forwarding even if the sender is authorized. That&amp;rsquo;s because the &amp;ldquo;forwarder&amp;rdquo; is technically not authorized to send emails on the behalf the original domain.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;&lt;a href=&#34;https://datatracker.ietf.org/doc/html/rfc6376/&#34;&gt;DomainKeys Identified Mail&lt;/a&gt; (DKIM)&lt;/strong&gt;
DKIM is an authentication method that allows the receiver to check if the email was authorized by the owner of the domain and functions as an integrity check to make sure the message hasn&amp;rsquo;t been modified.
This check is possible thanks to an additional header containing a digital signature. A public key, that makes the signature validation possible, is available in a dedicated &lt;code&gt;TXT&lt;/code&gt; DNS record. This method only checks the validity of email&amp;rsquo;s header and body, the envelope addresses are ignored. It&amp;rsquo;s possible to specify which headers to check, but the &lt;code&gt;RFC5322.From&lt;/code&gt; header must always be checked.
DKIM checks can and should be done at every SMTP hop and should resist relaying across &lt;a href=&#34;https://en.wikipedia.org/wiki/Message_transfer_agent&#34;&gt;MTAs&lt;/a&gt; .&lt;/p&gt;
&lt;p&gt;Important info contained in the DKIM headers of an email are:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;b&lt;/code&gt;: signature of header and body&lt;/li&gt;
&lt;li&gt;&lt;code&gt;bh&lt;/code&gt;: body hash&lt;/li&gt;
&lt;li&gt;&lt;code&gt;d&lt;/code&gt;: signing domain&lt;/li&gt;
&lt;li&gt;&lt;code&gt;s&lt;/code&gt;: selector&lt;/li&gt;
&lt;li&gt;&lt;code&gt;h&lt;/code&gt;: header fields that has been signed&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;But information about the protocol, the algorithm used to sign and more can be present in optional tags.&lt;/p&gt;
&lt;p&gt;The information useful to verify the signature are present in the &lt;code&gt;TXT&lt;/code&gt; DNS record and are presented in the form of key-value pairs:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;k&lt;/code&gt;: algorithm to be used&lt;/li&gt;
&lt;li&gt;&lt;code&gt;v&lt;/code&gt;: version of DKIM&lt;/li&gt;
&lt;li&gt;&lt;code&gt;p&lt;/code&gt;: public key to validate the signature&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;More tags can be present, but are not useful for our analysis.&lt;/p&gt;
&lt;p&gt;DKIM records are published at &lt;code&gt;selector._domainkey.example.com&lt;/code&gt;.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;strong&gt;&lt;a href=&#34;https://datatracker.ietf.org/doc/html/rfc7489&#34;&gt;Domain-based Message Authentication, Reporting and Conformance&lt;/a&gt; (DMARC)&lt;/strong&gt;
DMARC is an email authentication protocol. Using a &lt;code&gt;TXT&lt;/code&gt; DNS record, it dictates the conditions under which an email is considered authenticated.
It works on top of DKIM and SPF: these two mechanisms, as shown above, offer different checks on the authenticity of an email sender.&lt;br&gt;
Both DKIM and SPF can offer authenticated identifiers in DMARC, meaning that DKIM &lt;code&gt;d=&lt;/code&gt; tag of a validated DKIM-Signature header field and SPF validated &lt;code&gt;MAIL FROM&lt;/code&gt; field can be used to validate an email&amp;rsquo;s sender.&lt;/p&gt;
&lt;p&gt;DMARC alignment basically checks that the domain name in the &lt;code&gt;RFC5322.From&lt;/code&gt; field, is &amp;ldquo;aligned&amp;rdquo; (matches) with either DKIM or SPF authenticated identifier.
There are two types of alignment in DMARC, &lt;em&gt;strict&lt;/em&gt; or &lt;em&gt;relaxed&lt;/em&gt;.
With strict alignment, the domain needs to be identical, while with relaxed alignment, a domain is considered aligned if the top-level domain match.&lt;/p&gt;
&lt;p&gt;It&amp;rsquo;s also possible to define policies to specify how to deal with authentication failures.
These policies are:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;none&lt;/code&gt;: no action required by the receivers. It allows the domain to receive feedback reports.&lt;/li&gt;
&lt;li&gt;&lt;code&gt;quarantine&lt;/code&gt;: suggests that emails that fail DMARC check are flagged (marked as spam).&lt;/li&gt;
&lt;li&gt;&lt;code&gt;reject&lt;/code&gt;: suggests that emails that fail DMARC check are discarded.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;A &lt;code&gt;TXT&lt;/code&gt; DNS entry for DMARC is composed of:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;v&lt;/code&gt;: version&lt;/li&gt;
&lt;li&gt;&lt;code&gt;p&lt;/code&gt;: policy&lt;/li&gt;
&lt;li&gt;&lt;code&gt;sp&lt;/code&gt;: sub-domain policy&lt;/li&gt;
&lt;li&gt;&lt;code&gt;pct&lt;/code&gt;: percentage of non authenticated emails to which apply the policy&lt;/li&gt;
&lt;li&gt;&lt;code&gt;rua&lt;/code&gt;: email address to send reports to&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;The use of &lt;code&gt;pct&lt;/code&gt; is interesting because it can lower the protection offered by DMARC.
By default &lt;code&gt;pct&lt;/code&gt; is set to 100%, but if it wasn&amp;rsquo;t, the receiver should use a Bernoulli sampling algorithm to check how the policy is to be applied to the email.
If an email doesn&amp;rsquo;t fall under the percentage specified in &lt;code&gt;pct&lt;/code&gt;, a lower policy is to be applied to the email.
So if &lt;code&gt;p=reject&lt;/code&gt;, the quarantine policy is to be used and if &lt;code&gt;p=quarantine&lt;/code&gt;, the &lt;code&gt;none&lt;/code&gt; policy is to be applied.&lt;/p&gt;
&lt;p&gt;DMARC records are published at &lt;code&gt;_dmarc.example.com&lt;/code&gt;.&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;While SPF and DKIM work properly, they both have defects:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;SPF checks the envelope from address, leaving the header from address not considered.
This means that a malicious user can send an email from a whitelisted domain and spoof the header from address. This can lead to a situation in which the email is considered valid, but a domain different than the expected one is shown to the receiver.&lt;/li&gt;
&lt;li&gt;DKIM only checks parts of the email, this means that, leaving such parts untouched, a malicious user can &lt;a href=&#34;https://www.zdnet.com/article/dkim-useless-or-just-disappointing/&#34;&gt;add other headers&lt;/a&gt; and make the receiving part see an apparently valid message, but with spoofed parts.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;This leaves DMARC as the only viable solution for a more comprehensive domain security.&lt;/p&gt;
&lt;h2 id=&#34;vulnerable-configurations&#34;&gt;Vulnerable configurations&lt;/h2&gt;
&lt;p&gt;When it comes to email security implemented with DMARC, there are 4 main vulnerable scenarios to consider:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Case 1&lt;br&gt;
There is a DMARC DNS record, this entry describes a DMARC entry and it has a policy different than &amp;ldquo;none&amp;rdquo;.
In this case it&amp;rsquo;s impossible to spoof an email from this domain.&lt;/li&gt;
&lt;li&gt;Case 2&lt;br&gt;
There is a DMARC DNS record and a valid DMARC entry, but the policy is set to &amp;ldquo;none&amp;rdquo;, meaning that, even if feedback reports will be sent, the domain is spoofable in emails.&lt;/li&gt;
&lt;li&gt;Case 3&lt;br&gt;
There is no DMARC DNS record in a domain that is used to send emails. This is the worst possible scenario because the domain is completely unprotected.&lt;/li&gt;
&lt;li&gt;Case 4&lt;br&gt;
There is no DMARC DNS record in a domain not used to send emails. The domain is spoofable, but the impact is not as big as in case 3.
It is suggested to have DMARC in place even for domain not used to send emails, but it&amp;rsquo;s not fundamental.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Of course to thoroughly evaluate the security in place, it&amp;rsquo;s important to consider eventual SPF and DKIM policies, even if no DMARC protection is set up.&lt;/p&gt;
&lt;p&gt;The most direct way to check the configuration is to query the DNS, for this article I&amp;rsquo;ll specify the way to do this in a unix based system, but more info can be found &lt;a href=&#34;https://www.cisco.com/c/en/us/support/docs/security/secure-email-gateway/217073-how-to-use-dig-nslookup-to-find-spf-dki.html&#34;&gt;here&lt;/a&gt;. We will use google.com as a domain for our experiments.&lt;/p&gt;
&lt;h3 id=&#34;find-the-spf-record&#34;&gt;Find the SPF record&lt;/h3&gt;
&lt;p&gt;Using &lt;code&gt;dig&lt;/code&gt; it&amp;rsquo;s possible to get &lt;code&gt;TXT&lt;/code&gt; records for a domain.
The command is &lt;code&gt;dig google.com txt&lt;/code&gt; and the output looks like this:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;; &amp;lt;&amp;lt;&amp;gt;&amp;gt; DiG 9.16.8-Ubuntu &amp;lt;&amp;lt;&amp;gt;&amp;gt; google.com txt
;; global options: +cmd
;; Got answer:
;; -&amp;gt;&amp;gt;HEADER&amp;lt;&amp;lt;- opcode: QUERY, status: NOERROR, id: 8353
;; flags: qr rd ra; QUERY: 1, ANSWER: 9, AUTHORITY: 0, ADDITIONAL: 1

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 65494
;; QUESTION SECTION:
;google.com.			IN	TXT

;; ANSWER SECTION:
google.com.		3600	IN	TXT	&amp;quot;MS=E4A68B9AB2BB9670BCE15412F62916164C0B20BB&amp;quot;
google.com.		3600	IN	TXT	&amp;quot;v=spf1 include:_spf.google.com ~all&amp;quot;
google.com.		3600	IN	TXT	&amp;quot;google-site-verification=wD8N7i1JTNTkezJ49swvWW48f8_9xveREV4oB-0Hf5o&amp;quot;
google.com.		3600	IN	TXT	&amp;quot;google-site-verification=TV9-DBe4R80X4v0M4U_bd_J9cpOJM0nikft0jAgjmsQ&amp;quot;
google.com.		3600	IN	TXT	&amp;quot;apple-domain-verification=30afIBcvSuDV2PLX&amp;quot;
google.com.		3600	IN	TXT	&amp;quot;docusign=05958488-4752-4ef2-95eb-aa7ba8a3bd0e&amp;quot;
google.com.		3600	IN	TXT	&amp;quot;globalsign-smime-dv=CDYX+XFHUw2wml6/Gb8+59BsH31KzUr6c1l2BPvqKX8=&amp;quot;
google.com.		3600	IN	TXT	&amp;quot;facebook-domain-verification=22rm551cu4k0ab0bxsw536tlds4h95&amp;quot;
google.com.		3600	IN	TXT	&amp;quot;docusign=1b0a6754-49b1-4db5-8540-d2c12664b289&amp;quot;

;; Query time: 328 msec
;; SERVER: 127.0.0.53#53(127.0.0.53)
;; WHEN: Tue Nov 23 22:29:59 CET 2021
;; MSG SIZE  rcvd: 625
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;then we need to find the SPF record between &lt;code&gt;TXT&lt;/code&gt; records. We simply need to find the one starting with &lt;code&gt;v=spf&lt;/code&gt;, in this case it is
&lt;code&gt;google.com.  3600	IN	TXT	&amp;quot;v=spf1 include:_spf.google.com ~all&amp;quot;&lt;/code&gt;. Or we can use &lt;code&gt;grep&lt;/code&gt; to extract the information directly:
&lt;code&gt;dig google.com txt | grep spf&lt;/code&gt;.&lt;/p&gt;
&lt;h3 id=&#34;find-the-dkim-record&#34;&gt;Find the DKIM record&lt;/h3&gt;
&lt;p&gt;The DKIM entry is located at &lt;code&gt;selector._domainkey.example.com&lt;/code&gt;, so to find the DKIM record we first need to find the DKIM selector.
This can be done in two ways, get it from an email received from the domain we are researching or trying to achieve a zone transfer.&lt;/p&gt;
&lt;p&gt;From an email, we just need to look for the original message (containing the headers), if DKIM is enabled, one of the fields will be &lt;code&gt;DKIM-Signature:&lt;/code&gt; followed by different elements; what we are looking for is &lt;code&gt;s=&lt;/code&gt; that is followed by the selector.
If we can&amp;rsquo;t receive an email from a specific domain, it&amp;rsquo;s possible to try and get a zone transfer, it&amp;rsquo;s basically a dump of every DNS record from a nameserver.
This can be done with the command: &lt;code&gt;dig axfr @nameserver example.com&lt;/code&gt;.  The nameservers can be found using the command &lt;code&gt;dig ns example.com&lt;/code&gt;.
Sadly google.com won&amp;rsquo;t allow zone transfer. It&amp;rsquo;s possible to practice this technique using &lt;a href=&#34;https://digi.ninja/projects/zonetransferme.php&#34;&gt;zonetransfer.me&lt;/a&gt;, this website also contains a lot of cool info about DNS and zone transfers.&lt;/p&gt;
&lt;p&gt;I was able to recover the selector from an email received from google.com. Once we have the selector, we can get info about DKIM using the command:
&lt;code&gt;dig 20210112._domainkey.google.com txt&lt;/code&gt;.
The output looks like this:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;; &amp;lt;&amp;lt;&amp;gt;&amp;gt; DiG 9.16.8-Ubuntu &amp;lt;&amp;lt;&amp;gt;&amp;gt; 20210112._domainkey.google.com txt
;; global options: +cmd
;; Got answer:
;; -&amp;gt;&amp;gt;HEADER&amp;lt;&amp;lt;- opcode: QUERY, status: NOERROR, id: 52118
;; flags: qr rd ra; QUERY: 1, ANSWER: 1, AUTHORITY: 0, ADDITIONAL: 1

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 65494
;; QUESTION SECTION:
;20210112._domainkey.google.com.	IN	TXT

;; ANSWER SECTION:
20210112._domainkey.google.com.	3600 IN	TXT	&amp;quot;v=DKIM1; k=rsa; p=MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAtnbQAeqvEP2pG2L540W9JvVU7qy767Zs83Hjw34PCkZ9/9dWE6cK+CYaMNIQqTGfwq4uUe3diBuz3Uikkr+WPMj9AuxtxJqUAO8PsZ2Y5DneFpz5kVesC9/rtXgCwgYOmO&amp;quot; &amp;quot;9UjSy4IN11ewXUBuCH+zp2v5Abv5T0Lol/nWl8wLgRI1IesstingY4cnSfo3Pq3U0I1GAxdNFCK2FPedPpg4sdPpHqtxVvRLMLamRKoUfySBMjpXuMNL0UeCizmFfdUL73ZdiS+MNxGECzFNmeCngFBscLQN++urvfB9OqHQrbxLIwNyni3KMbE/E+cxPkx4KxhyGHSU2klV1vvIAHfwIDAQAB&amp;quot;

;; Query time: 92 msec
;; SERVER: 127.0.0.53#53(127.0.0.53)
;; WHEN: Tue Nov 23 22:23:32 CET 2021
;; MSG SIZE  rcvd: 483
&lt;/code&gt;&lt;/pre&gt;&lt;h3 id=&#34;find-the-dmarc-record&#34;&gt;Find the DMARC record&lt;/h3&gt;
&lt;p&gt;The DMARC record is easy to find, just for the SPF record, we can use &lt;code&gt;dig _dmarc.google.com txt&lt;/code&gt; to get what we are looking for.&lt;/p&gt;
&lt;p&gt;The output is:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;; &amp;lt;&amp;lt;&amp;gt;&amp;gt; DiG 9.16.8-Ubuntu &amp;lt;&amp;lt;&amp;gt;&amp;gt; _dmarc.google.com txt
;; global options: +cmd
;; Got answer:
;; -&amp;gt;&amp;gt;HEADER&amp;lt;&amp;lt;- opcode: QUERY, status: NOERROR, id: 28825
;; flags: qr rd ra; QUERY: 1, ANSWER: 1, AUTHORITY: 0, ADDITIONAL: 1

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 65494
;; QUESTION SECTION:
;_dmarc.google.com.		IN	TXT

;; ANSWER SECTION:
_dmarc.google.com.	300	IN	TXT	&amp;quot;v=DMARC1; p=reject; rua=mailto:mailauth-reports@google.com&amp;quot;

;; Query time: 44 msec
;; SERVER: 127.0.0.53#53(127.0.0.53)
;; WHEN: Tue Nov 23 22:29:14 CET 2021
;; MSG SIZE  rcvd: 117
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Another way to find these information is to use online tools like &lt;a href=&#34;https://mxtoolbox.com/SuperTool.aspx?action=mx%3alessonsec.com&amp;amp;run=toolpage#&#34;&gt;this&lt;/a&gt;, but I think that it&amp;rsquo;s better to query the DNS server manually to better understand how these things work.&lt;/p&gt;
&lt;h2 id=&#34;actually-spoofing-an-email&#34;&gt;Actually spoofing an email&lt;/h2&gt;
&lt;p&gt;Now that we have an overview of email security, we can go ahead and try to actually spoof an email.&lt;/p&gt;
&lt;p&gt;Now, if you tried sending an email via code in past, you know for sure that it&amp;rsquo;s really hard to avoid ending up in the spam folder, even if you are trying to send an email from a legitimate domain and you are authorized. Said that, let&amp;rsquo;s go through some experiments I made and examine how feasible it really is to send spoofed emails from scratches.&lt;/p&gt;
&lt;p&gt;Anyway, let&amp;rsquo;s dive into it.&lt;/p&gt;
&lt;p&gt;First of we need to setup a vulnerable server or try to find a vulnerable domain administrator that will allow you to spoof their domain name. Luckily using bug bounty programs it&amp;rsquo;s easy to find vulnerable domains you&amp;rsquo;re allowed to work with.&lt;/p&gt;
&lt;p&gt;Now, if you are familiar on the &amp;ldquo;raw&amp;rdquo; email format, you&amp;rsquo;ll know that the email is nothing but a text composed of headers-values and the content of the email. For this reason it&amp;rsquo;s possible to &amp;ldquo;spoof&amp;rdquo; headers like &lt;code&gt;From&lt;/code&gt;, &lt;code&gt;Reply-to&lt;/code&gt;, &lt;code&gt;Sender&lt;/code&gt;.&lt;/p&gt;
&lt;h3 id=&#34;first-attempt-using-gmail-smtp-server&#34;&gt;First attempt: using Gmail SMTP server&lt;/h3&gt;
&lt;p&gt;I tried using my gmail account to send an email using google servers.
To do that I had to enable access from less secure apps on my account. This is the only way to login into a google service from code you write.&lt;/p&gt;
&lt;p&gt;Now, it&amp;rsquo;s not possible to specify envelope information, but it&amp;rsquo;s possible to send the email and specify the &lt;code&gt;From:&lt;/code&gt;, &lt;code&gt;Reply-to:&lt;/code&gt; and &lt;code&gt;Sender:&lt;/code&gt; headers.
Using the &lt;code&gt;From:&lt;/code&gt; field, I was able to change the sender name, but the email displayed by the client would be the one from the account used to login into gmail. If no &lt;code&gt;From:&lt;/code&gt; header was specified, the header will be inferred by gmail servers and the email address (without the domain) will be used. Specifying the &lt;code&gt;Sender:&lt;/code&gt; header didn&amp;rsquo;t do much, if it was simply ignored, both with or without the &lt;code&gt;From:&lt;/code&gt; header.
The &lt;code&gt;Reply-to:&lt;/code&gt; header was interpreted just like Sender:, but if specified, emails would be marked as &amp;ldquo;promotions&amp;rdquo; by gmail&amp;rsquo;s client.&lt;/p&gt;
&lt;p&gt;Using different SMTP servers or clients will possibly lead to different results.&lt;/p&gt;
&lt;p&gt;This is the code snippet used for this experiment:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; style=&#34;color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-python&#34; data-lang=&#34;python&#34;&gt;&lt;span style=&#34;color:#f92672&#34;&gt;import&lt;/span&gt; smtplib

gmail_user &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#39;YOUR-EMAIL-HERE@gmail.com&amp;#39;&lt;/span&gt;
gmail_password &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#39;YOUR-PASSWORD-HERE&amp;#39;&lt;/span&gt;

sent_from_name &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;Foo&amp;#34;&lt;/span&gt;
sent_from &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#39;foobar@spam.com&amp;#39;&lt;/span&gt;
to &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#39;receiver@email.com&amp;#39;&lt;/span&gt;
subject &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#39;This is a spoofed email&amp;#39;&lt;/span&gt;
body &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;This is the content of a spoofed email&amp;#34;&lt;/span&gt;


email_text &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;f&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;&amp;#34;&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#ae81ff&#34;&gt;\
&lt;/span&gt;&lt;span style=&#34;color:#ae81ff&#34;&gt;&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;MIME-Version: 1.0
&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;Date: Thu, 29 Apr 2021 18:49:13 +0200
&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;Subject: &lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;{&lt;/span&gt;subject&lt;span style=&#34;color:#e6db74&#34;&gt;}&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;
&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;From: &lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;{&lt;/span&gt;sent_from_name&lt;span style=&#34;color:#e6db74&#34;&gt;}&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt; &amp;lt;&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;{&lt;/span&gt;sent_from&lt;span style=&#34;color:#e6db74&#34;&gt;}&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;gt;
&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;To: &lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;{&lt;/span&gt;to&lt;span style=&#34;color:#e6db74&#34;&gt;}&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;
&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;
&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;{&lt;/span&gt;body&lt;span style=&#34;color:#e6db74&#34;&gt;}&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;
&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;&amp;#34;&amp;#34;&lt;/span&gt;

&lt;span style=&#34;color:#66d9ef&#34;&gt;try&lt;/span&gt;:
    server &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; smtplib&lt;span style=&#34;color:#f92672&#34;&gt;.&lt;/span&gt;SMTP_SSL(&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#39;smtp.gmail.com&amp;#39;&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;465&lt;/span&gt;)
    server&lt;span style=&#34;color:#f92672&#34;&gt;.&lt;/span&gt;ehlo()
    server&lt;span style=&#34;color:#f92672&#34;&gt;.&lt;/span&gt;login(gmail_user, gmail_password)
    server&lt;span style=&#34;color:#f92672&#34;&gt;.&lt;/span&gt;sendmail(sent_from, to, email_text)
    server&lt;span style=&#34;color:#f92672&#34;&gt;.&lt;/span&gt;close()

    print(&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;Email sent!&amp;#34;&lt;/span&gt;)
&lt;span style=&#34;color:#66d9ef&#34;&gt;except&lt;/span&gt; &lt;span style=&#34;color:#a6e22e&#34;&gt;Exception&lt;/span&gt; &lt;span style=&#34;color:#66d9ef&#34;&gt;as&lt;/span&gt; e:
    print(e)
    print(&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;Email not sent!&amp;#34;&lt;/span&gt;)
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;second-attempt-setting-up-your-personal-smtp-server&#34;&gt;Second attempt: setting up your personal SMTP server&lt;/h3&gt;
&lt;p&gt;Installing an SMTP server on your machine would make it possible to send emails from your computer using a script similar to the one used for google. Sadly this experiment won&amp;rsquo;t let you send emails, this is for different reasons: for starters the IP address from which the email is sent is from a residential IP range. This means that if your ISP doesn&amp;rsquo;t block the email (very possible), the receiving client will ignore the email because of the poor IP reputation.&lt;/p&gt;
&lt;p&gt;I think it&amp;rsquo;s possible to send emails using this technique if an AWS, GCP or Azure VM is used, this simply because the IP wouldn&amp;rsquo;t be from a residential range anymore. I didn&amp;rsquo;t try this yet, but I&amp;rsquo;m confident that emails would be at least delivered.&lt;/p&gt;
&lt;h3 id=&#34;third-attempt-using-online-services&#34;&gt;Third attempt: using online services&lt;/h3&gt;
&lt;p&gt;With this approach I was able to send spoofed emails! I&amp;rsquo;m not linking any of the services I tried using, but there are free or paid services that actually work and let you specify the headers we are interested into.&lt;/p&gt;
&lt;p&gt;Sadly most of the emails will end up in the spam folder or discarded by the client due to bad IP reputation (I think).
But it&amp;rsquo;s a fun experiment to see how the emails are treated. Using a client with less protections (like online temporary email addresses ones) will allow the reception of the email.&lt;/p&gt;
&lt;h2 id=&#34;conclusions&#34;&gt;Conclusions&lt;/h2&gt;
&lt;p&gt;I think that the main take-away from this article should be an increased awareness about email security, mainly because of a deeper understanding of spoofing techniques.  For me personally, experimenting and researching on this topic was useful because I could work with DNS queries and gather insights about DNS security, a topic I&amp;rsquo;d love to further explore.&lt;/p&gt;
&lt;p&gt;Sadly I couldn&amp;rsquo;t experiment much at the moment, but I will for sure try and send emails from a VPS or Virtual Machine in the cloud that use a non-residential IP, I&amp;rsquo;m confident this approach would work in sending spoofed emails on vulnerable domains.&lt;/p&gt;
&lt;hr&gt;
&lt;p&gt;This article was reviewed by Nicola Selenu from &lt;a href=&#34;http://topdeliverability.com&#34;&gt;topdeliverability.com&lt;/a&gt;, big thanks to him!&lt;/p&gt;
</content:encoded>

      </item><item>
        <title>Walkthrough: CryptoHack CTF</title>
        <link>https://lessonsec.com/posts/walkthrough-cryptohack-ctf/</link>
        <guid isPermaLink="true">https://lessonsec.com/posts/walkthrough-cryptohack-ctf/</guid>
        <pubDate>Sun, 03 Oct 2021 12:41:44 &#43;0200</pubDate><description>Recently I&amp;rsquo;ve been meaning to get into cryptography more seriously, and to be honest I&amp;rsquo;ve also been postponing it for a while too, so I figured it was time I wrote this article to get motivated!</description>
	<content:encoded>&lt;p&gt;Recently I&amp;rsquo;ve been meaning to get into cryptography more seriously, and to be honest I&amp;rsquo;ve also been postponing it for a while too, so I figured it was time I wrote this article to get motivated!&lt;/p&gt;
&lt;p&gt;I&amp;rsquo;m approaching this cryptography deep dive with &lt;a href=&#34;https://cryptohack.org/&#34;&gt;https://cryptohack.org/&lt;/a&gt;.
Cryptohack it&amp;rsquo;s website offering CTF style challenges to understand and try to break modern cryptography. I really like this gamified approach so I decided to give it a shot.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;&lt;em&gt;&lt;strong&gt;Disclaimer&lt;/strong&gt;&lt;/em&gt;&lt;/p&gt;
&lt;p&gt;You always need to be extra careful when sharing CTFs solutions online. That&amp;rsquo;s the reason why I&amp;rsquo;m strictly following cryptohack&amp;rsquo;s guidelines.
As requested in the website&amp;rsquo;s &lt;a href=&#34;https://cryptohack.org/faq/#solutions&#34;&gt;FAQ&lt;/a&gt; I&amp;rsquo;m only sharing solutions for challenges worth 10 points or less.
These challenges are pretty basic, but I felt like it would be useful to have this kind of content published for those who are not familiar with basic cryptography or with the coding tools and technologies needed to solve the challenges. Each challenge solution will be explained but no flag will be available in this article.&lt;/p&gt;
&lt;p&gt;Cryptohack also has a functionality to share the solution once you get the flag for the challenge. Solutions to more complex challenges are to be shared exclusively there. The solutions are however only available for the solvers of the relative challenge.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;p&gt;Make sure to download the python notebook with the code snippets from this article &lt;a href=&#34;https://lessonsec.com/resources/cryptohack_walkthrough/cryptohack_walkthrough.ipynb&#34;&gt;here&lt;/a&gt;.&lt;/p&gt;
&lt;hr&gt;
&lt;h2 id=&#34;page-index&#34;&gt;Page index&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#setup&#34;&gt;Setup&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#introduction-challenges&#34;&gt;Introduction Challenges&lt;/a&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#finding-flags-2-pts&#34;&gt;Finding Flags&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#great-snakes-3-pts&#34;&gt;Great Snakes&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#network-attacks-5-pts&#34;&gt;Network Attacks&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#general-challenges&#34;&gt;General Challenges&lt;/a&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#ascii-5-pts&#34;&gt;ASCII&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#hex-5-pts&#34;&gt;Hex&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#base64-10-pts&#34;&gt;Base64&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#bytes-and-big-integers-10-pts&#34;&gt;Bytes and Big Integers&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#xor-starter-10-pts&#34;&gt;XOR Starter&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#mathematics&#34;&gt;Mathematics&lt;/a&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#vectors-10-pts&#34;&gt;Vectors&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#symmetric-ciphers&#34;&gt;Symmetric Ciphers&lt;/a&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#keyed-permutations-5-pts&#34;&gt;Keyed Permutations&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#resisting-bruteforce-10-pts&#34;&gt;Resisting Bruteforce&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#rsa&#34;&gt;RSA&lt;/a&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#rsa-starter-1-10-pts&#34;&gt;RSA Starter 1&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#diffie-hellman&#34;&gt;Diffie-Hellman&lt;/a&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#diffie-hellman-starter-1-10-pts&#34;&gt;Diffie-Hellman Starter 1&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#crypto-on-the-web&#34;&gt;Crypto On The Web&lt;/a&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#token-appreciation-5-pts&#34;&gt;Token Appreciation&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#jwt-sessions-10-pts&#34;&gt;JWT Sessions&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://lessonsec.com/posts/walkthrough-cryptohack-ctf/#conclusions&#34;&gt;Conclusions&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;hr&gt;
&lt;h2 id=&#34;setup&#34;&gt;Setup&lt;/h2&gt;
&lt;p&gt;Before starting I suggest getting the official docker image provided in the FAQs.
You simply need to pull &lt;code&gt;hyperreality/cryptohack:latest&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;To run the container simply run the provided command: &lt;code&gt;docker run -p 127.0.0.1:8888:8888 -it hyperreality/cryptohack:latest&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;This will start a Jupyter Notebook server reachable at &lt;code&gt;localhost:8888&lt;/code&gt;.
If you don&amp;rsquo;t want to use notebooks to solve the challenges but still want to use the container because of dependencies, you can overwrite the entrypoint of the image with the following command: &lt;code&gt;docker run -it --entrypoint /bin/bash -p 127.0.0.1:8888:8888 -v hyperreality/cryptohack:latest&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;Once the docker situation is under control, we can start working on the challenges.&lt;/p&gt;
&lt;hr&gt;
&lt;h2 id=&#34;introduction-challenges&#34;&gt;Introduction Challenges&lt;/h2&gt;
&lt;p&gt;These challenges are basically tutorials to get familiar with how the challenges on this website works.
They show the flag format, how to work with the challenge scripts and how to approach the network based attacks.&lt;/p&gt;
&lt;h4 id=&#34;finding-flags-2-pts&#34;&gt;Finding Flags (2 pts.)&lt;/h4&gt;
&lt;p&gt;Simply follow the instructions and copy-paste the flag in the text field.&lt;/p&gt;
&lt;h4 id=&#34;great-snakes-3-pts&#34;&gt;Great Snakes (3 pts.)&lt;/h4&gt;
&lt;p&gt;For this one you need to execute the provided python script, that will print out the flag.&lt;/p&gt;
&lt;h4 id=&#34;network-attacks-5-pts&#34;&gt;Network Attacks (5 pts.)&lt;/h4&gt;
&lt;p&gt;We need to interact with a TCP server using JSON messages.
The website suggests using python and &lt;code&gt;telnetlib&lt;/code&gt; to do so. It also provides an example showing how to interact with the server of this challenge.&lt;/p&gt;
&lt;p&gt;What we need to do to get the flag is to play around a little bit with the server and find the correct request to &lt;em&gt;buy&lt;/em&gt; a &lt;em&gt;flag&lt;/em&gt;.&lt;/p&gt;
&lt;p&gt;&lt;u&gt;Solution&lt;/u&gt;:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; style=&#34;color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-python&#34; data-lang=&#34;python&#34;&gt;&lt;span style=&#34;color:#75715e&#34;&gt;# import the libraries needed for the challenge&lt;/span&gt;
&lt;span style=&#34;color:#f92672&#34;&gt;import&lt;/span&gt; telnetlib
&lt;span style=&#34;color:#f92672&#34;&gt;import&lt;/span&gt; json

HOST &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;socket.cryptohack.org&amp;#34;&lt;/span&gt;
PORT &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;11112&lt;/span&gt;

&lt;span style=&#34;color:#75715e&#34;&gt;# initialize the connection&lt;/span&gt;
tn &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; telnetlib&lt;span style=&#34;color:#f92672&#34;&gt;.&lt;/span&gt;Telnet(HOST, PORT)

&lt;span style=&#34;color:#75715e&#34;&gt;# define functions to receive and send JSON payloads over TCP&lt;/span&gt;
&lt;span style=&#34;color:#66d9ef&#34;&gt;def&lt;/span&gt; &lt;span style=&#34;color:#a6e22e&#34;&gt;readline&lt;/span&gt;():
    &lt;span style=&#34;color:#66d9ef&#34;&gt;return&lt;/span&gt; tn&lt;span style=&#34;color:#f92672&#34;&gt;.&lt;/span&gt;read_until(&lt;span style=&#34;color:#e6db74&#34;&gt;b&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#ae81ff&#34;&gt;\n&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;&lt;/span&gt;)

&lt;span style=&#34;color:#66d9ef&#34;&gt;def&lt;/span&gt; &lt;span style=&#34;color:#a6e22e&#34;&gt;json_recv&lt;/span&gt;():
    line &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; readline()
    &lt;span style=&#34;color:#66d9ef&#34;&gt;return&lt;/span&gt; json&lt;span style=&#34;color:#f92672&#34;&gt;.&lt;/span&gt;loads(line&lt;span style=&#34;color:#f92672&#34;&gt;.&lt;/span&gt;decode())

&lt;span style=&#34;color:#66d9ef&#34;&gt;def&lt;/span&gt; &lt;span style=&#34;color:#a6e22e&#34;&gt;json_send&lt;/span&gt;(hsh):
    request &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; json&lt;span style=&#34;color:#f92672&#34;&gt;.&lt;/span&gt;dumps(hsh)&lt;span style=&#34;color:#f92672&#34;&gt;.&lt;/span&gt;encode()
    tn&lt;span style=&#34;color:#f92672&#34;&gt;.&lt;/span&gt;write(request)
  
&lt;span style=&#34;color:#75715e&#34;&gt;# reads the banner printed by the server&lt;/span&gt;
print(readline())
print(readline())
print(readline())
print(readline())

&lt;span style=&#34;color:#75715e&#34;&gt;# ------ Request example ------&lt;/span&gt;
&lt;span style=&#34;color:#75715e&#34;&gt;# Compose a request for the server&lt;/span&gt;
request &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; {&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;buy&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;clothes&amp;#34;&lt;/span&gt;}

&lt;span style=&#34;color:#75715e&#34;&gt;# Sends the request&lt;/span&gt;
json_send(request)

&lt;span style=&#34;color:#75715e&#34;&gt;# Gets the response&lt;/span&gt;
response &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; json_recv()

print(response) &lt;span style=&#34;color:#75715e&#34;&gt;# {&amp;#39;error&amp;#39;: &amp;#39;Sorry! All we have to sell are flags.&amp;#39;}&lt;/span&gt;

&lt;span style=&#34;color:#75715e&#34;&gt;# ------ Real request ------&lt;/span&gt;
&lt;span style=&#34;color:#75715e&#34;&gt;# mhhh flags you say?&lt;/span&gt;
request &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; {&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;buy&amp;#34;&lt;/span&gt;: &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;flag&amp;#34;&lt;/span&gt;}

&lt;span style=&#34;color:#75715e&#34;&gt;# Sends the request&lt;/span&gt;
json_send(request)

&lt;span style=&#34;color:#75715e&#34;&gt;# Gets the response&lt;/span&gt;
response &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; json_recv()

print(response)
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;hr&gt;
&lt;h2 id=&#34;general-challenges&#34;&gt;General Challenges&lt;/h2&gt;
&lt;h3 id=&#34;uencodingu&#34;&gt;&lt;u&gt;Encoding&lt;/u&gt;&lt;/h3&gt;
&lt;blockquote&gt;
&lt;p&gt;For these challenges it&amp;rsquo;s not really necessary to write any code. While writing your own scripts can help getting familiar with tools and techniques, a deeper understanding of encodings can be obtained solving the challenges in different ways.&lt;/p&gt;
&lt;p&gt;A super-versatile and commonly used tool for this kind of task is &lt;a href=&#34;https://gchq.github.io/CyberChef/&#34;&gt;CyberChef&lt;/a&gt;.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h4 id=&#34;ascii-5-pts&#34;&gt;ASCII (5 pts.)&lt;/h4&gt;
&lt;p&gt;We are given a 7-bit ASCII encoded string and we need to decode it to get the flag.
The challenge hint suggests that we use the python &lt;code&gt;chr()&lt;/code&gt; function to do to.&lt;/p&gt;
&lt;p&gt;&lt;u&gt;Solution&lt;/u&gt;:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; style=&#34;color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-python&#34; data-lang=&#34;python&#34;&gt;&lt;span style=&#34;color:#75715e&#34;&gt;# ASCII values to decode&lt;/span&gt;
values &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; [&lt;span style=&#34;color:#ae81ff&#34;&gt;99&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;114&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;121&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;112&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;116&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;111&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;123&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;65&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;83&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;67&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;73&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;73&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;95&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;112&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;114&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;49&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;110&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;116&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;52&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;98&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;108&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;51&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;125&lt;/span&gt;]

solution &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;&amp;#34;&lt;/span&gt;
&lt;span style=&#34;color:#66d9ef&#34;&gt;for&lt;/span&gt; v &lt;span style=&#34;color:#f92672&#34;&gt;in&lt;/span&gt; values:
    solution &lt;span style=&#34;color:#f92672&#34;&gt;+=&lt;/span&gt; chr(v)
    
print(solution)
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h4 id=&#34;hex-5-pts&#34;&gt;Hex (5 pts.)&lt;/h4&gt;
&lt;p&gt;In this challenge we are provided with an hex encoded string we need to decode.
This time the challenge hint suggests using the &lt;code&gt;bytes.fromhex()&lt;/code&gt; function.&lt;/p&gt;
&lt;p&gt;&lt;u&gt;Solution&lt;/u&gt;:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; style=&#34;color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-python&#34; data-lang=&#34;python&#34;&gt;&lt;span style=&#34;color:#75715e&#34;&gt;# HEX values to decode&lt;/span&gt;
values &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;63727970746f7b596f755f77696c6c5f62655f776f726b696e675f776974685f6865785f737472696e67735f615f6c6f747d&amp;#34;&lt;/span&gt;

solution &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; bytes&lt;span style=&#34;color:#f92672&#34;&gt;.&lt;/span&gt;fromhex(values)&lt;span style=&#34;color:#f92672&#34;&gt;.&lt;/span&gt;decode(&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#39;utf-8&amp;#39;&lt;/span&gt;)

print(solution)
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h4 id=&#34;base64-10-pts&#34;&gt;Base64 (10 pts.)&lt;/h4&gt;
&lt;p&gt;For this challenge we are given an hex encoded string, to be decoded and then encoded in base64 to be used as flag.
In this case we will be using the &lt;code&gt;base64&lt;/code&gt; python module, in particular the &lt;code&gt;base64.b64encode()&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;&lt;u&gt;Solution&lt;/u&gt;:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; style=&#34;color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-python&#34; data-lang=&#34;python&#34;&gt;&lt;span style=&#34;color:#f92672&#34;&gt;import&lt;/span&gt; base64

&lt;span style=&#34;color:#75715e&#34;&gt;# HEX values to decode&lt;/span&gt;
values &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;72bca9b68fc16ac7beeb8f849dca1d8a783e8acf9679bf9269f7bf&amp;#34;&lt;/span&gt;

&lt;span style=&#34;color:#75715e&#34;&gt;# Decoded values&lt;/span&gt;
tmp &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; bytes&lt;span style=&#34;color:#f92672&#34;&gt;.&lt;/span&gt;fromhex(values)
&lt;span style=&#34;color:#75715e&#34;&gt;# print(tmp)&lt;/span&gt;
solution &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; base64&lt;span style=&#34;color:#f92672&#34;&gt;.&lt;/span&gt;b64encode(tmp)&lt;span style=&#34;color:#f92672&#34;&gt;.&lt;/span&gt;decode(&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#39;utf-8&amp;#39;&lt;/span&gt;)

print(solution)
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h4 id=&#34;bytes-and-big-integers-10-pts&#34;&gt;Bytes and Big Integers (10 pts.)&lt;/h4&gt;
&lt;p&gt;Some cryptosystems like RSA work only when applied to numbers. We need to encode our messages as numbers in order to work with these cryptosystems.
One method to do so is to represent the data as bytes and convert these in a base-16 or base-10 number.&lt;/p&gt;
&lt;p&gt;In this challenge we are provided with a message encoded in this way and we need to get the original message out.&lt;/p&gt;
&lt;p&gt;For this challenge the PyCryptodome library it needed, we can work with this encoding using the functions: &lt;code&gt;Crypto.Util.number.bytes_to_long()&lt;/code&gt; and &lt;code&gt;Crypto.Util.number.long_to_bytes()&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;&lt;u&gt;Solution&lt;/u&gt;:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; style=&#34;color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-python&#34; data-lang=&#34;python&#34;&gt;&lt;span style=&#34;color:#f92672&#34;&gt;from&lt;/span&gt; Crypto.Util.number &lt;span style=&#34;color:#f92672&#34;&gt;import&lt;/span&gt; long_to_bytes

&lt;span style=&#34;color:#75715e&#34;&gt;# Message encoded as number&lt;/span&gt;
values &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;11515195063862318899931685488813747395775516287289682636499965282714637259206269&lt;/span&gt;

solution &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; long_to_bytes(values)&lt;span style=&#34;color:#f92672&#34;&gt;.&lt;/span&gt;decode(&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#39;utf-8&amp;#39;&lt;/span&gt;)

print(solution)
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;hr&gt;
&lt;h3 id=&#34;uxoru&#34;&gt;&lt;u&gt;XOR&lt;/u&gt;&lt;/h3&gt;
&lt;h4 id=&#34;xor-starter-10-pts&#34;&gt;XOR Starter (10 pts.)&lt;/h4&gt;
&lt;p&gt;In this challenge we need to XOR the value 13 to each character of the provided string, then we need to put the result in the cyber{flag} format.
The hint suggests that it&amp;rsquo;s possible to use the &lt;code&gt;xor()&lt;/code&gt; function from &lt;code&gt;pwntools&lt;/code&gt; but it&amp;rsquo;s just as easy to do the same in pure python.&lt;/p&gt;
&lt;p&gt;&lt;u&gt;Solution&lt;/u&gt;:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; style=&#34;color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-python&#34; data-lang=&#34;python&#34;&gt;&lt;span style=&#34;color:#75715e&#34;&gt;# Provided string&lt;/span&gt;
values &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;label&amp;#34;&lt;/span&gt;

solution &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;&amp;#34;&lt;/span&gt;
&lt;span style=&#34;color:#66d9ef&#34;&gt;for&lt;/span&gt; v &lt;span style=&#34;color:#f92672&#34;&gt;in&lt;/span&gt; values:
    solution &lt;span style=&#34;color:#f92672&#34;&gt;+=&lt;/span&gt; chr(ord(v) &lt;span style=&#34;color:#f92672&#34;&gt;^&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;13&lt;/span&gt;)
    
&lt;span style=&#34;color:#75715e&#34;&gt;# The {{{var}}} syntax is needed to excape curly braces in python f-strings&lt;/span&gt;
print(&lt;span style=&#34;color:#e6db74&#34;&gt;f&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;crypto&lt;/span&gt;&lt;span style=&#34;color:#ae81ff&#34;&gt;{{&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;{&lt;/span&gt;solution&lt;span style=&#34;color:#e6db74&#34;&gt;}&lt;/span&gt;&lt;span style=&#34;color:#ae81ff&#34;&gt;}}&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;&lt;/span&gt;)
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;hr&gt;
&lt;h2 id=&#34;mathematics&#34;&gt;Mathematics&lt;/h2&gt;
&lt;h3 id=&#34;ulatticesu&#34;&gt;&lt;u&gt;Lattices&lt;/u&gt;&lt;/h3&gt;
&lt;h4 id=&#34;vectors-10-pts&#34;&gt;Vectors (10 pts.)&lt;/h4&gt;
&lt;p&gt;In this challenge we are asked to perform operations on a three dimensional vector space.
If this sounds new to you make sure to carefully read the challenge description and check the suggested materials.&lt;/p&gt;
&lt;p&gt;&lt;u&gt;Solution&lt;/u&gt;:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; style=&#34;color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-python&#34; data-lang=&#34;python&#34;&gt;v &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; (&lt;span style=&#34;color:#ae81ff&#34;&gt;2&lt;/span&gt;,&lt;span style=&#34;color:#ae81ff&#34;&gt;6&lt;/span&gt;,&lt;span style=&#34;color:#ae81ff&#34;&gt;3&lt;/span&gt;)
w &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; (&lt;span style=&#34;color:#ae81ff&#34;&gt;1&lt;/span&gt;,&lt;span style=&#34;color:#ae81ff&#34;&gt;0&lt;/span&gt;,&lt;span style=&#34;color:#ae81ff&#34;&gt;0&lt;/span&gt;)
u &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; (&lt;span style=&#34;color:#ae81ff&#34;&gt;7&lt;/span&gt;,&lt;span style=&#34;color:#ae81ff&#34;&gt;7&lt;/span&gt;,&lt;span style=&#34;color:#ae81ff&#34;&gt;2&lt;/span&gt;)

&lt;span style=&#34;color:#66d9ef&#34;&gt;def&lt;/span&gt; &lt;span style=&#34;color:#a6e22e&#34;&gt;vector_minus&lt;/span&gt;(a, b):
   &lt;span style=&#34;color:#66d9ef&#34;&gt;return&lt;/span&gt; [x &lt;span style=&#34;color:#f92672&#34;&gt;-&lt;/span&gt; y &lt;span style=&#34;color:#66d9ef&#34;&gt;for&lt;/span&gt; x, y &lt;span style=&#34;color:#f92672&#34;&gt;in&lt;/span&gt; zip(a,b)]

&lt;span style=&#34;color:#66d9ef&#34;&gt;def&lt;/span&gt; &lt;span style=&#34;color:#a6e22e&#34;&gt;vector_dot&lt;/span&gt;(a,b):
    &lt;span style=&#34;color:#66d9ef&#34;&gt;return&lt;/span&gt; sum([x &lt;span style=&#34;color:#f92672&#34;&gt;*&lt;/span&gt; y &lt;span style=&#34;color:#66d9ef&#34;&gt;for&lt;/span&gt; x, y &lt;span style=&#34;color:#f92672&#34;&gt;in&lt;/span&gt; zip(a,b)])
    
&lt;span style=&#34;color:#66d9ef&#34;&gt;def&lt;/span&gt; &lt;span style=&#34;color:#a6e22e&#34;&gt;scalar_times&lt;/span&gt;(a, times):
    &lt;span style=&#34;color:#66d9ef&#34;&gt;return&lt;/span&gt; list(map( &lt;span style=&#34;color:#66d9ef&#34;&gt;lambda&lt;/span&gt; x: x &lt;span style=&#34;color:#f92672&#34;&gt;*&lt;/span&gt; times , a))

&lt;span style=&#34;color:#75715e&#34;&gt;# calculate 3*(2*v - w) ∙ 2*u&lt;/span&gt;
vector_dot(scalar_times(vector_minus(scalar_times(v, &lt;span style=&#34;color:#ae81ff&#34;&gt;2&lt;/span&gt;), w), &lt;span style=&#34;color:#ae81ff&#34;&gt;3&lt;/span&gt;), scalar_times(u, &lt;span style=&#34;color:#ae81ff&#34;&gt;2&lt;/span&gt;))
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;hr&gt;
&lt;h2 id=&#34;symmetric-ciphers&#34;&gt;Symmetric Ciphers&lt;/h2&gt;
&lt;p&gt;&lt;u&gt;&lt;strong&gt;How AES Works&lt;/strong&gt;&lt;/u&gt;&lt;/p&gt;
&lt;h4 id=&#34;keyed-permutations-5-pts&#34;&gt;Keyed Permutations (5 pts.)&lt;/h4&gt;
&lt;p&gt;In this challenge we are asked to answer a question: &lt;em&gt;What is the mathematical term for a one-to-one correspondence?&lt;/em&gt;
Google is your friend for this one!&lt;/p&gt;
&lt;h4 id=&#34;resisting-bruteforce-10-pts&#34;&gt;Resisting Bruteforce (10 pts.)&lt;/h4&gt;
&lt;p&gt;This time we are asked: &lt;em&gt;What is the name for the best single-key attack against AES?&lt;/em&gt;                &lt;br&gt;
Just make sure you carefully read the challenge description and you&amp;rsquo;re good to go!&lt;/p&gt;
&lt;hr&gt;
&lt;h2 id=&#34;rsa&#34;&gt;RSA&lt;/h2&gt;
&lt;p&gt;&lt;u&gt;&lt;strong&gt;Starter&lt;/strong&gt;&lt;/u&gt;&lt;/p&gt;
&lt;h4 id=&#34;rsa-starter-1-10-pts&#34;&gt;RSA Starter 1 (10 pts.)&lt;/h4&gt;
&lt;p&gt;The basis of RSA encryption is modular exponentiation. In this challenge we are asked to use such technique to create a &amp;ldquo;trapdoor function&amp;rdquo; (a function easy to calculate but hard to reverse).
This can be done using the &lt;code&gt;pow()&lt;/code&gt; function that python provides.&lt;/p&gt;
&lt;p&gt;&lt;u&gt;Solution&lt;/u&gt;:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; style=&#34;color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-python&#34; data-lang=&#34;python&#34;&gt;&lt;span style=&#34;color:#75715e&#34;&gt;# Calculate 101^17 mod 22663&lt;/span&gt;
pow(&lt;span style=&#34;color:#ae81ff&#34;&gt;101&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;17&lt;/span&gt;, &lt;span style=&#34;color:#ae81ff&#34;&gt;22663&lt;/span&gt;)
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;hr&gt;
&lt;h2 id=&#34;diffie-hellman&#34;&gt;Diffie-Hellman&lt;/h2&gt;
&lt;p&gt;&lt;u&gt;&lt;strong&gt;Starter&lt;/strong&gt;&lt;/u&gt;&lt;/p&gt;
&lt;h4 id=&#34;diffie-hellman-starter-1-10-pts&#34;&gt;Diffie-Hellman Starter 1 (10 pts.)&lt;/h4&gt;
&lt;p&gt;The Diffie-Hellman algorithm works with finite fields and modular exponentiation to allow to parties to exchange a shared secret.
If you&amp;rsquo;re not familiar with this algorithm or with the math behind it I would suggest to check out the &lt;a href=&#34;https://en.wikipedia.org/wiki/Diffie%E2%80%93Hellman_key_exchange#Cryptographic_explanation&#34;&gt;Wikipedia page&lt;/a&gt; to get started.&lt;/p&gt;
&lt;p&gt;In this challenge we are asked to find an inverse element given the prime number and the modulo.&lt;/p&gt;
&lt;p&gt;&lt;u&gt;Solution&lt;/u&gt;:&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; style=&#34;color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4&#34;&gt;&lt;code class=&#34;language-python&#34; data-lang=&#34;python&#34;&gt;g &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;209&lt;/span&gt;
p &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;991&lt;/span&gt;
fc &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;1&lt;/span&gt;

&lt;span style=&#34;color:#66d9ef&#34;&gt;for&lt;/span&gt; x &lt;span style=&#34;color:#f92672&#34;&gt;in&lt;/span&gt; range(&lt;span style=&#34;color:#ae81ff&#34;&gt;1&lt;/span&gt;, p):    
    &lt;span style=&#34;color:#66d9ef&#34;&gt;if&lt;/span&gt; (g &lt;span style=&#34;color:#f92672&#34;&gt;*&lt;/span&gt; x) &lt;span style=&#34;color:#f92672&#34;&gt;%&lt;/span&gt; p &lt;span style=&#34;color:#f92672&#34;&gt;==&lt;/span&gt; fc:         
        print(x)        
        &lt;span style=&#34;color:#66d9ef&#34;&gt;break&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;hr&gt;
&lt;h2 id=&#34;crypto-on-the-web&#34;&gt;Crypto On The Web&lt;/h2&gt;
&lt;p&gt;&lt;strong&gt;&lt;u&gt;JSON web tokens&lt;/u&gt;&lt;/strong&gt;&lt;/p&gt;
&lt;h4 id=&#34;token-appreciation-5-pts&#34;&gt;Token Appreciation (5 pts.)&lt;/h4&gt;
&lt;p&gt;&lt;a href=&#34;https://datatracker.ietf.org/doc/html/rfc7519&#34;&gt;JWTs or JSON Web Tokens&lt;/a&gt; are a standard method to safely represent claims between two parties.
This kind of token is not encrypted by default, and this is the reason why it&amp;rsquo;s possible to reverse the encoding and extract the original message.&lt;/p&gt;
&lt;p&gt;We are given the token:&lt;/p&gt;
&lt;p&gt;&lt;code&gt;eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJmbGFnIjoiY3J5cHRve2p3dF9jb250ZW50c19j&lt;/code&gt;
&lt;code&gt;YW5fYmVfZWFzaWx5X3ZpZXdlZH0iLCJ1c2VyIjoiQ3J5cHRvIE1jSGFjayIsImV4cCI6MjAwNT&lt;/code&gt;
&lt;code&gt;AzMzQ5M30.shKSmZfgGVvd2OSB2CGezzJ3N6WAULo3w9zCl_T47K&lt;/code&gt;&lt;/p&gt;
&lt;p&gt;Now, there are a few ways to solve this challenge, the suggested one is to use Python&amp;rsquo;s &lt;a href=&#34;https://pyjwt.readthedocs.io/en/stable/&#34;&gt;PyJWT&lt;/a&gt; library, but since it&amp;rsquo;s not installed in the docker container we are using, it&amp;rsquo;s easier to use an online tool like &lt;a href=&#34;https://gchq.github.io/CyberChef&#34;&gt;CyberChef&lt;/a&gt; or &lt;a href=&#34;https://jwt.io/&#34;&gt;jwt.io&lt;/a&gt;.&lt;/p&gt;
&lt;h4 id=&#34;jwt-sessions-10-pts&#34;&gt;JWT Sessions (10 pts.)&lt;/h4&gt;
&lt;p&gt;In this challenge we are given some information about the use of JWT tokens, now we are asked the &lt;em&gt;HTTP header used by the browser to send JWTs to the server&lt;/em&gt;. Once again Google is your friend!&lt;/p&gt;
&lt;p&gt;If you want to solve this challenge on your own, take out the developer tools in your browser, go to the network tab and start looking around for HTTP headers that could refer to the use of JWT tokens. You&amp;rsquo;re &lt;em&gt;authorized&lt;/em&gt; to do that!&lt;/p&gt;
&lt;hr&gt;
&lt;h2 id=&#34;conclusions&#34;&gt;Conclusions&lt;/h2&gt;
&lt;p&gt;Hope this article is useful to anyone who&amp;rsquo;s meaning to get into cryptography or CTFs in general.
Writing this article allowed me to go back and review my knowledge of basic cryptography as well as exploring a bit out of my comfort zone (when it came to more complex challenges not included in the writeup).&lt;/p&gt;
</content:encoded>

      </item><item>
        <title>Analysis of a Remote Control</title>
        <link>https://lessonsec.com/posts/analysis-of-a-remote-control/</link>
        <guid isPermaLink="true">https://lessonsec.com/posts/analysis-of-a-remote-control/</guid>
        <pubDate>Thu, 15 Jul 2021 16:45:40 &#43;0200</pubDate><description>A couple of days ago I found some old remote controls around the house and decided it was time to take out my old RTL-SDR and put it to good use.</description>
	<content:encoded>&lt;p&gt;A couple of days ago I found some old remote controls around the house and decided it was time to take out my old &lt;strong&gt;RTL-SDR&lt;/strong&gt; and put it to good use.
In this article I will describe step-by-step my experience with &lt;em&gt;studying&lt;/em&gt;, &lt;em&gt;reversing&lt;/em&gt; and &lt;em&gt;understanding&lt;/em&gt; these devices.&lt;/p&gt;
&lt;p&gt;In particular the analysis will comprehend:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Analysis of the &lt;strong&gt;board&lt;/strong&gt;&lt;/li&gt;
&lt;li&gt;Analysis of the &lt;strong&gt;behavior&lt;/strong&gt;&lt;/li&gt;
&lt;li&gt;Analysis of the &lt;strong&gt;signal&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;This will allow to have a complete overview of the remotes.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/rc_analysis/complete.jpeg#center&#34; alt=&#34;remote&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;Remote to analyze&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;h2 id=&#34;board-analysis&#34;&gt;Board analysis&lt;/h2&gt;
&lt;p&gt;The first thing I did was to operate the remote: of course whenever the yellow button was pressed, the led on its side would light up signaling that everything was working fine. The device could use different communication methods, but since there is no visible IR LED, it is possible to assume that the device works via radio signals.&lt;/p&gt;
&lt;p&gt;The very next step was to open up the remote and visually inspect the board.&lt;/p&gt;
&lt;p&gt;Inside the plastic casing I found this simple PCB.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/rc_analysis/pcb.jpg#center&#34; alt=&#34;RC pcb board&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;PCB board&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;At first glance it&amp;rsquo;s possible to notice that there&amp;rsquo;s an &lt;em&gt;antenna&lt;/em&gt;, &lt;em&gt;a crystal oscillator&lt;/em&gt;, a &lt;em&gt;trimmer&lt;/em&gt; an &lt;em&gt;integrated circuit&lt;/em&gt; and of course led, button and battery.
As expected, there&amp;rsquo;s everything needed for a radio transmitter to work.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/rc_analysis/clock.jpeg#center&#34; alt=&#34;crystal oscillator&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;30.875MHz oscillator&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;Looking at the components further it&amp;rsquo;s possible to gather insights about how the device works.
In particular the oscillator gives away that the device probably operates at &lt;em&gt;30.875MHz&lt;/em&gt; - this isn&amp;rsquo;t what I was expecting.&lt;/p&gt;
&lt;p&gt;In my country, &lt;strong&gt;Short Range Devices&lt;/strong&gt; should work in the ranges:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;27,5000 – 28,0000 MHz&lt;/li&gt;
&lt;li&gt;29,7000 – 30,0050 MHz&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Or, for general purpose applications they can work  in the ranges:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;433,000 – 435,0000 MHz (devices without a specific use)&lt;/li&gt;
&lt;li&gt;862,0000 – 876,0000 MHz (devices without a specific use, wireless audio, alarm systems, social alarms, radio microphones, and RFID devices)&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Radio transmitters are not forced to adopt the crystal oscillator frequency as working frequency, in fact it&amp;rsquo;s not uncommon that they use a multiple of such frequency instead. Said that, at this point it&amp;rsquo;s only a guess, but even if it&amp;rsquo;s not in the expected ranges, it&amp;rsquo;s possible that the working frequency of the remote would be around 30.875MHz.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/rc_analysis/dip_switch.jpeg#center&#34; alt=&#34;DIP switch&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;10-position DIP switch&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;We can also see that there&amp;rsquo;s a 10-position DIP switch.&lt;/p&gt;
&lt;p&gt;The first pin (1) of the DIP switch has written &amp;ldquo;ON&amp;rdquo; on top of it, meaning that the switch closes the circuit when the lever is in the &amp;ldquo;high&amp;rdquo; position.
This component suggests us that the remote sends at least 10 bits of data. I say at least, because it&amp;rsquo;s possible that the device sends preamble/ending bits and/or checksum or parity bits.&lt;/p&gt;
&lt;p&gt;Also, given the position of the switches, it&amp;rsquo;s possible to assume that the code sent by the remote would either be &lt;code&gt;0001000110&lt;/code&gt; or &lt;code&gt;1110111001&lt;/code&gt;.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/rc_analysis/unknown_ic.jpeg#center&#34; alt=&#34;ITF CIE9101&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;ITF CIE9101 Integrated Circuit&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;On the back of the PCB there&amp;rsquo;s the ITF CIE9101 integrated circuit. Sadly I wasn&amp;rsquo;t able to find any datasheets or information about this component (hit me up if you know something about it!).&lt;/p&gt;
&lt;p&gt;Inspecting the PCB it&amp;rsquo;s possible to see that this device is connected to the DIP switch, to the oscillator and to the antenna. We can make an educated guess and say that this IC is probably responsible for the radio transmission (in future it would be worth reverse engineering this IC to better understand how this device work).&lt;/p&gt;
&lt;h2 id=&#34;behavior-analysis&#34;&gt;Behavior analysis&lt;/h2&gt;
&lt;p&gt;To validate the hypothesis of the device being a radio transmitter, it&amp;rsquo;s fundamental to try to intercept and visualize the communication.&lt;/p&gt;
&lt;p&gt;The goal now is to find the transmitted signal. There is a limited set of possible frequency ranges, but it&amp;rsquo;s not always easy to blindly spot the signal you&amp;rsquo;re looking for, especially in areas in which similar devices are widely employed (think of remote car keys, AC remotes, radio weather stations and so on).&lt;/p&gt;
&lt;p&gt;To figure out the frequency and to work with the raw radio signal I used a Silver dongle &lt;a href=&#34;https://www.rtl-sdr.com/about-rtl-sdr/&#34;&gt;RTL-SDR&lt;/a&gt; and &lt;a href=&#34;https://gqrx.dk/&#34;&gt;gqrx&lt;/a&gt;.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/rc_analysis/rtl_antenna.jpeg#center&#34; alt=&#34;rtl-sdr and antenna&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;RTL-SDR and Antenna&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;Once &lt;em&gt;gqrx&lt;/em&gt; was open, it was necessary to spot the correct frequency. Since there is a 30.875MHz crystal oscillator in the remote, that was the first frequency I checked. And luckily the signal was right there. Well, for this remote in particular it was at 30.889MHz, but at least we got the working frequency.&lt;/p&gt;
&lt;p&gt;NOTE: I could work with 3 of these remotes, and each one was using a slightly different frequency, that&amp;rsquo;s why it was possible to find the signal at 30.889MHz and not exactly at 30.875MHz. This can depend on a number of factors and it&amp;rsquo;s completely normal.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/rc_analysis/gqrx_signal.gif#center&#34; alt=&#34;radio signal&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;Signal interception&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;Now it&amp;rsquo;s time to analyze the signal.&lt;/p&gt;
&lt;h2 id=&#34;signal-analysis&#34;&gt;Signal analysis&lt;/h2&gt;
&lt;p&gt;What I did at this point was to record the signal in &lt;em&gt;gqrx&lt;/em&gt; to analyze it.
Opening the signal in audacity shows the recorded waveform.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/rc_analysis/signal.jpeg#center&#34; alt=&#34;waveform&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;Signal waveform&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;We can see noise at the beginning and at the end of the recording, while the center part represent the communication.&lt;/p&gt;
&lt;p&gt;It&amp;rsquo;s possible to notice immediately that there are numerous spikes, this is due to the fact that I kept the button pressed for a few seconds while recording.
Visually it&amp;rsquo;s possible to say that the spikes are identical, so our scope is limited to understanding what one of these spikes represent.&lt;/p&gt;
&lt;p&gt;Now we need to zoom in on one spike to try and decode the actual digital data.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/rc_analysis/signal_zoom.jpeg#center&#34; alt=&#34;zoomed-in waveform&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;Zoomed waveform&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;Of course it&amp;rsquo;s a digital communication and It&amp;rsquo;s now clear that we are dealing with &lt;a href=&#34;https://en.wikipedia.org/wiki/Pulse-width_modulation&#34;&gt;Pulse Width Modulation (PWM)&lt;/a&gt;.
If we look closely at the signal, we can see that there are &amp;ldquo;short&amp;rdquo; and &amp;ldquo;long&amp;rdquo; pulses. Those represent either 1s or 0s depending on the protocol shared by the remote and the receiver.&lt;/p&gt;
&lt;p&gt;Counting the bits reveals that that&amp;rsquo;s more than a simple 10 bit communication. In fact, we are dealing with 14 bits.
If we compare the signal to the position of the switches in the remote, we see that the pattern matches, with the exception of the last 4 bits. These bits (either 0000 or 1111) are trailing bits, needed to signal the end of the communication.&lt;/p&gt;
&lt;p&gt;To prove that the signal actually corresponds to the one encoded by the switch + 4 trailing bits, I&amp;rsquo;m using &lt;code&gt;rtl_433&lt;/code&gt; to read and decode the signal.
So we run &lt;code&gt;rtl_433 -f 30888000 -A&lt;/code&gt; and we get this output:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;Attempting demodulation... short_width: 748, long_width: 1516, reset_limit: 5420, sync_width: 0
Use a flex decoder with -X &#39;n=name,m=OOK_PWM,s=748,l=1516,r=5420,g=1556,t=307,y=0&#39;
pulse_demod_pwm(): Analyzer Device
bitbuffer:: Number of rows: 6 
[00] {14} ee 40     : 11101110 010000
[01] {14} ee 40     : 11101110 010000
[02] {14} ee 40     : 11101110 010000
[03] {14} ee 40     : 11101110 010000
[04] {14} ee 40     : 11101110 010000
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;And we confirm that the signal uses a PWM modulation and is in fact &lt;code&gt;1110111001&lt;/code&gt; followed by &lt;code&gt;0000&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;To exclude the possibility that the last 4 bits are parity bits, we need to try other configurations in the remote and analyze the signal.
I proceeded to do so and one-by-one I lifted the switches corresponding to the 0s in the signal to see what would change in the transmitted bits.&lt;/p&gt;
&lt;p&gt;Changing bit 9 from 0 to 1 produced the following signal:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;[00] {14} ee c0     : 11101110 110000
[01] {14} ee c0     : 11101110 110000
[02] {14} ee c0     : 11101110 110000
[03] {14} ee c0     : 11101110 110000
[04] {14} ee c0     : 11101110 110000
[05] {14} ee c0     : 11101110 110000
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Similarly, changing bit 8, produced this signal:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;[00] {14} ef c0     : 11101111 110000
[01] {14} ef c0     : 11101111 110000
[02] {14} ef c0     : 11101111 110000
[03] {14} ef c0     : 11101111 110000
[04] {14} ef c0     : 11101111 110000
[05] {14} ef c0     : 11101111 110000
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Finally I changed bit 4 and I decoded signal was:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;[00] {14} ff c0     : 11111111 110000
[01] {14} ff c0     : 11111111 110000
[02] {14} ff c0     : 11111111 110000
[03] {14} ff c0     : 11111111 110000
[04] {14} ff c0     : 11111111 110000
[05] {14} ff c0     : 11111111 110000
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;As I suspected the last 4 bits don&amp;rsquo;t change even if the signal changes. This means that they are simple trailing bits and not parity bits or a form of checksum.&lt;/p&gt;
&lt;h2 id=&#34;conclusions&#34;&gt;Conclusions&lt;/h2&gt;
&lt;p&gt;After the analysis, everything about how this board operates is known.
Since this device was pretty old I wasn&amp;rsquo;t expecting behaviors any more complex that the ones we observed.&lt;/p&gt;
&lt;p&gt;I was left with a deeper understanding on radio communications, in particular of the concept of modulations.
This was in fact the first time I was confronted with the PWM modulation in a real life scenario.
Decoding these signals both visually and using specialized software allowed me to learn new tools I&amp;rsquo;ll be using for future experiments.&lt;/p&gt;
</content:encoded>

      </item><item>
        <title>Cloning RFID tags for fun and profit</title>
        <link>https://lessonsec.com/posts/cloning-rfid-tags-for-fun-and-profit/</link>
        <guid isPermaLink="true">https://lessonsec.com/posts/cloning-rfid-tags-for-fun-and-profit/</guid>
        <pubDate>Tue, 20 Apr 2021 16:27:00 &#43;0200</pubDate><description>RFID tags are a technology commonly used but not limited to industrial purposes. These systems are in fact used every day as public transport passes, as security token in access control systems or as a digital &amp;ldquo;bar code&amp;rdquo; in shops.</description>
	<content:encoded>&lt;p&gt;RFID tags are a technology commonly used but not limited to industrial purposes. These systems are in fact used every day as public transport passes, as security token in access control systems or as a digital &amp;ldquo;bar code&amp;rdquo; in shops.
Given the diffusion these tags have, it&amp;rsquo;s important to understand how they work and the security implication of their use.&lt;/p&gt;
&lt;blockquote&gt;
&lt;p&gt;Radio-frequency identification (RFID) uses electromagnetic fields to automatically identify and track tags attached to objects.&lt;br&gt;
An RFID system consists of a tiny radio transponder, a radio receiver and transmitter. When triggered by an electromagnetic interrogation pulse from a nearby RFID reader device,  the tag transmits digital data, back to the reader. - &lt;a href=&#34;https://en.wikipedia.org/wiki/Radio-frequency_identification&#34;&gt;Wikipedia&lt;/a&gt;&lt;/p&gt;
&lt;/blockquote&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/rfid/main.jpg&#34; alt=&#34;rfid tools&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;RFID tools&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;h3 id=&#34;whats-rfid&#34;&gt;What&amp;rsquo;s RFID?&lt;/h3&gt;
&lt;p&gt;RFID is a set of standards and technologies because it includes multiple frequency ranges such as:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;LF: 120–150 kHz&lt;/li&gt;
&lt;li&gt;HF: 13.56 MHz&lt;/li&gt;
&lt;li&gt;UHF: 433 MHz&lt;/li&gt;
&lt;li&gt;UHF: 865–868 MHz (Europe) 902–928 MHz (North America)&lt;/li&gt;
&lt;li&gt;microwave: 2450–5800 MHz&lt;/li&gt;
&lt;li&gt;microwave: 3.1–10 GHz&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;In practice, only tags operating in the LF range are commonly called RFID tags while tags operating in the HF range are called NFC tags.&lt;br&gt;
The rest are radio technologies not limited to the near field use (i.e. bluetooth).&lt;/p&gt;
&lt;p&gt;There&amp;rsquo;s a big difference between RFID and NFC tags and it hides in the specifications. They operate on different frequencies, use different protocols, offer different features and have different uses. Some RFID devices can be compatible with NFC readers, but that doesn&amp;rsquo;t mean that they strictly follow the NFC specs. Further considerations on the difference between these technologies are out of the scope of this article, but it&amp;rsquo;s important not to confuse the two.&lt;/p&gt;
&lt;p&gt;LF tags operate in the 120–150 kHz range, but the most commonly used frequencies are 125kHz for access control tags and 134kHz for uses like pet chips. Other frequencies can be used but the vast majority of tags use either 125kHz or 134kHz. Such low frequencies can limit the data transmission speed.&lt;/p&gt;
&lt;p&gt;RFID LF tags can be passive. This means that the tag is powered and interrogated by the reader. Or active, meaning that the tag is powered with a battery and that it continuously broadcasts data.
While active tags are used, they often have specific purposes. This article will focus on RFID LF passive tags since it&amp;rsquo;s the most common variant found in everyday life.&lt;/p&gt;
&lt;p&gt;RFID LF tags have poor transmission speed but are incredibly cheap to produce. Due to this, they are so widely employed where speed is not fundamental.
The reading distance of LF tags is usually better compared to HF reading distance. In fact, LF is referred as a vicinity technology, while HF is generally called a proximity technology.&lt;/p&gt;
&lt;p&gt;Industrial uses aside, one of the main uses of these tags is as access control tokens. It&amp;rsquo;s common to see these tags in form of badges or key fobs, and these can be used to access homes, offices or critical infrastructures.&lt;/p&gt;
&lt;p&gt;There are numerous models of RFID LF tags each with it&amp;rsquo;s specific features and peculiarities, but the use as a security token is not ideal for one main reason: RFID LF tags can be an insecure option. (note that are exceptions: some tags can employ a password or crypto mode, one of the very few examples are &lt;a href=&#34;https://www.nxp.com/products/rfid-nfc/hitag-lf:MC_42027&#34;&gt;Hitag2&lt;/a&gt; tags and these security measures &lt;a href=&#34;https://www.cs.bham.ac.uk/~tpc/isecsem/talks/EZ.pdf&#34;&gt;can still be circumvented&lt;/a&gt;!)&lt;/p&gt;
&lt;p&gt;In this article, we will see how it&amp;rsquo;s possible to read, write and clone these tags and learn about possible implications due to misuse of this technology.&lt;/p&gt;
&lt;h3 id=&#34;how-to-work-with-rfid-tags&#34;&gt;How to work with RFID tags&lt;/h3&gt;
&lt;p&gt;To work with RFID tags, specialized hardware is necessary.&lt;/p&gt;
&lt;p&gt;Different devices exist:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;Chinese cloners&lt;br&gt;
Simple devices that read from one tag and write on another.
Generally, these are hand-held, feature read and write buttons, and have a couple of status LEDs.
Some are more advanced than others and can feature a little screen.
Compatibility for frequencies and standards may vary, but these devices are usually good enough for simpler tasks.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;RFID Chameleon&lt;br&gt;
Developed to be used in RFID security assessments.
Doesn&amp;rsquo;t offer the most advanced features, but is designed to be used in the field, is battery powered and supports tag simulation and manipulation.
It is also programmable and you can use it with an app.&lt;/p&gt;
&lt;p&gt;It&amp;rsquo;s probably the best solution for a standalone use.&lt;br&gt;
More here: &lt;a href=&#34;https://kasper-oswald.de/gb/chameleonmini/&#34;&gt;https://kasper-oswald.de/gb/chameleonmini/&lt;/a&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Proxmark3&lt;br&gt;
As the website puts it: Proxmark is an RFID swiss-army tool.
It represents the state of the art when it comes to RFID research.
It allows interacting with the tags both high and low level.
Different versions have different features, including bluetooth support, battery packs,
swappable antennas and so on.&lt;/p&gt;
&lt;p&gt;It supports a standalone use, but it&amp;rsquo;s more powerful when connected to a PC.
It&amp;rsquo;s to be intended  as a research tool.&lt;br&gt;
More here: &lt;a href=&#34;https://www.proxmark.com/&#34;&gt;https://www.proxmark.com/&lt;/a&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Generic boards&lt;br&gt;
Other boards exist. These are usually sold as an Arduino add on, but dongles featuring
the same integrated circuits are available.
These are not widely used outside the makers world, but many are compatible with
&lt;a href=&#34;http://www.nfc-tools.org/index.php/Libnfc&#34;&gt;&lt;code&gt;libnfc&lt;/code&gt;&lt;/a&gt; and can be useful to perform simple to advanced operations.&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;The only device that I have available is a Proxmark3 easy (cheap Chinese version) so this
article will focus on its use. The underlying concepts about RFID tags should translate to other devices.&lt;/p&gt;
&lt;h3 id=&#34;tags-that-emulate-other-tags&#34;&gt;Tags that emulate other tags&lt;/h3&gt;
&lt;p&gt;When it comes to working with RFID LF tags, there&amp;rsquo;s one main player: the &lt;a href=&#34;http://ww1.microchip.com/downloads/en/DeviceDoc/Atmel-9187-RFID-ATA5577C_Datasheet.pdf&#34;&gt;T55xx&lt;/a&gt; tag&lt;/p&gt;
&lt;p&gt;They are a family of tags developed to emulate a wide range of regular tags.
This means that it&amp;rsquo;s possible to clone most of the RFID tags around using one of these
without having to carry writable cards for each and every tag model.&lt;/p&gt;
&lt;p&gt;This tag features 8 x 32 bit blocks in page 0 and 4 x 32 blocks in page 1.
Page 1 blocks are meant to be used for configuration purposes along with block 0 and 7 in page 0.
Blocks 1 to 6 in page 0 are dedicated to user data.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/rfid/t55xx.jpg#center&#34; alt=&#34;t55xx&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;T55xx memory layout&lt;br /&gt;Credit - Microchip ATA5577C datasheet&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;Of course, it&amp;rsquo;s possible to work directly on the configuration blocks, and this is what allows the emulation
of other type of tags, but doing so carelessly can easily lead to a brick!&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/rfid/bricked.jpg#center&#34; alt=&#34;bricked tag&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;Bricked T55xx&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;Original Atmel T5577 tags have a test mode and that can be helpful to recover soft-bricked cards.&lt;/p&gt;
&lt;h3 id=&#34;cloning-tags&#34;&gt;Cloning tags&lt;/h3&gt;
&lt;p&gt;Using the proxmark3 CLI, reading and writing devices is pretty straightforward.
First off you need to look for the device:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;[usb] pm3 --&amp;gt; lf search

[=] NOTE: some demods output possible binary
[=] if it finds something that looks like a tag
[=] False Positives ARE possible
[=] 
[=] Checking for known tags...
[=] 
[+] EM 410x ID 1122334455
[+] EM410x ( RF/64 )
[=] -------- Possible de-scramble patterns ---------
[+] Unique TAG ID      : 8844CC22AA
[=] HoneyWell IdentKey
[+]     DEZ 8          : 03359829
[+]     DEZ 10         : 0573785173
[+]     DEZ 5.5        : 08755.17493
[+]     DEZ 3.5A       : 017.17493
[+]     DEZ 3.5B       : 034.17493
[+]     DEZ 3.5C       : 051.17493
[+]     DEZ 14/IK2     : 00073588229205
[+]     DEZ 15/IK3     : 000585269781162
[+]     DEZ 20/ZK      : 08080404121202021010
[=] 
[+] Other              : 17493_051_03359829
[+] Pattern Paxton     : 289899093 [0x11478255]
[+] Pattern 1          : 5931804 [0x5A831C]
[+] Pattern Sebury     : 17493 51 3359829  [0x4455 0x33 0x334455]
[=] ------------------------------------------------

[+] Valid EM410x ID found!
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;The proxmark found an EM410x tag! We can now try to read it:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;[usb] pm3 --&amp;gt; lf em 410x reader
[+] EM 410x ID 1122334455
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Let&amp;rsquo;s try with another type of tag:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;[usb] pm3 --&amp;gt; lf search

[=] NOTE: some demods output possible binary
[=] if it finds something that looks like a tag
[=] False Positives ARE possible
[=] 
[=] Checking for known tags...
[=] 
[+] [H10301] - HID H10301 26-bit;  FC: 118  CN: 1603    parity: valid
[=] raw: 000000000000002006ec0c86

[+] Valid HID Prox ID found!
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;It&amp;rsquo;s an HID Prox tag, let&amp;rsquo;s try and read its ID:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;[+] [H10301] - HID H10301 26-bit;  FC: 118  CN: 1603    parity: valid
[=] raw: 000000000000002006ec0c86
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;And just like that we got the devices ID. That ID is the authentication token!
If we can write this token on a T55xx tag, we can emulate the card and possibly gain access
to a restricted perimeter.&lt;/p&gt;
&lt;p&gt;Let&amp;rsquo;s see how it&amp;rsquo;s done.&lt;br&gt;
First we need to get a T55xx tag and position it on the reader. When empty this device
can&amp;rsquo;t be found using &lt;code&gt;lf search&lt;/code&gt;, so we can make sure it&amp;rsquo;s a T55xx tag using the detect command:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;[usb] pm3 --&amp;gt; lf t55xx detect
[=]  Chip type......... T55x7
[=]  Modulation........ ASK
[=]  Bit rate.......... 2 - RF/32
[=]  Inverted.......... No
[=]  Offset............ 32
[=]  Seq. terminator... Yes
[=]  Block0............ 00088048 (auto detect)
[=]  Downlink mode..... default/fixed bit length
[=]  Password set...... No
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;The &lt;code&gt;lf t55 detect&lt;/code&gt; command is also necessary before using this tag because it detects the configuration in use and helps avoiding problems running other &lt;code&gt;lf t55&lt;/code&gt; commands.&lt;/p&gt;
&lt;p&gt;Now we can see the content of the device:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;[usb] pm3 --&amp;gt; lf t55xx dump
[+] Reading Page 0:
[+] blk | hex data | binary                           | ascii
[+] ----+----------+----------------------------------+-------
[+]  00 | 00088048 | 00000000000010001000000001001000 | ...H
[+]  01 | 00000000 | 00000000000000000000000000000000 | ....
[+]  02 | 00000000 | 00000000000000000000000000000000 | ....
[+]  03 | 00000000 | 00000000000000000000000000000000 | ....
[+]  04 | 00000000 | 00000000000000000000000000000000 | ....
[+]  05 | 00000000 | 00000000000000000000000000000000 | ....
[+]  06 | 00000000 | 00000000000000000000000000000000 | ....
[+]  07 | 00000000 | 00000000000000000000000000000000 | ....
[+] Reading Page 1:
[+] blk | hex data | binary                           | ascii
[+] ----+----------+----------------------------------+-------
[+]  00 | 00088048 | 00000000000010001000000001001000 | ...H
[+]  01 | E03900D0 | 11100000001110010000000011010000 | .9..
[+]  02 | C60337D7 | 11000110000000110011011111010111 | ..7.
[+]  03 | 00A00003 | 00000000101000000000000000000011 | ....
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Note that it&amp;rsquo;s possible to operate on single blocks too, but for the purpose of this article, it&amp;rsquo;s easier to dump the whole memory instead.&lt;/p&gt;
&lt;p&gt;We see that the card doesn&amp;rsquo;t contain user data. If it did, wiping the card with the &lt;code&gt;lf t55xx wipe&lt;/code&gt; command would be suggested.
We can now try and emulate tags on it!
To do that we only need to have the ID of the tags we want to emulate. We already saw how that&amp;rsquo;s done.&lt;/p&gt;
&lt;p&gt;We can now go ahead and clone the tags, let&amp;rsquo;s try the em410x first:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;[usb] pm3 --&amp;gt; lf em 410x clone --id 1122334455
[+] Preparing to clone EM4102 to T55x7 tag with ID 1122334455 (RF/64)
[#] Clock rate: 64
[#] Tag T55x7 written with 0xff8c65298c94a940
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Once the command is issued, we can read the device and verify that it emulates an em410x tag:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;[usb] pm3 --&amp;gt; lf em 410x reader
[+] EM 410x ID 1122334455
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Of course it&amp;rsquo;s still a T55xx tag (and the &lt;code&gt;detect&lt;/code&gt; command will tell you that) but it behaves exactly like and em410x.&lt;/p&gt;
&lt;p&gt;Now we can try with the HID Prox.&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;[usb] pm3 --&amp;gt; lf hid clone --r 000000000000002006ec0c86
[=] Preparing to clone HID tag using raw 000000000000002006ec0c86
[=] Done
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;And of course reading it reveals that we successfully cloned the tag:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;usb] pm3 --&amp;gt; lf hid reader
[+] [H10301] - HID H10301 26-bit;  FC: 118  CN: 1603    parity: valid
[=] raw: 000000000000002006ec0c86
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;We now have two key fob tags copied on T55xx cards!&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/rfid/cloned.jpg&#34; alt=&#34;cloned tags&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;Original and cloned tags&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;In this demo only HID Prox and em410x tags are examined, but it&amp;rsquo;s possible to clone and work with many more of these tags.&lt;/p&gt;
&lt;p&gt;Since it&amp;rsquo;s possible to emulate cards knowing the ID, we can clone some RFID LF cards &amp;ldquo;by sight&amp;rdquo; simply reading the ID printed to the device body.
This completely removes the limit of having to read the card with a specialized tool.
Some of these printed ID are &amp;ldquo;encoded&amp;rdquo; (or shifted by some value). This allows organizations to &amp;ldquo;decode&amp;rdquo; it, but prevents attackers from obtaining the ID by sight.&lt;/p&gt;
&lt;p&gt;At this point you might be wondering if it&amp;rsquo;s THAT easy to clone a tag in the real world, the answer is no. That&amp;rsquo;s for a simple reason, the tag is passive and if we use the standard antennas provided with whichever device, the reading range is limited to a few centimeters.&lt;/p&gt;
&lt;p&gt;Luckily, it&amp;rsquo;s possible to weaponize a bigger antenna! If we use a bigger and more powerful antenna, it&amp;rsquo;s possible to clone a LF tag from a usable distance. Of course the antenna will need to be powered by a big battery pack and carried in some kind of backpack or messenger bag, but that&amp;rsquo;s the price to pay.&lt;/p&gt;
&lt;p&gt;More here: &lt;a href=&#34;https://www.youtube.com/watch?v=wYmVtNQPlF4&#34;&gt;https://www.youtube.com/watch?v=wYmVtNQPlF4&lt;/a&gt;&lt;br&gt;
(NOTE: many other implementations exist!)&lt;/p&gt;
&lt;h3 id=&#34;defeating-password-protection&#34;&gt;Defeating password protection&lt;/h3&gt;
&lt;p&gt;When examining the T55xx tag, you may have noticed a parameter &amp;ldquo;Password set&amp;rdquo;. That&amp;rsquo;s because
this tag can be password protected!&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;[usb] pm3 --&amp;gt; lf t55xx protect -n 00001234
[=] Checking current configuration
[+] Wrote new password
[+] Validated new password
[+] Wrote modified configuration block
[!] ⚠️  Safety check: Could not detect if PWD bit is set in config block. Exits.
[?] Consider using the override parameter to force read.
[=] Block0 write detected, running `detect` to see if validation is possible
[=]  Chip type......... T55x7
[=]  Modulation........ ASK
[=]  Bit rate.......... 2 - RF/32
[=]  Inverted.......... No
[=]  Offset............ 33
[=]  Seq. terminator... Yes
[=]  Block0............ 000880F0 (auto detect)
[=]  Downlink mode..... default/fixed bit length
[=]  Password set...... Yes
[=]  Password.......... 00001234

[+] New configuration block 000880F0 password 00001234
[+] Success, tag is locked
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;At this point we can&amp;rsquo;t operate on this tag without knowing the password, for instance
the &lt;code&gt;detect&lt;/code&gt; command won&amp;rsquo;t work as expected:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;[usb] pm3 --&amp;gt; lf t55xx detect 
[!] ⚠️  Could not detect modulation automatically. Try setting it manually with &#39;lf t55xx config&#39;
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;But it does if the correct password is specified:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;[usb] pm3 --&amp;gt; lf t55xx detect -p 00001234
[=]  Chip type......... T55x7
[=]  Modulation........ ASK
[=]  Bit rate.......... 2 - RF/32
[=]  Inverted.......... No
[=]  Offset............ 33
[=]  Seq. terminator... Yes
[=]  Block0............ 000880F0 (auto detect)
[=]  Downlink mode..... default/fixed bit length
[=]  Password set...... Yes
[=]  Password.......... 00001234
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;Can we circumvent this? The simple answer is no.
The device is completely locked and without the password it&amp;rsquo;s impossible to do anything.&lt;/p&gt;
&lt;p&gt;Luckily the proxmark allows bruteforce attacks.&lt;/p&gt;
&lt;p&gt;While this type of attack works, it&amp;rsquo;s a really slow and instable method. This means it&amp;rsquo;s hard to try all the possible passwords before the connection drops. It may seem that the password protection is effective and that&amp;rsquo;s true if you don&amp;rsquo;t have the right tools. On the other hand, with quality reading devices and unlimited access to the target tag, success is granted.&lt;/p&gt;
&lt;p&gt;Here&amp;rsquo;s a demo on the tag we just password protected:&lt;/p&gt;
&lt;pre tabindex=&#34;0&#34;&gt;&lt;code&gt;[usb] pm3 --&amp;gt; lf t55xx bruteforce -s 00000000 -e FFFFFFFF
[=] press &#39;enter&#39; to cancel the command
[=] Search password range [00000000 -&amp;gt; FFFFFFFF]
.[=] Trying password 00000000
.[=] Trying password 00000001
.[=] Trying password 00000002
.[=] Trying password 00000003
.[=] Trying password 00000004
.[=] Trying password 00000005
.[=] Trying password 00000006
.[=] Trying password 00000007
.[=] Trying password 00000008
.[=] Trying password 00000009
.[=] Trying password 0000000A
.[=] Trying password 0000000B
.[=] Trying password 0000000C
.[=] Trying password 0000000D

[...]

.[=] Trying password 0000122D
.[=] Trying password 0000122E
.[=] Trying password 0000122F
.[=] Trying password 00001230
.[=] Trying password 00001231
.[=] Trying password 00001232
.[=] Trying password 00001233
.[=] Trying password 00001234
[=]  Chip type......... T55x7
[=]  Modulation........ ASK
[=]  Bit rate.......... 2 - RF/32
[=]  Inverted.......... No
[=]  Offset............ 33
[=]  Seq. terminator... Yes
[=]  Block0............ 000880F0 (auto detect)
[=]  Downlink mode..... default/fixed bit length
[=]  Password set...... Yes
[=]  Password.......... 00001234

[+] Found valid password: [ 00001234 ]
Downlink Mode used : default/fixed bit length

[+] time in bruteforce 1215 seconds
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;As you can see, it took ~20 minutes to crack a 4 hex digit password. It may seem to be a reasonable time but we must consider that the password can be double the length and that having access to the card for long periods of time is not always an option.&lt;/p&gt;
&lt;h3 id=&#34;attacks-on-rfid-readers&#34;&gt;Attacks on RFID readers&lt;/h3&gt;
&lt;p&gt;Finally, we can talk about attacks on the readers. There are two main attacks:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Tag simulation&lt;/li&gt;
&lt;li&gt;Data exfiltration&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;We saw that we can simulate a tag using the proxmark, but what if the ID we have read and simulated doesn&amp;rsquo;t have enough permission to grant us access somewhere?
In this scenario, it&amp;rsquo;s possible to use the read value as an upper limit to the ID space to research, and simulate every ID lower than that value hoping to find an ID with higher privileges. This attack is based on the assumption that lower IDs may have higher privileges because such privileges are associated with users registered earlier into the system, hence the lower ID value.
As for the bruteforce attack, this process may take a while, so it&amp;rsquo;s not always a usable technique.&lt;/p&gt;
&lt;p&gt;A sneakier way to get valid IDs is to install a device such as the &lt;a href=&#34;https://redteamtools.com/espkey&#34;&gt;ESPKey&lt;/a&gt; inside the reader.
This approach allows the interception of data directly from the wires and can harvest valid IDs.
Of course, this requires a physical access to the reader.&lt;/p&gt;
&lt;p&gt;Using the proxmark is also possible to sniff data from a tag to a reader.&lt;br&gt;
Given the antenna range, this is not a widely used technique and personally I haven&amp;rsquo;t tried it yet.&lt;/p&gt;
&lt;h3 id=&#34;conclusions&#34;&gt;Conclusions&lt;/h3&gt;
&lt;p&gt;This article shows how, with the right hardware, it is possible to clone RFID tags with relatively low skills.&lt;/p&gt;
&lt;p&gt;What&amp;rsquo;s scary is how easy it is to &amp;ldquo;steal&amp;rdquo; valuable credentials. In an access control context, a stolen ID constitutes a danger for a business because of the implications of a possible unauthorized entry into a critical infrastructure.&lt;/p&gt;
&lt;p&gt;Possible mitigations include using a stronger authentication mechanism and trainings on RFID security and how to keep access tokens safe. Simple precautions like using an RFID shield (test those! some doesn&amp;rsquo;t work!) and avoiding to keep a tag in sight can often be a huge improvement in access token security.&lt;/p&gt;
&lt;p&gt;A secure reader is also crucial. Some readers offer tamper detection mechanisms and actively try to detect and disable rewritable tags to avoid unauthorized entry.&lt;/p&gt;
&lt;p&gt;RFID credentials cloning can be one of the strongest tools in the arsenal of a physical penetration tester.&lt;/p&gt;
&lt;hr&gt;
&lt;p&gt;This article was reviewed by an external source, big thanks to them!&lt;/p&gt;
</content:encoded>

      </item><item>
        <title>Dev Chronicles: Creating an HTTP attack client</title>
        <link>https://lessonsec.com/posts/intrudo/</link>
        <guid isPermaLink="true">https://lessonsec.com/posts/intrudo/</guid>
        <pubDate>Thu, 01 Apr 2021 23:23:00 &#43;0200</pubDate><description>Intrudo is a tool for automating customized attacks against web applications loosely shaped after burp intruder.
        Intrudo logo    Check it out: https://github.</description>
	<content:encoded>&lt;p&gt;Intrudo is a tool for automating customized attacks against web applications loosely shaped after &lt;a href=&#34;https://portswigger.net/burp/documentation/desktop/tools/intruder&#34;&gt;burp intruder&lt;/a&gt;.&lt;/p&gt;
&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th style=&#34;text-align:center&#34;&gt;&lt;img src=&#34;https://lessonsec.com/images/intrudo/logo.png#center&#34; alt=&#34;intrudo logo&#34;&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&#34;text-align:center&#34;&gt;Intrudo logo&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p&gt;Check it out: &lt;a href=&#34;https://github.com/0xless/Intrudo&#34;&gt;https://github.com/0xless/Intrudo&lt;/a&gt;&lt;/p&gt;
&lt;h3 id=&#34;a-little-of-background&#34;&gt;A little of background&lt;/h3&gt;
&lt;p&gt;While working on CTFs I would usually write a bunch of lines of python to automate attacks, it worked fine, but I felt like I needed to improve my workflow. So I decided to learn new approaches and strengthen my use of commercial offensive tools.&lt;br&gt;
I have used burp suite in the past, but I have not taken the time to explore it thoroughly, so I figured the best way to do that would be the labs that &lt;a href=&#34;https://portswigger.net/web-security&#34;&gt;PortSwigger created for this reason&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;The idea of developing this tool came to me when working on SQL injection challenges. The labs and the learning material were great, but the throttling on the requests in burp intruder (community version only) was making it difficult to complete these challenges.  Due to the throttling, completing a challenge would take several hours since for every request sent, you have to wait more and more.&lt;/p&gt;
&lt;p&gt;Every challenge was focused on retrieving an administrative password, in some of these challenges a request needed to be sent for every possible letter and digit for each character of the password.  Now these challenges could be solved in two ways. You could either send requests to discover one character at time or try to automate it using the &amp;ldquo;cluster bomb&amp;rdquo; attack. In the first scenario, you&amp;rsquo;d have to adjust the parameters and manually launch the attack every 30 minutes or so. In the second scenario, you could automate the whole thing, if the challenge password didn&amp;rsquo;t change mid-attack because the client took so long to send the requests.&lt;/p&gt;
&lt;p&gt;One would assume these challenges were developed &lt;em&gt;specifically&lt;/em&gt; to make it harder to solve for those who didn&amp;rsquo;t have a paid version of the software. I&amp;rsquo;m not implying they have a malicious intent, but they could have made it easier for &lt;em&gt;everybody&lt;/em&gt; to solve the challenges and learn from the awesome materials they share.&lt;/p&gt;
&lt;p&gt;After my experience with PortSwigger&amp;rsquo;s labs, I decided to develop Intrudo; a fast, throttling free alternative to burp intruder.&lt;/p&gt;
&lt;h3 id=&#34;the-initial-approach&#34;&gt;The initial approach&lt;/h3&gt;
&lt;p&gt;My first idea was to use multithreading so I started surfing the web for ideas and found &lt;a href=&#34;https://docs.aiohttp.org/en/stable/&#34;&gt;aiohttp&lt;/a&gt;, and asynchronous HTTP Client/Server based on &lt;a href=&#34;https://docs.aiohttp.org/en/stable/glossary.html#term-asyncio&#34;&gt;asyncio&lt;/a&gt;. It wasn&amp;rsquo;t multithreading but it seemed perfect for this project.&lt;/p&gt;
&lt;p&gt;Unfortunately, I was not lucky with the choice of developing around &lt;code&gt;aiohttp&lt;/code&gt; as the client was strict on what requests can be sent and how they are sent.&lt;/p&gt;
&lt;p&gt;I learned this the hard way, of course. I spent a few days developing with &lt;code&gt;aiohttp&lt;/code&gt; and all I could achieve was an incredibly fast fuzzer that would only work on URL parameters. Big let down.&lt;/p&gt;
&lt;p&gt;At this point I could try two things:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;see if I could find some libraries I could fork&lt;/li&gt;
&lt;li&gt;implement my own client consisting of bare bones sockets and some good ol&#39; &lt;code&gt;asyncio&lt;/code&gt; magic&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id=&#34;the-wrong-way&#34;&gt;The wrong way&lt;/h3&gt;
&lt;p&gt;So I decided to try and modify some libraries first. It turns out every library that implements an HTTP client wants to ensure it is compliant and do so by thoroughly reviewing the data an user would want to send.
Usually these libraries make you specify method, URL, headers and body of the request separately.&lt;/p&gt;
&lt;p&gt;While this approach with HTTP complaint requests works well for standard clients and preventing errors, it is not flexible enough for this type of project.  This makes it incredibly hard to implement complex attack logic, work with headers and cookies and send non-HTTP compliant malformed data.&lt;/p&gt;
&lt;p&gt;After looking around, studying the HTTP protocol specifications and coding for a few hours, I was able to read some requests (non-chunked transfer encoding ones) and manage content compression!&lt;/p&gt;
&lt;p&gt;Well, to be completely honest, I borrowed and modified some code from &lt;a href=&#34;https://github.com/urllib3/urllib3/blob/main/src/urllib3/&#34;&gt;urllib3&lt;/a&gt; to handle the decompression.&lt;/p&gt;
&lt;p&gt;I did this for two reasons:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;the code is clean, simple and well tested&lt;/li&gt;
&lt;li&gt;someone has already considered aspects of the HTTP standard I didn&amp;rsquo;t even know existed&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Since &lt;code&gt;urllib3&lt;/code&gt; worked so well I decided to try and use as much code as I could.&lt;br&gt;
One tweak here and one tweak there and I got myself into completely modifying &lt;code&gt;urllib3&lt;/code&gt;&amp;hellip; Bad idea!&lt;br&gt;
&lt;code&gt;urllib3&lt;/code&gt; offers great client functionalities, but it&amp;rsquo;s too high level and wouldn&amp;rsquo;t let me work with &lt;code&gt;asyncio&lt;/code&gt; streams to read data.&lt;/p&gt;
&lt;p&gt;&lt;code&gt;urllib3&lt;/code&gt; requests are made by &lt;code&gt;http.client&lt;/code&gt;, a standard python library. So guess, what I tried next? You guessed correctly, I attempted to hack &lt;code&gt;http.client&lt;/code&gt; to work with &lt;code&gt;asyncio&lt;/code&gt;.
I knew from the beginning that it wasn&amp;rsquo;t a smart idea, and it turns out I was right: modifying the &lt;code&gt;http&lt;/code&gt; library to suit my needs is an hard task. &lt;code&gt;http.client&lt;/code&gt; would only read file-like objects and there was no way I could make it to use &lt;code&gt;asyncio&lt;/code&gt; streams (without rewriting a huge portion of the code, of course).&lt;/p&gt;
&lt;p&gt;If you can&amp;rsquo;t beat &amp;lsquo;em, join &amp;lsquo;em, right? So I decided to &amp;ldquo;transform&amp;rdquo; &lt;code&gt;asyncio&lt;/code&gt; streams into files with the hope &lt;code&gt;urllib3&lt;/code&gt; will come to like them.  At this point you may think: &amp;ldquo;&lt;em&gt;less, if you read the whole content of a socket, the client would not be asynchronous anymore!&lt;/em&gt;&amp;rdquo;, and my answer to that would be &lt;del&gt;&amp;quot;&lt;em&gt;mind your own business&lt;/em&gt;&amp;quot;&lt;/del&gt; &amp;ldquo;&lt;em&gt;we can manage sockets in some kind of spooled way!&lt;/em&gt;&amp;rdquo;. But of course that didn&amp;rsquo;t pan out.&lt;/p&gt;
&lt;p&gt;After a few hours of unsuccessful attempts, I decided to take a step back and code the whole client from scratch.&lt;/p&gt;
&lt;h3 id=&#34;the-right-way&#34;&gt;The right way?&lt;/h3&gt;
&lt;p&gt;I quickly realized it wasn&amp;rsquo;t as easy as I expected it to be, but I did find some &lt;a href=&#34;https://www.jmarshall.com/easy/http/&#34;&gt;well written documents&lt;/a&gt; that helped me better understand what I was I was looking for. So, the custom HTTP client adventure begins!&lt;/p&gt;
&lt;p&gt;I was able to put together some code I had already written and the decompression module from &lt;code&gt;urllib3&lt;/code&gt;. That resulted in an HTTP 1.0 semi-compliant client (it would have been nice if HTTP 1.0 was used anytime in history, but sadly it has not).
I want to make it HTTP 1.1 compliant to the extent that I need the client to be compliant, so the only thing missing would be to manage
&lt;code&gt;chunked transfer encoding&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;After avoiding this for a whole week, I realized it was easier than I expected. If I hadn&amp;rsquo;t wasted so much time trying to poke at the libraries, I probably would have had a nice piece of client already.
But you can&amp;rsquo;t cry over spilled milk, so let&amp;rsquo;s get back to work! After 1 hour of coding and 1 hour of debugging, I was able to achieve HTTP 1.1 compliance!&lt;/p&gt;
&lt;p&gt;And just like that &amp;ldquo;cliente&amp;rdquo; was born: a fully asynchronous, unrestricted, HTTP attack client. Simple yet effective.&lt;/p&gt;
&lt;h3 id=&#34;the-right-way-1&#34;&gt;The right way!&lt;/h3&gt;
&lt;p&gt;Everything seemed to work smoothly after the custom client was complete.
I implemented the payload position logics just like in burp intruder (pitchfork, sniper, cluster bomb and battering ram), it was not easy to work with two delimiters: I had to play around a little bit with &lt;code&gt;regex&lt;/code&gt; and had to work with payload position offsets given by the substitution of a text with a payload. To this day I&amp;rsquo;m sure there must be a better solution.&lt;/p&gt;
&lt;p&gt;After that I implemented a few simple callback mechanisms to manage, analyze and store incoming responses which match user specified criteria.&lt;/p&gt;
&lt;p&gt;It&amp;rsquo;s only a draft, but the very first version of Intrudo was complete!&lt;/p&gt;
&lt;p&gt;Here&amp;rsquo;s a little demo of the speed Intrudo can offer at the moment:&lt;/p&gt;
&lt;p&gt;&lt;img src=&#34;https://lessonsec.com/images/intrudo/demo.gif#center&#34; alt=&#34;intrudo demo&#34;&gt;&lt;/p&gt;
&lt;h3 id=&#34;what-i-learned&#34;&gt;What I learned&lt;/h3&gt;
&lt;p&gt;Of course the main takeaway is a deeper understanding of the HTTP protocol, especially when it comes to encodings and compression methods, since I  had to work with these directly.&lt;/p&gt;
&lt;p&gt;Working with raw HTTP requests was also the main challenge, ensuring that an user specified request is acceptable by the server was an hard task. Since there are no debug messages this process was based on a &amp;ldquo;try and fail&amp;rdquo; method and I had to read multiple rfc documents on the standard but I could complete this task, at least for the majority of servers I&amp;rsquo;ve experimented with.&lt;/p&gt;
&lt;p&gt;Another interesting thing I got from this project is a grasp of asynchronous programming. I had studied it in theory but learning a framework to actually write asynchronous programs is different thing.  &lt;code&gt;asyncio&lt;/code&gt; is a powerful tool I will be using in other projects.&lt;/p&gt;
&lt;p&gt;Finally I had to mess around with &lt;code&gt;regex&lt;/code&gt; and learned about greedy &lt;code&gt;regex&lt;/code&gt;. Handling the placeholder delimiters in the requests wasn&amp;rsquo;t straightforward and for the sake of performance (to avoid recomputing placeholder positions for each payload inserted) I had to develop a module that would insert the payload in the desired position considering the offsets from previously inserted payloads.&lt;/p&gt;
&lt;h3 id=&#34;to-be-continued&#34;&gt;To be continued&lt;/h3&gt;
&lt;p&gt;There are a few things that need to be done:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;The callbacks are not as complete as burp intruder ones.&lt;/li&gt;
&lt;li&gt;There is no payload generator (but that&amp;rsquo;s because Intrudo is to be used as a framework, not with a GUI).&lt;/li&gt;
&lt;li&gt;Some servers will always respond with &amp;ldquo;bad request&amp;rdquo; (can&amp;rsquo;t figure out why).&lt;/li&gt;
&lt;li&gt;Some serious testing is yet to be done.&lt;/li&gt;
&lt;li&gt;The timeout on requests is to be calculated with an adaptive function to optimize the throughput.&lt;/li&gt;
&lt;/ul&gt;
</content:encoded>

      </item>

  </channel>
</rss>
