密码侧信道分析实验-计时工攻击
备注 :密码侧信道分析课程的课内实验,仅供学习参考。不一定正确。
【实验目的】
1、掌握计时攻击的基本原理;
2、掌握计时攻击方法进行密钥猜测攻击的基本原理和方法;
3、掌握字符串验证过程中计时攻击的基本原理和方法。
【实验人数】
每组1人
【系统环境】
Windows
【编程语言】
Python
【实验原理】
计时攻击是侧信道攻击( Side Channel Attack, 简称SCA)
的一种。攻击者试图通过分析加密算法的时间执行来推导出密码。每一个逻辑运算在计算机需要时间来执行,根据输入不同,精确测量执行时间,根据执行时间反推出密码。
一个最简单的计时攻击的例子,某个函数负责比较用户输入的密码和存放在系统内密码是否相同,如果该函数是从第一位开始比较,发现不同就立即返回,那么通过计算返回的速度就知道了大概是哪一位开始不同的,这样就实现了电影中经常出现的按位破解密码的场景。密码破解复杂度成千上万倍甚至百万千万倍的下降。最简单的计时攻击防御方法是:“发现错误的时候并不立即返回,而是设一个标志位,直到完全比较完两个字符串再返回”。
下面两种不同的字符串比较方式:
1.正常的字符串比较方法。一旦遇到一个不同的字符就返回失败了,所以,理论上来说,只有前面2个字符相同字符串的比较时间,要比前面有10个字符相同的比较时间要长。你会说,这能相差多少呢?可能几微秒吧。但是,我们可以放大这个事。比如,在Web应用时,记录每个请求的返回所需赶时间(一般是毫秒级),如果我们重复50次,我们可以查看平均时间或是总时间,以了解哪个字符返回的时间比较长,如果某个我们要尝试的字符串的时间比较长,我们就可以确定地得出这个这字符串的前面一段必然是正确的。
2.改进的字符串比较方法。通过异或操作 1^1=0 , 1^0=1 , 0^1=1
,0^0=0,来比较每一位,如果每一位都相等的话,两个字符串肯定相等,最后存储累计异或值的变量 必定为 0,否则为 1。
【实验内容】
1、完成detime-student.py程序中正常字符串比较方法different_time_compare(val1,
val2)函数与改进的字符串比较方法constant_time_compare(val1,
val2)函数,比较两个函数在比较相同字符串与不同字符串之间的用时差别,并分析原因。
(1)补充different_time_compare函数与constant_time_compare函数
(2)different_time_compare函数比较相同字符串
(3)different_time_compare函数比较不相同字符串
(4)constant_time_compare函数比较相同字符串
(5)constant_time_compare函数比较不相同字符串
# -*- coding: utf-8 -*-
"""
Created on Fri Sep 17 15:21:17 2021
@author: lilin
"""
# -*- coding: utf-8 -*-
"""
Created on Fri Sep 17 11:01:37 2021
@author: lilin
"""
import random
import time
#字符串长度
length = 8000000 #值太小会出现计时偏差错误
def different_time_compare(val1, val2):
"""
存在计时攻击的字符串比较方法
"""
t1 = time.time()
if len(val1) != len(val2):
return False
#补充:用正常的字符串比较方法比较
for i in range(len(val1)):
if val1[i] != val2[i]:
t2 = time.time()
t3 = t2 - t1
return False, t3
t2 = time.time()
runTime = t2 - t1
return True,runTime
def constant_time_compare(val1, val2):
"""
防止计时攻击的字符串比较方法
"""
t1 = time.time()
if len(val1) != len(val2):
return False
result = 0
for x, y in zip(val1, val2):
#补充:用改进的字符串方法比较,通过异或操作比较
if (ord(x)^ord(y) != 0):
result += 1
if result != 0:
return False, time.time() - t1
t2 = time.time()
runTime = t2 - t1
return result == 0,runTime
#生成字符串
seed = "1234567890abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ!@#$%^&*()_+=-"
str1 = []
for i in range(length):
str1.append(random.choice(seed))
Stringright = ''.join(str1)
str2 = []
for i in range(length):
str2.append(random.choice(seed))
Stringguess = ''.join(str2)
#补充运行结果:根据实验内容1,调用different_time_compare与constant_time_compare函数,输出比较时间并在报告中做出分析
temp,timediff =different_time_compare(Stringguess,Stringright)
print('diff同字符串比较结果', temp,timediff)
temp,timediff=different_time_compare(Stringright,Stringright)
print('diff不同字符串比较结果', temp, timediff)
temp,timediff = constant_time_compare(Stringright,Stringguess)
print('const同字符串比较结果', temp,timediff)
temp,timediff = constant_time_compare(Stringright,Stringright)
print('const不同字符串比较结果', temp,timediff)
运行结果截图:
2、完成guess-student.py程序中登录密钥的猜测攻击:
(1)输出每次猜测的密钥、对应的猜测时间、输出每个猜测的验证次数
(2)观察不同猜测用时情况并分析原因
(3)共测试2组密钥数据
# -*- coding: utf-8 -*-
"""
Created on Fri Sep 17 15:48:11 2021
@author: lilin
"""
# -*- coding: utf-8 -*-
"""
Created on Fri Sep 17 10:02:02 2021
@author: lilin
"""
#import login
import time
import sys
length = 5
times = 1000 #验证次数初始值
password = "asdfv" #自己设定两个不同的密钥进行实验并分析运行结果
password = "guetp"
# 模拟登陆等字符串验证过程
def login(input):
for i in range(0,len(input)):
if password[i] != input[i]:
return False
# 模拟延时
time.sleep(0.00001)
return True
# 获取密码验证耗费时间
def getRunTime(input):
t1 = time.time()
# 多次验证,累计时间
for i in range(int(times)):
login(input)
t2 = time.time()
runTime = t2 - t1
return runTime
if __name__ == "__main__":
result = ""
for index in range(length):
# 验证次数随已猜测字符串长度增加而减少
times/=(index+1)
#补充:输出验证次数
print('验证次数:',times)
maxTime = 0
bestLetter = ''
for i in range(26):
letter = chr(ord('a')+i)
runTime = getRunTime(result+letter)
#补充:输出运行时间
print(runTime)
if runTime > maxTime:
maxTime = runTime
bestLetter = letter
result += bestLetter
#补充:输出此次比较的结果
print(result)
print(str(index/length*100)+"%")
print("100.0%")
print(result)
猜测第一组密钥
猜测第二组密钥
越往后,猜测密钥用时在不断减少,因为每猜对密钥当中的一个字符串,我们的验证次数就相应减少(这样可以更好的模拟攻击过程,因为每次模拟验证登陆,每正确一个字符串,就模拟一次延迟,随着猜对的密钥不断变长,模拟登陆本身就会有延迟增加,因此不必要每次都要相同的的验证次数)。
(讲的有点乱,看不懂就跳过这段话吧)
【思考问题】
现实生活中有什么与计时攻击相关的实例?
机器加工产品,每加工一个产品,耗时基本相同,我们可以根据时长判断加工的产品数量。
【心得体会】
体验了计时攻击的流程,这是一种简单,但却很重要,对于后面的深入学习起到了引导作用。通过模拟登陆的过程,理解了计时攻击的基本思路和整体过程。同时也知道,设置系统时,要注意防范计时攻击。
学习计划安排
我一共划分了六个阶段,但并不是说你得学完全部才能上手工作,对于一些初级岗位,学到第三四个阶段就足矣~
这里我整合并且整理成了一份【282G】的网络安全从零基础入门到进阶资料包,需要的小伙伴可以扫描下方CSDN官方合作二维码免费领取哦,无偿分享!!!
如果你对网络安全入门感兴趣,那么你需要的话可以
点击这里👉网络安全重磅福利:入门&进阶全套282G学习资源包免费分享!
①网络安全学习路线
②上百份渗透测试电子书
③安全攻防357页笔记
④50份安全攻防面试指南
⑤安全红队渗透工具包
⑥HW护网行动经验总结
⑦100个漏洞实战案例
⑧安全大厂内部视频资源
⑨历年CTF夺旗赛题解析
