File Coverage

Pari.xs
Criterion Covered Total %
statement 959 1494 64.1
branch 501 1048 47.8
condition n/a
subroutine n/a
pod n/a
total 1460 2542 57.4


line stmt bran cond sub pod time code
1             #ifdef _WIN32 /* including windows.h later leads to macro name collisions */
2             # define WIN32_LEAN_AND_MEAN
3             # include
4             #endif
5              
6             #define strtoi PARI_strtoi /* NetBSD declares a function strtoi() conflicting with PARI one */
7              
8             #ifdef USE_STANDALONE_PARILIB
9             # include
10             # include
11             #else
12             # include
13             # if PARI_VERSION_EXP < 2011000 /* Probably much earlier too... */
14             # include
15             # endif
16             # if 1 || PARI_VERSION_EXP < 2011000 /* Misses foreign*, varentries, fetch_entry... */
17             # include
18             # endif
19              
20             #ifdef HAVE_PARIPRIV
21             # if 1 || PARI_VERSION_EXP < 2011000 /* Misses EpNEW, EpVAR, precreal */
22             # include
23             # endif
24             #endif
25              
26             # if 1 || PARI_VERSION_EXP < 2011000 /* misses gp_get_plot */ /* Probably much earlier too... */
27             # include /* init_opts */
28             # endif
29             #endif /* !defined USE_STANDALONE_PARILIB */
30              
31             /* On some systems /usr/include/sys/dl.h attempts to declare
32             ladd which pari.h already defined with a different meaning.
33              
34             It is not clear whether this is a correct fix...
35             */
36             #undef ladd
37             #undef strtoi /* See above */
38              
39             #define PERL_POLLUTE /* We use older varnames */
40              
41             #ifdef __cplusplus
42             extern "C" {
43             #endif
44              
45             #if defined(_WIN64) && defined(long)
46             # undef long
47             # define NEED_TO_REDEFINE_LONG
48             #endif
49              
50             #include "EXTERN.h"
51             #include "perl.h"
52             #include "XSUB.h"
53             #include "func_codes.h"
54              
55             #ifdef NEED_TO_REDEFINE_LONG
56             # ifdef SSize_t /* XXX Defect in Perl??? Not in 5.18.0, but in 5.28.1. */
57             typedef SSize_t mySSize_t;
58             # undef SSize_t /* long long; would be expanded to long long long long */
59             # define SSize_t mySSize_t
60             # endif
61             # define long long long /* see parigen.h */
62             # define MYatol atoll
63             #else
64             # define MYatol atol
65             #endif
66              
67             #ifdef __cplusplus
68             }
69             #endif
70              
71             #ifndef PTRV
72             # define PTRV IV
73             #endif
74              
75             #ifndef TWOPOTBYTES_IN_LONG /* Miss starting from 2.4.2; taken from 2.3.5 */
76             #ifdef LONG_IS_64BIT
77             # define TWOPOTBYTES_IN_LONG 3
78             #else
79             # define TWOPOTBYTES_IN_LONG 2
80             #endif
81             #define BYTES_IN_LONG (1<
82             #endif
83              
84             #if !defined(na) && defined(PERL_VERSION) && (PERL_VERSION > 7) /* Added in 6 (???), Removed in 13 */
85             # define na PL_na
86             # define sv_no PL_sv_no
87             # define sv_yes PL_sv_yes
88             #endif
89              
90             #if PARI_VERSION_EXP < 2002012
91             void init_defaults(int force); /* Probably, will never be fixed in 2.1.* */
92             #endif
93              
94             #if PARI_VERSION_EXP >= 2004000 /* Unclear when exactly they disappeared. Miss in 3.5.0 */
95             extern entree functions_basic[];
96             extern entree functions_highlevel[];
97             #endif
98              
99             #if PARI_VERSION_EXP < 2009000
100             # define myPARI_top (top)
101             # define myPARI_bot (bot)
102             #else
103             # define myPARI_top (pari_mainstack->top)
104             # define myPARI_bot (pari_mainstack->bot)
105             # define lgef lg
106             #endif
107              
108             #if PARI_VERSION_EXP < 2002009
109             #define gen_0 gzero
110             #define gen_1 gun
111             #endif
112              
113             #if PARI_VERSION_EXP < 2002011
114             # define readseq lisexpr
115             #endif
116              
117             #if PARI_VERSION_EXP < 2002010
118             # define gequal gegal
119             #endif
120              
121             #if PARI_VERSION_EXP < 2000009
122             # define gpow gpui
123             #endif
124              
125             #if PARI_VERSION_EXP < 2002013
126             # define myforcecopy forcecopy
127             #else
128             # define myforcecopy gcopy
129             #endif
130              
131             /* This should not be defined at this moment, but in 5.001n is. */
132             #ifdef coeff
133             # undef coeff
134             #endif
135              
136             #ifdef warner
137             # undef warner
138             #endif
139              
140             /* $Id: Pari.xs,v 1.7 1995/01/23 18:50:58 ilya Exp ilya $ */
141             /* dFUNCTION should be the last declaration! */
142              
143             #ifdef __cplusplus
144             #define VARARG ...
145             #else
146             #define VARARG
147             #endif
148              
149             #define dFUNCTION(retv) retv (*FUNCTION)(VARARG) = \
150             (retv (*)(VARARG)) XSANY.any_dptr
151              
152             #if DEBUG_PARI
153             static int pari_debug = 0;
154             # define RUN_IF_DEBUG_PARI(a) \
155             do { if (pari_debug) {a;} } while (0)
156             # define PARI_DEBUG_set(d) ((pari_debug = (d)), 1)
157             # define PARI_DEBUG() (pari_debug)
158             #else
159             # define RUN_IF_DEBUG_PARI(a)
160             # define PARI_DEBUG_set(d) (0)
161             # define PARI_DEBUG(d) (0)
162             #endif
163              
164             #define DO_INTERFACE(inter) math_pari_subaddr = CAT2(XS_Math__Pari_interface, inter)
165             #define CASE_INTERFACE(inter) case inter: \
166             DO_INTERFACE(inter); break
167              
168             #ifndef XSINTERFACE_FUNC_SET /* Not in 5.004_04 */
169             # define XSINTERFACE_FUNC_SET(cv,f) \
170             CvXSUBANY(cv).any_dptr = (void (*) (void*))(f)
171             #endif
172              
173             #ifndef SvPV_nolen
174             STRLEN n___a;
175             # define SvPV_nolen(sv) SvPV((sv),n___a)
176             #endif
177              
178             #ifndef PERL_UNUSED_VAR
179             # define PERL_UNUSED_VAR(var) if (0) var = var
180             #endif
181              
182             /* Here is the rationals for managing SVs which keep GENs:
183             * SVs may reference GENs on stack, or
184             * or GEN on stack which we later moved to heap (so nobody else knows where they are!), or
185             * GEN which was originally on heap.
186             We assume that we do not need to free stuff
187             that was originally on heap. However, we need to free the stuff we
188             moved from the stack ourself.
189            
190             Here is how we do it: The variables that were initially off stack
191             have SvPVX == GENheap.
192            
193             The variables that were moved from the stack have SvPVX ==
194             GENmovedOffStack.
195              
196             If the variable is on stack, and it is the oldest one which is on
197             stack, then SvPVX == GENfirstOnStack.
198              
199             Otherwise SvPVX is the next older SV that refers to a GEN on stack.
200              
201             In the last two cases SvCUR is the offset on stack of the stack
202             frame on the entry into the function for which SV is the argument.
203             */
204              
205             #ifndef USE_SLOW_NARGS_ACCESS
206             # define USE_SLOW_NARGS_ACCESS (defined(PERL_VERSION) && (PERL_VERSION > 9))
207             #endif
208              
209             #if USE_SLOW_NARGS_ACCESS
210             # define PARI_MAGIC_TYPE ((char)0xDE)
211             # define PARI_MAGIC_PRIVATE 0x2020
212              
213             /* Can't return IV, since may not fit in mg_ptr;
214             However, we use it to store numargs, and result of gclone() */
215             static void**
216 38321           PARI_SV_to_voidpp(SV *const sv)
217             {
218             MAGIC *mg;
219 40876 50         for (mg = SvMAGIC(sv); mg; mg = mg->mg_moremagic) {
220 40876 100         if (mg->mg_type == PARI_MAGIC_TYPE
221 38321 50         && mg->mg_private == PARI_MAGIC_PRIVATE)
222 38321           return (void **) &mg->mg_ptr;
223             }
224 0           croak("panic: PARI narg value not attached");
225             return NULL;
226             }
227             # define PARI_SV_to_intp(sv) ((int*)PARI_SV_to_voidpp(sv))
228              
229             static void
230 1181           SV_myvoidp_set(SV *sv, void *p)
231             {
232             MAGIC *mg;
233              
234 1181           mg = sv_magicext((SV*)sv, NULL, PARI_MAGIC_TYPE, NULL, p, 0);
235 1181           mg->mg_private = PARI_MAGIC_PRIVATE;
236 1181           }
237              
238             # define SV_myvoidp_reset_clone(sv) \
239             STMT_START { \
240             if(SvTYPE(sv) == SVt_PVAV) { \
241             void **p = PARI_SV_to_voidpp(sv); \
242             *p = (void*) gclone((GEN)*p); \
243             } else { \
244             SV_myvoidp_reset_clone_IVX(sv); \
245             } } STMT_END
246              
247             /* Should be applied to SV* and AV* only */
248             # define SV_myvoidp_get(sv) \
249             ((SvTYPE(sv) == SVt_PVAV) ? *PARI_SV_to_voidpp(sv) : INT2PTR(void*,SvIV(sv)))
250             # define CV_myint_get(sv) INT2PTR(PTRV, *PARI_SV_to_voidpp(sv)) /* INT2PTR is two-way; PTR2INT missing in newer Perls */
251             # define CV_myint_set(sv,i) SV_myvoidp_set((sv), INT2PTR(void*,(PTRV)i))
252             #else /* !USE_SLOW_NARGS_ACCESS */
253             # define CV_myint_get(sv) SvIVX(sv) /* IVOK is not set! */
254             # define CV_myint_set(sv, i) (SvIVX(sv) = (i))
255             # define SV_myvoidp_get(sv) INT2PTR(void*, SvIVX(sv))
256             # define SV_myvoidp_set(sv, p) (SvIVX(sv) = PTR2IV(p))
257             # define SV_myvoidp_reset_clone SV_myvoidp_reset_clone_IVX
258             #endif
259              
260             #define SV_myvoidp_reset_clone_IVX(sv) (SvIVX(sv) = PTR2IV(gclone(INT2PTR(GEN, SvIV(sv)))))
261             #define CV_NUMARGS_get CV_myint_get
262             #define CV_NUMARGS_set CV_myint_set
263              
264             #ifndef USE_SLOW_ARRAY_ACCESS
265             # define USE_SLOW_ARRAY_ACCESS (defined(PERL_VERSION) && (PERL_VERSION > 9))
266             #endif
267              
268             #if USE_SLOW_ARRAY_ACCESS
269             /* 5.9.x and later assert that you're not using SvPVX() and SvCUR() on arrays,
270             so need a little more code to cheat round this. */
271             # define NEED_SLOW_ARRAY_ACCESS(sv) (SvTYPE(sv) == SVt_PVAV)
272             # define AV_SET_LEVEL(sv, val) (AvARRAY(sv) = (SV **)(val))
273             # define AV_GET_LEVEL(sv) ((char*)AvARRAY(sv))
274             #else
275             # define NEED_SLOW_ARRAY_ACCESS(sv) 0
276             # define AV_SET_LEVEL(sv, val) croak("Panic AV LEVEL") /* This will never be called */
277             # define AV_GET_LEVEL(sv) (croak("Panic AV LEVEL"),Nullch) /* This will never be called */
278             #endif
279              
280             /* XXXX May need a flavor when we know it is an AV??? */
281             #define SV_PARISTACK_set(sv, stack) \
282             (NEED_SLOW_ARRAY_ACCESS(sv) ? ( \
283             AV_SET_LEVEL(sv, stack), (void)0 \
284             ) : ( \
285             SvPVX(sv) = stack, (void)0 \
286             ))
287              
288             #define SV_OAVMA_PARISTACK_set(sv, level, stack) \
289             (NEED_SLOW_ARRAY_ACCESS(sv) ? ( \
290             AvFILLp(sv) = (level), \
291             AV_SET_LEVEL(sv, (stack)), (void)0 \
292             ) : ( \
293             SvCUR(sv) = (level), \
294             SvPVX(sv) = (char*)(stack), (void)0 \
295             ))
296              
297             #define SV_OAVMA_PARISTACK_get(sv, level, stack) \
298             (NEED_SLOW_ARRAY_ACCESS(sv) ? ( \
299             (level) = AvFILLp(sv), \
300             (stack) = AV_GET_LEVEL(sv), (void)0 \
301             ) : ( \
302             (level) = SvCUR(sv), \
303             (stack) = SvPVX(sv), (void)0 \
304             ))
305              
306             #define SV_OAVMA_switch(next, sv, newval) \
307             ( NEED_SLOW_ARRAY_ACCESS(sv) ? ( \
308             (next) = (SV *)AvARRAY(sv), \
309             AV_SET_LEVEL(sv, newval), (void)0 \
310             ) : ( \
311             next = (SV *) SvPVX(sv), \
312             SvPVX(sv) = newval, (void)0 \
313             ))
314              
315             #define SV_Stack_find_next(sv) \
316             ( NEED_SLOW_ARRAY_ACCESS(sv) ? ( \
317             (SV *)AvARRAY(sv) \
318             ) : ( \
319             (SV *) SvPVX(sv) \
320             ))
321              
322             #define GENmovedOffStack ((char*) 1) /* Just an atom. */
323             #define GENfirstOnStack ((char*) 2) /* Just an atom. */
324             #define GENheap NULL
325             #define ifact mpfact
326              
327             #if PARI_VERSION_EXP >= 2004002
328             typedef SV * PariVar; /* For loop variables. */
329             #else
330             typedef entree * PariVar; /* For loop variables. */
331             #endif
332              
333             typedef entree * PariName; /* For changevalue. */
334             #if PARI_VERSION_EXP >= 2004002
335             typedef GEN PariExpr, PariExpr2, PariExprV;
336             #else
337             typedef char * PariExpr, *PariExpr2, *PariExprV;
338             #endif
339             typedef GEN * GEN_Ptr;
340              
341             #if PARI_VERSION_EXP >= 2004002 /* Undocumented when it appeared; present in 2.5.0 */
342             # define AssignPariExprR(var,arg,is_void,sv) \
343             ((SvROK(arg) && (SvTYPE(SvRV(arg)) == SVt_PVCV)) ? \
344             (var = make_trampolinecv(SvRV(arg),is_void,sv)) \
345             : (warn("Argument-types E,I of string type not supported yet, substituting x->1"), var = code_return_1))
346             # define AssignPariExpr2R(var,arg,is_void,sv1,sv2) (warn("Argument-types E,I not supported yet, substituting (x,y)->1"), var = code2_return_1)
347             #else /* PARI_VERSION_EXP < 2004002 */ /* Undocumented when it appeared; present in 2.5.0 */
348             # define AssignPariExprR(var,arg,is_void,sv) \
349             ((SvROK(arg) && SvTYPE(SvRV(arg)) == SVt_PVCV) ? \
350             (var = ((char*)&(SvRV(arg)->sv_flags)) + LSB_in_U32) \
351             : (var = (char *)SvPV(arg,na)))
352             # define AssignPariExpr2R(var,arg,is_void,sv1,sv2) AssignPariExprR(var,arg,is_void,sv1)
353             #endif /* PARI_VERSION_EXP < 2004002 */ /* Undocumented when it appeared; present in 2.5.0 */
354              
355             #define MAYBE_NOTVOID 0 /* Used in 'typemap' - but only for Expr2 now */
356             #define AssignPariExpr2(var,arg) AssignPariExpr2R(var,arg,MAYBE_NOTVOID, 0, 0)
357             #define AssignPariExprR0(var,arg,is_void) AssignPariExprR(var,arg,is_void,0)
358              
359             XS((*math_pari_subaddr)); /* On CygWin XS() has attribute conflicting with static */
360              
361             #if defined(MYMALLOC) && defined(EMBEDMYMALLOC) && defined(UNEMBEDMYMALLOC)
362              
363             Malloc_t
364             malloc(register size_t nbytes)
365             {
366             return Perl_malloc(nbytes);
367             }
368              
369             Free_t
370             free(void *mp)
371             {
372             Perl_mfree(mp); /* What to return? */
373             }
374              
375             Malloc_t
376             realloc(void *mp, size_t nbytes)
377             {
378             return Perl_realloc(mp, nbytes);
379             }
380              
381             #endif
382              
383             /* We make a "fake" PVAV, not enough entries. */
384              
385             /* This macro resets avma *immediately* if IN is a global
386             static GEN (such as gnil, gen_1 etc). So it should be called near
387             the end of stack-manipulating scope */
388             #define setSVpari(sv, in, oldavma) \
389             setSVpari_or_do(sv, in, oldavma, avma = oldavma)
390              
391             #define setSVpari_keep_avma(sv, in, oldavma) \
392             setSVpari_or_do(sv, in, oldavma, ((void)0))
393              
394             #define setSVpari_or_do(sv, in, oldavma, action) do { \
395             sv_setref_pv(sv, "Math::Pari", (void*)in); \
396             morphSVpari(sv, in, oldavma, action); \
397             } while (0)
398              
399             #define morphSVpari(sv, in, oldavma, action) do { \
400             if (is_matvec_t(typ(in)) && SvTYPE(SvRV(sv)) != SVt_PVAV) { \
401             make_PariAV(sv); \
402             } \
403             if (isonstack(in)) { \
404             SV* g = SvRV(sv); \
405             SV_OAVMA_PARISTACK_set(g, oldavma - myPARI_bot, PariStack); \
406             PariStack = g; \
407             perlavma = avma; \
408             onStack_inc; \
409             } else { \
410             action; \
411             } \
412             SVnum_inc; \
413             } while (0)
414              
415             #if PARI_VERSION_EXP < 2002005
416             typedef long pari_sp;
417             #endif
418              
419             SV* PariStack; /* PariStack keeps the latest SV that
420             * keeps a GEN on stack. */
421             pari_sp perlavma; /* How much stack is needed
422             for GENs in Perl variables. */
423             pari_sp sentinel; /* How much stack was used
424             when Pari called Perl. */
425              
426             #ifdef DEBUG_PARI
427              
428             long SVnum;
429             long SVnumtotal;
430             long onStack;
431             long offStack;
432              
433             # define SVnum_inc (SVnum++, SVnumtotal++)
434             # define SVnum_dec (SVnum--)
435             # define onStack_inc (onStack++)
436             # define onStack_dec (onStack--)
437             # define offStack_inc (offStack++)
438             #else /* !defined DEBUG_PARI */
439             # define SVnum_inc
440             # define SVnum_dec
441             # define onStack_inc
442             # define onStack_dec
443             # define offStack_inc
444             #endif /* !defined DEBUG_PARI */
445              
446             #define pari_version_exp() PARI_VERSION_EXP
447              
448             #if !defined(ndec2prec) && PARI_VERSION_EXP < 2003000
449             # ifndef pariK1
450             # define pariK1 (0.103810253/(BYTES_IN_LONG/4)) /* log(10)/(SL*log(2)) */
451             # endif
452             # define ndec2prec(d) (long)(d*pariK1 + 3)
453             #endif
454              
455             #if PARI_VERSION_EXP >= 2008000
456             # define prec_words get_localprec()
457             # define prec_bits get_localbitprec()
458             #else /* !(PARI_VERSION_EXP >= 2008000) */
459             # if PARI_VERSION_EXP >= 2002012
460             # define prec_words precreal
461             # else
462             # define prec_words prec
463             # endif
464             #endif
465              
466             #if PARI_VERSION_EXP >= 2003005 /* XXX When did it actually start??? */
467             long dummy;
468             /* # define prec_words_set(w) (fmt_nbPset(w), precreal = prec2nbits(w)) */
469             # define prec_digits_set(w) setrealprecision(w, &dummy)
470             # define fmt_nbP getrealprecision()
471             # define fmt_nbPset(v) ((void)0)
472             #else /* !(PARI_VERSION_EXP >= 2008000) */
473             # define prec_words_set(p) (prec_words = (p))
474             # define prec_digits_set(d) prec_words_set(ndec2prec(d))
475              
476             int fmt_nb;
477             # define fmt_nbP fmt_nb
478             # define fmt_nbPset(v) fmt_nb = (v)
479              
480             # ifdef LONG_IS_64BIT
481             # define def_fmt_nb 38
482             # else
483             # define def_fmt_nb 28
484             # endif
485              
486             #endif /* !(PARI_VERSION_EXP >= 2008000) */
487              
488              
489             #ifdef USE_PERLLOCAL_PREC
490              
491             #else /* !defined(USE_PERLLOCAL_PREC) */
492             #endif /* !defined(USE_PERLLOCAL_PREC) */
493              
494             #if PARI_VERSION_EXP >= 2000018
495              
496             GEN
497 1           _gbitneg(GEN g)
498             {
499 1           return gbitneg(g,-1);
500             }
501              
502             #endif /* PARI_VERSION_EXP >= 2000018 */
503              
504             #if PARI_VERSION_EXP >= 2002001
505              
506             GEN
507 3           _gbitshiftl(GEN g, long s)
508             {
509 3           return gshift(g, s);
510             }
511              
512             #endif
513             #if PARI_VERSION_EXP >= 2002001 && PARI_VERSION_EXP <= 2002007
514              
515             GEN
516             _gbitshiftr(GEN g, long s)
517             {
518             return gshift3(g, -s, signe(g) < 0); /* Bug up to 2.2.2: 1 should be OK */
519             }
520              
521             #endif /* PARI_VERSION_EXP >= 2002001 && PARI_VERSION_EXP <= 2002007 */
522              
523             /* Upgrade to PVAV, attach a magic of type 'P' which is just a reference to
524             ourselves (non-standard refcounts, so needs special logic on DESTROY) */
525             void
526 1171           make_PariAV(SV *sv)
527             {
528 1171           AV *av = (AV*)SvRV(sv);
529 1171           char *s = SvPVX(av);
530 1171           void *p = INT2PTR(void*, SvIVX(av));
531 1171           SV *newsub = newRV_noinc((SV*)av); /* cannot use sv, it may be
532             sv_restore()d */
533              
534 1171 50         (void)SvUPGRADE((SV*)av, SVt_PVAV);
535 1171 50         SV_PARISTACK_set(av, s);
536 1171           SV_myvoidp_set((SV*)av, p);
537 1171           sv_magic((SV*)av, newsub, 'P', Nullch, 0);
538 1171           SvREFCNT_dec(newsub); /* now RC(newsub)==1 */
539             /* We avoid an reference loop, so should be careful on DESTROY */
540             #if 0
541             if ((mg = SvMAGIC((SV*)av)) && mg->mg_type == 'P' /* be extra paranoid */
542             && (mg->mg_flags & MGf_REFCOUNTED)) {
543             /* mg->mg_flags &= ~MGf_REFCOUNTED; */
544             /* SvREFCNT_dec(sv); */
545             sv_2mortal((SV*)av); /* We restore refcount on DESTROY */
546             }
547             #endif
548 1171           }
549              
550             SV*
551 0           wrongT(SV *sv, char *file, int line)
552             {
553 0 0         if (SvTYPE(sv) != SVt_PVCV && SvTYPE(sv) != SVt_PVGV) {
    0          
554 0           croak("Got the type 0x%x instead of CV=0x%x or GV=0x%x in %s, %i",
555 0           SvTYPE(sv), SVt_PVCV, SVt_PVGV, file, line);
556             } else {
557 0           croak("Something very wrong in %s, %i", file, line);
558             }
559             return NULL; /* To pacify compiler. */
560             }
561              
562             HV *pariStash; /* For quick id. */
563             HV *pariEpStash;
564              
565             #if PARI_VERSION_EXP < 2002012 /* Probably earlier too */
566             /* Copied from anal.c. */
567             static entree *
568             installep(void *f, char *name, int len, int valence, int add, entree **table)
569             {
570             entree *ep = (entree *) gpmalloc(sizeof(entree) + add + len+1);
571             const entree *ep1 = initial_value(ep);
572             char *u = (char *) ep1 + add;
573              
574             ep->name = u; strncpy(u, name,len); u[len]=0;
575             ep->args = NULL; ep->help = NULL; ep->code = NULL;
576             ep->value = f? f: (void *) ep1;
577             ep->next = *table;
578             ep->valence = valence;
579             ep->menu = 0;
580             return *table = ep;
581             }
582             #endif /* PARI_VERSION_EXP >= 2002012 */
583              
584             #if PARI_VERSION_EXP >= 2002012 /* Probably earlier too */
585             # if PARI_VERSION_EXP < 2009000 /* Probably earlier too */
586             # define my_fetch_named_var fetch_named_var
587             # else /* !(PARI_VERSION_EXP < 2009000) */
588             # define MAY_USE_FETCH_ENTRY
589             entree *
590 29           my_fetch_named_var(const char *s)
591             { /* A part of fetch_user_var() of 2.9.0 */
592 29           entree *ep = fetch_entry(s);
593 29           switch (EpVALENCE(ep))
594             {
595             case EpNEW:
596 2           pari_var_create(ep); /* fall through */
597 2           ep->valence = EpVAR;
598 2           ep->value = initial_value(ep);
599             case EpVAR:
600 29           return ep;
601 0           default: pari_err(e_MISC, "variable <<<%s>>> already exists with incompatible valence", s);
602             }
603 0           return 0; /* NOT REACHED */
604             }
605             # endif /* !(PARI_VERSION_EXP < 2009000) */
606             #else
607             static entree *
608             my_fetch_named_var(char *s)
609             {
610             long hash;
611             entree * ep = is_entry_intern(s, functions_hash, &hash);
612              
613             if (ep) {
614             if (EpVALENCE(ep) != EpVAR
615             #if PARI_VERSION_EXP >= 2004000
616             || typ(ep->value)==t_CLOSURE
617             #endif
618             )
619             croak("Got a function name instead of a variable");
620             } else {
621             ep = installep(NULL, s, strlen(s), EpVAR, 7*sizeof(long),
622             functions_hash + hash);
623             manage_var(0,ep);
624             }
625             return ep;
626             }
627             #endif
628              
629             #if PARI_VERSION_EXP <= 2002000 /* Global after 2.2.0 */
630             static void
631             changevalue(entree *ep, GEN val)
632             {
633             GEN y = gclone(val), x = (GEN)ep->value;
634              
635             ep->value = (void *)y;
636             if (x == (GEN) initial_value(ep) || !isclone(x))
637             {
638             y[-1] = (long)x; /* push new value */
639             return;
640             }
641             y[-1] = x[-1]; /* save initial value */
642             killbloc(x); /* destroy intermediate one */
643             }
644             #endif
645              
646             static GEN
647 584031           my_gpui(GEN x, GEN y)
648             {
649 584031           return gpow(x, y, prec_words);
650             }
651              
652             static long
653 9           numvar(GEN x)
654             {
655 18 50         if (typ(x) != t_POL || lgef(x) != 4 ||
656 18 50         !gcmp0((GEN)x[2]) || !gcmp1((GEN)x[3]))
657 0           croak("Corrupted data: should be variable");
658 9           return varn(x);
659             }
660              
661             static SV *
662 27           PARIvar(char *s)
663             {
664             SV *sv;
665             entree *ep;
666              
667 27           ep = my_fetch_named_var(s);
668 27           sv = NEWSV(909,0);
669 27           sv_setref_pv(sv, "Math::Pari::Ep", (void*)ep);
670 27           make_PariAV(sv);
671 27           return sv;
672             }
673              
674             #if PARI_VERSION_EXP >= 2004000
675             # define ORDVAR(n) (n) /* The big change... */
676             # define FETCH_CODE_const const /* ->code is const */
677             #else
678             # define ORDVAR(n) ordvar[n]
679             # define FETCH_CODE_const /* fetch_named_variable() cannot take const */
680             #endif /* PARI_VERSION_EXP >= 2004000 */
681              
682             static entree *
683 3           findVariable(SV *sv, int generate)
684             { /* Used for PariVar (generate=1, before 2.4.2) and PariName (generate=0; only for changevalue()) */
685             /* There may be 4 important cases:
686             a) we got a 'word' string, which we interpret as the name of
687             the variable to use;
688             b1) It is a pari value containing a polynomial 0+1*v, we use it;
689             b2) It is other pari value, we ignore it;
690             c) it is a string containing junk, same as 'b';
691             d) It is an ep value => typo (same iterator in two loops).
692             In any case we localize the value.
693             */
694 3           FETCH_CODE_const char *s = Nullch;
695             FETCH_CODE_const char *s1;
696             long hash;
697             entree *ep;
698             char name[50];
699              
700 3 100         if (SvROK(sv)) {
701 2           SV* tsv = SvRV(sv);
702 2 50         if (SvOBJECT(tsv)) {
703 2 100         if (SvSTASH(tsv) == pariStash) {
704             is_pari:
705             {
706 1 50         GEN x = (GEN)SV_myvoidp_get(tsv);
    50          
707 1 50         if (typ(x) == t_POL /* Polynomial. */
708 1 50         && lgef(x)==4 /* 2 terms */
709 1 50         && (gcmp0((GEN)x[2])) /* Free */
710 1 50         && (gcmp1((GEN)x[3]))) { /* Leading */
711 1           s = varentries[ORDVAR(varn(x))]->name;
712 1           goto repeat;
713             }
714 0           goto ignore;
715             }
716 1 50         } else if (SvSTASH(tsv) == pariEpStash) {
717             is_pari_ep:
718             {
719             /* Itsn't good to croak: $v=PARIvar 'v'; vector(3,$v,'v'); */
720             if (generate)
721             /*croak("Same iterator in embedded PARI loop construct")*/;
722 1 50         return (entree*) SV_myvoidp_get(tsv);
    0          
723             }
724 0 0         } else if (sv_derived_from(sv, "Math::Pari")) { /* Avoid recursion */
725 0 0         if (sv_derived_from(sv, "Math::Pari::Ep"))
726 0           goto is_pari_ep;
727             else
728 0           goto is_pari;
729             }
730             }
731             }
732 1 50         if (!SvOK(sv))
    0          
    0          
733 0           goto ignore;
734 1 50         s = SvPV(sv,na);
735             repeat:
736 2           s1 = s;
737 8 100         while (isalnum((unsigned char)*s1))
738 6           s1++;
739 2 50         if (*s1 || s1 == s || !isalpha((unsigned char)*s)) {
    50          
    50          
740             static int depth;
741              
742             ignore:
743 0 0         if (!generate)
744 0           croak("Bad PARI variable name \"%s\" specified",s);
745 0           SAVEINT(depth);
746 0           sprintf(name, "intiter%i",depth++);
747 0           s = name;
748 0           goto repeat;
749             }
750              
751 3           return my_fetch_named_var(s);
752             }
753              
754             #if PARI_VERSION_EXP >= 2004000
755             /* # define findVariable(sv,gen) (sv) */ /* Not needed */
756             # define bindVariable(sv) (sv)
757             #else /* !(PARI_VERSION_EXP >= 2004000) */
758             static PariVar
759             bindVariable(SV *sv)
760             {
761             /* There may be 4 important cases:
762             a) we got a 'word' string, which we interpret as the name of
763             the variable to use;
764             b1) It is a pari value containing a polynomial 0+1*v, we use it;
765             b2) It is other pari value, we ignore it, and generate a suitable name of iteration variable;
766             c) it is a string containing junk, same as 'b2';
767             d) It is an ep value => typo (same iterator in two loops).
768             In any case we localize the value.
769             */
770             long override = 0;
771             entree *ep;
772              
773             if (!SvREADONLY(sv)) {
774             save_item(sv); /* Localize it. */
775             override = 1;
776             }
777             ep = findVariable(sv, 1);
778             if (override) {
779             sv_setref_pv(sv, "Math::Pari::Ep", (void*)ep);
780             make_PariAV(sv);
781             }
782             return ep;
783             }
784             #endif /* !(PARI_VERSION_EXP >= 2004000) */
785              
786             static int
787 0           not_here(char *s)
788             {
789 0           croak("%s not implemented on this architecture", s);
790             return -1;
791             }
792              
793             unsigned long
794 3           longword(GEN x, long n)
795             {
796 3 100         if (n < 0 || n >= lg(x))
    100          
797 2           croak("The longword %ld ordinal out of bound", n);
798 1           return x[n];
799             }
800              
801             SV* worksv = 0;
802             SV* workErrsv = 0;
803              
804             /* Our output routines may be called several times during a Perl's statement */
805             #define renewWorkSv \
806             ((SvREFCNT(worksv) > 1 && /* Still in use */ \
807             (SvREFCNT_dec(worksv), /* Abandon the old copy */ \
808             worksv = NEWSV(910,0))), \
809             SvREFCNT_inc(worksv)) /* It is going to be mortalized soon */
810              
811             void
812 0           svputc(char c)
813             {
814 0           sv_catpvn(worksv,&c,1);
815 0           }
816              
817             #if PARI_VERSION_EXP >= 2002005
818             # define PUTS_CONST const
819             #else
820             # define PUTS_CONST
821             #endif
822              
823             #if PARI_VERSION_EXP < 2005000 && !defined(taille) /* When did it appear??? In >= 2.5.0 the definition of taille() and taille2() are mixed up */
824             # define gsizeword taille
825             #endif
826              
827             void
828 1257           svputs(PUTS_CONST char* p)
829             {
830 1257           sv_catpv(worksv,p);
831 1257           }
832              
833             void
834 358           svErrputc(char c)
835             {
836 358           sv_catpvn(workErrsv,&c,1);
837 358           }
838              
839             void
840 198           svErrputs(PUTS_CONST char* p)
841             {
842 198           sv_catpv(workErrsv,p);
843 198           }
844              
845             void
846 0           svOutflush(void)
847             {
848             /* EMPTY */
849 0           }
850              
851             /* Support error messages of the form (calling PARI('O(det2($mat))')):
852             PARI: *** obsolete function: O(det2($mat))
853             ^----------- */
854              
855             void
856 29           svErrflush(void)
857             {
858             STRLEN l;
859 29 50         char *s = SvPV(workErrsv, l);
860              
861 29 50         if (s && l) {
    100          
862 2           char *nl = memchr(s,'\n',l);
863 2 50         char *nl1 = nl ? memchr(nl+1,'\n',l - (STRLEN)(nl-s+1)) : NULL;
864              
865             /* Avoid signed/unsigned mismatch */
866 2 50         if (nl1 && (STRLEN)(nl1 - s) < l - 1)
    0          
867 0           warn("PARI: %.*s%*s%.*s%*s%s", (int)(nl + 1 - s), s, 6, "", (int)(nl1 - nl), nl + 1, 6, "", nl1 + 1);
868 2 50         else if (nl && (STRLEN)(nl - s) < l - 1)
    50          
869 0           warn("PARI: %.*s%*s%s", (int)(nl + 1 - s), s, 6, "", nl + 1);
870             else
871 2           warn("PARI: %s", s);
872 2           sv_setpv(workErrsv,"");
873             }
874 29           }
875              
876             enum _Unknown_Exception {Unknown_Exception=-1000};
877              
878             static pari_sp global_top;
879              
880             void
881 25           _svErrdie(long e)
882             {
883 25           SV *errSv = newSVsv(workErrsv);
884             STRLEN l;
885 25 50         char *s = SvPV(errSv,l), *nl, *nl1;
886              
887             if (e == -1) { /* XXXX Need to abandon our references to stack positions! */
888             }
889 25           sv_setpvn(workErrsv,"",0);
890 25           sv_2mortal(errSv);
891 25 50         if (l && s[l-1] == '\n')
    50          
892 0           s[l-- - 1] = 0;
893 25 50         if (l && s[l-1] == '.')
    100          
894 23           s[l-- - 1] = 0;
895 25           nl = memchr(s,'\n',l);
896 25 100         nl1 = nl ? memchr(nl+1,'\n',l - (STRLEN)(nl-s+1)) : NULL;
897              
898             #if PARI_VERSION_EXP >= 2005000 /* Undocumented when it changed; needed in 2.5.0 */
899             # ifdef CB_EXCEPTION_FLAGS
900 25 50         if (!cb_exception_resets_avma)
901             # endif
902 0           myPARI_top = global_top;
903             #endif
904             /* Avoid signed/unsigned mismatch */
905 25 100         if (nl1 && (STRLEN)(nl1 - s) < l - 1)
    50          
906 7           croak("PARI: %.*s%*s%.*s%*s%s", (int)(nl + 1 - s), s, 6, "", (int)(nl1 - nl), nl + 1, 6, "", nl1 + 1);
907 18 100         else if (nl && (STRLEN)(nl - s) < l - 1)
    50          
908 2           croak("PARI: %.*s%*s%s", (int)(nl + 1 - s), s, 6, "", nl + 1);
909             else
910 16           croak("PARI: %s", s);
911             }
912              
913             int
914 25           math_pari_handle_exception(long e)
915             {
916             # ifdef CB_EXCEPTION_FLAGS
917 25 50         if (!cb_exception_resets_avma)
918             # endif
919 0           myPARI_top = avma; /* ??? XXXX Do not let evalstate_reset() steal our avma! */
920 25           return 0;
921             }
922              
923             #if PARI_VERSION_EXP < 2004000 /* Undocumented when it changed; not present in 2.5.0 */
924             void
925             svErrdie(void)
926             {
927             _svErrdie(Unknown_Exception);
928             }
929              
930             PariOUT perlOut={svputc, svputs, svOutflush, NULL};
931             PariOUT perlErr={svErrputc, svErrputs, svErrflush, svErrdie};
932             #else /* !(PARI_VERSION_EXP < 2004000) */
933             PariOUT perlOut={svputc, svputs, svOutflush};
934             PariOUT perlErr={svErrputc, svErrputs, svErrflush};
935             #endif /* !(PARI_VERSION_EXP < 2004000) */
936              
937             static GEN
938 1           my_ulongtoi(ulong uv)
939             {
940 1           pari_sp oldavma = avma;
941 1           GEN a = stoi((long)(uv>>1));
942              
943 1           a = gshift(a, 1);
944 1 50         if (uv & 0x1)
945 0           a = gadd(a, gen_1);
946 1           return gerepileupto(oldavma, a);
947             }
948              
949             #ifdef LONG_SHORTER_THAN_IV
950             GEN
951             my_UVtoi(UV uv)
952             {
953             pari_sp oldavma = avma;
954             GEN a = my_ulongtoi((ulong)(uv>>(8*sizeof(ulong))));
955             GEN b = my_ulongtoi((ulong)(uv & ((((UV)1)<<(8*sizeof(ulong))) - 1)));
956              
957             a = gshift(a, (8*sizeof(ulong)));
958             return gerepileupto(oldavma, gadd(a,b));
959             }
960             GEN
961             my_IVtoi(IV iv)
962             {
963             pari_sp oldavma = avma;
964             GEN a;
965              
966             if (iv >= 0)
967             return my_UVtoi((UV)iv);
968             oldavma = avma;
969             return gerepileupto(oldavma, gneg(my_UVtoi((UV)-iv)));
970             }
971              
972             #else
973             #define my_IVtoi stoi
974             #define my_UVtoi my_ulongtoi
975             #endif
976              
977             #ifdef SvIsUV
978             # define mySvIsUV SvIsUV
979             #else
980             # define mySvIsUV(sv) 0
981             #endif
982             #define PerlInt_to_i(sv) (mySvIsUV(sv) ? my_UVtoi(SvUV(sv)) : my_IVtoi(SvIV(sv)))
983              
984             static int warn_undef = 0; /* Cannot enable until 'I' prototype can be distinguished: it may return undef correctly */
985              
986             #define is_gnil(g) ((g) == gnil)
987              
988             static GEN
989 52051           str2gen(char *s, int prefer_str)
990             {
991 52051 50         if (!prefer_str) return readseq(s);
992             { /* as genconcat() */
993 0           long ll, l = nchar2nlong((ll = strlen(s)) + 1);
994 0           GEN x = cgetg(l + 1, t_STR);
995            
996 0           strncpy(GSTR(x), s, ll+1);
997 0           return x;
998             }
999             }
1000              
1001             #define sv2pari(sv) sv2pariHow(sv,0)
1002             #define sv2pariStr(sv) sv2pariHow(sv,1) /* When given an array, use sv2pari() on the elements */
1003             #define sv2pariStrDeep(sv) sv2pariHow(sv,2)
1004              
1005             GEN
1006 6491079           sv2pariHow(SV* sv, int prefer_str)
1007             {
1008 6491079 100         if (SvGMAGICAL(sv)) mg_get(sv); /* MAYCHANGE in perlguts.pod - bug in perl */
1009 6491079 100         if (SvROK(sv)) {
1010 3816006           SV* tsv = SvRV(sv);
1011 3816006 100         if (SvOBJECT(tsv)) {
1012 3812866 100         if (SvSTASH(tsv) == pariStash) {
1013             is_pari:
1014             {
1015 3812832 100         return (GEN) SV_myvoidp_get(tsv);
    50          
1016             }
1017 36 100         } else if (SvSTASH(tsv) == pariEpStash) {
1018             is_pari_ep:
1019             {
1020 34 50         return (GEN)(((entree*) SV_myvoidp_get(tsv))->value);
    0          
1021             }
1022 2 50         } else if (sv_derived_from(sv, "Math::Pari")) { /* Avoid recursion */
1023 2 50         if (sv_derived_from(sv, "Math::Pari::Ep"))
1024 0           goto is_pari_ep;
1025             else
1026 2           goto is_pari;
1027             }
1028             }
1029             {
1030 3140           int type = SvTYPE(tsv);
1031 3140 50         if (type==SVt_PVAV) {
1032 3140           AV* av=(AV*) tsv;
1033 3140           I32 len=av_len(av); /* Length-1 */
1034 3140           GEN ret=cgetg(len+2, t_VEC);
1035             int i;
1036 9182 100         for (i=0;i<=len;i++) {
1037 6042           SV** svp=av_fetch(av,i,0);
1038 6042 50         if (!svp) croak("Internal error in sv2pari!");
1039 6042 50         ret[i+1]=(long)sv2pariHow(*svp, prefer_str > 1 ? 2 : 0);
1040             }
1041 3140           return ret;
1042             } else {
1043 0 0         return readseq(SvPV(sv,na)); /* For overloading */
1044             }
1045             }
1046             }
1047 2675073 100         else if (SvIOK(sv)) return PerlInt_to_i(sv);
    100          
    50          
    50          
1048 52424 100         else if (SvNOK(sv)) {
1049 372 50         double n = (double)SvNV(sv);
1050             #if !defined(PERL_VERSION) || (PERL_VERSION < 6)
1051             /* Earlier needed more voodoo, since sv_true sv_false are NOK,
1052             but not IOK. Now we propagate them to IOK in Pari.pm;
1053             This works at least with 5.5.640 onwards. */
1054             /* With 5.00553 they are (NOK,POK,READONLY,pNOK,pPOK).
1055             This would special-case all READONLY double-headed stuff;
1056             let's hope it is not too frequent... */
1057             if (SvREADONLY(sv) && SvPOK(sv) && (n == 1 || n == 0))
1058             return stoi((long)n);
1059             #endif /* !defined(PERL_VERSION) || (PERL_VERSION < 6) */
1060 372           return dbltor(n);
1061             }
1062 52052 100         else if (SvPOK(sv)) return str2gen(SvPV(sv,na), prefer_str);
    50          
1063 1 50         else if (SvIOKp(sv)) return PerlInt_to_i(sv);
    0          
    0          
    0          
1064 1 50         else if (SvNOKp(sv)) return dbltor((double)SvNV(sv));
    0          
1065 1 50         else if (SvPOKp(sv)) return str2gen(SvPV(sv,na), prefer_str);
    0          
1066 1 50         else if (SvOK(sv)) croak("Variable in sv2pari is not of known type");
    50          
    50          
1067              
1068 1 50         if (warn_undef) warn("undefined value in sv2pari");
1069 1           return gnil; /* was: stoi(0) */ /* !SvOK(sv) */
1070             }
1071              
1072             GEN
1073 289           sv2parimat(SV* sv)
1074             {
1075 289           GEN in=sv2pari(sv);
1076 289 50         if (typ(in)==t_VEC) {
1077 289           long len=lg(in)-1;
1078             long t;
1079 289           long l=lg((GEN)(in[1]));
1080 650 100         for (;len;len--) {
1081 361           GEN elt = (GEN)(in[len]);
1082              
1083 361 50         if ((t=typ(elt)) == t_VEC) {
1084 361           settyp(elt, t_COL);
1085 0 0         } else if (t != t_COL) {
1086 0           croak("Not a vector where column of a matrix expected");
1087             }
1088 361 50         if (lg(elt)!=l) {
1089 0           croak("Columns of input matrix are of different height");
1090             }
1091             }
1092 289           settyp(in, t_MAT);
1093 0 0         } else if (typ(in) != t_MAT) {
1094 0           croak("Not a matrix where matrix expected");
1095             }
1096 289           return in;
1097             }
1098              
1099             SV*
1100 35798           pari2iv(GEN in)
1101             {
1102             #ifdef SvIsUV
1103             # define HAVE_UVs 1
1104             UV uv;
1105             #else
1106             # define HAVE_UVs 0
1107             IV uv;
1108             #endif
1109 35798           int overflow = 0;
1110              
1111 35798 50         if (typ(in) != t_INT)
1112 0           return newSViv((IV)gtolong(in));
1113 35798           switch (lgef(in)) {
1114             case 2:
1115 35712           uv = 0;
1116 35712           break;
1117             case 3:
1118 86           uv = in[2];
1119 86 50         if (sizeof(long) >= sizeof(IV) && in[2] < 0)
1120 0           overflow = 1;
1121 86           break;
1122             case 4:
1123             if ( 2 * sizeof(long) > sizeof(IV)
1124             || ((2 * sizeof(long) == sizeof(IV)) && !HAVE_UVs && in[2] < 0) )
1125 0           goto do_nv;
1126             uv = in[2];
1127             uv = (uv << TWOPOTBYTES_IN_LONG) + in[3];
1128             break;
1129             default:
1130 0           goto do_nv;
1131             }
1132 35798 50         if (overflow) {
1133             #ifdef SvIsUV
1134 0 0         if (signe(in) > 0) {
1135 0           SV *sv = newSViv((IV)uv);
1136              
1137 0           SvIsUV_on(sv);
1138 0           return sv;
1139             } else
1140             #endif
1141 0           goto do_nv;
1142             }
1143 35798 100         return newSViv(signe(in) > 0 ? (IV)uv : -(IV)uv);
1144             do_nv:
1145 0           return newSVnv(gtodouble(in)); /* XXXX to NV, not to double? */
1146             }
1147              
1148             #if PARI_VERSION_EXP >= 2002005 && PARI_VERSION_EXP <= 2002007
1149             # define _gtodouble gtodouble
1150             #else /* !(PARI_VERSION_EXP >= 2002005 && PARI_VERSION_EXP <= 2002007) */
1151              
1152             #ifndef m_evallg
1153             # define m_evallg _evallg
1154             #endif
1155              
1156             double
1157 1           _gtodouble(GEN x)
1158             {
1159             static long reel4[4]={ evaltyp(t_REAL) | m_evallg(4),0,0,0 };
1160              
1161 1 50         if (typ(x)==t_REAL) return rtodbl(x);
1162 1           gaffect(x,(GEN)reel4); return rtodbl((GEN)reel4);
1163             }
1164             #endif /* !(PARI_VERSION_EXP >= 2002005 && PARI_VERSION_EXP <= 2002007) */
1165              
1166             #if PARI_VERSION_EXP >= 2003000 /* In 2.3.5 is using argument 0, in 2.1.7 it is still 1. */
1167             # define mybrute brute
1168             #else /* !(PARI_VERSION_EXP >= 2003000) */
1169             # if PARI_VERSION_EXP >= 2002005 && PARI_VERSION_EXP <= 2002007
1170             static void
1171             _initout(pariout_t *T, char f, long sigd, long sp, long fieldw, int prettyp)
1172             {
1173             T->format = f;
1174             T->sigd = sigd;
1175             T->sp = sp;
1176             T->fieldw = fieldw;
1177             T->initial = 1;
1178             T->prettyp = prettyp;
1179             }
1180              
1181             void
1182             mybruteall(GEN g, char f, long d, long sp)
1183             {
1184             pariout_t T; _initout(&T,f,d,sp,0, f_RAW);
1185             my_gen_output(g, &T);
1186             }
1187             # else /* !((PARI_VERSION_EXP >= 2002005 && PARI_VERSION_EXP <= 2002007) || PARI_VERSION_EXP >= 2004000) */
1188             # define mybruteall bruteall
1189             # endif /* !((PARI_VERSION_EXP >= 2002005 && PARI_VERSION_EXP <= 2002007) || PARI_VERSION_EXP >= 2004000) */
1190             # define mybrute(g,f,d) mybruteall(g,f,d,0) /* 0: compact pari-readable form */
1191             #endif /* !(PARI_VERSION_EXP >= 2003000) */
1192              
1193             SV*
1194 1           pari2nv(GEN in)
1195             {
1196 1           return newSVnv(_gtodouble(in));
1197             }
1198              
1199             SV*
1200 448           pari2pv(GEN in)
1201             {
1202 448 100         renewWorkSv;
    50          
1203 448 100         if (typ(in) == t_STR) /* Puts "" around without special-casing */
1204 1           return sv_setpv(worksv, GSTR(in)), worksv;
1205             {
1206 447           PariOUT *oldOut = pariOut;
1207 447           pariOut = &perlOut;
1208 447           sv_setpvn(worksv,"",0);
1209 447           mybrute(in,'g',-1);
1210 447           pariOut = oldOut;
1211 447           return worksv;
1212             }
1213             }
1214              
1215             long
1216 14           setprecision(long digits)
1217             {
1218 14           long m = fmt_nbP;
1219              
1220 14 50         if(digits>0) {fmt_nbPset(digits); prec_digits_set(digits);}
1221 14           return m;
1222             }
1223              
1224             #if 0
1225             long
1226             setbitprecision(long bits)
1227             {
1228             long m = fmt_nbP;
1229              
1230             if(bits>0) {fmt_nbPset((long)bits*10/3); prec_bits_set(bits);}
1231             return m;
1232             }
1233             #endif
1234              
1235             #if PARI_VERSION_EXP < 2002012 || PARI_VERSION_EXP >= 2003000
1236             long
1237 1           setseriesprecision(long digits)
1238             {
1239 1           long m = precdl;
1240              
1241 1 50         if(digits>0) {precdl = digits;}
1242 1           return m;
1243             }
1244             #endif /* PARI_VERSION_EXP < 2002012 || PARI_VERSION_EXP >= 2003000 */
1245              
1246             static IV primelimit;
1247             static UV parisize;
1248              
1249             IV
1250 0           setprimelimit(IV n)
1251             {
1252             byteptr ptr;
1253 0           IV o = primelimit;
1254              
1255 0 0         if (n != 0) {
1256             #if PARI_VERSION_EXP < 2007000
1257             ptr = initprimes(n);
1258             free(diffptr);
1259             diffptr = ptr;
1260             primelimit = n;
1261             #else
1262 0           initprimetable(n);
1263             #endif
1264             }
1265 0           return o;
1266             }
1267              
1268             SV*
1269 810           pari_print(GEN in)
1270             {
1271 810           PariOUT *oldOut = pariOut;
1272 810           pariOut = &perlOut;
1273 810 50         renewWorkSv;
    0          
1274 810           sv_setpvn(worksv,"",0);
1275 810           brute(in, 'g', fmt_nbP);
1276 810           pariOut = oldOut;
1277 810           return worksv;
1278             }
1279              
1280             SV*
1281 0           pari_pprint(GEN in)
1282             {
1283 0           PariOUT *oldOut = pariOut;
1284 0           pariOut = &perlOut;
1285 0 0         renewWorkSv;
    0          
1286 0           sv_setpvn(worksv,"",0);
1287             #if PARI_VERSION_EXP >= 2004000
1288 0           brute(in, 'g', fmt_nbP); /* Make a synonim of pari_print(), as in GP/PARI */
1289             #else
1290             sor(in, 'g'/*fmt.format*/, fmt_nbP, 0/*fmt.field*/);
1291             #endif
1292 0           pariOut = oldOut;
1293 0           return worksv;
1294             }
1295              
1296             SV*
1297 0           pari_texprint(GEN in)
1298             {
1299 0           PariOUT *oldOut = pariOut;
1300 0           pariOut = &perlOut;
1301 0 0         renewWorkSv;
    0          
1302 0           sv_setpvn(worksv,"",0);
1303 0           texe(in, 'g', fmt_nbP);
1304 0           pariOut = oldOut;
1305 0           return worksv;
1306             }
1307              
1308             SV*
1309 458302           pari2mortalsv(GEN in, long oldavma)
1310             { /* Oldavma should keep the value of
1311             * avma when entering a function call. */
1312 458302           SV *sv = sv_newmortal();
1313              
1314 458302 100         setSVpari_keep_avma(sv, in, oldavma);
    50          
    100          
    100          
1315 458302           return sv;
1316             }
1317              
1318             typedef struct {
1319             long items, words;
1320             SV *acc;
1321             int context;
1322             } heap_dumper_t;
1323              
1324             #ifndef BL_HEAD /* in 2.5.0 it is 4 */
1325             # define BL_HEAD 3 /* from init.c */
1326             #endif
1327             static void
1328 0           heap_dump_one(heap_dumper_t *d, GEN x)
1329             {
1330             SV* tmp;
1331              
1332 0           d->items++;
1333 0 0         if(!x[0]) { /* user function */
1334 0           d->words += strlen((char *)(x+2))/sizeof(long);
1335 0           tmp = newSVpv((char*)(x+2),0);
1336 0 0         } else if (x==bernzone) {
1337 0           d->words += x[0];
1338 0           tmp = newSVpv("bernzone",8);
1339             } else { /* GEN */
1340 0           d->words += gsizeword(x);
1341 0           tmp = pari_print(x);
1342             }
1343             /* add to output */
1344 0           switch(d->context) {
1345             case G_VOID:
1346 0 0         case G_SCALAR: sv_catpvf(d->acc, " %2ld: %s\n",
1347 0           (long)(d->items - 1), SvPV_nolen(tmp));
1348 0           SvREFCNT_dec(tmp); break;
1349 0           case G_ARRAY: av_push((AV*)d->acc,tmp); break;
1350             }
1351 0           }
1352              
1353             #if PARI_VERSION_EXP >= 2002012
1354              
1355             static void
1356 0           heap_dump_one_v(GEN x, void *v)
1357             {
1358 0           heap_dumper_t *d = (heap_dumper_t *)v;
1359              
1360 0           heap_dump_one(d, x);
1361 0           }
1362              
1363             static void
1364 0           heap_dumper(heap_dumper_t *d)
1365             {
1366 0           traverseheap(&heap_dump_one_v, (void*)d);
1367 0           }
1368              
1369             #else /* !( PARI_VERSION_EXP >= 2002012 ) */
1370              
1371             static void
1372             heap_dumper(heap_dumper_t *d)
1373             {
1374             /* create a new block on the heap so we can examine the linked list */
1375             GEN tmp1 = newbloc(1); /* at least 1 to avoid warning */
1376             GEN x = (GEN)bl_prev(tmp1);
1377              
1378             killbloc(tmp1);
1379              
1380             /* code adapted from getheap() in PARI src/language/init.c */
1381             for(; x; x = (GEN)bl_prev(x))
1382             heap_dump_one(d, x);
1383             }
1384              
1385             #endif /* !( PARI_VERSION_EXP >= 2002012 ) */
1386              
1387             void
1388 2           resetSVpari(SV* sv, GEN g, pari_sp oldavma)
1389             {
1390 2 50         if (SvROK(sv)) {
1391 2           SV* tsv = SvRV(sv);
1392              
1393 2 50         if (g && SvOBJECT(tsv)) {
    50          
1394 2           IV tmp = 0;
1395              
1396 2 50         if (SvSTASH(tsv) == pariStash) {
1397             #if 0 /* To dangerous to muck with this */
1398             is_pari:
1399             #endif
1400             {
1401 2 50         tmp = SvIV(tsv);
1402             }
1403             }
1404             #if 0 /* To dangerous to muck with this */
1405             else if (SvSTASH(tsv) == pariEpStash) {
1406             is_pari_ep:
1407             {
1408             tmp = SvIV(tsv);
1409             tmp = PTR2IV((INT2PTR(entree*, tmp))->value);
1410             }
1411             }
1412             else if (sv_derived_from(sv, "Math::Pari")) { /* Avoid recursion */
1413             if (sv_derived_from(sv, "Math::Pari::Ep"))
1414             goto is_pari_ep;
1415             else
1416             goto is_pari;
1417             }
1418             #endif
1419 2 50         if (tmp == PTR2IV(g)) /* Did not change */
1420 0           return;
1421             }
1422             }
1423             /* XXXX do it the non-optimized way */
1424 2 50         setSVpari_keep_avma(sv,g,oldavma);
    0          
    50          
    50          
1425             }
1426              
1427             static const
1428             unsigned char defcode[] = "xD0,G,D0,G,D0,G,D0,G,D0,G,D0,G,";
1429             int def_numargs = 6;
1430              
1431             static int doing_PARI_autoload = 0;
1432              
1433             long
1434 1231952           moveoffstack_newer_than(SV* sv)
1435             {
1436             SV* sv1;
1437             SV* nextsv;
1438 1231952           long ret=0;
1439            
1440 2521823 100         for (sv1 = PariStack; sv1 != sv; sv1 = nextsv) {
1441 1289871           ret++;
1442 1289871 100         SV_OAVMA_switch(nextsv, sv1, GENmovedOffStack); /* Mark as moved off stack. */
1443 1289871 100         SV_myvoidp_reset_clone(sv1); /* Relocate to cloned */
    50          
1444 1289871           onStack_dec;
1445 1289871           offStack_inc;
1446             }
1447 1231952           PariStack = sv;
1448 1231952           return ret;
1449             }
1450              
1451             #if PARI_VERSION_EXP > 2004002
1452             typedef long PerlFunctionArg1;
1453             # define toEntreeP(l) ((entree *)(l))
1454             # define elt_CV pvalue
1455             #else
1456             typedef entree *PerlFunctionArg1;
1457             # define toEntreeP
1458             # define elt_CV value
1459             #endif
1460              
1461             GEN
1462 458300           callPerlFunction_va_list(int rettype, int numargs, SV *cv, va_list args)
1463             {
1464             GEN res;
1465             int i;
1466 458300           dSP;
1467             int count ;
1468 458300           pari_sp oldavma = avma;
1469 458300           SV *oPariStack = PariStack;
1470             SV *sv;
1471              
1472             /* warn("Entering Perl handler inside PARI, %d args", numargs); */
1473 458300           ENTER ;
1474 458300           SAVETMPS;
1475 458300           SAVEINT(sentinel);
1476 458300           sentinel = avma;
1477 458300 50         PUSHMARK(sp);
1478 458300 50         EXTEND(sp, numargs + 1);
    50          
1479 916602 100         for (i = 0; i < numargs; i++) {
1480             /* It should be OK to have the same oldavma here, since avma
1481             is not modified... */
1482 458302 50         PUSHs(pari2mortalsv(va_arg(args, GEN), oldavma));
1483             /* warn("pushed an argument"); */
1484             }
1485 458300           PUTBACK;
1486 458300           count = perl_call_sv(cv, rettype);
1487 458300 100         if (rettype == G_VOID && count == 1)
    50          
1488 0           count = 0;
1489              
1490 458300           SPAGAIN;
1491 458300 50         if (count != (rettype == G_SCALAR))
1492 0           croak("Perl function exported into PARI returns unexpected number %d of values (need %d)", count, (rettype == G_SCALAR));
1493              
1494 458300 100         if (rettype == G_SCALAR)
1495 458229           sv = SvREFCNT_inc(POPs); /* Preserve the guy. */
1496              
1497 458300           PUTBACK ;
1498 458300 100         FREETMPS ;
1499 458300           LEAVE ;
1500              
1501 458300 100         if (rettype == G_VOID)
1502 71           return 0;
1503             /* Now PARI data created inside this subroutine sits above
1504             oldavma, but the caller is going to unwind the stack: */
1505 458229 100         if (PariStack != oPariStack)
1506 52262           moveoffstack_newer_than(oPariStack);
1507             /* Now, when everything is moved off stack, and avma is reset, we
1508             can get the answer: */
1509 458229           res = sv2pari(sv); /* XXXX When to decrement the count? */
1510             /* We need to copy it back to stack, otherwise we cannot decrement
1511             the count. The ABI is that a C function [which can be put into a
1512             GP/PARI function C-function slot] should have its result
1513             completely on stack. */
1514 458229           res = myforcecopy(res);
1515 458229           SvREFCNT_dec(sv);
1516            
1517 458229           return res;
1518             }
1519              
1520             GEN
1521 35766           callPerlFunction(PerlFunctionArg1 long_ep, ...)
1522             {
1523             GEN res;
1524 35766           entree *ep = toEntreeP(long_ep);
1525             va_list args;
1526 35766           SV *cv = (SV*) ep->elt_CV;
1527 35766           int numargs = CV_NUMARGS_get(cv);
1528              
1529 35766           va_start(args, long_ep);
1530             /* warn("calling with numargs=%d", numargs); */
1531 35766           res = callPerlFunction_va_list(G_SCALAR, numargs, cv, args);
1532             /* warn("ending call"); */
1533 35766           va_end(args);
1534             /* warn("ended call"); */
1535 35766           return res;
1536             }
1537              
1538             entree *
1539 10           installPerlFunctionCV(SV* cv, char *name, I32 numargs, char *help)
1540             {
1541             char *code, *s, *s0;
1542 10           I32 req = numargs, opt = 0;
1543             entree *ep;
1544             STRLEN len;
1545              
1546 10 100         if(SvROK(cv))
1547 1           cv = SvRV(cv);
1548              
1549 10 100         if (numargs < 0 && SvPOK(cv) && (s0 = s = SvPV(cv,len))) {
    50          
    50          
    50          
1550 9           char *end = s + len; /* CvCONST() may have a CvFILE() appended - depends on version */
1551              
1552             /* Get number of arguments. */
1553 9           req = opt = 0;
1554 20 100         while (s < end && *s == '$')
    50          
1555 11           req++, s++;
1556 9 50         if (s < end && *s == ';')
    0          
1557 0           s++;
1558 9 50         while (s < end && *s == '$')
    0          
1559 0           opt++, s++;
1560 9 50         if (s < end && *s == '@') {
    0          
1561 0           opt += 6; /* Max 6 optional arguments. */
1562 0           s++;
1563             }
1564 9 50         if (s == end) { /* Got it! */
1565 9           numargs = req + opt;
1566             } else {
1567 0           croak("Can't install Perl function with prototype `%s'", s0);
1568             }
1569             }
1570            
1571 10 50         if (numargs < 0) { /* Variable number of arguments. */
1572             /* Install something hairy with <= 6 args */
1573 0           code = (char*)defcode; /* Remove constness. */
1574 0           numargs = def_numargs;
1575 10 50         } else if (numargs >= 256) {
1576 0           croak("Import of Perl function with too many arguments");
1577             } else {
1578             /* Should not use gpmalloc(), since we call free()... */
1579 10           code = (char *)malloc(numargs*6 - req*5 + 2);
1580 10           code[0] = 'x';
1581 10           memset(code + 1, 'G', req);
1582 10           s = code + 1 + req;
1583 10 50         while (opt--) {
1584 0           strcpy(s, "D0,G,");
1585 0           s += 5;
1586             }
1587 10           *s = '\0';
1588             }
1589 10           CV_NUMARGS_set(cv, numargs);
1590 10           SAVEINT(doing_PARI_autoload);
1591 10           doing_PARI_autoload = 1;
1592 10           ep = install((void*)SvREFCNT_inc(cv), name, code);
1593             #if PARI_VERSION_EXP >= 2004002
1594 10           ep->pvalue = (void*)cv;
1595 10           ep->value = (void*)callPerlFunction;
1596             #endif
1597             /* warn("installed %#x code=<%s> numargs=%d", (int)ep->value, ep->code, (int)numargs); */
1598 10           doing_PARI_autoload = 0;
1599 10 50         if (code != (char*)defcode)
1600 10           free(code);
1601 10 50         if (help)
1602 0           ep->help = pari_strdup(help); /* Same code as in addhelp() so that the same free()ing code works */
1603 10           return ep;
1604             }
1605              
1606             void
1607 0           freePerlFunction(entree *ep)
1608             {
1609 0 0         if (!ep->code || (*ep->code != 'x')) {
    0          
1610 0           croak("Attempt to ask Perl to free PARI function not installed from Perl");
1611             }
1612 0 0         if (ep->code && (ep->code != (char *)defcode))
    0          
1613 0           free((void *)(ep->code));
1614 0           ep->code = NULL;
1615 0           SvREFCNT_dec((SV*)ep->elt_CV);
1616 0           ep->elt_CV = NULL;
1617 0           }
1618              
1619             void
1620 2           detach_stack(void)
1621             {
1622 2           moveoffstack_newer_than((SV *) GENfirstOnStack);
1623 2           }
1624              
1625             static unsigned long
1626 2           s_allocatemem(unsigned long newsize)
1627             {
1628             #ifdef CB_EXCEPTION_FLAGS
1629 2           int o = cb_exception_resets_avma;
1630             #endif
1631              
1632 2 50         if (newsize) {
1633 2           detach_stack();
1634             #if PARI_VERSION_EXP >= 2004000 /* ??? */
1635             # if PARI_VERSION_EXP >= 2009000 /* ??? */
1636             # ifdef CB_EXCEPTION_FLAGS__try_without
1637             cb_exception_resets_avma = 0; /* otherwise warn about stack increase would try to use old avma */
1638             # endif
1639 2 50         if (pari_mainstack->vsize)
1640 0           paristack_resize(newsize);
1641 2 50         else if (newsize != pari_mainstack->rsize)
1642 2           paristack_setsize(newsize, 0);
1643             # ifdef CB_EXCEPTION_FLAGS__try_without
1644             cb_exception_resets_avma = o;
1645             # endif
1646             # else /* !(PARI_VERSION_EXP >= 2009000) */
1647             pari_init_stack(newsize, 0);
1648             # endif /* !(PARI_VERSION_EXP >= 2009000) */
1649              
1650 2           parisize = myPARI_top - myPARI_bot;
1651             #else
1652             parisize = allocatemoremem(newsize);
1653             #endif
1654 2           perlavma = sentinel = avma;
1655             }
1656 2           global_top = myPARI_top;
1657 2           return parisize;
1658             }
1659              
1660             /* Currently with <=6 arguments only! */
1661              
1662             #if PARI_VERSION_EXP >= 2004000
1663             # define APF_CONST const
1664             #else /* !(PARI_VERSION_EXP >= 2004000) */
1665             # define APF_CONST
1666             #endif /* PARI_VERSION_EXP >= 2004000 */
1667              
1668             entree *
1669 7194           autoloadPerlFunction(APF_CONST char *s, long len)
1670             {
1671             CV *cv;
1672             SV* name;
1673             HV* converted;
1674              
1675 7194 100         if (doing_PARI_autoload)
1676 12           return 0;
1677 7182           converted = perl_get_hv("Math::Pari::converted",TRUE);
1678 7182 50         if (hv_fetch(converted, s, len, FALSE))
1679 0           return 0;
1680              
1681 7182           name = sv_2mortal(newSVpv(s, len));
1682              
1683 7182           cv = perl_get_cv(SvPVX(name), FALSE);
1684 7182 100         if (cv == Nullcv) {
1685 7173           return 0;
1686             }
1687             /* Got it! */
1688 9           return installPerlFunctionCV((SV*)cv, SvPVX(name), -1, NULL); /* -1 gives variable. */
1689             }
1690              
1691             GEN
1692 0           exprHandler_Perl(char *s)
1693             {
1694 0           SV* dummy = Nullsv; /* Avoid "without initialization" warnings from M$ */
1695 0           SV* cv = (SV*)(s - LSB_in_U32 -
1696             ((char*)&(dummy->sv_flags) - ((char*)dummy)));
1697             GEN res;
1698 0           dSP;
1699             SV *sv;
1700 0           SV *oPariStack = PariStack;
1701              
1702 0           ENTER ;
1703 0           SAVETMPS;
1704 0 0         PUSHMARK(sp);
1705 0           SAVEINT(sentinel);
1706 0           sentinel = avma;
1707 0           (void)perl_call_sv(cv, G_SCALAR); /* The retval is always 1 */
1708              
1709 0           SPAGAIN;
1710 0           sv = SvREFCNT_inc(POPs); /* Preserve it through FREETMPS */
1711              
1712 0           PUTBACK ;
1713 0 0         FREETMPS ;
1714 0           LEAVE ;
1715              
1716             /* Now PARI data created inside this subroutine sits above
1717             oldavma, but the caller is going to unwind the stack: */
1718 0 0         if (PariStack != oPariStack)
1719 0           moveoffstack_newer_than(oPariStack);
1720             /* Now, when everything is moved off stack, and avma is reset, we
1721             can get the answer: */
1722 0           res = sv2pari(sv);
1723             /* We need to copy it back to stack, otherwise we cannot decrement
1724             the count. */
1725 0           res = myforcecopy(res);
1726 0           SvREFCNT_dec(sv);
1727            
1728 0           return res;
1729             }
1730              
1731             static GEN
1732 47           Arr_FETCH(GEN g, I32 n)
1733             {
1734 47           I32 l = lg(g) - 1;
1735              
1736 47 50         if (!is_matvec_t(typ(g)))
1737 0           croak("Access to elements of not-a-vector");
1738 47 50         if (n >= l || n < 0)
    50          
1739 0           croak("Array index %li out of range", (long)n);
1740             #if 0
1741             warn("fetching %ld-th element of type %d", (long)n, typ((GEN)g[n + 1]));
1742             #endif
1743 47           return (GEN)g[n + 1];
1744             }
1745              
1746             static void
1747 6           Arr_STORE(GEN g, I32 n, GEN elt)
1748             {
1749 6           I32 l = lg(g) - 1, docol = 0;
1750             GEN old;
1751              
1752 6 50         if (!is_matvec_t(typ(g)))
1753 0           croak("Access to elements of not-a-vector");
1754 6 50         if (n >= l || n < 0)
    50          
1755 0           croak("Array index %li out of range", (long)n);
1756             #if 0
1757             warn("storing %ld-th element of type %d", (long)n, typ((GEN)g[n + 1]));
1758             #endif /* 0 */
1759              
1760 6 100         if (typ(g) == t_MAT) {
1761 4           long len = lg(g);
1762 4           long l = lg((GEN)(g[1]));
1763 4 50         if (typ(elt) != t_COL) {
1764 4 100         if (typ(elt) != t_VEC)
1765 1           croak("Not a vector where column of a matrix expected");
1766 3           docol = 1;
1767             }
1768 3 100         if (lg(elt)!=l && len != 2)
    100          
1769 1           croak("Assignment of a columns into a matrix of incompatible height");
1770             }
1771            
1772 4           old = (GEN)g[n + 1];
1773             /* It is not clear whether we need to clone if the elt is offstack */
1774 4           elt = gclone(elt);
1775 4 100         if (docol)
1776 2           settyp(elt, t_COL);
1777              
1778             /* anal.c is optimizing inspection away around here... */
1779 4 50         if (isclone(old)) killbloc(old);
1780 4           g[n + 1] = (long)elt;
1781 4           }
1782              
1783             #define Arr_FETCHSIZE(g) (lg(g) - 1)
1784             #define Arr_EXISTS(g,l) ((l)>=0 && l < lg(g) - 1)
1785              
1786             #define DFT_VAR (GEN)-1
1787             #define DFT_GEN (GEN)NULL
1788              
1789             static void
1790 0           check_pointer(unsigned int ptrs, GEN argvec[])
1791             {
1792             unsigned int i;
1793 0 0         for (i=0; ptrs; i++,ptrs>>=1)
1794 0 0         if (ptrs & 1) *((GEN*)argvec[i]) = gclone(*((GEN*)argvec[i]));
1795 0           }
1796              
1797             #define RETTYPE_VOID 0
1798             #define RETTYPE_LONG 1
1799             #define RETTYPE_GEN 2
1800             #define RETTYPE_INT 3
1801              
1802             #define ARGS_SUPPORTED 9
1803             #define THE_ARGS_SUPPORTED \
1804             argvec[0], argvec[1], argvec[2], argvec[3], \
1805             argvec[4], argvec[5], argvec[6], argvec[7], argvec[8]
1806              
1807             GEN code_return_1 = 0;
1808             GEN code2_return_1 = 0;
1809              
1810             #if PARI_VERSION_EXP >= 2004000
1811             struct trampoline_data_1v {SV *var1; SV* cv;};
1812              
1813             GEN
1814 422534           callPerlFunction_var(int rettype, int numargs, SV *cv, ...)
1815             {
1816             va_list args;
1817             GEN res;
1818              
1819 422534           va_start(args, cv);
1820 422534           res = callPerlFunction_va_list(rettype, numargs, cv, args);
1821 422534           va_end(args);
1822 422534           return res;
1823             }
1824              
1825 0           static GEN code_trampoline_1v_ret(GEN v)
1826             {
1827 0           struct trampoline_data_1v *tr = (struct trampoline_data_1v*)itos(v);
1828 0           GEN arg1 = get_lex(-2); /* XXX one before v, which is -1 ??? */
1829 0           GEN res = callPerlFunction_var(G_SCALAR, 1, tr->cv, arg1);
1830              
1831 0           return res;
1832             }
1833              
1834 0           static void code_trampoline_vL_ret(long v)
1835             {
1836 0           struct trampoline_data_1v *tr = (struct trampoline_data_1v*)v;
1837 0           GEN arg1 = get_lex(-2); /* XXX one before v, which is -1 ??? */
1838              
1839 0           (void)callPerlFunction_var(G_VOID, 1, tr->cv, arg1); /* works with G_SCALAR */
1840 0           return;
1841             }
1842              
1843 71           static void code_trampoline_vG_ret(GEN v)
1844             {
1845 71           struct trampoline_data_1v *tr = (struct trampoline_data_1v*)itos(v);
1846 71           GEN arg1 = get_lex(-2); /* XXX one before v, which is -1 ??? */
1847 71           SV *oPariStack = PariStack;
1848              
1849 71           (void)callPerlFunction_var(G_VOID, 1, tr->cv, arg1); /* works with G_SCALAR */
1850              
1851             /* Now PARI data created inside this subroutine sits above
1852             oldavma, but the caller is going to unwind the stack: */
1853 71 50         if (PariStack != oPariStack)
1854 0           moveoffstack_newer_than(oPariStack);
1855 71           return;
1856             }
1857              
1858 422463           static GEN code_trampoline_G_ret(GEN v)
1859             {
1860 422463           struct trampoline_data_1v *tr = (struct trampoline_data_1v*)itos(v);
1861 422463           GEN arg1 = get_lex(-2), ret; /* XXX one before v, which is -1 ??? */
1862 422463           SV *oPariStack = PariStack;
1863              
1864              
1865 422463           ret = callPerlFunction_var(G_SCALAR, 1, tr->cv, arg1);
1866             /* Now PARI data created inside this subroutine sits above
1867             oldavma, but the caller is going to unwind the stack: */
1868 422463 50         if (PariStack != oPariStack)
1869 0           moveoffstack_newer_than(oPariStack);
1870 422463           return ret;
1871             }
1872              
1873 0           static GEN code_trampoline_G_ret_SV(GEN v)
1874             {
1875 0           struct trampoline_data_1v *tr = (struct trampoline_data_1v*)itos(v);
1876 0           GEN arg1 = get_lex(-2), ret; /* XXX one before v, which is -1 ??? */
1877 0           SV *oPariStack = PariStack;
1878 0           pari_sp oldavma = avma;
1879              
1880 0 0         setSVpari_keep_avma(tr->var1, arg1, oldavma);
    0          
    0          
    0          
1881 0           ret = callPerlFunction_var(G_SCALAR, 0, tr->cv);
1882             /* Now PARI data created inside this subroutine sits above
1883             oldavma, but the caller is going to unwind the stack: */
1884 0 0         if (PariStack != oPariStack)
1885 0           moveoffstack_newer_than(oPariStack);
1886 0           return ret;
1887             }
1888             #endif /* PARI_VERSION_EXP >= 2004000 */
1889              
1890             #if PARI_VERSION_EXP >= 2004002 /* Undocumented when it appeared; present in 2.5.0 */
1891             static const entree eH_vG = {"___fake_MathPari_handler_vG",0x100/*EpSTATIC*/,(void*)code_trampoline_vG_ret,2,"vG","trampoline to call Perl call in PARI \"loops\"", 0, 1};
1892             static const entree eH_G = {"___fake_MathPari_handler_G",0x100/*EpSTATIC*/,(void*)code_trampoline_G_ret,2,"G","trampoline to call Perl call in PARI \"loops\"", 0, 1};
1893              
1894             static GEN
1895 782           make_trampolinecv(SV *cv, int is_void, SV *sv)
1896             { /* Poor man's snmk_closure(): create a no-argument closure which calls a 1-argument function e(callee);
1897             e extracts the current loop variable, and calls a 1-argument function callee->cv with this argument. */
1898             struct trampoline_data_1v *callee;
1899 782           char *s = "N/A";
1900             STRLEN len;
1901              
1902 782 100         if (!SvPOK(cv) || !(s = SvPV(cv,len)) || len != 1 || s[0] != '$') {
    50          
    50          
    50          
    50          
1903 7           warn("Argument-types E,I with prototype `%s' not supported yet, substituting x->1", s);
1904 7           return code_return_1;
1905             }
1906 775           warn("Ignoring the variable(s) of a closure");
1907 775           callee = (struct trampoline_data_1v*) stack_malloc(sizeof(struct trampoline_data_1v)); /* new_chunk(words)??? */
1908 775           callee->cv = cv;
1909 775           callee->var1 = sv;
1910 775           GEN extraargs = mkvec(stoi((long) callee)); /* Need real mkvec()!!! XXX ??? */
1911 782 100         return snm_closure((entree*) (is_void ? &eH_vG : &eH_G), extraargs);
1912             }
1913             #endif /* PARI_VERSION_EXP < 2004002 */ /* Undocumented when it appeared; present in 2.5.0 */
1914              
1915             static void
1916 1198           fill_argvect(entree *ep, const char *s, long *has_pointer, GEN *argvec,
1917             long *rettype, SV **args, int items,
1918             SV **sv_OUT, GEN *gen_OUT, long *OUT_cnt)
1919             { /* The last 3 to support '&' code - treated after the call */
1920             entree *ep1;
1921 1198           int i = 0, j = 0, saw_M = 0, saw_V = 0;
1922             long fake;
1923 1198           const char *s0 = s, *pre;
1924             PariExpr expr;
1925             #if PARI_VERSION_EXP >= 2004002
1926             # define MaxPariVar 7
1927             PariVar loopvars[MaxPariVar];
1928             # define LoopVar(i) loopvars[i]
1929             #else
1930             # define LoopVar(i) N/A
1931             #endif
1932              
1933 1198 50         if (!ep)
1934 0           croak("XSUB call through interface did not provide *function");
1935 1198 50         if (!s)
1936 0           croak("XSUB call through interface with a NULL code");
1937              
1938             /* croak("See arg specifier: '%s'", s); */
1939 1198           *OUT_cnt = 0;
1940 8718 100         while (*s) {
1941 7767 50         if (i >= ARGS_SUPPORTED - 1)
1942 0           croak("Too many args for a flexible-interface function");
1943 7767           switch (*s++)
1944             {
1945             case 'G': /* GEN */
1946 2746           argvec[i++] = sv2pari(args[j++]);
1947 2746           break;
1948              
1949             case 'M': /* long or a mneumonic string (string not supported) */
1950 5           saw_M = 1;
1951             /* Fall through */
1952             #if PARI_VERSION_EXP >= 2004002
1953             case 'P': /* series precision */
1954             #endif
1955             case 'L': /* long */
1956 142 100         argvec[i++] = (GEN) (long)SvIV(args[j]);
1957 142           j++;
1958 142           break;
1959              
1960             case 'n': /* var number */
1961 6           argvec[i++] = (GEN) numvar(sv2pari(args[j++]));
1962 6           break;
1963              
1964             case 'V': /* variable */
1965             #if PARI_VERSION_EXP < 2004002
1966             ep1 = bindVariable(args[j++]);
1967             argvec[i++] = (GEN)ep1;
1968             if (EpVALENCE(ep1) != EpVAR && *(s-1) == 'V')
1969             croak("Did not get a variable");
1970             saw_V++;
1971             #else
1972 607 50         if (*s != '=')
1973 0           warn("Unexpected: `V' not followed by `='"); /* appears in fordiv() etc. */
1974 607 50         if (saw_V >= MaxPariVar)
1975 0           croak("Too many loop variables in a signature (max=%d)", MaxPariVar);
1976 607           loopvars[saw_V++] = args[j++]; /* XXXX Ignore this variable (should be compiled into the closure!!!) ??? */
1977             #endif
1978 607           break;
1979             case 'S': /* symbol */
1980             #if PARI_VERSION_EXP < 2004002
1981             ep1 = bindVariable(args[j++]);
1982             argvec[i++] = (GEN)ep1;
1983             #else
1984 0           croak("Variable type `S' unsupported after 2.4.2");
1985             #endif
1986             break;
1987             case '&': /* *GEN */
1988 2           gen_OUT[*OUT_cnt] = sv2pari(args[j]);
1989 2           argvec[i++] = (GEN)(gen_OUT + *OUT_cnt);
1990 2           sv_OUT[(*OUT_cnt)++] = args[j++];
1991 2           break;
1992             case 'E': /* Input position - subroutine */
1993             case 'I': /* Input position - subroutine, ignore value */
1994 844 50         if (!args[j])
1995 0           croak("panic: no arg when AssignPariExpr()");
1996 844 50         if (saw_V > 1) {
1997 0 0         if (saw_V > 2)
1998 0           croak("More than 2 running variables per PARI entry point not supported");
1999 0           AssignPariExpr2R(expr,args[j], 'I'==s[-1], LoopVar(0), LoopVar(1));
2000 844 100         } else if (saw_V == 1) {
2001 607 50         AssignPariExprR(expr,args[j], 'I'==s[-1], LoopVar(0));
    50          
2002             } else
2003 237           croak("Type E, I without a preceding variable");
2004 607           argvec[i++] = (GEN) expr; /* XXXX Cast not needed after 2004002 */
2005 607           j++;
2006 607           break;
2007              
2008             case 's': /* expanded string; empty arg yields "" */
2009 20 100         if (*s == '*') {
2010 10           int ii = 0;
2011 10           GEN out = cgetg(items-j+1, t_VEC);
2012              
2013 10           s++;
2014 10           argvec[i++] = out;
2015 20 100         while (j < items)
2016 10           out[1 + ii++] = (long)sv2pariStr(args[j++]);
2017 10           goto args_done;
2018             }
2019             case 'r': /* raw */
2020 10 50         argvec[i++] = (GEN) SvPV(args[j],na);
2021 10           j++;
2022 10           break;
2023              
2024             case 'p': /* precision */
2025 661           argvec[i++] = (GEN) prec_words;
2026 661           break;
2027              
2028             #if PARI_VERSION_EXP >= 2008000
2029             case 'b': /* bitprecision */
2030 9           warn("===Passing precision=%ld; precreal=%ld", (long)prec_bits, (long)precreal);
2031 9           argvec[i++] = (GEN)precreal; /* prec_bits; */
2032 9           break;
2033             #endif
2034              
2035             case '=':
2036             case ',':
2037 683           break;
2038              
2039             case 'D': /* Has a default value */
2040 1956           pre = s;
2041 1956 100         if (j >= items || !SvOK(args[j]))
    100          
    50          
    50          
2042             {
2043 757 100         if (j < items)
2044 482           j++;
2045              
2046 757 100         if ( *s == 'G' || *s == '&'
    100          
2047 622 50         || *s == 'r' || *s == 's'
    50          
2048 622 50         || *s == 'E' || *s == 'I' || *s == 'V') {
    50          
    100          
2049 609           argvec[i++]=DFT_GEN; s++;
2050 609           break;
2051             }
2052 148 100         if (*s == 'n') {
2053 9           argvec[i++]=DFT_VAR; s++;
2054 9           break;
2055             }
2056 139 100         if (*s == 'P') {
2057 3           argvec[i++] = (GEN) precdl; s++;
2058 3           break;
2059             }
2060 274 50         while (*s && *s++ != ',');
    100          
2061 136 50         if (!*s)
2062 0 0         if (!s[0] && s[-1] != ',')
    0          
2063 0           goto unrecognized_syntax;
2064 136           switch (*s) {
2065             case 'r': case 's':
2066 0 0         if (pre[0] == '\"' && pre[1] == '\"'
    0          
2067 0 0         && s - pre == 3) {
2068 0           argvec[i++] = (GEN) "";
2069 0           break;
2070             }
2071 0           goto unknown;
2072             case 'M': /* long or a mneumonic string
2073             (string not supported) */
2074 4           saw_M = 1;
2075             /* Fall through */
2076             case 'L': /* long */
2077 136           argvec[i++] = (GEN) MYatol(pre);
2078 136           break;
2079             case 'G':
2080 0 0         if ((*pre == '1' || *pre == '0') && pre[1]==',') {
    0          
    0          
2081 0           argvec[i++] = (*pre == '1'
2082 0 0         ? gen_1 : gen_0);
2083 0           break;
2084             }
2085             default:
2086             unknown:
2087 0           croak("Cannot process default argument %.*s of type %.1s for prototype '%s'",
2088 0           (int)(s - pre - 1), pre, s, s0);
2089             }
2090 136           s++; /* Skip ',' */
2091             }
2092             else
2093 1199 100         if (*s == 'G' || *s == '&' || *s == 'n'
    100          
    100          
2094 313 50         || *s == 'P' || *s == 'r' || *s == 's'
    50          
    50          
2095 313 100         || *s == 'E' || *s == 'I' || *s == 'V')
    50          
    50          
2096             break;
2097 288 50         while (*s && *s++ != ',');
    100          
2098 212 100         if (!s[0] && s[-1] != ',') {
    50          
2099             unrecognized_syntax:
2100 0           croak("Unexpected syntax of default argument '%s' in prototype '%s'",
2101             pre - 1, s0);
2102             }
2103 212           break;
2104              
2105             #if PARI_VERSION_EXP < 2004002
2106             case 'P': /* series precision */
2107             argvec[i++] = (GEN) precdl;
2108             break;
2109             #endif
2110              
2111             case 'f': /* Fake *long argument */
2112 0           argvec[i++] = (GEN) &fake;
2113 0           break;
2114              
2115             case 'x': /* Foreign function */
2116 0           croak("Calling Perl via PARI with an unknown interface: avoiding loop");
2117             break;
2118              
2119             case 'l': /* Return long */
2120 8           *rettype = RETTYPE_LONG; break;
2121              
2122             case 'i': /* Return int */
2123 5           *rettype = RETTYPE_INT; break;
2124              
2125             case 'v': /* Return void */
2126 69           *rettype = RETTYPE_VOID; break;
2127              
2128             case '\n': /* Mneumonic starts */
2129 9 50         if (saw_M) {
2130 9           s = ""; /* Finish processing */
2131 9           break;
2132             }
2133             /* FALL THROUGH */
2134             default:
2135 0           croak("Unsupported code '%.1s' in signature '%s' of a PARI function `%s'", s-1, s0, ep->name);
2136             }
2137 7520 50         if (j > items)
2138 0           croak("Too few args %d for PARI function `%s'", items, ep->name);
2139             }
2140 951 50         if (j < items)
2141 0           croak("%d unused args for PARI function %s of signature `%s' (with %d args)", items - j, ep->name, ep->code, j);
2142             /* if (j>=1)
2143             dbgGEN(argvec[2],j-1); */
2144             args_done: {
2145             #if PURIFY
2146             for ( ; i
2147             #endif
2148             }
2149 961           }
2150              
2151             static void
2152 2           fill_outvect(SV **sv_OUT, GEN *gen_OUT, long c, pari_sp oldavma)
2153             {
2154 4 100         while (c-- > 0)
2155 2           resetSVpari(sv_OUT[c], gen_OUT[c], oldavma);
2156 2           }
2157              
2158             #define _to_int(in,dummy1,dummy2) to_int(in)
2159              
2160             static GEN
2161 1           to_int(GEN in)
2162             {
2163 1           long sign = gcmp(in,gen_0);
2164              
2165 1 50         if (!sign)
2166 0           return gen_0;
2167 1           switch (typ(in)) {
2168             case t_INT:
2169             #if PARI_VERSION_EXP < 2002008
2170             case t_SMALL:
2171             #endif
2172 0           return in;
2173             case t_INTMOD:
2174 0           return lift0(in, -1); /* -1: not as polmod */
2175             default:
2176 1           return gtrunc(in);
2177             }
2178             }
2179              
2180             typedef int (*FUNC_PTR)();
2181             typedef void (*TSET_FP)(char *s);
2182              
2183             #ifdef NO_HIGHLEVEL_PARI
2184             # define NO_GRAPHICS_PARI
2185             # define have_highlevel() 0
2186             #else
2187             # define have_highlevel() 1
2188             #endif
2189              
2190             #ifdef NO_GNUPLOT_PARI
2191             # define have_graphics() -1
2192             # define set_gnuterm(a,b,c) croak("This build of Math::Pari has no Gnuplot plotting support")
2193             # define int_set_term_ftable(a) croak("This build of Math::Pari has no Gnuplot plotting support")
2194             #else
2195             # ifdef NO_GRAPHICS_PARI
2196             # define have_graphics() 0
2197             # define set_gnuterm(a,b,c) croak("This build of Math::Pari has no plotting support")
2198             # define int_set_term_ftable(a) croak("This build of Math::Pari has no plotting support")
2199             # else
2200             # define have_graphics() 1
2201             # if PARI_VERSION_EXP < 2000013
2202             # define set_gnuterm(a,b,c) \
2203             set_term_funcp((FUNC_PTR)(a),(struct termentry *)(b))
2204             # else /* !( PARI_VERSION_EXP < 2000013 ) */
2205             # define set_gnuterm(a,b,c) \
2206             set_term_funcp3((FUNC_PTR)(INT2PTR(void*, a)), INT2PTR(struct termentry *, b), INT2PTR(TSET_FP,c))
2207             extern void set_term_funcp3(FUNC_PTR change_p, void *term_p, TSET_FP tchange);
2208              
2209             # endif /* PARI_VERSION_EXP < 2000013 */
2210              
2211             # define int_set_term_ftable(a) (v_set_term_ftable(INT2PTR(void*,a)))
2212             # endif
2213             #endif
2214              
2215             extern void v_set_term_ftable(void *a);
2216              
2217             /* Cast off `const' */
2218             #define s_type_name(x) (char *)type_name(typ(x));
2219              
2220             static int reset_on_reload = 0;
2221              
2222             int
2223 0           s_reset_on_reload(int newvalue)
2224             {
2225 0           int old = reset_on_reload;
2226 0 0         if (newvalue >= 0)
2227 0           reset_on_reload = newvalue;
2228 0           return old;
2229             }
2230              
2231             static int
2232 255863           isPariFunction(entree *ep)
2233             {
2234             #if PARI_VERSION_EXP < 2004000
2235             return EpVALENCE(ep) < EpUSER;
2236             /* && ep>=fonctions && ep < fonctions+NUMFUNC) */
2237             #else /* !( PARI_VERSION_EXP < 2004000) */
2238 255863 50         return (EpVALENCE(ep) == 0 || (EpVALENCE(ep) != EpNEW && typ((GEN)(ep->value))==t_CLOSURE)); /* == EpVAR */
    0          
    0          
2239             #endif /* !( PARI_VERSION_EXP < 2004000) */
2240             }
2241              
2242             #if 1
2243             # define checkPariFunction(arg)
2244             #else
2245             void
2246             checkPariFunction(const char *name)
2247             {
2248             long hash;
2249             entree *ep = is_entry_intern(name, functions_hash, &hash);
2250             warn( "Ep for `%s': VALENCE=%#04x, EpVAR=%d, EpINSTALL=%d, name=<%s>, code=<%s>, isFunction=%d", name, (ep ? (int)EpVALENCE(ep) : 0xDEAD),
2251             (int)EpVAR, (int)EpINSTALL, (ep ? ep->name : ""),
2252             ((ep && ep->code) ? ep->code : ""), (ep && isPariFunction(ep)));
2253             }
2254             #endif
2255              
2256             #if PARI_VERSION_EXP < 2008000 /* Need to recheck with each new major release??? See src/desc/gen_proto, src/test/32/help */
2257             # define TAG_community 12 /* "The PARI community" */
2258             #else /* !(PARI_VERSION_EXP < 2008000) */
2259             # if PARI_VERSION_EXP < 2010000
2260             # define TAG_community 15 /* "The PARI community" */
2261             # else /* !(PARI_VERSION_EXP < 2010000) */
2262             # if PARI_VERSION_EXP < 2014000
2263             # define TAG_community 17 /* "The PARI community" */
2264             # else /* !(PARI_VERSION_EXP < 2012000) */
2265             # define TAG_community TAG_community_unknown___needs_to_be_checked_for_every_new_version__see__GPbuilddir_src_test_32_help
2266             # endif /* !(PARI_VERSION_EXP < 2012000) */
2267             # endif /* !(PARI_VERSION_EXP < 2010000) */
2268             #endif /* !(PARI_VERSION_EXP < 2008000) */
2269              
2270             # define INTERNAL_TAG_start (TAG_community+1) /* symbolic_operators */
2271             # define INTERNAL_TAG_end (TAG_community+3) /* programming/internals (in between: member_functions) */
2272              
2273             int
2274 293216           _is_internal(int tag)
2275             { /* from gp_rl.c */
2276             #if PARI_VERSION_EXP < 2004000
2277             return 0;
2278             #else /* !( PARI_VERSION_EXP < 2004000) */
2279 293216 100         return tag >= INTERNAL_TAG_start && tag <= INTERNAL_TAG_end;
    50          
2280             #endif /* !( PARI_VERSION_EXP < 2004000) */
2281             }
2282              
2283             char *
2284 0           added_sections()
2285             {
2286             #if PARI_VERSION_EXP < 2013000
2287             /* Suggestion on format (part of 2.10.0), only use short names: "4: functions related to COMBINATORICS\n13: L-FUNCTIONS" */
2288             return "";
2289             #else /* !( PARI_VERSION_EXP < 2011000) */
2290             /* Check by entering "?" at gp prompt. Compare with the list in Pari.pm */
2291 0           croak("Do not know which \"sections\" (of list of functions) were added to PARI at v2.11.0");
2292             #endif /* !( PARI_VERSION_EXP < 2011000) */
2293             }
2294              
2295              
2296             #if PARI_VERSION_EXP >= 2006000 /* taken from 2.5.5 */
2297             static GEN
2298 0 0         gand(GEN x, GEN y) { return gequal0(x)? gen_0: (gequal0(y)? gen_0: gen_1); }
    0          
2299              
2300             static GEN
2301 0 0         gor(GEN x, GEN y) { return gequal0(x)? (gequal0(y)? gen_0: gen_1): gen_1; }
    0          
2302             #endif /* PARI_VERSION_EXP >= 2006000 */
2303              
2304              
2305             MODULE = Math::Pari PACKAGE = Math::Pari PREFIX = Arr_
2306              
2307             PROTOTYPES: ENABLE
2308              
2309             GEN
2310             Arr_FETCH(g,n)
2311             long oldavma=avma;
2312             GEN g
2313             I32 n
2314              
2315             void
2316             Arr_STORE(g,n,elt)
2317             long oldavma=avma;
2318             GEN g
2319             I32 n
2320             GEN elt
2321             CLEANUP:
2322 4           avma=oldavma;
2323              
2324             I32
2325             Arr_FETCHSIZE(g)
2326             long oldavma=avma;
2327             GEN g
2328             CLEANUP:
2329 0           avma=oldavma;
2330              
2331             I32
2332             Arr_EXISTS(g,elt)
2333             long oldavma=avma;
2334             GEN g
2335             long elt
2336             CLEANUP:
2337 0           avma=oldavma;
2338              
2339             MODULE = Math::Pari PACKAGE = Math::Pari
2340              
2341             PROTOTYPES: ENABLE
2342              
2343             int
2344             is_gnil(in)
2345             GEN in
2346              
2347             GEN
2348             sv2pari(sv)
2349             long oldavma=avma;
2350             SV * sv
2351              
2352             GEN
2353             sv2parimat(sv)
2354             long oldavma=avma;
2355             SV * sv
2356              
2357             SV *
2358             pari2iv(in)
2359             long oldavma=avma;
2360             GEN in
2361             CLEANUP:
2362 7           avma=oldavma;
2363              
2364             SV *
2365             pari2nv(in)
2366             long oldavma=avma;
2367             GEN in
2368             CLEANUP:
2369 1           avma=oldavma;
2370              
2371             SV *
2372             pari2num_(in,...)
2373             long oldavma=avma;
2374             GEN in
2375             CODE:
2376 35791 50         if (typ(in) == t_INT) {
2377 35791           RETVAL=pari2iv(in);
2378             } else {
2379 0           RETVAL=pari2nv(in);
2380             }
2381             OUTPUT:
2382             RETVAL
2383             CLEANUP:
2384 35791           avma=oldavma;
2385              
2386             SV *
2387             pari2num(in)
2388             long oldavma=avma;
2389             GEN in
2390             CODE:
2391 0 0         if (typ(in) == t_INT) {
2392 0           RETVAL=pari2iv(in);
2393             } else {
2394 0           RETVAL=pari2nv(in);
2395             }
2396             OUTPUT:
2397             RETVAL
2398             CLEANUP:
2399 0           avma=oldavma;
2400              
2401             SV *
2402             pari2pv(in,...)
2403             long oldavma=avma;
2404             GEN in
2405             CODE:
2406 448           RETVAL=pari2pv(in);
2407             OUTPUT:
2408             RETVAL
2409             CLEANUP:
2410 448           avma=oldavma;
2411              
2412             GEN
2413             _to_int(in, dummy1, dummy2)
2414             long oldavma=avma;
2415             GEN in
2416             SV *dummy1 = NO_INIT
2417             SV *dummy2 = NO_INIT
2418             CODE:
2419             PERL_UNUSED_VAR(dummy1); /* -W */
2420             PERL_UNUSED_VAR(dummy2); /* -W */
2421 1           RETVAL = _to_int(in, dummy1, dummy2);
2422             OUTPUT:
2423             RETVAL
2424              
2425             GEN
2426             PARI(...)
2427             long oldavma=avma;
2428             CODE:
2429 53132 50         if (items==1) {
2430 53132           RETVAL=sv2pari(ST(0));
2431             } else {
2432             int i;
2433              
2434 0           RETVAL=cgetg(items+1, t_VEC);
2435 0 0         for (i=0;i
2436 0           RETVAL[i+1]=(long)sv2pari(ST(i));
2437             }
2438             }
2439             OUTPUT:
2440             RETVAL
2441              
2442             GEN
2443             PARIcol(...)
2444             long oldavma=avma;
2445             CODE:
2446 3 50         if (items==1) {
2447 3           RETVAL=sv2pari(ST(0));
2448 3 50         if (t_VEC == typ(RETVAL))
2449 3           settyp(RETVAL, t_COL);
2450             } else {
2451             int i;
2452              
2453 0           RETVAL=cgetg(items+1, t_VEC);
2454 0 0         for (i=0;i
2455 0           RETVAL[i+1]=(long)sv2pari(ST(i));
2456             }
2457 0           settyp(RETVAL, t_COL);
2458             }
2459             OUTPUT:
2460             RETVAL
2461              
2462             GEN
2463             PARIvecL(...)
2464             long oldavma=avma;
2465             CODE:
2466             int i;
2467              
2468 0           RETVAL=cgetg(items+1, t_VEC);
2469 0 0         for (i=0;i
2470 0           RETVAL[i+1]=(long)sv2pari(ST(i));
2471             }
2472             OUTPUT:
2473             RETVAL
2474              
2475             GEN
2476             PARIcolL(...)
2477             long oldavma=avma;
2478             CODE:
2479             int i;
2480              
2481 12           RETVAL=cgetg(items+1, t_VEC);
2482 37 100         for (i=0;i
2483 25           RETVAL[i+1]=(long)sv2pari(ST(i));
2484             }
2485 12           settyp(RETVAL, t_COL);
2486             OUTPUT:
2487             RETVAL
2488              
2489             GEN
2490             PARImat(...)
2491             long oldavma=avma;
2492             CODE:
2493 289 50         if (items==1) {
2494 289           RETVAL=sv2parimat(ST(0));
2495             } else {
2496             int i;
2497              
2498 0           RETVAL=cgetg(items+1, t_MAT);
2499 0 0         for (i=0;i
2500 0           RETVAL[i+1]=(long)sv2pari(ST(i));
2501 0 0         if (t_VEC == typ((GEN)(RETVAL[i+1]))) {
2502 0           settyp(RETVAL[i+1], t_COL);
2503 0 0         } else if (t_COL != typ((GEN)(RETVAL[i+1]))) {
2504 0           croak("%ld'th argument (of %ld) to PARImat() is not a vector", (long)i, (long)items);
2505             }
2506             }
2507             }
2508             OUTPUT:
2509             RETVAL
2510              
2511             GEN
2512             PARImatL(...)
2513             long oldavma=avma;
2514             CODE:
2515             int i;
2516              
2517 0           RETVAL=cgetg(items+1, t_MAT);
2518 0 0         for (i=0;i
2519 0           RETVAL[i+1]=(long)sv2pari(ST(i));
2520 0 0         if (t_VEC == typ((GEN)(RETVAL[i+1]))) {
2521 0           settyp(RETVAL[i+1], t_COL);
2522 0 0         } else if (t_COL != typ((GEN)(RETVAL[i+1]))) {
2523 0           croak("%ld'th argument (of %ld) to PARImatL() is not a vector", (long)i, (long)items);
2524             }
2525             }
2526             OUTPUT:
2527             RETVAL
2528              
2529             void
2530             installPerlFunctionCV(cv, name, numargs = 1, help = NULL)
2531             SV* cv
2532             char *name
2533             I32 numargs
2534             char *help
2535             PROTOTYPE: DISABLE
2536              
2537             # In what follows if a function returns long, we do not need anything
2538             # on the stack, thus we add a cleanup section.
2539              
2540             void
2541             interface_flexible_void(...)
2542             long oldavma=avma;
2543             CODE:
2544             {
2545 69           entree *ep = (entree *) XSANY.any_dptr;
2546 69           void (*FUNCTION_real)(VARARG)
2547 69           = (void (*)(VARARG))ep->value;
2548             GEN argvec[ARGS_SUPPORTED];
2549 69           long rettype = RETTYPE_GEN;
2550 69           long has_pointer = 0; /* XXXX ?? */
2551             long OUT_cnt;
2552             SV *sv_OUT[ARGS_SUPPORTED];
2553             GEN gen_OUT[ARGS_SUPPORTED];
2554              
2555 69           fill_argvect(ep, ep->code, &has_pointer, argvec, &rettype, &ST(0), items,
2556             sv_OUT, gen_OUT, &OUT_cnt);
2557              
2558 69 50         if (rettype != RETTYPE_VOID)
2559 0           croak("Expected VOID return type, got code '%s'", ep->code);
2560            
2561 69           (FUNCTION_real)(THE_ARGS_SUPPORTED);
2562 58 50         if (has_pointer)
2563 0           check_pointer(has_pointer,argvec);
2564 58 50         if (OUT_cnt)
2565 0           fill_outvect(sv_OUT, gen_OUT, OUT_cnt, oldavma);
2566             }
2567              
2568             GEN
2569             interface_flexible_gen(...)
2570             long oldavma=avma;
2571             CODE:
2572             {
2573 1116           entree *ep = (entree *) XSANY.any_dptr;
2574 1116           GEN (*FUNCTION_real)(VARARG)
2575 1116           = (GEN (*)(VARARG))ep->value;
2576             GEN argvec[9];
2577 1116           long rettype = RETTYPE_GEN;
2578 1116           long has_pointer = 0; /* XXXX ?? */
2579             long OUT_cnt;
2580             SV *sv_OUT[ARGS_SUPPORTED];
2581             GEN gen_OUT[ARGS_SUPPORTED];
2582              
2583 1116           fill_argvect(ep, ep->code, &has_pointer, argvec, &rettype, &ST(0), items,
2584             sv_OUT, gen_OUT, &OUT_cnt);
2585              
2586 879 50         if (rettype != RETTYPE_GEN)
2587 0           croak("Expected GEN return type, got code '%s'", ep->code);
2588            
2589 879           RETVAL = (FUNCTION_real)(THE_ARGS_SUPPORTED);
2590 873 50         if (has_pointer)
2591 0           check_pointer(has_pointer,argvec);
2592 873 100         if (OUT_cnt)
2593 2           fill_outvect(sv_OUT, gen_OUT, OUT_cnt, oldavma);
2594             }
2595             OUTPUT:
2596             RETVAL
2597              
2598             long
2599             interface_flexible_long(...)
2600             long oldavma=avma;
2601             CODE:
2602             {
2603 8           entree *ep = (entree *) XSANY.any_dptr;
2604 8           long (*FUNCTION_real)(VARARG)
2605 8           = (long (*)(VARARG))ep->value;
2606             GEN argvec[9];
2607 8           long rettype = RETTYPE_GEN;
2608 8           long has_pointer = 0; /* XXXX ?? */
2609             long OUT_cnt;
2610             SV *sv_OUT[ARGS_SUPPORTED];
2611             GEN gen_OUT[ARGS_SUPPORTED];
2612              
2613 8           fill_argvect(ep, ep->code, &has_pointer, argvec, &rettype, &ST(0), items,
2614             sv_OUT, gen_OUT, &OUT_cnt);
2615              
2616 8 50         if (rettype != RETTYPE_LONG)
2617 0           croak("Expected long return type, got code '%s'", ep->code);
2618            
2619 8           RETVAL = FUNCTION_real(THE_ARGS_SUPPORTED);
2620 8 50         if (has_pointer)
2621 0           check_pointer(has_pointer,argvec);
2622 8 50         if (OUT_cnt)
2623 0           fill_outvect(sv_OUT, gen_OUT, OUT_cnt, oldavma);
2624             }
2625             OUTPUT:
2626             RETVAL
2627              
2628             int
2629             interface_flexible_int(...)
2630             long oldavma=avma;
2631             CODE:
2632             {
2633 5           entree *ep = (entree *) XSANY.any_dptr;
2634 5           int (*FUNCTION_real)(VARARG)
2635 5           = (int (*)(VARARG))ep->value;
2636             GEN argvec[9];
2637 5           long rettype = RETTYPE_GEN;
2638 5           long has_pointer = 0; /* XXXX ?? */
2639             long OUT_cnt;
2640             SV *sv_OUT[ARGS_SUPPORTED];
2641             GEN gen_OUT[ARGS_SUPPORTED];
2642              
2643 5           fill_argvect(ep, ep->code, &has_pointer, argvec, &rettype, &ST(0), items,
2644             sv_OUT, gen_OUT, &OUT_cnt);
2645              
2646 5 50         if (rettype != RETTYPE_INT)
2647 0           croak("Expected int return type, got code '%s'", ep->code);
2648            
2649 5           RETVAL=FUNCTION_real(argvec[0], argvec[1], argvec[2], argvec[3],
2650             argvec[4], argvec[5], argvec[6], argvec[7], argvec[8]);
2651 5 50         if (has_pointer)
2652 0           check_pointer(has_pointer,argvec);
2653 5 50         if (OUT_cnt)
2654 0           fill_outvect(sv_OUT, gen_OUT, OUT_cnt, oldavma);
2655             }
2656             OUTPUT:
2657             RETVAL
2658              
2659             GEN
2660             interface0()
2661             long oldavma=avma;
2662             CODE:
2663             {
2664 2705           dFUNCTION(GEN);
2665              
2666 2705 50         if (!FUNCTION) {
2667 0           croak("XSUB call through interface did not provide *function");
2668             }
2669              
2670 2705           RETVAL=FUNCTION(prec_words);
2671             }
2672             OUTPUT:
2673             RETVAL
2674              
2675             GEN
2676             interface9900()
2677             long oldavma=avma;
2678             CODE:
2679             { /* Code="" */
2680 1499           dFUNCTION(GEN);
2681              
2682 1499 50         if (!FUNCTION) {
2683 0           croak("XSUB call through interface did not provide *function");
2684             }
2685              
2686 1499           RETVAL=FUNCTION();
2687             }
2688             OUTPUT:
2689             RETVAL
2690              
2691             GEN
2692             interface1(arg1)
2693             long oldavma=avma;
2694             GEN arg1
2695             CODE:
2696             { /* Code="Gp" */
2697 36785           dFUNCTION(GEN);
2698              
2699 36785 50         if (!FUNCTION) {
2700 0           croak("XSUB call through interface did not provide *function");
2701             }
2702              
2703 36785           RETVAL=FUNCTION(arg1,prec_words);
2704             }
2705             OUTPUT:
2706             RETVAL
2707              
2708             # with fake arguments for overloading
2709              
2710             GEN
2711             interface199(arg1,arg2,inv)
2712             long oldavma=avma;
2713             GEN arg1
2714             GEN arg2 = NO_INIT
2715             long inv = NO_INIT
2716             CODE:
2717             {
2718 12914           dFUNCTION(GEN);
2719              
2720 12914 50         if (!FUNCTION) {
2721 0           croak("XSUB call through interface did not provide *function");
2722             }
2723              
2724             PERL_UNUSED_VAR(arg2); /* -W */
2725             PERL_UNUSED_VAR(inv); /* -W */
2726 12914           RETVAL=FUNCTION(arg1,prec_words);
2727             }
2728             OUTPUT:
2729             RETVAL
2730              
2731             long
2732             interface10(arg1)
2733             long oldavma=avma;
2734             GEN arg1
2735             CODE:
2736             { /* Code="lG" */
2737 8           dFUNCTION(long);
2738              
2739 8 50         if (!FUNCTION) {
2740 0           croak("XSUB call through interface did not provide *function");
2741             }
2742              
2743 8           RETVAL=FUNCTION(arg1);
2744             }
2745             OUTPUT:
2746             RETVAL
2747             CLEANUP:
2748 8           avma=oldavma;
2749              
2750             # With fake arguments for overloading
2751              
2752             long
2753             interface109(arg1,arg2,inv)
2754             long oldavma=avma;
2755             GEN arg1
2756             GEN arg2 = NO_INIT
2757             long inv = NO_INIT
2758             CODE:
2759             {
2760 0           dFUNCTION(long);
2761              
2762 0 0         if (!FUNCTION) {
2763 0           croak("XSUB call through interface did not provide *function");
2764             }
2765              
2766             PERL_UNUSED_VAR(arg2); /* -W */
2767             PERL_UNUSED_VAR(inv); /* -W */
2768 0           RETVAL=FUNCTION(arg1);
2769             }
2770             OUTPUT:
2771             RETVAL
2772             CLEANUP:
2773 0           avma=oldavma;
2774              
2775             GEN
2776             interface11(arg1)
2777             long oldavma=avma;
2778             long arg1
2779             CODE:
2780             { /* Code="L" */
2781 24           dFUNCTION(GEN);
2782              
2783 24 50         if (!FUNCTION) {
2784 0           croak("XSUB call through interface did not provide *function");
2785             }
2786              
2787 24           RETVAL=FUNCTION(arg1);
2788             }
2789             OUTPUT:
2790             RETVAL
2791              
2792             long
2793             interface15(arg1)
2794             long oldavma=avma;
2795             long arg1
2796             CODE:
2797             {
2798 0           dFUNCTION(long);
2799              
2800 0 0         if (!FUNCTION) {
2801 0           croak("XSUB call through interface did not provide *function");
2802             }
2803              
2804 0           RETVAL=FUNCTION(arg1);
2805             }
2806             OUTPUT:
2807             RETVAL
2808             CLEANUP:
2809 0           avma=oldavma;
2810              
2811             GEN
2812             interface18(arg1)
2813             long oldavma=avma;
2814             GEN arg1
2815             CODE:
2816             { /* Code="G" */
2817 380           dFUNCTION(GEN);
2818              
2819 380 50         if (!FUNCTION) {
2820 0           croak("XSUB call through interface did not provide *function");
2821             }
2822              
2823 380           RETVAL=FUNCTION(arg1);
2824             }
2825             OUTPUT:
2826             RETVAL
2827              
2828             GEN
2829             interface2(arg1,arg2)
2830             long oldavma=avma;
2831             GEN arg1
2832             GEN arg2
2833             CODE:
2834             { /* Code="GG" */
2835 80           dFUNCTION(GEN);
2836              
2837 80 50         if (!FUNCTION) {
2838 0           croak("XSUB call through interface did not provide *function");
2839             }
2840              
2841 80           RETVAL=FUNCTION(arg1,arg2);
2842             }
2843             OUTPUT:
2844             RETVAL
2845              
2846             # With fake arguments for overloading
2847              
2848             GEN
2849             interface299(arg1,arg2,inv)
2850             long oldavma=avma;
2851             GEN arg1
2852             GEN arg2
2853             bool inv
2854             CODE:
2855             {
2856 2941217           dFUNCTION(GEN);
2857              
2858 2941217 50         if (!FUNCTION) {
2859 0           croak("XSUB call through interface did not provide *function");
2860             }
2861              
2862 2941217 100         RETVAL = inv? FUNCTION(arg2,arg1): FUNCTION(arg1,arg2);
2863             }
2864             OUTPUT:
2865             RETVAL
2866              
2867             long
2868             interface20(arg1,arg2)
2869             long oldavma=avma;
2870             GEN arg1
2871             GEN arg2
2872             CODE:
2873             { /* Code="lGG" */
2874 2           dFUNCTION(long);
2875              
2876 2 50         if (!FUNCTION) {
2877 0           croak("XSUB call through interface did not provide *function");
2878             }
2879              
2880 2           RETVAL=FUNCTION(arg1,arg2);
2881             }
2882             OUTPUT:
2883             RETVAL
2884             CLEANUP:
2885 2           avma=oldavma;
2886              
2887             # With fake arguments for overloading and comparison to gen_1 for speed
2888              
2889             long
2890             interface2099(arg1,arg2,inv)
2891             long oldavma=avma;
2892             GEN arg1
2893             GEN arg2
2894             bool inv
2895             CODE:
2896             {
2897 69           dFUNCTION(GEN);
2898              
2899 69 50         if (!FUNCTION) {
2900 0           croak("XSUB call through interface did not provide *function");
2901             }
2902              
2903 69 100         RETVAL = (inv? FUNCTION(arg2,arg1): FUNCTION(arg1,arg2)) == gen_1;
2904             }
2905             OUTPUT:
2906             RETVAL
2907             CLEANUP:
2908 69           avma=oldavma;
2909              
2910             # With fake arguments for overloading
2911              
2912             long
2913             interface209(arg1,arg2,inv)
2914             long oldavma=avma;
2915             GEN arg1
2916             GEN arg2
2917             bool inv
2918             CODE:
2919             {
2920 0           dFUNCTION(long);
2921              
2922 0 0         if (!FUNCTION) {
2923 0           croak("XSUB call through interface did not provide *function");
2924             }
2925              
2926 0 0         RETVAL = inv? FUNCTION(arg2,arg1): FUNCTION(arg1,arg2);
2927             }
2928             OUTPUT:
2929             RETVAL
2930             CLEANUP:
2931 0           avma=oldavma;
2932              
2933             # With fake arguments for overloading, int return
2934              
2935             int
2936             interface2091(arg1,arg2,inv)
2937             long oldavma=avma;
2938             GEN arg1
2939             GEN arg2
2940             bool inv
2941             CODE:
2942             {
2943 20           dFUNCTION(int);
2944              
2945 20 50         if (!FUNCTION) {
2946 0           croak("XSUB call through interface did not provide *function");
2947             }
2948              
2949 20 100         RETVAL = inv? FUNCTION(arg2,arg1): FUNCTION(arg1,arg2);
2950             }
2951             OUTPUT:
2952             RETVAL
2953             CLEANUP:
2954 20           avma=oldavma;
2955              
2956             GEN
2957             interface29(arg1,arg2)
2958             long oldavma=avma;
2959             GEN arg1
2960             GEN arg2
2961             CODE:
2962             { /* Code="GGp" */
2963 11           dFUNCTION(GEN);
2964              
2965 11 50         if (!FUNCTION) {
2966 0           croak("XSUB call through interface did not provide *function");
2967             }
2968              
2969 11           RETVAL=FUNCTION(arg1,arg2,prec_words);
2970             }
2971             OUTPUT:
2972             RETVAL
2973              
2974             GEN
2975             interface3(arg1,arg2,arg3)
2976             long oldavma=avma;
2977             GEN arg1
2978             GEN arg2
2979             GEN arg3
2980             CODE:
2981             { /* Code="GGG" */
2982 18           dFUNCTION(GEN);
2983              
2984 18 50         if (!FUNCTION) {
2985 0           croak("XSUB call through interface did not provide *function");
2986             }
2987              
2988 18           RETVAL=FUNCTION(arg1,arg2,arg3);
2989             }
2990             OUTPUT:
2991             RETVAL
2992              
2993             long
2994             interface30(arg1,arg2,arg3)
2995             long oldavma=avma;
2996             GEN arg1
2997             GEN arg2
2998             GEN arg3
2999             CODE:
3000             { /* Code="lGGG" */
3001 0           dFUNCTION(long);
3002              
3003 0 0         if (!FUNCTION) {
3004 0           croak("XSUB call through interface did not provide *function");
3005             }
3006              
3007 0           RETVAL=FUNCTION(arg1,arg2,arg3);
3008             }
3009             OUTPUT:
3010             RETVAL
3011             CLEANUP:
3012 0           avma=oldavma;
3013              
3014             GEN
3015             interface4(arg1,arg2,arg3,arg4)
3016             long oldavma=avma;
3017             GEN arg1
3018             GEN arg2
3019             GEN arg3
3020             GEN arg4
3021             CODE:
3022             { /* Code="GGGG" */
3023 0           dFUNCTION(GEN);
3024              
3025 0 0         if (!FUNCTION) {
3026 0           croak("XSUB call through interface did not provide *function");
3027             }
3028              
3029 0           RETVAL=FUNCTION(arg1,arg2,arg3,arg4);
3030             }
3031             OUTPUT:
3032             RETVAL
3033              
3034             GEN
3035             interface5(arg1,arg2,arg3,arg4)
3036             long oldavma=avma;
3037             GEN arg1
3038             GEN arg2
3039             GEN arg3
3040             GEN arg4
3041             CODE:
3042             {
3043 0           dFUNCTION(GEN);
3044              
3045 0 0         if (!FUNCTION) {
3046 0           croak("XSUB call through interface did not provide *function");
3047             }
3048              
3049 0           RETVAL=FUNCTION(arg1,arg2,arg3,arg4,prec_words);
3050             }
3051             OUTPUT:
3052             RETVAL
3053              
3054             GEN
3055             interface12(arg1,arg2)
3056             long oldavma=avma;
3057             GEN arg1
3058             GEN arg2
3059             CODE:
3060             { /* Code="GnP" */
3061 0           dFUNCTION(GEN);
3062              
3063 0 0         if (!FUNCTION) {
3064 0           croak("XSUB call through interface did not provide *function");
3065             }
3066              
3067 0           RETVAL=FUNCTION(arg1,numvar(arg2), precdl);
3068             }
3069             OUTPUT:
3070             RETVAL
3071              
3072             GEN
3073             interface13(arg1, arg2=0, arg3=0)
3074             long oldavma=avma;
3075             GEN arg1
3076             long arg2
3077             GEN arg3
3078             CODE:
3079             { /* Code="GD0,L,DG" */ /* Was: Code="GD0,L,D0,G," */
3080 6           dFUNCTION(GEN);
3081              
3082 6 50         if (!FUNCTION) {
3083 0           croak("XSUB call through interface did not provide *function");
3084             }
3085              
3086 6           RETVAL=FUNCTION(arg1, arg2, arg3);
3087             }
3088             OUTPUT:
3089             RETVAL
3090              
3091             GEN
3092             interface14(arg1,arg2=0)
3093             long oldavma=avma;
3094             GEN arg1
3095             GEN arg2
3096             CODE:
3097             { /* Code="GDn" */
3098 47           dFUNCTION(GEN);
3099              
3100 47 50         if (!FUNCTION) {
3101 0           croak("XSUB call through interface did not provide *function");
3102             }
3103              
3104 47 100         RETVAL=FUNCTION(arg1,arg2 ? numvar(arg2) : -1);
3105             }
3106             OUTPUT:
3107             RETVAL
3108              
3109             GEN
3110             interface21(arg1,arg2)
3111             long oldavma=avma;
3112             GEN arg1
3113             long arg2
3114             CODE:
3115             { /* Code="GL" */
3116 0           dFUNCTION(GEN);
3117              
3118 0 0         if (!FUNCTION) {
3119 0           croak("XSUB call through interface did not provide *function");
3120             }
3121              
3122 0           RETVAL=FUNCTION(arg1,arg2);
3123             }
3124             OUTPUT:
3125             RETVAL
3126              
3127             # With fake arguments for overloading
3128             # This is very hairy: we need to chose the translation of arguments
3129             # depending on the value of inv
3130              
3131             GEN
3132             interface2199(arg1,arg2,inv)
3133             long oldavma=avma;
3134             GEN arg1 = NO_INIT
3135             long arg2 = NO_INIT
3136             bool inv
3137             CODE:
3138             {
3139 3           dFUNCTION(GEN);
3140              
3141 3 50         if (!FUNCTION) {
3142 0           croak("XSUB call through interface did not provide *function");
3143             }
3144 3 100         if (inv) {
3145 1           arg1 = sv2pari(ST(1));
3146 1 50         arg2 = (long)SvIV(ST(0));
3147             } else {
3148 2           arg1 = sv2pari(ST(0));
3149 2 50         arg2 = (long)SvIV(ST(1));
3150             }
3151              
3152 3           RETVAL = FUNCTION(arg1,arg2);
3153             }
3154             OUTPUT:
3155             RETVAL
3156              
3157             GEN
3158             interface22(arg1,arg2,arg3)
3159             long oldavma=avma;
3160             GEN arg1
3161             PariVar arg2
3162             PariExpr arg3
3163             CODE:
3164             { /* Code="GVI" */
3165 1           dFUNCTION(GEN);
3166              
3167 1 50         if (!FUNCTION) {
3168 0           croak("XSUB call through interface did not provide *function");
3169             }
3170             #if PARI_VERSION_EXP >= 2004002
3171 1           RETVAL = FUNCTION(arg1, arg3); /* XXXX Omit `V' instead of merging it into I/E */
3172             #else
3173             RETVAL = FUNCTION(arg1, arg2, arg3);
3174             #endif
3175             }
3176             OUTPUT:
3177             RETVAL
3178              
3179             GEN
3180             interface23(arg1,arg2)
3181             long oldavma=avma;
3182             GEN arg1
3183             long arg2
3184             CODE:
3185             { /* Code="GL" */
3186 9           dFUNCTION(GEN);
3187              
3188 9 50         if (!FUNCTION) {
3189 0           croak("XSUB call through interface did not provide *function");
3190             }
3191              
3192 9           RETVAL=FUNCTION(arg1,arg2);
3193             }
3194             OUTPUT:
3195             RETVAL
3196              
3197             GEN
3198             interface24(arg1,arg2)
3199             long oldavma=avma;
3200             long arg1
3201             GEN arg2
3202             CODE:
3203             { /* Code="LG" */
3204 3           dFUNCTION(GEN);
3205              
3206 3 50         if (!FUNCTION) {
3207 0           croak("XSUB call through interface did not provide *function");
3208             }
3209              
3210 3           RETVAL=FUNCTION(arg1,arg2);
3211             }
3212             OUTPUT:
3213             RETVAL
3214              
3215             GEN
3216             interface25(arg1,arg2,arg3=0)
3217             long oldavma=avma;
3218             GEN arg1
3219             GEN arg2
3220             long arg3
3221             CODE:
3222             { /* Code="GGD0,L," */
3223 16           dFUNCTION(GEN);
3224              
3225 16 50         if (!FUNCTION) {
3226 0           croak("XSUB call through interface did not provide *function");
3227             }
3228              
3229 16           RETVAL=FUNCTION(arg1,arg2,arg3);
3230             }
3231             OUTPUT:
3232             RETVAL
3233              
3234             GEN
3235             interface26(arg1,arg2,arg3)
3236             long oldavma=avma;
3237             GEN arg1
3238             GEN arg2
3239             GEN arg3
3240             CODE:
3241             { /* Code="GnG" */
3242 2           dFUNCTION(GEN);
3243              
3244 2 50         if (!FUNCTION) {
3245 0           croak("XSUB call through interface did not provide *function");
3246             }
3247              
3248 2           RETVAL=FUNCTION(arg1, numvar(arg2), arg3);
3249             }
3250             OUTPUT:
3251             RETVAL
3252              
3253             GEN
3254             interface27(arg1,arg2,arg3)
3255             long oldavma=avma;
3256             PariVar arg1
3257             GEN arg2
3258             PariExpr arg3
3259             CODE:
3260             { /* Code="V=GIp" */
3261 0           dFUNCTION(GEN);
3262              
3263 0 0         if (!FUNCTION) {
3264 0           croak("XSUB call through interface did not provide *function");
3265             }
3266             #if PARI_VERSION_EXP >= 2004002
3267 0           RETVAL=FUNCTION(arg2, arg3, prec_words); /* XXXX Omit `V' instead of merging it into I/E */
3268             #else
3269             RETVAL=FUNCTION(arg1, arg2, arg3, prec_words);
3270             #endif
3271             }
3272             OUTPUT:
3273             RETVAL
3274              
3275             GEN
3276             interface28(arg1,arg2=0,arg3=0)
3277             long oldavma=avma;
3278             GEN arg1
3279             PariVar arg2
3280             PariExpr arg3
3281             CODE:
3282             { /* Code="GDVDI" */
3283 25           dFUNCTION(GEN);
3284              
3285 25 50         if (!FUNCTION) {
3286 0           croak("XSUB call through interface did not provide *function");
3287             }
3288             #if PARI_VERSION_EXP >= 2004002
3289 25           RETVAL = FUNCTION(arg1, arg3); /* XXXX Omit `V' instead of merging it into I/E */
3290             #else
3291             RETVAL = FUNCTION(arg1, arg2, arg3);
3292             #endif
3293             }
3294             OUTPUT:
3295             RETVAL
3296              
3297             GEN
3298             interface28_old(arg1,arg2)
3299             long oldavma=avma;
3300             GEN arg1
3301             GEN arg2
3302             CODE:
3303             {
3304             long junk;
3305 0           dFUNCTION(GEN);
3306              
3307 0 0         if (!FUNCTION) {
3308 0           croak("XSUB call through interface did not provide *function");
3309             }
3310              
3311 0           RETVAL=FUNCTION(arg1, arg2, &junk);
3312             }
3313             OUTPUT:
3314             RETVAL
3315              
3316             long
3317             interface29_old(arg1,arg2)
3318             long oldavma=avma;
3319             GEN arg1
3320             long arg2
3321             CODE:
3322             {
3323 0           dFUNCTION(long);
3324              
3325 0 0         if (!FUNCTION) {
3326 0           croak("XSUB call through interface did not provide *function");
3327             }
3328              
3329 0           RETVAL=FUNCTION(arg1,arg2);
3330             }
3331             OUTPUT:
3332             RETVAL
3333             CLEANUP:
3334 0           avma=oldavma;
3335              
3336             GEN
3337             interface31(arg1,arg2=0,arg3=0,arg4=0)
3338             long oldavma=avma;
3339             GEN arg1
3340             GEN arg2
3341             GEN arg3
3342             GEN arg4
3343             CODE:
3344             { /* Code="GDGDGD&" */
3345 1           dFUNCTION(GEN);
3346              
3347 1 50         if (!FUNCTION) {
3348 0           croak("XSUB call through interface did not provide *function");
3349             }
3350              
3351 1 50         RETVAL=FUNCTION(arg1, arg2, arg3, arg4 ? &arg4 : NULL);
3352             }
3353             OUTPUT:
3354             RETVAL
3355              
3356             GEN
3357             interface32(arg1,arg2,arg3)
3358             long oldavma=avma;
3359             GEN arg1
3360             GEN arg2
3361             long arg3
3362             CODE:
3363             { /* Code="GGL" */
3364 2           dFUNCTION(GEN);
3365              
3366 2 50         if (!FUNCTION) {
3367 0           croak("XSUB call through interface did not provide *function");
3368             }
3369              
3370 2           RETVAL=FUNCTION(arg1,arg2,arg3);
3371             }
3372             OUTPUT:
3373             RETVAL
3374              
3375             GEN
3376             interface33(arg1,arg2,arg3,arg4=0)
3377             long oldavma=avma;
3378             GEN arg1
3379             GEN arg2
3380             GEN arg3
3381             long arg4
3382             CODE:
3383             { /* Code="GGGD0,L,p" */
3384 0           dFUNCTION(GEN);
3385              
3386 0 0         if (!FUNCTION) {
3387 0           croak("XSUB call through interface did not provide *function");
3388             }
3389              
3390 0           RETVAL=FUNCTION(arg1,arg2,arg3,arg4,prec_words);
3391             }
3392             OUTPUT:
3393             RETVAL
3394              
3395             void
3396             interface34(arg1,arg2,arg3)
3397             long arg1
3398             long arg2
3399             long arg3
3400             CODE:
3401             { /* Code="vLLL" */
3402 0           dFUNCTION(GEN);
3403              
3404 0 0         if (!FUNCTION) {
3405 0           croak("XSUB call through interface did not provide *function");
3406             }
3407              
3408 0           FUNCTION(arg1, arg2, arg3);
3409             }
3410              
3411             void
3412             interface35(arg1,arg2,arg3)
3413             long oldavma=avma;
3414             long arg1
3415             GEN arg2
3416             GEN arg3
3417             CODE:
3418             { /* Code="vLGG" */
3419 22           dFUNCTION(GEN);
3420              
3421 22 50         if (!FUNCTION) {
3422 0           croak("XSUB call through interface did not provide *function");
3423             }
3424              
3425 22           FUNCTION(arg1,arg2,arg3);
3426             }
3427             CLEANUP:
3428 22           avma=oldavma;
3429              
3430             GEN
3431             interface37(arg1,arg2,arg3,arg4)
3432             long oldavma=avma;
3433             PariVar arg1
3434             GEN arg2
3435             GEN arg3
3436             PariExpr arg4
3437             CODE:
3438             { /* Code="V=GGIp" */
3439 2           dFUNCTION(GEN);
3440              
3441 2 50         if (!FUNCTION) {
3442 0           croak("XSUB call through interface did not provide *function");
3443             }
3444             #if PARI_VERSION_EXP >= 2004002
3445 2           RETVAL=FUNCTION(arg2, arg3, arg4, prec_words); /* XXXX Omit `V' instead of merging it into I/E */
3446             #else
3447             RETVAL=FUNCTION(arg1, arg2, arg3, arg4, prec_words);
3448             #endif
3449             }
3450             OUTPUT:
3451             RETVAL
3452              
3453             GEN
3454             interface47(arg1,arg2,arg3,arg4,arg0=0)
3455             long oldavma=avma;
3456             GEN arg0
3457             PariVar arg1
3458             GEN arg2
3459             GEN arg3
3460             PariExpr arg4
3461             CODE:
3462             { /* Code="V=GGIDG" */
3463 137           dFUNCTION(GEN);
3464              
3465 137 50         if (!FUNCTION) {
3466 0           croak("XSUB call through interface did not provide *function");
3467             }
3468             #if PARI_VERSION_EXP >= 2004002
3469 137           RETVAL=FUNCTION(arg2, arg3, arg4, arg0); /* XXXX Omit `V' instead of merging it into I/E */
3470             #else
3471             RETVAL=FUNCTION(arg1, arg2, arg3, arg4, arg0);
3472             #endif
3473             }
3474             OUTPUT:
3475             RETVAL
3476              
3477             GEN
3478             interface48(arg1,arg2,arg3,arg4,arg0=0)
3479             long oldavma=avma;
3480             GEN arg0
3481             PariVar arg1
3482             GEN arg2
3483             GEN arg3
3484             PariExpr arg4
3485             CODE:
3486             { /* Code="V=GGIDG" */
3487 0           dFUNCTION(GEN);
3488              
3489 0 0         if (!FUNCTION) {
3490 0           croak("XSUB call through interface did not provide *function");
3491             }
3492             #if PARI_VERSION_EXP >= 2004002
3493 0           RETVAL=FUNCTION(arg2, arg3, arg4, arg0); /* XXXX Omit `V' instead of merging it into I/E */
3494             #else
3495             RETVAL=FUNCTION(arg1, arg2, arg3, arg4, arg0);
3496             #endif
3497             }
3498             OUTPUT:
3499             RETVAL
3500              
3501             GEN
3502             interface49(arg0,arg00,arg1=0,arg2=0,arg3=0)
3503             long oldavma=avma;
3504             GEN arg0
3505             GEN arg00
3506             PariVar arg1
3507             PariVar arg2
3508             PariExpr2 arg3
3509             CODE:
3510             { /* Code="GGDVDVDI" */
3511 0           dFUNCTION(GEN);
3512 0 0         # arg1 and arg2 may finish to be the same entree*, like after $x=$y=PARIvar 'x'
    0          
3513 0 0         if (arg1 == arg2 && arg1) {
3514 0           if (ST(2) == ST(3))
3515             croak("Same iterator for a double loop");
3516 0           # ST(3) is localized now
3517             #if PARI_VERSION_EXP >= 2004000
3518             croak("Panic (unreachable (?) in a double loop construct)");
3519             #else
3520             sv_unref(ST(3));
3521             arg2 = findVariable(ST(3),1);
3522             sv_setref_pv(ST(3), "Math::Pari::Ep", (void*)arg2);
3523 0 0         #endif
3524 0           }
3525             if (!FUNCTION) {
3526             croak("XSUB call through interface did not provide *function");
3527 0           }
3528             #if PARI_VERSION_EXP >= 2004002
3529             RETVAL=FUNCTION(arg0, arg00, arg3); /* XXXX Omit two `V's instead of merging them into I/E */
3530             #else
3531             RETVAL=FUNCTION(arg0, arg00, arg1, arg2, arg3);
3532             #endif
3533             }
3534             OUTPUT:
3535             RETVAL
3536              
3537             void
3538             interface83(arg1,arg2,arg3,arg4)
3539             long oldavma=avma;
3540             PariVar arg1
3541             GEN arg2
3542             GEN arg3
3543             PariExprV arg4
3544             CODE:
3545             { /* Code="vV=GGI" */
3546 1           dFUNCTION(void);
3547              
3548 1 50         if (!FUNCTION) {
3549 0           croak("XSUB call through interface did not provide *function");
3550             }
3551             #if PARI_VERSION_EXP >= 2004002
3552 1           FUNCTION(arg2, arg3, arg4); /* XXXX Omit `V' instead of merging it into I/E */
3553             #else
3554             FUNCTION(arg1, arg2, arg3, arg4);
3555             #endif
3556             }
3557             CLEANUP:
3558 1           avma=oldavma;
3559              
3560             void
3561             interface84(arg1,arg2,arg3)
3562             long oldavma=avma;
3563             GEN arg1
3564             PariVar arg2
3565             PariExprV arg3
3566             CODE:
3567             { /* Code="vGVI" */
3568 11           dFUNCTION(void);
3569              
3570 11 50         if (!FUNCTION) {
3571 0           croak("XSUB call through interface did not provide *function");
3572             }
3573             #if PARI_VERSION_EXP >= 2004002
3574 11           FUNCTION(arg1, arg3); /* XXXX Omit `V' instead of merging it into I/E */
3575             #else
3576             FUNCTION(arg1, arg2, arg3);
3577             #endif
3578             }
3579             CLEANUP:
3580 11           avma=oldavma;
3581              
3582             # These interfaces were automatically generated:
3583              
3584             long
3585             interface16(arg1)
3586             long oldavma=avma;
3587             char * arg1
3588             CODE:
3589             { /* Code="ls" */
3590 0           dFUNCTION(long);
3591              
3592 0 0         if (!FUNCTION) {
3593 0           croak("XSUB call through interface did not provide *function");
3594             }
3595              
3596 0           RETVAL=FUNCTION(arg1);
3597             }
3598             OUTPUT:
3599             RETVAL
3600             CLEANUP:
3601 0           avma=oldavma;
3602              
3603             void
3604             interface19(arg1, arg2)
3605             long arg1
3606             long arg2
3607             CODE:
3608             { /* Code="vLL" */
3609 0           dFUNCTION(GEN);
3610              
3611 0 0         if (!FUNCTION) {
3612 0           croak("XSUB call through interface did not provide *function");
3613             }
3614              
3615 0           FUNCTION(arg1, arg2);
3616             }
3617              
3618             GEN
3619             interface44(arg1, arg2, arg3, arg4)
3620             long oldavma=avma;
3621             long arg1
3622             long arg2
3623             long arg3
3624             long arg4
3625             CODE:
3626             {
3627 0           dFUNCTION(GEN);
3628              
3629 0 0         if (!FUNCTION) {
3630 0           croak("XSUB call through interface did not provide *function");
3631             }
3632              
3633 0           RETVAL=FUNCTION(arg1, arg2, arg3, arg4);
3634             }
3635             OUTPUT:
3636             RETVAL
3637              
3638             GEN
3639             interface45(arg1, arg2, arg3=0)
3640             long oldavma=avma;
3641             long arg1
3642             GEN arg2
3643             long arg3
3644             CODE:
3645             { /* Code="LGD0,L," */
3646 0           dFUNCTION(GEN);
3647              
3648 0 0         if (!FUNCTION) {
3649 0           croak("XSUB call through interface did not provide *function");
3650             }
3651              
3652 0           RETVAL=FUNCTION(arg1, arg2, arg3);
3653             }
3654             OUTPUT:
3655             RETVAL
3656              
3657             void
3658             interface59(arg1, arg2, arg3, arg4, arg5)
3659             long oldavma=avma;
3660             long arg1
3661             GEN arg2
3662             GEN arg3
3663             GEN arg4
3664             GEN arg5
3665             CODE:
3666             { /* Code="vLGGGG" */
3667 6           dFUNCTION(GEN);
3668              
3669 6 50         if (!FUNCTION) {
3670 0           croak("XSUB call through interface did not provide *function");
3671             }
3672              
3673 6           FUNCTION(arg1, arg2, arg3, arg4, arg5);
3674             }
3675             CLEANUP:
3676 6           avma=oldavma;
3677              
3678             GEN
3679             interface73(arg1, arg2, arg3, arg4, arg5, arg6=0, arg7=0)
3680             long oldavma=avma;
3681             long arg1
3682             PariVar arg2
3683             GEN arg3
3684             GEN arg4
3685             PariExprV arg5
3686             long arg6
3687             long arg7
3688             CODE:
3689             { /* Code="LV=GGIpD0,L,D0,L," */
3690 0           dFUNCTION(GEN);
3691              
3692 0 0         if (!FUNCTION) {
3693 0           croak("XSUB call through interface did not provide *function");
3694             }
3695             #if PARI_VERSION_EXP >= 2004002
3696 0           RETVAL=FUNCTION(arg1, arg3, arg4, arg5, prec_words, arg6, arg7); /* XXXX Omit `V' instead of merging it into I/E */
3697             #else
3698             RETVAL=FUNCTION(arg1, arg2, arg3, arg4, arg5, prec_words, arg6, arg7);
3699             #endif
3700             }
3701             OUTPUT:
3702             RETVAL
3703              
3704             void
3705             interface86(arg1, arg2, arg3, arg4, arg5)
3706             long oldavma=avma;
3707             PariVar arg1
3708             GEN arg2
3709             GEN arg3
3710             GEN arg4
3711             PariExprV arg5
3712             CODE:
3713             { /* Code="vV=GGGI" */
3714 1           dFUNCTION(GEN);
3715              
3716 1 50         if (!FUNCTION) {
3717 0           croak("XSUB call through interface did not provide *function");
3718             }
3719             #if PARI_VERSION_EXP >= 2004002
3720 1           FUNCTION(arg2, arg3, arg4, arg5); /* XXXX Omit `V' instead of merging it into I/E */
3721             #else
3722             FUNCTION(arg1, arg2, arg3, arg4, arg5);
3723             #endif
3724             }
3725             CLEANUP:
3726 1           avma=oldavma;
3727              
3728             void
3729             interface87(arg1, arg2, arg3, arg4=0)
3730             long oldavma=avma;
3731             PariVar arg1
3732             GEN arg2
3733             PariExprV arg3
3734             long arg4
3735             CODE:
3736             { /* Code="vV=GID0,L," */
3737 1           dFUNCTION(GEN);
3738              
3739 1 50         if (!FUNCTION) {
3740 0           croak("XSUB call through interface did not provide *function");
3741             }
3742             #if PARI_VERSION_EXP >= 2004002
3743 1           FUNCTION(arg2, arg3, arg4); /* XXXX Omit `V' instead of merging it into I/E */
3744             #else
3745             FUNCTION(arg1, arg2, arg3, arg4);
3746             #endif
3747             }
3748             CLEANUP:
3749 1           avma=oldavma;
3750              
3751             bool
3752             _2bool(arg1,arg2,inv)
3753             long oldavma=avma;
3754             GEN arg1
3755             GEN arg2 = NO_INIT
3756             long inv = NO_INIT
3757             CODE:
3758             PERL_UNUSED_VAR(arg2); /* -W */
3759             PERL_UNUSED_VAR(inv); /* -W */
3760 18           RETVAL=!gcmp0(arg1);
3761             OUTPUT:
3762             RETVAL
3763             CLEANUP:
3764 18           avma=oldavma;
3765              
3766             bool
3767             pari2bool(arg1)
3768             long oldavma=avma;
3769             GEN arg1
3770             CODE:
3771 0           RETVAL=!gcmp0(arg1);
3772             OUTPUT:
3773             RETVAL
3774             CLEANUP:
3775 0           avma=oldavma;
3776              
3777             CV *
3778             loadPari(name, v = 99)
3779             char * name
3780             int v
3781             CODE:
3782             {
3783 255977           char *olds = name;
3784 255977           entree *ep=NULL;
3785 255977           long hash, valence = -1; /* Avoid uninit warning */
3786 255977           void (*func)(void*)=NULL;
3787 255977           void (*unsupported)(void*) = (void (*)(void*)) not_here;
3788              
3789 255977 100         if (*name=='g') {
3790 8337           switch (name[1]) {
3791             case 'a':
3792 5237 100         if (strEQ(name,"gadd")) {
3793 1           valence=2;
3794 1           func=(void (*)(void*)) gadd;
3795 5236 50         } else if (strEQ(name,"gand")) {
3796 0           valence=2;
3797 0           func=(void (*)(void*)) gand;
3798             }
3799 5237           break;
3800             case 'c':
3801 476 50         if (strEQ(name,"gcmp0")) {
3802 0           valence=10;
3803 0           func=(void (*)(void*)) gcmp0;
3804 476 50         } else if (strEQ(name,"gcmp1")) {
3805 0           valence=10;
3806 0           func=(void (*)(void*)) gcmp1;
3807 476 50         } else if (strEQ(name,"gcmp_1")) {
3808 0           valence=10;
3809 0           func=(void (*)(void*)) gcmp_1;
3810 476 50         } else if (strEQ(name,"gcmp")) {
3811 0           valence=20;
3812 0           func=(void (*)(void*)) gcmp;
3813             }
3814 476           break;
3815             case 'd':
3816 2 50         if (strEQ(name,"gdiv")) {
3817 0           valence=2;
3818 0           func=(void (*)(void*)) gdiv;
3819 2 100         } else if (strEQ(name,"gdivent")) {
3820 1           valence=2;
3821 1           func=(void (*)(void*)) gdivent;
3822 1 50         } else if (strEQ(name,"gdivround")) {
3823 1           valence=2;
3824 1           func=(void (*)(void*)) gdivround;
3825             }
3826 2           break;
3827             case 'e':
3828 2619 100         if (strEQ(name,"geq")) {
3829 1           valence=2;
3830 1           func=(void (*)(void*)) geq;
3831 2618 50         } else if (strEQ(name,"gegal") || strEQ(name,"gequal")) { /* old name */
    50          
3832 0           valence=20;
3833 0           func=(void (*)(void*)) gequal;
3834             }
3835 2619           break;
3836             case 'g':
3837 0 0         if (strEQ(name,"gge")) {
3838 0           valence=2;
3839 0           func=(void (*)(void*)) gge;
3840 0 0         } else if (strEQ(name,"ggt")) {
3841 0           valence=2;
3842 0           func=(void (*)(void*)) ggt;
3843             }
3844 0           break;
3845             case 'l':
3846 0 0         if (strEQ(name,"gle")) {
3847 0           valence=2;
3848 0           func=(void (*)(void*)) gle;
3849 0 0         } else if (strEQ(name,"glt")) {
3850 0           valence=2;
3851 0           func=(void (*)(void*)) glt;
3852             }
3853 0           break;
3854             case 'm':
3855 0 0         if (strEQ(name,"gmul")) {
3856 0           valence=2;
3857 0           func=(void (*)(void*)) gmul;
3858 0 0         } else if (strEQ(name,"gmod")) {
3859 0           valence=2;
3860 0           func=(void (*)(void*)) gmod;
3861             }
3862 0           break;
3863             case 'n':
3864 1 50         if (strEQ(name,"gneg")) {
3865 0           valence=1;
3866 0           func=(void (*)(void*)) gneg;
3867 1 50         } else if (strEQ(name,"gne")) {
3868 1           valence=2;
3869 1           func=(void (*)(void*)) gne;
3870             }
3871 1           break;
3872             case 'o':
3873 0 0         if (strEQ(name,"gor")) {
3874 0           valence=2;
3875 0           func=(void (*)(void*)) gor;
3876             }
3877 0           break;
3878             case 'p':
3879 1 50         if (strEQ(name,"gpui") || strEQ(name,"gpow")) {
    0          
3880 1           valence=2;
3881 1           func=(void (*)(void*)) my_gpui;
3882             }
3883 1           break;
3884             case 's':
3885 1 50         if (strEQ(name,"gsub")) {
3886 1           valence=2;
3887 1           func=(void (*)(void*)) gsub;
3888             }
3889 8337           break;
3890             }
3891 247640 100         } else if (*name=='_') {
3892 105 100         if (name[1] == 'g') {
3893 102           switch (name[2]) {
3894             case 'a':
3895 16 50         if (strEQ(name,"_gadd")) {
3896 16           valence=299;
3897 16           func=(void (*)(void*)) gadd;
3898 0 0         } else if (strEQ(name,"_gand")) {
3899 0           valence=2099;
3900 0           func=(void (*)(void*)) gand;
3901             }
3902 16           break;
3903             #if PARI_VERSION_EXP >= 2000018
3904             case 'b':
3905 6 100         if (strEQ(name,"_gbitand")) {
3906 1           valence=299;
3907 1           func=(void (*)(void*)) gbitand;
3908 5 100         } else if (strEQ(name,"_gbitor")) {
3909 1           valence=299;
3910 1           func=(void (*)(void*)) gbitor;
3911 4 100         } else if (strEQ(name,"_gbitxor")) {
3912 1           valence=299;
3913 1           func=(void (*)(void*)) gbitxor;
3914 3 100         } else if (strEQ(name,"_gbitneg")) {
3915 1           valence=199;
3916 1           func=(void (*)(void*)) _gbitneg;
3917             #if PARI_VERSION_EXP >= 2002001
3918 2 50         } else if (strEQ(name,"_gbitshiftl")) {
3919 2           valence=2199;
3920 2           func=(void (*)(void*)) _gbitshiftl;
3921             #endif
3922             #if PARI_VERSION_EXP >= 2002001 && PARI_VERSION_EXP <= 2002007
3923             } else if (strEQ(name,"_gbitshiftr")) {
3924             valence=2199;
3925             func=(void (*)(void*)) _gbitshiftr;
3926             #endif
3927             }
3928 6           break;
3929             #endif
3930             case 'c':
3931 0 0         if (strEQ(name,"_gcmp")) {
3932 0           valence=209;
3933 0           func=(void (*)(void*)) gcmp;
3934 0 0         } else if (strEQ(name,"_gcmp0")) {
3935 0           valence=109;
3936 0           func=(void (*)(void*)) gcmp0;
3937             }
3938 0           break;
3939             case 'd':
3940 15 50         if (strEQ(name,"_gdiv")) {
3941 15           valence=299;
3942 15           func=(void (*)(void*)) gdiv;
3943             }
3944 15           break;
3945             case 'e':
3946 2 50         if (strEQ(name,"_geq")) {
3947 2           valence=2099;
3948 2           func=(void (*)(void*)) geq;
3949             }
3950 2           break;
3951             case 'g':
3952 1 50         if (strEQ(name,"_gge")) {
3953 1           valence=2099;
3954 1           func=(void (*)(void*)) gge;
3955 0 0         } else if (strEQ(name,"_ggt")) {
3956 0           valence=2099;
3957 0           func=(void (*)(void*)) ggt;
3958             }
3959 1           break;
3960             case 'l':
3961 4 100         if (strEQ(name,"_gle")) {
3962 1           valence=2099;
3963 1           func=(void (*)(void*)) gle;
3964 3 50         } else if (strEQ(name,"_glt")) {
3965 3           valence=2099;
3966 3           func=(void (*)(void*)) glt;
3967             }
3968 4           break;
3969             case 'm':
3970 19 100         if (strEQ(name,"_gmul")) {
3971 17           valence=299;
3972 17           func=(void (*)(void*)) gmul;
3973 2 50         } else if (strEQ(name,"_gmod")) {
3974 2           valence=299;
3975 2           func=(void (*)(void*)) gmod;
3976             }
3977 19           break;
3978             case 'n':
3979 10 100         if (strEQ(name,"_gneg")) {
3980 9           valence=199;
3981 9           func=(void (*)(void*)) gneg;
3982 1 50         } else if (strEQ(name,"_gne")) {
3983 1           valence=2099;
3984 1           func=(void (*)(void*)) gne;
3985             }
3986 10           break;
3987             case 'o':
3988 0 0         if (strEQ(name,"_gor")) {
3989 0           valence=2099;
3990 0           func=(void (*)(void*)) gor;
3991             }
3992 0           break;
3993             case 'p':
3994 15 50         if (strEQ(name,"_gpui")) {
3995 15           valence=299;
3996 15           func=(void (*)(void*)) my_gpui;
3997             }
3998 15           break;
3999             case 's':
4000 14 50         if (strEQ(name,"_gsub")) {
4001 14           valence=299;
4002 14           func=(void (*)(void*)) gsub;
4003             }
4004 102           break;
4005             }
4006             } else {
4007 3           switch (name[1]) {
4008             case 'a':
4009 1 50         if (strEQ(name,"_abs")) {
4010 1           valence=199;
4011 1           func=(void (*)(void*)) gabs;
4012             }
4013 1           break;
4014             case 'c':
4015 0 0         if (strEQ(name,"_cos")) {
4016 0           valence=199;
4017 0           func=(void (*)(void*)) gcos;
4018             }
4019 0           break;
4020             case 'e':
4021 1 50         if (strEQ(name,"_exp")) {
4022 1           valence=199;
4023 1           func=(void (*)(void*)) gexp;
4024             }
4025 1           break;
4026             case 'l':
4027 1 50         if (strEQ(name,"_lex")) {
4028 1           valence=2091;
4029 1           func=(void (*)(void*)) lexcmp;
4030 0 0         } else if (strEQ(name,"_log")) {
4031 0           valence=199;
4032 0           func=(void (*)(void*)) glog;
4033             }
4034 1           break;
4035             case 's':
4036 0 0         if (strEQ(name,"_sin")) {
4037 0           valence=199;
4038 0           func=(void (*)(void*)) gsin;
4039 0 0         } else if (strEQ(name,"_sqrt")) {
4040 0           valence=199;
4041 0           func=(void (*)(void*)) gsqrt;
4042             }
4043 0           break;
4044             }
4045             }
4046             }
4047 255977 100         if (!func) {
4048 255865           SAVEINT(doing_PARI_autoload);
4049 255865           doing_PARI_autoload = 1;
4050             checkPariFunction(name);
4051             #ifdef MAY_USE_FETCH_ENTRY
4052 255865           ep = is_entry(name);
4053             #else
4054             ep = is_entry_intern(name, functions_hash, &hash);
4055             #endif
4056 255865           doing_PARI_autoload = 0;
4057 255865 100         if (!ep)
4058 2           croak("`%s' is not a Pari function name",name);
4059              
4060 255863 50         if (ep && isPariFunction(ep)) {
    50          
4061             /* Builtin */
4062 255863           IV table_valence = 99;
4063              
4064 255863 50         if (ep->code /* This is in func_codes.h: */
    100          
4065 253720 100         && (*(ep->code) ? (PERL_constant_ISIV == func_ord_by_type (aTHX_ ep->code,
4066             strlen(ep->code), &table_valence)) /* Essentially, PERL_constant_ISIV means: recognized */
4067 2143           : (table_valence = 9900)))
4068 127578           valence = table_valence;
4069             else
4070 128285           valence = 99;
4071             #ifdef CHECK_VALENCE
4072             if (ep->code && valence != EpVALENCE(ep)
4073             && EpVALENCE(ep) != 99
4074             && !(valence == 23 && EpVALENCE(ep) == 21)
4075             && !(valence == 48 && EpVALENCE(ep) == 47)
4076             && !(valence == 96 && EpVALENCE(ep) == 91)
4077             && !(valence == 99 && EpVALENCE(ep) == 0)
4078             && !(valence == 9900 && EpVALENCE(ep) == 0))
4079             warn("funcname=`%s', code=`%s', val=%d, calc_val=%d\n",
4080             name, ep->code, (int)EpVALENCE(ep), (int)valence);
4081             #endif
4082 255863           func=(void (*)(void*)) ep->value;
4083 255863 50         if (!func) {
4084 255863           func = unsupported;
4085             }
4086             }
4087             }
4088 255975 50         if (func == unsupported) {
4089 0           croak("Do not know how to work with Pari control structure `%s'",
4090             olds);
4091 255975 50         } else if (func) {
4092 255975           char* file = __FILE__, *proto = NULL;
4093 255975           char subname[276]="Math::Pari::";
4094 255975           char buf[64], *pbuf = buf;
4095             const char *s, *s1;
4096             CV *protocv;
4097 255975           int flexible = 0;
4098            
4099 255975           sprintf(buf, "%ld", valence);
4100             /* warn("See valence = %d", valence); */
4101 255975           switch (valence) {
4102             case 0:
4103 715 50         if (!ep->code) {
4104 0           croak("Unsupported Pari function %s, interface 0 code NULL", olds);
4105 715 50         } else if (ep->code[0] == 'p' && ep->code[1] == 0) {
    50          
4106 715           DO_INTERFACE(0);
4107 0 0         } else if (ep->code[0] == 0) {
4108 0           DO_INTERFACE(9900);
4109             } else {
4110 0           goto flexible;
4111             }
4112 715           break;
4113 10710           CASE_INTERFACE(1);
4114 5950           CASE_INTERFACE(10);
4115 12           CASE_INTERFACE(199);
4116 0           CASE_INTERFACE(109);
4117 3094           CASE_INTERFACE(11);
4118 0           CASE_INTERFACE(15);
4119 30710           CASE_INTERFACE(2);
4120 2142           CASE_INTERFACE(20);
4121 82           CASE_INTERFACE(299);
4122 0           CASE_INTERFACE(209);
4123 8           CASE_INTERFACE(2099);
4124 1           CASE_INTERFACE(2091);
4125 2           CASE_INTERFACE(2199);
4126 12376           CASE_INTERFACE(3);
4127 238           CASE_INTERFACE(30);
4128 1428           CASE_INTERFACE(4);
4129 0           CASE_INTERFACE(5);
4130 0           CASE_INTERFACE(21);
4131 2856           CASE_INTERFACE(23);
4132 476           CASE_INTERFACE(24);
4133 8568           CASE_INTERFACE(25);
4134 5236           CASE_INTERFACE(29);
4135 1428           CASE_INTERFACE(32);
4136 0           CASE_INTERFACE(33);
4137 1190           CASE_INTERFACE(35);
4138 0           CASE_INTERFACE(12);
4139 238           CASE_INTERFACE(13);
4140 3811           CASE_INTERFACE(14);
4141 238           CASE_INTERFACE(26);
4142 714           CASE_INTERFACE(28);
4143 238           CASE_INTERFACE(31);
4144 0           CASE_INTERFACE(34);
4145 476           CASE_INTERFACE(22);
4146 0           CASE_INTERFACE(27);
4147 476           CASE_INTERFACE(37);
4148 715           CASE_INTERFACE(47);
4149 0           CASE_INTERFACE(48);
4150 0           CASE_INTERFACE(49);
4151 714           CASE_INTERFACE(83);
4152 1191           CASE_INTERFACE(84);
4153 26420           CASE_INTERFACE(18);
4154             /* These interfaces were automatically generated: */
4155 238           CASE_INTERFACE(16);
4156 476           CASE_INTERFACE(19);
4157 0           CASE_INTERFACE(44);
4158 238           CASE_INTERFACE(45);
4159 238           CASE_INTERFACE(59);
4160 0           CASE_INTERFACE(73);
4161 238           CASE_INTERFACE(86);
4162 238           CASE_INTERFACE(87);
4163 2143           CASE_INTERFACE(9900);
4164              
4165             default:
4166 129713 50         if (!ep)
4167 0           croak("Unsupported interface %ld for \"direct-link\" Pari function %s",
4168             valence, olds);
4169 129713 50         if (!ep->code)
4170 0           croak("Unsupported interface %ld and no code for a Pari function %s",
4171             valence, olds);
4172             flexible:
4173 129713           s1 = s = ep->code;
4174 129713 50         if (*s1 == 'x')
4175 0           s1++;
4176 129713 100         if (*s1 == 'v') {
4177 13328           pbuf = "_flexible_void";
4178 13328           DO_INTERFACE(_flexible_void);
4179             }
4180 116385 100         else if (*s1 == 'l') {
4181 7378           pbuf = "_flexible_long";
4182 7378           DO_INTERFACE(_flexible_long);
4183             }
4184 109007 100         else if (*s1 == 'i') {
4185 4046           pbuf = "_flexible_int";
4186 4046           DO_INTERFACE(_flexible_int);
4187             }
4188             else {
4189 104961           pbuf = "_flexible_gen";
4190 104961           DO_INTERFACE(_flexible_gen);
4191             }
4192            
4193 129713           flexible = 1;
4194             }
4195 255975           strcpy(subname+12,"interface");
4196 255975           strcpy(subname+12+9,pbuf);
4197 255975           protocv = perl_get_cv(subname, FALSE);
4198 255975 50         if (protocv) {
4199 255975 50         proto = SvPV((SV*)protocv,na);
4200             }
4201            
4202 255975           strcpy(subname+12,olds);
4203 255975           RETVAL = newXS(subname,math_pari_subaddr,file);
4204 255975 50         if (proto)
4205 255975           sv_setpv((SV*)RETVAL, proto);
4206 255975 100         XSINTERFACE_FUNC_SET(RETVAL, flexible ? (void*)ep : (void*)func);
4207             } else {
4208 0 0         croak( "Cannot load a Pari macro `%s': macros are unsupported; VALENCE=%#04x, code=<%s>, isFunction=%d, EpVAR=%d",
    0          
4209 0           olds, (ep ? (int)EpVALENCE(ep) : 0x666), (ep->code ? ep->code : ""), isPariFunction(ep), (int)EpVAR);
4210             }
4211             }
4212             OUTPUT:
4213             RETVAL
4214              
4215             # Tag is menu entry, or -1 for all.
4216              
4217             void
4218             _listPari(tag)
4219             int tag
4220             PPCODE:
4221             {
4222             long valence;
4223 255           entree *ep, *table = functions_basic;
4224 255           int i=-1;
4225              
4226 510 50         while (++i <= 1) {
4227 510 100         if (i==1)
4228             #if defined(NO_HIGHLEVEL_PARI) || PARI_VERSION_EXP >= 2009000 /* Probably disappered earlier */
4229 255           break;
4230             #else
4231             table = functions_highlevel;
4232             #endif
4233            
4234 314415 100         for(ep = table; ep->name; ep++) {
4235 314160           valence = EpVALENCE(ep);
4236 314160 100         if ((tag == -1 && !_is_internal(ep->menu)) || ep->menu == tag) {
    100          
    100          
4237 259793 50         switch (valence) {
4238             default:
4239             case 0:
4240 259793 100         if (ep->code == 0)
4241 1673           break;
4242             /* FALL THROUGH */
4243             case 1:
4244             case 10:
4245             case 199:
4246             case 109:
4247             case 11:
4248             case 15:
4249             case 2:
4250             case 20:
4251             case 299:
4252             case 209:
4253             case 2099:
4254             case 2199:
4255             case 3:
4256             case 30:
4257             case 4:
4258             case 5:
4259             case 21:
4260             case 23:
4261             case 24:
4262             case 25:
4263             case 29:
4264             case 32:
4265             case 33:
4266             case 35:
4267             case 12:
4268             case 13:
4269             case 14:
4270             case 26:
4271             case 28:
4272             case 31:
4273             case 34:
4274             case 22:
4275             case 27:
4276             case 37:
4277             case 47:
4278             case 48:
4279             case 49:
4280             case 83:
4281             case 84:
4282             case 18:
4283             /* These interfaces were automatically generated: */
4284             case 16:
4285             case 19:
4286             case 44:
4287             case 45:
4288             case 59:
4289             case 73:
4290             case 86:
4291             case 87:
4292 258120 100         XPUSHs(sv_2mortal(newSVpv(ep->name, 0)));
4293             }
4294             }
4295             }
4296             }
4297             }
4298              
4299             BOOT:
4300             {
4301             static int reboot;
4302 244           SV *mem = perl_get_sv("Math::Pari::initmem", FALSE);
4303 244           SV *pri = perl_get_sv("Math::Pari::initprimes", FALSE);
4304             pari_sp av;
4305 244 50         if (!mem || !SvOK(mem)) {
    50          
    0          
    0          
4306 0           croak("$Math::Pari::initmem not defined!");
4307             }
4308 244 50         if (!pri || !SvOK(pri)) {
    50          
    0          
    0          
4309 0           croak("$Math::Pari::initprimes not defined!");
4310             }
4311 244 50         if (reboot) {
4312 0           detach_stack();
4313             #if PARI_VERSION_EXP >= 2002012 /* Present at least in 2.3.5; assume correct due to http://pari.math.u-bordeaux.fr/archives/pari-dev-0511/msg00037.html */
4314 0           pari_close_opts(INIT_DFTm);
4315             #else /* PARI_VERSION_EXP < 2002012 */
4316             if (reset_on_reload)
4317             freeall();
4318             else
4319             allocatemoremem(1008);
4320             #endif
4321             }
4322             #if PARI_VERSION_EXP >= 2002012
4323             /* pari_init_defaults(); */ /* Not needed with INIT_DFTm */
4324             #else
4325             INIT_JMP_off;
4326             INIT_SIG_off;
4327             /* These guys are new in 2.0. */
4328             init_defaults(1);
4329             #endif
4330             /* Different order of init required */
4331             #if PARI_VERSION_EXP < 2003000
4332             if (!(reboot++)) {
4333             # ifndef NO_HIGHLEVEL_PARI
4334             # if PARI_VERSION_EXP >= 2002012
4335             pari_add_module(functions_highlevel);
4336             # else /* !( PARI_VERSION_EXP >= 2002012 ) */
4337             pari_addfunctions(&pari_modules,
4338             functions_highlevel, helpmessages_highlevel);
4339             # endif /* !( PARI_VERSION_EXP >= 2002012 ) */
4340             init_graph();
4341             # endif
4342             }
4343             #endif /* PARI_VERSION_EXP < 2003000 */
4344 244 50         primelimit = SvIV(pri);
4345 244 50         parisize = SvIV(mem);
4346             #if PARI_VERSION_EXP >= 2002012
4347 244           pari_init_opts(parisize, primelimit, INIT_DFTm);
4348             /* Default: take four million bytes of
4349             * memory for the stack, calculate
4350             * primes up to 500000. */
4351             #else
4352             init(parisize, primelimit); /* Default: take four million bytes of
4353             * memory for the stack, calculate
4354             * primes up to 500000. */
4355             #endif
4356             /* Different order of init required */
4357             #if PARI_VERSION_EXP >= 2003000
4358 244 50         if (!(reboot++)) {
4359             # ifndef NO_HIGHLEVEL_PARI
4360             # if PARI_VERSION_EXP >= 2002012
4361             # if PARI_VERSION_EXP < 2009000 /* Probably disappered earlier */
4362             pari_add_module(functions_highlevel);
4363             # endif /* PARI_VERSION_EXP < 2009000 */
4364             # else /* !( PARI_VERSION_EXP >= 2002012 ) */
4365             pari_addfunctions(&pari_modules,
4366             functions_highlevel, helpmessages_highlevel);
4367             # endif /* !( PARI_VERSION_EXP >= 2002012 ) */
4368             #if PARI_VERSION_EXP >= 2011000
4369 244           pari_set_plot_engine(gp_get_plot);
4370             #else
4371             init_graph();
4372             #endif
4373             # endif
4374             }
4375             #endif /* PARI_VERSION_EXP >= 2003000 */
4376 244           PariStack = (SV *) GENfirstOnStack;
4377 244 50         if (!worksv)
4378 244           worksv = NEWSV(910,0);
4379 244 50         if (workErrsv)
4380 0           sv_setpvn(workErrsv, "", 0); /* Just in case, on restart */
4381             else
4382 244           workErrsv = newSVpvn("",0);
4383 244           pariErr = &perlErr;
4384             #if PARI_VERSION_EXP >= 2003000
4385 244           pari_set_last_newline(1); /* Bug in PARI: at the start, we do not need extra newlines */
4386             #endif
4387             #if PARI_VERSION_EXP >= 2004000 /* Undocumented when it appeared; present in 2.5.0 */
4388 244           cb_pari_err_recover = _svErrdie; /* XXXX Not enough for our needs! */
4389 244           cb_pari_handle_exception = math_pari_handle_exception;
4390             # ifdef CB_EXCEPTION_FLAGS
4391 244           cb_exception_resets_avma = 1;
4392 244           cb_exception_flushes_err = 1;
4393             # endif
4394 244           av = avma;
4395             /* Init the rest ourselves */
4396             #if PARI_VERSION_EXP >= 2009000
4397 244 50         if (!GP_DATA->colormap) /* init_defaults() leaves them NULL */
4398 0           sd_graphcolormap("[\"white\",\"black\",\"gray\",\"violetred\",\"red\",\"green\",\"blue\",\"gainsboro\",\"purple\"]",0);
4399 244 50         if (!GP_DATA->graphcolors)
4400 0           sd_graphcolors("[4,5]",0);
4401 244           avma = av;
4402             #else /* !(PARI_VERSION_EXP >= 2009000) */
4403             if (!pari_colormap) /* init_defaults() leaves them NULL */
4404             pari_colormap = gclone(readseq("[\"white\",\"black\",\"gray\",\"violetred\",\"red\",\"green\",\"blue\",\"gainsboro\",\"purple\"]"));
4405             if (!pari_graphcolors)
4406             pari_graphcolors = gclone(readseq("[4,5]"));
4407             avma = av;
4408             #endif /* !(PARI_VERSION_EXP >= 2009000) */
4409             #endif
4410             #if PARI_VERSION_EXP < 2005000 /* Undocumented when it disappeared; missing in 2.5.0 */
4411             foreignHandler = (void*)&callPerlFunction;
4412             foreignExprSwitch = (char)SVt_PVCV;
4413             foreignExprHandler = &exprHandler_Perl;
4414             #endif
4415 244           foreignAutoload = &autoloadPerlFunction;
4416 244           foreignFuncFree = &freePerlFunction;
4417 244           pariStash = gv_stashpv("Math::Pari", TRUE);
4418 244           pariEpStash = gv_stashpv("Math::Pari::Ep", TRUE);
4419 244           perlavma = sentinel = avma;
4420             fmt_nbPset(def_fmt_nb);
4421 244           global_top = myPARI_top;
4422             #if PARI_VERSION_EXP >= 2004002 /* Undocumented when it appeared; present in 2.5.0 */
4423 244 50         if (! code_return_1) {
4424 244           code_return_1 = gclone(compile_str("x->1"));
4425 244           code2_return_1 = gclone(compile_str("(x,y)->1"));
4426 244           avma = sentinel;
4427             }
4428             #endif
4429             }
4430              
4431             void
4432             memUsage()
4433             PPCODE:
4434             #ifdef DEBUG_PARI
4435 18 50         EXTEND(sp, 4); /* Got cv + 0, - but on newer Perls, this does not count. Return 4. */
4436 18           PUSHs(sv_2mortal(newSViv(SVnumtotal)));
4437 18           PUSHs(sv_2mortal(newSViv(SVnum)));
4438 18           PUSHs(sv_2mortal(newSViv(onStack)));
4439 18           PUSHs(sv_2mortal(newSViv(offStack)));
4440             #endif
4441            
4442              
4443             void
4444             dumpStack()
4445             PPCODE:
4446 19           long i = 0, ssize, oursize = 0;
4447             SV *ret, *sv1, *nextsv;
4448 19           const char *pref = "";
4449              
4450 19 50         switch(GIMME_V) {
4451             case G_VOID:
4452 19           pref = "# ";
4453             case G_SCALAR:
4454 19           ssize = getstack();
4455 19           ret = newSVpvf("%sstack size is %ld bytes (%ld x %ld longs)\n",
4456             pref, ssize, (long)sizeof(long), ssize/sizeof(long));
4457 122 100         for (sv1 = PariStack; sv1 != (SV *) GENfirstOnStack; sv1 = nextsv) {
4458 103 100         GEN x = (GEN) SV_myvoidp_get(sv1);
    50          
4459 103           SV* tmp = pari_print(x);
4460 103 50         sv_catpvf(ret,"%s %2ld: %s\n", pref, i, SvPV_nolen(tmp));
4461 103           SvREFCNT_dec(tmp);
4462 103           i++;
4463 103           oursize += gsizeword(x);
4464 103 100         nextsv = SV_Stack_find_next(sv1);
4465             }
4466 19           sv_catpvf(ret,"%sour data takes %ld words out of %ld words on stack\n", pref, oursize, ssize/sizeof(long));
4467 19 50         if(GIMME_V == G_VOID) {
    50          
4468 19 50         PerlIO_puts(PerlIO_stdout(), SvPV_nolen(ret));
4469 19           SvREFCNT_dec(ret);
4470 19           XSRETURN(0);
4471             } else {
4472 0           ST(0) = sv_2mortal(ret);
4473 0           XSRETURN(1);
4474             }
4475             case G_ARRAY:
4476 0 0         for (sv1 = PariStack; sv1 != (SV *) GENfirstOnStack; sv1 = nextsv) {
4477 0 0         GEN x = (GEN) SV_myvoidp_get(sv1);
    0          
4478 0 0         XPUSHs(sv_2mortal(pari_print(x)));
4479 0 0         nextsv = SV_Stack_find_next(sv1);
4480             }
4481             }
4482              
4483             void
4484             __dumpStack()
4485             PPCODE:
4486 0           GEN x = (GEN)avma; /* If this works, it is accidental only: it assumes the entry point to “the region on stack” is at its smallest address. */
4487 0           long ssize, i = 0;
4488             SV* ret;
4489              
4490 0 0         switch(GIMME_V) {
4491             case G_VOID:
4492             case G_SCALAR:
4493 0           ssize = getstack();
4494 0           ret = newSVpvf("stack size is %ld bytes (%ld x %ld longs)\n",
4495             ssize,(long)sizeof(long),ssize/sizeof(long));
4496 0 0         for(; x < (GEN)myPARI_top; x += gsizeword(x), i++) {
4497 0           SV* tmp = pari_print(x);
4498 0 0         sv_catpvf(ret," %2ld: %s\n",i,SvPV_nolen(tmp));
4499 0           SvREFCNT_dec(tmp);
4500             }
4501 0 0         if(GIMME_V == G_VOID) {
    0          
4502 0 0         PerlIO_puts(PerlIO_stdout(), SvPV_nolen(ret));
4503 0           SvREFCNT_dec(ret);
4504 0           XSRETURN(0);
4505             } else {
4506 0           ST(0) = sv_2mortal(ret);
4507 0           XSRETURN(1);
4508             }
4509             case G_ARRAY:
4510 0 0         for(; x < (GEN)myPARI_top; x += gsizeword(x), i++)
4511 0 0         XPUSHs(sv_2mortal(pari_print(x)));
4512             }
4513              
4514             void
4515             dumpHeap()
4516             PPCODE:
4517             heap_dumper_t hd;
4518 0 0         int context = GIMME_V, m;
4519              
4520 0           SV* ret = Nullsv; /* Avoid unit warning */
4521              
4522 0           switch(context) {
4523             case G_VOID:
4524 0           case G_SCALAR: ret = newSVpvn("",0); break;
4525 0           case G_ARRAY: ret = (SV*)newAV(); break;
4526             }
4527              
4528 0           hd.words = hd.items = 0;
4529 0           hd.acc = ret;
4530 0           hd.context = context;
4531              
4532 0           heap_dumper(&hd);
4533              
4534 0           switch(context) {
4535             case G_VOID:
4536             case G_SCALAR: {
4537 0           SV* tmp = newSVpvf("heap had %ld bytes (%ld items)\n",
4538 0           (hd.words + BL_HEAD * hd.items) * sizeof(long),
4539             hd.items);
4540 0           sv_catsv(tmp,ret);
4541 0           SvREFCNT_dec(ret);
4542 0 0         if(GIMME_V == G_VOID) {
    0          
4543 0 0         PerlIO_puts(PerlIO_stdout(), SvPV_nolen(tmp));
4544 0           SvREFCNT_dec(tmp);
4545 0           XSRETURN(0);
4546             } else {
4547 0           ST(0) = sv_2mortal(tmp);
4548 0           XSRETURN(1);
4549             }
4550             }
4551             case G_ARRAY:
4552 0 0         for(m = 0; m <= av_len((AV*)ret); m++)
4553 0 0         XPUSHs(sv_2mortal(SvREFCNT_inc(*av_fetch((AV*)ret,m,0))));
4554 0           SvREFCNT_dec(ret);
4555             }
4556              
4557             MODULE = Math::Pari PACKAGE = Math::Pari
4558              
4559             void
4560             DESTROY(rv)
4561             SV * rv
4562             CODE:
4563             {
4564             /* PariStack keeps the latest SV that keeps a GEN on stack. */
4565 3508612           SV* sv = SvRV(rv);
4566             char* ostack; /* The value of PariStack when the
4567             * variable was created, thus the
4568             * previous SV that keeps a GEN from
4569             * stack, or some atoms. */
4570             long oldavma; /* The value of avma on the entry
4571             * to function having the SV as
4572             * argument. */
4573             long howmany;
4574 3508612 100         SV_OAVMA_PARISTACK_get(sv, oldavma, ostack);
4575 3508612           oldavma += myPARI_bot;
4576             #if 1
4577 3508612 100         if (SvMAGICAL(sv) && SvTYPE(sv) == SVt_PVAV) {
    50          
4578 1175           MAGIC *mg = mg_find(sv, 'P');
4579             SV *obj;
4580              
4581             /* Be extra paranoid: is refcount is artificially low? */
4582 1175 50         if (mg && (obj = mg->mg_obj) && SvROK(obj) && SvRV(obj) == sv) {
    50          
    100          
    50          
4583 1145           mg->mg_flags &= ~MGf_REFCOUNTED;
4584 1145           SvREFCNT_inc(sv);
4585 1145           SvREFCNT_dec(obj);
4586             }
4587             /* We manipulated SvCUR(), which for AV overwrites AvFILLp();
4588             make sure that array looks like an empty one */
4589 1175           AvFILLp((AV*)sv) = -1;
4590             }
4591             #endif
4592 3508612 100         SV_PARISTACK_set(sv, GENheap); /* To avoid extra free() in moveoff.... */
4593 3508612 100         if (ostack == GENheap) /* Leave it alone? XXXX */
4594             /* break */ ;
4595 2469559 100         else if (ostack == GENmovedOffStack) {/* Know that it _was temporary. */
4596 1289871 100         killbloc((GEN)SV_myvoidp_get(sv));
    50          
4597             } else {
4598             /* Still on stack */
4599 1179688 50         if (ostack != (char*)PariStack) { /* But not the newest one. */
4600 1179688           howmany = moveoffstack_newer_than(sv);
4601 1179688 50         RUN_IF_DEBUG_PARI( warn("%li items moved off stack, onStack=%ld, offStack=%ld", howmany, (long)onStack, (long)offStack) );
4602             }
4603             /* Now fall through: */
4604             /* case (IV)GENfirstOnStack: */
4605             /* Now sv is the newest one on stack. */
4606 1179688           onStack_dec;
4607 1179688           perlavma = oldavma;
4608 1179688 50         if (oldavma > sentinel) {
4609 0           avma = sentinel; /* Mark the space on stack as free. */
4610             } else {
4611 1179688           avma = oldavma; /* Mark the space on stack as free. */
4612             }
4613 1179688           PariStack = (SV*)ostack; /* The same on the Perl/PARI side. */
4614             }
4615 3508612           SVnum_dec;
4616             }
4617              
4618             SV *
4619             pari_print(in)
4620             GEN in
4621              
4622             SV *
4623             pari_pprint(in)
4624             GEN in
4625              
4626             SV *
4627             pari_texprint(in)
4628             GEN in
4629              
4630             I32
4631             typ(in)
4632             GEN in
4633              
4634             SV *
4635             PARIvar(in)
4636             char *in
4637              
4638             GEN
4639             ifact(arg1)
4640             long oldavma=avma;
4641             long arg1
4642              
4643             void
4644             changevalue(name, val)
4645             PariName name
4646             GEN val
4647              
4648             void
4649             set_gnuterm(a,b,c=0)
4650             IV a
4651             IV b
4652             IV c
4653              
4654             long
4655             setprecision(digits=0)
4656             long digits
4657              
4658             long
4659             setseriesprecision(digits=0)
4660             long digits
4661              
4662             IV
4663             setprimelimit(n = 0)
4664             IV n
4665              
4666             void
4667             int_set_term_ftable(a)
4668             IV a
4669              
4670             long
4671             pari_version_exp()
4672              
4673             long
4674             have_highlevel()
4675              
4676             long
4677             have_graphics()
4678              
4679             int
4680             PARI_DEBUG()
4681              
4682             int
4683             PARI_DEBUG_set(val)
4684             int val
4685              
4686             long
4687             lgef(x)
4688             GEN x
4689              
4690             long
4691             lgefint(x)
4692             GEN x
4693              
4694             long
4695             lg(x)
4696             GEN x
4697              
4698             unsigned long
4699             longword(x,n)
4700             GEN x
4701             long n
4702              
4703             char *
4704             added_sections()
4705              
4706             void
4707             __detach_stack()
4708             CODE:
4709 0           detach_stack();
4710              
4711             MODULE = Math::Pari PACKAGE = Math::Pari PREFIX = s_
4712              
4713             char *
4714             s_type_name(x)
4715             GEN x
4716              
4717             int
4718             s_reset_on_reload(newvalue = -1)
4719             int newvalue
4720              
4721             #ifdef WITH_CRASHYOURSELF
4722              
4723             void
4724             crash_yourself()
4725             CODE:
4726             char *s = (char *) make_PariAV;
4727             *s = s[0];
4728              
4729             #endif /* defined(WITH_CRASHYOURSELF) */
4730              
4731             # Cannot do this: it is xsubpp which needs the typemap entry for UV,
4732             # and it needs to convert *all* the branches.
4733             #/* #if defined(PERL_VERSION) && (PERL_VERSION >= 6)*//* 5.6.0 has UV in the typemap */
4734              
4735             #if 0
4736             #UV
4737             #allocatemem(newsize = 0)
4738             #UV newsize
4739              
4740             #else /* !( HAVE_UVs ) */
4741              
4742             unsigned long
4743             s_allocatemem(newsize = 0)
4744             unsigned long newsize
4745              
4746             #endif /* !( HAVE_UVs ) */