首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >OpenSSL BN_CTX使用

OpenSSL BN_CTX使用
EN

Stack Overflow用户
提问于 2013-05-08 09:47:11
回答 1查看 5.4K关注 0票数 15

这里中我了解到,BN_CTX是一个包含BIGNUM临时变量的结构。这些BIGNUM变量何时进入BN_CTX的BN_POOL?如果我有一个bignum_ctx BN_CTX *ctx;(要么在函数顶部声明,要么作为参数传入),我应该什么时候做?

代码语言:javascript
复制
ctx = BN_CTX_new();
/* Do something */
BN_CTX_free(ctx);

我什么时候应该做下面的事情呢?

代码语言:javascript
复制
BN_CTX_start(ctx);
/* Do something */
BN_CTX_end(ctx);

如果我有一个大型BIGNUM *bn;,在什么情况下我应该使用

代码语言:javascript
复制
BN_CTX_start(ctx);
bn = BN_CTX_get(ctx);
BN_CTX_end(ctx);

而不是只是新的和自由的实例?

代码语言:javascript
复制
bn = BN_new();
if (bn)
    BN_free(bn);
EN

回答 1

Stack Overflow用户

发布于 2013-05-16 03:56:14

我在这里回答我自己的问题。我想这种事总是会发生的。

OpenSSL中的BIGNUM是一个复杂的结构,包含任意大的数字,因此重复创建和释放BIGNUM实例将导致相当大的开销。创建并使用BIGNUM上下文或BN_CTX来节省此开销。

结构

BN_CTX结构包含两个结构:BN_POOLBN_STACKBN_POOL使用链接列表保存一捆临时符号,而BN_STACK则管理堆栈框架。

On Create

BN_CTX实例ctx是用BN_CTX_new()创建的。函数必须调用BN_CTX_start()才能首先获得新的堆栈帧。通过调用BN_CTX_get(ctx),OpenSSL在BN_POOL of ctx中查找未使用的大号。如果没有可用的temp,OpenSSL将创建一个并链接到链接列表。这必须在将ctx作为参数传递给其他函数之前完成。

当然,有一种机制可以防止用户创建过多的临时宏。您可以在BN_POOL中创建的预定义值为16。一旦超出限制,可能的分割错误将在OpenSSL库中的任意位置发生。

出口

在使用从ctx获得并准备退出的BIGNUM实例完成该函数之后,将调用BN_CTX_end()来释放临时值,这意味着这些值将变为“未使用”,并且可以被下一个BN_CTX_get()请求。

最后,在多次使用BN_CTX_start()BN_CTX_end()之后,可能会调用BN_CTX_end()来释放BN_STACK结构,并在BN_POOL中清除自由值。

示例代码

代码语言:javascript
复制
void foo(){
    BN_CTX* ctx;
    ctx = BN_CTX_new();

    /* Using BIGNUM context in a series of BIGNUM operations */
    bar(ctx);
    bar(ctx);
    bar(ctx);

    /* Using BIGNUM context in a function called in loops */
    while(/*condition*/){
        bar(ctx);
    }

    BN_CTX_free(ctx);
}

这是函数bar( )

代码语言:javascript
复制
void bar(BN_CTX* ctx){
    BIGNUM *bn;
    BN_CTX_start(ctx);
    bn = BN_CTX_get(ctx);

    /* Do something with bn */

    BN_CTX_end(ctx);
}

函数foo()创建一个新的BIGNUM上下文,并将其作为参数传递给函数bar()。在bar()第一次调用BN_CTX_get()时,将创建一个临时大号并将其存储在BN_POOL中并返回。在后续的BN_CTX_get()中,bar()将不会创建新的bignum,而是返回它首先创建的一个。这个临时的大号最终将被BN_CTX_free() in foo()释放。

结论

在考虑性能时,请使用BN_CTX将BIGNUM创建的开销传递给以下函数:

  1. 要求BIGNUM结构保存临时大数字,以及
  2. 按顺序调用以执行某些bignum操作,或
  3. 被反复调用的循环。

请注意,在BN_CTX中存储的大型表的数量是有限制的。如果性能不是问题,那么使用

代码语言:javascript
复制
bn = BN_new();
if (bn)
    BN_free(bn);

一切都很好。

票数 25
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/16437475

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档