Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
btwise
openssl
提交
3ba1f111
O
openssl
项目概览
btwise
/
openssl
通知
1
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
DevOps
流水线
流水线任务
计划
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
O
openssl
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
DevOps
DevOps
流水线
流水线任务
计划
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
流水线任务
提交
Issue看板
体验新版 GitCode,发现更多精彩内容 >>
提交
3ba1f111
编写于
11月 15, 2001
作者:
B
Bodo Möller
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
Improve EC efficiency.
上级
bbc206fd
变更
4
隐藏空白更改
内联
并排
Showing
4 changed file
with
373 addition
and
13 deletion
+373
-13
CHANGES
CHANGES
+10
-3
crypto/ec/ec.h
crypto/ec/ec.h
+1
-0
crypto/ec/ec_err.c
crypto/ec/ec_err.c
+1
-0
crypto/ec/ec_mult.c
crypto/ec/ec_mult.c
+361
-10
未找到文件。
CHANGES
浏览文件 @
3ba1f111
...
...
@@ -12,6 +12,10 @@
*) applies to 0.9.6a/0.9.6b/0.9.6c and 0.9.7
+) applies to 0.9.7 only
+) Use wNAFs in EC_POINTs_mul() for improved efficiency (about 10%
better than before for single multiplications over P-192 or P-224).
[Bodo Moeller]
-) [In 0.9.6c-engine release:]
Add support for Broadcom crypto accelerator cards, backported
from 0.9.7.
...
...
@@ -943,9 +947,12 @@ des-cbc 3624.96k 5258.21k 5530.91k 5624.30k 5628.26k
don't write to the wrong index in ERR_set_error_data.
[Bodo Moeller]
+) Function EC_POINTs_mul for simultaneous scalar multiplication
of an arbitrary number of elliptic curve points, optionally
including the generator defined for the EC_GROUP.
+) Function EC_POINTs_mul for multiple scalar multiplication
of an arbitrary number of elliptic curve points
\sum scalars[i]*points[i],
optionally including the generator defined for the EC_GROUP:
scalar*generator + \sum scalars[i]*points[i].
EC_POINT_mul is a simple wrapper function for the typical case
that the point list has just one item (besides the optional
generator).
...
...
crypto/ec/ec.h
浏览文件 @
3ba1f111
...
...
@@ -177,6 +177,7 @@ void ERR_load_EC_strings(void);
/* Error codes for the EC functions. */
/* Function codes. */
#define EC_F_COMPUTE_WNAF 143
#define EC_F_EC_GFP_MONT_FIELD_DECODE 133
#define EC_F_EC_GFP_MONT_FIELD_ENCODE 134
#define EC_F_EC_GFP_MONT_FIELD_MUL 131
...
...
crypto/ec/ec_err.c
浏览文件 @
3ba1f111
...
...
@@ -66,6 +66,7 @@
#ifndef OPENSSL_NO_ERR
static
ERR_STRING_DATA
EC_str_functs
[]
=
{
{
ERR_PACK
(
0
,
EC_F_COMPUTE_WNAF
,
0
),
"COMPUTE_WNAF"
},
{
ERR_PACK
(
0
,
EC_F_EC_GFP_MONT_FIELD_DECODE
,
0
),
"ec_GFp_mont_field_decode"
},
{
ERR_PACK
(
0
,
EC_F_EC_GFP_MONT_FIELD_ENCODE
,
0
),
"ec_GFp_mont_field_encode"
},
{
ERR_PACK
(
0
,
EC_F_EC_GFP_MONT_FIELD_MUL
,
0
),
"ec_GFp_mont_field_mul"
},
...
...
crypto/ec/ec_mult.c
浏览文件 @
3ba1f111
...
...
@@ -58,11 +58,369 @@
#include "ec_lcl.h"
/* TODO: width-m NAFs */
/* TODO: optional precomputation of multiples of the generator */
#if 1
/*
* wNAF-based interleaving multi-exponentation method
*/
/* Determine the width-(w+1) Non-Adjacent Form of 'scalar'.
* This is an array r[] of values that are either zero or odd with an
* absolute value less than 2^w satisfying
* scalar = \sum_j r[j]*2^j
* where at most one of any w+1 consecutive digits is non-zero.
*/
static
signed
char
*
compute_wNAF
(
const
BIGNUM
*
scalar
,
int
w
,
size_t
*
ret_len
,
BN_CTX
*
ctx
)
{
BIGNUM
*
c
;
int
ok
=
0
;
signed
char
*
r
=
NULL
;
int
sign
=
1
;
int
bit
,
next_bit
,
mask
;
size_t
len
,
j
;
BN_CTX_start
(
ctx
);
c
=
BN_CTX_get
(
ctx
);
if
(
c
==
NULL
)
goto
err
;
if
(
w
<=
0
||
w
>
7
)
/* 'unsigned char' can represent integers with absolute values less than 2^7 */
{
ECerr
(
EC_F_COMPUTE_WNAF
,
ERR_R_INTERNAL_ERROR
);
goto
err
;
}
bit
=
1
<<
w
;
/* at most 128 */
next_bit
=
bit
<<
1
;
/* at most 256 */
mask
=
next_bit
-
1
;
/* at most 255 */
if
(
!
BN_copy
(
c
,
scalar
))
goto
err
;
if
(
c
->
neg
)
{
sign
=
-
1
;
c
->
neg
=
0
;
}
len
=
BN_num_bits
(
c
)
+
1
;
/* wNAF may be one digit longer than binary representation */
r
=
OPENSSL_malloc
(
len
);
if
(
r
==
NULL
)
goto
err
;
j
=
0
;
while
(
!
BN_is_zero
(
c
))
{
int
u
=
0
;
if
(
BN_is_odd
(
c
))
{
if
(
c
->
d
==
NULL
||
c
->
top
==
0
)
{
ECerr
(
EC_F_COMPUTE_WNAF
,
ERR_R_INTERNAL_ERROR
);
goto
err
;
}
u
=
c
->
d
[
0
]
&
mask
;
if
(
u
&
bit
)
{
u
-=
next_bit
;
/* u < 0 */
if
(
!
BN_add_word
(
c
,
-
u
))
goto
err
;
}
else
{
/* u > 0 */
if
(
!
BN_sub_word
(
c
,
u
))
goto
err
;
}
if
(
u
<=
-
bit
||
u
>=
bit
||
!
(
u
&
1
)
||
c
->
neg
)
{
ECerr
(
EC_F_COMPUTE_WNAF
,
ERR_R_INTERNAL_ERROR
);
goto
err
;
}
}
r
[
j
++
]
=
sign
*
u
;
if
(
BN_is_odd
(
c
))
{
ECerr
(
EC_F_COMPUTE_WNAF
,
ERR_R_INTERNAL_ERROR
);
goto
err
;
}
if
(
!
BN_rshift1
(
c
,
c
))
goto
err
;
}
if
(
j
>
len
)
{
ECerr
(
EC_F_COMPUTE_WNAF
,
ERR_R_INTERNAL_ERROR
);
goto
err
;
}
len
=
j
;
ok
=
1
;
err:
BN_CTX_end
(
ctx
);
if
(
!
ok
)
{
OPENSSL_free
(
r
);
r
=
NULL
;
}
if
(
ok
)
*
ret_len
=
len
;
return
r
;
}
/* TODO: table should be optimised for the wNAF-based implementation */
#define EC_window_bits_for_scalar_size(b) \
((b) >= 2000 ? 6 : \
(b) >= 800 ? 5 : \
(b) >= 300 ? 4 : \
(b) >= 70 ? 3 : \
(b) >= 20 ? 2 : \
1)
/* Compute
* \sum scalars[i]*points[i],
* also including
* scalar*generator
* in the addition if scalar != NULL
*/
int
EC_POINTs_mul
(
const
EC_GROUP
*
group
,
EC_POINT
*
r
,
const
BIGNUM
*
scalar
,
size_t
num
,
const
EC_POINT
*
points
[],
const
BIGNUM
*
scalars
[],
BN_CTX
*
ctx
)
{
BN_CTX
*
new_ctx
=
NULL
;
EC_POINT
*
generator
=
NULL
;
EC_POINT
*
tmp
=
NULL
;
size_t
totalnum
;
size_t
i
,
j
;
int
k
;
int
r_is_inverted
=
0
;
int
r_is_at_infinity
=
1
;
size_t
*
wsize
=
NULL
;
/* individual window sizes */
size_t
*
wNAF_len
=
NULL
;
size_t
max_len
=
0
;
signed
char
**
wNAF
=
NULL
;
/* individual wNAFs */
size_t
num_val
;
EC_POINT
**
val
=
NULL
;
/* precomputation */
EC_POINT
**
v
;
EC_POINT
***
val_sub
=
NULL
;
/* pointers to sub-arrays of 'val' */
int
ret
=
0
;
if
(
scalar
!=
NULL
)
{
generator
=
EC_GROUP_get0_generator
(
group
);
if
(
generator
==
NULL
)
{
ECerr
(
EC_F_EC_POINTS_MUL
,
EC_R_UNDEFINED_GENERATOR
);
return
0
;
}
}
for
(
i
=
0
;
i
<
num
;
i
++
)
{
if
(
group
->
meth
!=
points
[
i
]
->
meth
)
{
ECerr
(
EC_F_EC_POINTS_MUL
,
EC_R_INCOMPATIBLE_OBJECTS
);
return
0
;
}
}
totalnum
=
num
+
(
scalar
!=
NULL
);
wsize
=
OPENSSL_malloc
(
totalnum
*
sizeof
wsize
[
0
]);
wNAF_len
=
OPENSSL_malloc
(
totalnum
*
sizeof
wNAF_len
[
0
]);
wNAF
=
OPENSSL_malloc
(
totalnum
*
sizeof
wNAF
[
0
]
+
1
);
if
(
wNAF
!=
NULL
)
{
wNAF
[
0
]
=
NULL
;
/* preliminary pivot */
}
if
(
wsize
==
NULL
||
wNAF_len
==
NULL
||
wNAF
==
NULL
)
goto
err
;
/* num_val := total number of points to precompute */
num_val
=
0
;
for
(
i
=
0
;
i
<
totalnum
;
i
++
)
{
size_t
bits
;
bits
=
i
<
num
?
BN_num_bits
(
scalars
[
i
])
:
BN_num_bits
(
scalar
);
wsize
[
i
]
=
EC_window_bits_for_scalar_size
(
bits
);
num_val
+=
1u
<<
(
wsize
[
i
]
-
1
);
}
/* all precomputed points go into a single array 'val',
* 'val_sub[i]' is a pointer to the subarray for the i-th point */
val
=
OPENSSL_malloc
((
num_val
+
1
)
*
sizeof
val
[
0
]);
if
(
val
==
NULL
)
goto
err
;
val
[
num_val
]
=
NULL
;
/* pivot element */
val_sub
=
OPENSSL_malloc
(
totalnum
*
sizeof
val_sub
[
0
]);
if
(
val_sub
==
NULL
)
goto
err
;
/* allocate points for precomputation */
v
=
val
;
for
(
i
=
0
;
i
<
totalnum
;
i
++
)
{
val_sub
[
i
]
=
v
;
for
(
j
=
0
;
j
<
(
1u
<<
(
wsize
[
i
]
-
1
));
j
++
)
{
*
v
=
EC_POINT_new
(
group
);
if
(
*
v
==
NULL
)
goto
err
;
v
++
;
}
}
if
(
!
(
v
==
val
+
num_val
))
{
ECerr
(
EC_F_EC_POINTS_MUL
,
ERR_R_INTERNAL_ERROR
);
goto
err
;
}
if
(
ctx
==
NULL
)
{
ctx
=
new_ctx
=
BN_CTX_new
();
if
(
ctx
==
NULL
)
goto
err
;
}
tmp
=
EC_POINT_new
(
group
);
if
(
tmp
==
NULL
)
goto
err
;
/* prepare precomputed values:
* val_sub[i][0] := points[i]
* val_sub[i][1] := 3 * points[i]
* val_sub[i][2] := 5 * points[i]
* ...
*/
for
(
i
=
0
;
i
<
totalnum
;
i
++
)
{
if
(
i
<
num
)
{
if
(
!
EC_POINT_copy
(
val_sub
[
i
][
0
],
points
[
i
]))
goto
err
;
}
else
{
if
(
!
EC_POINT_copy
(
val_sub
[
i
][
0
],
generator
))
goto
err
;
}
if
(
wsize
[
i
]
>
1
)
{
if
(
!
EC_POINT_dbl
(
group
,
tmp
,
val_sub
[
i
][
0
],
ctx
))
goto
err
;
for
(
j
=
1
;
j
<
(
1u
<<
(
wsize
[
i
]
-
1
));
j
++
)
{
if
(
!
EC_POINT_add
(
group
,
val_sub
[
i
][
j
],
val_sub
[
i
][
j
-
1
],
tmp
,
ctx
))
goto
err
;
}
}
wNAF
[
i
+
1
]
=
NULL
;
/* make sure we always have a pivot */
wNAF
[
i
]
=
compute_wNAF
((
i
<
num
?
scalars
[
i
]
:
scalar
),
wsize
[
i
],
&
wNAF_len
[
i
],
ctx
);
if
(
wNAF
[
i
]
==
NULL
)
goto
err
;
if
(
wNAF_len
[
i
]
>
max_len
)
max_len
=
wNAF_len
[
i
];
}
#if 1
/* optional; EC_window_bits_for_scalar_size assumes we do this step */
if
(
!
EC_POINTs_make_affine
(
group
,
num_val
,
val
,
ctx
))
goto
err
;
#endif
r_is_at_infinity
=
1
;
for
(
k
=
max_len
-
1
;
k
>=
0
;
k
--
)
{
if
(
!
r_is_at_infinity
)
{
if
(
!
EC_POINT_dbl
(
group
,
r
,
r
,
ctx
))
goto
err
;
}
for
(
i
=
0
;
i
<
totalnum
;
i
++
)
{
if
(
wNAF_len
[
i
]
>
k
)
{
int
digit
=
wNAF
[
i
][
k
];
int
is_neg
;
if
(
digit
)
{
is_neg
=
digit
<
0
;
if
(
is_neg
)
digit
=
-
digit
;
if
(
is_neg
!=
r_is_inverted
)
{
if
(
!
r_is_at_infinity
)
{
if
(
!
EC_POINT_invert
(
group
,
r
,
ctx
))
goto
err
;
}
r_is_inverted
=
!
r_is_inverted
;
}
/* digit > 0 */
if
(
r_is_at_infinity
)
{
if
(
!
EC_POINT_copy
(
r
,
val_sub
[
i
][
digit
>>
1
]))
goto
err
;
r_is_at_infinity
=
0
;
}
else
{
if
(
!
EC_POINT_add
(
group
,
r
,
r
,
val_sub
[
i
][
digit
>>
1
],
ctx
))
goto
err
;
}
}
}
}
}
if
(
r_is_at_infinity
)
{
if
(
!
EC_POINT_set_to_infinity
(
group
,
r
))
goto
err
;
}
else
{
if
(
r_is_inverted
)
if
(
!
EC_POINT_invert
(
group
,
r
,
ctx
))
goto
err
;
}
ret
=
1
;
err:
if
(
new_ctx
!=
NULL
)
BN_CTX_free
(
new_ctx
);
if
(
tmp
!=
NULL
)
EC_POINT_free
(
tmp
);
if
(
wsize
!=
NULL
)
OPENSSL_free
(
wsize
);
if
(
wNAF_len
!=
NULL
)
OPENSSL_free
(
wNAF_len
);
if
(
wNAF
!=
NULL
)
{
signed
char
**
w
;
for
(
w
=
wNAF
;
*
w
!=
NULL
;
w
++
)
OPENSSL_free
(
*
w
);
OPENSSL_free
(
wNAF
);
}
if
(
val
!=
NULL
)
{
for
(
v
=
val
;
*
v
!=
NULL
;
v
++
)
EC_POINT_clear_free
(
*
v
);
OPENSSL_free
(
val
);
}
if
(
val_sub
!=
NULL
)
{
OPENSSL_free
(
val_sub
);
}
return
ret
;
}
#else
/*
* Basic interleaving multi-exponentation method
*/
#define EC_window_bits_for_scalar_size(b) \
((b) >= 2000 ? 6 : \
(b) >= 800 ? 5 : \
...
...
@@ -143,14 +501,6 @@
* w = 1 if 19 >= b
*/
/* Compute
* \sum scalars[i]*points[i],
* also including
* scalar*generator
* in the addition if scalar != NULL
*/
int
EC_POINTs_mul
(
const
EC_GROUP
*
group
,
EC_POINT
*
r
,
const
BIGNUM
*
scalar
,
size_t
num
,
const
EC_POINT
*
points
[],
const
BIGNUM
*
scalars
[],
BN_CTX
*
ctx
)
{
...
...
@@ -369,6 +719,7 @@ int EC_POINTs_mul(const EC_GROUP *group, EC_POINT *r, const BIGNUM *scalar,
}
return
ret
;
}
#endif
int
EC_POINT_mul
(
const
EC_GROUP
*
group
,
EC_POINT
*
r
,
const
BIGNUM
*
g_scalar
,
const
EC_POINT
*
point
,
const
BIGNUM
*
p_scalar
,
BN_CTX
*
ctx
)
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录