第二届帕鲁杯wp by YHalo

RSA_Quartic_Quandary解题步骤:

rsa解密,需要p和q,我们可以设 p, q 为未知数,列方程组 p, q = symbols(‘p q’, integer=True) eq1 = Eq(p * q, n) eq2 = Eq(p4 + q4, s)来求解

解题脚本:
from Crypto.Util.number import long_to_bytes
from sympy import symbols, Eq, solve

# 直接赋值参数
n = 125997816345753096048865891139073286898143461169514858050232837657906289840897974068391106608902082960171083817785532702158298589600947834699494234633846206712414663927142998976208173208829799860130354978308649020815886262453865196867390105038666506017720712272359417586671917060323891124382072599746305448903
e = 65537
c = 16076213508704830809521504161524867240789661063230251272973700316524961511842110066547743812160813341691286895800830395413052502516451815705610447484880112548934311914559776633140762863945819054432492392315491109745915225117227073045171062365772401296382778452901831550773993089344837645958797206220200272941
s = 35935569267272146368441512592153486419244649035623643902985220815940198358146024590300394059909370115858091217597774010493938674472746828352595432824315405933241792789402041405932624651226442192749572918686958461029988244396875361295785103356745756304497466567342796329331150560777052588294638069488836419744297241409127729615544668547101580333420563318486256358906310909703237944327684178950282413703357020770127158209107658407007489563388980582632159120621869165333921661377997970334407786581024278698231418756106787058054355713472306409772260619117725561889350862414726861327985706773512963177174611689685575805282

# 设 p, q 为未知数,列方程组
p, q = symbols('p q', integer=True)
eq1 = Eq(p * q, n)
eq2 = Eq(p**4 + q**4, s)

# 求解 p, q
sol = solve((eq1, eq2), (p, q))
for _p, _q in sol:
  if _p > 1 and _q > 1:
      p, q = int(_p), int(_q)
      break

# 计算私钥 d
phi = (p - 1) * (q - 1)
d = pow(e, -1, phi)

# 解密
m = pow(c, d, n)
flag = long_to_bytes(m)
print(flag)

PositionalXOR解题步骤:

密文是 cipher = "qcoq~Vh{e~bccocH^@Lgt{gt|g"

Flag格式是 palu{},说明解密后的字符串里应该包含这个特征。

加密是基于“位置”的异或,也就是说:密文字符 = 明文字符 XOR 某个和字符位置相关的数

题目说“基于位置的异或”,所以密钥 K 是字符所在索引 i 的函数。

位置相关的key不一定简单线性,可能有偏移或倍数。写脚本穷举

解题脚本:
cipher = "qcoq~Vh{e~bccocH^@Lgt{gt|g"

def try_decrypt(cipher, key_func):
  n = len(cipher)
  plain_chars = []
  for i, c in enumerate(cipher):
      key = key_func(i, n)
      plain_c = chr(ord(c) ^ key)
      plain_chars.append(plain_c)
  return "".join(plain_chars)

def main():
  cipher = "qcoq~Vh{e~bccocH^@Lgt{gt|g"
  n = len(cipher)

  for start_i in [0, 1]:
      for offset in range(31): # 0 ~ 30
          for factor in range(1, 11): # 1 ~ 10

              plain = try_decrypt(cipher, lambda i, n: ((i + offset) * factor) % 256 if start_i == 0 else ((i + start_i + offset) * factor) % 256)
              if "palu{" in plain:
                  print(f"[+] Found flag! start_i={start_i}, offset={offset}, factor={factor}")
                  print(plain)
                  return

  print("[-] No flag found in tested key ranges.")

if __name__ == "__main__":
  main()

时间折叠(TimeFold Paradox)解题步骤:

观察题目的值,可以发现一个模式:

  • 每组高位值是 0x0 ~ 0x38,每次+0x10,像是一个线性递增的“时间”。
  • 每组低位保持在 8位(2字节)范围内,
  • 所以我们可以假设,这个“timestamp”其实是一个结构体编码:php-template
    <index (高位)> <byte (低位)>

我们从每个 timestamp 中提取低位两个 hex 数字,构造成一个字节流:

fe ef e2 fb f5 da e6 e7 fd d1 e7 fd d1 cf d1 dd ef e3 fe e2 eb d1 c8 e2 ef e9 d1 cd e6 ef e0 e9 eb d1 c3 eb af af f3

推测是某种简单加密或者编码:

比如XOR 解密

解题脚本:
data = bytes.fromhex("feefe2fbf5dae6e7fdd1e7fdd1cfd1ddefe3fee2ebd1c8e2efe9d1cde6efe0e9ebd1c3ebafaff3")

# 单字节 XOR 爆破
for k in range(256):
  decoded = bytes([b ^ k for b in data])
  if all(32 <= c <= 126 for c in decoded): # 可打印 ASCII
      print(f"Key: {k:02x} -> {decoded.decode()}")

然后在输出中找到Key: 8e -> palu{This_is_A_Sample_Flag_Change_Me!!}

TopSecret解题步骤:

看文件像base64加密,而palu的base64加密为cGFs,所以直接在文件中查找cGFs

找到疑似有重叠的密文 cGFsdXtZb3VfcmVfYV9yZWFsXzUwd30= cwPIy0wF54q32yv+WXlWo7yCCuyR4M7GeTEp1=JNLNUqPeYBNKHSOuLA0lV

base64解码得到palu{You_re_a_real_50w}

循环锁链解题步骤:

把文件放到010editor里面,提取出16进制,11 0D 19 0E 12 2A 74 42 31 2B 25 00 07 0C 16 39 27 21 03 00 28 0D 27 20 26 2C 19 00 0C 3B 04 39 22 19 52 44 0D

如果我们把题目“锁在了一个无尽的循环中”理解为:

每个明文字符是由密文当前字符与前一个明文字符 XOR 得到的

就像是:

vbnet复制编辑plaintext[0] = ciphertext[0] ^ key[0]
plaintext[i] = ciphertext[i] ^ plaintext[i - 1]

我们知道:

  • plaintext 以 palu{ 开头
  • 我们可以爆破密文的起点(旋转)
  1. 遍历所有偏移(rotate)
  2. 假设第一个明文字符是 p,根据密文推回 key 或前态
  3. 用链式 XOR 递推解出整个明文
  4. 找到符合 palu{ 开头和 } 结尾的内容
解题脚本:
ciphertext = [
  0x11, 0x0D, 0x19, 0x0E, 0x12, 0x2A, 0x74, 0x42, 0x31, 0x2B, 0x25, 0x00,
  0x07, 0x0C, 0x16, 0x39, 0x27, 0x21, 0x03, 0x00, 0x28, 0x0D, 0x27, 0x20,
  0x26, 0x2C, 0x19, 0x00, 0x0C, 0x3B, 0x04, 0x39, 0x22, 0x19, 0x52, 0x44,
  0x0D
]

known_prefix = "palu{"
known_ascii = [ord(c) for c in known_prefix]
n = len(ciphertext)

def is_printable(s):
  return all(32 <= ord(c) <= 126 for c in s)

for offset in range(n):
  rotated = ciphertext[offset:] + ciphertext[:offset]
  first_plain = ord('p')
  key = rotated[0] ^ first_plain

  plaintext = [first_plain]
  try:
      for i in range(1, n):
          next_char = rotated[i] ^ plaintext[i - 1]
          if not (0x20 <= next_char <= 0x7E):
              raise ValueError("non-printable")
          plaintext.append(next_char)

      decoded = ''.join(chr(c) for c in plaintext)
      if decoded.startswith(known_prefix) and "}" in decoded:
          flag = decoded[:decoded.index("}") + 1]
          print(f"Found flag at offset {offset}, key = {key:#x}")
          print(f"Flag: {flag}")
          break
  except:
      continue

轮回密码解题步骤:

题目附件实现了一个名为 samsara_encrypt 的加密函数,该函数使用了三步加密过程:

  1. 循环移位加密 :根据 key_word 的长度计算出一个循环步长 cycle_step ,然后对输入的 text 进行循环移位加密。具体来说,每个字节的高位和低位进行循环移位。
  2. Base85编码 :将第一步得到的字节序列进行Base85编码。这是一种将二进制数据编码为可打印字符的方式。
  3. 再次循环移位加密 :对Base85编码后的结果再次进行循环移位加密。
  4. 异或加密 :最后一步是将第三步的结果与 key_word 进行异或操作,得到最终的加密结果。

题目给了提示

密文:zQL0AmL5D2NvD2NuAQR6ZwZk

key;Bore

解题脚本:
import base64

def rotate_left(byte, steps):
  return ((byte << steps) & 0xFF) | (byte >> (8 - steps))

def samsara_decrypt(cipher, key_word):
  cycle_step = len(key_word) % 6 + 1

  # 异或密钥得到phase3
  phase3 = bytes([c ^ key_word[i % len(key_word)] for i, c in enumerate(cipher)])

  # phase3循环左移cycle_step位得到phase2
  phase2 = bytes([rotate_left(c, cycle_step) for c in phase3])

  # Base85解码得到phase1
  phase1 = base64.b85decode(phase2)

  # phase1循环左移cycle_step位得到明文
  plain = bytes([rotate_left(c, cycle_step) for c in phase1])

  return plain

cipher_str = "y¦•_•6•>X¬y•!,!n¡mS•aÜñüë•••9¼•6•"
cipher = cipher_str.encode('latin-1')
key = b"Bore"

# 解密
flag = samsara_decrypt(cipher, key)
print("解密结果:", flag.decode())

欧几里得解题步骤:

题目逻辑梳理

m1 = bytes_to_long(flag)
m2 = bytes_to_long(os.urandom(2) * 35)
c1 = Paillier_encode(m1, g, n)
c2 = Paillier_encode(m2, g, n)
print(Paillier_decode(c1 * c2, p, q, g, n))

这个语句 Paillier_decode(c1 * c2) 正好利用了 Paillier 的加法同态性

Paillier 有性质:

$$
E(m_1) \cdot E(m_2) \mod n^2 = E(m_1 + m_2 \mod n)
$$

所以:

Paillier_decode(c1 * c2) == m1 + m2  (mod n)

可以遍历所有可能的 x = os.urandom(2) 值,然后构造 m2_candidate = bytes_to_long(x * 35),接着:

m1_candidate = c - m2_candidate
尝试将 m1_candidate 转回 bytes,看是否是 flag 格式
解题脚本:
from Crypto.Util.number import long_to_bytes, bytes_to_long

c = 1426774899479339414711783875769670405758108494041927642533743607154735397076811133205075799614352194241060726689487117802867974494099614371033282640015883625484033889861

for i in range(0, 1 << 16): # 遍历所有 2 字节的可能
  x = i.to_bytes(2, 'big')
  m2 = bytes_to_long(x * 35)
  m1 = c - m2
  try:
      flag = long_to_bytes(m1)
      if b'palu' in flag:  
          print("Found!", flag)
          break
  except:
      continue

应急响应1 -1解题步骤:

查找日志

/var/log/nginx/access.log

access.log没数据,找access.log.1

遍历数据,找到可疑ip 192.168.31.240,因为它试图访问 /shell.php

所以得到flag:palu{192.168.31.240}

应急响应2-1解题步骤:

直接打开堡垒机,在留存日志处找到flag

palu{2025_qiandao_flag}

评论

  1. Macintosh Chrome
    3 天前
    2025-12-13 23:20:55

    It’s fascinating how easily accessible online gaming has become, but responsible play is key. Platforms like arion play app casino emphasize security, which is a good sign-important for both enjoyment & protection. Setting limits is smart!

发送评论 编辑评论


				
|´・ω・)ノ
ヾ(≧∇≦*)ゝ
(☆ω☆)
(╯‵□′)╯︵┴─┴
 ̄﹃ ̄
(/ω\)
∠( ᐛ 」∠)_
(๑•̀ㅁ•́ฅ)
→_→
୧(๑•̀⌄•́๑)૭
٩(ˊᗜˋ*)و
(ノ°ο°)ノ
(´இ皿இ`)
⌇●﹏●⌇
(ฅ´ω`ฅ)
(╯°A°)╯︵○○○
φ( ̄∇ ̄o)
ヾ(´・ ・`。)ノ"
( ง ᵒ̌皿ᵒ̌)ง⁼³₌₃
(ó﹏ò。)
Σ(っ °Д °;)っ
( ,,´・ω・)ノ"(´っω・`。)
╮(╯▽╰)╭
o(*////▽////*)q
>﹏<
( ๑´•ω•) "(ㆆᴗㆆ)
😂
😀
😅
😊
🙂
🙃
😌
😍
😘
😜
😝
😏
😒
🙄
😳
😡
😔
😫
😱
😭
💩
👻
🙌
🖕
👍
👫
👬
👭
🌚
🌝
🙈
💊
😶
🙏
🍦
🍉
😣
Source: github.com/k4yt3x/flowerhd
颜文字
Emoji
小恐龙
花!
上一篇
下一篇