ctf://events/kictf-2026/heart-beat

Heart Beat

Event KICTF 2026
Category Misc
Points 100
Status ✓ SOLVED

Heart Beat

Category: Misc Points: 100 Flag: KICTF{th15_15_pr1m3_t1m3}

Challenge Overview

We were given a looping GIF animation. The description mentioned:

  • 100 heartbeats
  • Each heartbeat is measured in 1/100th of a second
  • Some numbers "stand apart" in mathematics

This clearly hinted at prime numbers.

Step 1 – Verify Frame Count

We checked the number of frames using ImageMagick.

Step 2 – Extract Frame Delays

We extracted all frame delay values in milliseconds.

Step 3 – Use Prime Frame Positions

Prime numbers between 1 and 100: 2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31, 37, 41, 43, 47, 53, 59, 61, 67, 71, 73, 79, 83, 89, 97

We selected delay values at these prime positions, divided by 10, and converted to ASCII.

import subprocess

delays = subprocess.check_output(
    ["identify", "-format", "%T\n", "chall.gif"]
).decode().splitlines()

delays = list(map(int, delays))

def is_prime(n):
    if n < 2:
        return False
    for i in range(2, int(n**0.5) + 1):
        if n % i == 0:
            return False
    return True

primes = [i for i in range(1, 101) if is_prime(i)]

flag = ""
for p in primes:
    value = delays[p - 1] // 10
    flag += chr(value)

print(flag)

> Flag

KICTF{th15_15_pr1m3_t1m3}