微波EDA网,见证研发工程师的成长!
首页 > 硬件设计 > 嵌入式设计 > 如何用C语言描述AES256加密算法最高效?

如何用C语言描述AES256加密算法最高效?

时间:01-23 来源:3721RD 点击:

然后,为输入状态中的下一个列采用相同乘法矩阵重复这个过程,直到处理完所有输入状态列。

既然我们已经理解了 AES 加密和解密算法所需的详细步骤,那么还需要知道一个循环中这些步骤的应用顺序以及我们是否必须为每个循环应用所有步骤。每个 AES 加密循环都包含全部四个步骤,并按照以下顺序:
1. 字节替换 (SubBytes) ;
2. 行位移变换 (ShiftRows);
3. 列混合变换 (MixColumns) (只针对循环 1 至N–1);
4. 轮密钥加 (AddRoundKey)( 使用扩展秘钥)。

当然,我们需要能够反转这个过程,将不可读的密文变回纯文本,让加密信息有用。为此,我们将步骤进行如下排序:
1. 反转行位移变换;
2. 反转字节替换;
3. 轮密钥加(使用扩展秘钥);
4. 反转列混合变换(只针对循环 1 至 N–1)。
执行第一轮加密之前,我们需要为加密和解密执行初始轮密钥加 (AddRoundKey) 操作。

可在更高抽象层上高效地描述 AES,就像在传统软件开发中那样,但在 FPGA 中实现起来最为高效。开发人员甚至可在布线中"免费"获得一些操作。

我们看一下扩展秘钥必须使用的算法,以便提供足够的秘钥位,用以执行相应数量的轮密钥加(AddRoundKey) 步骤(图 5)。进行秘钥扩展时,16、24 或 32 字节的秘钥长度分别需要 44、52 或 60个循环。扩展秘钥的第一个字节等于初始秘钥。这意味着对于我们的 AES256 实例来说,扩展秘钥的最开始的 32 个字节就是秘钥本身。秘钥扩展操作在每次迭代中为扩展秘钥生成 32 个附加位。

用C 语言描述AES256 加密算法

图 5 - 秘钥扩展算法

扩展秘钥的第一个字节等于初始秘钥。这意味着对于我们的 AES256 实例来说,扩展秘钥的最开始的 32 个字节就是秘钥本身。

以下是重要的扩展步骤:
RotateWord: 与行位移变换 (ShiftRows) 类似,这个步骤重新组织 32 位字,以使最高有效字节变为最低有效字节。
SubWord: 这个步骤使用的替换盒与加密时进行字节替换所使用的替换盒相同。
rcon: 该阶段对用户定义的值进行 2 次幂运算。
与列混合变换 (MixColumns) 阶段类似,rcon 也在有限域 (28) 中执行; 因此这个步骤普遍使用预先计算的查找表。
EK: 从扩展秘钥返回 4 个字节。
K: 与 EK 类似,从秘钥返回 4 个字节。
如何知道我们已经正确实现了加密和秘钥扩展算法? AES 的 NIST 规范包含多个有效实例,可用来检查我们自己的实现结果。

创建代码
为了确保能够加速 Zynq SoC 的 PL 中 AES 代码的加密部分,我们必须一开始就要以这个目标来开发代码(见这里的编码规则)。要考虑的第一件事是算法的架构;我们需要正确对其进行分段。AES 很适合这种方案,因为我们可以为每个阶段编写函数,然后再根据需要调用。 我们还必须编写要在自身的文件中进行加速的函数。软件架构包括以下内容。

main.c: 该文件包含秘钥扩展算法、加密秘钥和纯文本输入,以及对 AES 加密函数的调用。

aes_enc.c: 该文件执行加密。我们将每个阶段编写为单独的函数,这样就能根据 AES 循环的需要进行调用。为确保程序设计对于处理器上执行的程序具有通用性,我们为混合步骤的乘法使用查找表。

aes_enc.h: 这个文件包含 aes_funcTIon 的定义以及用来确定大小的参数(例如 mk、nb 和 nr)。

sbox.h: 这个文件包含用于替换字节的替换盒、执行秘钥扩展的 rcon 函数的查找表以及用于列混合变换乘法的乘法查找表。

在这个结构中,我们可以选择 AES 加密函数( 图 6) 作为要进行加速的函数,只需右键点击该函数并选择" Toggle HW/SW"即可。

用C 语言描述AES256 加密算法

图 6 - 要加速的函数

为了能确定基准性能以及通过函数加速获得的保存结果,我们必须对函数的执行进行时间控制。为此,我们使用 sds_lib.h 中的sds_clock_counter。

编写源代码(在 github 提供)之后,在用 ZynqSoC 中的单个 ARM? Cortex ? -A9 处理器内核在软件中执行 AES 算法时,我记录了 36,662 个处理器周期。

为加速而进行的优化
加速 AES 算法比前一个问题中的矩阵乘法算法还要稍稍复杂一些。这是因为 AES 算法的主循环包含互相依赖的阶段。

我加速 AES 算法时所采用的方法是:检查循环以找出可以展开的地方; 优化存储器带宽; 选择正确的数据移动时钟频率和硬件功能频率。

AES 加密函数的主循环包含用于执行每个 AES步骤的函数。AES 算法中的每个函数必须完整执行,并在下个函数运行之前计算出结果。这种互相依赖性需要我们将精力集中于作为独立函数的 AES步骤。这些步骤中存在足够多的优化潜力。

我们可将轮密钥加 (AddRoundKey) 、字节替换(SubBytes)

Copyright © 2017-2020 微波EDA网 版权所有

网站地图

Top