吾爱破解 - LCG - LSG |安卓破解|病毒分析|破解软件|www.52pojie.cn

 找回密码
 注册[Register]

QQ登录

只需一步,快速开始

领取今日签到奖励
查看: 2885|回复: 33

[CTF] Base64编码原理及脚本的简单实现

[复制链接]
发表于 2018-11-30 14:03
本帖最后由 yaoyao7 于 2018-11-30 14:52 编辑

base64编码的产生是因为在数据传输的时候,并不是所有的字符都可以受到支持,很多时候只能传输可见字符,对于不可见字符的传输需要经过特殊处理,这就是base64产生的原因.
base64编码之后,可以将所有的字符转变成base64支持的64个可见字符.
base64的字符表如下图所示:
base64字符集.png
从上面的字符表中我们知道一共有2^6=64个字符,那么只需要6位就可以描述出所有的字符.但是我们的计算机中一个字节有8位,这样就会多出两位,我们使用0进行填充.
使用上表中的字符表示所有字符的过程:
1,首先将所有的待转换字符转换成二进制形式,例如:"abc"转换成二进制表示为‭011000 010110 001001 100011

2,按照每6位截取,并在每个6位之前填充00,"abc"的二进制表示就变成了00011000 00010110 00001001 00100011
将原来3个8位转换成了4个6位,然后因为base64是将3个8位变成4个6位,所以最后得到的字节数目一定是4的倍数,如果不是4的倍数就是用=填充.
3,使用填充的例子:假定待转换字符为"youtest"
转换成二进制后为:01111001 01101111 01110101 01110100 01100101 01110011 01110100
我们所给的字符串长度为7,7×8=56,无法被6整除,这个时候我们需要填充至可以被6整除。即在末尾填充2两个字符,这样总共有56+16=72位,最后可以转变为12个字符,
‭01111001 01101111 01110101 01110100 01100101 01110011 01110100 00000000 00000000
然后按照6位一个字符进行截取排列:
011110   010110    111101    110101    011101    000110     010101     110011    011101    000000    000000    000000

然后进行00填充:
00011110  00010110  00111101  00110101  00000110  00010101  00110011  0001101  00000000  0000000  00000000

然后将二进制数据转换成十进制:
30 22 61 53 29 6 21 51 29 0 0 0
对照base64表进行字符替换得到:
eW91dGVzdAAA
最后将AA换成===即可:
eW91dGVzdA==
我们在python中验证一下我们的结果是否正确:


验证base64.png
可以看到,我们的结果是正确的,最后附上从ichunqiu上看到的一个base64的编码脚本:
[Python] 纯文本查看 复制代码
def myBase64Encode(preCoding) :
        charTable = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/' #字符表

        if len(preCoding) < 0 :
                return ''  #字符串为空则返回空
        lackCharNums = 3-len(preCoding)%3
        if lackCharNums == 3 : lackCharNums = 0 #整除说明不缺字符
        #待转换字符不是3的倍数的情况补全它
        for i in range(lackCharNums) :
                preCoding = preCoding + b'\x00'
        result = '' #用于保存最终结果的str数据
        rp = '' #处理补全字符时的暂存变量
        #每三个字符处理一轮
        for i in range(int(len(preCoding)/3)) :
                threeChar = preCoding[i*3:i*3+3] #取三个字符出来
                tCode = '' #用于存放三个字符拼接后的二进制数值 文本形式
                pCode = '' #暂存变量
                for j in range(3) :
                        pCode = bin(threeChar[j])[2:]  #把省略的0补上
                        lackZeroNums = 8-len(pCode) #省略的0的个数
                        for x in range(lackZeroNums) :
                                pCode = '0'+pCode
                        tCode = tCode + pCode
                pCode = ''
                for j in range(4) : #每6位一个字符
                        pCode = tCode[j*6:j*6+6]
                        rp = rp + charTable[int(pCode,2)]
                #处理补全的00字符
                result = rp[:len(rp)-lackCharNums]
                for j in range(lackCharNums) :
                        result = result + '='
        return bytes(result,encoding="utf-8")

def myBase64Decode(encodedBin) :
        charTable = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/' #字符表

        #如果字符不是4的倍数 返回空
        if not len(encodedBin)%4 == 0 :
                return ''

        tCode = '' #用于存放最终的二进制文本字符串
        pCpde = '' #暂存变量
        #遍历encodedBin每一个字符
        for i in encodedBin :
                for j in range(len(charTable)) : #找到表中对应坐标
                        if chr(i) == charTable[j] :
                                pCode = bin(j)[2:]  #转二进制去除开头的0b
                                lackZeroNums = 6-len(pCode) #省略的0的个数
                                for x in range(lackZeroNums) :
                                        pCode = '0'+pCode
                                tCode = tCode + pCode
        pCode = ''
        result = '' #储存最终结果
        for i in range(int(len(tCode)/8)) :
                pCode = tCode[i*8:i*8+8]
                result = result + chr(int(pCode,2))
        return bytes(result,encoding="utf-8")

免费评分

参与人数 6吾爱币 +10 热心值 +6 收起 理由
金野喵君 + 1 + 1 谢谢@Thanks!
行单影只 + 1 + 1 热心回复!
oranges + 1 + 1 我很赞同!
panjun + 1 谢谢@Thanks!
Hmily + 6 + 1 欢迎分析讨论交流,吾爱破解论坛有你更精彩!
Amd794 + 1 + 1 真的不错,讲的挺好的

查看全部评分

本帖被以下淘专辑推荐:

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你在论坛求助问题,并且已经从坛友或者管理的回复中解决了问题,请把帖子分类或者标题加上【已解决】

如何回报帮助你解决问题的坛友,一个好办法就是给对方加【热心】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

 楼主| 发表于 2018-11-30 14:46
pikachu888 发表于 2018-11-30 14:36
其实很多时候用的不是Base64,而是改进之后的Base62,
很详细的文章,不错不错

写的都是很基础的东西,实际应用中都会做适当的修改,除非是真的懒得不行了,才会直接用base64,总比裸奔好
发表于 2018-11-30 14:33
发表于 2018-11-30 14:36
其实很多时候用的不是Base64,而是改进之后的Base62,
很详细的文章,不错不错
发表于 2018-11-30 14:39
看起来把原理都讲完了
 楼主| 发表于 2018-11-30 14:47

一起学习进步
 楼主| 发表于 2018-11-30 14:48
dddl 发表于 2018-11-30 14:39
看起来把原理都讲完了

基本的说了一下,算是给不了解的师傅们抛个砖,基于base64的变体还是很多的
发表于 2018-11-30 14:54
很厉害 通俗易懂 终于懂了
发表于 2018-11-30 15:52
支持支持支持支持支持
发表于 2018-11-30 16:10 来自手机
谢谢老板分享
您需要登录后才可以回帖 登录 | 注册[Register]

本版积分规则


免责声明:
吾爱破解所发布的一切破解补丁、注册机和注册信息及软件的解密分析文章仅限用于学习和研究目的;不得将上述内容用于商业或者非法用途,否则,一切后果请用户自负。本站信息来自网络,版权争议与本站无关。您必须在下载后的24个小时之内,从您的电脑中彻底删除上述内容。如果您喜欢该程序,请支持正版软件,购买注册,得到更好的正版服务。如有侵权请邮件与我们联系处理。

Mail To:Service@52PoJie.Cn

快速回复 收藏帖子 返回列表 搜索

RSS订阅|手机版|小黑屋|联系我们|吾爱破解 - LCG - LSG ( 京ICP备16042023号 | 京公网安备 11010502030087号 )

GMT+8, 2019-3-26 06:14

Powered by Discuz!

© 2001-2017 Comsenz Inc.

快速回复 返回顶部 返回列表