C号字节表示

时间:2011-06-20 17:40:31

标签: c byte biginteger gmp sign

我有一个代表bigint的unsigned char vector mynumber[]。 这个数字是正数,我想将其转换为负数。

我试过这种方式

for(int i = 0; i < dimvector;i++)
 mynumber[i] = ~mynumber[i];

我迭代我的矢量,但我需要总结一个。 如何总和?

如果我有溢出,怎么解决?

我使用GMP,导出后我必须将矢量传递给SHA256。

最后,我使用导入(GMP)在大数字中转换摘要的结果。

在导入中我有同样的导出问题。 标志很重要。

1 个答案:

答案 0 :(得分:2)

Crikey。好的,首先,如何实现bignums:在GMP和其他库中,通常您将固定宽度字段指定为“肢体”或数字的一部分。到目前为止,你已经得到了那个部分,除了你更有可能分别使用uint32_tuint64_t用于32位和64位平台,因为这些是寄存器和指令的大小,如{ {1}}如果添加两个寄存器溢出,则设置进位标志。

无论如何,重点是,这些肢体代表了bignum的实际大小,而不是它的标志。使用两个补码,我们期望在某个地方有一个符号位,但是如果你想调整一个数字(并且adc不关心签名,它只是进行二进制加法)会变得混乱,因为你需要找到旧标志位,提取它,记住它,然后它回到正确的位置......非常慢。

我不确定你想要实现的是如何反转每个肢体中的位。如果你想象一组像这样的肢体(简单的简称)

adc

你最终得到:

1011 0111 1010 1011 = 47019

无论如何,GMP并不代表四肢的标志。 GMP中的带符号整数类型是0100 1000 0101 0100 = 18516 ,由此结构定义:

mpz_t

正如您所看到的,typedef struct { int _mp_alloc; /* Number of *limbs* allocated and pointed to by the _mp_d field. */ int _mp_size; /* abs(_mp_size) is the number of limbs the last field points to. If _mp_size is negative this is a negative number. */ mp_limb_t *_mp_d; /* Pointer to the limbs. */ } __mpz_struct; typedef __mpz_struct mpz_t[1]; 是GMP代表签名号码的方式。

在代码中(具体来说,_mp_size)你会看到这个:

mpz/aors.h

实际操作由usize = u->_mp_size; vsize = VARIATION v->_mp_size; // ..... if ((usize ^ vsize) < 0) { /* U and V have different sign. Need to compare them to determine which operand to subtract from which. */ // does subtraction instead of add. 系列函数执行,这些函数是您的无符号类型。

GMP具有许多基本类型的导入/导出功能,可以让您正确设置大小。我不太确定你要做什么,但假设它们不够,你应该能够自己设置它。