当前位置: 首页 > news >正文

openssl签名报错

在调用RSA_private_encrypt函数时遇到如下报错。

0:error:0D07803A:asn1 encoding routines:asn1_item_embed_d2i:nested asn1 error:crypto/asn1/tasn_dec.c:309:Type=X509
0:error:2406C06E:random number generator:RAND_DRBG_instantiate:error retrieving entropy:crypto/rand/drbg_lib.c:335:
0:error:2406B072:random number generator:RAND_DRBG_generate:in error state:crypto/rand/drbg_lib.c:588:
0:error:2406C06E:random number generator:RAND_DRBG_instantiate:error retrieving entropy:crypto/rand/drbg_lib.c:335:
0:error:2406B072:random number generator:RAND_DRBG_generate:in error state:crypto/rand/drbg_lib.c:588:
0:error:04088003:rsa routines:RSA_setup_blinding:BN lib:crypto/rsa/rsa_crpt.c:155:
0:error:04066044:rsa routines:rsa_ossl_private_encrypt:internal error:crypto/rsa/rsa_ossl.c:297:

openssl库版本为1.1.1Q。

$ openssl version
OpenSSL 1.1.1q 

查看openssl源码,随机数生成器(DRBG)在获取熵时遇到了错误,错误码RAND_R_ERROR_RETRIEVING_ENTROPY。

int RAND_DRBG_instantiate(RAND_DRBG *drbg,const unsigned char *pers, size_t perslen)
{if (drbg->get_entropy != NULL)entropylen = drbg->get_entropy(drbg, &entropy, min_entropy,   min_entropylen, max_entropylen, 0);if (entropylen < min_entropylen || entropylen > max_entropylen) {RANDerr(RAND_F_RAND_DRBG_INSTANTIATE, RAND_R_ERROR_RETRIEVING_ENTROPY);goto end;}

将程序与openssl库做静态链接,放到其它机器上运行一切正常,排除了openssl库的问题,应当是系统问题。

# gcc rsasign.c -L/lib/x86_64-linux-gnu/ libssl.a  libcrypto.a -ldl -lpthread 

使用strace调试,发现问题出在getrandom函数,出错的机器上提示函数未实现。

$ strace ./rsasign
...
prlimit64(0, RLIMIT_STACK, NULL, {rlim_cur=8192*1024, rlim_max=RLIM64_INFINITY}) = 0
getrandom(0x7f0366004398, 8, GRND_NONBLOCK) = -1 ENOSYS (Function not implemented)
brk(NULL)                               = 0x7f036633b000
brk(0x7f036635c000)                     = 0x7f036635c000

单独写一个getrandom.c测试程序:

#include<stdio.h>
#include <errno.h>
#include <string.h>
#define _GNU_SOURCE        /* See feature_test_macros(7) */
#include <unistd.h>
#include <sys/syscall.h>   /* For SYS_xxx definitions */
#define __NR_getrandom 318int main(int argc, void *argv[])
{unsigned char buf[32];ssize_t result = syscall(__NR_getrandom, buf, sizeof(buf), 0);if (result == -1) {printf("getrandom failed:%s\n", strerror(errno));return 1;}for (int i = 0; i < sizeof(buf); i++)printf("%02x ", buf[i]);printf("\n");return 0;
}

运行测试程序,同样有如下报错:

$ gcc getrandom.c -o rand
$ ./rand
getrandom failed:Function not implemented

其它正常运行的设备上,如下信息,可以正常获取到随机数:

$ ./rand
32 69 78 58 4b c8 8b a4 3d c5 11 95 b6 de 00 29 4f 6f 9e 02 0b 66 28 78 f9 70 e4 53 62 1b 64 e6 

openssl文件crypto/rand/rand_unix.c中函数syscall_random代码如下,linux内核在3.17版本之后开始支持getrandom系统调用。出问题的系统内核为3.10,还不能支持getrandom。

/* syscall_random(): Try to get random data using a system call* returns the number of bytes returned in buf, or < 0 on error.*/
static ssize_t syscall_random(void *buf, size_t buflen)
{/* Linux supports this since version 3.17 */
#  if defined(__linux) && defined(__NR_getrandom)return syscall(__NR_getrandom, buf, buflen, 0);

另外,对于linux系统,随机数还可以从以下设备文件中获取。

#  define DEVRANDOM "/dev/urandom", "/dev/random", "/dev/hwrng", "/dev/srandom"

在由设备文件读取随机数之前,函数wait_random_seeded等待设备有足够的种子(seed)。

size_t rand_pool_acquire_entropy(RAND_POOL *pool)
{
#   if defined(OPENSSL_RAND_SEED_DEVRANDOM)if (wait_random_seeded()) {size_t bytes_needed;unsigned char *buffer;bytes_needed = rand_pool_bytes_needed(pool, 1 /*entropy_factor*/);for (i = 0; bytes_needed > 0 && i < OSSL_NELEM(random_device_paths); i++) {ssize_t bytes = 0; int attempts = 3;    /* Maximum number of consecutive unsuccessful attempts */const int fd = get_random_device(i);if (fd == -1) continue;while (bytes_needed != 0 && attempts-- > 0) {buffer = rand_pool_add_begin(pool, bytes_needed);bytes = read(fd, buffer, bytes_needed);

从内核4.8(DEVRANDOM_SAFE_KERNEL)开始,当/dev/random(DEVRANDOM_WAIT)可读时,不确保设备/dev/urandom被正确的Seed。这里使用uname获取系统的内核版本,如果版本号大于4.8,返回0。

否则,检查/dev/random是否可读,来判断/dev/urandom是否正确的Seed。

static int wait_random_seeded(void)
{static int seeded = OPENSSL_RAND_SEED_DEVRANDOM_SHM_ID < 0;static const int kernel_version[] = { DEVRANDOM_SAFE_KERNEL };if (!seeded) {     /* See if anything has created the global seeded indication */if ((shm_id = shmget(OPENSSL_RAND_SEED_DEVRANDOM_SHM_ID, 1, 0)) == -1) {/** Check the kernel's version and fail if it is too recent.* Linux kernels from 4.8 onwards do not guarantee that* /dev/urandom is properly seeded when /dev/random becomes* readable.  However, such kernels support the getentropy(2)* system call and this should always succeed which renders* this alternative but essentially identical source moot.*/if (uname(&un) == 0) {kernel[0] = atoi(un.release);p = strchr(un.release, '.');kernel[1] = p == NULL ? 0 : atoi(p + 1);if (kernel[0] > kernel_version[0] || (kernel[0] == kernel_version[0] && kernel[1] >= kernel_version[1]))return 0;}/* Open /dev/random and wait for it to be readable */if ((fd = open(DEVRANDOM_WAIT, O_RDONLY)) != -1) {if (DEVRANDM_WAIT_USE_SELECT && fd < FD_SETSIZE) {FD_ZERO(&fds);FD_SET(fd, &fds);while ((r = select(fd + 1, &fds, NULL, NULL, NULL)) < 0 && errno == EINTR);} else {while ((r = read(fd, &c, 1)) < 0 && errno == EINTR);

出现问题的系统使用的内核为3.10,但是uname系统调用获取到的内核版本为5.16,导致了问题的产生。修复uname的问题,获取内核版本号为实际的版本号3.10之后,问题得到解决。

命令strace跟踪,不再调用getrandom,而是使用了urandom来获取随机数。

$ strace ./rsasign
open("/dev/urandom", O_RDONLY|O_NOCTTY|O_NONBLOCK) = 3

相关文章:

openssl签名报错

在调用RSA_private_encrypt函数时遇到如下报错。 0:error:0D07803A:asn1 encoding routines:asn1_item_embed_d2i:nested asn1 error:crypto/asn1/tasn_dec.c:309:TypeX509 0:error:2406C06E:random number generator:RAND_DRBG_instantiate:error retrieving entropy:crypto/…...

如何在不使用 VPN 的情况下通过 SOCKS 隧道安全地路由 Web 流量

前些天发现了一个巨牛的人工智能学习网站&#xff0c;通俗易懂&#xff0c;风趣幽默&#xff0c;忍不住分享一下给大家。点击跳转到网站。 介绍 在某些情况下&#xff0c;您可能会发现自己处于一个不安全的网络或者有一个过于严格的防火墙&#xff0c;您会希望确保没有人在监…...

android openGL ES详解——缓冲区VBO/VAO/EBO/FBO

目录 一、缓冲区对象概念 二、分类 三、顶点缓冲区对象VBO 1、概念 2、为什么使用VBO 3、如何使用VBO 生成缓冲区对象 绑定缓冲区对象 输入缓冲区数据 更新缓冲区中的数据 删除缓冲区 4、VBO应用 四、顶点数组对象VAO 1、概念 2、为什么使用VAO 3、如何使用VAO…...

计算机网络——传输层服务

传输层会给段加上目标ip和目标端口号 应用层去识别报文的开始和结束...

gin入门教程(8):渲染与静态文件

目录结构 /hello-gin │ ├── cmd/ │ └── main.go ├── pkg/ │ └── shared_lib.go ├── internal/ │ └── internal_lib.go ├── api/ │ └── routes.go ├── config/ │ └── config.go ├── migrations/ │ └── migration.sql └…...

Fast Simulation of Mass-Spring Systems in Rust 论文阅读

参考资料&#xff1a; 文章目录 概述流程概述&#xff1a;1.前置知识1.1 运动方程&#xff08;牛顿第二定律&#xff09;1.2 二阶导数的离散化1.3 代入运动方程1.4 物理意义 2. 将隐式积分问题转化为一个优化问题2.1 要解的是隐式积分问题是&#xff1a;2.2 引入辅助变量d1. 左…...

javaWeb项目-ssm+vue志愿者招募网站功能说明介绍

本项目源码&#xff08;点击下方链接下载&#xff09;&#xff1a;java-ssmvue志愿者招募网站实现源码(项目源码-说明文档)资源-CSDN文库 项目关键技术 开发工具&#xff1a;IDEA 、Eclipse 编程语言: Java 数据库: MySQL5.7 框架&#xff1a;ssm、Springboot 前端&#xff1a…...

Selenium + Titanium代理获取请求的接口数据

有一个采集数据的需求&#xff0c;分析了页面数据后发现列表有一个id&#xff0c;但是没有其他数据&#xff0c;打开详情并不是通过id&#xff0c;而是其他一个字段&#xff0c;这就说明通过selenium抓取页面数据还不行&#xff0c;还要接口返回的数据。这个时候就需要用到代理…...

ELK Stack与Graylog:强大的日志分析和可视化工具

ELK Stack的使用方法 ELK Stack由Elasticsearch、Logstash和Kibana三个核心组件组成&#xff0c;它们协同工作&#xff0c;提供了从日志收集、解析、存储到可视化的完整解决方案。 安装与配置Elasticsearch Elasticsearch是ELK Stack的存储和查询引擎&#xff0c;负责存储日…...

安全见闻(6)——开阔眼界,不做井底之蛙

内容预览 ≧∀≦ゞ 安全见闻六&#xff1a;通讯协议安全问题剖析声明引言一、通讯协议的保密性问题二、通讯协议的完整性问题三、身份验证问题四、可用性问题五、通讯协议的实现问题六、协议设计缺陷七、移动通讯协议的安全问题八、物联网通讯协议的安全问题九、工业控制系统通…...

GRU神经网络理解

全文参考以下B站视频及《神经网络与深度学习》邱锡鹏&#xff0c;侧重对GPU模型的理解&#xff0c;初学者入门自用记录&#xff0c;有问题请指正【重温经典】GRU循环神经网络 —— LSTM的轻量级版本&#xff0c;大白话讲解_哔哩哔哩_bilibili 更新门、重置门、学习与输出 注&a…...

Windows 10、Office 2016/2019 和 PPTP 和 L2TP协议即将退役,企业应尽早做好准备

关心微软技术和产品的朋友一定对这个网站很熟悉&#xff1a;https://microsoftgraveyard.com/&#xff0c;这里静静的躺着很多微软技术和产品。近日&#xff0c;微软又在准备一场新的“告别仪式”了&#xff0c;这次是 Windows 10、Office 2016/2019 和一些老旧的协议与技术。让…...

论文阅读:Guided Linear Upsampling

今天介绍一篇有趣的文章&#xff0c;Guided Linear Upsampling&#xff0c;基于引导的线性上采样&#xff0c;这是发表在 ACM transaction on Graphic 的一篇工作。 Abstract 引导上采样是加速高分辨率图像处理的一种有效方法。在本文中&#xff0c;文章作者提出了一种简单而…...

深度图和RGB图对齐

坐标系间的转换_坐标系转换-CSDN博客 深度图与彩色图的配准与对齐_彩色 深度 配准-CSDN博客 kinect 2.0 SDK学习笔记&#xff08;四&#xff09;--深度图与彩色图对齐_mapdepthframetocolorspace-CSDN博客 相机标定&#xff08;三&#xff09;-相机成像模型_相机小孔成像模型…...

滑动窗口与TCP的缓冲区(buff)的关系

‌滑动窗口与TCP的缓冲区&#xff08;buff&#xff09;有直接关联。‌ 滑动窗口机制是TCP协议中用于流量控制和拥塞控制的重要机制。滑动窗口实际上是一个操作系统开辟的缓存空间&#xff0c;用于指定无需等待确认应答即可继续发送数据的最大值。这个窗口大小&#xff08;win&…...

一款好用的搜索软件——everthing(搜索比文件资源管理器快)

everthing官网链接 在官网选择下载 1.下载后双击打开 2.点击OK&#xff08;需要其他语言自己选择&#xff09; 3.选择安装位置&#xff08;路径最好别带中文和空格&#xff09; 继续点击下一步 4. 点击下一步 5.继续点击安装 6.然后就完成了 7.点击打开然后就可以搜索了...

C#WPF的App.xaml启动第一个窗体的3种方式

WPF的App.xaml启动第一个窗体的3种方式 1.使用App.xaml的StartupUri属性启动&#xff08;推荐使用&#xff09; 在App.xaml文件中&#xff0c;你可以设置StartupUri属性来指定启动时显示的第一个窗口&#xff1a; <Application x:Class"浅看一眼WPF.App"xmlns&…...

【JAVA毕设】基于JAVA的酒店管理系统

一、项目介绍 本系统前端框架采用了比较流行的渐进式JavaScript框架Vue.js。使用Vue-Router实现动态路由&#xff0c;Ajax实现前后端通信&#xff0c;Element-plus组件库使页面快速成型。后端部分&#xff1a;采用SpringBoot作为开发框架&#xff0c;同时集成MyBatis、Redis、…...

聚类--机器学习西瓜书阅读笔记(六)

无监督学习&#xff1a;通过对无标记训练样本的学习&#xff0c;揭示数据内在规律和性质。 聚类试图将数据集中的样本划分为若干不相交的子集&#xff0c;聚类过程自动形成簇结构&#xff0c;簇对应的语义需要子集命名把握。 聚类过程可以作为单独的过程&#xff0c;寻找数据…...

OpenHarmony(1)开发环境搭建

一&#xff1a;开源项目 OpenHarmony是由开放原子开源基金会&#xff08;OpenAtom Foundation&#xff09;孵化及运营的开源项目&#xff0c;目标是面向全场景、全连接、全智能时代&#xff0c;基于开源的方式&#xff0c;搭建一个智能终端设备操作系统的框架和平台&#xff0…...

【Axure高保真原型】引导弹窗

今天和大家中分享引导弹窗的原型模板&#xff0c;载入页面后&#xff0c;会显示引导弹窗&#xff0c;适用于引导用户使用页面&#xff0c;点击完成后&#xff0c;会显示下一个引导弹窗&#xff0c;直至最后一个引导弹窗完成后进入首页。具体效果可以点击下方视频观看或打开下方…...

接口测试中缓存处理策略

在接口测试中&#xff0c;缓存处理策略是一个关键环节&#xff0c;直接影响测试结果的准确性和可靠性。合理的缓存处理策略能够确保测试环境的一致性&#xff0c;避免因缓存数据导致的测试偏差。以下是接口测试中常见的缓存处理策略及其详细说明&#xff1a; 一、缓存处理的核…...

React 第五十五节 Router 中 useAsyncError的使用详解

前言 useAsyncError 是 React Router v6.4 引入的一个钩子&#xff0c;用于处理异步操作&#xff08;如数据加载&#xff09;中的错误。下面我将详细解释其用途并提供代码示例。 一、useAsyncError 用途 处理异步错误&#xff1a;捕获在 loader 或 action 中发生的异步错误替…...

内存分配函数malloc kmalloc vmalloc

内存分配函数malloc kmalloc vmalloc malloc实现步骤: 1)请求大小调整:首先,malloc 需要调整用户请求的大小,以适应内部数据结构(例如,可能需要存储额外的元数据)。通常,这包括对齐调整,确保分配的内存地址满足特定硬件要求(如对齐到8字节或16字节边界)。 2)空闲…...

三维GIS开发cesium智慧地铁教程(5)Cesium相机控制

一、环境搭建 <script src"../cesium1.99/Build/Cesium/Cesium.js"></script> <link rel"stylesheet" href"../cesium1.99/Build/Cesium/Widgets/widgets.css"> 关键配置点&#xff1a; 路径验证&#xff1a;确保相对路径.…...

docker 部署发现spring.profiles.active 问题

报错&#xff1a; org.springframework.boot.context.config.InvalidConfigDataPropertyException: Property spring.profiles.active imported from location class path resource [application-test.yml] is invalid in a profile specific resource [origin: class path re…...

JVM 内存结构 详解

内存结构 运行时数据区&#xff1a; Java虚拟机在运行Java程序过程中管理的内存区域。 程序计数器&#xff1a; ​ 线程私有&#xff0c;程序控制流的指示器&#xff0c;分支、循环、跳转、异常处理、线程恢复等基础功能都依赖这个计数器完成。 ​ 每个线程都有一个程序计数…...

C++课设:简易日历程序(支持传统节假日 + 二十四节气 + 个人纪念日管理)

名人说:路漫漫其修远兮,吾将上下而求索。—— 屈原《离骚》 创作者:Code_流苏(CSDN)(一个喜欢古诗词和编程的Coder😊) 专栏介绍:《编程项目实战》 目录 一、为什么要开发一个日历程序?1. 深入理解时间算法2. 练习面向对象设计3. 学习数据结构应用二、核心算法深度解析…...

数学建模-滑翔伞伞翼面积的设计,运动状态计算和优化 !

我们考虑滑翔伞的伞翼面积设计问题以及运动状态描述。滑翔伞的性能主要取决于伞翼面积、气动特性以及飞行员的重量。我们的目标是建立数学模型来描述滑翔伞的运动状态,并优化伞翼面积的设计。 一、问题分析 滑翔伞在飞行过程中受到重力、升力和阻力的作用。升力和阻力与伞翼面…...

SQL Server 触发器调用存储过程实现发送 HTTP 请求

文章目录 需求分析解决第 1 步:前置条件,启用 OLE 自动化方式 1:使用 SQL 实现启用 OLE 自动化方式 2:Sql Server 2005启动OLE自动化方式 3:Sql Server 2008启动OLE自动化第 2 步:创建存储过程第 3 步:创建触发器扩展 - 如何调试?第 1 步:登录 SQL Server 2008第 2 步…...