南邮-NCTF2022 WRITE UP

前言

首先恭喜zysgmzb师傅荣获最想暴打的出题人荣誉,不得不说zys师傅出的misc题的质量确实高!学习!

Signin

程序设计实验作业,但是签到题(听zys说建议把终端字体调小一点并且只需要输入一串来自35年前的神秘秘籍

根据题目描述找到神秘秘籍上上下下左右左右ba,直接输入后得到flag

image-20221205082611518

image-20221205075828428

NCTF{VVelc0m3_T0_NCTF_2022!!!}

只因因

这是什么只因因

得到一个txt

You have the following sequence reads from a genomic clone of the Homo sapiens genome:
Read 1: ATGCGATCTGTGAGCCGAGTCTTTA
Read 2: AACAAAAATGTTGTTATTTTTATTTCAGATG
Read 3: TTCAGATGCGATCTGTGAGCCGAG
Read 4: TGTCTGCCATTCTTAAAAACAAAAATGT
Read 5: TGTTATTTTTATTTCAGATGCGA
Read 6: AACAAAAATGTTGTTATT

Use these six sequence reads to create a sequence contig of this part of the H. sapiens genome.
Go to the BLAST page (http://www.ncbi.nlm.nih.gov/BLAST/) and see if you can identify the gene of which this sequence is a part.

flag内容为查询到的基因名称简写的md5值,包上NCTF{}提交。

根据txt描述在网站的nucleotide blast去搜核苷酸序列

image-20221203190506042

结果翻译一下,有好多智人,都是CFTR基因的片段

image-20221203190534792

md5(CFTR)

NCTF{254e72a3768938792446548561412d43}

qrssssssss

有什么东西掩盖住了zys的双眼,好像在给他指明方向!(flag括号内的内容只有26位)

打开得到一堆二维码

image-20221205083211178

脚本批量读取二维码数据

image-20221203161453489

# -*- coding: utf-8 -*-

from PIL import Image
import pyzbar.pyzbar as pyzbar
import os

def qrcode_parse_content(img_path):
    '''
    单张图片的二维码解析
    '''
    img = Image.open(img_path)

    #使用pyzbar解析二维码图片内容
    barcodes = pyzbar.decode(img)

    #打印解析结果,从结果上可以看出,data是识别到的二维码内容,rect是二维码所在的位置
    # print(barcodes)
    # [Decoded(data=b'http://www.h3blog.com', type='QRCODE', rect=Rect(left=7, top=7, width=244, height=244), polygon=[Point(x=7, y=7), Point(x=7, y=251), Point(x=251, y=251), Point(x=251, y=7)])]

    result = []
    for barcode in barcodes:
        barcode_content = barcode.data.decode('utf-8')
        result.append(barcode_content)
   
    return result

def load_imgs(folder):
    '''
    加载文件夹下的图片
    '''
    imgs = []
    for img_path in os.listdir(folder):
        ext = os.path.splitext(img_path)
        if len(ext) > 1 and is_img(ext[1]):
            imgs.append(img_path)

    return imgs

def is_img(ext):
    '''
    判断文件后缀是否是图片
    '''
    ext = ext.lower()
    if ext == '.jpg':
        return True
    elif ext == '.png':
        return True
    elif ext == '.jpeg':
        return True
    elif ext == '.bmp':
        return True
    else:
        return False

if __name__ == "__main__":

    imgs = load_imgs('./') # 打开图片文件夹,我这里是当前程序运行目录
    contents = []
    # for img in imgs:
    #     contents.extend(qrcode_parse_content(img))
    #     print( img)
    # file = './result.txt' # 写入文件路径,我这里程序当前运行目录下的result.txt
    # with open(file,'w',encoding='utf-8') as f:
    #     for c in contents:
    #         f.write(c + '\n')
    for img in imgs:
        print(qrcode_parse_content(img)[0],end='')
e1b19411bCT3ef91e-T6--5115-b-eNe5-01e-1-0}1a15-0e91e50N15-eTa3-0e}8bC16ee11feeeeb7{ae1eeNbC7Ta1T-5bFb--398a515-NbTfbb-8-7ef-}0C-Te4eF501f{6a51e4be--5-Fb0}Fb-5{b97ef8a-{fa11bC9fee-3-e9N{1-51T1NN01C41883{577-1e-T1603{C{-17-NNeC0f-0C39711514{9117F--6-F-e05a7517C3b4-F{F71f}-1fe70-34-{7805C}b{bCf1f-aT{e3aFe-f-0bT6C17000N78e-76}af7-}4N-907}03187b113T9eaeF--13ebeN71b-C9Te1eF-680-468675F17410674N910F51b1511--80FF565165-19}beT}N17N-1758e-}1a8-4C-0057e-5b7b0}5}{7eaN-{-b}36b}7eb0-606{15b4b01971T-59388-Te351eFC044417af

通过字频统计发现应该是16个flag打乱了顺序

image-20221203161518097

一开始没有思路,后来revenge给了纠错级别LMQH的提示

image-20221205083600011

结合flag内容26位的提示,加上NCTF{}刚好32位,猜测字符位置对应32种纠错类型

测试了几个发现NCTF刚好对应L1,L2,L3,L4

由于网上没有找到读取纠错类型的脚本,只能配合QRbox疯狂手搓一小时

image-20221203161408826

  • 一个非预期

    可以直接根据图片生成的时间戳来爆破

赛后复现

预期解确实没有现成的函数可以直接识别,用python读取二维码纠错的数据块,识别纠错类型

image-20221205085504530

from PIL import Image
from pyzbar.pyzbar import decode
import os

def maskanalysis(img):
	sign=''
	for ii in range(510,670,20):
		pi=img.getpixel((ii,170))
		if(pi==0):
			sign+='1'
		if(pi==255):
			sign+='0'
	return sign

def scanqr(img):
	decocdeQR = decode(img)
	return decocdeQR[0].data.decode('ascii')

qrlist=os.listdir(r"C:\Users\22826\Desktop\qrssssssss_revenge")
flag=[0]*32
masklist=['11000100','11110011','10101010','10011101','00101111','00011000','01000001','01110110','00010010','00100101','01111100','01001011','11111001','11001110','10010111','10100000','01011111','01101000','00110001','00000110','10110100','10000011','11011010','11101101','10001001','10111110','11100111','11010000','01100010','01010101','00001100','00111011']
for i in qrlist:
	img=Image.open(r"C:\Users\22826\Desktop\qrssssssss_revenge\{}".format(i))
	qrmask=maskanalysis(img)
	for j in range(32):
		if(masklist[j]==qrmask):
			flag[j]=scanqr(img)

print(''.join(flag))
NCTF{737150-eeb-465-e91-110a8fb}

qrssssssss_revenge

同样思路如上题,只是把时间的非预期给去掉了

NCTF{62130783efd44b3692b4ddbecf}

炉边聚会

听说炉石传说快关服了,zys很难过,决定在最后的时间里再组一套卡组玩玩,你能找到藏在里面的flag吗?

打开得到一串base64,根据题目描述搜索发现是炉石的卡组代码

AAEDAZoFKIwGngXIBrwFzgnQBfIHygf0CIgJkAi+BogJ1gjMCPIHtgeeBeAD6AfyB7YHvgbgA+AD4AO2B7wFkgnMCMwI+ga2B/QImgi6BJAIiAn2BOIJAAA=

参考链接:炉石传说卡组代码组成结构分析 - 知乎 (zhihu.com)

队里师傅的脚本:

import base64
from Crypto.Util.number import *
c = "AAEDAZoFKIwGngXIBrwFzgnQBfIHygf0CIgJkAi+BogJ1gjMCPIHtgeeBeAD6AfyB7YHvgbgA+AD4AO2B7wFkgnMCMwI+ga2B/QImgi6BJAIiAn2BOIJAA=="
c=base64.b64decode(c)
a1=''
a2=[]
for i in c:
    a1+=(str(bin(i)[2:].zfill(8)))
a1=a1+'0'*4
for j in range(len(a1)//8+1):
    a2.append(a1[j*8:(j+1)*8])
a2=a2[7:]
a4=[]
for k in range(len(a2)//2):
    a4.append(a2[k*2:(k+1)*2])
a4=a4[:-1]
for i in range(len(a4)):
    a5=''
    for j in range(8):
        l=a4[i][1][j]
        if(l=='1'):
            a5+=a4[i][1][j:]
            break
    a5+=a4[i][0][1:]
    o=str(int(a5,2))[:-1]
    print(long_to_bytes(o))

出题人给的脚本:

fflag=['10001100','00000110','10011110','00000101','11001000','00000110','10111100','00000101','11001110','00001001','11010000','00000101','11110010','00000111','11001010','00000111','11110100','00001000','10001000','00001001','10010000','00001000','10111110','00000110','10001000','00001001','11010110','00001000','11001100','00001000','11110010','00000111','10110110','00000111','10011110','00000101','11100000','00000011','11101000','00000111','11110010','00000111','10110110','00000111','10111110','00000110','11100000','00000011','11100000','00000011','11100000','00000011','10110110','00000111','10111100','00000101','10010010','00001001','11001100','00001000','11001100','00001000','11111010','00000110','10110110','00000111','11110100','00001000','10011010','00001000','10111010','00000100','10010000','00001000','10001000','00001001','11110110','00000100','11100010','00001001','00000000','00000000']
for i in range(40):
    flag=fflag[2*i+1]+fflag[2*i][1:-1]+fflag[2*i][-1]
    fla=int(flag,2)
    fl=fla//10
    print(chr(fl),end='')

甚至解法三:

python有个库就叫hearthstone,直接用就好了

from hearthstone.deckstrings import Deck

deck = Deck.from_deckstring('AAEDAZoFKIwGngXIBrwFzgnQBfIHygf0CIgJkAi+BogJ1gjMCPIHtgeeBeAD6AfyB7YHvgbgA+AD4AO2B7wFkgnMCMwI+ga2B/QImgi6BJAIiAn2BOIJAAA=')

for card in deck.cards:
    flag_part = int(card[0] / 10)
    print(chr(flag_part), end='')
NCTF{HearthStone_C0de_S000_FunnY_ri9ht?}

zystego

文件尾可以找到一个zip,提取出来后爆破密码是114514

image-20221205085910105

image-20221205085835995

flag.txt循环解base64可以得到一个假的flag

image-20221205090005375

NCTF{1t_1s_N0t_th@t_s1mpL3_S0_th1s_1s_A_F@k3_f1a9_L0L}

zip里另一个东西是pgp的私钥

放大图片发现右侧有一段不正常的东西

image-20221203190949856

而图片像素也是不正常的515*512,将这串东西的RGB提取出来,发现全是5的倍数

image-20221203191314692

多次尝试之后发现以除以5后的结果的奇偶,即能否被10整除读取二进制可以得到一个加密脚本

image-20221203191726701

image-20221203191740578

是一个简单的dct算法,末尾给了一个key,猜测是gpg算法的密钥

import secret

丁真 = np.float32(cv2.imread(r"C:\Users\16334\Desktop\fadian.png", 1))

for i in range(64):
	for j in range(64):
		芝士 = randint(0,2)
		小马珍珠 = 丁真[:, :, 芝士]
		雪豹 = cv2.dct(小马珍珠[8*i:8*i+8, 8*j:8*j+8])
		if(secret[i*64+j] == '1'):
			雪豹[7,7] = 20
		elif(secret[i*64+j] == '0'):
			雪豹[7,7] = -20
		小马珍珠[8*i:8*i+8, 8*j:8*j+8] = cv2.idct(雪豹)
		丁真[:, :, 芝士] = 小马珍珠

cv2.imwrite(r"C:\Users\16334\Desktop\fd.png", 丁真)
#a gift for you : %$#%$#jhgasdfg76342t........................

尝试打印[7,7]位置可以看出数据有略微偏差

image-20221205090412813

偏差数据最大不超过10,用正负十作为条件根据逻辑写对应的解密脚本

import numpy as np
import cv2

丁真 = np.float32(cv2.imread(r"1.png", 1))

for i in range(64):
    for j in range(64):
        for 芝士 in range(3):
            小马珍珠 = 丁真[:, :, 芝士]
            雪豹 = cv2.dct(小马珍珠[8*i:8*i+8, 8*j:8*j+8])
            #print(雪豹[7,7])
            if(雪豹[7,7] > 10):
                print(1,end='')
            elif(雪豹[7,7] < -10):
                print(0,end='')

#a gift for you : %$#%$#jhgasdfg76342t........................

得到一个zip,解开后得到pgp加密文件

image-20221203192151841

image-20221203192205847

放kali里面直接解

image-20221205090847350

NCTF{zys_1s_s0_V3g3T@13lE_qwq}

猜你喜欢

转载自blog.csdn.net/jyttttttt/article/details/128181075