这篇文章主要是学习一波MP3格式fuzz的知识。目录如下

0x0.MP3格式的构成

0x0.MP3格式的构成

  MP3是一种通俗叫法,学名叫MPEG1 Layer-3。MP3是三段式的结构,依次由ID3V2、Frame、ID3V1构成。其中Frame为帧,这是MP3格式的基本单位,一个个的帧构成了整个MP3文件。先来看结构最简单的ID3V1,这个结构的大小是固定的,共128字节。可见都是一些MP3的相关信息如作者、标题之类的。

typedef struct tagID3V1
{
char Header[]; //固定为"TAG"
char Title[]; //标题
char Artist[]; //作者
char Album[]; //专辑
char Year[]; //出品年代
char Comment[]; //备注
char reserve; //保留
char track; //音轨
char Genre; //类型
}ID3V1,*pID3V1;

接下来是存放数据的Frame帧结构。其中FrameHeader一共4个字节共32位,这32位是当作标志来用的,就是说每个位对应不同的意义。其中CRC域有可能不存在,这是有FrameHeader中的位决定的。而且FrameHeader中的帧头记录的MainData的大小。

typedef struct _FRAME
{
char FrameHeader[];//每个帧都有一个4字节的帧头
char CRC[]; //帧头第16字节决定是否存在CRC
char MainData[?]; //帧头决定大小
}FRAME,*PFRAME;

FrameHeader定义为AAAAAAAAAAA BB CC D EEEE FF G H II JJ K L MM,不同字母代表不同意义的域。以下是这些域的意义。

A-   帧同步
B- 表示版本,有1、、.5三种
C- 表示Layer版本,即mp1、mp2、mp3
D- 决定是否有CRC
E- 表示比特率
F- 表示采样率
G- 表示填充位
H- 保留
I- 表示声道
J- 立体声的扩展模式
K- 是否有版权信息
L- 是否是原创
M- 强调

前面已经说过了Frame的大小是由FrameHeader来决定的,

下面来看下ID3V2标签,ID3V2标签是MP3文件的第一个标签,由一个标签头和若干个标签帧构成。其中标签头如下所示

typedef struct tagID3V2
{
char Header[];//固定为"ID3"
char Ver; //记录版本号,3表示ID3V2.3
char Revision; //副版本号,这里为0
char Flag; //定义标识位
char Size[]; //定义标签大小,包括这10个字节
}ID3V2,*PID3V2;
Size算法是每个字节取后7位来组成28位数字,作为大小的值。
typedef struct Header
{
char FrameID[];//帧标识,说明这个帧的含义
char Size[]; //帧内容的大小,不包括帧头,不得小于1
char Flags[]; //存放标识
}HEADER;
Size是32位的大小值

ID3V2的大小只取每个字节的前位进行计算,作为ID3V2块的总大小进行计算。

如上所示每个ID3V2所属的标签还有其他的标签头,每个小标签头所表示的标签具有一定的含义,含义由FrameID决定,下面列出了一些常见的FrameID。size的计算法就是当成4个字节的DWORD来计算的。Flag和FrameID更多的值可以在附件的PDF里面看。

 TIT2 标题
TPE1 作者
TALB 专集
TRCK 音轨
TYER 年代
TCON 类型
COMM 备注

0x1.MP3格式的脆弱点

前面主要是介绍了一下MP3文件的文件格式,这里在就要对MP3文件格式进行FUZZING之前要搞清楚的一点是MP3文件的脆弱点在哪里,就是说哪里是可能出现问题的地方,搞清楚这一点对于Fuzzing样本的生成也有很大的好处。而且有一个问题就是MP3的帧大小问题。我们前面已经知道了一个MP3是由许多帧构成的,但是注意帧头中并没有size域,因为一个帧的大小是由比特率和采样率算出来的,而比特率和采用率储存在帧头中分别为E、F。计算公式如下。

帧长度(字节)= 每帧采样数 / 采样率(HZ) * 比特率(bps)/ + 填充
例:LayerIII 比特率 128000,采样率 44100,填充0 =〉帧大小 417字节 这样来说还有一个简单的公式(144*比特率)/采样率+填充位
注意,比特率是以k为单位的,比如128是128k的比特率。

MPEG1

MPEG2

MPEG2.5

Layer1

384

384

384

Layer2

1152

1152

1152

Layer3

1152

576

576



【每帧采【每帧采样数表】


这样就有一个问题了,我们要不要对E、F进行随机生成呢?如果也对E、F进行随机生成那么帧大小就会乱掉了。但是如果不随机生成的话,那么这几个域就固定了。这点我还没想明白怎么搞的。

下面提供了一个解析MP3文件操作的步骤

解析方法
当你想读取MPEG文件的信息时,解析前三个字节,判断是否有ID3V2标签,有则根据上面的方法算出ID3V2标签的总大小,这样就找到了音频数据帧的第一帧,读取它的头信息,获取比特率、采样率、MPEG版本号、Layer描述号等信息,根据上面提供的方法算出
每帧的长度和每帧持续时间,对于定比特率的其它帧是相同的,也就是说解析第一帧就达到了目的。但这也不是所有情况。变比特率的MPEG文件使用使用所谓比特变换,也就是说每一帧的比特率依照具体内容变化。这时就需要你每一帧都解析。

这个解析步骤是从网上看到的,我不知道有哪些的解码器是用这种方法解码的,但是我们可以根据上面提供的这个操作猜测出一些信息。首先IDV2的size标签域不能随意生成,因为如果随意生成这个域的话,那么就没有办法定位到第一帧了,那么这个mp3文件就整个乱掉的了,对于这种情况估计播放器会直接说文件损坏根本起不到测试的效果了。与此类似的是数据帧的比特率和采样率也不能随意生成,因为这两个值是用来计算数据帧大小用的,如果随意生成那么帧的大小就会计算错误,根据上面的解析方法可以解析的方法就是逐大小往下移,如果一个帧的大小计算不对,那么整个mp3的解析都会出现问题。这样同样就是无法达到测试的效果的。但是如果都是动态生成呢?我觉得当然是可以的了,但是数据的逻辑关系就太复杂了。尤其是很蛋疼的有一个按位的运算,这个直接用标签好像难以实现的,应该需要内嵌pyhon脚本来实现。目前还不知道该怎么搞,所以先生成固定长度的内容。

MP3 Fuzz学习的更多相关文章

  1. AFL++初探-手把手Fuzz一个PDF解析器

    CVE-2019-13288 目前漏洞在正式版本已经被修复,本文章仅供学习Fuzz过程,不存在漏洞利用的内容 这是一个pdf查看器的漏洞,可能通过精心制作的文件导致无限递归,由于程序中每个被调用的函数 ...

  2. [原题复现]ByteCTF 2019 –WEB- Boring-Code[无参数rce、绕过filter_var(),等]

    简介  原题复现:  考察知识点:无参数命令执行.绕过filter_var(), preg_match()  线上平台:https://buuoj.cn(北京联合大学公开的CTF平台) 榆林学院内可使 ...

  3. 从零开始学习PYTHON3讲义(十四)写一个mp3播放器

    <从零开始PYTHON3>第十四讲 通常来说,Python解释执行,运行速度慢,并不适合完整的开发游戏.随着电脑速度的快速提高,这种情况有所好转,但开发游戏仍然不是Python的重点工作. ...

  4. 关于Fuzz——peach的学习

    最近在搞漏洞挖掘,之前写过一个文件格式漏洞挖掘的博文,使用的是光刃牛写的Alpha Fuzz工具.感觉样本生成的质量不是很好,这次打算使用一下老牌的Fuzz工具peach.学长介绍了一下说peach的 ...

  5. ANDROID_MARS学习笔记_S01原始版_023_MP3PLAYER003_播放mp3

    一.简介 1.在onListItemClick中实现点击条目时,跳转到PlayerActivity,mp3info通过Intent传给PlayerActivity 2.PlayerActivity通过 ...

  6. ANDROID_MARS学习笔记_S01原始版_021_MP3PLAYER001_下载mp3文件

    一.简介 1.在onListItemClick()中new Intent,Intent以存储序列化后的mp2Info对象作为参数,启动serivce 2.DownloadService在onStart ...

  7. 吴裕雄--天生自然python学习笔记:python 用pygame模块制作 MP3 音乐播放器

    利用 music 对象来制作一个 MP3 音乐播放器 . 应用程序总览 从歌曲清单中选择指定的歌曲,单击“播放”按钮可开始播放, 在播放 xxx 歌曲”的信息. 歌曲播放的过程中,可以暂停.停止,也可 ...

  8. 【C#学习笔记】播放wma/mp3文件

    using System; using System.Runtime.InteropServices; namespace ConsoleApplication { class Program { [ ...

  9. Android的fuzz测试技术之符号执行浅谈-android学习之旅(82)

    简单的漏洞越来越少,需要改进目前的方法 : 通过符号执行,得出执行路径,然后在进行fuzzy是较为有效的方法之一 1)为待测单元自动地生成可到达的测试数据,即提高测试目标的覆盖率 2)根据特定的漏洞模 ...

随机推荐

  1. 南昌邀请赛网络赛 D.Match Stick Game(dp)

    南昌邀请赛网络赛 D.Match Stick Game 题目传送门 题目就会给你一个长度为n的字符串,其中\(1<n<100\).这个字符串是一个表达式,只有加减运算符,然后输入的每一个字 ...

  2. 题解【51nod 1290 Counting Diff Pairs】

    Description 求区间内有多少对 \((i,j)\) 满足 \(|a_i - a_j| \leq k\) Solution 可以莫队做(万能的莫队) 只需要考虑加入一个数会产生多少贡献即可 离 ...

  3. Docker入门与应用系列(四)数据卷管理

    一.介绍 Docker镜像是由多个文件系统(只读层)叠加而成.当我们启动一个容器的时候,Docker会加载只读镜像层并在其上(译者注:镜像栈顶部)添加一个读写层.如果运行中的容器修改了现有的一个已经存 ...

  4. Python中hashlib模块

    介绍hashlib hashlib 是一个提供了一些流行的hash算法的 Python 标准库.其中所包括的算法有 md5, sha1, sha224, sha256, sha384, sha512. ...

  5. 64位Ubuntu 安装scrapy遇到的问题

    这两天准备开始学习Python爬虫,安装scrapy框架后出现 Traceback (most recent call last): File "/usr/local/bin/scrapy& ...

  6. 八卦Minsky打压神经网络始末

    八卦Minsky打压神经网络始末 谈下Minsky造成的神经网络冰河事件:57年一个叫弗兰克的大概只有二流水平的学者搞出了感知机,理论和实践证明了对线性可分问题的有效性,引起一阵轰动,特别是非科学圈类 ...

  7. Javascript 常用的工具函数,更新中...

    1.时间戳转为格式化时间 /** * 时间戳转为格式化时间 * @Author chenjun * @DateTime 2017-11-10 * @param {[date]} timestamp [ ...

  8. HDFS的java接口——简化HDFS文件系统操作

    今天闲来无事,于是把HDFS的基本操作用java写出简化程序出来给大家一些小小帮助! package com.quanttech; import org.apache.hadoop.conf.Conf ...

  9. transform动画效果

     transform动画效果 transform :移动,旋转.倾斜.缩放.     transform:translate(0,300px); x代表的是水平的偏移距离,y代表垂直的.      t ...

  10. mogodb的安装与配置

    下载:https://www.mongodb.com/https://www.mongodb.com/ 安装:一直next,中间选择custom,选择自己的安装路径,最后安装成功. 配置:打开安装好的 ...