1 /****************************************
2 * Computer Algebra System SINGULAR *
3 ****************************************/
4 /***************************************************************
5 * File: kInline.h
6 * Purpose: implementation of std related inline routines
7 * Author: obachman (Olaf Bachmann)
8 * Created: 8/00
9 *******************************************************************/
10 #ifndef KINLINE_H
11 #define KINLINE_H
12
13 #if !defined(NO_KINLINE) || defined(KUTIL_CC)
14 /* this file is a header file with inline routines,
15 * if NO_KINLINE is not defined (AND ONLY THEN!)
16 * otherwise it is an part of kutil.cc and a source file!
17 * (remark: NO_KINLINE is defined by KDEBUG, i.e. in the debug version)
18 */
19
20 #include "omalloc/omalloc.h"
21 #include "misc/options.h"
22 #include "polys/monomials/p_polys.h"
23 #include "polys/kbuckets.h"
24
25 #include "kernel/polys.h"
26
27 #ifdef HAVE_SHIFTBBA
28 #include "polys/shiftop.h"
29 #endif
30
31
32 #define HAVE_TAIL_BIN
33 // This doesn't really work, fixme, if necessary
34 // #define HAVE_LM_BIN
35
36
37
S_2_T(int i)38 KINLINE TObject* skStrategy::S_2_T(int i)
39 {
40 assume(i>= 0 && i<=sl);
41 assume(S_2_R[i] >= 0 && S_2_R[i] <= tl);
42 TObject* TT = R[S_2_R[i]];
43 assume(TT != NULL && TT->p == S[i]);
44 return TT;
45 }
46
s_2_t(int i)47 KINLINE TObject* skStrategy::s_2_t(int i)
48 {
49 if (i >= 0 && i <= sl)
50 {
51 int sri= S_2_R[i];
52 if ((sri >= 0) && (sri <= tl))
53 {
54 TObject* t = R[sri];
55 if ((t != NULL) && (t->p == S[i]))
56 return t;
57 }
58 // last but not least, try kFindInT
59 sri = kFindInT(S[i], T, tl);
60 if (sri >= 0)
61 return &(T[sri]);
62 }
63 return NULL;
64 }
65
kNoetherTail()66 KINLINE poly skStrategy::kNoetherTail()
67 {
68 if (tailRing == currRing)
69 return kNoether;
70 else
71 {
72 assume((kNoether == NULL && t_kNoether == NULL) ||
73 (kNoether != NULL && t_kNoether != NULL));
74 return t_kNoether;
75 }
76 }
77
78 /***************************************************************
79 *
80 * Operation on TObjects
81 *
82 ***************************************************************/
83
initT()84 KINLINE TSet initT ()
85 {
86 TSet T = (TSet)omAlloc0(setmaxT*sizeof(TObject));
87 for (int i=setmaxT-1; i>=0; i--)
88 {
89 T[i].tailRing = currRing;
90 T[i].i_r = -1;
91 }
92 return T;
93 }
94
initR()95 KINLINE TObject** initR()
96 {
97 return (TObject**) omAlloc0(setmaxT*sizeof(TObject*));
98 }
99
initsevT()100 KINLINE unsigned long* initsevT()
101 {
102 return (unsigned long*) omAlloc0(setmaxT*sizeof(unsigned long));
103 }
104
105 // initialization
Set(ring r)106 KINLINE void sTObject::Set(ring r)
107 {
108 tailRing = r;
109 }
Init(ring r)110 KINLINE void sTObject::Init(ring r)
111 {
112 memset(this, 0, sizeof(sTObject));
113 i_r = -1;
114 Set(r);
115 }
sTObject(ring r)116 KINLINE sTObject::sTObject(ring r)
117 {
118 Init(r);
119 }
Set(poly p_in,ring r)120 KINLINE void sTObject::Set(poly p_in, ring r)
121 {
122 if (r != currRing)
123 {
124 assume(r == tailRing);
125 #ifdef HAVE_SHIFTBBA
126 if (r->isLPring)
127 {
128 shift = si_max(p_mFirstVblock(p_in, r) - 1, 0);
129 if (!shift) p_Test(p_in, r);
130 }
131 else
132 #endif
133 {
134 p_Test(p_in, r);
135 }
136 t_p = p_in;
137 }
138 else
139 {
140 #ifdef HAVE_SHIFTBBA
141 if (currRing->isLPring)
142 {
143 shift = si_max(p_mFirstVblock(p_in, currRing) - 1, 0);
144 if (!shift) p_Test(p_in, currRing);
145 }
146 else
147 #endif
148 {
149 p_Test(p_in, currRing);
150 }
151 p = p_in;
152 }
153 pLength=::pLength(p_in);
154 }
155
sTObject(poly p_in,ring r)156 KINLINE sTObject::sTObject(poly p_in, ring r)
157 {
158 Init(r);
159 Set(p_in, r);
160 }
161
Set(poly p_in,ring c_r,ring t_r)162 KINLINE void sTObject::Set(poly p_in, ring c_r, ring t_r)
163 {
164 if (c_r != t_r)
165 {
166 assume(c_r == currRing && t_r == tailRing);
167 #ifdef HAVE_SHIFTBBA
168 if (c_r->isLPring)
169 {
170 shift = si_max(p_mFirstVblock(p_in, c_r) - 1, 0);
171 if (!shift) p_Test(p_in, currRing);
172 }
173 else
174 #endif
175 {
176 p_Test(p_in, currRing);
177 }
178 p = p_in;
179 pLength=::pLength(p_in);
180 }
181 else
182 {
183 Set(p_in, c_r);
184 }
185 }
186
sTObject(poly p_in,ring c_r,ring t_r)187 KINLINE sTObject::sTObject(poly p_in, ring c_r, ring t_r)
188 {
189 Init(t_r);
190 Set(p_in, c_r, t_r);
191 }
192
sTObject(sTObject * T,int copy)193 KINLINE sTObject::sTObject(sTObject* T, int copy)
194 {
195 *this = *T;
196 if (copy)
197 {
198 if (t_p != NULL)
199 {
200 t_p = p_Copy(t_p, tailRing);
201 p = k_LmInit_tailRing_2_currRing(t_p, tailRing);
202 }
203 else
204 {
205 p = p_Copy(p, currRing);
206 }
207 }
208 }
209
Delete()210 KINLINE void sTObject::Delete()
211 {
212 if (t_p != NULL)
213 {
214 p_Delete(&t_p, tailRing);
215 if (p != NULL)
216 p_LmFree(p, currRing);
217 }
218 else
219 {
220 p_Delete(&p, currRing);
221 }
222 }
223
Clear()224 KINLINE void sTObject::Clear()
225 {
226 p = NULL;
227 t_p = NULL;
228 ecart = 0;
229 length = 0;
230 pLength = 0;
231 FDeg = 0;
232 is_normalized = FALSE;
233 }
234
Copy()235 KINLINE void sTObject::Copy()
236 {
237 if (t_p != NULL)
238 {
239 t_p = p_Copy(t_p, tailRing);
240 if (p != NULL) /* and t_p!=NULL*/
241 {
242 p = p_LmInit(p, currRing);
243 pGetCoeff(p)=pGetCoeff(t_p);
244 pNext(p) = pNext(t_p);
245 }
246 }
247 else
248 {
249 p = p_Copy(p, currRing);
250 }
251 }
252
GetLmCurrRing()253 KINLINE poly sTObject::GetLmCurrRing()
254 {
255 if (p == NULL && t_p != NULL)
256 p = k_LmInit_tailRing_2_currRing(t_p, tailRing);
257
258 return p;
259 }
GetLmTailRing()260 KINLINE poly sTObject::GetLmTailRing()
261 {
262 if (t_p == NULL)
263 {
264 if (p != NULL && tailRing != currRing)
265 {
266 t_p = k_LmInit_currRing_2_tailRing(p, tailRing);
267 return t_p;
268 }
269 return p;
270 }
271 return t_p;
272 }
GetLm(ring r)273 KINLINE poly sTObject::GetLm(ring r)
274 {
275 assume(r == tailRing || r == currRing);
276 if (r == currRing)
277 return GetLmCurrRing();
278
279 if (t_p == NULL && p != NULL)
280 t_p = k_LmInit_currRing_2_tailRing(p, tailRing);
281
282 return t_p;
283 }
284
GetLm(poly & p_r,ring & r_r)285 KINLINE void sTObject::GetLm(poly &p_r, ring &r_r) const
286 {
287 if (t_p != NULL)
288 {
289 p_r = t_p;
290 r_r = tailRing;
291 }
292 else
293 {
294 p_r = p;
295 r_r = currRing;
296 }
297 }
298
IsNull()299 KINLINE BOOLEAN sTObject::IsNull() const
300 {
301 return (p == NULL && t_p == NULL);
302 }
303
GetpLength()304 KINLINE int sTObject::GetpLength()
305 {
306 if (pLength <= 0) pLength = ::pLength(p != NULL ? p : t_p);
307 return pLength;
308 }
309
SetLmCurrRing()310 KINLINE void sTObject::SetLmCurrRing()
311 {
312 if (p == NULL && t_p != NULL)
313 p = k_LmInit_tailRing_2_currRing(t_p, tailRing);
314 }
315
Next()316 KINLINE poly sTObject::Next()
317 {
318 assume(p != NULL || t_p != NULL);
319 if (t_p != NULL) return pNext(t_p);
320 return pNext(p);
321 }
322
323 // Iterations
LmDeleteAndIter()324 KINLINE void sTObject::LmDeleteAndIter()
325 {
326 assume(p != NULL || t_p != NULL);
327 if (t_p != NULL)
328 {
329 t_p = p_LmDeleteAndNext(t_p, tailRing);
330 if (p != NULL)
331 {
332 p_LmFree(p, currRing);
333 p = NULL;
334 }
335 }
336 else
337 {
338 p = p_LmDeleteAndNext(p, currRing);
339 }
340 is_normalized = FALSE;
341 }
342
343
344 // arithmetic
Mult_nn(number n)345 KINLINE void sTObject::Mult_nn(number n)
346 {
347 if (t_p != NULL)
348 {
349 t_p = p_Mult_nn(t_p, n, tailRing);
350 if (p != NULL) pSetCoeff0(p, pGetCoeff(t_p));
351 }
352 else
353 {
354 p = p_Mult_nn(p, n, currRing, tailRing);
355 }
356 }
357
Normalize()358 KINLINE void sLObject::Normalize()
359 {
360 if (t_p != NULL)
361 {
362 pNormalize(t_p);
363 if (p != NULL) pSetCoeff0(p, pGetCoeff(t_p));
364 }
365 else
366 {
367 pNormalize(p);
368 }
369 if (bucket!=NULL) kBucketNormalize(bucket);
370 }
371
CanonicalizeP()372 KINLINE void sLObject::CanonicalizeP()
373 {
374 if (bucket != NULL)
375 kBucketCanonicalize(bucket);
376 }
377
HeadNormalize()378 KINLINE void sLObject::HeadNormalize()
379 {
380 if (t_p != NULL)
381 {
382 nNormalize(pGetCoeff(t_p));
383 if (p != NULL) pSetCoeff0(p, pGetCoeff(t_p));
384 }
385 else
386 {
387 nNormalize(pGetCoeff(p));
388 }
389 }
390
391 KINLINE void
ShallowCopyDelete(ring new_tailRing,omBin new_tailBin,pShallowCopyDeleteProc p_shallow_copy_delete,BOOLEAN set_max)392 sTObject::ShallowCopyDelete(ring new_tailRing, omBin new_tailBin,
393 pShallowCopyDeleteProc p_shallow_copy_delete,
394 BOOLEAN set_max)
395 {
396 if (new_tailBin == NULL) new_tailBin = new_tailRing->PolyBin;
397 if (t_p != NULL)
398 {
399 t_p = p_shallow_copy_delete(t_p, tailRing, new_tailRing, new_tailBin);
400 if (p != NULL)
401 pNext(p) = pNext(t_p);
402 if (new_tailRing == currRing)
403 {
404 if (p == NULL) p = t_p;
405 else p_LmFree(t_p, tailRing);
406 t_p = NULL;
407 }
408 }
409 else if (p != NULL) /* && t_p==NULL */
410 {
411 if (pNext(p) != NULL)
412 {
413 pNext(p) = p_shallow_copy_delete(pNext(p),
414 tailRing, new_tailRing, new_tailBin);
415 }
416 if (new_tailRing != currRing)
417 {
418 t_p = k_LmInit_currRing_2_tailRing(p, new_tailRing);
419 pNext(t_p) = pNext(p);
420 }
421 }
422 if (max_exp != NULL)
423 {
424 max_exp = p_shallow_copy_delete(max_exp,tailRing,new_tailRing,new_tailBin);
425 }
426 else if (set_max && pNext(t_p) != NULL)
427 {
428 max_exp = p_GetMaxExpP(pNext(t_p), new_tailRing);
429 }
430 tailRing = new_tailRing;
431 }
432
pFDeg()433 KINLINE long sTObject::pFDeg() const
434 {
435 if (p != NULL) return p_FDeg(p, currRing);
436 return tailRing->pFDeg(t_p, tailRing);
437 }
pTotalDeg()438 KINLINE long sTObject::pTotalDeg() const
439 {
440 if (p != NULL) return p_Totaldegree(p, currRing);
441 return p_Totaldegree(t_p,tailRing);
442 }
SetpFDeg()443 KINLINE long sTObject::SetpFDeg()
444 {
445 FDeg = this->pFDeg();
446 return FDeg;
447 }
GetpFDeg()448 KINLINE long sTObject::GetpFDeg() const
449 {
450 assume(FDeg == this->pFDeg());
451 return FDeg;
452 }
pLDeg()453 KINLINE long sTObject::pLDeg()
454 {
455 return tailRing->pLDeg(GetLmTailRing(), &length, tailRing);
456 }
SetDegStuffReturnLDeg()457 KINLINE long sTObject::SetDegStuffReturnLDeg()
458 {
459 FDeg = this->pFDeg();
460 long d = this->pLDeg();
461 ecart = d - FDeg;
462 return d;
463 }
464
465 //extern void pCleardenom(poly p);
466 // extern void pNorm(poly p);
467
468 // manipulations
pCleardenom()469 KINLINE void sTObject::pCleardenom()
470 {
471 assume(p != NULL);
472 if (TEST_OPT_CONTENTSB)
473 {
474 number n;
475 if (t_p != NULL)
476 {
477 p_Cleardenom_n(t_p, tailRing, n);
478 pSetCoeff0(p, pGetCoeff(t_p));
479 }
480 else
481 {
482 p_Cleardenom_n(p, currRing, n);
483 }
484 if (!nIsOne(n))
485 {
486 denominator_list denom=(denominator_list)omAlloc(sizeof(denominator_list_s));
487 denom->n=nInvers(n);
488 denom->next=DENOMINATOR_LIST;
489 DENOMINATOR_LIST=denom;
490 }
491 nDelete(&n);
492 }
493 else
494 {
495 if (t_p != NULL)
496 {
497 p_ProjectiveUnique(t_p, tailRing);
498 pSetCoeff0(p, pGetCoeff(t_p));
499 }
500 else
501 {
502 p_ProjectiveUnique(p, currRing);
503 }
504 }
505 }
506
pContent()507 KINLINE void sTObject::pContent()
508 {
509 assume(p != NULL);
510 if (t_p != NULL)
511 {
512 p_SimpleContent(t_p, 1, tailRing);
513 if (!n_GreaterZero(pGetCoeff(t_p),tailRing->cf))
514 {
515 t_p=p_Neg (t_p,tailRing);
516 }
517 pSetCoeff0(p, pGetCoeff(t_p));
518 }
519 else
520 {
521 p_SimpleContent(p, 1, currRing);
522 if (!n_GreaterZero(pGetCoeff(p),currRing->cf))
523 {
524 p=p_Neg (p,currRing);
525 }
526 }
527 }
528
pNorm()529 KINLINE void sTObject::pNorm() // pNorm seems to be a _bad_ method name...
530 {
531 assume(p != NULL);
532 if (! is_normalized)
533 {
534 p_Norm(p, currRing);
535 if (t_p != NULL)
536 pSetCoeff0(t_p, pGetCoeff(p));
537 is_normalized = TRUE;
538 }
539 }
540
541
542
543 /***************************************************************
544 *
545 * Operation on LObjects
546 *
547 ***************************************************************/
548 // Initialization
Clear()549 KINLINE void sLObject::Clear()
550 {
551 sTObject::Clear();
552 sev = 0;
553 }
554 // Initialization
Delete()555 KINLINE void sLObject::Delete()
556 {
557 sTObject::Delete();
558 if (bucket != NULL)
559 kBucketDeleteAndDestroy(&bucket);
560 }
561
Init(ring r)562 KINLINE void sLObject::Init(ring r)
563 {
564 memset(this, 0, sizeof(sLObject));
565 i_r1 = -1;
566 i_r2 = -1;
567 i_r = -1;
568 Set(r);
569 }
sLObject(ring r)570 KINLINE sLObject::sLObject(ring r)
571 {
572 Init(r);
573 }
sLObject(poly p_in,ring r)574 KINLINE sLObject::sLObject(poly p_in, ring r)
575 {
576 Init(r);
577 Set(p_in, r);
578 }
579
sLObject(poly p_in,ring c_r,ring t_r)580 KINLINE sLObject::sLObject(poly p_in, ring c_r, ring t_r)
581 {
582 Init(t_r);
583 Set(p_in, c_r, t_r);
584 }
585
PrepareRed(BOOLEAN use_bucket)586 KINLINE void sLObject::PrepareRed(BOOLEAN use_bucket)
587 {
588 if (bucket == NULL)
589 {
590 unsigned l = GetpLength();
591 if (use_bucket && (l > 1))
592 {
593 poly tp = GetLmTailRing();
594 assume(l == ::pLength(tp));
595 bucket = kBucketCreate(tailRing);
596 kBucketInit(bucket, pNext(tp), l-1);
597 pNext(tp) = NULL;
598 if (p != NULL) pNext(p) = NULL;
599 pLength = 0;
600 }
601 }
602 }
603
SetLmTail(poly lm,poly p_tail,int p_Length,int use_bucket,ring _tailRing)604 KINLINE void sLObject::SetLmTail(poly lm, poly p_tail, int p_Length, int use_bucket, ring _tailRing)
605 {
606
607 Set(lm, _tailRing);
608 if (use_bucket)
609 {
610 bucket = kBucketCreate(_tailRing);
611 kBucketInit(bucket, p_tail, p_Length);
612 pNext(lm) = NULL;
613 pLength = 0;
614 }
615 else
616 {
617 pNext(lm) = p_tail;
618 pLength = p_Length + 1;
619 }
620 }
621
Tail_Mult_nn(number n)622 KINLINE void sLObject::Tail_Mult_nn(number n)
623 {
624 if (bucket != NULL)
625 {
626 kBucket_Mult_n(bucket, n);
627 }
628 else
629 {
630 poly _p = (t_p != NULL ? t_p : p);
631 assume(_p != NULL);
632 pNext(_p) = __p_Mult_nn(pNext(_p), n, tailRing);
633 }
634 }
635
Tail_Minus_mm_Mult_qq(poly m,poly q,int lq,poly spNoether)636 KINLINE void sLObject::Tail_Minus_mm_Mult_qq(poly m, poly q, int lq,
637 poly spNoether)
638 {
639 if (bucket != NULL)
640 {
641 kBucket_Minus_m_Mult_p(bucket, m, q, &lq, spNoether);
642 }
643 else
644 {
645 if (lq<=0) lq= ::pLength(q);
646 poly _p = (t_p != NULL ? t_p : p);
647 assume(_p != NULL);
648
649 int lp=pLength-1;
650 pNext(_p) = p_Minus_mm_Mult_qq( pNext(_p), m, q, lp, lq,
651 spNoether, tailRing );
652 pLength=lp+1;
653 // tailRing->p_Procs->p_Minus_mm_Mult_qq(pNext(_p), m, q, shorter,spNoether, tailRing, last);
654 // pLength += lq - shorter;
655 }
656 }
657
LmDeleteAndIter()658 KINLINE void sLObject::LmDeleteAndIter()
659 {
660 sTObject::LmDeleteAndIter();
661 if (bucket != NULL)
662 {
663 poly _p = kBucketExtractLm(bucket);
664 if (_p == NULL)
665 {
666 kBucketDestroy(&bucket);
667 p = t_p = NULL;
668 return;
669 }
670 Set(_p, tailRing);
671 }
672 else
673 {
674 pLength--;
675 }
676 }
677
LmExtractAndIter()678 KINLINE poly sLObject::LmExtractAndIter()
679 {
680 poly ret = GetLmTailRing();
681 poly pn;
682
683 assume(p != NULL || t_p != NULL);
684
685 if (bucket != NULL)
686 {
687 pn = kBucketExtractLm(bucket);
688 if (pn == NULL)
689 kBucketDestroy(&bucket);
690 }
691 else
692 {
693 pn = pNext(ret);
694 }
695 pLength--;
696 pNext(ret) = NULL;
697 if (p != NULL && t_p != NULL)
698 p_LmFree(p, currRing);
699
700 Set(pn, tailRing);
701 return ret;
702 }
703
GetTP()704 KINLINE poly sLObject::GetTP()
705 {
706 //kTest_L(this);
707 poly tp = GetLmTailRing();
708 assume(tp != NULL);
709
710 if (bucket != NULL)
711 {
712 kBucketClear(bucket, &pNext(tp), &pLength);
713 kBucketDestroy(&bucket);
714 pLength++;
715 }
716 return tp;
717 }
718
719
GetP(omBin lmBin)720 KINLINE poly sLObject::GetP(omBin lmBin)
721 {
722 //kTest_L(this);
723 if (p == NULL)
724 {
725 p = k_LmInit_tailRing_2_currRing(t_p, tailRing,
726 ((lmBin!=NULL)?lmBin:currRing->PolyBin));
727 FDeg = pFDeg();
728 }
729 else if ((lmBin != NULL) && (lmBin != currRing->PolyBin))
730 {
731 p = p_LmShallowCopyDelete(p, currRing);
732 FDeg = pFDeg();
733 }
734
735 if (bucket != NULL)
736 {
737 kBucketClear(bucket, &pNext(p), &pLength);
738 kBucketDestroy(&bucket);
739 pLength++;
740 if (t_p != NULL) pNext(t_p) = pNext(p);
741 }
742 //kTest_L(this);
743 return p;
744 }
745
746 KINLINE void
ShallowCopyDelete(ring new_tailRing,pShallowCopyDeleteProc p_shallow_copy_delete)747 sLObject::ShallowCopyDelete(ring new_tailRing,
748 pShallowCopyDeleteProc p_shallow_copy_delete)
749 {
750 if (bucket != NULL)
751 kBucketShallowCopyDelete(bucket, new_tailRing, new_tailRing->PolyBin,
752 p_shallow_copy_delete);
753 sTObject::ShallowCopyDelete(new_tailRing,
754 new_tailRing->PolyBin,p_shallow_copy_delete,
755 FALSE);
756 }
757
SetShortExpVector()758 KINLINE void sLObject::SetShortExpVector()
759 {
760 if (t_p != NULL)
761 {
762 sev = p_GetShortExpVector(t_p, tailRing);
763 }
764 else
765 {
766 sev = p_GetShortExpVector(p, currRing);
767 }
768 }
769
Copy()770 KINLINE void sLObject::Copy()
771 {
772 if (bucket != NULL)
773 {
774 int i = kBucketCanonicalize(bucket);
775 kBucket_pt new_bucket = kBucketCreate(tailRing);
776 kBucketInit(new_bucket,
777 p_Copy(bucket->buckets[i], tailRing),
778 bucket->buckets_length[i]);
779 bucket = new_bucket;
780 if (t_p != NULL) pNext(t_p) = NULL;
781 if (p != NULL) pNext(p) = NULL;
782 }
783 TObject::Copy();
784 }
785
pLDeg()786 KINLINE long sLObject::pLDeg()
787 {
788 poly tp = GetLmTailRing();
789 assume(tp != NULL);
790 if (bucket != NULL)
791 {
792 int i = kBucketCanonicalize(bucket);
793 pNext(tp) = bucket->buckets[i];
794 long ldeg = tailRing->pLDeg(tp, &length, tailRing);
795 pNext(tp) = NULL;
796 return ldeg;
797 }
798 else
799 return tailRing->pLDeg(tp, &length, tailRing);
800 }
pLDeg(BOOLEAN deg_last)801 KINLINE long sLObject::pLDeg(BOOLEAN deg_last)
802 {
803 if (! deg_last || bucket != NULL) return sLObject::pLDeg();
804
805 long ldeg;
806 ldeg = tailRing->pLDeg(GetLmTailRing(), &length, tailRing);
807 #ifndef SING_NDEBUG
808 if ( pLength == 0)
809 p_Last(GetLmTailRing(), pLength, tailRing);
810 assume ( pLength == length || rIsSyzIndexRing(currRing));
811 #else
812 pLength=length;
813 #endif
814 return ldeg;
815 }
816
SetDegStuffReturnLDeg()817 KINLINE long sLObject::SetDegStuffReturnLDeg()
818 {
819 FDeg = this->pFDeg();
820 long d = this->pLDeg();
821 ecart = d - FDeg;
822 return d;
823 }
SetDegStuffReturnLDeg(BOOLEAN use_last)824 KINLINE long sLObject::SetDegStuffReturnLDeg(BOOLEAN use_last)
825 {
826 FDeg = this->pFDeg();
827 long d = this->pLDeg(use_last);
828 ecart = d - FDeg;
829 return d;
830 }
GetpLength()831 KINLINE int sLObject::GetpLength()
832 {
833 if (bucket == NULL)
834 return sTObject::GetpLength();
835 int i = kBucketCanonicalize(bucket);
836 return bucket->buckets_length[i] + 1;
837 }
SetLength(BOOLEAN length_pLength)838 KINLINE int sLObject::SetLength(BOOLEAN length_pLength)
839 {
840 if (length_pLength)
841 {
842 length = this->GetpLength();
843 }
844 else
845 this->pLDeg();
846 return length;
847 }
MinComp()848 KINLINE long sLObject::MinComp()
849 {
850 poly tp = GetLmTailRing();
851 assume(tp != NULL);
852 if (bucket != NULL)
853 {
854 int i = kBucketCanonicalize(bucket);
855 pNext(tp) = bucket->buckets[i];
856 long m = p_MinComp(tp, tailRing);
857 pNext(tp) = NULL;
858 return m;
859 }
860 else
861 return p_MinComp(tp, tailRing);
862 }
Comp()863 KINLINE long sLObject::Comp()
864 {
865 poly pp;
866 ring r;
867 GetLm(pp, r);
868 assume(pp != NULL);
869 return p_GetComp(pp, r);
870 }
871
872 KINLINE sLObject& sLObject::operator=(const sTObject& t)
873 {
874 memset(this, 0, sizeof(*this));
875 memcpy(this, &t, sizeof(sTObject));
876 return *this;
877 }
878
T_1(const skStrategy * s)879 KINLINE TObject* sLObject::T_1(const skStrategy* s)
880 {
881 if (p1 == NULL) return NULL;
882 if (i_r1 == -1) i_r1 = kFindInT(p1, s->T, s->tl);
883 assume(i_r1 >= 0 && i_r1 <= s->tl);
884 TObject* T = s->R[i_r1];
885 assume(T->p == p1);
886 return T;
887 }
888
T_2(const skStrategy * strat)889 KINLINE TObject* sLObject::T_2(const skStrategy* strat)
890 {
891 if (p1 == NULL) return NULL;
892 assume(p2 != NULL);
893 if (i_r2 == -1) i_r2 = kFindInT(p2, strat->T, strat->tl);
894 assume(i_r2 >= 0 && i_r2 <= strat->tl);
895 TObject* T = strat->R[i_r2];
896 assume(T->p == p2);
897 return T;
898 }
899
T_1_2(const skStrategy * strat,TObject * & T_1,TObject * & T_2)900 KINLINE void sLObject::T_1_2(const skStrategy* strat,
901 TObject* &T_1, TObject* &T_2)
902 {
903 if (p1 == NULL)
904 {
905 T_1 = NULL;
906 T_2 = NULL;
907 return;
908 }
909 assume(p1 != NULL && p2 != NULL);
910 if (i_r1 == -1) i_r1 = kFindInT(p1, strat->T, strat->tl);
911 if (i_r2 == -1) i_r2 = kFindInT(p2, strat->T, strat->tl);
912 assume(i_r1 >= 0 && i_r1 <= strat->tl);
913 assume(i_r2 >= 0 && i_r2 <= strat->tl);
914 T_1 = strat->R[i_r1];
915 T_2 = strat->R[i_r2];
916 assume(T_1->p == p1);
917 assume(T_2->p == p2);
918 return;
919 }
920
921 /***************************************************************
922 *
923 * Conversion of polys
924 *
925 ***************************************************************/
926
k_LmInit_currRing_2_tailRing(poly p,ring tailRing,omBin tailBin)927 KINLINE poly k_LmInit_currRing_2_tailRing(poly p, ring tailRing, omBin tailBin)
928 {
929
930 poly t_p = p_LmInit(p, currRing, tailRing, tailBin);
931 pNext(t_p) = pNext(p);
932 pSetCoeff0(t_p, pGetCoeff(p));
933 return t_p;
934 }
935
k_LmInit_tailRing_2_currRing(poly t_p,ring tailRing,omBin lmBin)936 KINLINE poly k_LmInit_tailRing_2_currRing(poly t_p, ring tailRing, omBin lmBin)
937 {
938 poly p = p_LmInit(t_p, tailRing, currRing, lmBin);
939 pNext(p) = pNext(t_p);
940 pSetCoeff0(p, pGetCoeff(t_p));
941 return p;
942 }
943
944 // this should be made more efficient
k_LmShallowCopyDelete_currRing_2_tailRing(poly p,ring tailRing,omBin tailBin)945 KINLINE poly k_LmShallowCopyDelete_currRing_2_tailRing(poly p, ring tailRing, omBin tailBin)
946 {
947 poly np = k_LmInit_currRing_2_tailRing(p, tailRing, tailBin);
948 p_LmFree(p, currRing);
949 return np;
950 }
951
k_LmShallowCopyDelete_tailRing_2_currRing(poly p,ring tailRing,omBin lmBin)952 KINLINE poly k_LmShallowCopyDelete_tailRing_2_currRing(poly p, ring tailRing, omBin lmBin)
953 {
954 poly np = k_LmInit_tailRing_2_currRing(p, tailRing, lmBin);
955 p_LmFree(p, tailRing);
956 return np;
957 }
958
k_LmInit_currRing_2_tailRing(poly p,ring tailRing)959 KINLINE poly k_LmInit_currRing_2_tailRing(poly p, ring tailRing)
960 {
961 return k_LmInit_currRing_2_tailRing(p, tailRing, tailRing->PolyBin);
962 }
963
k_LmInit_tailRing_2_currRing(poly p,ring tailRing)964 KINLINE poly k_LmInit_tailRing_2_currRing(poly p, ring tailRing)
965 {
966 return k_LmInit_tailRing_2_currRing(p, tailRing, currRing->PolyBin);
967 }
968
k_LmShallowCopyDelete_currRing_2_tailRing(poly p,ring tailRing)969 KINLINE poly k_LmShallowCopyDelete_currRing_2_tailRing(poly p, ring tailRing)
970 {
971 return k_LmShallowCopyDelete_currRing_2_tailRing(p, tailRing, tailRing->PolyBin);
972 }
973
k_LmShallowCopyDelete_tailRing_2_currRing(poly p,ring tailRing)974 KINLINE poly k_LmShallowCopyDelete_tailRing_2_currRing(poly p, ring tailRing)
975 {
976 return k_LmShallowCopyDelete_tailRing_2_currRing(p, tailRing, currRing->PolyBin);
977 }
978
979 /***************************************************************
980 *
981 * Lcm business
982 *
983 ***************************************************************/
984 // get m1 = LCM(LM(p1), LM(p2))/LM(p1)
985 // m2 = LCM(LM(p1), LM(p2))/LM(p2)
k_GetLeadTerms(const poly p1,const poly p2,const ring p_r,poly & m1,poly & m2,const ring m_r)986 KINLINE BOOLEAN k_GetLeadTerms(const poly p1, const poly p2, const ring p_r,
987 poly &m1, poly &m2, const ring m_r)
988 {
989 p_LmCheckPolyRing(p1, p_r);
990 p_LmCheckPolyRing(p2, p_r);
991
992 int i;
993 long x;
994 m1 = p_Init(m_r,m_r->PolyBin);
995 m2 = p_Init(m_r,m_r->PolyBin);
996
997 for (i = p_r->N; i; i--)
998 {
999 x = p_GetExpDiff(p1, p2, i, p_r);
1000 if (x > 0)
1001 {
1002 if (x > (long) m_r->bitmask) goto false_return;
1003 p_SetExp(m2,i,x, m_r);
1004 p_SetExp(m1,i,0, m_r);
1005 }
1006 else
1007 {
1008 if (-x > (long) m_r->bitmask) goto false_return;
1009 p_SetExp(m1,i,-x, m_r);
1010 p_SetExp(m2,i,0, m_r);
1011 }
1012 }
1013
1014 p_Setm(m1, m_r);
1015 p_Setm(m2, m_r);
1016 return TRUE;
1017
1018 false_return:
1019 p_LmFree(m1, m_r);
1020 p_LmFree(m2, m_r);
1021 m1 = m2 = NULL;
1022 return FALSE;
1023 }
1024
1025 #ifdef HAVE_RINGS
1026 // get m1 = LCM(LM(p1), LM(p2))/LM(p1)
1027 // m2 = LCM(LM(p1), LM(p2))/LM(p2) in tailRing
1028 // lcm = LCM(LM(p1), LM(p2)) in leadRing
k_GetStrongLeadTerms(const poly p1,const poly p2,const ring leadRing,poly & m1,poly & m2,poly & lcm,const ring tailRing)1029 KINLINE void k_GetStrongLeadTerms(const poly p1, const poly p2, const ring leadRing,
1030 poly &m1, poly &m2, poly &lcm, const ring tailRing)
1031 {
1032 p_LmCheckPolyRing(p1, leadRing);
1033 p_LmCheckPolyRing(p2, leadRing);
1034
1035 int i;
1036 int x;
1037 int e1;
1038 int e2;
1039 int s;
1040 m1 = p_Init(tailRing,tailRing->PolyBin);
1041 m2 = p_Init(tailRing,tailRing->PolyBin);
1042 lcm = p_Init(leadRing,leadRing->PolyBin);
1043
1044 for (i = leadRing->N; i>=0; i--)
1045 {
1046 e1 = p_GetExp(p1,i,leadRing);
1047 e2 = p_GetExp(p2,i,leadRing);
1048 x = e1 - e2;
1049 if (x > 0)
1050 {
1051 p_SetExp(m2,i,x, tailRing);
1052 //p_SetExp(m1,i,0, tailRing); // done by p_Init
1053 s = e1;
1054 }
1055 else if (x<0)
1056 {
1057 p_SetExp(m1,i,-x, tailRing);
1058 //p_SetExp(m2,i,0, tailRing); // done by p_Init
1059 s = e2;
1060 }
1061 else
1062 s = e1; // e1==e2
1063 p_SetExp(lcm,i,s, leadRing);
1064 }
1065
1066 p_Setm(m1, tailRing);
1067 p_Setm(m2, tailRing);
1068 p_Setm(lcm, leadRing);
1069 }
1070 #endif
1071
1072 /***************************************************************
1073 *
1074 * Misc things
1075 *
1076 ***************************************************************/
ksReducePolyTailLC_Z(LObject * PR,TObject * PW,LObject * Red)1077 KINLINE int ksReducePolyTailLC_Z(LObject* PR, TObject* PW, LObject* Red)
1078 {
1079 BOOLEAN ret;
1080 number mult, rest;
1081 TObject red = *PW;
1082 red.Copy();
1083 rest = n_QuotRem(pGetCoeff(Red->p), pGetCoeff(red.p),
1084 &mult, currRing->cf);
1085 red.Mult_nn(rest);
1086
1087 assume(PR->GetLmCurrRing() != red.GetLmCurrRing());
1088 ret = ksReducePolyLC(Red, &red, NULL, &mult);
1089 red.Delete();
1090 red.Clear();
1091
1092 return ret;
1093 }
1094
ksReducePolyTail_Z(LObject * PR,TObject * PW,LObject * Red)1095 KINLINE int ksReducePolyTail_Z(LObject* PR, TObject* PW, LObject* Red)
1096 {
1097 BOOLEAN ret;
1098 number coef;
1099
1100 assume(PR->GetLmCurrRing() != PW->GetLmCurrRing());
1101 ret = ksReducePoly(Red, PW, NULL, &coef);
1102
1103 if (!ret)
1104 {
1105 if (! n_IsOne(coef, currRing->cf))
1106 {
1107 PR->Mult_nn(coef);
1108 // HANNES: mark for Normalize
1109 }
1110 n_Delete(&coef, currRing->cf);
1111 }
1112 return ret;
1113 }
1114
ksReducePolyTail(LObject * PR,TObject * PW,LObject * Red)1115 KINLINE int ksReducePolyTail(LObject* PR, TObject* PW, LObject* Red)
1116 {
1117 BOOLEAN ret;
1118 number coef;
1119
1120 assume(PR->GetLmCurrRing() != PW->GetLmCurrRing());
1121 Red->HeadNormalize();
1122 ret = ksReducePoly(Red, PW, NULL, &coef);
1123
1124 if (!ret)
1125 {
1126 if (! n_IsOne(coef, currRing->cf))
1127 {
1128 PR->Mult_nn(coef);
1129 // HANNES: mark for Normalize
1130 }
1131 n_Delete(&coef, currRing->cf);
1132 }
1133 return ret;
1134 }
1135
1136 /***************************************************************
1137 *
1138 * Routines for backwards-Compatibility
1139 *
1140 *
1141 ***************************************************************/
ksOldSpolyRed(poly p1,poly p2,poly spNoether)1142 KINLINE poly ksOldSpolyRed(poly p1, poly p2, poly spNoether)
1143 {
1144 LObject L(p2);
1145 TObject T(p1);
1146
1147 ksReducePoly(&L, &T, spNoether);
1148
1149 return L.GetLmCurrRing();
1150 }
1151
ksOldSpolyRedNew(poly p1,poly p2,poly spNoether)1152 KINLINE poly ksOldSpolyRedNew(poly p1, poly p2, poly spNoether)
1153 {
1154 LObject L(p_Copy(p2, currRing));
1155 TObject T(p1);
1156
1157 ksReducePoly(&L, &T, spNoether);
1158
1159 return L.GetLmCurrRing();
1160 }
1161
ksOldCreateSpoly(poly p1,poly p2,poly spNoether,ring r)1162 KINLINE poly ksOldCreateSpoly(poly p1, poly p2, poly spNoether, ring r)
1163 {
1164 LObject L(r);
1165 L.p1 = p1;
1166 L.p2 = p2;
1167
1168 ksCreateSpoly(&L, spNoether);
1169 return L.GetLmCurrRing();
1170 }
1171
ksOldSpolyTail(poly p1,poly q,poly q2,poly spNoether,ring r)1172 void ksOldSpolyTail(poly p1, poly q, poly q2, poly spNoether, ring r)
1173 {
1174 LObject L(q, currRing, r);
1175 TObject T(p1, currRing, r);
1176
1177 ksReducePolyTail(&L, &T, q2, spNoether);
1178 }
1179
redtailBba(poly p,int pos,kStrategy strat,BOOLEAN normalize)1180 KINLINE poly redtailBba (poly p,int pos,kStrategy strat,BOOLEAN normalize)
1181 {
1182 LObject L(p);
1183 return redtailBba(&L, pos, strat,FALSE, normalize);
1184 }
1185
redtailBbaBound(poly p,int pos,kStrategy strat,int bound,BOOLEAN normalize)1186 KINLINE poly redtailBbaBound (poly p,int pos,kStrategy strat,int bound,BOOLEAN normalize)
1187 {
1188 LObject L(p, currRing, strat->tailRing); // ? L(p); ??
1189 return redtailBbaBound(&L, pos, strat,bound, FALSE, normalize);
1190 }
1191
1192 #ifdef HAVE_RINGS
redtailBba_Ring(poly p,int pos,kStrategy strat)1193 KINLINE poly redtailBba_Ring (poly p,int pos,kStrategy strat)
1194 {
1195 LObject L(p, currRing, strat->tailRing);
1196 return redtailBba_Ring(&L, pos, strat);
1197 }
redtailBba_Z(poly p,int pos,kStrategy strat)1198 KINLINE poly redtailBba_Z (poly p,int pos,kStrategy strat)
1199 {
1200 LObject L(p, currRing, strat->tailRing);
1201 return redtailBba_Z(&L, pos, strat);
1202 }
1203 #endif
1204
clearS(poly p,unsigned long p_sev,int * at,int * k,kStrategy strat)1205 KINLINE void clearS (poly p, unsigned long p_sev, int* at, int* k,
1206 kStrategy strat)
1207 {
1208 assume(p_sev == pGetShortExpVector(p));
1209 if (strat->noClearS) return;
1210 #ifdef HAVE_RINGS
1211 if(rField_is_Ring(currRing))
1212 {
1213 if (!pLmShortDivisibleBy(p,p_sev, strat->S[*at], ~ strat->sevS[*at]))
1214 return;
1215 if(!n_DivBy(pGetCoeff(strat->S[*at]), pGetCoeff(p), currRing->cf))
1216 return;
1217 }
1218 else
1219 #endif
1220 {
1221 if (!pLmShortDivisibleBy(p,p_sev, strat->S[*at], ~ strat->sevS[*at])) return;
1222 }
1223 deleteInS((*at),strat);
1224 (*at)--;
1225 (*k)--;
1226 }
1227
1228 // dummy function for function pointer strat->rewCrit being usable in all
1229 // possible choices for criteria
arriRewDummy(poly,unsigned long,poly,kStrategy,int)1230 KINLINE BOOLEAN arriRewDummy(poly /*sig*/, unsigned long /*not_sevSig*/, poly /*lm*/, kStrategy /*strat*/, int /*start=0*/)
1231 {
1232 return FALSE;
1233 }
1234
1235 #endif // defined(KINLINE) || defined(KUTIL_CC)
1236 #endif // KINLINE_H
1237