Karim BELABAS on Mon, 13 Jan 2003 14:37:29 +0100 (MET)


[Date Prev] [Date Next] [Thread Prev] [Thread Next] [Date Index] [Thread Index]

Re: is this the right list for this question?


On Mon, 13 Jan 2003, Ramón Casero Cañas wrote:
> I do not know whether this is the right list for a question regarding some
> C++ code I'm writting based on PARI functions (maybe I should write to the
> users list). It's basic code, actually; at present, just input a (bool **) and
> copy it to a PARI matrix. I get a segmentation fault at the outbeaut()
> function:
>
> ----------------------------------------------------------------
>
> inverse_mat_mod2: size = 32
> Matrix? a = 1078694052
>
> [  ***   segmentation fault: bug in PARI or calling program.
>   ***   Error in the PARI system. End of program.
>
> ----------------------------------------------------------------
>
> bool inverse_mat_mod2(bool **_a, unsigned _size, bool _CHECK) {
>   long paristacksize = 500000;
>   GEN a;           // temp matrix by columns
>   unsigned i, j;   // counter
>   unsigned sizepari = _size + 1;
>   GEN v;           // auxiliay pointer for columns
>   GEN z;           // auxiliary element of the matrix
>
>   if (sizeof(long) * _size * _size > (unsigned)paristacksize) {
>     paristacksize = sizeof(long) * _size * _size * 2; // this's a guess of
> mine w/o any base
>   }

The space needed to _hold_ a square matrix of dimension n with elements in
F_2 (as t_INTMOD) is (at most)

  SIZE := (n + 1)^2 + n^2 * [ 3 + 2 * 3 ]

long integers [ using t_VECSMALL and 'long' entries reduce the bracketed
quantity from 9 to 1 ].

You need some more space to actually _operate_ on a. Multiplying SIZE by 10
should be enough. [ with t_VECSMALL, most things are done in place, and you
need about 3 * SIZE ]

>   pari_init(paristacksize, 2); // init PARI stack
>
>   /* allocate memory for the temp matrix
>    * note: remember that PARI matrices of mxn need (m+1)x(n+1), and
>    * that elements go a[1], a[2], ..., as a[0] is for type
>    * information */
>   std::cout << "inverse_mat_mod2: size = " << _size << std::endl;
>   a = cgetg(sizepari, t_MAT); // `a' has _size columns
>   if (!a) err(talker, "inverse_mat_mod2: memory!\n");

cgetg always return a non-NULL result. In case of problems, it raises a
"stack overflow" exception which terminates the program. Your test
is a no-op.

>   for (i = 1; i < sizepari; ++i) { // alloc `a' columns
>     a[i] = lgetg(sizepari, t_COL);
>     if (!a[i]) err(talker, "inverse_mat_mod2: memory!\n");

Same here.

>   }
>   for (i = 1; i < sizepari; ++i) { // alloc space for elements
>     for (j = 1; j < sizepari; ++j) {
>
>        z = gcoeff(a, i, j);
>        z = cgetg(3, t_INTMOD);
>        z[1] = (long)2;
>        z[2] = (long)1;

Rather

  z[1] = lstoi(2);
  z[2] = lstoi(1);

The components of an INTMOD are GENs, not longs !

>     }
>   }
>
>   std::cout << "Matrix? a = " << (int)a << std::endl;
>   outbeaut(a);
>   return true;
> }

Maybe outbeaut( ginv(a) ) ?

Cheers,

    Karim.
-- 
Karim Belabas                    Tel: (+33) (0)1 69 15 57 48
Dép. de Mathématiques, Bât. 425  Fax: (+33) (0)1 69 15 60 19
Université Paris-Sud             Email: Karim.Belabas@math.u-psud.fr
F-91405 Orsay (France)           http://www.math.u-psud.fr/~belabas/
--
PARI/GP Home Page: http://www.parigp-home.de/