《密码系统设计》第四周

密码系统设计

第四周预习报告

学习内容

AI 对学习内容的总结(1分)s

要求

  • 让AI(kimi,元宝等)阅读学习内容并进行总结,教材内容可以使用微信读书或者云班课电子教材

总结

《Windows C/C++加密解密实战》

第14章主要介绍了SM2算法的实现,这是一种基于椭圆曲线密码体制的非对称加密算法,由我国国家密码管理局推出,旨在替代RSA算法,提高信息系统的安全性。

SM2算法概述

  • 背景: SM2算法是为了提高公钥算法的安全性而设计,特别是在RSA算法面临安全威胁的情况下,SM2提供了更短的密钥长度和更高的安全性。
  • 特点: 相比于RSA,SM2算法在签名和密钥交换方面采用了更安全的机制,使用了推荐的256位标准曲线。

SM2算法的数学基础

  • 椭圆曲线: SM2基于椭圆曲线,这些曲线由特定的方程定义,并通过参数a、b确定。
  • 有限域: 讨论了有限域的概念,包括素域和二元扩域,这些是椭圆曲线密码体制的基础。

SM2算法的流程

  • 密钥生成: 包括私钥和公钥的生成,公钥通过椭圆曲线上的点乘运算得到。
  • 加密: 描述了SM2加密算法的详细步骤,包括随机数的生成、点的计算、密钥派生函数KDF的应用等。
  • 解密: 介绍了如何使用私钥对加密的信息进行解密。

SM2算法的安全性

  • 参数验证: 讨论了椭圆曲线系统参数的验证,确保参数满足特定的安全条件。
  • 公钥验证: 描述了公钥验证的步骤,确保公钥有效且安全。

SM2算法的编程实现

  • 大数运算: 介绍了MIRACL库的使用,这是一个用于大数运算的库,对于实现SM2算法至关重要。
  • 加解密实现: 提供了SM2加解密算法的C/C++代码实现,包括初始化、密钥生成、加密、解密和自测试函数。

SM2数字签名

  • 签名生成: 描述了数字签名的生成过程,包括计算杂凑值、生成随机数、计算签名值等。
  • 签名验证: 介绍了如何验证数字签名的有效性。

总结
SM2算法作为国产非对称加密算法,提供了一种安全的加密和数字签名解决方案。第14章不仅介绍了SM2算法的理论基础和实现步骤,还提供了实际的编程代码,帮助读者更好地理解和应用SM2算法。通过学习SM2算法,可以增强信息安全防护能力,为我国的信息化建设提供支持。

《Head First C》

这份PDF文档是《Head First C》第五章的内容,主要介绍了C语言中的结构体(structs)、联合(unions)、位字段(bitfields)以及枚举(enums)。下面是对这些概念的总结:

  1. 结构体(structs):

    • 结构体允许你将不同的数据类型组合成一个自定义的数据类型。
    • 结构体在内存中是固定长度的,并且字段按声明的顺序存储。
    • 可以通过点操作符(.)访问结构体的字段。
    • 结构体可以嵌套,即一个结构体内部可以包含另一个结构体。
    • 可以用typedef为结构体创建别名,简化变量声明。
  2. 联合(unions):

    • 联合可以存储不同的数据类型,但在同一时间只能存储其中一个字段的值。
    • 联合的大小总是等于其最大字段的大小。
    • 联合可以用来节省内存空间,特别是当你知道在同一时间只会使用一个字段时。
    • 联合字段的访问也通过点操作符(.),并且可以与结构体结合使用。
  3. 位字段(bitfields):

    • 位字段允许你指定结构体中某个字段的存储位数。
    • 位字段常用于存储二进制值,如标志位。
    • 位字段可以大幅节省内存,尤其是当字段只需要一两个位来存储时。
  4. 枚举(enums):

    • 枚举创建一个符号列表,通常用于表示一组固定的选项。
    • 枚举变量只能赋值为枚举列表中的值。
    • 枚举可以用来跟踪联合中存储的值的类型,从而避免类型混淆的问题。
  5. 指针与结构体:

    • 将结构体传递给函数时,如果不使用指针,函数内部对结构体字段的修改不会影响到原始数据。
    • 使用指向结构体的指针,可以修改原始数据。
  6. 初始化:

    • 结构体可以使用数组初始化语法进行初始化。
    • C99标准引入了指定初始化器,可以通过字段名来初始化。
  7. 内存对齐和填充:

    • 编译器可能会在结构体字段之间添加填充字节,以确保数据按照特定的对齐方式存储。
  8. typedef:

    • typedef不仅可以为结构体创建别名,还可以用于基本数据类型。
  9. 函数和结构体:

    • 函数可以通过结构体指针来修改原始结构体数据。

通过学习这些概念,C语言程序员可以创建复杂的数据类型,以模拟现实世界中的实体和概念。这些工具在处理复杂的数据结构时非常有用,比如在图形处理、网络编程和嵌入式系统开发中。

对 AI 总结的反思与补充(2分)

要求

  • AI总结的问题
  • 自己的补充

反思与补充

AI总结的问题
密钥对的生成和公钥的验证:这部分内容可能需要更详细的说明,包括生成密钥对的过程和公钥验证的详细步骤。
自己的补充
网页搜索
在SM2算法中,密钥对的生成和公钥的验证是两个关键步骤,确保了算法的安全性和有效性。
密钥对的生成
密钥对包括一个私钥和一个公钥,生成过程如下:

  1. 选择椭圆曲线参数

    • 确定有限域F_q的规模q,以及椭圆曲线E(F_q)的方程参数ab
    • 确定基点G,这是一个在椭圆曲线上的点,且具有一个大的阶n
  2. 生成私钥

    • 私钥dA是一个随机选择的整数,位于区间[1, n-2]内。
  3. 计算公钥

    • 公钥PA是私钥dA与基点G的点乘结果,即PA = [dA]G
    • 公钥通常表示为点(xA, yA),即PA的坐标。

公钥的验证
公钥的验证过程确保公钥是有效的,并且确实位于椭圆曲线上:

  1. 检查点是否在曲线上

    • 验证公钥PA的坐标(xA, yA)是否满足椭圆曲线方程y^2 = x^3 + ax + b
  2. 检查点是否在域内

    • 确保xAyA都在有限域F_q内。
  3. 检查点的阶

    • 验证PA是否具有阶n,即[n]PA是否为无穷远点O
  4. 检查点是否为无穷远点

    • 确保PA不是无穷远点。

实现示例
以下是使用C语言和MIRACL库实现的公钥验证的简化示例:

#include "miracl.h"
#include "sm2.h"

// 假设全局变量定义了椭圆曲线参数和基点G
extern big para_a, para_b, para_p, para_n;
extern epoint *G;

// 验证点是否在椭圆曲线上
int TestPoint(epoint *point) {
    big x, y, x3, tmp;
    x = mirvar(0);
    y = mirvar(0);
    x3 = mirvar(0);
    tmp = mirvar(0);

    epoint_get(point, x, y);
    power(x, 3, para_p, x3); // x3 = x^3 mod p
    multiply(x, para_a, x);  // x = ax mod p
    divide(x, para_p, tmp);  // x = (ax mod p) / p
    add(x3, x, x);           // x = x^3 + ax
    add(x, para_b, x);       // x = x^3 + ax + b
    divide(x, para_p, tmp);  // x = (x^3 + ax + b) mod p

    power(y, 2, para_p, y);  // y = y^2 mod p
    if (mr_compare(x, y) != 0) {
        return ERR_NOT_VALID_POINT;
    }
    return 0;
}

// 验证公钥
int TestPubKey(epoint *pubKey) {
    big x, y;
    epoint *nP;
    x = mirvar(0);
    y = mirvar(0);
    nP = epoint_init();

    // 检查是否为无穷远点
    if (point_at_infinity(pubKey)) {
        return ERR_INFINITY_POINT;
    }

    // 检查x和y是否在域内
    epoint_get(pubKey, x, y);
    if (mr_compare(x, para_p) >= 0 || mr_compare(y, para_p) >= 0) {
        return ERR_NOT_VALID_ELEMENT;
    }

    // 检查是否在椭圆曲线上
    if (TestPoint(pubKey) != 0) {
        return ERR_NOT_VALID_POINT;
    }

    // 检查点的阶是否为n
    ecurve_mult(para_n, pubKey, nP); // nP = [n]pubKey
    if (!point_at_infinity(nP)) {    // 如果nP不是无穷远点
        return ERR_ORDER;
    }

    return 0;
}

在这个示例中,TestPoint函数检查一个点是否满足椭圆曲线方程,而TestPubKey函数则验证公钥的有效性,包括检查点是否在曲线上、是否为无穷远点、以及点的阶是否正确。

学习思维导图(2分)

mindmap root(加密解密实战) 算法概述 定义 特点 与ECC算法的关系 数学基础 椭圆曲线 有限域 椭圆曲线系统参数 密钥对生成 选择素数 计算N 选择公钥指数e 计算私钥d 加密算法 加密过程 加密示例 解密算法 解密过程 解密示例 数字签名 签名生成 签名验证 签名示例 算法实现 MIRACL库 RSA实现 SM2加解密实现 SM2签名验签实现 安全性 参数验证 公钥验证 标准协议 PKCS#1 填充机制 密钥语法 攻击分析 因子分解攻击 选择密文攻击 公共模数攻击 小指数攻击

图片展示:

mindmap root((Head First C第五章)) structs 定义结构体 struct关键字 组合基本数据类型 访问字段 点操作符(.) 嵌套结构体 一个结构体包含另一个 typedef 创建别名 简化变量声明 unions 定义联合 union关键字 同一内存位置不同数据类型 访问字段 点操作符(.) 与structs结合 包含union的结构体 bitfields 定义位字段 指定字段位数 内存效率 节省空间 应用 存储标志位 enums 定义枚举类型 创建符号列表 限制变量值 提高代码可读性 algorithms RSA加密算法 非对称加密 公钥和私钥 RSA安全基础 大数分解难度 素数 素数定义 素性检测 模运算 模运算定义 模运算性质 RSA实现 密钥生成 加密过程 解密过程 memory 栈与堆 内存分配 动态内存管理 pointer 指针运算 指针与数组 preprocessor 预处理器指令 文件包含 宏定义

图片展示:

基于 AI 的学习(2分)

要求
  • 至少找到自己理解不是太好 2 个概念,让 AI 对自己进行苏格拉底提问
  • 参考下面提示语或者使用 AI Agent

提示词:“我在学***X知识点,请你以苏格拉底的方式对我进行提问,一次一个问题”

  1. 核心是要求AI工具:“请你以苏格拉底的方式对我进行提问”
  2. 然后AI工具就会给你提问,如果不知道问题的答案,可以反问AI:“你的理解(回答)是什么?”
  3. 如果你觉得差不多了,可以先问问AI工具:“针对我XXX知识点,我理解了吗?”
  4. AI工具会给出它的判断,如果你也觉得自己想清楚了,可以最后问AI工具:“我的回答结束了,请对我的回答进行评价总结”,让它帮你总结一下。

学习内容

一、

:我在学习SM2知识点,请你以苏格拉底的方式对我进行提问,一次一个问题
AI:SM2算法属于哪种密码学范畴?
:SM2算法属于非对称加密算法范畴。
AI:什么是SM2算法中的密钥派生函数?
:密钥派生函数(KDF)在SM2算法中用于从共享的秘密(如密钥交换中的共享点)派生出实际使用的会话密钥。
AI:在SM2算法中,密钥派生函数(KDF)具体是如何工作的?
:在SM2算法中,密钥派生函数(KDF)通常采用密码杂凑函数(如SM3)来实现。它从一个输入值(比如密钥交换中得到的共享点的坐标)出发,通过多次迭代密码杂凑函数,生成一个足够安全的会话密钥。KDF的目的是确保即使共享秘密被泄露,会话密钥仍然难以被破解。
:针对我SM2知识点,我理解了吗?
AI:看来你已经对SM2算法有了一定的了解,我们可以一起探讨,帮助你更深入地理解SM2算法。
:我的回答结束了,请对我的回答进行评价总结
AI:既然你的回答已经结束,以下是对你掌握SM2算法知识的评价和总结:
理解算法基础:你似乎已经理解了SM2算法是基于椭圆曲线密码学,这是一种非对称加密算法。
密钥对生成:你掌握了SM2算法中密钥对的生成过程,包括选择大素数、计算模数N、选择公钥指数e和计算私钥d。
公钥和私钥用途:你清楚公钥用于加密和验证签名,私钥用于解密和生成签名。
椭圆曲线离散对数问题:你理解椭圆曲线离散对数问题是SM2安全性的基础,并且知道它在算法中的应用。
密钥派生函数:你了解KDF的作用是从共享秘密中派生出会话密钥,并且知道它通常使用密码杂凑函数。
公钥验证:你掌握了如何验证公钥的有效性,包括检查它是否在椭圆曲线上和是否满足特定的阶。
安全性因素:你认识到密钥长度和参数选择对SM2算法安全性的影响。
数字签名流程:你描述了SM2算法在数字签名中的基本流程,包括签名的生成和验证。
应用场景:你理解SM2算法适用于需要高安全性的场合,如数字签名和密钥交换。
与RSA的比较:你能够对比SM2算法和RSA算法,并指出它们的优缺点。
总结来说,你已经对SM2算法有了相当全面的理解。如果你在某些领域还需要进一步的澄清或深入,可以考虑以下几个方向:
实际应用:研究SM2算法在现实世界应用中的具体案例,如电子政务、电子商务等。
安全性分析:深入研究SM2算法可能面临的安全威胁和相应的防护措施。
性能优化:探索如何优化SM2算法以提高其在各种环境下的性能。
继续探索和实践将有助于你在理论和应用方面进一步提高对SM2算法的理解。

二、

:我在学习C语言中的结构体知识点,请你以苏格拉底的方式对我进行提问,一次一个问题,同时生成答案‘
AI:什么是typedef,它与结构体有什么关系
:typedef用于为数据类型创建别名,提高代码的可读性。与结构体结合时,可以使用typedef struct为结构体创建一个简短的名字。
AI: 如果我已经定义了一个使用typedef的别名,如何引用原始类型?
: 一旦使用typedef定义了别名,别名和原始类型可以互换使用,编译器会识别它们是相同的类型。
AI:在C语言中,typedef是否还有其他高级用法?
:是的,typedef可以用于定义更复杂的类型,如函数指针的别名,这在定义回调函数时非常有用。此外,它还可以用于定义数组类型的别名,尽管这种情况较少见。
:针对我C语言中的结构体知识点,我理解了吗?
AI:根据你之前的回答和对结构体知识点的讨论,看起来你对C语言中的结构体已经有了相当好的理解。
:我的回答结束了,请对我的回答进行评价总结
AI:根据你的回答和对C语言结构体知识点的讨论,可以总结如下:
理解程度:你对结构体的概念有清晰的理解,包括它们的定义、成员访问、初始化以及与typedef结合使用。
知识应用:你掌握了如何将结构体应用到实际编程中,包括使用结构体来模拟现实世界的数据和操作。
代码组织:你认识到了结构体在代码组织和数据封装方面的重要性,能够将相关的数据项组合成一个逻辑单元。
指针与结构体:你理解了指针在结构体中的应用,包括通过指针访问结构体成员和动态分配结构体内存。
结构体数组:你掌握了结构体数组的创建和使用,这对于处理批量数据非常重要。
高级概念:你对嵌套结构体、结构体与函数的交互、以及内存对齐和填充等更高级的概念有所了解。
实际应用:你能够将结构体应用于解决实际问题,如使用结构体来模拟对象和状态。
代码可读性:你理解了typedef的使用,这表明你注重代码的可读性和维护性。
性能意识:你意识到了结构体内存布局对程序性能的影响,这是优化程序性能的重要一步。
继续学习:对于结构体的高级用法,如函数指针和复杂数据结构的构建,你可能还有提升空间。
总体来说,你的回答表明你对C语言中的结构体知识点有扎实的理解。如果你希望进一步提升,可以通过解决实际问题、阅读更多示例代码、或者尝试实现更复杂的数据结构来加强你的技能。

学习实践过程遇到的问题与解决方式(AI 驱动,优先使用AI工具解决问题)(2分)

问题:在SM2算法中,如何验证一个公钥的有效性?
AI:

在SM2算法中,验证公钥的有效性通常包括以下几个步骤:

  1. 验证点是否在椭圆曲线上

    • 公钥通常表示为椭圆曲线上的一个点(x, y)。
    • 需要验证这个点是否满足椭圆曲线的方程,即检查 ( y^2 ) 是否等于 ( x^3 + ax + b ) 在给定的有限域内。
  2. 检查点是否为无穷远点

    • 无穷远点不是有效的公钥。
    • 在椭圆曲线密码学中,无穷远点通常用作加法的单位元素。
  3. 验证点是否在有限域内

    • 确保公钥的坐标值在有限域 ( F_q ) 的范围内。
  4. 检查点的阶

    • 公钥对应的点的阶应该等于椭圆曲线的阶 ( n )。
    • 可以通过计算 ( [n]P )(即点倍运算 ( n ) 次)来检查,如果结果是无穷远点,则验证通过。
  5. 检查公钥是否在一组有效的公钥范围内

    • 在某些实现中,可能会有一个公钥的有效范围,需要检查公钥的坐标是否在这个范围内。

一个简单的代码示例来验证公钥的有效性?
以下是一个简化的C语言伪代码示例,用于验证公钥的有效性:

#include "miracl.h"

// 假设全局变量定义了椭圆曲线参数和基点G
extern big para_a, para_b, para_p, para_n;
extern epoint *G;

// 检查点是否在椭圆曲线上
int is_point_on_curve(epoint *point) {
    big x, y, lhs, rhs;
    x = mirvar(0);
    y = mirvar(0);
    lhs = mirvar(0);
    rhs = mirvar(0);

    epoint_get(point, x, y); // 获取点的坐标
    power(x, 3, para_p, lhs); // 计算 x^3
    multiply(lhs, para_a, lhs); // 计算 ax^3
    add(lhs, para_b, lhs); // 计算 ax^3 + b
    power(y, 2, para_p, rhs); // 计算 y^2

    if (mr_compare(lhs, rhs) != 0) {
        return 0; // 不在曲线上
    }
    return 1; // 在曲线上
}

// 验证公钥是否有效
int verify_pubkey(epoint *pubkey) {
    // 检查是否为无穷远点
    if (point_at_infinity(pubkey)) {
        return 0; // 无穷远点无效
    }

    // 检查点是否在椭圆曲线上
    if (!is_point_on_curve(pubkey)) {
        return 0; // 不在曲线上无效
    }

    // 检查点的阶是否为n
    epoint *nP = epoint_init();
    ecurve_mult(para_n, pubkey, nP); // 计算 [n]P
    if (!point_at_infinity(nP)) { // 如果 [n]P 不是无穷远点
        epoint_free(nP);
        return 0; // 阶不为n无效
    }
    epoint_free(nP);

    return 1; // 公钥有效
}

在这个示例中,is_point_on_curve函数检查一个点是否满足椭圆曲线方程,而verify_pubkey函数则验证公钥的有效性,包括检查是否为无穷远点、是否在曲线上以及点的阶是否正确。

作业提交要求(1分)

  1. 提交Markdown 文件,文档命名“学号姓名《密码系统设计》.md”
  2. 提交Markdown 文件转为 PDF,文档命名“学号姓名《密码系统设计》第 X 周.pdf”
  3. 提交代码托管链接(可选):学号姓名 gitee(github) 链接
  4. 内容质量高有加分

参考资料

posted @ 2024-09-29 16:03  20221404李震  阅读(30)  评论(0编辑  收藏  举报