错误的地址值传递给C

时间:2016-01-27 07:56:36

标签: c pointers memory-management

这与incorrect pointer value passed to a C function类似,但似乎没有答案。

我有一个名为bigint的结构,其中包含字段char signsize_t lenuint32_t *valbigintbigint_init()函数初始化,该函数为uint32_t数组分配一些内存,设置默认值等。

我有一个功能void bigint_subtract(bigint a, bigint b, bigint *diff),可以a-b存储diff。我之前测试过这个函数,如下所示:

bigint test = bigint_inithex("4567890987654345678987654adbfcaedcfaaebfc625213");
bigint test2 = bigint_inithex("acbefabedfc13271723976aebdfcabefc12837618237");
bigint diff = bigint_init();
bigint_subtract(test,test2,&diff);
printf("0x%s - 0x%s == 0x%s\n\n",bigint_tohex(test), bigint_tohex(test2),bigint_tohex(diff));

在众多其他边缘情况测试,不同长度等测试中。所有测试都检查出来。

现在,我在另一个函数中,void bigint_egcd(bigint a, bigint b, bigint c, bigint *x, bigint *y);这只是扩展的欧几里德算法。在扩展欧几里德算法的主循环中,我有以下代码:

bigint rold, rnew, q, r, ...;
rold = bigint_init();
bigint_cpy(&rold, a);
rnew = bigint_init();
bigint_cpy(&rnew, b);
...[more initializations, etc.]

while(!bigint_isval(rnew, 0)){
    bigint_divide(rold,rnew,&q,&r);

    bigint_cpy(&tmp1, rnew); 
    bigint_multiply(q,rnew,&tmp2); 
    bigint_subtract(rold,tmp2,&rnew); 
    bigint_cpy(&rold, tmp1);
    ....
}

事情出错了,所以我做了一些调试,无法解决任何问题,所以我开始添加printfs。以下是它现在的样子:

while(!bigint_isval(rnew, 0)){
    bigint_divide(rold,rnew,&q,&r);

    printf("\t%s = %s * %s + %s\n", bigint_tohex(rold), bigint_tohex(rnew), bigint_tohex(q), bigint_tohex(r));fflush(stdout);
    bigint_cpy(&tmp1, rnew); 
    printf("\tupdated r = %s - %s * %s = ", bigint_tohex(rold), bigint_tohex(q), bigint_tohex(rnew));fflush(stdout);
    bigint_multiply(q,rnew,&tmp2); 
    printf("%s - %s = (%p) ", bigint_tohex(rold), bigint_tohex(tmp2), &rnew);fflush(stdout);
    bigint_subtract(rold,tmp2,&rnew); 
    printf("%s at address %p\n", bigint_tohex(rnew),&rnew);fflush(stdout);
    bigint_cpy(&rold, tmp1);

bigint_subtract的开头,我添加了以下printf:

void bigint_subtract(bigint a, bigint b, bigint *diff){
    printf("BIGINT_SUBTRACT diff address is %p\n", diff);fflush(stdout);
    ....

所以我发现bigint_subtract收到的地址与bigint_egcd中传递给它的地址不一样。同时,减法实际上是正确的,它只是存储一些随机地址,而不是更新存储在rnew的值。

与此同时,循环后面的完全相同的代码,ts代替其r对应代码,不会出现此行为 - 所有地址都正确传递。 rnewrold已在bigint_egcd的顶部正确初始化,其方式与ts对应方式完全相同。

简而言之,我有一个变量bar1。我将&bar1传递给foo(type *var),但不知何故,只有在foo内,它才会成为其他内容。是什么赋予了?什么样的错误可能导致这种情况发生?

修改

这是bigint_tohex

static const char *BII_HEX="0123456789abcdef";

char *bigint_tohex(bigint a){
    char *hex = calloc((a.len<<3) + 1,sizeof(char));
    uint8_t j;
    for(size_t i=0; i<a.len; i++){
        for(j=0; j<8; j++){
            hex[ (i<<3) + j ] = BII_HEX[(a.val[i] >> ((7-j)<<2)) & 0xF];
        }
    }
    hex[a.len<<3] = 0;

    //any leading 0s should be removed:
    int i=0;
    while(hex[i]=='0' && hex[i+1]!=0) ++i;

    memmove(hex,hex+i,strlen(hex)+1-i);

    if(a.sign == BII_NEG){
        hex = realloc(hex, (strlen(hex)+1)*sizeof(char));
        memmove(hex+1,hex,strlen(hex)+1);
        hex[0]='-';
    }
    return hex;
}

0 个答案:

没有答案