My Project
Loading...
Searching...
No Matches
ring.cc
Go to the documentation of this file.
1/****************************************
2* Computer Algebra System SINGULAR *
3****************************************/
4/*
5* ABSTRACT - the interpreter related ring operations
6*/
7
8/* includes */
9#include <cmath>
10
11#include "misc/auxiliary.h"
12#include "misc/mylimits.h"
13#include "misc/options.h"
14#include "misc/int64vec.h"
15
16#include "coeffs/numbers.h"
17#include "coeffs/coeffs.h"
18
20#include "polys/simpleideals.h"
23#include "polys/prCopy.h"
25
26#include "polys/matpol.h"
27
29
30#ifdef HAVE_PLURAL
31#include "polys/nc/nc.h"
32#include "polys/nc/sca.h"
33#endif
34
35
36#include "ext_fields/algext.h"
37#include "ext_fields/transext.h"
38
39
40#define BITS_PER_LONG 8*SIZEOF_LONG
41
42typedef char * char_ptr;
45
46
47static const char * const ringorder_name[] =
48{
49 " ?", ///< ringorder_no = 0,
50 "a", ///< ringorder_a,
51 "A", ///< ringorder_a64,
52 "c", ///< ringorder_c,
53 "C", ///< ringorder_C,
54 "M", ///< ringorder_M,
55 "S", ///< ringorder_S,
56 "s", ///< ringorder_s,
57 "lp", ///< ringorder_lp,
58 "dp", ///< ringorder_dp,
59 "ip", ///< ringorder_ip,
60 "Dp", ///< ringorder_Dp,
61 "wp", ///< ringorder_wp,
62 "Wp", ///< ringorder_Wp,
63 "Ip", ///< ringorder_Ip,
64 "ls", ///< ringorder_ls,
65 "ds", ///< ringorder_ds,
66 "Ds", ///< ringorder_Ds,
67 "ws", ///< ringorder_ws,
68 "Ws", ///< ringorder_Ws,
69 "am", ///< ringorder_am,
70 "L", ///< ringorder_L,
71 "aa", ///< ringorder_aa
72 "is", ///< ringorder_is,
73 "IS", ///< ringorder_IS
74 " _" ///< ringorder_unspec
75};
76
77
78const char * rSimpleOrdStr(int ord)
79{
80 return ringorder_name[ord];
81}
82
83/// unconditionally deletes fields in r
84void rDelete(ring r);
85/// set r->VarL_Size, r->VarL_Offset, r->VarL_LowIndex
86static void rSetVarL(ring r);
87/// get r->divmask depending on bits per exponent
88static unsigned long rGetDivMask(int bits);
89/// right-adjust r->VarOffset
90static void rRightAdjustVarOffset(ring r);
91static void rOptimizeLDeg(ring r);
92
93/*0 implementation*/
94//BOOLEAN rField_is_R(ring r)
95//{
96// if (r->cf->ch== -1)
97// {
98// if (r->float_len==(short)0) return TRUE;
99// }
100// return FALSE;
101//}
102
103ring rDefault(const coeffs cf, int N, char **n,int ord_size, rRingOrder_t *ord, int *block0, int *block1, int** wvhdl, unsigned long bitmask)
104{
105 assume( cf != NULL);
107 r->N = N;
108 r->cf = cf;
109 /*rPar(r) = 0; Alloc0 */
110 /*names*/
111 r->names = (char **) omAlloc0(N * sizeof(char *));
112 int i;
113 for(i=0;i<N;i++)
114 {
115 r->names[i] = omStrDup(n[i]);
116 }
117 /*weights: entries for 2 blocks: NULL*/
118 if (wvhdl==NULL)
119 r->wvhdl = (int **)omAlloc0((ord_size+1) * sizeof(int *));
120 else
121 r->wvhdl=wvhdl;
122 r->order = ord;
123 r->block0 = block0;
124 r->block1 = block1;
125 if (bitmask!=0) r->wanted_maxExp=bitmask;
126
127 /* complete ring initializations */
128 rComplete(r);
129 return r;
130}
131ring rDefault(int ch, int N, char **n,int ord_size, rRingOrder_t *ord, int *block0, int *block1,int ** wvhdl)
132{
133 coeffs cf;
134 if (ch==0) cf=nInitChar(n_Q,NULL);
135 else cf=nInitChar(n_Zp,(void*)(long)ch);
136 assume( cf != NULL);
137 return rDefault(cf,N,n,ord_size,ord,block0,block1,wvhdl);
138}
139ring rDefault(const coeffs cf, int N, char **n, const rRingOrder_t o)
140{
141 assume( cf != NULL);
142 /*order: o=lp,0*/
143 rRingOrder_t *order = (rRingOrder_t *) omAlloc(2* sizeof(rRingOrder_t));
144 int *block0 = (int *)omAlloc0(2 * sizeof(int));
145 int *block1 = (int *)omAlloc0(2 * sizeof(int));
146 /* ringorder o=lp for the first block: var 1..N */
147 order[0] = o;
148 block0[0] = 1;
149 block1[0] = N;
150 /* the last block: everything is 0 */
151 order[1] = (rRingOrder_t)0;
152
153 return rDefault(cf,N,n,2,order,block0,block1);
154}
155
156ring rDefault(int ch, int N, char **n)
157{
158 coeffs cf;
159 if (ch==0) cf=nInitChar(n_Q,NULL);
160 else cf=nInitChar(n_Zp,(void*)(long)ch);
161 assume( cf != NULL);
162 return rDefault(cf,N,n);
163}
164
165///////////////////////////////////////////////////////////////////////////
166//
167// rInit: define a new ring from sleftv's
168//
169//-> ipshell.cc
170
171/////////////////////////////
172// Auxiliary functions
173//
174
175// check intvec, describing the ordering
177{
178 if ((iv->length()!=2)&&(iv->length()!=3))
179 {
180 WerrorS("weights only for orderings wp,ws,Wp,Ws,a,M");
181 return TRUE;
182 }
183 return FALSE;
184}
185
186int rTypeOfMatrixOrder(const intvec* order)
187{
188 int i=0,j,typ=1;
189 int sz = (int)sqrt((double)(order->length()-2));
190 if ((sz*sz)!=(order->length()-2))
191 {
192 WerrorS("Matrix order is not a square matrix");
193 typ=0;
194 }
195 while ((i<sz) && (typ==1))
196 {
197 j=0;
198 while ((j<sz) && ((*order)[j*sz+i+2]==0)) j++;
199 if (j>=sz)
200 {
201 typ = 0;
202 WerrorS("Matrix order not complete");
203 }
204 else if ((*order)[j*sz+i+2]<0)
205 typ = -1;
206 else
207 i++;
208 }
209 return typ;
210}
211
212
213int r_IsRingVar(const char *n, char**names,int N)
214{
215 if (names!=NULL)
216 {
217 for (int i=0; i<N; i++)
218 {
219 if (names[i]==NULL) return -1;
220 if (strcmp(n,names[i]) == 0) return (int)i;
221 }
222 }
223 return -1;
224}
225
226
228{
229 if ((r==NULL)||(r->order==NULL))
230 return; /*to avoid printing after errors....*/
231
232 assume(r != NULL);
233 const coeffs C = r->cf;
234 assume(C != NULL);
235
236 int nblocks=rBlocks(r);
237
238 // omCheckAddrSize(r,sizeof(ip_sring));
239 omCheckAddrSize(r->order,nblocks*sizeof(int));
240 omCheckAddrSize(r->block0,nblocks*sizeof(int));
241 omCheckAddrSize(r->block1,nblocks*sizeof(int));
242 omCheckAddrSize(r->wvhdl,nblocks*sizeof(int *));
243 omCheckAddrSize(r->names,r->N*sizeof(char *));
244
245 nblocks--;
246
247
248 //Print("ref:%d, C->ref:%d\n",r->ref,C->ref);
249 PrintS("// coefficients: ");
250 if( nCoeff_is_algExt(C) )
251 {
252 // NOTE: the following (non-thread-safe!) UGLINESS
253 // (changing naRing->ShortOut for a while) is due to Hans!
254 // Just think of other ring using the VERY SAME naRing and possible
255 // side-effects...
256 ring R = C->extRing;
257 const BOOLEAN bSaveShortOut = rShortOut(R); R->ShortOut = rShortOut(r) & rCanShortOut(R);
258
259 n_CoeffWrite(C, details); // for correct printing of minpoly... WHAT AN UGLINESS!!!
260
261 R->ShortOut = bSaveShortOut;
262 }
263 else
265 PrintLn();
266// {
267// PrintS("// characteristic : ");
268//
269// char const * const * const params = rParameter(r);
270//
271// if (params!=NULL)
272// {
273// Print ("// %d parameter : ",rPar(r));
274//
275// char const * const * sp= params;
276// int nop=0;
277// while (nop<rPar(r))
278// {
279// PrintS(*sp);
280// PrintS(" ");
281// sp++; nop++;
282// }
283// PrintS("\n// minpoly : ");
284// if ( rField_is_long_C(r) )
285// {
286// // i^2+1:
287// Print("(%s^2+1)\n", params[0]);
288// }
289// else if (rMinpolyIsNULL(r))
290// {
291// PrintS("0\n");
292// }
293// else
294// {
295// StringSetS(""); n_Write(r->cf->minpoly, r); PrintS(StringEndS("\n")); // NOTE/TODO: use StringAppendS("\n"); omFree(s);
296// }
297// //if (r->qideal!=NULL)
298// //{
299// // iiWriteMatrix((matrix)r->qideal,"// minpolys",1,r,0);
300// // PrintLn();
301// //}
302// }
303// }
304 Print("// number of vars : %d",r->N);
305
306 //for (nblocks=0; r->order[nblocks]; nblocks++);
307 nblocks=rBlocks(r)-1;
308
309 for (int l=0, nlen=0 ; l<nblocks; l++)
310 {
311 int i=0;
312 Print("\n// block %3d : ",l+1);
313
314 Print("ordering %s", rSimpleOrdStr(r->order[l]));
315
316
317 if (r->order[l] == ringorder_IS)
318 {
319 assume( r->block0[l] == r->block1[l] );
320 const int s = r->block0[l];
321 assume( (-2 < s) && (s < 2) );
322 Print("(%d)", s); // 0 => prefix! +/-1 => suffix!
323 continue;
324 }
325 else if (r->order[l]==ringorder_s)
326 {
327 assume( l == 0 );
328 Print(" syz_comp: %d",r->block0[l]);
329 continue;
330 }
331 else if (
332 ( (r->order[l] >= ringorder_lp)
333 ||(r->order[l] == ringorder_M)
334 ||(r->order[l] == ringorder_a)
335 ||(r->order[l] == ringorder_am)
336 ||(r->order[l] == ringorder_a64)
337 ||(r->order[l] == ringorder_aa) ) && (r->order[l] < ringorder_IS) )
338 {
339 PrintS("\n// : names ");
340 for (i = r->block0[l]-1; i<r->block1[l]; i++)
341 {
342 nlen = strlen(r->names[i]);
343 Print(" %s",r->names[i]);
344 }
345 }
346
347 if (r->wvhdl[l]!=NULL)
348 {
349 #ifndef SING_NDEBUG
350 if((r->order[l] != ringorder_wp)
351 &&(r->order[l] != ringorder_Wp)
352 &&(r->order[l] != ringorder_ws)
353 &&(r->order[l] != ringorder_Ws)
354 &&(r->order[l] != ringorder_a)
355 &&(r->order[l] != ringorder_a64)
356 &&(r->order[l] != ringorder_am)
357 &&(r->order[l] != ringorder_M))
358 {
359 Warn("should not have wvhdl entry at pos. %d",l);
360 }
361 #endif
362 int bl=r->block1[l]-r->block0[l]+1;
363 for (int j= 0;
364 j<(r->block1[l]-r->block0[l]+1)*(r->block1[l]-r->block0[l]+1);
365 j+=bl)
366 {
367 PrintS("\n// : weights ");
368 for (i = 0; i<=r->block1[l]-r->block0[l]; i++)
369 {
370 if (r->order[l] == ringorder_a64)
371 {
372 int64 *w=(int64 *)r->wvhdl[l];
373 #if SIZEOF_LONG == 4
374 Print("%*lld " ,nlen,w[i+j]);
375 #else
376 Print(" %*ld" ,nlen,w[i+j]);
377 #endif
378 }
379 else
380 Print(" %*d" ,nlen,r->wvhdl[l][i+j]);
381 }
382 if (r->order[l]!=ringorder_M) break;
383 }
384 if (r->order[l]==ringorder_am)
385 {
386 int m=r->wvhdl[l][bl];
387 Print("\n// : %d module weights ",m);
388 m+=bl;i=bl+1;
389 for(;i<=m;i++) Print(" %*d" ,nlen,r->wvhdl[l][i]);
390 }
391 }
392 }
393#ifdef HAVE_PLURAL
394 if(rIsPluralRing(r))
395 {
396 PrintS("\n// noncommutative relations:");
397 if( details )
398 {
399 poly pl=NULL;
400 int nl;
401 int i,j;
402 for (i = 1; i<r->N; i++)
403 {
404 for (j = i+1; j<=r->N; j++)
405 {
406 nl = n_IsOne(p_GetCoeff(MATELEM(r->GetNC()->C,i,j),r), r->cf);
407 if ( (MATELEM(r->GetNC()->D,i,j)!=NULL) || (!nl) )
408 {
409 Print("\n// %s%s=",r->names[j-1],r->names[i-1]);
410 pl = MATELEM(r->GetNC()->MT[UPMATELEM(i,j,r->N)],1,1);
411 p_Write0(pl, r, r);
412 }
413 }
414 }
415 } else
416 PrintS(" ...");
417
418#if MYTEST /*Singularg should not differ from Singular except in error case*/
419 Print("\n// noncommutative type:%d", (int)ncRingType(r));
420 Print("\n// is skew constant:%d",r->GetNC()->IsSkewConstant);
421 if( rIsSCA(r) )
422 {
423 Print("\n// alternating variables: [%d, %d]", scaFirstAltVar(r), scaLastAltVar(r));
424 const ideal Q = SCAQuotient(r); // resides within r!
425 PrintS("\n// quotient of sca by ideal");
426
427 if (Q!=NULL)
428 {
429 iiWriteMatrix((matrix)Q,"scaQ",1,r,0);
430 }
431 else
432 PrintS(" (NULL)");
433 }
434#endif
435 }
436 if (rIsLPRing(r))
437 {
438 Print("\n// letterplace ring (block size %d, ncgen count %d)",r->isLPring, r->LPncGenCount);
439 }
440#endif
441 if (r->qideal!=NULL)
442 {
443 PrintS("\n// quotient ring from ideal");
444 if( details )
445 {
446 PrintLn();
447 iiWriteMatrix((matrix)r->qideal,"_",1,r,0);
448 } else PrintS(" ...");
449 }
450}
451
453{
454 int i, j;
455
456 if (r == NULL) return;
457 if( r->ref > 0 ) // ->ref means the number of Interpreter objects referring to the ring...
458 return;
459
460 if (r->ppNoether!=NULL) p_Delete(&(r->ppNoether),r);
461 if( r->qideal != NULL )
462 {
463 ideal q = r->qideal;
464 r->qideal = NULL;
465 id_Delete(&q, r);
466 }
467
468#ifdef HAVE_PLURAL
469 if (rIsPluralRing(r))
470 nc_rKill(r);
471#endif
472
473 rUnComplete(r); // may need r->cf for p_Delete
474 nKillChar(r->cf); r->cf = NULL;
475 // delete order stuff
476 if (r->order != NULL)
477 {
478 i=rBlocks(r);
479 assume(r->block0 != NULL && r->block1 != NULL && r->wvhdl != NULL);
480 // delete order
481 omFreeSize((ADDRESS)r->order,i*sizeof(rRingOrder_t));
482 omFreeSize((ADDRESS)r->block0,i*sizeof(int));
483 omFreeSize((ADDRESS)r->block1,i*sizeof(int));
484 // delete weights
485 for (j=0; j<i; j++)
486 {
487 if (r->wvhdl[j]!=NULL)
488 omFree(r->wvhdl[j]);
489 }
490 omFreeSize((ADDRESS)r->wvhdl,i*sizeof(int *));
491 }
492 else
493 {
494 assume(r->block0 == NULL && r->block1 == NULL && r->wvhdl == NULL);
495 }
496
497 // delete varnames
498 if(r->names!=NULL)
499 {
500 for (i=0; i<r->N; i++)
501 {
502 if (r->names[i] != NULL) omFree((ADDRESS)r->names[i]);
503 }
504 omFreeSize((ADDRESS)r->names,r->N*sizeof(char *));
505 }
506
508}
509
511{
512 int order=ringorder_unspec;
513 while (order!= 0)
514 {
515 if (strcmp(ordername,rSimpleOrdStr(order))==0)
516 break;
517 order--;
518 }
519 if (order==0) Werror("wrong ring order `%s`",ordername);
521 return (rRingOrder_t)order;
522}
523
524char * rOrdStr(ring r)
525{
526 if ((r==NULL)||(r->order==NULL)) return omStrDup("");
527 int nblocks,l,i;
528
529 for (nblocks=0; r->order[nblocks]; nblocks++);
530 nblocks--;
531
532 StringSetS("");
533 for (l=0; ; l++)
534 {
535 StringAppendS((char *)rSimpleOrdStr(r->order[l]));
536 if (r->order[l] == ringorder_s)
537 {
538 StringAppend("(%d)",r->block0[l]);
539 }
540 else if (
541 (r->order[l] != ringorder_c)
542 && (r->order[l] != ringorder_C)
543 && (r->order[l] != ringorder_s)
544 && (r->order[l] != ringorder_S)
545 && (r->order[l] != ringorder_IS)
546 )
547 {
548 if (r->wvhdl[l]!=NULL)
549 {
550 #ifndef SING_NDEBUG
551 if((r->order[l] != ringorder_wp)
552 &&(r->order[l] != ringorder_Wp)
553 &&(r->order[l] != ringorder_ws)
554 &&(r->order[l] != ringorder_Ws)
555 &&(r->order[l] != ringorder_a)
556 &&(r->order[l] != ringorder_a64)
557 &&(r->order[l] != ringorder_am)
558 &&(r->order[l] != ringorder_M))
559 {
560 Warn("should not have wvhdl entry at pos. %d",l);
561 StringAppend("(%d)",r->block1[l]-r->block0[l]+1);
562 }
563 else
564 #endif
565 {
566 StringAppendS("(");
567 for (int j= 0;
568 j<(r->block1[l]-r->block0[l]+1)*(r->block1[l]-r->block0[l]+1);
569 j+=i+1)
570 {
571 char c=',';
572 if(r->order[l]==ringorder_a64)
573 {
574 int64 * w=(int64 *)r->wvhdl[l];
575 for (i = 0; i<r->block1[l]-r->block0[l]; i++)
576 {
577 StringAppend("%lld," ,w[i]);
578 }
579 StringAppend("%lld)" ,w[i]);
580 break;
581 }
582 else
583 {
584 for (i = 0; i<r->block1[l]-r->block0[l]; i++)
585 {
586 StringAppend("%d," ,r->wvhdl[l][i+j]);
587 }
588 }
589 if (r->order[l]!=ringorder_M)
590 {
591 StringAppend("%d)" ,r->wvhdl[l][i+j]);
592 break;
593 }
594 if (j+i+1==(r->block1[l]-r->block0[l]+1)*(r->block1[l]-r->block0[l]+1))
595 c=')';
596 StringAppend("%d%c" ,r->wvhdl[l][i+j],c);
597 }
598 }
599 }
600 else
601 StringAppend("(%d)",r->block1[l]-r->block0[l]+1);
602 }
603 else if (r->order[l] == ringorder_IS)
604 {
605 assume( r->block0[l] == r->block1[l] );
606 const int s = r->block0[l];
607 assume( (-2 < s) && (s < 2) );
608
609 StringAppend("(%d)", s);
610 }
611
612 if (l==nblocks)
613 {
614 if (r->wanted_maxExp!=0)
615 {
616 long mm=r->wanted_maxExp;
618 StringAppend(",L(%ld)",mm);
619 }
620 return StringEndS();
621 }
622 StringAppendS(",");
623 }
624}
625
626char * rVarStr(ring r)
627{
628 if ((r==NULL)||(r->names==NULL)) return omStrDup("");
629 int i;
630 int l=2;
631 char *s;
632
633 for (i=0; i<r->N; i++)
634 {
635 l+=strlen(r->names[i])+1;
636 }
637 s=(char *)omAlloc((long)l);
638 s[0]='\0';
639 for (i=0; i<r->N-1; i++)
640 {
641 strcat(s,r->names[i]);
642 strcat(s,",");
643 }
644 strcat(s,r->names[i]);
645 return s;
646}
647
648/// TODO: make it a virtual method of coeffs, together with:
649/// Decompose & Compose, rParameter & rPar
650char * rCharStr(const ring r){ assume( r != NULL ); return nCoeffString(r->cf); }
651
652char * rParStr(ring r)
653{
654 if ((r==NULL)||(rParameter(r)==NULL)) return omStrDup("");
655
656 char const * const * const params = rParameter(r);
657
658 int i;
659 int l=2;
660
661 for (i=0; i<rPar(r); i++)
662 {
663 l+=strlen(params[i])+1;
664 }
665 char *s=(char *)omAlloc((long)l);
666 s[0]='\0';
667 for (i=0; i<rPar(r)-1; i++)
668 {
669 strcat(s, params[i]);
670 strcat(s,",");
671 }
672 strcat(s, params[i]);
673 return s;
674}
675
676char * rString(ring r)
677{
678 if ((r!=NULL)&&(r->cf!=NULL))
679 {
680 char *ch=rCharStr(r);
681 char *var=rVarStr(r);
682 char *ord=rOrdStr(r);
683 char *res=(char *)omAlloc(strlen(ch)+strlen(var)+strlen(ord)+9);
684 sprintf(res,"(%s),(%s),(%s)",ch,var,ord);
685 omFree((ADDRESS)ch);
686 omFree((ADDRESS)var);
687 omFree((ADDRESS)ord);
688 return res;
689 }
690 else
691 return omStrDup("undefined");
692}
693
694
695/*
696// The fowolling function seems to be never used. Remove?
697static int binaryPower (const int a, const int b)
698{
699 // computes a^b according to the binary representation of b,
700 // i.e., a^7 = a^4 * a^2 * a^1. This saves some multiplications.
701 int result = 1;
702 int factor = a;
703 int bb = b;
704 while (bb != 0)
705 {
706 if (bb % 2 != 0) result = result * factor;
707 bb = bb / 2;
708 factor = factor * factor;
709 }
710 return result;
711}
712*/
713
714/* we keep this otherwise superfluous method for compatibility reasons
715 towards the SINGULAR svn trunk */
716int rChar(ring r) { return r->cf->ch; }
717
718
719
720// creates a commutative nc extension; "converts" comm.ring to a Plural ring
721#ifdef HAVE_PLURAL
723{
724 r = rCopy(r);
725 if (rIsPluralRing(r))
726 return r;
727
728 matrix C = mpNew(r->N,r->N); // ring-independent!?!
729 matrix D = mpNew(r->N,r->N);
730
731 for(int i=1; i<r->N; i++)
732 for(int j=i+1; j<=r->N; j++)
733 MATELEM(C,i,j) = p_One( r);
734
735 if (nc_CallPlural(C, D, NULL, NULL, r, false, true, false, r/*??currRing??*/, TRUE)) // TODO: what about quotient ideal?
736 WarnS("Error initializing multiplication!"); // No reaction!???
737
738 return r;
739}
740#endif
741
742
743/*2
744 *returns -1 for not compatible, (sum is undefined)
745 * 1 for compatible (and sum)
746 */
747/* vartest: test for variable/parameter names
748* dp_dp: 0:block ordering
749* 1:for comm. rings: use block order dp + dp/ds/wp
750* 2:order aa(..),dp
751*/
753{
754
756 memset(&tmpR,0,sizeof(tmpR));
757 /* check coeff. field =====================================================*/
758
759 if (r1->cf==r2->cf)
760 {
761 tmpR.cf=nCopyCoeff(r1->cf);
762 }
763 else /* different type */
764 {
765 if (getCoeffType(r1->cf)==n_Zp)
766 {
767 if (getCoeffType(r2->cf)==n_Q)
768 {
769 tmpR.cf=nCopyCoeff(r1->cf);
770 }
771 else if (nCoeff_is_Extension(r2->cf) && rChar(r2) == rChar(r1))
772 {
773 /*AlgExtInfo extParam;
774 extParam.r = r2->cf->extRing;
775 extParam.i = r2->cf->extRing->qideal;*/
776 tmpR.cf=nCopyCoeff(r2->cf);
777 }
778 else
779 {
780 WerrorS("Z/p+...");
781 return -1;
782 }
783 }
784 else if ((getCoeffType(r1->cf)==n_Zn)||(getCoeffType(r1->cf)==n_Znm))
785 {
786 if (getCoeffType(r2->cf)==n_Q)
787 {
788 tmpR.cf=nCopyCoeff(r1->cf);
789 }
790 else if (nCoeff_is_Extension(r2->cf)
791 && (mpz_cmp(r1->cf->modNumber,r2->cf->extRing->cf->modNumber)==0))
792 { // covers transext.cc and algext.cc
793 tmpR.cf=nCopyCoeff(r2->cf);
794 }
795 else
796 {
797 WerrorS("Z/n+...");
798 return -1;
799 }
800 }
801 else if (getCoeffType(r1->cf)==n_R)
802 {
803 WerrorS("R+..");
804 return -1;
805 }
806 else if (getCoeffType(r1->cf)==n_Q)
807 {
808 if (getCoeffType(r2->cf)==n_Zp)
809 {
810 tmpR.cf=nCopyCoeff(r2->cf);
811 }
812 else if (nCoeff_is_Extension(r2->cf))
813 {
814 tmpR.cf=nCopyCoeff(r2->cf);
815 }
816 else
817 {
818 WerrorS("Q+...");
819 return -1;
820 }
821 }
822 else if (nCoeff_is_Extension(r1->cf))
823 {
824 if (r1->cf->extRing->cf==r2->cf)
825 {
826 tmpR.cf=nCopyCoeff(r1->cf);
827 }
828 else if (getCoeffType(r1->cf->extRing->cf)==n_Zp && getCoeffType(r2->cf)==n_Q) //r2->cf == n_Zp should have been handled above
829 {
830 tmpR.cf=nCopyCoeff(r1->cf);
831 }
832 else
833 {
834 WerrorS ("coeff sum of two extension fields not implemented");
835 return -1;
836 }
837 }
838 else
839 {
840 WerrorS("coeff sum not yet implemented");
841 return -1;
842 }
843 }
844 /* variable names ========================================================*/
845 int i,j,k;
846 int l=r1->N+r2->N;
847 char **names=(char **)omAlloc0(l*sizeof(char *));
848 k=0;
849
850 // collect all varnames from r1, except those which are parameters
851 // of r2, or those which are the empty string
852 for (i=0;i<r1->N;i++)
853 {
854 BOOLEAN b=TRUE;
855
856 if (*(r1->names[i]) == '\0')
857 b = FALSE;
858 else if ((rParameter(r2)!=NULL) && (strlen(r1->names[i])==1))
859 {
860 if (vartest)
861 {
862 for(j=0;j<rPar(r2);j++)
863 {
864 if (strcmp(r1->names[i],rParameter(r2)[j])==0)
865 {
866 b=FALSE;
867 break;
868 }
869 }
870 }
871 }
872
873 if (b)
874 {
875 //Print("name : %d: %s\n",k,r1->names[i]);
876 names[k]=omStrDup(r1->names[i]);
877 k++;
878 }
879 //else
880 // Print("no name (par1) %s\n",r1->names[i]);
881 }
882 // Add variables from r2, except those which are parameters of r1
883 // those which are empty strings, and those which equal a var of r1
884 for(i=0;i<r2->N;i++)
885 {
886 BOOLEAN b=TRUE;
887
888 if (*(r2->names[i]) == '\0')
889 b = FALSE;
890 else if ((rParameter(r1)!=NULL) && (strlen(r2->names[i])==1))
891 {
892 if (vartest)
893 {
894 for(j=0;j<rPar(r1);j++)
895 {
896 if (strcmp(r2->names[i],rParameter(r1)[j])==0)
897 {
898 b=FALSE;
899 break;
900 }
901 }
902 }
903 }
904
905 if (b)
906 {
907 if (vartest)
908 {
909 for(j=0;j<r1->N;j++)
910 {
911 if (strcmp(r1->names[j],r2->names[i])==0)
912 {
913 b=FALSE;
914 break;
915 }
916 }
917 }
918 if (b)
919 {
920 //Print("name : %d : %s\n",k,r2->names[i]);
921 names[k]=omStrDup(r2->names[i]);
922 k++;
923 }
924 //else
925 // Print("no name (var): %s\n",r2->names[i]);
926 }
927 //else
928 // Print("no name (par): %s\n",r2->names[i]);
929 }
930 // check whether we found any vars at all
931 if (k == 0)
932 {
933 names[k]=omStrDup("");
934 k=1;
935 }
936 tmpR.N=k;
937 tmpR.names=names;
938 /* ordering *======================================================== */
939 tmpR.OrdSgn=0;
940 if ((dp_dp==2)
941 && (r1->OrdSgn==1)
942 && (r2->OrdSgn==1)
945#endif
946 )
947 {
948 tmpR.order=(rRingOrder_t*)omAlloc0(4*sizeof(rRingOrder_t));
949 tmpR.block0=(int*)omAlloc0(4*sizeof(int));
950 tmpR.block1=(int*)omAlloc0(4*sizeof(int));
951 tmpR.wvhdl=(int**) omAlloc0(4*sizeof(int**));
952 // ----
953 tmpR.block0[0] = 1;
954 tmpR.block1[0] = rVar(r1)+rVar(r2);
955 tmpR.order[0] = ringorder_aa;
956 tmpR.wvhdl[0]=(int*)omAlloc0((rVar(r1)+rVar(r2) + 1)*sizeof(int));
957 for(int i=0;i<rVar(r1);i++) tmpR.wvhdl[0][i]=1;
958 // ----
959 tmpR.block0[1] = 1;
960 tmpR.block1[1] = rVar(r1)+rVar(r2);
961 tmpR.order[1] = ringorder_dp;
962 // ----
963 tmpR.order[2] = ringorder_C;
964 }
965 else if (dp_dp
968#endif
969 )
970 {
971 tmpR.order=(rRingOrder_t*)omAlloc(4*sizeof(rRingOrder_t));
972 tmpR.block0=(int*)omAlloc0(4*sizeof(int));
973 tmpR.block1=(int*)omAlloc0(4*sizeof(int));
974 tmpR.wvhdl=(int**)omAlloc0(4*sizeof(int *));
975 tmpR.order[0]=ringorder_dp;
976 tmpR.block0[0]=1;
977 tmpR.block1[0]=rVar(r1);
978 if (r2->OrdSgn==1)
979 {
980 if ((r2->block0[0]==1)
981 && (r2->block1[0]==rVar(r2))
982 && ((r2->order[0]==ringorder_wp)
983 || (r2->order[0]==ringorder_Wp)
984 || (r2->order[0]==ringorder_Dp))
985 )
986 {
987 tmpR.order[1]=r2->order[0];
988 if (r2->wvhdl[0]!=NULL)
989 #ifdef HAVE_OMALLOC
990 tmpR.wvhdl[1]=(int *)omMemDup(r2->wvhdl[0]);
991 #else
992 {
993 int l=r2->block1[0]-r2->block0[0]+1;
994 if (r2->order[0]==ringorder_a64) l*=2;
995 else if (r2->order[0]==ringorder_M) l=l*l;
996 else if (r2->order[0]==ringorder_am)
997 {
998 l+=r2->wvhdl[1][r2->block1[0]-r2->block0[0]+1]+1;
999 }
1000 tmpR.wvhdl[1]=(int*)omalloc(l*sizeof(int));
1001 memcpy(tmpR.wvhdl[1],r2->wvhdl[0],l*sizeof(int));
1002 }
1003 #endif
1004 }
1005 else
1006 tmpR.order[1]=ringorder_dp;
1007 }
1008 else
1009 {
1010 tmpR.order[1]=ringorder_ds;
1011 tmpR.OrdSgn=-1;
1012 }
1013 tmpR.block0[1]=rVar(r1)+1;
1014 tmpR.block1[1]=rVar(r1)+rVar(r2);
1015 tmpR.order[2]=ringorder_C;
1016 tmpR.order[3]=(rRingOrder_t)0;
1017 }
1018 else
1019 {
1020 if ((r1->order[0]==ringorder_unspec)
1021 && (r2->order[0]==ringorder_unspec))
1022 {
1023 tmpR.order=(rRingOrder_t*)omAlloc(3*sizeof(rRingOrder_t));
1024 tmpR.block0=(int*)omAlloc(3*sizeof(int));
1025 tmpR.block1=(int*)omAlloc(3*sizeof(int));
1026 tmpR.wvhdl=(int**)omAlloc0(3*sizeof(int *));
1027 tmpR.order[0]=ringorder_unspec;
1028 tmpR.order[1]=ringorder_C;
1029 tmpR.order[2]=(rRingOrder_t)0;
1030 tmpR.block0[0]=1;
1031 tmpR.block1[0]=tmpR.N;
1032 }
1033 else if (l==k) /* r3=r1+r2 */
1034 {
1035 int b;
1036 ring rb;
1037 if (r1->order[0]==ringorder_unspec)
1038 {
1039 /* extend order of r2 to r3 */
1040 b=rBlocks(r2);
1041 rb=r2;
1042 tmpR.OrdSgn=r2->OrdSgn;
1043 }
1044 else if (r2->order[0]==ringorder_unspec)
1045 {
1046 /* extend order of r1 to r3 */
1047 b=rBlocks(r1);
1048 rb=r1;
1049 tmpR.OrdSgn=r1->OrdSgn;
1050 }
1051 else
1052 {
1053 b=rBlocks(r1)+rBlocks(r2)-2; /* for only one order C, only one 0 */
1054 rb=NULL;
1055 }
1056 tmpR.order=(rRingOrder_t*)omAlloc0(b*sizeof(rRingOrder_t));
1057 tmpR.block0=(int*)omAlloc0(b*sizeof(int));
1058 tmpR.block1=(int*)omAlloc0(b*sizeof(int));
1059 tmpR.wvhdl=(int**)omAlloc0(b*sizeof(int *));
1060 /* weights not implemented yet ...*/
1061 if (rb!=NULL)
1062 {
1063 for (i=0;i<b;i++)
1064 {
1065 tmpR.order[i]=rb->order[i];
1066 tmpR.block0[i]=rb->block0[i];
1067 tmpR.block1[i]=rb->block1[i];
1068 if (rb->wvhdl[i]!=NULL)
1069 WarnS("rSum: weights not implemented");
1070 }
1071 tmpR.block0[0]=1;
1072 }
1073 else /* ring sum for complete rings */
1074 {
1075 for (i=0;r1->order[i]!=0;i++)
1076 {
1077 tmpR.order[i]=r1->order[i];
1078 tmpR.block0[i]=r1->block0[i];
1079 tmpR.block1[i]=r1->block1[i];
1080 if (r1->wvhdl[i]!=NULL)
1081 #ifdef HAVE_OMALLOC
1082 tmpR.wvhdl[i] = (int*) omMemDup(r1->wvhdl[i]);
1083 #else
1084 {
1085 int l=r1->block1[i]-r1->block0[i]+1;
1086 if (r1->order[i]==ringorder_a64) l*=2;
1087 else if (r1->order[i]==ringorder_M) l=l*l;
1088 else if (r1->order[i]==ringorder_am)
1089 {
1090 l+=r1->wvhdl[i][r1->block1[i]-r1->block0[i]+1]+1;
1091 }
1092 tmpR.wvhdl[i]=(int*)omalloc(l*sizeof(int));
1093 memcpy(tmpR.wvhdl[i],r1->wvhdl[i],l*sizeof(int));
1094 }
1095 #endif
1096 }
1097 j=i;
1098 i--;
1099 if ((r1->order[i]==ringorder_c)
1100 ||(r1->order[i]==ringorder_C))
1101 {
1102 j--;
1103 tmpR.order[b-2]=r1->order[i];
1104 }
1105 for (i=0;r2->order[i]!=0;i++)
1106 {
1107 if ((r2->order[i]!=ringorder_c)
1108 &&(r2->order[i]!=ringorder_C))
1109 {
1110 tmpR.order[j]=r2->order[i];
1111 tmpR.block0[j]=r2->block0[i]+rVar(r1);
1112 tmpR.block1[j]=r2->block1[i]+rVar(r1);
1113 if (r2->wvhdl[i]!=NULL)
1114 {
1115 #ifdef HAVE_OMALLOC
1116 tmpR.wvhdl[j] = (int*) omMemDup(r2->wvhdl[i]);
1117 #else
1118 {
1119 int l=r2->block1[i]-r2->block0[i]+1;
1120 if (r2->order[i]==ringorder_a64) l*=2;
1121 else if (r2->order[i]==ringorder_M) l=l*l;
1122 else if (r2->order[i]==ringorder_am)
1123 {
1124 l+=r2->wvhdl[i][r2->block1[i]-r2->block0[i]+1]+1;
1125 }
1126 tmpR.wvhdl[j]=(int*)omalloc(l*sizeof(int));
1127 memcpy(tmpR.wvhdl[j],r2->wvhdl[i],l*sizeof(int));
1128 }
1129 #endif
1130 }
1131 j++;
1132 }
1133 }
1134 if((r1->OrdSgn==-1)||(r2->OrdSgn==-1))
1135 tmpR.OrdSgn=-1;
1136 }
1137 }
1138 else if ((k==rVar(r1)) && (k==rVar(r2))) /* r1 and r2 are "quite"
1139 the same ring */
1140 /* copy r1, because we have the variables from r1 */
1141 {
1142 int b=rBlocks(r1);
1143
1144 tmpR.order=(rRingOrder_t*)omAlloc0(b*sizeof(rRingOrder_t));
1145 tmpR.block0=(int*)omAlloc0(b*sizeof(int));
1146 tmpR.block1=(int*)omAlloc0(b*sizeof(int));
1147 tmpR.wvhdl=(int**)omAlloc0(b*sizeof(int *));
1148 /* weights not implemented yet ...*/
1149 for (i=0;i<b;i++)
1150 {
1151 tmpR.order[i]=r1->order[i];
1152 tmpR.block0[i]=r1->block0[i];
1153 tmpR.block1[i]=r1->block1[i];
1154 if (r1->wvhdl[i]!=NULL)
1155 {
1156 #ifdef HAVE_OMALLOC
1157 tmpR.wvhdl[i] = (int*) omMemDup(r1->wvhdl[i]);
1158 #else
1159 {
1160 int l=r1->block1[i]-r1->block0[i]+1;
1161 if (r1->order[i]==ringorder_a64) l*=2;
1162 else if (r1->order[i]==ringorder_M) l=l*l;
1163 else if (r1->order[i]==ringorder_am)
1164 {
1165 l+=r1->wvhdl[i][r1->block1[i]-r1->block0[i]+1]+1;
1166 }
1167 tmpR.wvhdl[i]=(int*)omalloc(l*sizeof(int));
1168 memcpy(tmpR.wvhdl[i],r1->wvhdl[i],l*sizeof(int));
1169 }
1170 #endif
1171 }
1172 }
1173 tmpR.OrdSgn=r1->OrdSgn;
1174 }
1175 else
1176 {
1177 for(i=0;i<k;i++) omFree((ADDRESS)tmpR.names[i]);
1178 omFreeSize((ADDRESS)names,tmpR.N*sizeof(char *));
1179 Werror("variables must not overlap (# of vars: %d,%d -> %d)",rVar(r1),rVar(r2),k);
1180 return -1;
1181 }
1182 }
1183 tmpR.bitmask=si_max(r1->bitmask,r2->bitmask);
1185 memcpy(sum,&tmpR,sizeof(ip_sring));
1186 rComplete(sum);
1187
1188//#ifdef RDEBUG
1189// rDebugPrint(sum);
1190//#endif
1191
1192
1193
1194#ifdef HAVE_PLURAL
1195 if(1)
1196 {
1197// ring old_ring = currRing;
1198
1201
1202 if ( (R1_is_nc) || (R2_is_nc))
1203 {
1206
1207#if 0
1208#ifdef RDEBUG
1209 rWrite(R1);
1210 rDebugPrint(R1);
1211#endif
1212#endif
1214#if 0
1215#ifdef RDEBUG
1216 rWrite(R2);
1217 rDebugPrint(R2);
1218#endif
1219#endif
1220
1221// rChangeCurrRing(sum); // ?
1222
1223 // Projections from R_i into Sum:
1224 /* multiplication matrices business: */
1225 /* find permutations of vars and pars */
1226 int *perm1 = (int *)omAlloc0((rVar(R1)+1)*sizeof(int));
1227 int *par_perm1 = NULL;
1228 if (rPar(R1)!=0) par_perm1=(int *)omAlloc0((rPar(R1)+1)*sizeof(int));
1229
1230 int *perm2 = (int *)omAlloc0((rVar(R2)+1)*sizeof(int));
1231 int *par_perm2 = NULL;
1232 if (rPar(R2)!=0) par_perm2=(int *)omAlloc0((rPar(R2)+1)*sizeof(int));
1233
1234 maFindPerm(R1->names, rVar(R1), rParameter(R1), rPar(R1),
1235 sum->names, rVar(sum), rParameter(sum), rPar(sum),
1236 perm1, par_perm1, sum->cf->type);
1237
1238 maFindPerm(R2->names, rVar(R2), rParameter(R2), rPar(R2),
1239 sum->names, rVar(sum), rParameter(sum), rPar(sum),
1240 perm2, par_perm2, sum->cf->type);
1241
1242
1243 matrix C1 = R1->GetNC()->C, C2 = R2->GetNC()->C;
1244 matrix D1 = R1->GetNC()->D, D2 = R2->GetNC()->D;
1245
1246 // !!!! BUG? C1 and C2 might live in different baserings!!!
1247
1248 int l = rVar(R1) + rVar(R2);
1249
1250 matrix C = mpNew(l,l);
1251 matrix D = mpNew(l,l);
1252
1253 for (i = 1; i <= rVar(R1); i++)
1254 for (j= rVar(R1)+1; j <= l; j++)
1255 MATELEM(C,i,j) = p_One(sum); // in 'sum'
1256
1257 id_Test((ideal)C, sum);
1258
1259 nMapFunc nMap1 = n_SetMap(R1->cf,sum->cf); /* can change something global: not usable
1260 after the next nSetMap call :( */
1261 // Create blocked C and D matrices:
1262 for (i=1; i<= rVar(R1); i++)
1263 for (j=i+1; j<=rVar(R1); j++)
1264 {
1265 assume(MATELEM(C1,i,j) != NULL);
1266 MATELEM(C,i,j) = p_PermPoly(MATELEM(C1,i,j), perm1, R1, sum, nMap1, par_perm1, rPar(R1)); // need ADD + CMP ops.
1267
1268 if (MATELEM(D1,i,j) != NULL)
1270 }
1271
1272 id_Test((ideal)C, sum);
1273 id_Test((ideal)D, sum);
1274
1275
1276 nMapFunc nMap2 = n_SetMap(R2->cf,sum->cf); /* can change something global: not usable
1277 after the next nSetMap call :( */
1278 for (i=1; i<= rVar(R2); i++)
1279 for (j=i+1; j<=rVar(R2); j++)
1280 {
1281 assume(MATELEM(C2,i,j) != NULL);
1283
1284 if (MATELEM(D2,i,j) != NULL)
1286 }
1287
1288 id_Test((ideal)C, sum);
1289 id_Test((ideal)D, sum);
1290
1291 // Now sum is non-commutative with blocked structure constants!
1292 if (nc_CallPlural(C, D, NULL, NULL, sum, false, false, true, sum))
1293 WarnS("Error initializing non-commutative multiplication!");
1294
1295 /* delete R1, R2*/
1296
1297#if 0
1298#ifdef RDEBUG
1299 rWrite(sum);
1301
1302 Print("\nRefs: R1: %d, R2: %d\n", R1->GetNC()->ref, R2->GetNC()->ref);
1303
1304#endif
1305#endif
1306
1307
1308 rDelete(R1);
1309 rDelete(R2);
1310
1311 /* delete perm arrays */
1312 if (perm1!=NULL) omFree((ADDRESS)perm1);
1313 if (perm2!=NULL) omFree((ADDRESS)perm2);
1316
1317// rChangeCurrRing(old_ring);
1318 }
1319
1320 }
1321#endif
1322
1323 ideal Q=NULL;
1324 ideal Q1=NULL, Q2=NULL;
1325 if (r1->qideal!=NULL)
1326 {
1327// rChangeCurrRing(sum);
1328// if (r2->qideal!=NULL)
1329// {
1330// WerrorS("todo: qring+qring");
1331// return -1;
1332// }
1333// else
1334// {}
1335 /* these were defined in the Plural Part above... */
1336 int *perm1 = (int *)omAlloc0((rVar(r1)+1)*sizeof(int));
1337 int *par_perm1 = NULL;
1338 if (rPar(r1)!=0) par_perm1=(int *)omAlloc0((rPar(r1)+1)*sizeof(int));
1339 maFindPerm(r1->names, rVar(r1), rParameter(r1), rPar(r1),
1340 sum->names, rVar(sum), rParameter(sum), rPar(sum),
1341 perm1, par_perm1, sum->cf->type);
1342 nMapFunc nMap1 = n_SetMap(r1->cf,sum->cf);
1343 Q1 = idInit(IDELEMS(r1->qideal),1);
1344
1345 for (int for_i=0;for_i<IDELEMS(r1->qideal);for_i++)
1346 Q1->m[for_i] = p_PermPoly(
1347 r1->qideal->m[for_i], perm1,
1348 r1, sum,
1349 nMap1,
1350 par_perm1, rPar(r1));
1351
1353 }
1354
1355 if (r2->qideal!=NULL)
1356 {
1357 //if (currRing!=sum)
1358 // rChangeCurrRing(sum);
1359 int *perm2 = (int *)omAlloc0((rVar(r2)+1)*sizeof(int));
1360 int *par_perm2 = NULL;
1361 if (rPar(r2)!=0) par_perm2=(int *)omAlloc0((rPar(r2)+1)*sizeof(int));
1362 maFindPerm(r2->names, rVar(r2), rParameter(r2), rPar(r2),
1363 sum->names, rVar(sum), rParameter(sum), rPar(sum),
1364 perm2, par_perm2, sum->cf->type);
1365 nMapFunc nMap2 = n_SetMap(r2->cf,sum->cf);
1366 Q2 = idInit(IDELEMS(r2->qideal),1);
1367
1368 for (int for_i=0;for_i<IDELEMS(r2->qideal);for_i++)
1369 Q2->m[for_i] = p_PermPoly(
1370 r2->qideal->m[for_i], perm2,
1371 r2, sum,
1372 nMap2,
1373 par_perm2, rPar(r2));
1374
1376 }
1377 if (Q1!=NULL)
1378 {
1379 if ( Q2!=NULL)
1380 Q = id_SimpleAdd(Q1,Q2,sum);
1381 else
1382 Q=id_Copy(Q1,sum);
1383 }
1384 else
1385 {
1386 if ( Q2!=NULL)
1387 Q = id_Copy(Q2,sum);
1388 else
1389 Q=NULL;
1390 }
1391 sum->qideal = Q;
1392
1393#ifdef HAVE_PLURAL
1394 if( rIsPluralRing(sum) )
1396#endif
1397 return 1;
1398}
1399
1400/*2
1401 *returns -1 for not compatible, (sum is undefined)
1402 * 0 for equal, (and sum)
1403 * 1 for compatible (and sum)
1404 */
1406{
1407 if ((r1==NULL)||(r2==NULL)
1408 ||(r1->cf==NULL)||(r2->cf==NULL))
1409 return -1;
1410 if (r1==r2)
1411 {
1412 sum=r1;
1413 rIncRefCnt(r1);
1414 return 0;
1415 }
1416 return rSumInternal(r1,r2,sum,TRUE,FALSE);
1417}
1418
1419/*2
1420 * create a copy of the ring r
1421 * used for qring definition,..
1422 * DOES NOT CALL rComplete
1423 */
1425{
1426 if (r == NULL) return NULL;
1427 int i,j;
1429 //memset: res->idroot=NULL; /* local objects */
1430 //ideal minideal;
1431 res->options=r->options; /* ring dependent options */
1432
1433 //memset: res->ordsgn=NULL;
1434 //memset: res->typ=NULL;
1435 //memset: res->VarOffset=NULL;
1436 //memset: res->firstwv=NULL;
1437
1438 //struct omBin PolyBin; /* Bin from where monoms are allocated */
1439 //memset: res->PolyBin=NULL; // rComplete
1440 res->cf=nCopyCoeff(r->cf); /* coeffs */
1441
1442 //memset: res->ref=0; /* reference counter to the ring */
1443
1444 res->N=rVar(r); /* number of vars */
1445
1446 res->firstBlockEnds=r->firstBlockEnds;
1447#ifdef HAVE_PLURAL
1448 res->real_var_start=r->real_var_start;
1449 res->real_var_end=r->real_var_end;
1450#endif
1451
1452#ifdef HAVE_SHIFTBBA
1453 res->isLPring=r->isLPring; /* 0 for non-letterplace rings, otherwise the number of LP blocks, at least 1, known also as lV */
1454 res->LPncGenCount=r->LPncGenCount;
1455#endif
1456
1457 res->VectorOut=r->VectorOut;
1458 res->ShortOut=r->ShortOut;
1459 res->CanShortOut=r->CanShortOut;
1460
1461 //memset: res->ExpL_Size=0;
1462 //memset: res->CmpL_Size=0;
1463 //memset: res->VarL_Size=0;
1464 //memset: res->pCompIndex=0;
1465 //memset: res->pOrdIndex=0;
1466 //memset: res->OrdSize=0;
1467 //memset: res->VarL_LowIndex=0;
1468 //memset: res->NegWeightL_Size=0;
1469 //memset: res->NegWeightL_Offset=NULL;
1470 //memset: res->VarL_Offset=NULL;
1471
1472 // the following are set by rComplete unless predefined
1473 // therefore, we copy these values: maybe they are non-standard
1474 /* mask for getting single exponents */
1475 res->bitmask=r->bitmask;
1476 res->divmask=r->divmask;
1477 res->BitsPerExp = r->BitsPerExp;
1478 res->ExpPerLong = r->ExpPerLong;
1479
1480 //memset: res->p_Procs=NULL;
1481 //memset: res->pFDeg=NULL;
1482 //memset: res->pLDeg=NULL;
1483 //memset: res->pFDegOrig=NULL;
1484 //memset: res->pLDegOrig=NULL;
1485 //memset: res->p_Setm=NULL;
1486 //memset: res->cf=NULL;
1487
1488/*
1489 if (r->extRing!=NULL)
1490 r->extRing->ref++;
1491
1492 res->extRing=r->extRing;
1493 //memset: res->qideal=NULL;
1494*/
1495
1496
1497 if (copy_ordering == TRUE)
1498 {
1499 res->LexOrder=r->LexOrder; // TRUE if the monomial ordering has polynomial and power series blocks
1500 res->MixedOrder=r->MixedOrder; // TRUE for mixed (global/local) ordering, FALSE otherwise,
1501 i=rBlocks(r);
1502 res->wvhdl = (int **)omAlloc(i * sizeof(int *));
1503 res->order = (rRingOrder_t *) omAlloc(i * sizeof(rRingOrder_t));
1504 res->block0 = (int *) omAlloc(i * sizeof(int));
1505 res->block1 = (int *) omAlloc(i * sizeof(int));
1506 for (j=0; j<i; j++)
1507 {
1508 if (r->wvhdl[j]!=NULL)
1509 {
1510 #ifdef HAVE_OMALLOC
1511 res->wvhdl[j] = (int*) omMemDup(r->wvhdl[j]);
1512 #else
1513 {
1514 int l=r->block1[j]-r->block0[j]+1;
1515 if (r->order[j]==ringorder_a64) l*=2;
1516 else if (r->order[j]==ringorder_M) l=l*l;
1517 else if (r->order[j]==ringorder_am)
1518 {
1519 l+=r->wvhdl[j][r->block1[j]-r->block0[j]+1]+1;
1520 }
1521 res->wvhdl[j]=(int*)omalloc(l*sizeof(int));
1522 memcpy(res->wvhdl[j],r->wvhdl[j],l*sizeof(int));
1523 }
1524 #endif
1525 }
1526 else
1527 res->wvhdl[j]=NULL;
1528 }
1529 memcpy(res->order,r->order,i * sizeof(rRingOrder_t));
1530 memcpy(res->block0,r->block0,i * sizeof(int));
1531 memcpy(res->block1,r->block1,i * sizeof(int));
1532 }
1533 //memset: else
1534 //memset: {
1535 //memset: res->wvhdl = NULL;
1536 //memset: res->order = NULL;
1537 //memset: res->block0 = NULL;
1538 //memset: res->block1 = NULL;
1539 //memset: }
1540
1541 res->names = (char **)omAlloc0(rVar(r) * sizeof(char *));
1542 for (i=0; i<rVar(res); i++)
1543 {
1544 res->names[i] = omStrDup(r->names[i]);
1545 }
1546 if (r->qideal!=NULL)
1547 {
1548 if (copy_qideal)
1549 {
1551 rComplete(res);
1552 res->qideal= idrCopyR_NoSort(r->qideal, r, res);
1554 }
1555 //memset: else res->qideal = NULL;
1556 }
1557 //memset: else res->qideal = NULL;
1558 //memset: res->GetNC() = NULL; // copy is purely commutative!!!
1559 return res;
1560}
1561
1562/*2
1563 * create a copy of the ring r
1564 * used for qring definition,..
1565 * DOES NOT CALL rComplete
1566 */
1568{
1569 if (r == NULL) return NULL;
1570 int i,j;
1572 //memcpy(res,r,sizeof(ip_sring));
1573 //memset: res->idroot=NULL; /* local objects */
1574 //ideal minideal;
1575 res->options=r->options; /* ring dependent options */
1576
1577 //memset: res->ordsgn=NULL;
1578 //memset: res->typ=NULL;
1579 //memset: res->VarOffset=NULL;
1580 //memset: res->firstwv=NULL;
1581
1582 //struct omBin PolyBin; /* Bin from where monoms are allocated */
1583 //memset: res->PolyBin=NULL; // rComplete
1584 res->cf=nCopyCoeff(r->cf); /* coeffs */
1585
1586 //memset: res->ref=0; /* reference counter to the ring */
1587
1588 res->N=rVar(r); /* number of vars */
1589
1590 res->firstBlockEnds=r->firstBlockEnds;
1591#ifdef HAVE_PLURAL
1592 res->real_var_start=r->real_var_start;
1593 res->real_var_end=r->real_var_end;
1594#endif
1595
1596#ifdef HAVE_SHIFTBBA
1597 res->isLPring=r->isLPring; /* 0 for non-letterplace rings, otherwise the number of LP blocks, at least 1, known also as lV */
1598 res->LPncGenCount=r->LPncGenCount;
1599#endif
1600
1601 res->VectorOut=r->VectorOut;
1602 res->ShortOut=r->ShortOut;
1603 res->CanShortOut=r->CanShortOut;
1604 res->LexOrder=r->LexOrder; // TRUE if the monomial ordering has polynomial and power series blocks
1605 res->MixedOrder=r->MixedOrder; // TRUE for mixed (global/local) ordering, FALSE otherwise,
1606
1607 //memset: res->ExpL_Size=0;
1608 //memset: res->CmpL_Size=0;
1609 //memset: res->VarL_Size=0;
1610 //memset: res->pCompIndex=0;
1611 //memset: res->pOrdIndex=0;
1612 //memset: res->OrdSize=0;
1613 //memset: res->VarL_LowIndex=0;
1614 //memset: res->NegWeightL_Size=0;
1615 //memset: res->NegWeightL_Offset=NULL;
1616 //memset: res->VarL_Offset=NULL;
1617
1618 // the following are set by rComplete unless predefined
1619 // therefore, we copy these values: maybe they are non-standard
1620 /* mask for getting single exponents */
1621 res->bitmask=r->bitmask;
1622 res->divmask=r->divmask;
1623 res->BitsPerExp = r->BitsPerExp;
1624 res->ExpPerLong = r->ExpPerLong;
1625
1626 //memset: res->p_Procs=NULL;
1627 //memset: res->pFDeg=NULL;
1628 //memset: res->pLDeg=NULL;
1629 //memset: res->pFDegOrig=NULL;
1630 //memset: res->pLDegOrig=NULL;
1631 //memset: res->p_Setm=NULL;
1632 //memset: res->cf=NULL;
1633
1634/*
1635 if (r->extRing!=NULL)
1636 r->extRing->ref++;
1637
1638 res->extRing=r->extRing;
1639 //memset: res->qideal=NULL;
1640*/
1641
1642
1643 if (copy_ordering == TRUE)
1644 {
1645 i=rBlocks(r)+1; // DIFF to rCopy0
1646 res->wvhdl = (int **)omAlloc(i * sizeof(int *));
1647 res->order = (rRingOrder_t *) omAlloc(i * sizeof(rRingOrder_t));
1648 res->block0 = (int *) omAlloc(i * sizeof(int));
1649 res->block1 = (int *) omAlloc(i * sizeof(int));
1650 for (j=0; j<i-1; j++)
1651 {
1652 if (r->wvhdl[j]!=NULL)
1653 {
1654 #ifdef HAVE_OMALLOC
1655 res->wvhdl[j+1] = (int*) omMemDup(r->wvhdl[j]); //DIFF
1656 #else
1657 {
1658 int l=r->block1[j]-r->block0[j]+1;
1659 if (r->order[j]==ringorder_a64) l*=2;
1660 else if (r->order[j]==ringorder_M) l=l*l;
1661 else if (r->order[j]==ringorder_am)
1662 {
1663 l+=r->wvhdl[j][r->block1[j]-r->block0[j]+1]+1;
1664 }
1665 res->wvhdl[j+1]=(int*)omalloc(l*sizeof(int));
1666 memcpy(res->wvhdl[j+1],r->wvhdl[j],l*sizeof(int));
1667 }
1668 #endif
1669 }
1670 else
1671 res->wvhdl[j+1]=NULL; //DIFF
1672 }
1673 memcpy(&(res->order[1]),r->order,(i-1) * sizeof(rRingOrder_t)); //DIFF
1674 memcpy(&(res->block0[1]),r->block0,(i-1) * sizeof(int)); //DIFF
1675 memcpy(&(res->block1[1]),r->block1,(i-1) * sizeof(int)); //DIFF
1676 }
1677 //memset: else
1678 //memset: {
1679 //memset: res->wvhdl = NULL;
1680 //memset: res->order = NULL;
1681 //memset: res->block0 = NULL;
1682 //memset: res->block1 = NULL;
1683 //memset: }
1684
1685 //the added A
1686 res->order[0]=ringorder_a64;
1687 int length=wv64->rows();
1688 int64 *A=(int64 *)omAlloc(length*sizeof(int64));
1689 for(j=length-1;j>=0;j--)
1690 {
1691 A[j]=(*wv64)[j];
1692 }
1693 res->wvhdl[0]=(int *)A;
1694 res->block0[0]=1;
1695 res->block1[0]=length;
1696 //
1697
1698 res->names = (char **)omAlloc0(rVar(r) * sizeof(char *));
1699 for (i=0; i<rVar(res); i++)
1700 {
1701 res->names[i] = omStrDup(r->names[i]);
1702 }
1703 if (r->qideal!=NULL)
1704 {
1705 if (copy_qideal)
1706 {
1707 #ifndef SING_NDEBUG
1708 if (!copy_ordering)
1709 WerrorS("internal error: rCopy0(Q,TRUE,FALSE)");
1710 else
1711 #endif
1712 {
1713 #ifndef SING_NDEBUG
1714 WarnS("internal bad stuff: rCopy0(Q,TRUE,TRUE)");
1715 #endif
1716 rComplete(res);
1717 res->qideal= idrCopyR_NoSort(r->qideal, r, res);
1719 }
1720 }
1721 //memset: else res->qideal = NULL;
1722 }
1723 //memset: else res->qideal = NULL;
1724 //memset: res->GetNC() = NULL; // copy is purely commutative!!!
1725 return res;
1726}
1727
1728/*2
1729 * create a copy of the ring r, which must be equivalent to currRing
1730 * used for qring definition,..
1731 * (i.e.: normal rings: same nCopy as currRing;
1732 * qring: same nCopy, same idCopy as currRing)
1733 */
1735{
1736 if (r == NULL) return NULL;
1738 rComplete(res, 1); // res is purely commutative so far
1739 if (r->qideal!=NULL) res->qideal=idrCopyR_NoSort(r->qideal, r, res);
1740
1741#ifdef HAVE_PLURAL
1742 if (rIsPluralRing(r))
1743 if( nc_rCopy(res, r, true) ) {}
1744#endif
1745
1746 return res;
1747}
1748
1750{
1751 if (r1 == r2) return TRUE;
1752 if (r1 == NULL || r2 == NULL) return FALSE;
1753 if (r1->cf!=r2->cf) return FALSE;
1754 if (rVar(r1)!=rVar(r2)) return FALSE;
1755 if (r1->bitmask!=r2->bitmask) return FALSE;
1756 #ifdef HAVE_SHIFTBBA
1757 if (r1->isLPring!=r2->isLPring) return FALSE;
1758 if (r1->LPncGenCount!=r2->LPncGenCount) return FALSE;
1759 #endif
1760
1761 if( !rSamePolyRep(r1, r2) )
1762 return FALSE;
1763
1764 int i/*, j*/;
1765
1766 for (i=0; i<rVar(r1); i++)
1767 {
1768 if ((r1->names[i] != NULL) && (r2->names[i] != NULL))
1769 {
1770 if (strcmp(r1->names[i], r2->names[i])) return FALSE;
1771 }
1772 else if ((r1->names[i] != NULL) ^ (r2->names[i] != NULL))
1773 {
1774 return FALSE;
1775 }
1776 }
1777
1778 if (qr)
1779 {
1780 if (r1->qideal != NULL)
1781 {
1782 ideal id1 = r1->qideal, id2 = r2->qideal;
1783 int i, n;
1784 poly *m1, *m2;
1785
1786 if (id2 == NULL) return FALSE;
1787 if ((n = IDELEMS(id1)) != IDELEMS(id2)) return FALSE;
1788
1789 {
1790 m1 = id1->m;
1791 m2 = id2->m;
1792 for (i=0; i<n; i++)
1793 if (! p_EqualPolys(m1[i],m2[i], r1, r2)) return FALSE;
1794 }
1795 }
1796 else if (r2->qideal != NULL) return FALSE;
1797 }
1798
1799 return TRUE;
1800}
1801
1803{
1804 int i, j;
1805
1806 if (r1 == r2) return TRUE;
1807
1808 if (r1 == NULL || r2 == NULL) return FALSE;
1809
1810 if ((r1->cf != r2->cf)
1811 || (rVar(r1) != rVar(r2))
1812 || (r1->OrdSgn != r2->OrdSgn))
1813 return FALSE;
1814
1815 i=0;
1816 while (r1->order[i] != 0)
1817 {
1818 if (r2->order[i] == 0) return FALSE;
1819 if ((r1->order[i] != r2->order[i])
1820 || (r1->block0[i] != r2->block0[i])
1821 || (r1->block1[i] != r2->block1[i]))
1822 return FALSE;
1823 if (r1->wvhdl[i] != NULL)
1824 {
1825 if (r2->wvhdl[i] == NULL)
1826 return FALSE;
1827 for (j=0; j<r1->block1[i]-r1->block0[i]+1; j++)
1828 if (r2->wvhdl[i][j] != r1->wvhdl[i][j])
1829 return FALSE;
1830 }
1831 else if (r2->wvhdl[i] != NULL) return FALSE;
1832 i++;
1833 }
1834 if (r2->order[i] != 0) return FALSE;
1835
1836 // we do not check variable names
1837 // we do not check minpoly/minideal
1838 // we do not check qideal
1839
1840 return TRUE;
1841}
1842
1844{
1845 // check for simple ordering
1846 if (rHasSimpleOrder(r))
1847 {
1848 if ((r->order[1] == ringorder_c)
1849 || (r->order[1] == ringorder_C))
1850 {
1851 switch(r->order[0])
1852 {
1853 case ringorder_dp:
1854 case ringorder_wp:
1855 case ringorder_ds:
1856 case ringorder_ws:
1857 case ringorder_ls:
1858 case ringorder_unspec:
1859 if (r->order[1] == ringorder_C
1860 || r->order[0] == ringorder_unspec)
1861 return rOrderType_ExpComp;
1862 return rOrderType_Exp;
1863
1864 default:
1865 assume(r->order[0] == ringorder_lp ||
1866 r->order[0] == ringorder_rs ||
1867 r->order[0] == ringorder_Dp ||
1868 r->order[0] == ringorder_Wp ||
1869 r->order[0] == ringorder_Ds ||
1870 r->order[0] == ringorder_Ws);
1871
1872 if (r->order[1] == ringorder_c) return rOrderType_ExpComp;
1873 return rOrderType_Exp;
1874 }
1875 }
1876 else
1877 {
1878 assume((r->order[0]==ringorder_c)||(r->order[0]==ringorder_C));
1879 return rOrderType_CompExp;
1880 }
1881 }
1882 else
1883 return rOrderType_General;
1884}
1885
1887{
1888 return (r->order[0] == ringorder_c);
1889}
1891{
1892 if (r->order[0] == ringorder_unspec) return TRUE;
1893 int blocks = rBlocks(r) - 1;
1894 assume(blocks >= 1);
1895 if (blocks == 1) return TRUE;
1896
1897 int s = 0;
1898 while( (s < blocks) && (r->order[s] == ringorder_IS) && (r->order[blocks-1] == ringorder_IS) )
1899 {
1900 s++;
1901 blocks--;
1902 }
1903
1904 if ((blocks - s) > 2) return FALSE;
1905
1906 assume( blocks == s + 2 );
1907
1908 if (
1909 (r->order[s] != ringorder_c)
1910 && (r->order[s] != ringorder_C)
1911 && (r->order[s+1] != ringorder_c)
1912 && (r->order[s+1] != ringorder_C)
1913 )
1914 return FALSE;
1915 if ((r->order[s+1] == ringorder_M)
1916 || (r->order[s] == ringorder_M))
1917 return FALSE;
1918 return TRUE;
1919}
1920
1922{
1923 if (r->order[0] == ringorder_s) return FALSE;
1924 int s=0;
1925 if ((r->order[0] == ringorder_c)
1926 || (r->order[0] == ringorder_C)) s=1;
1927
1928 if ((r->block0[s]!=1)||(r->block1[s]!=r->N))
1929 return TRUE;
1930 if ((r->order[s] == ringorder_aa)
1931 || (r->order[s] == ringorder_lp)
1932 || (r->order[s] == ringorder_rp)
1933 || (r->order[s] == ringorder_ls)
1934 || (r->order[s] == ringorder_rs))
1935 return TRUE;
1936 return FALSE;
1937}
1938
1939// returns TRUE, if simple lp or ls ordering
1941{
1942 return rHasSimpleOrder(r) &&
1943 (r->order[0] == ringorder_ls ||
1944 r->order[0] == ringorder_lp ||
1945 r->order[1] == ringorder_ls ||
1946 r->order[1] == ringorder_lp);
1947}
1948
1950{
1951 switch(order)
1952 {
1953 case ringorder_dp:
1954 case ringorder_Dp:
1955 case ringorder_ds:
1956 case ringorder_Ds:
1957 case ringorder_Ws:
1958 case ringorder_Wp:
1959 case ringorder_ws:
1960 case ringorder_wp:
1961 return TRUE;
1962
1963 default:
1964 return FALSE;
1965 }
1966}
1967
1969{
1970 switch(order)
1971 {
1972 case ringorder_Ws:
1973 case ringorder_Wp:
1974 case ringorder_ws:
1975 case ringorder_wp:
1976 return TRUE;
1977
1978 default:
1979 return FALSE;
1980 }
1981}
1982
1984{
1985 if (r->order[0] == ringorder_unspec) return TRUE;
1986 int blocks = rBlocks(r) - 1;
1987 assume(blocks >= 1);
1988 if (blocks == 1) return TRUE;
1989
1990 int s = 0;
1991 while( (s < blocks) && (r->order[s] == ringorder_IS) && (r->order[blocks-1] == ringorder_IS) )
1992 {
1993 s++;
1994 blocks--;
1995 }
1996
1997 if ((blocks - s) > 3) return FALSE;
1998
1999// if ((blocks > 3) || (blocks < 2)) return FALSE;
2000 if ((blocks - s) == 3)
2001 {
2002 return (((r->order[s] == ringorder_aa) && (r->order[s+1] != ringorder_M) &&
2003 ((r->order[s+2] == ringorder_c) || (r->order[s+2] == ringorder_C))) ||
2004 (((r->order[s] == ringorder_c) || (r->order[s] == ringorder_C)) &&
2005 (r->order[s+1] == ringorder_aa) && (r->order[s+2] != ringorder_M)));
2006 }
2007 else
2008 {
2009 return ((r->order[s] == ringorder_aa) && (r->order[s+1] != ringorder_M));
2010 }
2011}
2012
2013// return TRUE if p_SetComp requires p_Setm
2015{
2016 if (r->typ != NULL)
2017 {
2018 int pos;
2019 for (pos=0;pos<r->OrdSize;pos++)
2020 {
2021 sro_ord* o=&(r->typ[pos]);
2022 if ( (o->ord_typ == ro_syzcomp)
2023 || (o->ord_typ == ro_syz)
2024 || (o->ord_typ == ro_is)
2025 || (o->ord_typ == ro_am)
2026 || (o->ord_typ == ro_isTemp))
2027 return TRUE;
2028 }
2029 }
2030 return FALSE;
2031}
2032
2033// return TRUE if p->exp[r->pOrdIndex] holds total degree of p */
2035{
2036 // Hmm.... what about Syz orderings?
2037 return ((rVar(r) > 1) &&
2038 ((rHasSimpleOrder(r) &&
2039 ((rOrder_is_DegOrdering((rRingOrder_t)r->order[0]) ||
2040 rOrder_is_DegOrdering(( rRingOrder_t)r->order[1])))) ||
2041 ((rHasSimpleOrderAA(r) &&
2042 (rOrder_is_DegOrdering((rRingOrder_t)r->order[1]) ||
2043 ((r->order[1]!=0) &&
2044 rOrder_is_DegOrdering((rRingOrder_t)r->order[2])))))));
2045}
2046
2048{
2049 int ord=0;
2050 if ((r->order[0]==ringorder_C)||(r->order[0]==ringorder_c)) ord=1;
2051 return ((rVar(r) > 1) &&
2052 (r->order[ord]==ringorder_dp)
2053 &&(r->block0[ord]==1)
2054 &&(r->block1[ord]==r->N));
2055}
2056
2058{
2059 int ord=0;
2060 if ((r->order[0]==ringorder_C)||(r->order[0]==ringorder_c)) ord=1;
2061 return ((rVar(r) > 1) &&
2062 (r->order[ord]==ringorder_ds)
2063 &&(r->block0[ord]==1)
2064 &&(r->block1[ord]==r->N));
2065}
2066
2068{
2069 int ord=0;
2070 if ((r->order[0]==ringorder_C)||(r->order[0]==ringorder_c)) ord=1;
2071 return ((rVar(r) > 1) &&
2072 (r->order[ord]==ringorder_Ds)
2073 &&(r->block0[ord]==1)
2074 &&(r->block1[ord]==r->N));
2075}
2076
2077// return TRUE if p->exp[r->pOrdIndex] holds a weighted degree of p */
2079{
2080 // Hmm.... what about Syz orderings?
2081 return ((rVar(r) > 1) &&
2082 rHasSimpleOrder(r) &&
2085}
2086
2087#ifdef RDEBUG
2088// This should eventually become a full-fledge ring check, like pTest
2089BOOLEAN rDBTest(ring r, const char* fn, const int l)
2090{
2091 int i,j;
2092
2093 if (r == NULL)
2094 {
2095 dReportError("Null ring in %s:%d", fn, l);
2096 return FALSE;
2097 }
2098
2099
2100 if (r->N == 0) return TRUE;
2101
2102 if ((r->OrdSgn!=1) && (r->OrdSgn!= -1))
2103 {
2104 dReportError("missing OrdSgn in %s:%d", fn, l);
2105 return FALSE;
2106 }
2107
2108// omCheckAddrSize(r,sizeof(ip_sring));
2109#if OM_CHECK > 0
2110 i=rBlocks(r);
2111 omCheckAddrSize(r->order,i*sizeof(int));
2112 omCheckAddrSize(r->block0,i*sizeof(int));
2113 omCheckAddrSize(r->block1,i*sizeof(int));
2114 for(int j=0;j<=i;j++)
2115 {
2116 if((r->order[j]<0)||(r->order[j]>ringorder_unspec))
2117 dError("wrong order in r->order");
2118 }
2119 if (r->wvhdl!=NULL)
2120 {
2121 omCheckAddrSize(r->wvhdl,i*sizeof(int *));
2122 for (j=0;j<i; j++)
2123 {
2124 if (r->wvhdl[j] != NULL) omCheckAddr(r->wvhdl[j]);
2125 }
2126 }
2127#endif
2128 if (r->VarOffset == NULL)
2129 {
2130 dReportError("Null ring VarOffset -- no rComplete (?) in n %s:%d", fn, l);
2131 return FALSE;
2132 }
2133 omCheckAddrSize(r->VarOffset,(r->N+1)*sizeof(int));
2134
2135 if ((r->OrdSize==0)!=(r->typ==NULL))
2136 {
2137 dReportError("mismatch OrdSize and typ-pointer in %s:%d");
2138 return FALSE;
2139 }
2140 omcheckAddrSize(r->typ,r->OrdSize*sizeof(*(r->typ)));
2141 omCheckAddrSize(r->VarOffset,(r->N+1)*sizeof(*(r->VarOffset)));
2142 // test assumptions:
2143 for(i=0;i<=r->N;i++) // for all variables (i = 0..N)
2144 {
2145 if(r->typ!=NULL)
2146 {
2147 for(j=0;j<r->OrdSize;j++) // for all ordering blocks (j =0..OrdSize-1)
2148 {
2149 if(r->typ[j].ord_typ == ro_isTemp)
2150 {
2151 const int p = r->typ[j].data.isTemp.suffixpos;
2152
2153 if(p <= j)
2154 dReportError("ordrec prefix %d is unmatched",j);
2155
2156 assume( p < r->OrdSize );
2157
2158 if(r->typ[p].ord_typ != ro_is)
2159 dReportError("ordrec prefix %d is unmatched (suffix: %d is wrong!!!)",j, p);
2160
2161 // Skip all intermediate blocks for undone variables:
2162 if(r->typ[j].data.isTemp.pVarOffset[i] != -1) // Check i^th variable
2163 {
2164 j = p - 1; // SKIP ALL INTERNAL BLOCKS...???
2165 continue; // To make for check OrdSize bound...
2166 }
2167 }
2168 else if (r->typ[j].ord_typ == ro_is)
2169 {
2170 // Skip all intermediate blocks for undone variables:
2171 if(r->typ[j].data.is.pVarOffset[i] != -1)
2172 {
2173 // TODO???
2174 }
2175
2176 }
2177 else
2178 {
2179 if (r->typ[j].ord_typ==ro_cp)
2180 {
2181 if(((short)r->VarOffset[i]) == r->typ[j].data.cp.place)
2182 dReportError("ordrec %d conflicts with var %d",j,i);
2183 }
2184 else
2185 if ((r->typ[j].ord_typ!=ro_syzcomp)
2186 && (r->VarOffset[i] == r->typ[j].data.dp.place))
2187 dReportError("ordrec %d conflicts with var %d",j,i);
2188 }
2189 }
2190 }
2191 int tmp;
2192 tmp=r->VarOffset[i] & 0xffffff;
2193 #if SIZEOF_LONG == 8
2194 if ((r->VarOffset[i] >> 24) >63)
2195 #else
2196 if ((r->VarOffset[i] >> 24) >31)
2197 #endif
2198 dReportError("bit_start out of range:%d",r->VarOffset[i] >> 24);
2199 if (i > 0 && ((tmp<0) ||(tmp>r->ExpL_Size-1)))
2200 {
2201 dReportError("varoffset out of range for var %d: %d",i,tmp);
2202 }
2203 }
2204 if(r->typ!=NULL)
2205 {
2206 for(j=0;j<r->OrdSize;j++)
2207 {
2208 if ((r->typ[j].ord_typ==ro_dp)
2209 || (r->typ[j].ord_typ==ro_wp)
2210 || (r->typ[j].ord_typ==ro_wp_neg))
2211 {
2212 if (r->typ[j].data.dp.start > r->typ[j].data.dp.end)
2213 dReportError("in ordrec %d: start(%d) > end(%d)",j,
2214 r->typ[j].data.dp.start, r->typ[j].data.dp.end);
2215 if ((r->typ[j].data.dp.start < 1)
2216 || (r->typ[j].data.dp.end > r->N))
2217 dReportError("in ordrec %d: start(%d)<1 or end(%d)>vars(%d)",j,
2218 r->typ[j].data.dp.start, r->typ[j].data.dp.end,r->N);
2219 }
2220 }
2221 }
2222
2223 assume(r != NULL);
2224 assume(r->cf != NULL);
2225
2226 if (nCoeff_is_algExt(r->cf))
2227 {
2228 assume(r->cf->extRing != NULL);
2229 assume(r->cf->extRing->qideal != NULL);
2230 omCheckAddr(r->cf->extRing->qideal->m[0]);
2231 }
2232
2233 //assume(r->cf!=NULL);
2234
2235 return TRUE;
2236}
2237#endif
2238
2239static void rO_Align(int &place, int &bitplace)
2240{
2241 // increment place to the next aligned one
2242 // (count as Exponent_t,align as longs)
2244 {
2245 place++;
2247 }
2248}
2249
2250static void rO_TDegree(int &place, int &bitplace, int start, int end,
2251 long *o, sro_ord &ord_struct)
2252{
2253 // degree (aligned) of variables v_start..v_end, ordsgn 1
2254 rO_Align(place,bitplace);
2255 ord_struct.ord_typ=ro_dp;
2256 ord_struct.data.dp.start=start;
2257 ord_struct.data.dp.end=end;
2258 ord_struct.data.dp.place=place;
2259 o[place]=1;
2260 place++;
2261 rO_Align(place,bitplace);
2262}
2263
2264static void rO_TDegree_neg(int &place, int &bitplace, int start, int end,
2265 long *o, sro_ord &ord_struct)
2266{
2267 // degree (aligned) of variables v_start..v_end, ordsgn -1
2268 rO_Align(place,bitplace);
2269 ord_struct.ord_typ=ro_dp;
2270 ord_struct.data.dp.start=start;
2271 ord_struct.data.dp.end=end;
2272 ord_struct.data.dp.place=place;
2273 o[place]=-1;
2274 place++;
2275 rO_Align(place,bitplace);
2276}
2277
2278static void rO_WDegree(int &place, int &bitplace, int start, int end,
2279 long *o, sro_ord &ord_struct, int *weights)
2280{
2281 // weighted degree (aligned) of variables v_start..v_end, ordsgn 1
2282 while((start<end) && (weights[0]==0)) { start++; weights++; }
2283 while((start<end) && (weights[end-start]==0)) { end--; }
2284 int i;
2285 int pure_tdeg=1;
2286 for(i=start;i<=end;i++)
2287 {
2288 if(weights[i-start]!=1)
2289 {
2290 pure_tdeg=0;
2291 break;
2292 }
2293 }
2294 if (pure_tdeg)
2295 {
2296 rO_TDegree(place,bitplace,start,end,o,ord_struct);
2297 return;
2298 }
2299 rO_Align(place,bitplace);
2300 ord_struct.ord_typ=ro_wp;
2301 ord_struct.data.wp.start=start;
2302 ord_struct.data.wp.end=end;
2303 ord_struct.data.wp.place=place;
2304 ord_struct.data.wp.weights=weights;
2305 o[place]=1;
2306 place++;
2307 rO_Align(place,bitplace);
2308 for(i=start;i<=end;i++)
2309 {
2310 if(weights[i-start]<0)
2311 {
2312 ord_struct.ord_typ=ro_wp_neg;
2313 break;
2314 }
2315 }
2316}
2317
2318static void rO_WMDegree(int &place, int &bitplace, int start, int end,
2319 long *o, sro_ord &ord_struct, int *weights)
2320{
2321 assume(weights != NULL);
2322
2323 // weighted degree (aligned) of variables v_start..v_end, ordsgn 1
2324// while((start<end) && (weights[0]==0)) { start++; weights++; }
2325// while((start<end) && (weights[end-start]==0)) { end--; }
2326 rO_Align(place,bitplace);
2327 ord_struct.ord_typ=ro_am;
2328 ord_struct.data.am.start=start;
2329 ord_struct.data.am.end=end;
2330 ord_struct.data.am.place=place;
2331 ord_struct.data.am.weights=weights;
2332 ord_struct.data.am.weights_m = weights + (end-start+1);
2333 ord_struct.data.am.len_gen=weights[end-start+1];
2334 assume( ord_struct.data.am.weights_m[0] == ord_struct.data.am.len_gen );
2335 o[place]=1;
2336 place++;
2337 rO_Align(place,bitplace);
2338}
2339
2340static void rO_WDegree64(int &place, int &bitplace, int start, int end,
2341 long *o, sro_ord &ord_struct, int64 *weights)
2342{
2343 // weighted degree (aligned) of variables v_start..v_end, ordsgn 1,
2344 // reserved 2 places
2345 rO_Align(place,bitplace);
2346 ord_struct.ord_typ=ro_wp64;
2347 ord_struct.data.wp64.start=start;
2348 ord_struct.data.wp64.end=end;
2349 ord_struct.data.wp64.place=place;
2350 #ifdef HAVE_OMALLOC
2351 ord_struct.data.wp64.weights64=weights;
2352 #else
2353 int l=end-start+1;
2354 ord_struct.data.wp64.weights64=(int64*)omAlloc(l*sizeof(int64));
2355 for(int i=0;i<l;i++) ord_struct.data.wp64.weights64[i]=weights[i];
2356 #endif
2357 o[place]=1;
2358 place++;
2359 o[place]=1;
2360 place++;
2361 rO_Align(place,bitplace);
2362}
2363
2364static void rO_WDegree_neg(int &place, int &bitplace, int start, int end,
2365 long *o, sro_ord &ord_struct, int *weights)
2366{
2367 // weighted degree (aligned) of variables v_start..v_end, ordsgn -1
2368 while((start<end) && (weights[0]==0)) { start++; weights++; }
2369 while((start<end) && (weights[end-start]==0)) { end--; }
2370 rO_Align(place,bitplace);
2371 ord_struct.ord_typ=ro_wp;
2372 ord_struct.data.wp.start=start;
2373 ord_struct.data.wp.end=end;
2374 ord_struct.data.wp.place=place;
2375 ord_struct.data.wp.weights=weights;
2376 o[place]=-1;
2377 place++;
2378 rO_Align(place,bitplace);
2379 int i;
2380 for(i=start;i<=end;i++)
2381 {
2382 if(weights[i-start]<0)
2383 {
2384 ord_struct.ord_typ=ro_wp_neg;
2385 break;
2386 }
2387 }
2388}
2389
2390static void rO_LexVars(int &place, int &bitplace, int start, int end,
2391 int &prev_ord, long *o,int *v, int bits, int opt_var)
2392{
2393 // a block of variables v_start..v_end with lex order, ordsgn 1
2394 int k;
2395 int incr=1;
2396 if(prev_ord==-1) rO_Align(place,bitplace);
2397
2398 if (start>end)
2399 {
2400 incr=-1;
2401 }
2402 for(k=start;;k+=incr)
2403 {
2404 bitplace-=bits;
2405 if (bitplace < 0) { bitplace=BITS_PER_LONG-bits; place++; }
2406 o[place]=1;
2407 v[k]= place | (bitplace << 24);
2408 if (k==end) break;
2409 }
2410 prev_ord=1;
2411 if (opt_var!= -1)
2412 {
2413 assume((opt_var == end+1) ||(opt_var == end-1));
2414 if((opt_var != end+1) &&(opt_var != end-1)) WarnS("hier-2");
2416 bitplace-=bits;
2417 if (bitplace < 0)
2418 {
2420 return;
2421 }
2422 // there is enough space for the optional var
2423 v[opt_var]=place | (bitplace << 24);
2424 }
2425}
2426
2427static void rO_LexVars_neg(int &place, int &bitplace, int start, int end,
2428 int &prev_ord, long *o,int *v, int bits, int opt_var)
2429{
2430 // a block of variables v_start..v_end with lex order, ordsgn -1
2431 int k;
2432 int incr=1;
2433 if(prev_ord==1) rO_Align(place,bitplace);
2434
2435 if (start>end)
2436 {
2437 incr=-1;
2438 }
2439 for(k=start;;k+=incr)
2440 {
2441 bitplace-=bits;
2442 if (bitplace < 0) { bitplace=BITS_PER_LONG-bits; place++; }
2443 o[place]=-1;
2444 v[k]=place | (bitplace << 24);
2445 if (k==end) break;
2446 }
2447 prev_ord=-1;
2448// #if 0
2449 if (opt_var!= -1)
2450 {
2451 assume((opt_var == end+1) ||(opt_var == end-1));
2452 if((opt_var != end+1) &&(opt_var != end-1)) WarnS("hier-1");
2454 bitplace-=bits;
2455 if (bitplace < 0)
2456 {
2458 return;
2459 }
2460 // there is enough space for the optional var
2461 v[opt_var]=place | (bitplace << 24);
2462 }
2463// #endif
2464}
2465
2466static void rO_Syzcomp(int &place, int &bitplace, int &prev_ord,
2467 long *o, sro_ord &ord_struct)
2468{
2469 // ordering is derived from component number
2470 rO_Align(place,bitplace);
2471 ord_struct.ord_typ=ro_syzcomp;
2472 ord_struct.data.syzcomp.place=place;
2473 ord_struct.data.syzcomp.Components=NULL;
2474 ord_struct.data.syzcomp.ShiftedComponents=NULL;
2475 o[place]=1;
2476 prev_ord=1;
2477 place++;
2478 rO_Align(place,bitplace);
2479}
2480
2481static void rO_Syz(int &place, int &bitplace, int &prev_ord,
2482 int syz_comp, long *o, sro_ord &ord_struct)
2483{
2484 // ordering is derived from component number
2485 // let's reserve one Exponent_t for it
2486 if ((prev_ord== 1) || (bitplace!=BITS_PER_LONG))
2487 rO_Align(place,bitplace);
2488 ord_struct.ord_typ=ro_syz;
2489 ord_struct.data.syz.place=place;
2490 ord_struct.data.syz.limit=syz_comp;
2491 if (syz_comp>0)
2492 ord_struct.data.syz.syz_index = (int*) omAlloc0((syz_comp+1)*sizeof(int));
2493 else
2494 ord_struct.data.syz.syz_index = NULL;
2495 ord_struct.data.syz.curr_index = 1;
2496 o[place]= -1;
2497 prev_ord=-1;
2498 place++;
2499}
2500
2501#ifndef SING_NDEBUG
2502# define MYTEST 0
2503#else /* ifndef SING_NDEBUG */
2504# define MYTEST 0
2505#endif /* ifndef SING_NDEBUG */
2506
2507static void rO_ISPrefix(int &place, int &bitplace, int &prev_ord,
2508 long *o, int N, int *v, sro_ord &ord_struct)
2509{
2510 if ((prev_ord== 1) || (bitplace!=BITS_PER_LONG))
2511 rO_Align(place,bitplace);
2512 // since we add something afterwards - it's better to start with anew!?
2513
2514 ord_struct.ord_typ = ro_isTemp;
2515 ord_struct.data.isTemp.start = place;
2516 #ifdef HAVE_OMALLOC
2517 ord_struct.data.isTemp.pVarOffset = (int *)omMemDup(v);
2518 #else
2519 ord_struct.data.isTemp.pVarOffset = (int *)omAlloc((N+1)*sizeof(int));
2520 memcpy(ord_struct.data.isTemp.pVarOffset,v,(N+1)*sizeof(int));
2521 #endif
2522 ord_struct.data.isTemp.suffixpos = -1;
2523
2524 // We will act as rO_Syz on our own!!!
2525 // Here we allocate an exponent as a level placeholder
2526 o[place]= -1;
2527 prev_ord=-1;
2528 place++;
2529}
2530static void rO_ISSuffix(int &place, int &bitplace, int &prev_ord, long *o,
2531 int N, int *v, sro_ord *tmp_typ, int &typ_i, int sgn)
2532{
2533
2534 // Let's find previous prefix:
2535 int typ_j = typ_i - 1;
2536 while(typ_j >= 0)
2537 {
2538 if( tmp_typ[typ_j].ord_typ == ro_isTemp)
2539 break;
2540 typ_j --;
2541 }
2542
2543 assume( typ_j >= 0 );
2544
2545 if( typ_j < 0 ) // Found NO prefix!!! :(
2546 return;
2547
2548 assume( tmp_typ[typ_j].ord_typ == ro_isTemp );
2549
2550 // Get saved state:
2551 const int start = tmp_typ[typ_j].data.isTemp.start;
2552 int *pVarOffset = tmp_typ[typ_j].data.isTemp.pVarOffset;
2553
2554/*
2555 // shift up all blocks
2556 while(typ_j < (typ_i-1))
2557 {
2558 tmp_typ[typ_j] = tmp_typ[typ_j+1];
2559 typ_j++;
2560 }
2561 typ_j = typ_i - 1; // No increment for typ_i
2562*/
2563 tmp_typ[typ_j].data.isTemp.suffixpos = typ_i;
2564
2565 // Let's keep that dummy for now...
2566 typ_j = typ_i; // the typ to change!
2567 typ_i++; // Just for now...
2568
2569
2570 for( int i = 0; i <= N; i++ ) // Note [0] == component !!! No Skip?
2571 {
2572 // Was i-th variable allocated in between?
2573 if( v[i] != pVarOffset[i] )
2574 {
2575 pVarOffset[i] = v[i]; // Save for later...
2576 v[i] = -1; // Undo!
2577 assume( pVarOffset[i] != -1 );
2578 }
2579 else
2580 pVarOffset[i] = -1; // No change here...
2581 }
2582
2583 if( pVarOffset[0] != -1 )
2584 pVarOffset[0] &= 0x0fff;
2585
2587
2588
2589 ord_struct.ord_typ = ro_is;
2590 ord_struct.data.is.start = start;
2591 ord_struct.data.is.end = place;
2592 ord_struct.data.is.pVarOffset = pVarOffset;
2593
2594
2595 // What about component???
2596// if( v[0] != -1 ) // There is a component already...???
2597// if( o[ v[0] & 0x0fff ] == sgn )
2598// {
2599// pVarOffset[0] = -1; // NEVER USED Afterwards...
2600// return;
2601// }
2602
2603
2604 // Moreover: we need to allocate the module component (v[0]) here!
2605 if( v[0] == -1) // It's possible that there was module component v0 at the beginning (before prefix)!
2606 {
2607 // Start with a whole long exponent
2608 if( bitplace != BITS_PER_LONG )
2609 rO_Align(place, bitplace);
2610
2613 assume(bitplace == 0);
2614 v[0] = place | (bitplace << 24); // Never mind whether pVarOffset[0] > 0!!!
2615 o[place] = sgn; // Singnum for component ordering
2616 prev_ord = sgn;
2617 }
2618}
2619
2620
2621static unsigned long rGetExpSize(unsigned long bitmask, int & bits)
2622{
2623 if (bitmask == 0)
2624 {
2625 bits=16; bitmask=0xffff;
2626 }
2627 else if (bitmask <= 1L)
2628 {
2629 bits=1; bitmask = 1L;
2630 }
2631 else if (bitmask <= 3L)
2632 {
2633 bits=2; bitmask = 3L;
2634 }
2635 else if (bitmask <= 7L)
2636 {
2637 bits=3; bitmask=7L;
2638 }
2639 else if (bitmask <= 0xfL)
2640 {
2641 bits=4; bitmask=0xfL;
2642 }
2643 else if (bitmask <= 0x1fL)
2644 {
2645 bits=5; bitmask=0x1fL;
2646 }
2647 else if (bitmask <= 0x3fL)
2648 {
2649 bits=6; bitmask=0x3fL;
2650 }
2651#if SIZEOF_LONG == 8
2652 else if (bitmask <= 0x7fL)
2653 {
2654 bits=7; bitmask=0x7fL; /* 64 bit longs only */
2655 }
2656#endif
2657 else if (bitmask <= 0xffL)
2658 {
2659 bits=8; bitmask=0xffL;
2660 }
2661#if SIZEOF_LONG == 8
2662 else if (bitmask <= 0x1ffL)
2663 {
2664 bits=9; bitmask=0x1ffL; /* 64 bit longs only */
2665 }
2666#endif
2667 else if (bitmask <= 0x3ffL)
2668 {
2669 bits=10; bitmask=0x3ffL;
2670 }
2671#if SIZEOF_LONG == 8
2672 else if (bitmask <= 0xfffL)
2673 {
2674 bits=12; bitmask=0xfff; /* 64 bit longs only */
2675 }
2676#endif
2677 else if (bitmask <= 0xffffL)
2678 {
2679 bits=16; bitmask=0xffffL;
2680 }
2681#if SIZEOF_LONG == 8
2682 else if (bitmask <= 0xfffffL)
2683 {
2684 bits=20; bitmask=0xfffffL; /* 64 bit longs only */
2685 }
2686 else if (bitmask <= 0xffffffffL)
2687 {
2688 bits=32; bitmask=0xffffffffL;
2689 }
2690 else if (bitmask <= 0x7fffffffffffffffL)
2691 {
2692 bits=63; bitmask=0x7fffffffffffffffL; /* for overflow tests*/
2693 }
2694 else
2695 {
2696 bits=63; bitmask=0x7fffffffffffffffL; /* for overflow tests*/
2697 }
2698#else
2699 else if (bitmask <= 0x7fffffff)
2700 {
2701 bits=31; bitmask=0x7fffffff; /* for overflow tests*/
2702 }
2703 else
2704 {
2705 bits=31; bitmask=0x7fffffffL; /* for overflow tests*/
2706 }
2707#endif
2708 return bitmask;
2709}
2710
2711/*2
2712* optimize rGetExpSize for a block of N variables, exp <=bitmask
2713*/
2714unsigned long rGetExpSize(unsigned long bitmask, int & bits, int N)
2715{
2716 bitmask =rGetExpSize(bitmask, bits);
2718 int bits1;
2719 loop
2720 {
2721 if (bits == BIT_SIZEOF_LONG-1)
2722 {
2723 bits = BIT_SIZEOF_LONG - 1;
2724 return LONG_MAX;
2725 }
2726 unsigned long bitmask1 =rGetExpSize(bitmask+1, bits1);
2728 if ((((N+vars_per_long-1)/vars_per_long) ==
2730 {
2732 bits=bits1;
2733 bitmask=bitmask1;
2734 }
2735 else
2736 {
2737 return bitmask; /* and bits */
2738 }
2739 }
2740}
2741
2742
2743/*2
2744 * create a copy of the ring r, which must be equivalent to currRing
2745 * used for std computations
2746 * may share data structures with currRing
2747 * DOES CALL rComplete
2748 */
2751 unsigned long exp_limit)
2752{
2753 assume (r != NULL );
2754 assume (exp_limit > 1);
2756
2757 int bits;
2759 BOOLEAN need_other_ring = (exp_limit != r->bitmask);
2760
2761 int iNeedInducedOrderingSetup = 0; ///< How many induced ordering block do we have?
2762
2763 int nblocks=rBlocks(r);
2765 int *block0=(int*)omAlloc0((nblocks+1)*sizeof(int));
2766 int *block1=(int*)omAlloc0((nblocks+1)*sizeof(int));
2767 int **wvhdl=(int**)omAlloc0((nblocks+1)*sizeof(int *));
2768
2769 int i=0;
2770 int j=0; /* i index in r, j index in res */
2771
2772 for( rRingOrder_t r_ord=r->order[i]; (r_ord != (rRingOrder_t)0) && (i < nblocks); j++, r_ord=r->order[++i])
2773 {
2775
2776 if (r->block0[i]==r->block1[i])
2777 {
2778 switch(r_ord)
2779 {
2780 case ringorder_wp:
2781 case ringorder_dp:
2782 case ringorder_Wp:
2783 case ringorder_Dp:
2785 break;
2786 case ringorder_Ws:
2787 case ringorder_Ds:
2788 case ringorder_ws:
2789 case ringorder_ds:
2791 break;
2792 default:
2793 break;
2794 }
2795 }
2796 switch(r_ord)
2797 {
2798 case ringorder_S:
2799 {
2800#ifndef SING_NDEBUG
2801 Warn("Error: unhandled ordering in rModifyRing: ringorder_S = [%d]", r_ord);
2802#endif
2803 order[j]=r_ord; /*r->order[i];*/
2804 break;
2805 }
2806 case ringorder_C:
2807 case ringorder_c:
2808 if (!try_omit_comp)
2809 {
2810 order[j]=r_ord; /*r->order[i]*/;
2811 }
2812 else
2813 {
2814 j--;
2818 }
2819 break;
2820 case ringorder_wp:
2821 case ringorder_dp:
2822 case ringorder_ws:
2823 case ringorder_ds:
2824 if(!omit_degree)
2825 {
2826 order[j]=r_ord; /*r->order[i]*/;
2827 }
2828 else
2829 {
2830 order[j]=ringorder_rs;
2834 }
2835 break;
2836 case ringorder_Wp:
2837 case ringorder_Dp:
2838 case ringorder_Ws:
2839 case ringorder_Ds:
2840 if(!omit_degree)
2841 {
2842 order[j]=r_ord; /*r->order[i];*/
2843 }
2844 else
2845 {
2846 order[j]=ringorder_lp;
2850 }
2851 break;
2852 case ringorder_IS:
2853 {
2854 if (try_omit_comp)
2855 {
2856 // tried, but cannot omit component due to the ordering block [%d]: %d (ringorder_IS)", i, r_ord
2858 }
2859 order[j]=r_ord; /*r->order[i];*/
2861 break;
2862 }
2863 case ringorder_s:
2864 {
2865 assume((i == 0) && (j == 0));
2866 if (try_omit_comp)
2867 {
2868 // tried, but cannot omit component due to the ordering block [%d]: %d (ringorder_s)", i, r_ord
2870 }
2871 order[j]=r_ord; /*r->order[i];*/
2872 break;
2873 }
2874 default:
2875 order[j]=r_ord; /*r->order[i];*/
2876 break;
2877 }
2878 if (copy_block_index)
2879 {
2880 block0[j]=r->block0[i];
2881 block1[j]=r->block1[i];
2882 wvhdl[j]=r->wvhdl[i];
2883 }
2884
2885 // order[j]=ringorder_no; // done by omAlloc0
2886 }
2887 if(!need_other_ring)
2888 {
2889 omFreeSize(order,(nblocks+1)*sizeof(rRingOrder_t));
2890 omFreeSize(block0,(nblocks+1)*sizeof(int));
2891 omFreeSize(block1,(nblocks+1)*sizeof(int));
2892 omFreeSize(wvhdl,(nblocks+1)*sizeof(int *));
2893 return r;
2894 }
2896 *res = *r; // includes r->options
2897
2898#ifdef HAVE_PLURAL
2899 res->GetNC() = NULL;// to re-create it
2900#endif
2901
2902 // res->qideal, res->idroot ???
2903 res->wvhdl=wvhdl;
2904 res->order=order;
2905 res->block0=block0;
2906 res->block1=block1;
2907 res->bitmask=exp_limit;
2908 res->wanted_maxExp=r->wanted_maxExp;
2909 //int tmpref=r->cf->ref0;
2910 rComplete(res, 1);
2911 //r->cf->ref=tmpref;
2912
2913 // adjust res->pFDeg: if it was changed globally, then
2914 // it must also be changed for new ring
2915 if (r->pFDegOrig != res->pFDegOrig &&
2917 {
2918 // still might need adjustment for weighted orderings
2919 // and omit_degree
2920 res->firstwv = r->firstwv;
2921 res->firstBlockEnds = r->firstBlockEnds;
2922 res->pFDeg = res->pFDegOrig = p_WFirstTotalDegree;
2923 }
2924 if (omitted_degree)
2925 res->pLDeg = r->pLDegOrig;
2926
2927 rOptimizeLDeg(res); // also sets res->pLDegOrig
2928
2929 // set syzcomp
2930 if (res->typ != NULL)
2931 {
2932 if( res->typ[0].ord_typ == ro_syz) // "s" Always on [0] place!
2933 {
2934 res->typ[0] = r->typ[0]; // Copy struct!? + setup the same limit!
2935
2936 if (r->typ[0].data.syz.limit > 0)
2937 {
2938 res->typ[0].data.syz.syz_index
2939 = (int*) omAlloc((r->typ[0].data.syz.limit +1)*sizeof(int));
2940 memcpy(res->typ[0].data.syz.syz_index, r->typ[0].data.syz.syz_index,
2941 (r->typ[0].data.syz.limit +1)*sizeof(int));
2942 }
2943 }
2944
2946 {
2947 for(j = 0, i = 0; (i < nblocks) && (iNeedInducedOrderingSetup > 0); i++)
2948 if( res->typ[i].ord_typ == ro_is ) // Search for suffixes!
2949 {
2950 ideal F = idrHeadR(r->typ[i].data.is.F, r, res); // Copy F from r into res!
2951 assume(
2953 F, // WILL BE COPIED!
2954 r->typ[i].data.is.limit,
2955 j++
2956 )
2957 );
2958 id_Delete(&F, res);
2960 }
2961 } // Process all induced Ordering blocks! ...
2962 }
2963 // the special case: homog (omit_degree) and 1 block rs: that is global:
2964 // it comes from dp
2965 res->OrdSgn=r->OrdSgn;
2966
2967
2968#ifdef HAVE_PLURAL
2969 if (rIsPluralRing(r))
2970 {
2971 if ( nc_rComplete(r, res, false) ) // no qideal!
2972 {
2973#ifndef SING_NDEBUG
2974 WarnS("error in nc_rComplete");
2975#endif
2976 // cleanup?
2977
2978// rDelete(res);
2979// return r;
2980
2981 // just go on..
2982 }
2983
2984 if( rIsSCA(r) )
2985 {
2987 WarnS("error in sca_Force!");
2988 }
2989 }
2990#endif
2991
2992 return res;
2993}
2994
2995// construct Wp,C ring
2996ring rModifyRing_Wp(ring r, int* weights)
2997{
2999 *res = *r;
3000#ifdef HAVE_PLURAL
3001 res->GetNC() = NULL;
3002#endif
3003
3004 /*weights: entries for 3 blocks: NULL*/
3005 res->wvhdl = (int **)omAlloc0(3 * sizeof(int *));
3006 /*order: Wp,C,0*/
3007 res->order = (rRingOrder_t *) omAlloc(3 * sizeof(rRingOrder_t *));
3008 res->block0 = (int *)omAlloc0(3 * sizeof(int *));
3009 res->block1 = (int *)omAlloc0(3 * sizeof(int *));
3010 /* ringorder Wp for the first block: var 1..r->N */
3011 res->order[0] = ringorder_Wp;
3012 res->block0[0] = 1;
3013 res->block1[0] = r->N;
3014 res->wvhdl[0] = weights;
3015 /* ringorder C for the second block: no vars */
3016 res->order[1] = ringorder_C;
3017 /* the last block: everything is 0 */
3018 res->order[2] = (rRingOrder_t)0;
3019
3020 //int tmpref=r->cf->ref;
3021 rComplete(res, 1);
3022 //r->cf->ref=tmpref;
3023#ifdef HAVE_PLURAL
3024 if (rIsPluralRing(r))
3025 {
3026 if ( nc_rComplete(r, res, false) ) // no qideal!
3027 {
3028#ifndef SING_NDEBUG
3029 WarnS("error in nc_rComplete");
3030#endif
3031 // cleanup?
3032
3033// rDelete(res);
3034// return r;
3035
3036 // just go on..
3037 }
3038 }
3039#endif
3040 return res;
3041}
3042
3043// construct lp, C ring with r->N variables, r->names vars....
3045{
3046 simple=TRUE;
3047 if (!rHasSimpleOrder(r))
3048 {
3049 simple=FALSE; // sorting needed
3050 assume (r != NULL );
3051 assume (exp_limit > 1);
3052 int bits;
3053
3055
3056 int nblocks=1+(ommit_comp!=0);
3058 int *block0=(int*)omAlloc0((nblocks+1)*sizeof(int));
3059 int *block1=(int*)omAlloc0((nblocks+1)*sizeof(int));
3060 int **wvhdl=(int**)omAlloc0((nblocks+1)*sizeof(int *));
3061
3062 order[0]=ringorder_lp;
3063 block0[0]=1;
3064 block1[0]=r->N;
3065 if (!ommit_comp)
3066 {
3067 order[1]=ringorder_C;
3068 }
3070 *res = *r;
3071#ifdef HAVE_PLURAL
3072 res->GetNC() = NULL;
3073#endif
3074 // res->qideal, res->idroot ???
3075 res->wvhdl=wvhdl;
3076 res->order=order;
3077 res->block0=block0;
3078 res->block1=block1;
3079 res->bitmask=exp_limit;
3080 res->wanted_maxExp=r->wanted_maxExp;
3081 //int tmpref=r->cf->ref;
3082 rComplete(res, 1);
3083 //r->cf->ref=tmpref;
3084
3085#ifdef HAVE_PLURAL
3086 if (rIsPluralRing(r))
3087 {
3088 if ( nc_rComplete(r, res, false) ) // no qideal!
3089 {
3090#ifndef SING_NDEBUG
3091 WarnS("error in nc_rComplete");
3092#endif
3093 // cleanup?
3094
3095// rDelete(res);
3096// return r;
3097
3098 // just go on..
3099 }
3100 }
3101#endif
3102
3104
3105 return res;
3106 }
3108}
3109
3111{
3112 r->qideal=NULL;r->idroot=NULL; // was taken from original
3113 rUnComplete(r);
3114 omFree(r->order);
3115 omFree(r->block0);
3116 omFree(r->block1);
3117 omFree(r->wvhdl);
3119}
3120
3122{
3123 rUnComplete(r);
3124 omFree(r->order);
3125 omFree(r->block0);
3126 omFree(r->block1);
3127 omFree(r->wvhdl[0]);
3128 omFree(r->wvhdl);
3130}
3131
3132static void rSetOutParams(ring r)
3133{
3134 r->VectorOut = (r->order[0] == ringorder_c);
3135 if (rIsNCRing(r))
3136 r->CanShortOut=FALSE;
3137 else
3138 {
3139 r->CanShortOut = TRUE;
3140 int i;
3141 if (rParameter(r)!=NULL)
3142 {
3143 for (i=0;i<rPar(r);i++)
3144 {
3145 if(strlen(rParameter(r)[i])>1)
3146 {
3147 r->CanShortOut=FALSE;
3148 break;
3149 }
3150 }
3151 }
3152 if (r->CanShortOut)
3153 {
3154 int N = r->N;
3155 for (i=(N-1);i>=0;i--)
3156 {
3157 if(r->names[i] != NULL && strlen(r->names[i])>1)
3158 {
3159 r->CanShortOut=FALSE;
3160 break;
3161 }
3162 }
3163 }
3164 }
3165 r->ShortOut = r->CanShortOut;
3166
3167 assume( !( !r->CanShortOut && r->ShortOut ) );
3168}
3169
3170static void rSetFirstWv(ring r, int i, rRingOrder_t* order, int* block0, int* block1, int** wvhdl)
3171{
3172 // cheat for ringorder_aa
3173 if (order[i] == ringorder_aa)
3174 i++;
3175 if(block1[i]!=r->N) r->LexOrder=TRUE;
3176 r->firstBlockEnds=block1[i];
3177 r->firstwv = wvhdl[i];
3178 if ((order[i]== ringorder_ws)
3179 || (order[i]==ringorder_Ws)
3180 || (order[i]== ringorder_wp)
3181 || (order[i]==ringorder_Wp)
3182 || (order[i]== ringorder_a)
3183 /*|| (order[i]==ringorder_A)*/)
3184 {
3185 int j;
3186 for(j=block1[i]-block0[i];j>=0;j--)
3187 {
3188 if (r->firstwv[j]==0) r->LexOrder=TRUE;
3189 }
3190 }
3191 else if (order[i]==ringorder_a64)
3192 {
3193 int j;
3194 int64 *w=rGetWeightVec(r);
3195 for(j=block1[i]-block0[i];j>=0;j--)
3196 {
3197 if (w[j]==0) r->LexOrder=TRUE;
3198 }
3199 }
3200}
3201
3202static void rOptimizeLDeg(ring r)
3203{
3204 if (r->pFDeg == p_Deg)
3205 {
3206 if (r->pLDeg == pLDeg1)
3207 r->pLDeg = pLDeg1_Deg;
3208 if (r->pLDeg == pLDeg1c)
3209 r->pLDeg = pLDeg1c_Deg;
3210 }
3211 else if (r->pFDeg == p_Totaldegree)
3212 {
3213 if (r->pLDeg == pLDeg1)
3214 r->pLDeg = pLDeg1_Totaldegree;
3215 if (r->pLDeg == pLDeg1c)
3216 r->pLDeg = pLDeg1c_Totaldegree;
3217 }
3218 else if (r->pFDeg == p_WFirstTotalDegree)
3219 {
3220 if (r->pLDeg == pLDeg1)
3221 r->pLDeg = pLDeg1_WFirstTotalDegree;
3222 if (r->pLDeg == pLDeg1c)
3223 r->pLDeg = pLDeg1c_WFirstTotalDegree;
3224 }
3225 r->pLDegOrig = r->pLDeg;
3226 if (r->pFDeg == p_WTotaldegree)
3227 { // only c,C,dp,lp,rp: use p_Totaldegree
3228 int i=0;
3229 loop
3230 {
3231 if ((r->order[i]!=ringorder_c)
3232 && (r->order[i]!=ringorder_C)
3233 && (r->order[i]!=ringorder_lp)
3234 && (r->order[i]!=ringorder_rp)
3235 && (r->order[i]!=ringorder_dp)
3236 && (r->order[i]!=ringorder_Dp))
3237 return;
3238 i++;
3239 if (r->order[i]==0) break;
3240 }
3241 r->pFDeg == p_Totaldegree;
3242 }
3243}
3244
3245// set pFDeg, pLDeg, requires OrdSgn already set
3246static void rSetDegStuff(ring r)
3247{
3248 rRingOrder_t* order = r->order;
3249 int* block0 = r->block0;
3250 int* block1 = r->block1;
3251 int** wvhdl = r->wvhdl;
3252
3253 if (order[0]==ringorder_S ||order[0]==ringorder_s || order[0]==ringorder_IS)
3254 {
3255 order++;
3256 block0++;
3257 block1++;
3258 wvhdl++;
3259 }
3260 r->LexOrder = FALSE;
3261 r->pFDeg = p_Totaldegree;
3262 r->pLDeg = (r->OrdSgn == 1 ? pLDegb : pLDeg0);
3263
3264 /*======== ordering type is (am,_) ==================*/
3265 if (order[0]==ringorder_am)
3266 {
3267 for(int ii=block0[0];ii<=block1[0];ii++)
3268 if (wvhdl[0][ii-1]<0) { r->MixedOrder=2;break;}
3269 r->LexOrder=FALSE;
3270 for(int ii=block0[0];ii<=block1[0];ii++)
3271 if (wvhdl[0][ii-1]==0) { r->LexOrder=TRUE;break;}
3272 if ((block0[0]==1)&&(block1[0]==r->N))
3273 {
3274 r->pFDeg = p_Deg;
3275 r->pLDeg = pLDeg1c_Deg;
3276 }
3277 else
3278 {
3279 r->pFDeg = p_WTotaldegree;
3280 r->LexOrder=TRUE;
3281 r->pLDeg = pLDeg1c_WFirstTotalDegree;
3282 }
3283 r->firstwv = wvhdl[0];
3284 }
3285 /*======== ordering type is (_,c) =========================*/
3286 else if ((order[0]==ringorder_unspec) || (order[1] == 0)
3287 ||(
3288 ((order[1]==ringorder_c)||(order[1]==ringorder_C)
3289 ||(order[1]==ringorder_S)
3290 ||(order[1]==ringorder_s))
3291 && (order[0]!=ringorder_M)
3292 && (order[2]==0))
3293 )
3294 {
3295 if (r->OrdSgn == -1) r->pLDeg = pLDeg0c;
3296 if ((order[0] == ringorder_lp)
3297 || (order[0] == ringorder_ls)
3298 || (order[0] == ringorder_rp)
3299 || (order[0] == ringorder_rs))
3300 {
3301 r->LexOrder=TRUE;
3302 r->pLDeg = pLDeg1c;
3303 r->pFDeg = p_Totaldegree;
3304 }
3305 else if ((order[0] == ringorder_a)
3306 || (order[0] == ringorder_wp)
3307 || (order[0] == ringorder_Wp))
3308 {
3309 r->pFDeg = p_WFirstTotalDegree;
3310 }
3311 else if ((order[0] == ringorder_ws)
3312 || (order[0] == ringorder_Ws))
3313 {
3314 for(int ii=block0[0];ii<=block1[0];ii++)
3315 {
3316 if (wvhdl[0][ii-1]<0) { r->MixedOrder=2;break;}
3317 }
3318 if (r->MixedOrder==0)
3319 {
3320 if ((block0[0]==1)&&(block1[0]==r->N))
3321 r->pFDeg = p_WTotaldegree;
3322 else
3323 r->pFDeg = p_WFirstTotalDegree;
3324 }
3325 else
3326 r->pFDeg = p_Totaldegree;
3327 }
3328 r->firstBlockEnds=block1[0];
3329 r->firstwv = wvhdl[0];
3330 }
3331 /*======== ordering type is (c,_) =========================*/
3332 else if (((order[0]==ringorder_c)
3333 ||(order[0]==ringorder_C)
3334 ||(order[0]==ringorder_S)
3335 ||(order[0]==ringorder_s))
3336 && (order[1]!=ringorder_M)
3337 && (order[2]==0))
3338 {
3339 if ((order[1] == ringorder_lp)
3340 || (order[1] == ringorder_ls)
3341 || (order[1] == ringorder_rp)
3342 || order[1] == ringorder_rs)
3343 {
3344 r->LexOrder=TRUE;
3345 r->pLDeg = pLDeg1c;
3346 r->pFDeg = p_Totaldegree;
3347 }
3348 r->firstBlockEnds=block1[1];
3349 if (wvhdl!=NULL) r->firstwv = wvhdl[1];
3350 if ((order[1] == ringorder_a)
3351 || (order[1] == ringorder_wp)
3352 || (order[1] == ringorder_Wp))
3353 r->pFDeg = p_WFirstTotalDegree;
3354 else if ((order[1] == ringorder_ws)
3355 || (order[1] == ringorder_Ws))
3356 {
3357 for(int ii=block0[1];ii<=block1[1];ii++)
3358 if (wvhdl[1][ii-1]<0) { r->MixedOrder=2;break;}
3359 if (r->MixedOrder==FALSE)
3360 r->pFDeg = p_WFirstTotalDegree;
3361 else
3362 r->pFDeg = p_Totaldegree;
3363 }
3364 }
3365 /*------- more than one block ----------------------*/
3366 else
3367 {
3368 if ((r->VectorOut)||(order[0]==ringorder_C)||(order[0]==ringorder_S)||(order[0]==ringorder_s))
3369 {
3370 rSetFirstWv(r, 1, order, block0, block1, wvhdl);
3371 }
3372 else
3373 rSetFirstWv(r, 0, order, block0, block1, wvhdl);
3374
3375 if ((order[0]!=ringorder_c)
3376 && (order[0]!=ringorder_C)
3377 && (order[0]!=ringorder_S)
3378 && (order[0]!=ringorder_s))
3379 {
3380 r->pLDeg = pLDeg1c;
3381 }
3382 else
3383 {
3384 r->pLDeg = pLDeg1;
3385 }
3386 r->pFDeg = p_WTotaldegree; // may be improved: p_Totaldegree for lp/dp/ls/.. blocks
3387 }
3388
3391 {
3392 if(r->MixedOrder==FALSE)
3393 r->pFDeg = p_Deg;
3394 else
3395 r->pFDeg = p_Totaldegree;
3396 }
3397
3398 if( rGetISPos(0, r) != -1 ) // Are there Schreyer induced blocks?
3399 {
3400#ifndef SING_NDEBUG
3401 assume( r->pFDeg == p_Deg || r->pFDeg == p_WTotaldegree || r->pFDeg == p_Totaldegree);
3402#endif
3403
3404 r->pLDeg = pLDeg1; // ?
3405 }
3406
3407 r->pFDegOrig = r->pFDeg;
3408 // NOTE: this leads to wrong ecart during std
3409 // in Old/sre.tst
3410 rOptimizeLDeg(r); // also sets r->pLDegOrig
3411}
3412
3413/*2
3414* set NegWeightL_Size, NegWeightL_Offset
3415*/
3416static void rSetNegWeight(ring r)
3417{
3418 int i,l;
3419 if (r->typ!=NULL)
3420 {
3421 l=0;
3422 for(i=0;i<r->OrdSize;i++)
3423 {
3424 if((r->typ[i].ord_typ==ro_wp_neg)
3425 ||(r->typ[i].ord_typ==ro_am))
3426 l++;
3427 }
3428 if (l>0)
3429 {
3430 r->NegWeightL_Size=l;
3431 r->NegWeightL_Offset=(int *) omAlloc(l*sizeof(int));
3432 l=0;
3433 for(i=0;i<r->OrdSize;i++)
3434 {
3435 if(r->typ[i].ord_typ==ro_wp_neg)
3436 {
3437 r->NegWeightL_Offset[l]=r->typ[i].data.wp.place;
3438 l++;
3439 }
3440 else if(r->typ[i].ord_typ==ro_am)
3441 {
3442 r->NegWeightL_Offset[l]=r->typ[i].data.am.place;
3443 l++;
3444 }
3445 }
3446 return;
3447 }
3448 }
3449 r->NegWeightL_Size = 0;
3450 r->NegWeightL_Offset = NULL;
3451}
3452
3453static void rSetOption(ring r)
3454{
3455 // set redthrough
3456 if (!TEST_OPT_OLDSTD && r->OrdSgn == 1 && ! r->LexOrder)
3457 r->options |= Sy_bit(OPT_REDTHROUGH);
3458 else
3459 r->options &= ~Sy_bit(OPT_REDTHROUGH);
3460
3461 // set intStrategy
3462 if ( (r->cf->extRing!=NULL)
3463 || rField_is_Q(r)
3464 || rField_is_Ring(r)
3465 || (((int)getCoeffType(r->cf))>16) /* OSCAR types*/
3466 )
3467 r->options |= Sy_bit(OPT_INTSTRATEGY);
3468 else
3469 r->options &= ~Sy_bit(OPT_INTSTRATEGY);
3470
3471 // set redTail
3472 if (r->LexOrder || r->OrdSgn == -1 || (r->cf->extRing!=NULL))
3473 r->options &= ~Sy_bit(OPT_REDTAIL);
3474 else
3475 r->options |= Sy_bit(OPT_REDTAIL);
3476}
3477
3478static void rCheckOrdSgn(ring r,int i/*last block*/);
3479
3480/* -------------------------------------------------------- */
3481/*2
3482* change all global variables to fit the description of the new ring
3483*/
3484
3485void p_SetGlobals(const ring r, BOOLEAN complete)
3486{
3487 r->pLexOrder=r->LexOrder;
3488 if (complete)
3489 {
3491 si_opt_1 |= r->options;
3492 }
3493}
3494
3495static inline int sign(int x) { return (x > 0) - (x < 0);}
3497{
3498 int i;
3499 poly p=p_One(r);
3500 p_SetExp(p,1,1,r);
3501 p_Setm(p,r);
3502 int vz=sign(p_FDeg(p,r));
3503 for(i=2;i<=rVar(r);i++)
3504 {
3505 p_SetExp(p,i-1,0,r);
3506 p_SetExp(p,i,1,r);
3507 p_Setm(p,r);
3508 if (sign(p_FDeg(p,r))!=vz)
3509 {
3510 p_Delete(&p,r);
3511 return TRUE;
3512 }
3513 }
3514 p_Delete(&p,r);
3515 return FALSE;
3516}
3517
3519{
3520 if (r->VarOffset!=NULL && force == 0) return FALSE;
3521 rSetOutParams(r);
3522 int n=rBlocks(r)-1;
3523 int i;
3524 int bits;
3525 r->bitmask=rGetExpSize(r->wanted_maxExp,bits,r->N);
3526 r->BitsPerExp = bits;
3527 r->ExpPerLong = BIT_SIZEOF_LONG / bits;
3528 r->divmask=rGetDivMask(bits);
3529
3530 // will be used for ordsgn:
3531 long *tmp_ordsgn=(long *)omAlloc0(3*(n+r->N)*sizeof(long));
3532 // will be used for VarOffset:
3533 int *v=(int *)omAlloc((r->N+1)*sizeof(int));
3534 for(i=r->N; i>=0 ; i--)
3535 {
3536 v[i]=-1;
3537 }
3538 sro_ord *tmp_typ=(sro_ord *)omAlloc0(3*(n+r->N)*sizeof(sro_ord));
3539 int typ_i=0;
3540 int prev_ordsgn=0;
3541
3542 // fill in v, tmp_typ, tmp_ordsgn, determine typ_i (== ordSize)
3543 int j=0;
3545
3546 BOOLEAN need_to_add_comp=FALSE; // Only for ringorder_s and ringorder_S!
3547
3548 for(i=0;i<n;i++)
3549 {
3550 tmp_typ[typ_i].order_index=i;
3551 switch (r->order[i])
3552 {
3553 case ringorder_a:
3554 case ringorder_aa:
3555 rO_WDegree(j,j_bits,r->block0[i],r->block1[i],tmp_ordsgn,tmp_typ[typ_i],
3556 r->wvhdl[i]);
3557 typ_i++;
3558 break;
3559
3560 case ringorder_am:
3561 rO_WMDegree(j,j_bits,r->block0[i],r->block1[i],tmp_ordsgn,tmp_typ[typ_i],
3562 r->wvhdl[i]);
3563 typ_i++;
3564 break;
3565
3566 case ringorder_a64:
3567 rO_WDegree64(j,j_bits,r->block0[i],r->block1[i],tmp_ordsgn,
3568 tmp_typ[typ_i], (int64 *)(r->wvhdl[i]));
3569 typ_i++;
3570 break;
3571
3572 case ringorder_c:
3573 rO_Align(j, j_bits);
3575 r->ComponentOrder=1;
3576 break;
3577
3578 case ringorder_C:
3579 rO_Align(j, j_bits);
3581 r->ComponentOrder=-1;
3582 break;
3583
3584 case ringorder_M:
3585 {
3586 int k,l;
3587 k=r->block1[i]-r->block0[i]+1; // number of vars
3588 for(l=0;l<k;l++)
3589 {
3590 rO_WDegree(j,j_bits,r->block0[i],r->block1[i],tmp_ordsgn,
3591 tmp_typ[typ_i],
3592 r->wvhdl[i]+(r->block1[i]-r->block0[i]+1)*l);
3593 typ_i++;
3594 }
3595 break;
3596 }
3597
3598 case ringorder_lp:
3599 rO_LexVars(j, j_bits, r->block0[i],r->block1[i], prev_ordsgn,
3600 tmp_ordsgn,v,bits, -1);
3601 break;
3602
3603 case ringorder_ls:
3604 rO_LexVars_neg(j, j_bits, r->block0[i],r->block1[i], prev_ordsgn,
3605 tmp_ordsgn,v, bits, -1);
3606 break;
3607
3608 case ringorder_is:
3609 rO_LexVars_neg(j, j_bits, r->block1[i],r->block0[i], prev_ordsgn,
3610 tmp_ordsgn,v, bits, -1);
3611 break;
3612
3613 case ringorder_ip:
3614 rO_LexVars(j, j_bits, r->block1[i],r->block0[i], prev_ordsgn,
3615 tmp_ordsgn,v, bits, -1);
3616 break;
3617
3618 case ringorder_dp:
3619 if (r->block0[i]==r->block1[i])
3620 {
3621 rO_LexVars(j, j_bits, r->block0[i],r->block0[i], prev_ordsgn,
3622 tmp_ordsgn,v, bits, -1);
3623 }
3624 else
3625 {
3626 rO_TDegree(j,j_bits,r->block0[i],r->block1[i],tmp_ordsgn,
3627 tmp_typ[typ_i]);
3628 typ_i++;
3629 rO_LexVars_neg(j, j_bits, r->block1[i],r->block0[i]+1,
3630 prev_ordsgn,tmp_ordsgn,v,bits, r->block0[i]);
3631 }
3632 break;
3633
3634 case ringorder_Dp:
3635 if (r->block0[i]==r->block1[i])
3636 {
3637 rO_LexVars(j, j_bits, r->block0[i],r->block0[i], prev_ordsgn,
3638 tmp_ordsgn,v, bits, -1);
3639 }
3640 else
3641 {
3642 rO_TDegree(j,j_bits,r->block0[i],r->block1[i],tmp_ordsgn,
3643 tmp_typ[typ_i]);
3644 typ_i++;
3645 rO_LexVars(j, j_bits, r->block0[i],r->block1[i]-1, prev_ordsgn,
3646 tmp_ordsgn,v, bits, r->block1[i]);
3647 }
3648 break;
3649
3650 case ringorder_Ip:
3651 if (r->block0[i]==r->block1[i])
3652 {
3653 rO_LexVars(j, j_bits, r->block0[i],r->block0[i], prev_ordsgn,
3654 tmp_ordsgn,v, bits, -1);
3655 }
3656 else
3657 {
3658 rO_TDegree(j,j_bits,r->block0[i],r->block1[i],tmp_ordsgn,
3659 tmp_typ[typ_i]);
3660 typ_i++;
3661 rO_LexVars(j, j_bits, r->block1[i],r->block0[i], prev_ordsgn,
3662 tmp_ordsgn,v, bits, -1);
3663 }
3664 break;
3665
3666 case ringorder_ds:
3667 if (r->block0[i]==r->block1[i])
3668 {
3669 rO_LexVars_neg(j, j_bits,r->block0[i],r->block1[i],prev_ordsgn,
3670 tmp_ordsgn,v,bits, -1);
3671 }
3672 else
3673 {
3674 rO_TDegree_neg(j,j_bits,r->block0[i],r->block1[i],tmp_ordsgn,
3675 tmp_typ[typ_i]);
3676 typ_i++;
3677 rO_LexVars_neg(j, j_bits, r->block1[i],r->block0[i]+1,
3678 prev_ordsgn,tmp_ordsgn,v,bits, r->block0[i]);
3679 }
3680 break;
3681
3682 case ringorder_Ds:
3683 if (r->block0[i]==r->block1[i])
3684 {
3685 rO_LexVars_neg(j, j_bits, r->block0[i],r->block0[i],prev_ordsgn,
3686 tmp_ordsgn,v, bits, -1);
3687 }
3688 else
3689 {
3690 rO_TDegree_neg(j,j_bits,r->block0[i],r->block1[i],tmp_ordsgn,
3691 tmp_typ[typ_i]);
3692 typ_i++;
3693 rO_LexVars(j, j_bits, r->block0[i],r->block1[i]-1, prev_ordsgn,
3694 tmp_ordsgn,v, bits, r->block1[i]);
3695 }
3696 break;
3697
3698 case ringorder_wp:
3699 rO_WDegree(j,j_bits,r->block0[i],r->block1[i],tmp_ordsgn,
3700 tmp_typ[typ_i], r->wvhdl[i]);
3701 typ_i++;
3702 { // check for weights <=0
3703 int jj;
3705 for(jj=r->block1[i]-r->block0[i];jj>=0; jj--)
3706 {
3707 if (r->wvhdl[i][jj]<=0) have_bad_weights=TRUE;
3708 }
3709 if (have_bad_weights)
3710 {
3711 rO_TDegree(j,j_bits,r->block0[i],r->block1[i],tmp_ordsgn,
3712 tmp_typ[typ_i]);
3713 typ_i++;
3714 }
3715 }
3716 if (r->block1[i]!=r->block0[i])
3717 {
3718 rO_LexVars_neg(j, j_bits,r->block1[i],r->block0[i]+1, prev_ordsgn,
3719 tmp_ordsgn, v,bits, r->block0[i]);
3720 }
3721 break;
3722
3723 case ringorder_Wp:
3724 rO_WDegree(j,j_bits,r->block0[i],r->block1[i],tmp_ordsgn,
3725 tmp_typ[typ_i], r->wvhdl[i]);
3726 typ_i++;
3727 { // check for weights <=0
3728 int jj;
3730 for(jj=r->block1[i]-r->block0[i];jj>=0; jj--)
3731 {
3732 if (r->wvhdl[i][jj]<=0) have_bad_weights=TRUE;
3733 }
3734 if (have_bad_weights)
3735 {
3736 rO_TDegree(j,j_bits,r->block0[i],r->block1[i],tmp_ordsgn,
3737 tmp_typ[typ_i]);
3738 typ_i++;
3739 }
3740 }
3741 if (r->block1[i]!=r->block0[i])
3742 {
3743 rO_LexVars(j, j_bits,r->block0[i],r->block1[i]-1, prev_ordsgn,
3744 tmp_ordsgn,v, bits, r->block1[i]);
3745 }
3746 break;
3747
3748 case ringorder_ws:
3749 rO_WDegree_neg(j,j_bits,r->block0[i],r->block1[i],tmp_ordsgn,
3750 tmp_typ[typ_i], r->wvhdl[i]);
3751 typ_i++;
3752 if (r->block1[i]!=r->block0[i])
3753 {
3754 rO_LexVars_neg(j, j_bits,r->block1[i],r->block0[i]+1, prev_ordsgn,
3755 tmp_ordsgn, v,bits, r->block0[i]);
3756 }
3757 break;
3758
3759 case ringorder_Ws:
3760 rO_WDegree_neg(j,j_bits,r->block0[i],r->block1[i],tmp_ordsgn,
3761 tmp_typ[typ_i], r->wvhdl[i]);
3762 typ_i++;
3763 if (r->block1[i]!=r->block0[i])
3764 {
3765 rO_LexVars(j, j_bits,r->block0[i],r->block1[i]-1, prev_ordsgn,
3766 tmp_ordsgn,v, bits, r->block1[i]);
3767 }
3768 break;
3769
3770 case ringorder_S:
3771 assume(typ_i == 1); // For LaScala3 only: on the 2nd place ([1])!
3772 // TODO: for K[x]: it is 0...?!
3775 r->ComponentOrder=-1;
3776 typ_i++;
3777 break;
3778
3779 case ringorder_s:
3780 assume(typ_i == 0 && j == 0);
3781 rO_Syz(j, j_bits, prev_ordsgn, r->block0[i], tmp_ordsgn, tmp_typ[typ_i]); // set syz-limit?
3783 r->ComponentOrder=-1;
3784 typ_i++;
3785 break;
3786
3787 case ringorder_IS:
3788 {
3789
3790 assume( r->block0[i] == r->block1[i] );
3791 const int s = r->block0[i];
3792 assume( -2 < s && s < 2);
3793
3794 if(s == 0) // Prefix IS
3795 rO_ISPrefix(j, j_bits, prev_ordsgn, tmp_ordsgn, r->N, v, tmp_typ[typ_i++]); // What about prev_ordsgn?
3796 else // s = +1 or -1 // Note: typ_i might be incremented here inside!
3797 {
3798 rO_ISSuffix(j, j_bits, prev_ordsgn, tmp_ordsgn, r->N, v, tmp_typ, typ_i, s); // Suffix.
3800 }
3801
3802 break;
3803 }
3804 case ringorder_unspec:
3805 case ringorder_no:
3806 default:
3807 dReportError("undef. ringorder used\n");
3808 break;
3809 }
3810 }
3811 rCheckOrdSgn(r,n-1);
3812
3813 int j0=j; // save j
3814 int j_bits0=j_bits; // save jbits
3815 rO_Align(j,j_bits);
3816 r->CmpL_Size = j;
3817
3818 j_bits=j_bits0; j=j0;
3819
3820 // fill in some empty slots with variables not already covered
3821 // v0 is special, is therefore normally already covered
3822 // now we do have rings without comp...
3823 if((need_to_add_comp) && (v[0]== -1))
3824 {
3825 if (prev_ordsgn==1)
3826 {
3827 rO_Align(j, j_bits);
3829 }
3830 else
3831 {
3832 rO_Align(j, j_bits);
3834 }
3835 }
3836 // the variables
3837 for(i=1 ; i<=r->N ; i++)
3838 {
3839 if(v[i]==(-1))
3840 {
3841 if (prev_ordsgn==1)
3842 {
3844 }
3845 else
3846 {
3848 }
3849 }
3850 }
3851
3852 rO_Align(j,j_bits);
3853 // ----------------------------
3854 // finished with constructing the monomial, computing sizes:
3855
3856 r->ExpL_Size=j;
3857 r->PolyBin = omGetSpecBin(POLYSIZE + (r->ExpL_Size)*sizeof(long));
3858 assume(r->PolyBin != NULL);
3859
3860 // ----------------------------
3861 // indices and ordsgn vector for comparison
3862 //
3863 // r->pCompHighIndex already set
3864 r->ordsgn=(long *)omAlloc0(r->ExpL_Size*sizeof(long));
3865
3866 for(j=0;j<r->CmpL_Size;j++)
3867 {
3868 r->ordsgn[j] = tmp_ordsgn[j];
3869 }
3870
3871 omFreeSize((ADDRESS)tmp_ordsgn,(3*(n+r->N)*sizeof(long)));
3872
3873 // ----------------------------
3874 // description of orderings for setm:
3875 //
3876 r->OrdSize=typ_i;
3877 if (typ_i==0) r->typ=NULL;
3878 else
3879 {
3880 r->typ=(sro_ord*)omAlloc(typ_i*sizeof(sro_ord));
3881 memcpy(r->typ,tmp_typ,typ_i*sizeof(sro_ord));
3882 }
3883 omFreeSize((ADDRESS)tmp_typ,(3*(n+r->N)*sizeof(sro_ord)));
3884
3885 // ----------------------------
3886 // indices for (first copy of ) variable entries in exp.e vector (VarOffset):
3887 r->VarOffset=v;
3888
3889 // ----------------------------
3890 // other indices
3891 r->pCompIndex=(r->VarOffset[0] & 0xffff); //r->VarOffset[0];
3892 i=0; // position
3893 j=0; // index in r->typ
3894 if (i==r->pCompIndex) i++; // IS???
3895 while ((j < r->OrdSize)
3896 && ((r->typ[j].ord_typ==ro_syzcomp) ||
3897 (r->typ[j].ord_typ==ro_syz) || (r->typ[j].ord_typ==ro_isTemp) || (r->typ[j].ord_typ==ro_is) ||
3898 (r->order[r->typ[j].order_index] == ringorder_aa)))
3899 {
3900 i++; j++;
3901 }
3902
3903 if (i==r->pCompIndex) i++;
3904 r->pOrdIndex=i;
3905
3906 // ----------------------------
3907 rSetDegStuff(r); // OrdSgn etc already set
3908 rSetOption(r);
3909 // ----------------------------
3910 // r->p_Setm
3911 r->p_Setm = p_GetSetmProc(r);
3912
3913 // ----------------------------
3914 // set VarL_*
3915 rSetVarL(r);
3916
3917 // ----------------------------
3918 // right-adjust VarOffset
3920
3921 // ----------------------------
3922 // set NegWeightL*
3923 rSetNegWeight(r);
3924
3925 // ----------------------------
3926 // p_Procs: call AFTER NegWeightL
3927 r->p_Procs = (p_Procs_s*)omAlloc(sizeof(p_Procs_s));
3928 p_ProcsSet(r, r->p_Procs);
3929
3930 // use totaldegree on crazy oderings:
3931 if ((r->pFDeg==p_WTotaldegree) && rOrd_is_MixedDegree_Ordering(r))
3932 r->pFDeg = p_Totaldegree;
3933 return FALSE;
3934}
3935
3936static void rCheckOrdSgn(ring r,int b/*last block*/)
3937{ // set r->OrdSgn, r->MixedOrder
3938 // for each variable:
3939 int nonpos=0;
3940 int nonneg=0;
3941 for(int i=1;i<=r->N;i++)
3942 {
3943 int found=0;
3944 // for all blocks:
3945 for(int j=0;(j<=b) && (found==0);j++)
3946 {
3947 // search the first block containing var(i)
3948 if ((r->block0[j]<=i)&&(r->block1[j]>=i))
3949 {
3950 // what kind if block is it?
3951 if ((r->order[j]==ringorder_ls)
3952 || (r->order[j]==ringorder_ds)
3953 || (r->order[j]==ringorder_Ds)
3954 || (r->order[j]==ringorder_ws)
3955 || (r->order[j]==ringorder_Ws)
3956 || (r->order[j]==ringorder_rs))
3957 {
3958 r->OrdSgn=-1;
3959 nonpos++;
3960 found=1;
3961 }
3962 else if((r->order[j]==ringorder_a)
3963 ||(r->order[j]==ringorder_aa))
3964 {
3965 // <0: local/mixed ordering
3966 // >0: var(i) is okay, look at other vars
3967 // ==0: look at other blocks for var(i)
3968 if(r->wvhdl[j][i-r->block0[j]]<0)
3969 {
3970 r->OrdSgn=-1;
3971 nonpos++;
3972 found=1;
3973 }
3974 else if(r->wvhdl[j][i-r->block0[j]]>0)
3975 {
3976 nonneg++;
3977 found=1;
3978 }
3979 }
3980 else if(r->order[j]==ringorder_M)
3981 {
3982 // <0: local/mixed ordering
3983 // >0: var(i) is okay, look at other vars
3984 // ==0: look at other blocks for var(i)
3985 if(r->wvhdl[j][i-r->block0[j]]<0)
3986 {
3987 r->OrdSgn=-1;
3988 nonpos++;
3989 found=1;
3990 }
3991 else if(r->wvhdl[j][i-r->block0[j]]>0)
3992 {
3993 nonneg++;
3994 found=1;
3995 }
3996 else
3997 {
3998 // very bad: try next row(s)
3999 int add=r->block1[j]-r->block0[j]+1;
4000 int max_i=r->block0[j]+add*add-add-1;
4001 while(found==0)
4002 {
4003 i+=add;
4004 if (r->wvhdl[j][i-r->block0[j]]<0)
4005 {
4006 r->OrdSgn=-1;
4007 nonpos++;
4008 found=1;
4009 }
4010 else if(r->wvhdl[j][i-r->block0[j]]>0)
4011 {
4012 nonneg++;
4013 found=1;
4014 }
4015 else if(i>max_i)
4016 {
4017 nonpos++;
4018 nonneg++;
4019 found=1;
4020 }
4021 }
4022 }
4023 }
4024 else if ((r->order[j]==ringorder_lp)
4025 || (r->order[j]==ringorder_dp)
4026 || (r->order[j]==ringorder_Dp)
4027 || (r->order[j]==ringorder_wp)
4028 || (r->order[j]==ringorder_Wp)
4029 || (r->order[j]==ringorder_rp))
4030 {
4031 found=1;
4032 nonneg++;
4033 }
4034 }
4035 }
4036 }
4037 if (nonpos>0)
4038 {
4039 r->OrdSgn=-1;
4040 if (nonneg>0) r->MixedOrder=1;
4041 }
4042 else
4043 {
4044 r->OrdSgn=1;
4045 r->MixedOrder=0;
4046 }
4047}
4048
4050{
4051 if (r == NULL) return;
4052 if (r->VarOffset != NULL)
4053 {
4054 if (r->OrdSize!=0 && r->typ != NULL)
4055 {
4056 for(int i = 0; i < r->OrdSize; i++)
4057 if( r->typ[i].ord_typ == ro_is) // Search for suffixes! (prefix have the same VarOffset)
4058 {
4059 id_Delete(&r->typ[i].data.is.F, r);
4060
4061 if( r->typ[i].data.is.pVarOffset != NULL )
4062 {
4063 omFreeSize((ADDRESS)r->typ[i].data.is.pVarOffset, (r->N +1)*sizeof(int));
4064 }
4065 }
4066 else if (r->typ[i].ord_typ == ro_syz)
4067 {
4068 if(r->typ[i].data.syz.limit > 0)
4069 omFreeSize(r->typ[i].data.syz.syz_index, ((r->typ[i].data.syz.limit) +1)*sizeof(int));
4070 }
4071 else if (r->typ[i].ord_typ == ro_syzcomp)
4072 {
4073 assume( r->typ[i].data.syzcomp.ShiftedComponents == NULL );
4074 assume( r->typ[i].data.syzcomp.Components == NULL );
4075// WarnS( "rUnComplete : ord_typ == ro_syzcomp was unhandled!!! Possibly memory leak!!!" );
4076#ifndef SING_NDEBUG
4077// assume(0);
4078#endif
4079 }
4080
4081 omFreeSize((ADDRESS)r->typ,r->OrdSize*sizeof(sro_ord)); r->typ = NULL;
4082 }
4083
4084 if (r->PolyBin != NULL)
4085 omUnGetSpecBin(&(r->PolyBin));
4086
4087 omFreeSize((ADDRESS)r->VarOffset, (r->N +1)*sizeof(int));
4088 r->VarOffset=NULL;
4089
4090 if (r->ordsgn != NULL && r->CmpL_Size != 0)
4091 {
4092 omFreeSize((ADDRESS)r->ordsgn,r->ExpL_Size*sizeof(long));
4093 r->ordsgn=NULL;
4094 }
4095 if (r->p_Procs != NULL)
4096 {
4097 omFreeSize(r->p_Procs, sizeof(p_Procs_s));
4098 r->p_Procs=NULL;
4099 }
4100 omfreeSize(r->VarL_Offset, r->VarL_Size*sizeof(int));
4101 r->VarL_Offset=NULL;
4102 }
4103 if (r->NegWeightL_Offset!=NULL)
4104 {
4105 omFreeSize(r->NegWeightL_Offset, r->NegWeightL_Size*sizeof(int));
4106 r->NegWeightL_Offset=NULL;
4107 }
4108}
4109
4110// set r->VarL_Size, r->VarL_Offset, r->VarL_LowIndex
4111static void rSetVarL(ring r)
4112{
4113 int min = INT_MAX, min_j = -1;
4114 int* VarL_Number = (int*) omAlloc0(r->ExpL_Size*sizeof(int));
4115
4116 int i,j;
4117
4118 // count how often a var long is occupied by an exponent
4119 for (i=1; i<=r->N; i++)
4120 {
4121 VarL_Number[r->VarOffset[i] & 0xffffff]++;
4122 }
4123
4124 // determine how many and min
4125 for (i=0, j=0; i<r->ExpL_Size; i++)
4126 {
4127 if (VarL_Number[i] != 0)
4128 {
4129 if (min > VarL_Number[i])
4130 {
4131 min = VarL_Number[i];
4132 min_j = j;
4133 }
4134 j++;
4135 }
4136 }
4137
4138 r->VarL_Size = j; // number of long with exp. entries in
4139 // in p->exp
4140 r->VarL_Offset = (int*) omAlloc(r->VarL_Size*sizeof(int));
4141 r->VarL_LowIndex = 0;
4142
4143 // set VarL_Offset
4144 for (i=0, j=0; i<r->ExpL_Size; i++)
4145 {
4146 if (VarL_Number[i] != 0)
4147 {
4148 r->VarL_Offset[j] = i;
4149 if (j > 0 && r->VarL_Offset[j-1] != r->VarL_Offset[j] - 1)
4150 r->VarL_LowIndex = -1;
4151 j++;
4152 }
4153 }
4154 if (r->VarL_LowIndex >= 0)
4155 r->VarL_LowIndex = r->VarL_Offset[0];
4156
4157 if (min_j != 0)
4158 {
4159 j = r->VarL_Offset[min_j];
4160 r->VarL_Offset[min_j] = r->VarL_Offset[0];
4161 r->VarL_Offset[0] = j;
4162 }
4164}
4165
4167{
4168 int* shifts = (int*) omAlloc(r->ExpL_Size*sizeof(int));
4169 int i;
4170 // initialize shifts
4171 for (i=0;i<r->ExpL_Size;i++)
4173
4174 // find minimal bit shift in each long exp entry
4175 for (i=1;i<=r->N;i++)
4176 {
4177 if (shifts[r->VarOffset[i] & 0xffffff] > r->VarOffset[i] >> 24)
4178 shifts[r->VarOffset[i] & 0xffffff] = r->VarOffset[i] >> 24;
4179 }
4180 // reset r->VarOffset: set the minimal shift to 0
4181 for (i=1;i<=r->N;i++)
4182 {
4183 if (shifts[r->VarOffset[i] & 0xffffff] != 0)
4184 r->VarOffset[i]
4185 = (r->VarOffset[i] & 0xffffff) |
4186 (((r->VarOffset[i] >> 24) - shifts[r->VarOffset[i] & 0xffffff]) << 24);
4187 }
4188 omFree(shifts);
4189}
4190
4191// get r->divmask depending on bits per exponent
4192static unsigned long rGetDivMask(int bits)
4193{
4194 unsigned long divmask = 1;
4195 int i = bits;
4196
4197 while (i < BIT_SIZEOF_LONG)
4198 {
4199 divmask |= (((unsigned long) 1) << (unsigned long) i);
4200 i += bits;
4201 }
4202 return divmask;
4203}
4204
4205#ifdef RDEBUG
4206void rDebugPrint(const ring r)
4207{
4208 if (r==NULL)
4209 {
4210 PrintS("NULL ?\n");
4211 return;
4212 }
4213 // corresponds to ro_typ from ring.h:
4214 const char *TYP[]={"ro_dp","ro_wp","ro_am","ro_wp64","ro_wp_neg","ro_cp",
4215 "ro_syzcomp", "ro_syz", "ro_isTemp", "ro_is", "ro_none"};
4216 int i,j;
4217
4218 Print("ExpL_Size:%d ",r->ExpL_Size);
4219 Print("CmpL_Size:%d ",r->CmpL_Size);
4220 Print("VarL_Size:%d\n",r->VarL_Size);
4221 Print("bitmask=0x%lx (expbound=%ld) \n",r->bitmask, r->bitmask);
4222 Print("divmask=%lx\n", r->divmask);
4223 Print("BitsPerExp=%d ExpPerLong=%d at L[%d]\n", r->BitsPerExp, r->ExpPerLong, r->VarL_Offset[0]);
4224
4225 Print("VarL_LowIndex: %d\n", r->VarL_LowIndex);
4226 PrintS("VarL_Offset:\n");
4227 if (r->VarL_Offset==NULL) PrintS(" NULL");
4228 else
4229 for(j = 0; j < r->VarL_Size; j++)
4230 Print(" VarL_Offset[%d]: %d ", j, r->VarL_Offset[j]);
4231 PrintLn();
4232
4233
4234 PrintS("VarOffset:\n");
4235 if (r->VarOffset==NULL) PrintS(" NULL\n");
4236 else
4237 for(j=0;j<=r->N;j++)
4238 Print(" v%d at e-pos %d, bit %d\n",
4239 j,r->VarOffset[j] & 0xffffff, r->VarOffset[j] >>24);
4240 PrintS("ordsgn:\n");
4241 for(j=0;j<r->CmpL_Size;j++)
4242 Print(" ordsgn %ld at pos %d\n",r->ordsgn[j],j);
4243 Print("OrdSgn:%d\n",r->OrdSgn);
4244 PrintS("ordrec:\n");
4245 for(j=0;j<r->OrdSize;j++)
4246 {
4247 Print(" typ %s", TYP[r->typ[j].ord_typ]);
4248 if (r->typ[j].ord_typ==ro_syz)
4249 {
4250 const short place = r->typ[j].data.syz.place;
4251 const int limit = r->typ[j].data.syz.limit;
4252 const int curr_index = r->typ[j].data.syz.curr_index;
4253 const int* syz_index = r->typ[j].data.syz.syz_index;
4254
4255 Print(" limit %d (place: %d, curr_index: %d), syz_index: ", limit, place, curr_index);
4256
4257 if( syz_index == NULL )
4258 PrintS("(NULL)");
4259 else
4260 {
4261 PrintS("{");
4262 for( i=0; i <= limit; i++ )
4263 Print("%d ", syz_index[i]);
4264 PrintS("}");
4265 }
4266
4267 }
4268 else if (r->typ[j].ord_typ==ro_isTemp)
4269 {
4270 Print(" start (level) %d, suffixpos: %d, VO: ",r->typ[j].data.isTemp.start, r->typ[j].data.isTemp.suffixpos);
4271
4272 }
4273 else if (r->typ[j].ord_typ==ro_is)
4274 {
4275 Print(" start %d, end: %d: ",r->typ[j].data.is.start, r->typ[j].data.is.end);
4276
4277// for( int k = 0; k <= r->N; k++) if (r->typ[j].data.is.pVarOffset[k] != -1) Print("[%2d]: %04x; ", k, r->typ[j].data.is.pVarOffset[k]);
4278
4279 Print(" limit %d",r->typ[j].data.is.limit);
4280#ifndef SING_NDEBUG
4281 //PrintS(" F: ");idShow(r->typ[j].data.is.F, r, r, 1);
4282#endif
4283
4284 PrintLn();
4285 }
4286 else if (r->typ[j].ord_typ==ro_am)
4287 {
4288 Print(" place %d",r->typ[j].data.am.place);
4289 Print(" start %d",r->typ[j].data.am.start);
4290 Print(" end %d",r->typ[j].data.am.end);
4291 Print(" len_gen %d",r->typ[j].data.am.len_gen);
4292 PrintS(" w:");
4293 int l=0;
4294 for(l=r->typ[j].data.am.start;l<=r->typ[j].data.am.end;l++)
4295 Print(" %d",r->typ[j].data.am.weights[l-r->typ[j].data.am.start]);
4296 l=r->typ[j].data.am.end+1;
4297 int ll=r->typ[j].data.am.weights[l-r->typ[j].data.am.start];
4298 PrintS(" m:");
4299 for(int lll=l+1;lll<l+ll+1;lll++)
4300 Print(" %d",r->typ[j].data.am.weights[lll-r->typ[j].data.am.start]);
4301 }
4302 else
4303 {
4304 Print(" place %d",r->typ[j].data.dp.place);
4305
4306 if (r->typ[j].ord_typ!=ro_syzcomp && r->typ[j].ord_typ!=ro_syz)
4307 {
4308 Print(" start %d",r->typ[j].data.dp.start);
4309 Print(" end %d",r->typ[j].data.dp.end);
4310 if ((r->typ[j].ord_typ==ro_wp)
4311 || (r->typ[j].ord_typ==ro_wp_neg))
4312 {
4313 PrintS(" w:");
4314 for(int l=r->typ[j].data.wp.start;l<=r->typ[j].data.wp.end;l++)
4315 Print(" %d",r->typ[j].data.wp.weights[l-r->typ[j].data.wp.start]);
4316 }
4317 else if (r->typ[j].ord_typ==ro_wp64)
4318 {
4319 PrintS(" w64:");
4320 int l;
4321 for(l=r->typ[j].data.wp64.start;l<=r->typ[j].data.wp64.end;l++)
4322 Print(" %ld",(long)(r->typ[j].data.wp64.weights64+l-r->typ[j].data.wp64.start));
4323 }
4324 }
4325 }
4326 PrintLn();
4327 }
4328 Print("pOrdIndex:%d pCompIndex:%d\n", r->pOrdIndex, r->pCompIndex);
4329 Print("OrdSize:%d\n",r->OrdSize);
4330 PrintS("--------------------\n");
4331 for(j=0;j<r->ExpL_Size;j++)
4332 {
4333 Print("L[%d]: ",j);
4334 if (j< r->CmpL_Size)
4335 Print("ordsgn %ld ", r->ordsgn[j]);
4336 else
4337 PrintS("no comp ");
4338 i=1;
4339 for(;i<=r->N;i++)
4340 {
4341 if( (r->VarOffset[i] & 0xffffff) == j )
4342 { Print("v%d at e[%d], bit %d; ", i,r->VarOffset[i] & 0xffffff,
4343 r->VarOffset[i] >>24 ); }
4344 }
4345 if( r->pCompIndex==j ) PrintS("v0; ");
4346 for(i=0;i<r->OrdSize;i++)
4347 {
4348 if (r->typ[i].data.dp.place == j)
4349 {
4350 Print("ordrec:%s (start:%d, end:%d) ",TYP[r->typ[i].ord_typ],
4351 r->typ[i].data.dp.start, r->typ[i].data.dp.end);
4352 }
4353 }
4354
4355 if (j==r->pOrdIndex)
4356 PrintS("pOrdIndex\n");
4357 else
4358 PrintLn();
4359 }
4360 Print("LexOrder:%d, MixedOrder:%d\n",r->LexOrder, r->MixedOrder);
4361
4362 Print("NegWeightL_Size: %d, NegWeightL_Offset: ", r->NegWeightL_Size);
4363 if (r->NegWeightL_Offset==NULL) PrintS(" NULL");
4364 else
4365 for(j = 0; j < r->NegWeightL_Size; j++)
4366 Print(" [%d]: %d ", j, r->NegWeightL_Offset[j]);
4367 PrintLn();
4368
4369 // p_Procs stuff
4371 const char* field;
4372 const char* length;
4373 const char* ord;
4374 p_Debug_GetProcNames(r, &proc_names); // changes p_Procs!!!
4376
4377 Print("p_Spec : %s, %s, %s\n", field, length, ord);
4378 PrintS("p_Procs :\n");
4379 for (i=0; i<(int) (sizeof(p_Procs_s)/sizeof(void*)); i++)
4380 {
4381 Print(" %s,\n", ((char**) &proc_names)[i]);
4382 }
4383
4384 {
4385 PrintLn();
4386 PrintS("pFDeg : ");
4387#define pFDeg_CASE(A) if(r->pFDeg == A) PrintS( "" #A "" )
4391 pFDeg_CASE(p_Deg); else
4392#undef pFDeg_CASE
4393 Print("(%p)", r->pFDeg); // default case
4394
4395 PrintLn();
4396 Print("pLDeg : (%p)", r->pLDeg);
4397 PrintLn();
4398 }
4399 PrintS("pSetm:");
4400 void p_Setm_Dummy(poly p, const ring r);
4401 void p_Setm_TotalDegree(poly p, const ring r);
4402 void p_Setm_WFirstTotalDegree(poly p, const ring r);
4403 void p_Setm_General(poly p, const ring r);
4404 if (r->p_Setm==p_Setm_General) PrintS("p_Setm_General\n");
4405 else if (r->p_Setm==p_Setm_Dummy) PrintS("p_Setm_Dummy\n");
4406 else if (r->p_Setm==p_Setm_TotalDegree) PrintS("p_Setm_Totaldegree\n");
4407 else if (r->p_Setm==p_Setm_WFirstTotalDegree) PrintS("p_Setm_WFirstTotalDegree\n");
4408 else Print("%p\n",r->p_Setm);
4409}
4410
4411void p_DebugPrint(poly p, const ring r)
4412{
4413 int i,j;
4414 p_Write(p,r);
4415 j=2;
4416 while(p!=NULL)
4417 {
4418 Print("\nexp[0..%d]\n",r->ExpL_Size-1);
4419 for(i=0;i<r->ExpL_Size;i++)
4420 Print("%ld ",p->exp[i]);
4421 PrintLn();
4422 Print("v0:%ld ",p_GetComp(p, r));
4423 for(i=1;i<=r->N;i++) Print(" v%d:%ld",i,p_GetExp(p,i, r));
4424 PrintLn();
4425 pIter(p);
4426 j--;
4427 if (j==0) { PrintS("...\n"); break; }
4428 }
4429}
4430
4431#endif // RDEBUG
4432
4433/// debug-print monomial poly/vector p, assuming that it lives in the ring R
4434static inline void m_DebugPrint(const poly p, const ring R)
4435{
4436 Print("\nexp[0..%d]\n", R->ExpL_Size - 1);
4437 for(int i = 0; i < R->ExpL_Size; i++)
4438 Print("%09lx ", p->exp[i]);
4439 PrintLn();
4440 Print("v0:%9ld ", p_GetComp(p, R));
4441 for(int i = 1; i <= R->N; i++) Print(" v%d:%5ld",i, p_GetExp(p, i, R));
4442 PrintLn();
4443}
4444
4445
4446/*2
4447* assume that rComplete was called with r
4448* assume that the first block ist ringorder_S
4449* change the block to reflect the sequence given by appending v
4450*/
4452{
4453 assume(r->typ[1].ord_typ == ro_syzcomp);
4454
4455 r->typ[1].data.syzcomp.ShiftedComponents = currShiftedComponents;
4456 r->typ[1].data.syzcomp.Components = currComponents;
4457}
4458
4459static inline void rNGetSComps(int** currComponents, long** currShiftedComponents, ring r)
4460{
4461 assume(r->typ[1].ord_typ == ro_syzcomp);
4462
4463 *currShiftedComponents = r->typ[1].data.syzcomp.ShiftedComponents;
4464 *currComponents = r->typ[1].data.syzcomp.Components;
4465}
4466#ifdef PDEBUG
4467static inline void rDBChangeSComps(int* currComponents,
4469 int length,
4470 ring r)
4471{
4472 assume(r->typ[1].ord_typ == ro_syzcomp);
4473
4474 r->typ[1].data.syzcomp.length = length;
4476}
4477static inline void rDBGetSComps(int** currComponents,
4478 long** currShiftedComponents,
4479 int *length,
4480 ring r)
4481{
4482 assume(r->typ[1].ord_typ == ro_syzcomp);
4483
4484 *length = r->typ[1].data.syzcomp.length;
4486}
4487#endif
4488
4490{
4491#ifdef PDEBUG
4493#else
4495#endif
4496}
4497
4499{
4500#ifdef PDEBUG
4502#else
4504#endif
4505}
4506
4507
4508/////////////////////////////////////////////////////////////////////////////
4509//
4510// The following routines all take as input a ring r, and return R
4511// where R has a certain property. R might be equal r in which case r
4512// had already this property
4513//
4515{
4516 if ( r->order[0] == ringorder_c ) return r;
4517 return rAssure_SyzComp(r,complete);
4518}
4520{
4521 if ( r->order[0] == ringorder_s ) return r;
4522
4523 if ( r->order[0] == ringorder_IS )
4524 {
4525#ifndef SING_NDEBUG
4526 WarnS("rAssure_SyzComp: input ring has an IS-ordering!");
4527#endif
4528// return r;
4529 }
4530 ring res=rCopy0(r, FALSE, FALSE);
4531 int i=rBlocks(r);
4532 int j;
4533
4534 res->order=(rRingOrder_t *)omAlloc((i+1)*sizeof(rRingOrder_t));
4535 res->block0=(int *)omAlloc0((i+1)*sizeof(int));
4536 res->block1=(int *)omAlloc0((i+1)*sizeof(int));
4537 int ** wvhdl =(int **)omAlloc0((i+1)*sizeof(int**));
4538 for(j=i;j>0;j--)
4539 {
4540 res->order[j]=r->order[j-1];
4541 res->block0[j]=r->block0[j-1];
4542 res->block1[j]=r->block1[j-1];
4543 if (r->wvhdl[j-1] != NULL)
4544 {
4545 #ifdef HAVE_OMALLOC
4546 wvhdl[j] = (int*) omMemDup(r->wvhdl[j-1]);
4547 #else
4548 {
4549 int l=r->block1[j-1]-r->block0[j-1]+1;
4550 if (r->order[j-1]==ringorder_a64) l*=2;
4551 else if (r->order[j-1]==ringorder_M) l=l*l;
4552 else if (r->order[j-1]==ringorder_am)
4553 {
4554 l+=r->wvhdl[j-1][r->block1[j-1]-r->block0[j-1]+1]+1;
4555 }
4556 wvhdl[j]=(int*)omalloc(l*sizeof(int));
4557 memcpy(wvhdl[j],r->wvhdl[j-1],l*sizeof(int));
4558 }
4559 #endif
4560 }
4561 }
4562 res->order[0]=ringorder_s;
4563
4564 res->wvhdl = wvhdl;
4565
4566 if (complete)
4567 {
4568 rComplete(res, 1);
4569#ifdef HAVE_PLURAL
4570 if (rIsPluralRing(r))
4571 {
4572 if ( nc_rComplete(r, res, false) ) // no qideal!
4573 {
4574#ifndef SING_NDEBUG
4575 WarnS("error in nc_rComplete"); // cleanup?// rDelete(res);// return r; // just go on..
4576#endif
4577 }
4578 }
4580#endif
4581
4582#ifdef HAVE_PLURAL
4583 ring old_ring = r;
4584#endif
4585 if (r->qideal!=NULL)
4586 {
4587 res->qideal= idrCopyR_NoSort(r->qideal, r, res);
4588 assume(id_RankFreeModule(res->qideal, res) == 0);
4589#ifdef HAVE_PLURAL
4590 if( rIsPluralRing(res) )
4591 {
4592 if( nc_SetupQuotient(res, r, true) )
4593 {
4594// WarnS("error in nc_SetupQuotient"); // cleanup? rDelete(res); return r; // just go on...?
4595 }
4596 assume(id_RankFreeModule(res->qideal, res) == 0);
4597 }
4598#endif
4599 }
4600
4601#ifdef HAVE_PLURAL
4602 assume((res->qideal==NULL) == (old_ring->qideal==NULL));
4606#endif
4607 }
4608 return res;
4609}
4610
4612{
4613 if (r->N==1) // special: dp(1)==lp(1)== no entry in typ
4614 {
4615 pos=r->VarL_LowIndex;
4616 return r;
4617 }
4618 if (r->typ!=NULL)
4619 {
4620 for(int i=r->OrdSize-1;i>=0;i--)
4621 {
4622 if ((r->typ[i].ord_typ==ro_dp)
4623 && (r->typ[i].data.dp.start==1)
4624 && (r->typ[i].data.dp.end==r->N))
4625 {
4626 pos=r->typ[i].data.dp.place;
4627 //printf("no change, pos=%d\n",pos);
4628 return r;
4629 }
4630 }
4631 }
4632
4633#ifdef HAVE_PLURAL
4634 nc_struct* save=r->GetNC();
4635 r->GetNC()=NULL;
4636#endif
4637 ring res=rCopy(r);
4638 if (res->qideal!=NULL)
4639 {
4640 id_Delete(&res->qideal,r);
4641 }
4642
4643 int j;
4644
4645 res->ExpL_Size=r->ExpL_Size+1; // one word more in each monom
4646 res->PolyBin=omGetSpecBin(POLYSIZE + (res->ExpL_Size)*sizeof(long));
4647 omFree((ADDRESS)res->ordsgn);
4648 res->ordsgn=(long *)omAlloc0(res->ExpL_Size*sizeof(long));
4649 for(j=0;j<r->CmpL_Size;j++)
4650 {
4651 res->ordsgn[j] = r->ordsgn[j];
4652 }
4653 res->OrdSize=r->OrdSize+1; // one block more for pSetm
4654 if (r->typ!=NULL)
4655 omFree((ADDRESS)res->typ);
4656 res->typ=(sro_ord*)omAlloc0(res->OrdSize*sizeof(sro_ord));
4657 if (r->typ!=NULL)
4658 memcpy(res->typ,r->typ,r->OrdSize*sizeof(sro_ord));
4659 // the additional block for pSetm: total degree at the last word
4660 // but not included in the compare part
4661 res->typ[res->OrdSize-1].ord_typ=ro_dp;
4662 res->typ[res->OrdSize-1].data.dp.start=1;
4663 res->typ[res->OrdSize-1].data.dp.end=res->N;
4664 res->typ[res->OrdSize-1].data.dp.place=res->ExpL_Size-1;
4665 pos=res->ExpL_Size-1;
4666 //res->pOrdIndex=pos; //NO: think of a(1,0),dp !
4667 extern void p_Setm_General(poly p, ring r);
4668 res->p_Setm=p_Setm_General;
4669 // ----------------------------
4670 omFree((ADDRESS)res->p_Procs);
4671 res->p_Procs = (p_Procs_s*)omAlloc(sizeof(p_Procs_s));
4672
4673 p_ProcsSet(res, res->p_Procs);
4674#ifdef HAVE_PLURAL
4675 r->GetNC()=save;
4676 if (rIsPluralRing(r))
4677 {
4678 if ( nc_rComplete(r, res, false) ) // no qideal!
4679 {
4680#ifndef SING_NDEBUG
4681 WarnS("error in nc_rComplete");
4682#endif
4683 // just go on..
4684 }
4685 }
4686#endif
4687 if (r->qideal!=NULL)
4688 {
4689 res->qideal=idrCopyR_NoSort(r->qideal,r, res);
4690#ifdef HAVE_PLURAL
4691 if (rIsPluralRing(res))
4692 {
4693// nc_SetupQuotient(res, currRing);
4694 nc_SetupQuotient(res, r); // ?
4695 }
4696 assume((res->qideal==NULL) == (r->qideal==NULL));
4697#endif
4698 }
4699
4700#ifdef HAVE_PLURAL
4702 assume(rIsSCA(res) == rIsSCA(r));
4704#endif
4705
4706 return res;
4707}
4708
4710{
4711 int last_block;
4712 int i=0;
4713 do
4714 {
4715 if (r->order[i] == ringorder_c ||
4716 r->order[i] == ringorder_C) return r;
4717 if (r->order[i] == 0)
4718 break;
4719 i++;
4720 } while (1);
4721 //WarnS("re-creating ring with comps");
4722 last_block=i-1;
4723
4724 ring new_r = rCopy0(r, FALSE, FALSE);
4725 i+=2;
4726 new_r->wvhdl=(int **)omAlloc0(i * sizeof(int *));
4727 new_r->order = (rRingOrder_t *) omAlloc0(i * sizeof(rRingOrder_t));
4728 new_r->block0 = (int *) omAlloc0(i * sizeof(int));
4729 new_r->block1 = (int *) omAlloc0(i * sizeof(int));
4730 memcpy(new_r->order,r->order,(i-1) * sizeof(rRingOrder_t));
4731 memcpy(new_r->block0,r->block0,(i-1) * sizeof(int));
4732 memcpy(new_r->block1,r->block1,(i-1) * sizeof(int));
4733 for (int j=0; j<=last_block; j++)
4734 {
4735 if (r->wvhdl[j]!=NULL)
4736 {
4737 #ifdef HAVE_OMALLOC
4738 new_r->wvhdl[j] = (int*) omMemDup(r->wvhdl[j]);
4739 #else
4740 {
4741 int l=r->block1[j]-r->block0[j]+1;
4742 if (r->order[j]==ringorder_a64) l*=2;
4743 else if (r->order[j]==ringorder_M) l=l*l;
4744 else if (r->order[j]==ringorder_am)
4745 {
4746 l+=r->wvhdl[j][r->block1[j]-r->block0[j]+1]+1;
4747 }
4748 new_r->wvhdl[j]=(int*)omalloc(l*sizeof(int));
4749 memcpy(new_r->wvhdl[j],r->wvhdl[j],l*sizeof(int));
4750 }
4751 #endif
4752 }
4753 }
4754 last_block++;
4756 //new_r->block0[last_block]=0;
4757 //new_r->block1[last_block]=0;
4758 //new_r->wvhdl[last_block]=NULL;
4759
4760 rComplete(new_r, 1);
4761
4762#ifdef HAVE_PLURAL
4763 if (rIsPluralRing(r))
4764 {
4765 if ( nc_rComplete(r, new_r, false) ) // no qideal!
4766 {
4767#ifndef SING_NDEBUG
4768 WarnS("error in nc_rComplete"); // cleanup?// rDelete(res);// return r; // just go on..
4769#endif
4770 }
4771 }
4773#endif
4774
4775 return new_r;
4776}
4777
4779{
4780 int last_block = rBlocks(r) - 2;
4781 if (r->order[last_block] != ringorder_c &&
4782 r->order[last_block] != ringorder_C)
4783 {
4784 int c_pos = 0;
4785 int i;
4786
4787 for (i=0; i< last_block; i++)
4788 {
4789 if (r->order[i] == ringorder_c || r->order[i] == ringorder_C)
4790 {
4791 c_pos = i;
4792 break;
4793 }
4794 }
4795 if (c_pos != -1)
4796 {
4797 ring new_r = rCopy0(r, FALSE, TRUE);
4798 for (i=c_pos+1; i<=last_block; i++)
4799 {
4800 new_r->order[i-1] = new_r->order[i];
4801 new_r->block0[i-1] = new_r->block0[i];
4802 new_r->block1[i-1] = new_r->block1[i];
4803 new_r->wvhdl[i-1] = new_r->wvhdl[i];
4804 }
4805 new_r->order[last_block] = r->order[c_pos];
4806 new_r->block0[last_block] = r->block0[c_pos];
4807 new_r->block1[last_block] = r->block1[c_pos];
4808 new_r->wvhdl[last_block] = r->wvhdl[c_pos];
4809 if (complete)
4810 {
4811 rComplete(new_r, 1);
4812
4813#ifdef HAVE_PLURAL
4814 if (rIsPluralRing(r))
4815 {
4816 if ( nc_rComplete(r, new_r, false) ) // no qideal!
4817 {
4818#ifndef SING_NDEBUG
4819 WarnS("error in nc_rComplete"); // cleanup?// rDelete(res);// return r; // just go on..
4820#endif
4821 }
4822 }
4824#endif
4825 }
4826 return new_r;
4827 }
4828 }
4829 return r;
4830}
4831
4832// Moves _c or _C ordering to the last place AND adds _s on the 1st place
4834{
4835 rTest(r);
4836
4837 ring new_r_1 = rAssure_CompLastBlock(r, FALSE); // due to this FALSE - no completion!
4838 ring new_r = rAssure_SyzComp(new_r_1, FALSE); // new_r_1 is used only here!!!
4839
4840 if (new_r == r)
4841 return r;
4842
4843 ring old_r = r;
4844 if (new_r_1 != new_r && new_r_1 != old_r) rDelete(new_r_1);
4845
4847#ifdef HAVE_PLURAL
4848 if (rIsPluralRing(old_r))
4849 {
4850 if ( nc_rComplete(old_r, new_r, false) ) // no qideal!
4851 {
4852# ifndef SING_NDEBUG
4853 WarnS("error in nc_rComplete"); // cleanup? rDelete(res); return r; // just go on...?
4854# endif
4855 }
4856 }
4857#endif
4858
4859///? rChangeCurrRing(new_r);
4860 if (old_r->qideal != NULL)
4861 {
4862 new_r->qideal = idrCopyR(old_r->qideal, old_r, new_r);
4863 }
4864
4865#ifdef HAVE_PLURAL
4866 if( rIsPluralRing(old_r) )
4867 if( nc_SetupQuotient(new_r, old_r, true) )
4868 {
4869#ifndef SING_NDEBUG
4870 WarnS("error in nc_SetupQuotient"); // cleanup? rDelete(res); return r; // just go on...?
4871#endif
4872 }
4873#endif
4874
4875#ifdef HAVE_PLURAL
4876 assume((new_r->qideal==NULL) == (old_r->qideal==NULL));
4880#endif
4881
4882 rTest(new_r);
4883 rTest(old_r);
4884 return new_r;
4885}
4886
4887// use this for global orderings consisting of two blocks
4889{
4890 int r_blocks = rBlocks(r);
4891
4892 assume(b1 == ringorder_c || b1 == ringorder_C ||
4893 b2 == ringorder_c || b2 == ringorder_C ||
4894 b2 == ringorder_S);
4895 if ((r_blocks == 3) &&
4896 (r->order[0] == b1) &&
4897 (r->order[1] == b2) &&
4898 (r->order[2] == 0))
4899 return r;
4900 ring res = rCopy0(r, FALSE, FALSE);
4901 res->order = (rRingOrder_t*)omAlloc0(3*sizeof(rRingOrder_t));
4902 res->block0 = (int*)omAlloc0(3*sizeof(int));
4903 res->block1 = (int*)omAlloc0(3*sizeof(int));
4904 res->wvhdl = (int**)omAlloc0(3*sizeof(int*));
4905 res->order[0] = b1;
4906 res->order[1] = b2;
4907 if (b1 == ringorder_c || b1 == ringorder_C)
4908 {
4909 res->block0[1] = 1;
4910 res->block1[1] = r->N;
4911 }
4912 else
4913 {
4914 res->block0[0] = 1;
4915 res->block1[0] = r->N;
4916 }
4917 rComplete(res, 1);
4918 if (r->qideal!=NULL) res->qideal= idrCopyR_NoSort(r->qideal, r, res);
4919#ifdef HAVE_PLURAL
4920 if (rIsPluralRing(r))
4921 {
4922 if ( nc_rComplete(r, res, false) ) // no qideal!
4923 {
4924#ifndef SING_NDEBUG
4925 WarnS("error in nc_rComplete");
4926#endif
4927 }
4928 }
4929#endif
4930// rChangeCurrRing(res);
4931 return res;
4932}
4933
4935{
4936 int r_blocks = rBlocks(r);
4937
4938 if ((r_blocks == 3) &&
4939 (r->order[0] == ringorder_Wp) &&
4940 (r->order[1] == ringorder_C) &&
4941 (r->order[2] == 0))
4942 {
4943 BOOLEAN ok=TRUE;
4944 for(int i=0;i<r->N;i++)
4945 {
4946 if ((*w)[i]!=r->wvhdl[0][i]) { ok=FALSE;break;}
4947 }
4948 if (ok) return r;
4949 }
4950 ring res = rCopy0(r, FALSE, FALSE);
4951 res->order = (rRingOrder_t*)omAlloc0(3*sizeof(rRingOrder_t));
4952 res->block0 = (int*)omAlloc0(3*sizeof(int));
4953 res->block1 = (int*)omAlloc0(3*sizeof(int));
4954 res->wvhdl = (int**)omAlloc0(3*sizeof(int*));
4955 res->order[0] = ringorder_Wp;
4956 res->order[1] = ringorder_C;
4957 res->block0[1] = 1;
4958 res->block1[1] = r->N;
4959 res->wvhdl[0]=(int*)omAlloc(r->N*sizeof(int));
4960 for(int i=0;i<r->N;i++)
4961 {
4962 r->wvhdl[0][i]=(*w)[i];
4963 }
4964 rComplete(res, 1);
4965 if (r->qideal!=NULL) res->qideal= idrCopyR_NoSort(r->qideal, r, res);
4966#ifdef HAVE_PLURAL
4967 if (rIsPluralRing(r))
4968 {
4969 if ( nc_rComplete(r, res, false) ) // no qideal!
4970 {
4971#ifndef SING_NDEBUG
4972 WarnS("error in nc_rComplete");
4973#endif
4974 }
4975 }
4976#endif
4977// rChangeCurrRing(res);
4978 return res;
4979}
4980
4981ring rAssure_InducedSchreyerOrdering(const ring r, BOOLEAN complete/* = TRUE*/, int sgn/* = 1*/)
4982{ // TODO: ???? Add leading Syz-comp ordering here...????
4983
4984#if MYTEST
4985 Print("rAssure_InducedSchreyerOrdering(r, complete = %d, sgn = %d): r: \n", complete, sgn);
4986 rWrite(r);
4987#ifdef RDEBUG
4988 rDebugPrint(r);
4989#endif
4990 PrintLn();
4991#endif
4992 assume((sgn == 1) || (sgn == -1));
4993
4994 ring res=rCopy0(r, FALSE, FALSE); // No qideal & ordering copy.
4995
4996 int n = rBlocks(r); // Including trailing zero!
4997
4998 // Create 2 more blocks for prefix/suffix:
4999 res->order=(rRingOrder_t *)omAlloc0((n+2)*sizeof(rRingOrder_t)); // 0 .. n+1
5000 res->block0=(int *)omAlloc0((n+2)*sizeof(int));
5001 res->block1=(int *)omAlloc0((n+2)*sizeof(int));
5002 int ** wvhdl =(int **)omAlloc0((n+2)*sizeof(int**));
5003
5004 // Encapsulate all existing blocks between induced Schreyer ordering markers: prefix and suffix!
5005 // Note that prefix and suffix have the same ringorder marker and only differ in block[] parameters!
5006
5007 // new 1st block
5008 int j = 0;
5009 res->order[j] = ringorder_IS; // Prefix
5010 res->block0[j] = res->block1[j] = 0;
5011 // wvhdl[j] = NULL;
5012 j++;
5013
5014 for(int i = 0; (i <= n) && (r->order[i] != 0); i++, j++) // i = [0 .. n-1] <- non-zero old blocks
5015 {
5016 res->order [j] = r->order [i];
5017 res->block0[j] = r->block0[i];
5018 res->block1[j] = r->block1[i];
5019
5020 if (r->wvhdl[i] != NULL)
5021 {
5022 #ifdef HAVE_OMALLOC
5023 wvhdl[j] = (int*) omMemDup(r->wvhdl[i]);
5024 #else
5025 {
5026 int l=(r->block1[i]-r->block0[i]+1);
5027 if (r->order[i]==ringorder_a64) l*=2;
5028 else if (r->order[i]==ringorder_M) l=l*l;
5029 else if (r->order[i]==ringorder_am)
5030 {
5031 l+=r->wvhdl[i][r->block1[i]-r->block0[i]+1]+1;
5032 }
5033 wvhdl[j]=(int*)omalloc(l*sizeof(int));
5034 memcpy(wvhdl[j],r->wvhdl[i],l*sizeof(int));
5035 }
5036 #endif
5037 } // else wvhdl[j] = NULL;
5038 }
5039
5040 // new last block
5041 res->order [j] = ringorder_IS; // Suffix
5042 res->block0[j] = res->block1[j] = sgn; // Sign of v[o]: 1 for C, -1 for c
5043 // wvhdl[j] = NULL;
5044 j++;
5045
5046 // res->order [j] = 0; // The End!
5047 res->wvhdl = wvhdl;
5048
5049 // j == the last zero block now!
5050 assume(j == (n+1));
5051 assume(res->order[0]==ringorder_IS);
5052 assume(res->order[j-1]==ringorder_IS);
5053 assume(res->order[j]==0);
5054
5055
5056 if (complete)
5057 {
5058 rComplete(res, 1);
5059
5060#ifdef HAVE_PLURAL
5061 if (rIsPluralRing(r))
5062 {
5063 if ( nc_rComplete(r, res, false) ) // no qideal!
5064 {
5065#ifndef SING_NDEBUG
5066 WarnS("error in nc_rComplete"); // cleanup?// rDelete(res);// return r; // just go on..
5067#endif
5068 }
5069 }
5071#endif
5072
5073
5074#ifdef HAVE_PLURAL
5075 ring old_ring = r;
5076#endif
5077
5078 if (r->qideal!=NULL)
5079 {
5080 res->qideal= idrCopyR_NoSort(r->qideal, r, res);
5081
5082 assume(id_RankFreeModule(res->qideal, res) == 0);
5083
5084#ifdef HAVE_PLURAL
5085 if( rIsPluralRing(res) )
5086 if( nc_SetupQuotient(res, r, true) )
5087 {
5088// WarnS("error in nc_SetupQuotient"); // cleanup? rDelete(res); return r; // just go on...?
5089 }
5090
5091#endif
5092 assume(id_RankFreeModule(res->qideal, res) == 0);
5093 }
5094
5095#ifdef HAVE_PLURAL
5096 assume((res->qideal==NULL) == (old_ring->qideal==NULL));
5100#endif
5101 }
5102
5103 return res;
5104}
5105
5107{
5109}
5110
5112{
5114}
5115
5117{
5119}
5120
5122{
5124}
5125
5127{
5129}
5130
5131
5132
5133/// Finds p^th IS ordering, and returns its position in r->typ[]
5134/// returns -1 if something went wrong!
5135/// p - starts with 0!
5136int rGetISPos(const int p, const ring r)
5137{
5138 // Put the reference set F into the ring -ordering -recor
5139#if MYTEST
5140 Print("rIsIS(p: %d)\nF:", p);
5141 PrintLn();
5142#endif
5143
5144 if (r->typ==NULL)
5145 {
5146// dReportError("'rIsIS:' Error: wrong ring! (typ == NULL)");
5147 return -1;
5148 }
5149
5150 int j = p; // Which IS record to use...
5151 for( int pos = 0; pos < r->OrdSize; pos++ )
5152 if( r->typ[pos].ord_typ == ro_is)
5153 if( j-- == 0 )
5154 return pos;
5155
5156 return -1;
5157}
5158
5159
5160
5161
5162
5163
5164/// Changes r by setting induced ordering parameters: limit and reference leading terms
5165/// F belong to r, we will DO a copy!
5166/// We will use it AS IS!
5167/// returns true is everything was alright!
5168BOOLEAN rSetISReference(const ring r, const ideal F, const int i, const int p)
5169{
5170 // Put the reference set F into the ring -ordering -recor
5171
5172 if (r->typ==NULL)
5173 {
5174 dReportError("Error: WRONG USE of rSetISReference: wrong ring! (typ == NULL)");
5175 return FALSE;
5176 }
5177
5178
5179 int pos = rGetISPos(p, r);
5180
5181 if( pos == -1 )
5182 {
5183 dReportError("Error: WRONG USE of rSetISReference: specified ordering block was not found!!!" );
5184 return FALSE;
5185 }
5186
5187#if MYTEST
5188 if( i != r->typ[pos].data.is.limit )
5189 Print("Changing record on pos: %d\nOld limit: %d --->> New Limit: %d\n", pos, r->typ[pos].data.is.limit, i);
5190#endif
5191
5192 const ideal FF = idrHeadR(F, r, r); // id_Copy(F, r); // ???
5193
5194
5195 if( r->typ[pos].data.is.F != NULL)
5196 {
5197#if MYTEST
5198 PrintS("Deleting old reference set F... \n"); // idShow(r->typ[pos].data.is.F, r); PrintLn();
5199#endif
5200 id_Delete(&r->typ[pos].data.is.F, r);
5201 r->typ[pos].data.is.F = NULL;
5202 }
5203
5204 assume(r->typ[pos].data.is.F == NULL);
5205
5206 r->typ[pos].data.is.F = FF; // F is owened by ring now! TODO: delete at the end!
5207
5208 r->typ[pos].data.is.limit = i; // First induced component
5209
5210#if MYTEST
5211 PrintS("New reference set FF : \n"); idShow(FF, r, r, 1); PrintLn();
5212#endif
5213
5214 return TRUE;
5215}
5216
5217#ifdef PDEBUG
5219#endif
5220
5221
5222void rSetSyzComp(int k, const ring r)
5223{
5224 if(k < 0)
5225 {
5226 dReportError("rSetSyzComp with negative limit!");
5227 return;
5228 }
5229
5230 assume( k >= 0 );
5231 if (TEST_OPT_PROT) Print("{%d}", k);
5232 if ((r->typ!=NULL) && (r->typ[0].ord_typ==ro_syz))
5233 {
5234 r->block0[0]=r->block1[0] = k;
5235 if( k == r->typ[0].data.syz.limit )
5236 return; // nothing to do
5237
5238 int i;
5239 if (r->typ[0].data.syz.limit == 0)
5240 {
5241 r->typ[0].data.syz.syz_index = (int*) omAlloc0((k+1)*sizeof(int));
5242 r->typ[0].data.syz.syz_index[0] = 0;
5243 r->typ[0].data.syz.curr_index = 1;
5244 }
5245 else
5246 {
5247 r->typ[0].data.syz.syz_index = (int*)
5248 omReallocSize(r->typ[0].data.syz.syz_index,
5249 (r->typ[0].data.syz.limit+1)*sizeof(int),
5250 (k+1)*sizeof(int));
5251 }
5252 for (i=r->typ[0].data.syz.limit + 1; i<= k; i++)
5253 {
5254 r->typ[0].data.syz.syz_index[i] =
5255 r->typ[0].data.syz.curr_index;
5256 }
5257 if(k < r->typ[0].data.syz.limit) // ?
5258 {
5259#ifndef SING_NDEBUG
5260 Warn("rSetSyzComp called with smaller limit (%d) as before (%d)", k, r->typ[0].data.syz.limit);
5261#endif
5262 r->typ[0].data.syz.curr_index = 1 + r->typ[0].data.syz.syz_index[k];
5263 }
5264
5265
5266 r->typ[0].data.syz.limit = k;
5267 r->typ[0].data.syz.curr_index++;
5268 }
5269 else if(
5270 (r->typ!=NULL) &&
5271 (r->typ[0].ord_typ==ro_isTemp)
5272 )
5273 {
5274// (r->typ[currRing->typ[0].data.isTemp.suffixpos].data.is.limit == k)
5275#ifndef SING_NDEBUG
5276 Warn("rSetSyzComp(%d) in an IS ring! Be careful!", k);
5277#endif
5278 }
5279 else if (r->order[0]==ringorder_s)
5280 {
5281 r->block0[0] = r->block1[0] = k;
5282 }
5283 else if (r->order[0]!=ringorder_c)
5284 {
5285 dReportError("syzcomp in incompatible ring");
5286 }
5287#ifdef PDEBUG
5289 pDBsyzComp=k;
5290#endif
5291}
5292
5293// return the max-comonent wchich has syzIndex i
5294int rGetMaxSyzComp(int i, const ring r)
5295{
5296 if ((r->typ!=NULL) && (r->typ[0].ord_typ==ro_syz) &&
5297 r->typ[0].data.syz.limit > 0 && i > 0)
5298 {
5299 assume(i <= r->typ[0].data.syz.limit);
5300 int j;
5301 for (j=0; j<r->typ[0].data.syz.limit; j++)
5302 {
5303 if (r->typ[0].data.syz.syz_index[j] == i &&
5304 r->typ[0].data.syz.syz_index[j+1] != i)
5305 {
5306 assume(r->typ[0].data.syz.syz_index[j+1] == i+1);
5307 return j;
5308 }
5309 }
5310 return r->typ[0].data.syz.limit;
5311 }
5312 else
5313 {
5314 #ifndef SING_NDEBUG
5315 WarnS("rGetMaxSyzComp: order c");
5316 #endif
5317 return 0;
5318 }
5319}
5320
5322{
5323 assume(r != NULL);
5324 int lb = rBlocks(r) - 2;
5325 return (r->order[lb] == ringorder_c || r->order[lb] == ringorder_C);
5326}
5327
5329{
5330 if ((r->order[0]==ringorder_dp) &&(r->block0[0]==1) &&(r->block1[0]==r->N))
5331 return TRUE;
5332 if (((r->order[0]==ringorder_c)||(r->order[0]==ringorder_C))
5333 && ((r->order[1]==ringorder_dp) &&(r->block0[1]==1) &&(r->block1[1]==r->N)))
5334 return TRUE;
5335 return FALSE;
5336}
5337
5339{
5340 if ((r->order[0]==ringorder_Dp) &&(r->block0[0]==1) &&(r->block1[0]==r->N))
5341 return TRUE;
5342 if (((r->order[0]==ringorder_c)||(r->order[0]==ringorder_C))
5343 && ((r->order[1]==ringorder_Dp) &&(r->block0[1]==1) &&(r->block1[1]==r->N)))
5344 return TRUE;
5345 return FALSE;
5346}
5347
5349{
5350 if ((r->order[0]==ringorder_lp) &&(r->block0[0]==1) &&(r->block1[0]==r->N))
5351 return TRUE;
5352 if (((r->order[0]==ringorder_c)||(r->order[0]==ringorder_C))
5353 && ((r->order[1]==ringorder_lp) &&(r->block0[1]==1) &&(r->block1[1]==r->N)))
5354 return TRUE;
5355 return FALSE;
5356}
5357
5359{
5360 assume(r!=NULL);
5361 assume(r->OrdSize>0);
5362 int i=0;
5363 while((r->typ[i].ord_typ!=ro_wp64) && (r->typ[i].ord_typ>0)) i++;
5364 if (r->typ[i].ord_typ!=ro_wp64) return NULL; /* should not happen*/
5365 return r->typ[i].data.wp64.weights64;
5366}
5367
5369{
5370 assume(r!=NULL);
5371 assume(r->OrdSize>0);
5372 assume(r->typ[0].ord_typ==ro_wp64);
5373 memcpy(r->typ[0].data.wp64.weights64,wv,r->N*sizeof(int64));
5374}
5375
5376#include <ctype.h>
5377
5378static int rRealloc1(ring r, int size, int pos)
5379{
5380 r->order=(rRingOrder_t*)omReallocSize(r->order, size*sizeof(rRingOrder_t), (size+1)*sizeof(rRingOrder_t));
5381 r->block0=(int*)omReallocSize(r->block0, size*sizeof(int), (size+1)*sizeof(int));
5382 r->block1=(int*)omReallocSize(r->block1, size*sizeof(int), (size+1)*sizeof(int));
5383 r->wvhdl=(int **)omReallocSize(r->wvhdl,size*sizeof(int *), (size+1)*sizeof(int *));
5384 for(int k=size; k>pos; k--) r->wvhdl[k]=r->wvhdl[k-1];
5385 r->order[size]=(rRingOrder_t)0;
5386 size++;
5387 return size;
5388}
5389#if 0 // currently unused
5390static int rReallocM1(ring r, int size, int pos)
5391{
5392 r->order=(int*)omReallocSize(r->order, size*sizeof(int), (size-1)*sizeof(int));
5393 r->block0=(int*)omReallocSize(r->block0, size*sizeof(int), (size-1)*sizeof(int));
5394 r->block1=(int*)omReallocSize(r->block1, size*sizeof(int), (size-1)*sizeof(int));
5395 r->wvhdl=(int **)omReallocSize(r->wvhdl,size*sizeof(int *), (size-1)*sizeof(int *));
5396 for(int k=pos+1; k<size; k++) r->wvhdl[k]=r->wvhdl[k+1];
5397 size--;
5398 return size;
5399}
5400#endif
5401static void rOppWeight(int *w, int l)
5402{
5403 /* works for commutative/Plural; need to be changed for Letterplace */
5404 /* Letterpace: each block of vars needs to be reverted on it own */
5405 int i2=(l+1)/2;
5406 for(int j=0; j<=i2; j++)
5407 {
5408 int t=w[j];
5409 w[j]=w[l-j];
5410 w[l-j]=t;
5411 }
5412}
5413
5414#define rOppVar(R,I) (rVar(R)+1-I)
5415/* nice for Plural, need to be changed for Letterplace: requires also the length of a monomial */
5416
5418 /* creates an opposite algebra of R */
5419 /* that is R^opp, where f (*^opp) g = g*f */
5420 /* treats the case of qring */
5421{
5422 if (src == NULL) return(NULL);
5423
5424 //rChangeCurrRing(src);
5425#ifdef RDEBUG
5426 rTest(src);
5427// rWrite(src);
5428// rDebugPrint(src);
5429#endif
5430
5431 ring r = rCopy0(src,FALSE);
5432 if (src->qideal != NULL)
5433 {
5434 id_Delete(&(r->qideal), src);
5435 }
5436
5437 // change vars v1..vN -> vN..v1
5438 int i;
5439 int i2 = (rVar(r)-1)/2;
5440 for(i=i2; i>=0; i--)
5441 {
5442 // index: 0..N-1
5443 //Print("ex var names: %d <-> %d\n",i,rOppVar(r,i));
5444 // exchange names
5445 char *p;
5446 p = r->names[rVar(r)-1-i];
5447 r->names[rVar(r)-1-i] = r->names[i];
5448 r->names[i] = p;
5449 }
5450// i2=(rVar(r)+1)/2;
5451// for(int i=i2; i>0; i--)
5452// {
5453// // index: 1..N
5454// //Print("ex var places: %d <-> %d\n",i,rVar(r)+1-i);
5455// // exchange VarOffset
5456// int t;
5457// t=r->VarOffset[i];
5458// r->VarOffset[i]=r->VarOffset[rOppVar(r,i)];
5459// r->VarOffset[rOppVar(r,i)]=t;
5460// }
5461 // change names:
5462 // TODO: does this work the same way for Letterplace?
5463 for (i=rVar(r)-1; i>=0; i--)
5464 {
5465 char *p=r->names[i];
5466 if(isupper(*p)) *p = tolower(*p);
5467 else *p = toupper(*p);
5468 }
5469 // change ordering: listing
5470 // change ordering: compare
5471// for(i=0; i<r->OrdSize; i++)
5472// {
5473// int t,tt;
5474// switch(r->typ[i].ord_typ)
5475// {
5476// case ro_dp:
5477// //
5478// t=r->typ[i].data.dp.start;
5479// r->typ[i].data.dp.start=rOppVar(r,r->typ[i].data.dp.end);
5480// r->typ[i].data.dp.end=rOppVar(r,t);
5481// break;
5482// case ro_wp:
5483// case ro_wp_neg:
5484// {
5485// t=r->typ[i].data.wp.start;
5486// r->typ[i].data.wp.start=rOppVar(r,r->typ[i].data.wp.end);
5487// r->typ[i].data.wp.end=rOppVar(r,t);
5488// // invert r->typ[i].data.wp.weights
5489// rOppWeight(r->typ[i].data.wp.weights,
5490// r->typ[i].data.wp.end-r->typ[i].data.wp.start);
5491// break;
5492// }
5493// //case ro_wp64:
5494// case ro_syzcomp:
5495// case ro_syz:
5496// WerrorS("not implemented in rOpposite");
5497// // should not happen
5498// break;
5499//
5500// case ro_cp:
5501// t=r->typ[i].data.cp.start;
5502// r->typ[i].data.cp.start=rOppVar(r,r->typ[i].data.cp.end);
5503// r->typ[i].data.cp.end=rOppVar(r,t);
5504// break;
5505// case ro_none:
5506// default:
5507// Werror("unknown type in rOpposite(%d)",r->typ[i].ord_typ);
5508// break;
5509// }
5510// }
5511 // Change order/block structures (needed for rPrint, rAdd etc.)
5512
5513 int j=0;
5514 int l=rBlocks(src);
5515 if ( ! rIsLPRing(src) )
5516 {
5517 // ie Plural or commutative
5518 for(i=0; src->order[i]!=0; i++)
5519 {
5520 switch (src->order[i])
5521 {
5522 case ringorder_c: /* c-> c */
5523 case ringorder_C: /* C-> C */
5524 case ringorder_no /*=0*/: /* end-of-block */
5525 r->order[j]=src->order[i];
5526 j++; break;
5527 case ringorder_lp: /* lp -> rp */
5528 r->order[j]=ringorder_rp;
5529 r->block0[j]=rOppVar(r, src->block1[i]);
5530 r->block1[j]=rOppVar(r, src->block0[i]);
5531 j++;break;
5532 case ringorder_rp: /* rp -> lp */
5533 r->order[j]=ringorder_lp;
5534 r->block0[j]=rOppVar(r, src->block1[i]);
5535 r->block1[j]=rOppVar(r, src->block0[i]);
5536 j++;break;
5537 case ringorder_dp: /* dp -> a(1..1),ls */
5538 {
5539 l=rRealloc1(r,l,j);
5540 r->order[j]=ringorder_a;
5541 r->block0[j]=rOppVar(r, src->block1[i]);
5542 r->block1[j]=rOppVar(r, src->block0[i]);
5543 r->wvhdl[j]=(int*)omAlloc((r->block1[j]-r->block0[j]+1)*sizeof(int));
5544 for(int k=r->block0[j]; k<=r->block1[j]; k++)
5545 r->wvhdl[j][k-r->block0[j]]=1;
5546 j++;
5547 r->order[j]=ringorder_ls;
5548 r->block0[j]=rOppVar(r, src->block1[i]);
5549 r->block1[j]=rOppVar(r, src->block0[i]);
5550 j++;
5551 break;
5552 }
5553 case ringorder_Dp: /* Dp -> a(1..1),rp */
5554 {
5555 l=rRealloc1(r,l,j);
5556 r->order[j]=ringorder_a;
5557 r->block0[j]=rOppVar(r, src->block1[i]);
5558 r->block1[j]=rOppVar(r, src->block0[i]);
5559 r->wvhdl[j]=(int*)omAlloc((r->block1[j]-r->block0[j]+1)*sizeof(int));
5560 for(int k=r->block0[j]; k<=r->block1[j]; k++)
5561 r->wvhdl[j][k-r->block0[j]]=1;
5562 j++;
5563 r->order[j]=ringorder_rp;
5564 r->block0[j]=rOppVar(r, src->block1[i]);
5565 r->block1[j]=rOppVar(r, src->block0[i]);
5566 j++;
5567 break;
5568 }
5569 case ringorder_wp: /* wp -> a(...),ls */
5570 {
5571 l=rRealloc1(r,l,j);
5572 r->order[j]=ringorder_a;
5573 r->block0[j]=rOppVar(r, src->block1[i]);
5574 r->block1[j]=rOppVar(r, src->block0[i]);
5575 r->wvhdl[j]=r->wvhdl[j+1]; r->wvhdl[j+1]=NULL;
5576 rOppWeight(r->wvhdl[j], r->block1[j]-r->block0[j]);
5577 j++;
5578 r->order[j]=ringorder_ls;
5579 r->block0[j]=rOppVar(r, src->block1[i]);
5580 r->block1[j]=rOppVar(r, src->block0[i]);
5581 j++;
5582 break;
5583 }
5584 case ringorder_Wp: /* Wp -> a(...),rp */
5585 {
5586 l=rRealloc1(r,l,j);
5587 r->order[j]=ringorder_a;
5588 r->block0[j]=rOppVar(r, src->block1[i]);
5589 r->block1[j]=rOppVar(r, src->block0[i]);
5590 r->wvhdl[j]=r->wvhdl[j+1]; r->wvhdl[j+1]=NULL;
5591 rOppWeight(r->wvhdl[j], r->block1[j]-r->block0[j]);
5592 j++;
5593 r->order[j]=ringorder_rp;
5594 r->block0[j]=rOppVar(r, src->block1[i]);
5595 r->block1[j]=rOppVar(r, src->block0[i]);
5596 j++;
5597 break;
5598 }
5599 case ringorder_M: /* M -> M */
5600 {
5601 r->order[j]=ringorder_M;
5602 r->block0[j]=rOppVar(r, src->block1[i]);
5603 r->block1[j]=rOppVar(r, src->block0[i]);
5604 int n=r->block1[j]-r->block0[j];
5605 /* M is a (n+1)x(n+1) matrix */
5606 for (int nn=0; nn<=n; nn++)
5607 {
5608 rOppWeight(&(r->wvhdl[j][nn*(n+1)]), n /*r->block1[j]-r->block0[j]*/);
5609 }
5610 j++;
5611 break;
5612 }
5613 case ringorder_a: /* a(...),ls -> wp/dp */
5614 {
5615 r->block0[j]=rOppVar(r, src->block1[i]);
5616 r->block1[j]=rOppVar(r, src->block0[i]);
5617 rOppWeight(r->wvhdl[j], r->block1[j]-r->block0[j]);
5618 if (src->order[i+1]==ringorder_ls)
5619 {
5620 r->order[j]=ringorder_wp;
5621 i++;
5622 //l=rReallocM1(r,l,j);
5623 }
5624 else
5625 {
5626 r->order[j]=ringorder_a;
5627 }
5628 j++;
5629 break;
5630 }
5631 default:
5632 #if 0
5633 // not yet done:
5634 case ringorder_ls:
5635 case ringorder_rs:
5636 case ringorder_ds:
5637 case ringorder_Ds:
5638 case ringorder_ws:
5639 case ringorder_Ws:
5640 case ringorder_am:
5641 case ringorder_a64:
5642 // should not occur:
5643 case ringorder_S:
5644 case ringorder_IS:
5645 case ringorder_s:
5646 case ringorder_aa:
5647 case ringorder_L:
5648 case ringorder_unspec:
5649 #endif
5650 Werror("order %s not (yet) supported", rSimpleOrdStr(src->order[i]));
5651 break;
5652 }
5653 }
5654 } /* end if (!rIsLPRing(src)) */
5655 if (rIsLPRing(src))
5656 {
5657 // applies to Letterplace only
5658 // Letterplace conventions: dp<->Dp, lp<->rp
5659 // Wp(v) cannot be converted since wp(v) does not encode a monomial ordering
5660 // (a(w),<) is troublesome and thus postponed
5661 for(i=0; src->order[i]!=0; i++)
5662 {
5663 switch (src->order[i])
5664 {
5665 case ringorder_c: /* c-> c */
5666 case ringorder_C: /* C-> C */
5667 case ringorder_no /*=0*/: /* end-of-block */
5668 r->order[j]=src->order[i];
5669 j++; break;
5670 case ringorder_lp: /* lp -> rp */
5671 r->order[j]=ringorder_rp;
5672 r->block0[j]=rOppVar(r, src->block1[i]);
5673 r->block1[j]=rOppVar(r, src->block0[i]);
5674 j++;break;
5675 case ringorder_rp: /* rp -> lp */
5676 r->order[j]=ringorder_lp;
5677 r->block0[j]=rOppVar(r, src->block1[i]);
5678 r->block1[j]=rOppVar(r, src->block0[i]);
5679 j++;break;
5680 case ringorder_dp: /* dp -> Dp */
5681 {
5682 r->order[j]=ringorder_Dp;
5683 r->block0[j]=rOppVar(r, src->block1[i]);
5684 r->block1[j]=rOppVar(r, src->block0[i]);
5685 j++;break;
5686 }
5687 case ringorder_Dp: /* Dp -> dp*/
5688 {
5689 r->order[j]=ringorder_dp;
5690 r->block0[j]=rOppVar(r, src->block1[i]);
5691 r->block1[j]=rOppVar(r, src->block0[i]);
5692 j++;break;
5693 }
5694 // not clear how to do:
5695 case ringorder_wp:
5696 case ringorder_Wp:
5697 case ringorder_M:
5698 case ringorder_a:
5699 // not yet done:
5700 case ringorder_ls:
5701 case ringorder_rs:
5702 case ringorder_ds:
5703 case ringorder_Ds:
5704 case ringorder_ws:
5705 case ringorder_Ws:
5706 case ringorder_am:
5707 case ringorder_a64:
5708 case ringorder_Ip:
5709 // should not occur:
5710 case ringorder_S:
5711 case ringorder_IS:
5712 case ringorder_s:
5713 case ringorder_aa:
5714 case ringorder_L:
5715 case ringorder_unspec:
5716 Werror("order %s not (yet) supported", rSimpleOrdStr(src->order[i]));
5717 break;
5718 }
5719 }
5720 } /* end if (rIsLPRing(src)) */
5721 rComplete(r);
5722
5723 //rChangeCurrRing(r);
5724#ifdef RDEBUG
5725 rTest(r);
5726// rWrite(r);
5727// rDebugPrint(r);
5728#endif
5729
5730#ifdef HAVE_PLURAL
5731 // now, we initialize a non-comm structure on r
5732 if (rIsPluralRing(src))
5733 {
5734// assume( currRing == r);
5735
5736 int *perm = (int *)omAlloc0((rVar(r)+1)*sizeof(int));
5737 int *par_perm = NULL;
5738 nMapFunc nMap = n_SetMap(src->cf,r->cf);
5739 int ni,nj;
5740 for(i=1; i<=r->N; i++)
5741 {
5742 perm[i] = rOppVar(r,i);
5743 }
5744
5745 matrix C = mpNew(rVar(r),rVar(r));
5746 matrix D = mpNew(rVar(r),rVar(r));
5747
5748 for (i=1; i< rVar(r); i++)
5749 {
5750 for (j=i+1; j<=rVar(r); j++)
5751 {
5752 ni = r->N +1 - i;
5753 nj = r->N +1 - j; /* i<j ==> nj < ni */
5754
5755 assume(MATELEM(src->GetNC()->C,i,j) != NULL);
5756 MATELEM(C,nj,ni) = p_PermPoly(MATELEM(src->GetNC()->C,i,j),perm,src,r, nMap,par_perm,rPar(src));
5757
5758 if(MATELEM(src->GetNC()->D,i,j) != NULL)
5759 MATELEM(D,nj,ni) = p_PermPoly(MATELEM(src->GetNC()->D,i,j),perm,src,r, nMap,par_perm,rPar(src));
5760 }
5761 }
5762
5763 id_Test((ideal)C, r);
5764 id_Test((ideal)D, r);
5765
5766 if (nc_CallPlural(C, D, NULL, NULL, r, false, false, true, r)) // no qring setup!
5767 WarnS("Error initializing non-commutative multiplication!");
5768
5769#ifdef RDEBUG
5770 rTest(r);
5771// rWrite(r);
5772// rDebugPrint(r);
5773#endif
5774
5775 assume( r->GetNC()->IsSkewConstant == src->GetNC()->IsSkewConstant);
5776
5777 omFreeSize((ADDRESS)perm,(rVar(r)+1)*sizeof(int));
5778 }
5779#endif /* HAVE_PLURAL */
5780
5781 /* now oppose the qideal for qrings */
5782 if (src->qideal != NULL)
5783 {
5784#ifdef HAVE_PLURAL
5785 r->qideal = idOppose(src, src->qideal, r); // into the currRing: r
5786#else
5787 r->qideal = id_Copy(src->qideal, r); // ?
5788#endif
5789
5790#ifdef HAVE_PLURAL
5791 if( rIsPluralRing(r) )
5792 {
5794#ifdef RDEBUG
5795 rTest(r);
5796// rWrite(r);
5797// rDebugPrint(r);
5798#endif
5799 }
5800#endif
5801 }
5802#ifdef HAVE_PLURAL
5803 if( rIsPluralRing(r) )
5804 assume( ncRingType(r) == ncRingType(src) );
5805#endif
5806 rTest(r);
5807
5808 return r;
5809}
5810
5812 /* creates an enveloping algebra of R */
5813 /* that is R^e = R \tensor_K R^opp */
5814{
5815 ring Ropp = rOpposite(R);
5816 ring Renv = NULL;
5817 int stat = rSum(R, Ropp, Renv); /* takes care of qideals */
5818 if ( stat <=0 )
5819 WarnS("Error in rEnvelope at rSum");
5820 rTest(Renv);
5821 return Renv;
5822}
5823
5824#ifdef HAVE_PLURAL
5826/* returns TRUE is there were errors */
5827/* dest is actually equals src with the different ordering */
5828/* we map src->nc correctly to dest->src */
5829/* to be executed after rComplete, before rChangeCurrRing */
5830{
5831// NOTE: Originally used only by idElimination to transfer NC structure to dest
5832// ring created by dirty hack (without nc_CallPlural)
5833 rTest(src);
5834
5835 assume(!rIsPluralRing(dest)); // destination must be a newly constructed commutative ring
5836
5837 if (!rIsPluralRing(src))
5838 {
5839 return FALSE;
5840 }
5841
5842 const int N = dest->N;
5843
5844 assume(src->N == N);
5845
5846// ring save = currRing;
5847
5848// if (dest != save)
5849// rChangeCurrRing(dest);
5850
5851 const ring srcBase = src;
5852
5853 assume( n_SetMap(srcBase->cf,dest->cf) == n_SetMap(dest->cf,dest->cf) ); // currRing is important here!
5854
5855 matrix C = mpNew(N,N); // ring independent
5856 matrix D = mpNew(N,N);
5857
5858 matrix C0 = src->GetNC()->C;
5859 matrix D0 = src->GetNC()->D;
5860
5861 // map C and D into dest
5862 for (int i = 1; i < N; i++)
5863 {
5864 for (int j = i + 1; j <= N; j++)
5865 {
5866 const number n = n_Copy(p_GetCoeff(MATELEM(C0,i,j), srcBase), srcBase->cf); // src, mapping for coeffs into currRing = dest!
5867 const poly p = p_NSet(n, dest);
5868 MATELEM(C,i,j) = p;
5869 if (MATELEM(D0,i,j) != NULL)
5870 MATELEM(D,i,j) = prCopyR(MATELEM(D0,i,j), srcBase, dest); // ?
5871 }
5872 }
5873 /* One must test C and D _only_ in r->GetNC()->basering!!! not in r!!! */
5874
5875 id_Test((ideal)C, dest);
5876 id_Test((ideal)D, dest);
5877
5878 if (nc_CallPlural(C, D, NULL, NULL, dest, bSetupQuotient, false, true, dest)) // also takes care about quotient ideal
5879 {
5880 //WarnS("Error transferring non-commutative structure");
5881 // error message should be in the interpreter interface
5882
5883 mp_Delete(&C, dest);
5884 mp_Delete(&D, dest);
5885
5886// if (currRing != save)
5887// rChangeCurrRing(save);
5888
5889 return TRUE;
5890 }
5891
5892// mp_Delete(&C, dest); // used by nc_CallPlural!
5893// mp_Delete(&D, dest);
5894
5895// if (dest != save)
5896// rChangeCurrRing(save);
5897
5898 assume(rIsPluralRing(dest));
5899 return FALSE;
5900}
5901#endif
5902
5903poly rGetVar(const int varIndex, const ring r)
5904{
5905 poly p = p_ISet(1, r);
5906 p_SetExp(p, varIndex, 1, r);
5907 p_Setm(p, r);
5908 return p;
5909}
5910
5911
5912/// TODO: rewrite somehow...
5913int n_IsParam(const number m, const ring r)
5914{
5915 assume(r != NULL);
5916 const coeffs C = r->cf;
5917 assume(C != NULL);
5918
5920
5922
5923 if(( _filed_type == n_algExt )||( _filed_type == n_polyExt ))
5924 return naIsParam(m, C);
5925
5926 if( _filed_type == n_transExt )
5927 return ntIsParam(m, C);
5928
5929 Werror("n_IsParam: IsParam is not to be used for (coeff_type = %d)",getCoeffType(C));
5930
5931 return 0;
5932}
5933
5934ring rPlusVar(const ring r, char *v,int left)
5935{
5936 if (r->order[2]!=0)
5937 {
5938 WerrorS("only for rings with an ordering of one block");
5939 return NULL;
5940 }
5941 int p;
5942 if((r->order[0]==ringorder_C)
5943 ||(r->order[0]==ringorder_c))
5944 p=1;
5945 else
5946 p=0;
5947 if((r->order[p]!=ringorder_dp)
5948 && (r->order[p]!=ringorder_Dp)
5949 && (r->order[p]!=ringorder_lp)
5950 && (r->order[p]!=ringorder_rp)
5951 && (r->order[p]!=ringorder_ds)
5952 && (r->order[p]!=ringorder_Ds)
5953 && (r->order[p]!=ringorder_ls))
5954 {
5955 WerrorS("ordering must be dp,Dp,lp,rp,ds,Ds or ls");
5956 return NULL;
5957 }
5958 for(int i=r->N-1;i>=0;i--)
5959 {
5960 if (strcmp(r->names[i],v)==0)
5961 {
5962 Werror("duplicate variable name >>%s<<",v);
5963 return NULL;
5964 }
5965 }
5966 ring R=rCopy0(r);
5967 char **names;
5968 #ifdef HAVE_SHIFTBBA
5969 if (rIsLPRing(r))
5970 {
5971 R->isLPring=r->isLPring+1;
5972 R->N=((r->N)/r->isLPring)+r->N;
5973 names=(char**)omAlloc(R->N*sizeof(char_ptr));
5974 if (left)
5975 {
5976 for(int b=0;b<((r->N)/r->isLPring);b++)
5977 {
5978 names[b*R->isLPring]=omStrDup(v);
5979 for(int i=R->isLPring-1;i>0;i--)
5980 names[i+b*R->isLPring]=R->names[i-1+b*r->isLPring];
5981 }
5982 }
5983 else
5984 {
5985 for(int b=0;b<((r->N)/r->isLPring);b++)
5986 {
5987 names[(b+1)*R->isLPring-1]=omStrDup(v);
5988 for(int i=R->isLPring-2;i>=0;i--)
5989 names[i+b*R->isLPring]=R->names[i+b*r->isLPring];
5990 }
5991 }
5992 }
5993 else
5994 #endif
5995 {
5996 R->N++;
5997 names=(char**)omAlloc(R->N*sizeof(char_ptr));
5998 if (left)
5999 {
6000 names[0]=omStrDup(v);
6001 for(int i=R->N-1;i>0;i--) names[i]=R->names[i-1];
6002 }
6003 else
6004 {
6005 names[R->N-1]=omStrDup(v);
6006 for(int i=R->N-2;i>=0;i--) names[i]=R->names[i];
6007 }
6008 }
6009 omFreeSize(R->names,r->N*sizeof(char_ptr));
6010 R->names=names;
6011 R->block1[p]=R->N;
6012 rComplete(R);
6013 return R;
6014}
6015
6016ring rMinusVar(const ring r, char *v)
6017{
6018 if (r->order[2]!=0)
6019 {
6020 WerrorS("only for rings with an ordering of one block");
6021 return NULL;
6022 }
6023 int p;
6024 if((r->order[0]==ringorder_C)
6025 ||(r->order[0]==ringorder_c))
6026 p=1;
6027 else
6028 p=0;
6029 if((r->order[p]!=ringorder_dp)
6030 && (r->order[p]!=ringorder_Dp)
6031 && (r->order[p]!=ringorder_lp)
6032 && (r->order[p]!=ringorder_rp)
6033 && (r->order[p]!=ringorder_ds)
6034 && (r->order[p]!=ringorder_Ds)
6035 && (r->order[p]!=ringorder_ls))
6036 {
6037 WerrorS("ordering must be dp,Dp,lp,rp,ds,Ds or ls");
6038 return NULL;
6039 }
6040 ring R=rCopy0(r);
6041 int i=R->N-1;
6042 while(i>=0)
6043 {
6044 if (strcmp(R->names[i],v)==0)
6045 {
6046 R->N--;
6047 omFree(R->names[i]);
6048 for(int j=i;j<R->N;j++) R->names[j]=R->names[j+1];
6049 R->names=(char**)omReallocSize(R->names,r->N*sizeof(char_ptr),R->N*sizeof(char_ptr));
6050 }
6051 i--;
6052 }
6053 R->block1[p]=R->N;
6054 rComplete(R,1);
6055 return R;
6056}
int sgn(const Rational &a)
Definition GMPrat.cc:430
int naIsParam(number m, const coeffs cf)
if m == var(i)/1 => return i,
Definition algext.cc:1104
All the auxiliary stuff.
long int64
Definition auxiliary.h:68
static int si_max(const int a, const int b)
Definition auxiliary.h:125
#define BIT_SIZEOF_LONG
Definition auxiliary.h:80
int BOOLEAN
Definition auxiliary.h:88
#define TRUE
Definition auxiliary.h:101
#define FALSE
Definition auxiliary.h:97
int size(const CanonicalForm &f, const Variable &v)
int size ( const CanonicalForm & f, const Variable & v )
Definition cf_ops.cc:600
const CanonicalForm CFMap CFMap & N
Definition cfEzgcd.cc:56
int l
Definition cfEzgcd.cc:100
int m
Definition cfEzgcd.cc:128
int i
Definition cfEzgcd.cc:132
int k
Definition cfEzgcd.cc:99
Variable x
Definition cfModGcd.cc:4090
int p
Definition cfModGcd.cc:4086
CanonicalForm cf
Definition cfModGcd.cc:4091
CanonicalForm b
Definition cfModGcd.cc:4111
int length() const
int length() const
Definition intvec.h:94
Coefficient rings, fields and other domains suitable for Singular polynomials.
static FORCE_INLINE number n_Copy(number n, const coeffs r)
return a copy of 'n'
Definition coeffs.h:455
static FORCE_INLINE void n_CoeffWrite(const coeffs r, BOOLEAN details=TRUE)
output the coeff description
Definition coeffs.h:720
static FORCE_INLINE BOOLEAN nCoeff_is_Extension(const coeffs r)
Definition coeffs.h:839
n_coeffType
Definition coeffs.h:27
@ n_R
single prescision (6,6) real numbers
Definition coeffs.h:31
@ n_polyExt
used to represent polys as coefficients
Definition coeffs.h:34
@ n_Q
rational (GMP) numbers
Definition coeffs.h:30
@ n_Znm
only used if HAVE_RINGS is defined
Definition coeffs.h:45
@ n_algExt
used for all algebraic extensions, i.e., the top-most extension in an extension tower is algebraic
Definition coeffs.h:35
@ n_Zn
only used if HAVE_RINGS is defined
Definition coeffs.h:44
@ n_Zp
\F{p < 2^31}
Definition coeffs.h:29
@ n_transExt
used for all transcendental extensions, i.e., the top-most extension in an extension tower is transce...
Definition coeffs.h:38
static FORCE_INLINE char * nCoeffString(const coeffs cf)
TODO: make it a virtual method of coeffs, together with: Decompose & Compose, rParameter & rPar.
Definition coeffs.h:956
static FORCE_INLINE nMapFunc n_SetMap(const coeffs src, const coeffs dst)
set the mapping function pointers for translating numbers from src to dst
Definition coeffs.h:701
coeffs nInitChar(n_coeffType t, void *parameter)
one-time initialisations for new coeffs in case of an error return NULL
Definition numbers.cc:406
static FORCE_INLINE n_coeffType getCoeffType(const coeffs r)
Returns the type of coeffs domain.
Definition coeffs.h:429
static FORCE_INLINE coeffs nCopyCoeff(const coeffs r)
"copy" coeffs, i.e. increment ref
Definition coeffs.h:437
static FORCE_INLINE BOOLEAN nCoeff_is_algExt(const coeffs r)
TRUE iff r represents an algebraic extension field.
Definition coeffs.h:903
number(* nMapFunc)(number a, const coeffs src, const coeffs dst)
maps "a", which lives in src, into dst
Definition coeffs.h:80
void nKillChar(coeffs r)
undo all initialisations
Definition numbers.cc:556
static FORCE_INLINE BOOLEAN n_IsOne(number n, const coeffs r)
TRUE iff 'n' represents the one element.
Definition coeffs.h:472
#define Print
Definition emacs.cc:80
#define Warn
Definition emacs.cc:77
#define WarnS
Definition emacs.cc:78
#define StringAppend
Definition emacs.cc:79
const CanonicalForm int s
Definition facAbsFact.cc:51
CanonicalForm res
Definition facAbsFact.cc:60
const CanonicalForm & w
Definition facAbsFact.cc:51
const Variable & v
< [in] a sqrfree bivariate poly
Definition facBivar.h:39
bool found
int j
Definition facHensel.cc:110
static int min(int a, int b)
Definition fast_mult.cc:268
void WerrorS(const char *s)
Definition feFopen.cc:24
#define D(A)
Definition gentable.cc:128
#define EXTERN_VAR
Definition globaldefs.h:6
#define VAR
Definition globaldefs.h:5
ideal id_Copy(ideal h1, const ring r)
copy an ideal
static BOOLEAN length(leftv result, leftv arg)
Definition interval.cc:257
static bool rIsSCA(const ring r)
Definition nc.h:190
ideal idOppose(ring Rop_src, ideal I, const ring Rop_dst)
opposes a module I from Rop to currRing(dst)
bool nc_rCopy(ring res, const ring r, bool bSetupQuotient)
bool nc_SetupQuotient(ring rGR, const ring rG=NULL, bool bCopy=false)
static nc_type & ncRingType(nc_struct *p)
Definition nc.h:159
BOOLEAN nc_CallPlural(matrix cc, matrix dd, poly cn, poly dn, ring r, bool bSetupQuotient, bool bCopyInput, bool bBeQuiet, ring curr, bool dummy_ring=false)
returns TRUE if there were errors analyze inputs, check them for consistency detects nc_type,...
void nc_rKill(ring r)
complete destructor
#define UPMATELEM(i, j, nVar)
Definition nc.h:36
bool sca_Force(ring rGR, int b, int e)
Definition sca.cc:1159
void maFindPerm(char const *const *const preim_names, int preim_n, char const *const *const preim_par, int preim_p, char const *const *const names, int n, char const *const *const par, int nop, int *perm, int *par_perm, n_coeffType ch)
Definition maps.cc:163
void mp_Delete(matrix *a, const ring r)
Definition matpol.cc:874
matrix mpNew(int r, int c)
create a r x c zero-matrix
Definition matpol.cc:37
void iiWriteMatrix(matrix im, const char *n, int dim, const ring r, int spaces)
set spaces to zero by default
Definition matpol.cc:828
#define MATELEM(mat, i, j)
1-based access to matrix
Definition matpol.h:29
STATIC_VAR unsigned add[]
Definition misc_ip.cc:108
#define assume(x)
Definition mod2.h:389
int dReportError(const char *fmt,...)
Definition dError.cc:44
#define p_GetComp(p, r)
Definition monomials.h:64
#define pIter(p)
Definition monomials.h:37
#define POLYSIZE
Definition monomials.h:233
#define p_GetCoeff(p, r)
Definition monomials.h:50
gmp_float sqrt(const gmp_float &a)
const int MAX_INT_VAL
Definition mylimits.h:12
The main handler for Singular numbers which are suitable for Singular polynomials.
Definition qr.h:46
#define omStrDup(s)
#define omFreeSize(addr, size)
#define omCheckAddr(addr)
#define omAlloc(size)
#define omReallocSize(addr, o_size, size)
#define omAllocBin(bin)
#define omCheckAddrSize(addr, size)
#define omAlloc0Bin(bin)
#define omalloc(size)
#define omFree(addr)
#define omAlloc0(size)
#define omFreeBin(addr, bin)
#define omMemDup(s)
#define omcheckAddrSize(addr, size)
#define omfreeSize(addr, size)
#define omGetSpecBin(size)
Definition omBin.h:11
#define omUnGetSpecBin(bin_ptr)
Definition omBin.h:14
#define NULL
Definition omList.c:12
omBin_t * omBin
Definition omStructs.h:12
VAR unsigned si_opt_1
Definition options.c:5
#define OPT_INTSTRATEGY
Definition options.h:93
#define OPT_REDTAIL
Definition options.h:92
#define TEST_OPT_OLDSTD
Definition options.h:125
#define OPT_REDTHROUGH
Definition options.h:83
#define Sy_bit(x)
Definition options.h:31
#define TEST_OPT_PROT
Definition options.h:105
void p_ProcsSet(ring r, p_Procs_s *p_Procs)
void p_Debug_GetProcNames(const ring r, p_Procs_s *p_Procs)
void p_Debug_GetSpecNames(const ring r, const char *&field, const char *&length, const char *&ord)
void p_Setm_WFirstTotalDegree(poly p, const ring r)
Definition p_polys.cc:553
long pLDegb(poly p, int *l, const ring r)
Definition p_polys.cc:812
long pLDeg1_Totaldegree(poly p, int *l, const ring r)
Definition p_polys.cc:976
long p_WFirstTotalDegree(poly p, const ring r)
Definition p_polys.cc:595
long pLDeg1_WFirstTotalDegree(poly p, int *l, const ring r)
Definition p_polys.cc:1039
long pLDeg1c_WFirstTotalDegree(poly p, int *l, const ring r)
Definition p_polys.cc:1069
void p_Setm_Dummy(poly p, const ring r)
Definition p_polys.cc:540
void p_Setm_TotalDegree(poly p, const ring r)
Definition p_polys.cc:546
poly p_ISet(long i, const ring r)
returns the poly representing the integer i
Definition p_polys.cc:1298
long pLDeg1c_Deg(poly p, int *l, const ring r)
Definition p_polys.cc:942
long pLDeg1(poly p, int *l, const ring r)
Definition p_polys.cc:842
poly p_PermPoly(poly p, const int *perm, const ring oldRing, const ring dst, nMapFunc nMap, const int *par_perm, int OldPar, BOOLEAN use_mult)
Definition p_polys.cc:4211
long pLDeg1_Deg(poly p, int *l, const ring r)
Definition p_polys.cc:911
long p_WTotaldegree(poly p, const ring r)
Definition p_polys.cc:612
p_SetmProc p_GetSetmProc(const ring r)
Definition p_polys.cc:559
void p_Setm_General(poly p, const ring r)
Definition p_polys.cc:158
long pLDeg1c(poly p, int *l, const ring r)
Definition p_polys.cc:878
long pLDeg1c_Totaldegree(poly p, int *l, const ring r)
Definition p_polys.cc:1006
long pLDeg0c(poly p, int *l, const ring r)
Definition p_polys.cc:771
long pLDeg0(poly p, int *l, const ring r)
Definition p_polys.cc:740
poly p_One(const ring r)
Definition p_polys.cc:1314
poly p_NSet(number n, const ring r)
returns the poly representing the number n, destroys n
Definition p_polys.cc:1474
long p_Deg(poly a, const ring r)
Definition p_polys.cc:586
BOOLEAN p_EqualPolys(poly p1, poly p2, const ring r)
Definition p_polys.cc:4621
static long p_FDeg(const poly p, const ring r)
Definition p_polys.h:382
void p_Write(poly p, ring lmRing, ring tailRing)
Definition polys0.cc:342
static unsigned long p_SetExp(poly p, const unsigned long e, const unsigned long iBitmask, const int VarOffset)
set a single variable exponent @Note: VarOffset encodes the position in p->exp
Definition p_polys.h:490
static void p_Setm(poly p, const ring r)
Definition p_polys.h:235
static long p_GetExp(const poly p, const unsigned long iBitmask, const int VarOffset)
get a single variable exponent @Note: the integer VarOffset encodes:
Definition p_polys.h:471
static void p_Delete(poly *p, const ring r)
Definition p_polys.h:903
void p_Write0(poly p, ring lmRing, ring tailRing)
Definition polys0.cc:332
static long p_Totaldegree(poly p, const ring r)
Definition p_polys.h:1523
poly prCopyR(poly p, ring src_r, ring dest_r)
Definition prCopy.cc:34
ideal idrCopyR(ideal id, ring src_r, ring dest_r)
Definition prCopy.cc:192
ideal idrCopyR_NoSort(ideal id, ring src_r, ring dest_r)
Definition prCopy.cc:205
ideal idrHeadR(ideal id, ring r, ring dest_r)
Copy leading terms of id[i] via prHeeadR into dest_r.
Definition prCopy.cc:156
void StringSetS(const char *st)
Definition reporter.cc:128
void StringAppendS(const char *st)
Definition reporter.cc:107
void PrintS(const char *s)
Definition reporter.cc:284
char * StringEndS()
Definition reporter.cc:151
void PrintLn()
Definition reporter.cc:310
void Werror(const char *fmt,...)
Definition reporter.cc:189
static void rSetNegWeight(ring r)
Definition ring.cc:3416
BOOLEAN rOrd_SetCompRequiresSetm(const ring r)
return TRUE if p_SetComp requires p_Setm
Definition ring.cc:2014
static void rO_ISSuffix(int &place, int &bitplace, int &prev_ord, long *o, int N, int *v, sro_ord *tmp_typ, int &typ_i, int sgn)
Definition ring.cc:2530
int rSum(ring r1, ring r2, ring &sum)
Definition ring.cc:1405
ring rAssure_TDeg(ring r, int &pos)
Definition ring.cc:4611
void rWrite(ring r, BOOLEAN details)
Definition ring.cc:227
ring rAssure_InducedSchreyerOrdering(const ring r, BOOLEAN complete, int sgn)
Definition ring.cc:4981
static ring rAssure_Global(rRingOrder_t b1, rRingOrder_t b2, const ring r)
Definition ring.cc:4888
BOOLEAN rOrder_is_WeightedOrdering(rRingOrder_t order)
Definition ring.cc:1968
void rGetSComps(int **currComponents, long **currShiftedComponents, int *length, ring r)
Definition ring.cc:4498
BOOLEAN rRing_ord_pure_Dp(const ring r)
Definition ring.cc:5338
static void rNChangeSComps(int *currComponents, long *currShiftedComponents, ring r)
Definition ring.cc:4451
ring rModifyRing_Wp(ring r, int *weights)
construct Wp, C ring
Definition ring.cc:2996
BOOLEAN rOrder_is_DegOrdering(const rRingOrder_t order)
Definition ring.cc:1949
BOOLEAN rHasSimpleOrderAA(ring r)
Definition ring.cc:1983
void rSetWeightVec(ring r, int64 *wv)
Definition ring.cc:5368
BOOLEAN rHasBlockOrder(const ring r)
Definition ring.cc:1921
static void rSetOption(ring r)
Definition ring.cc:3453
BOOLEAN rComplete(ring r, int force)
this needs to be called whenever a new ring is created: new fields in ring are created (like VarOffse...
Definition ring.cc:3518
int r_IsRingVar(const char *n, char **names, int N)
Definition ring.cc:213
#define rOppVar(R, I)
Definition ring.cc:5414
int rGetISPos(const int p, const ring r)
Finds p^th IS ordering, and returns its position in r->typ[] returns -1 if something went wrong!...
Definition ring.cc:5136
static void rNGetSComps(int **currComponents, long **currShiftedComponents, ring r)
Definition ring.cc:4459
#define BITS_PER_LONG
Definition ring.cc:40
static void rO_WDegree64(int &place, int &bitplace, int start, int end, long *o, sro_ord &ord_struct, int64 *weights)
Definition ring.cc:2340
BOOLEAN rHasSimpleLexOrder(const ring r)
returns TRUE, if simple lp or ls ordering
Definition ring.cc:1940
void p_SetGlobals(const ring r, BOOLEAN complete)
set all properties of a new ring - also called by rComplete
Definition ring.cc:3485
ring rAssure_SyzComp(const ring r, BOOLEAN complete)
Definition ring.cc:4519
BOOLEAN nc_rComplete(const ring src, ring dest, bool bSetupQuotient)
Definition ring.cc:5825
void p_DebugPrint(poly p, const ring r)
Definition ring.cc:4411
void rKillModifiedRing(ring r)
Definition ring.cc:3110
BOOLEAN rRing_ord_pure_dp(const ring r)
Definition ring.cc:5328
static void rSetVarL(ring r)
set r->VarL_Size, r->VarL_Offset, r->VarL_LowIndex
Definition ring.cc:4111
static void rO_LexVars(int &place, int &bitplace, int start, int end, int &prev_ord, long *o, int *v, int bits, int opt_var)
Definition ring.cc:2390
const char * rSimpleOrdStr(int ord)
Definition ring.cc:78
ring rAssure_Wp_C(const ring r, intvec *w)
Definition ring.cc:4934
BOOLEAN rOrd_is_MixedDegree_Ordering(ring r)
Definition ring.cc:3496
static void rDBChangeSComps(int *currComponents, long *currShiftedComponents, int length, ring r)
Definition ring.cc:4467
ring rAssure_c_dp(const ring r)
Definition ring.cc:5126
static void rSetOutParams(ring r)
Definition ring.cc:3132
static void rSetDegStuff(ring r)
Definition ring.cc:3246
static void rDBGetSComps(int **currComponents, long **currShiftedComponents, int *length, ring r)
Definition ring.cc:4477
rOrderType_t rGetOrderType(ring r)
Definition ring.cc:1843
int rChar(ring r)
Definition ring.cc:716
int rTypeOfMatrixOrder(const intvec *order)
Definition ring.cc:186
VAR omBin sip_sring_bin
Definition ring.cc:43
void rUnComplete(ring r)
Definition ring.cc:4049
ring nc_rCreateNCcomm_rCopy(ring r)
Definition ring.cc:722
char * char_ptr
Definition ring.cc:42
static void rOppWeight(int *w, int l)
Definition ring.cc:5401
static void rO_WDegree_neg(int &place, int &bitplace, int start, int end, long *o, sro_ord &ord_struct, int *weights)
Definition ring.cc:2364
void rKillModified_Wp_Ring(ring r)
Definition ring.cc:3121
ring rMinusVar(const ring r, char *v)
undo rPlusVar
Definition ring.cc:6016
BOOLEAN rRing_has_CompLastBlock(const ring r)
Definition ring.cc:5321
ring rAssure_Dp_C(const ring r)
Definition ring.cc:5116
ring rCopy0AndAddA(const ring r, int64vec *wv64, BOOLEAN copy_qideal, BOOLEAN copy_ordering)
Definition ring.cc:1567
static void rO_Syzcomp(int &place, int &bitplace, int &prev_ord, long *o, sro_ord &ord_struct)
Definition ring.cc:2466
BOOLEAN rOrd_is_Totaldegree_Ordering(const ring r)
Definition ring.cc:2034
ring rModifyRing(ring r, BOOLEAN omit_degree, BOOLEAN try_omit_comp, unsigned long exp_limit)
Definition ring.cc:2749
ring rAssure_SyzOrder(const ring r, BOOLEAN complete)
Definition ring.cc:4514
static void rO_TDegree(int &place, int &bitplace, int start, int end, long *o, sro_ord &ord_struct)
Definition ring.cc:2250
ring rAssure_C_dp(const ring r)
Definition ring.cc:5121
BOOLEAN rHasSimpleOrder(const ring r)
Definition ring.cc:1890
int rGetMaxSyzComp(int i, const ring r)
return the max-comonent wchich has syzIndex i Assume: i<= syzIndex_limit
Definition ring.cc:5294
BOOLEAN rSetISReference(const ring r, const ideal F, const int i, const int p)
Changes r by setting induced ordering parameters: limit and reference leading terms F belong to r,...
Definition ring.cc:5168
char * rString(ring r)
Definition ring.cc:676
ring rAssure_HasComp(const ring r)
Definition ring.cc:4709
BOOLEAN rOrd_is_Ds(const ring r)
Definition ring.cc:2067
ring rCopy0(const ring r, BOOLEAN copy_qideal, BOOLEAN copy_ordering)
Definition ring.cc:1424
static void rO_WMDegree(int &place, int &bitplace, int start, int end, long *o, sro_ord &ord_struct, int *weights)
Definition ring.cc:2318
static void rO_Syz(int &place, int &bitplace, int &prev_ord, int syz_comp, long *o, sro_ord &ord_struct)
Definition ring.cc:2481
BOOLEAN rHas_c_Ordering(const ring r)
Definition ring.cc:1886
static int rRealloc1(ring r, int size, int pos)
Definition ring.cc:5378
#define pFDeg_CASE(A)
static unsigned long rGetExpSize(unsigned long bitmask, int &bits)
Definition ring.cc:2621
void rDebugPrint(const ring r)
Definition ring.cc:4206
static void rCheckOrdSgn(ring r, int i)
Definition ring.cc:3936
BOOLEAN rRing_ord_pure_lp(const ring r)
Definition ring.cc:5348
poly rGetVar(const int varIndex, const ring r)
Definition ring.cc:5903
BOOLEAN rOrd_is_dp(const ring r)
Definition ring.cc:2047
ring rModifyRing_Simple(ring r, BOOLEAN ommit_degree, BOOLEAN ommit_comp, unsigned long exp_limit, BOOLEAN &simple)
Definition ring.cc:3044
void rChangeSComps(int *currComponents, long *currShiftedComponents, int length, ring r)
Definition ring.cc:4489
static void m_DebugPrint(const poly p, const ring R)
debug-print monomial poly/vector p, assuming that it lives in the ring R
Definition ring.cc:4434
static unsigned long rGetDivMask(int bits)
get r->divmask depending on bits per exponent
Definition ring.cc:4192
BOOLEAN rSamePolyRep(ring r1, ring r2)
returns TRUE, if r1 and r2 represents the monomials in the same way FALSE, otherwise this is an analo...
Definition ring.cc:1802
ring rAssure_SyzComp_CompLastBlock(const ring r)
makes sure that c/C ordering is last ordering and SyzIndex is first
Definition ring.cc:4833
char * rParStr(ring r)
Definition ring.cc:652
char * rCharStr(const ring r)
TODO: make it a virtual method of coeffs, together with: Decompose & Compose, rParameter & rPar.
Definition ring.cc:650
static void rOptimizeLDeg(ring r)
Definition ring.cc:3202
BOOLEAN rCheckIV(const intvec *iv)
Definition ring.cc:176
rRingOrder_t rOrderName(char *ordername)
Definition ring.cc:510
ring rOpposite(ring src)
Definition ring.cc:5417
char * rOrdStr(ring r)
Definition ring.cc:524
void rDelete(ring r)
unconditionally deletes fields in r
Definition ring.cc:452
ring rDefault(const coeffs cf, int N, char **n, int ord_size, rRingOrder_t *ord, int *block0, int *block1, int **wvhdl, unsigned long bitmask)
Definition ring.cc:103
static void rRightAdjustVarOffset(ring r)
right-adjust r->VarOffset
Definition ring.cc:4166
VAR omBin char_ptr_bin
Definition ring.cc:44
char * rVarStr(ring r)
Definition ring.cc:626
ring rPlusVar(const ring r, char *v, int left)
K[x],"y" -> K[x,y] resp. K[y,x].
Definition ring.cc:5934
ring rAssure_CompLastBlock(ring r, BOOLEAN complete)
makes sure that c/C ordering is last ordering
Definition ring.cc:4778
static void rO_ISPrefix(int &place, int &bitplace, int &prev_ord, long *o, int N, int *v, sro_ord &ord_struct)
Definition ring.cc:2507
static void rO_Align(int &place, int &bitplace)
Definition ring.cc:2239
ring rAssure_dp_S(const ring r)
Definition ring.cc:5106
BOOLEAN rOrd_is_ds(const ring r)
Definition ring.cc:2057
static void rO_TDegree_neg(int &place, int &bitplace, int start, int end, long *o, sro_ord &ord_struct)
Definition ring.cc:2264
static void rSetFirstWv(ring r, int i, rRingOrder_t *order, int *block0, int *block1, int **wvhdl)
Definition ring.cc:3170
ring rEnvelope(ring R)
Definition ring.cc:5811
BOOLEAN rEqual(ring r1, ring r2, BOOLEAN qr)
returns TRUE, if r1 equals r2 FALSE, otherwise Equality is determined componentwise,...
Definition ring.cc:1749
int rSumInternal(ring r1, ring r2, ring &sum, BOOLEAN vartest, BOOLEAN dp_dp)
returns -1 for not compatible, 1 for compatible (and sum) dp_dp:0: block ordering,...
Definition ring.cc:752
void rSetSyzComp(int k, const ring r)
Definition ring.cc:5222
static const char *const ringorder_name[]
Definition ring.cc:47
static int sign(int x)
Definition ring.cc:3495
static void rO_WDegree(int &place, int &bitplace, int start, int end, long *o, sro_ord &ord_struct, int *weights)
Definition ring.cc:2278
BOOLEAN rOrd_is_WeightedDegree_Ordering(const ring r)
Definition ring.cc:2078
int n_IsParam(const number m, const ring r)
TODO: rewrite somehow...
Definition ring.cc:5913
int64 * rGetWeightVec(const ring r)
Definition ring.cc:5358
static void rO_LexVars_neg(int &place, int &bitplace, int start, int end, int &prev_ord, long *o, int *v, int bits, int opt_var)
Definition ring.cc:2427
ring rAssure_dp_C(const ring r)
Definition ring.cc:5111
ring rCopy(ring r)
Definition ring.cc:1734
VAR int pDBsyzComp
Definition ring.cc:5218
BOOLEAN rDBTest(ring r, const char *fn, const int l)
Definition ring.cc:2089
#define ringorder_rp
Definition ring.h:100
struct p_Procs_s p_Procs_s
Definition ring.h:24
static BOOLEAN rIsPluralRing(const ring r)
we must always have this test!
Definition ring.h:406
ro_typ ord_typ
Definition ring.h:226
static int rBlocks(const ring r)
Definition ring.h:574
static ring rIncRefCnt(ring r)
Definition ring.h:849
static int rPar(const ring r)
(r->cf->P)
Definition ring.h:605
@ ro_wp64
Definition ring.h:56
@ ro_syz
Definition ring.h:61
@ ro_cp
Definition ring.h:59
@ ro_dp
Definition ring.h:53
@ ro_is
Definition ring.h:62
@ ro_wp_neg
Definition ring.h:57
@ ro_wp
Definition ring.h:54
@ ro_isTemp
Definition ring.h:62
@ ro_am
Definition ring.h:55
@ ro_syzcomp
Definition ring.h:60
static BOOLEAN rIsLPRing(const ring r)
Definition ring.h:417
rRingOrder_t
order stuff
Definition ring.h:69
@ ringorder_lp
Definition ring.h:78
@ ringorder_a
Definition ring.h:71
@ ringorder_am
Definition ring.h:90
@ ringorder_a64
for int64 weights
Definition ring.h:72
@ ringorder_C
Definition ring.h:74
@ ringorder_S
S?
Definition ring.h:76
@ ringorder_ds
Definition ring.h:86
@ ringorder_Dp
Definition ring.h:81
@ ringorder_unspec
Definition ring.h:96
@ ringorder_L
Definition ring.h:91
@ ringorder_Ds
Definition ring.h:87
@ ringorder_Ip
Definition ring.h:84
@ ringorder_dp
Definition ring.h:79
@ ringorder_c
Definition ring.h:73
@ ringorder_aa
for idElimination, like a, except pFDeg, pWeigths ignore it
Definition ring.h:93
@ ringorder_no
Definition ring.h:70
@ ringorder_Wp
Definition ring.h:83
@ ringorder_ip
Definition ring.h:80
@ ringorder_is
opposite of ls
Definition ring.h:94
@ ringorder_ws
Definition ring.h:88
@ ringorder_Ws
Definition ring.h:89
@ ringorder_IS
Induced (Schreyer) ordering.
Definition ring.h:95
@ ringorder_ls
degree, ip
Definition ring.h:85
@ ringorder_s
s?
Definition ring.h:77
@ ringorder_wp
Definition ring.h:82
@ ringorder_M
Definition ring.h:75
static BOOLEAN rField_is_Q(const ring r)
Definition ring.h:512
#define ringorder_rs
Definition ring.h:101
static BOOLEAN rShortOut(const ring r)
Definition ring.h:587
rOrderType_t
Definition ring.h:104
@ rOrderType_CompExp
simple ordering, component has priority
Definition ring.h:106
@ rOrderType_Exp
simple ordering, exponent vector has priority component is compatible with exp-vector order
Definition ring.h:109
@ rOrderType_General
non-simple ordering as specified by currRing
Definition ring.h:105
@ rOrderType_ExpComp
simple ordering, exponent vector has priority component not compatible with exp-vector order
Definition ring.h:107
static BOOLEAN rIsNCRing(const ring r)
Definition ring.h:427
static char const ** rParameter(const ring r)
(r->cf->parameter)
Definition ring.h:631
static BOOLEAN rCanShortOut(const ring r)
Definition ring.h:592
static short rVar(const ring r)
#define rVar(r) (r->N)
Definition ring.h:598
#define rTest(r)
Definition ring.h:794
#define rField_is_Ring(R)
Definition ring.h:491
ideal SCAQuotient(const ring r)
Definition sca.h:10
static short scaLastAltVar(ring r)
Definition sca.h:25
static short scaFirstAltVar(ring r)
Definition sca.h:18
ideal idInit(int idsize, int rank)
initialise an ideal / module
void id_Delete(ideal *h, ring r)
deletes an ideal/module/matrix
long id_RankFreeModule(ideal s, ring lmRing, ring tailRing)
return the maximal component number found in any polynomial in s
void idShow(const ideal id, const ring lmRing, const ring tailRing, const int debugPrint)
ideal id_SimpleAdd(ideal h1, ideal h2, const ring R)
concat the lists h1 and h2 without zeros
#define IDELEMS(i)
#define id_Test(A, lR)
#define R
Definition sirandom.c:27
#define A
Definition sirandom.c:24
#define Q
Definition sirandom.c:26
Definition nc.h:68
#define loop
Definition structs.h:71
EXTERN_VAR long * currShiftedComponents
Definition syz.h:118
int ntIsParam(number m, const coeffs cf)
if m == var(i)/1 => return i,
Definition transext.cc:2308