• [Geek Challenge 2022] crypto部分


    这个比赛是一个网友让我看看的,这个比赛很有意思,crypto题全是百度网盘,pwn题全是谷歌网盘,这样我这pwn题就基本over了。还好这些crypto都不怎么难,都答出来了。最后成绩到10名了。

    w_or_m?

    第1个50分的题,还真不会,看来看去,由于flag头是SYC{所以可以找到一些线索We后是间隔3字符,前边(右边)是间隔4字符,看上去就是栅栏,根据字符猜就是welcome,然后猜第2行,与第1行方向相反。经网友提示是Rail Fence就是一种特殊的栅栏,前边被题目的说明zigzag误导了。这个好像真没啥关系。

    1. 0_cmdo1elfe_2_}WtoC!{0mr!C__7!YtepoS34
    2. ^ ^ ^ ^ ^ ^ ^ ^ <---从右向左
    3. c 1 e W { C Y S
    4. 0 m e _ t 0 _ t 3 <---从左向右
    5. d l 2 o m _ e <---右向左
    6. _ o f _ C r 7 p 4
    7. } ! ! ! o

    正确的应该解法是

    1. (1)倒序
    2. '0_cmdo1elfe_2_}WtoC!{0mr!C__7!YtepoS34'[::-1]
    3. '43SopetY!7__C!rm0{!CotW}_2_efle1odmc_0'
    4. (2)cyberchef->Rail Fence Cipher Decode
    5. Key:9
    6. Offset:27
    7. }!!!o4p7rC_fo_dl2om_e3t_0t_em0c1eW{CYS
    8. (3)倒序
    9. '}!!!o4p7rC_fo_dl2om_e3t_0t_em0c1eW{CYS'[::-1]
    10. 'SYC{We1c0me_t0_t3e_mo2ld_of_Cr7p4o!!!}'

     

    ez_classic

    题目给了个摩尔斯电码

    -../.-../.-./---/.--/---/-/.--./-.--/.-./-.-./---/.-../.-.././....

    解码后再反过来

    1. dlrowotpyrcolleh
    2. SYC{hellocryptoworld}

    definitely ez RSA

    一个标准的小指数攻击题e=6,m很小n很大

    1. from Crypto.Util.number import *
    2. import libnum
    3. flag = b'****hidden_message****'
    4. p = getPrime(512)
    5. q = getPrime(512)
    6. n = p * q
    7. e = 6
    8. m = libnum.s2n(flag)
    9. c = pow(m,e,n)
    10. print(c)
    11. print(n)
    12. '''
    13. *****************************************************
    14. c = 50072006338339389555118552154159240037219794211505206943873038914830972293138548550568229783754227896661905769853250134014183574039535969574789925550365619292404703617997980492432173682029840923107651199593049684918577536870537471401209938966780904496397505606866028917883152417396458811357069626629334483341
    15. n = 147194403642833538539720995718314310463580322118979932658805936518215523735242613107271741138837389303135352865058107054820876285524238471152015504027014461168105771913435200522726300893493981125032256531337768716089003105857799620333243431585087621669813946444872568719527503184655024233193716871553607529747
    16. *****************************************************
    17. '''

    解法就是直接开根号,不够开就加个n,因为6次一般情况不会溢出多少。

    1. from gmpy2 import iroot
    2. c = ...
    3. n = ...
    4. while True:
    5. v,k = iroot(c,6)
    6. if k:
    7. print(bytes.fromhex(hex(int(v))[2:]))
    8. break
    9. c +=n
    10. #SYC{0ops_y0u_f1Nd_m3!}
    11. '''
    12. R. = PolynomialRing(Zmod(n))
    13. f = x^6 - c
    14. f.monic()
    15. f.roots()
    16. '''

     

    Pairs

    给了一个密文:3tl2nv2zl2zl2zl4pg6gh5tr2z76kf2nt5zc56a6w0

    一共42字节,也要放到网盘上。有提示:hint: My twin brother send me a message.Can you decrypt it? 1、 Alice and Bob are twins of Hex

    一个twin-hex加密,直接找网站解

    StarterRSA

    又一个rsa的题,仅给了n,c,e但明显n非常小,可以直接分解

    1. n= 69984814757288857831977509185208500866724771756561629279687819301222483218728663
    2. e= 65537
    3. c= 67672845063517415442486175096448664617581579564885311842326107871805595697454701

    经过分解发现p是一个小因子,直接解rsa

    1. from gmpy2 import *
    2. from Crypto.Util.number import long_to_bytes
    3. n= 69984814757288857831977509185208500866724771756561629279687819301222483218728663
    4. e= 65537
    5. c= 67672845063517415442486175096448664617581579564885311842326107871805595697454701
    6. p = 733
    7. q = 95477237049507309456995237633299455479842799122185033123721445158557275878211
    8. phi = (p-1)*(q-1)
    9. d = invert(e, phi)
    10. m = pow(c,d,n)
    11. print(long_to_bytes(m))
    12. #SYC{5t4rt_R5A_ls_1t_3a5y?}

     

    Blind

    还是个rsa题,题目有点长,先是加密m得到c但n没有给出,后边两个paper提示是对p,q分别进行的rsa加密

    1. flag = b'xxxxxx'
    2. p = getPrime(1024)
    3. q = getPrime(1024)
    4. m = bytes_to_long(flag)
    5. n = p*q
    6. e = 65537
    7. c = pow(m,e,n)
    8. print('c={}'.format(c))
    9. p1 = getPrime(1024)
    10. q1 = getPrime(1024)
    11. n1 = p1*q1
    12. e1 = 65537
    13. assert gcd(e1,(p1-1)*(q1-1)) == 1
    14. c1 = pow(p,e1,n1)
    15. print('n1={}'.format(n1))
    16. print('c1={}'.format(c1))
    17. hint1 = pow(2022 * p1 + q1, 222222, n1)
    18. hint2 = pow(2023 * p1 + 232323, q1, n1)
    19. print('hint1={}'.format(hint1))
    20. print('hint2={}'.format(hint2))
    21. p2 = getPrime(1024)
    22. q2 = getPrime(1024)
    23. n2 = p2*q2
    24. e2 = 65537
    25. assert gcd(e1,(p2-1)*(q2-1)) == 1
    26. c2 = pow(q,e2,n2)
    27. hint3 = pow(2022 * p2 + 2023 * q2, 222222, n2)
    28. hint4 = pow(2023 * p2 + 2022 * q2, 232323, n2)
    29. print('n2={}'.format(n2))
    30. print('c2={}'.format(c2))
    31. print('hint3={}'.format(hint3))
    32. print('hint4={}'.format(hint4))

    这种曾经作过类似的也就没有难度了。第一步先对q1取模得到仅含p1的两个算式,将p1约掉后得到q1,再与n1取公约数得到q1,然后解Rsa得到p

    1. #p
    2. t1 = hint1 * pow(2022, -222222, n1) % n1
    3. t2 = (hint2 - 232323) * pow(2023,-1, n1) % n1
    4. q1 = gcd(t1 - pow(t2, 222222, n1) , n1)
    5. p1 = n1//q1
    6. phi1 = (p1 - 1)* (q1 - 1)
    7. d1 = invert(e, phi1)
    8. p = pow(c1, d1, n1)
    9. print(f'p = {p}')

     第2步同理得到q

    1. #q
    2. t3 = pow(hint3 * pow(2023, -222222, n2),232323,n2)
    3. t4 = pow(hint4 * pow(2022, -232323, n2),222222,n2)
    4. p2 = gcd(t3-t4, n2)
    5. q2 = n2//p2
    6. phi2 = (p2-1)*(q2-1)
    7. d2 = invert(e, phi2)
    8. q = pow(c2, d2, n2)
    9. print(f'q = {q}')

    最后由p,q得到m

    1. n = p*q
    2. phi = (p-1)*(q-1)
    3. d = invert(e, phi)
    4. flag = pow(c,d,n)
    5. print(long_to_bytes(flag))
    6. #The_key_I_am_white_Please_continue_decryting

     这时候还没完,flag.txt是维吉尼亚加密的,得到的是key:iamwhite,到网站上在线解得到

    1. #Key:iamwhite
    2. #密文(flag.txt文件): ayo{2ek_g0n_v3i11y_4ujk_bai_zisda_ig5amr}
    3. #SYC{2dz_y0a_s3a11y_4iiz_tnf_rigcp_at5xer}

    link_start

    又是一个rsa,两个m分别是m加上两个padding得到的,而padding已知,所以这个用关联信息

    1. from Crypto.Util.number import *
    2. flag = b'xxxxxxxxxx'
    3. m = bytes_to_long(flag)
    4. e = 3
    5. p = getPrime(256)
    6. q = getPrime(256)
    7. n = p * q
    8. pad1 = 105932791230388043786415766547423404991945041940365436758701967602353965252168
    9. pad2 = 927899423531845853332048235055407925992275378422616390929
    10. m1 = m + pad1
    11. m2 = m + pad2
    12. c1 = pow(m1,e,n)
    13. c2 = pow(m2,e,n)
    14. print("c1 =",c1)
    15. print("c2 =",c2)
    16. print("n =",n)
    17. '''
    18. c1 = 3720637940274958886432460233359341402765303073408436397771852426914390218432084755791424796944302399361378059153348441733368574505589165431342734218087692
    19. c2 = 1857483070190148986251195374434228339562792548542508665250465210130431058280559201968992393617573644598954953409645690993451979549050973992242158354491780
    20. n = 5106069782765072129956779902712742815006764735937158686628819801242945179548793829832666946413859309545558089370129318039174135569850663668730057188261837
    21. '''

    这个关联信息攻击有模板,只当个搬运工。

    1. def related_message_attack(c1,c2, di, e,n):
    2. from Crypto.Util.number import GCD
    3. #展开(x+a)^e的系数,杨辉三角
    4. def poly_coef(a, e):
    5. assert e >= 0
    6. if e == 0:
    7. return 1
    8. elif e == 1:
    9. return [1,1]
    10. else:
    11. res = [1]
    12. coe_prev = poly_coef(a, e-1)
    13. for i in range(len(coe_prev)-1):
    14. res.append(sum(coe_prev[i:i+2]))
    15. res.append(1)
    16. return res
    17. def poly_extend(a, e, n,c):
    18. coef = poly_coef(a, e)
    19. res = [a**i * coef[i] for i in range(len(coef))]
    20. res[-1] = res[-1] + c
    21. res = [x%n for x in res]
    22. return res
    23. #化首1
    24. def poly_monic(pl,n):
    25. from gmpy2 import invert
    26. for p in pl:
    27. if p!=0:
    28. inv = invert(p,n)
    29. break
    30. return [int((x*inv)%n) for x in pl]
    31. #模运算,这部分写的不是很好,待优化
    32. def poly_mod(pl1,pl2,n):
    33. from functools import reduce
    34. assert len(pl1) == len(pl2)
    35. pl1 = poly_monic(pl1,n)
    36. pl2 = poly_monic(pl2,n)
    37. for i in range(len(pl1)):
    38. if pl1[i] > pl2[i]:
    39. break
    40. elif pl1[i] < pl2[i]:
    41. return poly_mod(pl2,pl1,n)
    42. else:
    43. return 0
    44. idx = -1
    45. for i in range(len(pl1)):
    46. if pl1[i] == 1:
    47. idx = i
    48. break
    49. for i in range(idx,len(pl2)):
    50. if pl2[i] == 1:
    51. pl2 = pl2[:idx] + pl2[i:]
    52. pl2 += [0]*(len(pl1)-len(pl2))
    53. break
    54. res = []
    55. for i in range(len(pl1)):
    56. if pl2[i] == 0:
    57. res.append(pl1[i])
    58. else:
    59. res.append(pl1[i]-pl2[i])
    60. res = [int(x%n) for x in res]
    61. g = int(reduce(GCD,res))
    62. if g > 1:
    63. res = [x//g for x in res]
    64. return res
    65. #最大公因式
    66. def poly_gcd(pl1,pl2,n):
    67. while pl2 != 0:
    68. pl1,pl2 = pl2, poly_mod(pl1,pl2,n)
    69. pl1 = poly_monic(pl1,n)
    70. return pl1
    71. #x^e-c1
    72. #(x+di)^e-c2
    73. pl1 = poly_extend(0,e,n,-c1)
    74. pl2 = poly_extend(di,e,n,-c2)
    75. pl_d = poly_gcd(pl1,pl2,n)
    76. #求得(x-m),所以取负数即为m
    77. m = n - pl_d[-1]
    78. return m
    79. x = related_message_attack(c1, c2, pad2-pad1, e, n)
    80. bytes.fromhex(hex(x-pad2)[2:])
    81. #SYC{1_c4n_d0_th15_a1l_d@y}

     

    Long_But_Short

    终于走出rsa了,这里给出了q=p+1然后c = (m+p)**q %p 

    1. from Crypto.Util.number import *
    2. from secret import flag
    3. flag = bytes_to_long(flag)
    4. p = getPrime(1024)
    5. q = p+1
    6. assert flag**2 < p
    7. a = pow(flag+p, q, p)
    8. print('p=',p)
    9. print('a=',a)
    10. '''
    11. p= 132485702522161146757217734716447479208806639208543182360084149642567339473293168036770464973129405874692085101982109256055320486303869520189058357502693388509190430447787056423080714947904812339604787610679547711291646116182650401371922642011766279740399192613052280061981102203595808184804858315094410004923
    12. a= 1718205151527213531940354061216609955728503626623437131525315244599535856595391286686273033612529023037466615611832668265075325829196053041494716601943531710744433426780718569225
    13. '''

    根据费马小定理,先把这个q分成p-1+2,将p-1去掉,后边就剩个开平方了,模p的话flag+p=flag

    1. long_to_bytes(iroot(a,2)[0])
    2. #SYC{7ca905c9dbba1ffe7ff0ee3ee93f1ac1}

     

    just lcg

    这题目很长很长,但一看也没内容,已经一个很普通的式子运算

    1. import signal
    2. import socketserver
    3. import os
    4. import string, random
    5. from hashlib import sha256
    6. from secret import flag
    7. num = 1000
    8. class Task(socketserver.BaseRequestHandler):
    9. def _recvall(self):
    10. BUFF_SIZE = 2048
    11. data = b''
    12. while True:
    13. part = self.request.recv(BUFF_SIZE)
    14. data += part
    15. if len(part) < BUFF_SIZE:
    16. break
    17. return data.strip()
    18. def send(self, msg, newline=True):
    19. try:
    20. if newline:
    21. msg += b'\n'
    22. self.request.sendall(msg)
    23. except:
    24. pass
    25. def recv(self, prompt=b'[+]'):
    26. self.send(prompt, newline=False)
    27. return self._recvall()
    28. def close(self):
    29. self.send(b"Remember to solve me later~")
    30. self.request.close()
    31. def cal(self):
    32. from Crypto.Util.number import getRandomNBitInteger
    33. k = 2753645094
    34. n = 17968909282851700307
    35. c = getRandomNBitInteger(56)
    36. a = getRandomNBitInteger(36)
    37. b = (a * k + c) % n
    38. self.send(b'[+] k = ' + str(k).encode())
    39. self.send(b'[+] n = ' + str(n).encode())
    40. self.send(b'[+] a = ' + str(a).encode())
    41. self.send(b'[+] b = ' + str(b).encode())
    42. self.send(b'[+] b = (a * k + c) % n')
    43. self.send(b'Please give me c:')
    44. return self.recv(prompt=b'[+] c = ').decode() == str(c)
    45. def handle(self):
    46. for turn in range(num):
    47. if not self.cal():
    48. self.send(b"It's wrong. Please try again!")
    49. return
    50. else:
    51. self.send(b'Good job!')
    52. self.send(b'the encflag is = ' + str(flag).encode())
    53. class ThreadedServer(socketserver.ThreadingMixIn, socketserver.TCPServer):
    54. pass
    55. class ForkedServer(socketserver.ThreadingMixIn, socketserver.TCPServer):
    56. pass
    57. if __name__ == "__main__":
    58. HOST, PORT = '0.0.0.0', 80
    59. server = ForkedServer((HOST, PORT), Task)
    60. server.allow_reuse_address = True
    61. server.serve_forever()

    因为不知道它什么时候结束,只能读到爆为止

    1. from pwn import *
    2. p = remote('124.71.215.231', 2223)
    3. context.log_level = 'debug'
    4. def aaa():
    5. k = eval(p.recvline().split(b' = ')[1])
    6. n = eval(p.recvline().split(b' = ')[1])
    7. a = eval(p.recvline().split(b' = ')[1])
    8. b = eval(p.recvline().split(b' = ')[1])
    9. print(k,n,a,b)
    10. c = (b - a*k)%n
    11. p.sendlineafter(b'[+] c = ', str(c).encode())
    12. res = p.recvline()
    13. return b'Good' in res
    14. while True:
    15. aaa()
    16. '''
    17. [DEBUG] Received 0x92 bytes:
    18. b'[+] k = 2753645094\n'
    19. b'[+] n = 17968909282851700307\n'
    20. b'[+] a = 67398904367\n'
    21. b'[+] b = 5963091574066878625\n'
    22. b'[+] b = (a * k + c) % n\n'
    23. b'Please give me c:\n'
    24. b'[+] c = '
    25. 2753645094 17968909282851700307 67398904367 5963091574066878625
    26. [DEBUG] Sent 0x12 bytes:
    27. b'59522051419156197\n'
    28. [DEBUG] Received 0x4f bytes:
    29. b'Good job!\n'
    30. b"the encflag is = b'U1lDezEwMDBfTENHX0BuZF95MHVfa24wd18zaGVfZjFAZ30='\n"
    31. '''

    Anime picture

    一个非常长的程序

    1. from PIL import Image
    2. from Crypto.Util.number import *
    3. from numpy import array, zeros, uint8
    4. from random import randint
    5. from secret import x,y
    6. import cv2
    7. import hashlib
    8. import gmpy2
    9. def gen_key(a,b):
    10. key = ''
    11. for i in range(len(a)):
    12. if a[i] >= '1' and a[i] <= '9':
    13. key += '0'
    14. else:
    15. key += '1'
    16. for j in range(len(b)):
    17. if b[j] >= '1' and b[j] <= '9':
    18. key += '1'
    19. else:
    20. key += '0'
    21. return key
    22. def add(n):
    23. s = 0
    24. for i in range(0,len(n),2):
    25. s += int(n[i])
    26. return s
    27. image = cv2.imread("flag.jpg")
    28. img_array = array(image)
    29. dim1 = len(img_array)
    30. dim2 = len(img_array[0])
    31. dim3 = 3
    32. count = 0
    33. a = randint(1,2**64)
    34. b = randint(1,2**64)
    35. assert a * x + b * y == gmpy2.gcd(a, b)
    36. tmp_1 = hashlib.md5(str(x).encode('utf-8')).hexdigest()
    37. tmp_2 = hashlib.md5(str(y).encode('utf-8')).hexdigest()
    38. key = gen_key(tmp_1,tmp_2)
    39. for i in range(len(key)):
    40. if key[i] == '1':
    41. count += 1
    42. else:
    43. continue
    44. s = add(key)
    45. enc_img = zeros(shape=[dim1, dim2, dim3], dtype=uint8)
    46. for t in range(0,count):
    47. for i in range(0, dim1):
    48. for j in range(0, dim2):
    49. for k in range(0, dim3):
    50. enc_img[i][j][k] = (img_array[i][j][k] ^ (s + int(key)%3))
    51. s += 3
    52. enc_array = Image.fromarray(enc_img)
    53. enc_array.show()
    54. enc_array.save("encflag.jpg")
    55. print("a = ",a)
    56. print("b = ",b)
    57. '''
    58. a = 12071216147395236101
    59. b = 12613118707743158458
    60. '''

    题目长到不想看,就是把一个东西加密成写成图片,其实这跟图也没啥关系就是个数据。因为前边有md5然后再把数据变成01也基本不可逆。唯一办法就是爆破,不过对于jpg图来说,差点也没关系,大概能看出来就行,眼的容错率很高

    1. from PIL import Image
    2. from Crypto.Util.number import *
    3. from numpy import array, zeros, uint8
    4. import cv2
    5. import hashlib
    6. import gmpy2
    7. '''
    8. tmp_1 = hashlib.md5(str(x).encode('utf-8')).hexdigest()
    9. tmp_2 = hashlib.md5(str(y).encode('utf-8')).hexdigest()
    10. key = gen_key(tmp_1,tmp_2)
    11. for i in range(len(key)): #根据key计算count MD5 64位16进制 count<128
    12. if key[i] == '1':
    13. count += 1
    14. else:
    15. continue
    16. s = add(key)
    17. enc_img = zeros(shape=[dim1, dim2, dim3], dtype=uint8)
    18. for t in range(0,count):
    19. for i in range(0, dim1):
    20. for j in range(0, dim2):
    21. for k in range(0, dim3):
    22. enc_img[i][j][k] = (img_array[i][j][k] ^ (s + int(key)%3))
    23. s += 3
    24. '''
    25. image = cv2.imread("encflag.jpg")
    26. img_array = array(image)
    27. dim1 = len(img_array)
    28. dim2 = len(img_array[0])
    29. dim3 = 3
    30. #s<64
    31. ps = 0
    32. for key_3 in range(1):
    33. for count in range(128):
    34. for s in range(64):
    35. ps = s
    36. enc_img = zeros(shape=[dim1, dim2, dim3], dtype=uint8)
    37. for t in range(0,count):
    38. for i in range(0, dim1):
    39. for j in range(0, dim2):
    40. for k in range(0, dim3):
    41. enc_img[i][j][k] = (img_array[i][j][k] ^ (s + key_3))
    42. s += 3
    43. enc_array = Image.fromarray(enc_img)
    44. enc_array.save(f"./img/f{key_3}_{count}_{ps}.jpg")
    45. #SYC{not_n1c0_Nico_n1_1t_i5_l0velive}

     这个程序会生成很多图片,每过一段就会越来越清楚,比较清楚的就能看到flag

     

    Crypto1957

    最后几个题干脆名字都没有了。这个把flag与密文异或

    1. from Crypto.Util.number import *
    2. from flag import flag
    3. key = bytes_to_long(flag)
    4. f = open('message.txt','r').read().split('\n')
    5. cipher = open('cipher.txt','w')
    6. for i in f:
    7. i = bytes_to_long(i.encode())
    8. c = i ^ key
    9. cipher.write(hex(c)[2:]+'\n')
    10. cipher.close()

    好像也没有好办法,前一段作一题叫snake就是一个个字母猜,开头有4个已知SYC{拿这个异或后得到一堆数据

    1. 0 b'The '
    2. 1 b'd by'
    3. 2 b'cord'
    4. 3 b' by '
    5. 4 b'sinc'
    6. 5 b' if '
    7. 6 b'5 de'
    8. 7 b'rota'
    9. 8 b'e el'
    10. 9 b'put '
    11. 10 b'ol s'
    12. 11 b'le f'
    13. 12 b' its'
    14. 13 b' is '
    15. 14 b'd as'
    16. 15 b'"lea'
    17. 16 b'ying'
    18. 17 b' in '
    19. 18 b'et w'
    20. 19 b'f th'
    21. 20 b'four'
    22. 21 b' tar'
    23. 22 b'n an'
    24. 23 b' fro'
    25. 24 b' mis'
    26. 25 b'ngle'
    27. 26 b'ptio'
    28. 27 b' ang'

     这里可以猜的字符很多,比如19行猜是the,14行后边可能是空格,这样用程序辅助一个个猜。单词猜中的面还是比较大的,而且越往后越容易。

    1. c = open('cipher.txt','r').read().split()
    2. a = [bytes.fromhex(i) for i in c[:-1]]
    3. #print(a)
    4. flag = b'SYC{' #b'SYC{A1m9_1nfr4r3d_guid4nc3}'
    5. flag+= bytes([a[19][len(flag)]^ord('e')])
    6. print(flag)
    7. for i,v in enumerate(a):
    8. print(i, bytes([v[j]^flag[j] for j in range(len(flag))]))

    Crypto20xx

    给了c和一个缺两位的公钥

    1. -----BEGIN PUBLIC KEY-----
    2. MC??DQYJKoZIhvcNAQEBBQADGwAwGAIRAIO444FSJFXBf/yDN67IcCMCAwZpnQ==
    3. -----END PUBLIC KEY-----
    4. c = 85806005072257465677925369913039323947

    因为就差两位,基本上就等于直接给了,爆破出来就行,而且公钥非常小,很容易分解

     

    1. from Crypto.PublicKey import RSA
    2. from Crypto.Cipher import PKCS1_OAEP
    3. from Crypto.Util.number import long_to_bytes
    4. from gmpy2 import invert
    5. a = 'MC??DQYJKoZIhvcNAQEBBQADGwAwGAIRAIO444FSJFXBf/yDN67IcCMCAwZpnQ=='
    6. b64s = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/'
    7. for i in b64s:
    8. for j in b64s:
    9. c = a[:2]+i+j+a[4:]
    10. kstr = "-----BEGIN PUBLIC KEY-----\n"+c+"\n-----END PUBLIC KEY-----\n"
    11. try:
    12. f = kstr.encode()
    13. pub = RSA.importKey(f)
    14. print('n,e=',pub.n,',',pub.e)
    15. except:
    16. pass
    17. c = 85806005072257465677925369913039323947
    18. n,e= 175088864422629078008785584658147995683 , 420253
    19. p = 12865536769562115787
    20. q = 13609137928614252809
    21. phi = (p-1)*(q-1)
    22. d = invert(e,phi)
    23. m = pow(c,d,n)
    24. print(long_to_bytes(m))
    25. #Panzer_Vor!
    26. #SYC{Panzer_Vor!}

    Crypto1976

    这个题给了个远程,就是算 e=(r*h+p)%q 的p,其中e,h,q已知

    1. import signal
    2. from Crypto.Util.number import *
    3. import gmpy2 as gp
    4. import random
    5. import hashlib
    6. from secret import flag
    7. def gen(self,bound):
    8. q=getPrime(bound)
    9. bound1=int(gp.iroot(q//2,2)[0])
    10. bound2=int(gp.iroot(q//4,2)[0])
    11. while True:
    12. f,g=random.randint(1,bound1),random.randint(bound2,bound1)
    13. if gp.gcd(f,q*g) == 1 :
    14. break
    15. h=(gp.invert(f,q)*g)%q
    16. return q,h,f,g
    17. def gen_m(self,bound):
    18. p=getPrime(gp.iroot(bound//4,2)[0])
    19. p_=long_to_bytes(p)
    20. hash=hashlib.md5()
    21. hash.update(p_)
    22. return p,hash.hexdigest()
    23. def dec(self,e,f,g,q):
    24. a=f*e%q
    25. b=gp.invert(f,g)*a%g
    26. return b
    27. def check(self,rec,hash):
    28. hash_=hashlib.md5()
    29. hash_.update(rec)
    30. if hash == hash_.hexdigest():
    31. return 1
    32. else:
    33. return 0
    34. signal.alarm(60)
    35. bound=1024
    36. f=1
    37. for i in range(50):
    38. q,h,f,g=gen(bound)
    39. p,hash=gen_m(bound)
    40. r=getPrime(bound//2)
    41. e=(r*h+p)%q
    42. print(b'q= '+f'{q}'.encode()+b'\n'+b'h= '+f'{h}'.encode()+b'\n'+b'e= '+f'{e}'.encode()+b'\n')
    43. rec = input(b'Input md5 p: ')
    44. if rec.decode() == hash:
    45. print(b'YES!')
    46. continue
    47. else:
    48. print(b'NO!')
    49. f=0
    50. break
    51. if f :
    52. print(flag)

    这个题是一个很标准的NRTU,也就是求最短向量问题(SVP),先前存了个模板,直接套就行了。

    1. from pwn import *
    2. import hashlib
    3. from Crypto.Util.number import long_to_bytes
    4. io = remote('124.71.215.231', 1145)
    5. context.log_level = 'debug'
    6. def get_v():
    7. #c = rh + m mod p
    8. p = eval(io.recvline().split(b'= ')[1])
    9. h = eval(io.recvline().split(b'= ')[1])
    10. c = eval(io.recvline().split(b'= ')[1])
    11. print(p,h,c)
    12. M = matrix(ZZ, [[1,h],[0,p]])
    13. f,g = shortest_vector = M.LLL()[0]
    14. if f<0:
    15. f = -f
    16. if g<0:
    17. g = -g
    18. a = f*c % p % g
    19. m = a * inverse_mod(f, g) % g
    20. print('m = ', m)
    21. hs = hashlib.md5()
    22. hs.update(long_to_bytes(m))
    23. v = hs.hexdigest()
    24. print('v = ', v)
    25. io.sendlineafter(b'Input md5 p: ', v.encode())
    26. io.recvline()
    27. for i in range(50):
    28. get_v()
    29. print(p.recvline())

     

    Crypto1985

    这题以前没遇到过LWE问题有提示,网友给了搜到的贴子

    1. from Crypto.Util.number import *
    2. import gmpy2 as gp
    3. from secret import flag
    4. m = 132
    5. n = 400
    6. p = 3
    7. q = 2^20
    8. def gen_mat():
    9. return matrix(ZZ, [[q//2 - randrange(q) for _ in range(n)] for _ in range(m)])
    10. rp,rq = getPrime(m*3),getPrime(400)
    11. sp,sq = bin(rp)[2:] ,bin(rq)[2:]
    12. A, B, C = gen_mat(), gen_mat(), gen_mat()
    13. x = vector(ZZ, [int(sp[i]) for i in range(0,m)])
    14. y = vector(ZZ, [int(sp[i]) for i in range(m,2*m)])
    15. z = vector(ZZ, [int(sp[i]) for i in range(2*m,3*m)])
    16. e = vector(ZZ, [int(i) for i in sq])
    17. c = x*A+y*B+z*C+e
    18. flag = bytes_to_long(flag)
    19. n = rp * rq
    20. re=65537
    21. h = gp.powmod(flag,re,n)
    22. print('A = \n',A)
    23. print('B = \n',B)
    24. print('C = \n',C)
    25. print('c = ',c)
    26. print('h = ',h)
    27. print('n = ',n)
    28. #

    把p(396位)分成3段,分别乘上个随机矩阵,然后加一起再加上q,这里q分成位0和1,对于LWE就是那个误差,解法直接套。p这396位先合到一起,组成矩阵,ABC合到一起,求出误差e来取前400位就是q

    1. from text import *
    2. #A,B,C,c
    3. M = matrix(ZZ, 0, 400)
    4. for t in [A,B,C]:
    5. for r in t:
    6. M = M.stack(vector(r))
    7. c = matrix(ZZ, c)
    8. # c = X*M + e
    9. z = matrix(ZZ, [0 for _ in range(396)]).transpose()
    10. beta = matrix(ZZ, [1])
    11. T = block_matrix([[M, z], [matrix(c), beta]])
    12. L = T.LLL()
    13. print(L[0])
    14. #e = (1, 0, 0, 0, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0, 1, 1, 1, 0, 0, 1, 1, 0, 0, 0, 1, 0, 1, 0, 1, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1, 0, 1, 1, 1, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 0, 1, 0, 0, 1, 0, 1, 1, 0, 1, 0, 0, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 0, 0, 0, 0, 1, 0, 1, 0, 1, 0, 0, 1, 0, 1, 1, 1, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 0, 1, 0, 1, 1, 0, 0, 0, 0, 0, 1, 1, 0, 1, 0, 1, 1, 0, 1, 1, 1, 0, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 1, 0, 0, 1, 1, 1, 0, 0, 1, 1, 0, 0, 0, 1, 0, 1, 0, 0, 1, 0, 1, 0, 0, 1, 1, 1, 1, 0, 0, 1, 0, 1, 1, 0, 1, 0, 0, 1, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 1, 1, 0, 1, 1, 0, 1, 1, 0, 1, 1, 1, 0, 0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 0, 1, 0, 0, 0, 1, 0, 1, 1, 1, 1, 1, 0, 0, 1, 0, 1, 1, 1, 0, 1, 0, 1, 0, 0, 1, 1, 0, 1, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 1, 1, 0, 0, 0, 1, 1, 0, 1, 1, 0, 1, 0, 0, 0, 1, 1, 1, 1, 1, 0, 1, 0, 0, 1, 1, 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 1, 0, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0, 1, 0, 1, 1, 1, 1, 0, 1, 1, 1, 1)
    15. q = int(''.join([str(i) for i in L[0][:400]]), 2)
    16. p = n//q
    17. m = pow(h,inverse_mod(65537,(p-1)*(q-1)),n)
    18. print(bytes.fromhex(hex(m)[2:]))
    19. #{afb65e240bf2b8c5d67756967e2ec2d6}
    20. #SYC{afb65e240bf2b8c5d67756967e2ec2d6}

  • 相关阅读:
    【Webpack】样式处理 - 样式预处理
    【操作系统 | Linux】终端切换与帮助命令
    axios.js get 请求 生成参数的方法,兼容golang gin
    R语言统计分析:bootstrap方法
    JS简易计算器
    云之道知识付费v1.5.4小程序+前端(含pc付费插件)
    方形平板振动克拉尼图形可视化计算MATLAB程序(Chladni Patterns)
    分布式系统中的经典思想实验——两将军问题和拜占庭将军问题
    【python】eval函数
    聊聊 GPU 产品选型那些事
  • 原文地址:https://blog.csdn.net/weixin_52640415/article/details/127977121