Juicy
Juicy

Reputation: 12520

"Aborted" program using GNU MP "large numbers" library

I'm trying to implement the following (pseudo-code-python) in C using large numbers:

while i * i < n:
    if n % i:
    i += 1

I came up with the following using the gmp.h library:

#include <stdio.h>
#include <gmp.h>

int main () {
    mpz_t n;
    mpz_t i;
    mpz_t o; // Hold constant mpz "1" for incrementing i
    mpz_t x; // Holds "i * i" each loop

    mpz_set_str(n, "338852330881981183", 10);
    mpz_set_str(i, "2", 10);
    mpz_set_str(o, "1", 10);
    mpz_set_str(x, "4", 10);


    while( mpz_cmp(x, n) < 0 ) {
        mpz_add(i, i, o);
        mpz_pow_ui(x, i, 2);
    }

    mpz_clear(i);
    mpz_clear(n);
    return 0;
}

I don't get any errors when I compile with GCC but when I try to run the program I get the following Aborted. I've never seen this before and don't program much in C let alone using gmp.h and very large numbers.

*** glibc detected *** ./factor: realloc(): invalid old size: 0x00000000004006d0 ***
======= Backtrace: =========
/lib/x86_64-linux-gnu/libc.so.6(+0x76d76)[0x7fdc1eb7bd76]
/lib/x86_64-linux-gnu/libc.so.6(+0x7c94c)[0x7fdc1eb8194c]
/lib/x86_64-linux-gnu/libc.so.6(realloc+0xf0)[0x7fdc1eb81c60]
/usr/lib/x86_64-linux-gnu/libgmp.so.10(__gmp_default_reallocate+0x1c)[0x7fdc1ee98a1c]
/usr/lib/x86_64-linux-gnu/libgmp.so.10(__gmpz_realloc+0x3a)[0x7fdc1eeaebba]
/usr/lib/x86_64-linux-gnu/libgmp.so.10(__gmpz_set_str+0x301)[0x7fdc1eeafef1]
./factor[0x400810]
/lib/x86_64-linux-gnu/libc.so.6(__libc_start_main+0xfd)[0x7fdc1eb23ead]
./factor[0x4006f9]
======= Memory map: ========
00400000-00401000 r-xp 00000000 08:01 1723311                            /root/Desktop/factor
00600000-00601000 rw-p 00000000 08:01 1723311                            /root/Desktop/factor
01629000-0164a000 rw-p 00000000 00:00 0                                  [heap]
7fdc18000000-7fdc18021000 rw-p 00000000 00:00 0 
7fdc18021000-7fdc1c000000 ---p 00000000 00:00 0 
7fdc1e8ef000-7fdc1e904000 r-xp 00000000 08:01 1445725                    /lib/x86_64-linux-gnu/libgcc_s.so.1
7fdc1e904000-7fdc1eb04000 ---p 00015000 08:01 1445725                    /lib/x86_64-linux-gnu/libgcc_s.so.1
7fdc1eb04000-7fdc1eb05000 rw-p 00015000 08:01 1445725                    /lib/x86_64-linux-gnu/libgcc_s.so.1
7fdc1eb05000-7fdc1ec85000 r-xp 00000000 08:01 1445701                    /lib/x86_64-linux-gnu/libc-2.13.so
7fdc1ec85000-7fdc1ee85000 ---p 00180000 08:01 1445701                    /lib/x86_64-linux-gnu/libc-2.13.so
7fdc1ee85000-7fdc1ee89000 r--p 00180000 08:01 1445701                    /lib/x86_64-linux-gnu/libc-2.13.so
7fdc1ee89000-7fdc1ee8a000 rw-p 00184000 08:01 1445701                    /lib/x86_64-linux-gnu/libc-2.13.so
7fdc1ee8a000-7fdc1ee8f000 rw-p 00000000 00:00 0 
7fdc1ee8f000-7fdc1eef6000 r-xp 00000000 08:01 2240985                    /usr/lib/x86_64-linux-gnu/libgmp.so.10.0.5
7fdc1eef6000-7fdc1f0f6000 ---p 00067000 08:01 2240985                    /usr/lib/x86_64-linux-gnu/libgmp.so.10.0.5
7fdc1f0f6000-7fdc1f0fe000 rw-p 00067000 08:01 2240985                    /usr/lib/x86_64-linux-gnu/libgmp.so.10.0.5
7fdc1f0fe000-7fdc1f11e000 r-xp 00000000 08:01 1445677                    /lib/x86_64-linux-gnu/ld-2.13.so
7fdc1f2fb000-7fdc1f2fe000 rw-p 00000000 00:00 0 
7fdc1f31b000-7fdc1f31d000 rw-p 00000000 00:00 0 
7fdc1f31d000-7fdc1f31e000 r--p 0001f000 08:01 1445677                    /lib/x86_64-linux-gnu/ld-2.13.so
7fdc1f31e000-7fdc1f31f000 rw-p 00020000 08:01 1445677                    /lib/x86_64-linux-gnu/ld-2.13.so
7fdc1f31f000-7fdc1f320000 rw-p 00000000 00:00 0 
7fffa2304000-7fffa2325000 rw-p 00000000 00:00 0                          [stack]
7fffa23b2000-7fffa23b4000 r-xp 00000000 00:00 0                          [vdso]
ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0                  [vsyscall]
Aborted

Upvotes: 0

Views: 354

Answers (1)

You should initialize GMP bigintegers using mpz_init. So your main function should start with

mpz_t n;
mpz_t i;
mpz_t o; // Hold constant mpz "1" for incrementing i
mpz_t x; // Holds "i * i" each loop

mpz_init(n);
mpz_init(i);
mpz_init(o);
mpz_init(x);

BTW, you probably want to output x near the end of main using

mpz_out_str (stdout, 10, x);

before the calls to mpz_clear

Then you should compile with gcc -Wall -Wextra -g yourprog.c -lgmp -o yourprog. Once the program is correctly debugged, you might add -O2 mtune=native to optimize your program.

Upvotes: 5

Related Questions