南七星之家 发表于 2024-5-12 22:28:34

ctfshow刷题记录-cry方向-1

0x00

标题泉源:ctfshow 菜狗杯 crypto方向 base47
标题描述:
神必字符: E9CVT+HT5#X36RF4@LAU703+F$E-0N$@68LMXCVDRJJD5@MP#7MUZDTE?WWLG1S#L@+66H@59KTWYK8TW0RV
神必字典:
0123456789ABCDEFGHJKLMNPQRSTUVWXYZ?!@#$%^&*-+
0x01

第一次做这种base换表的标题,在网上查了查相干wp,感觉自己对base家族还不太熟悉,于是自己先用py写了个base64的加解密的脚本,代码如下:
string1 = "E9CV^T+HT5#X36RF4@LAU703+F$E-0N$@68LMXCVDRJJD5@MP#7MUZDTE?WWLG1S#L@+^66H@59KTWYK8TW0RV"
test_string = "abc123"
dict1 = "0123456789ABCDEFGHJKLMNPQRSTUVWXYZ?!@#$%^&*-+"


def base64_encode(test_string):
    dict2 = ("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/")# base64表
    temp_string = str()
    for i in test_string:# 字符->二进制ascii码, 放到temp_string里
      temp_string += bin(ord(i)).zfill(8)
    temp_list = list()
    if len(test_string) % 3 == 1:
      temp_string += "0000"
    if len(test_string) % 3 == 2:
      temp_string += "00"
    while temp_string!='':
      temp_list.append(temp_string)
      temp_string=temp_string
    fina_list = list()# 以这些6位的二进制数值查找base表,存到fina_list中
    for i in range(0, len(temp_list)):
      fina_list.append(dict2, 2)])
    fina_string = str()
    for i in fina_list:# 转化成字符串fina_string
      fina_string +=i
    if len(test_string) % 3 == 1:
      fina_string += "=="
    if len(test_string) % 3 == 2:
      fina_string += "="
    return fina_string

'''print("asfaegqfa123:", base64_encode("asfaegqfa123"), "YXNmYWVncWZhMTIz"==base64_encode("asfaegqfa123"))
print("asfaegqfa12:", base64_encode("asfaegqfa12"), "YXNmYWVncWZhMTI="==base64_encode("asfaegqfa12"))
print("asfaegqfa1231:", base64_encode("asfaegqfa1231"), "YXNmYWVncWZhMTIzMQ=="==base64_encode("asfaegqfa1231"))'''


def base64_decode(string):
    #dict2 = "0123456789ABCDEFGHJKLMNPQRSTUVWXYZ?!@#$%^&*-+"
    dict2="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"
    list2 = list(dict2)
    temp_string=str()
    if string[-1] == "=" and string[-2] == "=":
      string = string
    if string[-1] == "=" and string[-2] != "=":
      string = string
    for i in string:# 字符转二进制码
      temp_string+=str(bin(list2.index(i)).zfill(6))
    length=len(temp_string)
    if length%8==2:
      temp_string=temp_string
    if length%8==4:
      temp_string=temp_string
    fina_list=list()
    while temp_string!='':   #每八位分一组放入fina_list中
      fina_list.append(temp_string)
      temp_string=temp_string
    fina_string=str()
    for i in fina_list:
      fina_string+=chr(int(i,2))
    return fina_string

'''print("asfaegqfa123"==base64_decode("YXNmYWVncWZhMTIz"))
print("asfaegqfa12" == base64_decode("YXNmYWVncWZhMTI="))
print("asfaegqfa1231"==base64_decode(""))'''
`厥后问了问王师傅,基本明白了base的本质其实就是进制转换,每个字符串都对应一串256进制的数字(一个字符都是8bit,用ascii解码方式)   回过头来看标题,这个其实就是base45加密的字符串,思绪应该是密文中每个字符对应字典的下标这一串数字是len(字典)进制的,先转成10进制,再转ascii码字符串即可,脚本代码如下:
import libnum
cipher = "E9CV^T+HT5#X36RF4@LAU703+F$E-0N$@68LMXCVDRJJD5@MP#7MUZDTE?WWLG1S#L@+^66H@59KTWYK8TW0RV"
key = "0123456789ABCDEFGHJKLMNPQRSTUVWXYZ?!@#$%^&*-+"
sum=0
for i in range(len(cipher)):
    sum+=key.index(cipher)*pow(len(key),len(cipher)-1-i)
flag=libnum.n2s(sum)
print(flag)0x02

由这道题引发的思索,可不可以做一个base任意数字的编码,由上述原理写出了一个basexx加解密的脚本,代码如下:
import libnum
def base_xx_decode(cipher):
    # key为任意映射表
    # key = "0123456789ABCDEFGHJKLMNPQRSTUVWXYZ?!@#$%^&*-+"
    key = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"#base64表
    sum = 0
    for i in range(len(cipher)):
      sum += key.index(cipher) * pow(len(key), len(cipher) - 1 - i)#len(key)进制转10进制
    flag = libnum.n2s(sum)    #ascii值转字符串
    return flag
print(base_xx_decode("YWJjMTIz"))       # just an example=='abc123'

def base_xx_encode(plaintext):
    key = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"
    beichushu = libnum.s2n(plaintext)
    cipher=str()
    chushu = len(key)   #给chushu yushu shang beichushu赋初值然后辗转相除法进行10进制转len(key)进制,并直接映射到cipher里
    yushu = beichushu % chushu
    shang = beichushu // chushu
    beichushu = shang
    cipher += key
    while shang != 0:
      yushu = beichushu % chushu
      shang = beichushu // chushu
      beichushu = shang
      cipher += key
    cipher=cipher[::-1]
    return cipher
print(base_xx_encode("abc123"))# just an example   =='YWJjMTIz' 这个脚本只能加解密无添补规则且ascii编码的那种,比如base64就是无“=”

免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!更多信息从访问主页:qidao123.com:ToB企服之家,中国第一个企服评测及商务社交产业平台。
页: [1]
查看完整版本: ctfshow刷题记录-cry方向-1