100 WORD *ll, *m, *w, *llf, *OldWork, *StartWork, *ww, *mm, *t, *OldTermBuffer = 0;
101 WORD power = 0, i, msign = 0, ll2;
103 int numdollars = 0, protosize, oldallnumrhs;
104 CBUF *C = cbuf+AM.rbufnum, *CC;
111 if ( *ll == TYPEEXPRESSION ) {
117 else if ( *ll == TYPEREPEAT ) {
121 else if ( *ll == TYPEENDREPEAT ) {
122 if ( *AN.RepPoint ) {
129 if ( AN.RepPoint < AT.RepCount ) {
130 MLOCK(ErrorMessageLock);
131 MesPrint(
"Internal problems with REPEAT count");
132 MUNLOCK(ErrorMessageLock);
138 else if ( *ll == TYPEOPERATION ) {
142 if ( (*(FG.OperaFind[ll[2]]))(BHEAD term,ll) )
return(-1);
148 OldWork = AT.WorkPointer;
149 if ( AT.WorkPointer < term + *term ) AT.WorkPointer = term + *term;
167 if ( ( ja + 2 ) > AN.patternbuffersize ) {
168 if ( AN.patternbuffer ) M_free(AN.patternbuffer,
"AN.patternbuffer");
169 AN.patternbuffersize = 2 * ja + 2;
170 AN.patternbuffer = (WORD *)Malloc1(AN.patternbuffersize *
sizeof(WORD),
173 ma = AN.patternbuffer;
179 AN.WildValue = w = m + SUBEXPSIZE;
180 protosize = IDHEAD + m[1];
188 if ( ( ll[4] & DOLLARFLAG ) != 0 ) {
189 WORD oldRepPoint = *AN.RepPoint, olddefer = AR.DeferFlag;
194 ww = AT.WorkPointer; i = m[0]; mm = m;
197 *ww++ = 1; *ww++ = 1; *ww++ = 3;
201 if (
Generator(BHEAD StartWork,AR.Cnumlhs) ) {
203 AT.WorkPointer = OldWork;
204 AR.DeferFlag = olddefer;
208 if (
EndSort(BHEAD ww,0) < 0 ) {}
209 AR.DeferFlag = olddefer;
210 if ( *ww == 0 || *(ww+*ww) != 0 ) {
211 if ( AP.lhdollarerror == 0 ) {
215 MLOCK(ErrorMessageLock);
216 MesPrint(
"&LHS must be one term");
217 MUNLOCK(ErrorMessageLock);
218 AP.lhdollarerror = 1;
220 AT.WorkPointer = OldWork;
224 if ( m[*m-1] < 0 ) { msign = 1; m[*m-1] = -m[*m-1]; }
225 if ( *ww || m[*m-1] != 3 || m[*m-2] != 1 || m[*m-3] != 1 ) {
226 MLOCK(ErrorMessageLock);
227 MesPrint(
"Dollar variable develops into an illegal pattern in id-statement");
228 MUNLOCK(ErrorMessageLock);
232 if ( ( *m + 1 + protosize ) > AN.patternbuffersize ) {
233 if ( AN.patternbuffer ) M_free(AN.patternbuffer,
"AN.patternbuffer");
234 AN.patternbuffersize = 2 * (*m) + 2 + protosize;
235 AN.patternbuffer = (WORD *)Malloc1(AN.patternbuffersize *
sizeof(WORD),
237 mm = ll; ww = AN.patternbuffer; i = protosize;
239 AN.FullProto = AN.patternbuffer + IDHEAD;
240 AN.WildValue = w = AN.FullProto + SUBEXPSIZE;
241 AN.WildStop = AN.patternbuffer + protosize;
243 mm = AN.patternbuffer + protosize;
246 m = AN.patternbuffer + protosize;
253 WORD *mmm = m + *m, *m1 = m+1, jm, noveto = 0;
255 if ( *m1 == SYMBOL ) {
256 for ( jm = 2; jm < m1[1]; jm+=2 ) {
257 if ( m1[jm+1] < MAXPOWER && m1[jm+1] > -MAXPOWER )
break;
259 if ( jm < m1[1] ) { noveto = 1;
break; }
261 else if ( *m1 == DOTPRODUCT ) {
262 for ( jm = 2; jm < m1[1]; jm+=3 ) {
263 if ( m1[jm+2] < MAXPOWER && m1[jm+2] > -MAXPOWER )
break;
265 if ( jm < m1[1] ) { noveto = 1;
break; }
267 else { noveto = 1;
break; }
271 ll2 = ll2 & ~SUBMASK;
275 AT.WorkPointer = ww = StartWork;
276 *AN.RepPoint = oldRepPoint;
284 if ( ( ll2 & SUBMASK ) == SUBALL ) {
285 WORD *t = AN.patternbuffer+IDHEAD, *tt;
286 WORD *tstop, *ttstop, ii;
287 t += t[1]; tstop = t + *t; t++;
288 while ( t < tstop ) {
289 if ( *t < FUNCTION )
break;
293 MLOCK(ErrorMessageLock);
294 MesPrint(
"Error: id,all can only be used with (products of) functions and/or tensors.");
295 MUNLOCK(ErrorMessageLock);
298 OldTermBuffer = AN.termbuffer;
299 AN.termbuffer = TermMalloc(
"id,all");
303 tt = term; ttstop = tt+*tt; ttstop -= ABS(ttstop[-1]); tt++;
305 while ( tt < ttstop ) {
306 if ( *tt >= FUNCTION && *tt != AR.PolyFun && *tt != AR.PolyFunInv ) {
307 ii = tt[1]; NCOPY(t,tt,ii);
311 *t++ = 1; *t++ = 1; *t++ = 3; AN.termbuffer[0] = t-AN.termbuffer;
319 while ( w < AN.WildStop ) {
320 if ( *w == LOADDOLLAR ) numdollars++;
324 AN.RepFunList = AT.WorkPointer;
325 AT.WorkPointer = (WORD *)(((UBYTE *)(AT.WorkPointer)) + AM.MaxTer/2);
326 if ( AT.WorkPointer >= AT.WorkTop ) {
327 MLOCK(ErrorMessageLock);
329 MUNLOCK(ErrorMessageLock);
332 AN.DisOrderFlag = ll2 & SUBDISORDER;
333 AN.nogroundlevel = 0;
334 switch ( ll2 & SUBMASK ) {
337 AN.UseFindOnly = 1; AN.ForFindOnly = 0;
338 if ( FindRest(BHEAD term,m) && ( AN.UsedOtherFind ||
339 FindOnly(BHEAD term,m) ) ) {
341 if ( msign ) term[term[0]-1] = -term[term[0]-1];
347 if ( ( power = FindRest(BHEAD term,m) ) > 0 ) {
348 if ( ( power = FindOnce(BHEAD term,m) ) > 0 ) {
351 if ( msign ) term[term[0]-1] = -term[term[0]-1];
352 Substitute(BHEAD term,m,1);
354 WildDollars(BHEAD (WORD *)0);
357 if ( ww < term+term[0] ) ww = term+term[0];
363 AT.WorkPointer = (WORD *)(((UBYTE *)(AT.WorkPointer)) + AM.MaxTer/2);
364 if ( AT.WorkPointer >= AT.WorkTop ) {
365 MLOCK(ErrorMessageLock);
367 MUNLOCK(ErrorMessageLock);
377 AN.nogroundlevel = 0;
378 }
while ( FindRest(BHEAD term,m) && ( AN.UsedOtherFind ||
379 FindOnce(BHEAD term,m) ) );
382 else if ( power < 0 ) {
384 if ( msign ) term[term[0]-1] = -term[term[0]-1];
385 Substitute(BHEAD term,m,1);
387 WildDollars(BHEAD (WORD *)0);
390 if ( ww < term+term[0] ) ww = term+term[0];
396 AT.WorkPointer = (WORD *)(((UBYTE *)(AT.WorkPointer)) + AM.MaxTer/2);
397 if ( AT.WorkPointer >= AT.WorkTop ) {
398 MLOCK(ErrorMessageLock);
400 MUNLOCK(ErrorMessageLock);
410 }
while ( FindRest(BHEAD term,m) );
414 else if ( power < 0 ) {
415 if ( FindOnce(BHEAD term,m) ) {
417 if ( msign ) term[term[0]-1] = -term[term[0]-1];
418 Substitute(BHEAD term,m,1);
420 WildDollars(BHEAD (WORD *)0);
423 if ( ww < term+term[0] ) ww = term+term[0];
429 AT.WorkPointer = (WORD *)(((UBYTE *)(AT.WorkPointer)) + AM.MaxTer/2);
430 if ( AT.WorkPointer >= AT.WorkTop ) {
431 MLOCK(ErrorMessageLock);
433 MUNLOCK(ErrorMessageLock);
443 }
while ( FindOnce(BHEAD term,m) );
448 if ( ( ll2 & SUBAFTER ) != 0 ) *level = AC.Labels[ll[3]];
451 if ( ( ll2 & SUBAFTERNOT ) != 0 ) *level = AC.Labels[ll[3]];
456 if ( FindRest(BHEAD term,m) && ( AN.UsedOtherFind || FindOnce(BHEAD term,m) ) ) {
458 if ( msign ) term[term[0]-1] = -term[term[0]-1];
463 power = FindMulti(BHEAD term,m);
464 if ( ( power & 1 ) != 0 && msign ) term[term[0]-1] = -term[term[0]-1];
467 while ( ( power = FindAll(BHEAD term,m,*level,(WORD *)0) ) != 0 ) {
468 if ( ( power & 1 ) != 0 && msign ) term[term[0]-1] = -term[term[0]-1];
473 llf = ll + IDHEAD; llf += llf[1]; llf += *llf;
474 AN.UseFindOnly = 1; AN.ForFindOnly = llf;
475 if ( FindRest(BHEAD term,m) && ( AN.UsedOtherFind || FindOnly(BHEAD term,m) ) ) {
476 if ( msign ) term[term[0]-1] = -term[term[0]-1];
484 if ( *term > AN.sizeselecttermundo ) {
485 if ( AN.selecttermundo ) M_free(AN.selecttermundo,
"AN.selecttermundo");
486 AN.sizeselecttermundo = *term +10;
487 AN.selecttermundo = (WORD *)Malloc1(
488 AN.sizeselecttermundo*
sizeof(WORD),
"AN.selecttermundo");
490 t1 = term; t2 = AN.selecttermundo; i = *term;
494 Substitute(BHEAD term,m,power);
496 if ( TestSelect(term,llf) ) {
499 t1 = term; t2 = AN.selecttermundo; i = *t2;
502 if ( ( ll2 & SUBAFTERNOT ) != 0 ) {
503 *level = AC.Labels[ll[3]];
510 WildDollars(BHEAD (WORD *)0);
514 if ( ( ll2 & SUBAFTER ) != 0 ) {
515 *level = AC.Labels[ll[3]];
519 if ( ( ll2 & SUBAFTERNOT ) != 0 ) {
520 *level = AC.Labels[ll[3]];
527 CC = cbuf+AT.allbufnum;
528 oldallnumrhs = CC->numrhs;
529 t =
AddRHS(AT.allbufnum,1);
532 AT.idallmaxnum = ll[5];
534 if ( FindRest(BHEAD AN.termbuffer,m) || AT.idallflag > 1 ) {
535 WORD *t, *tstop, *tt, first = 1, ii;
538 if ( msign ) term[term[0]-1] = -term[term[0]-1];
550 t = term; tstop = t + *t; ii = ABS(tstop[-1]); tstop -= ii;
551 tt = AT.WorkPointer+1;
553 while ( t < tstop ) {
554 if ( *t >= FUNCTION && *t != AR.PolyFun && *t != AR.PolyFunInv ) {
556 *tt++ = SUBEXPRESSION;
560 *tt++ = AT.allbufnum;
567 i = t[1]; NCOPY(tt,t,i);
570 if ( ( ll[4] & NORMALIZEFLAG ) != 0 ) {
577 for ( i = 0; i < ii; i++ ) tt[i] = t[i];
578 Divvy(BHEAD (UWORD *)tt,&na,(UWORD *)(&(AT.idallnum)),1);
587 ii = tt-AT.WorkPointer;
588 *(AT.WorkPointer) = ii;
589 tt = AT.WorkPointer; t = term;
592 if ( ( ll2 & SUBAFTER ) != 0 ) {
593 *level = AC.Labels[ll[3]];
595 TermFree(AN.termbuffer,
"id,all");
596 AN.termbuffer = OldTermBuffer;
597 AT.WorkPointer = AN.RepFunList;
600 TransferBuffer(AT.aebufnum,AT.ebufnum,AT.allbufnum);
605 CC->numrhs = oldallnumrhs;
606 TermFree(AN.termbuffer,
"id,all");
607 AN.termbuffer = OldTermBuffer;
613 Substitute(BHEAD term,m,power);
615 WildDollars(BHEAD (WORD *)0);
619 if ( ( ll2 & SUBAFTER ) != 0 ) {
620 *level = AC.Labels[ll[3]];
624 AT.WorkPointer = AN.RepFunList;
625 if ( ( ll2 & SUBAFTERNOT ) != 0 ) {
626 *level = AC.Labels[ll[3]];
630 }
while ( (*level)++ < AR.Cnumlhs && C->
lhs[*level][0] == TYPEIDOLD );
632 AT.WorkPointer = AN.RepFunList;
641void Substitute(PHEAD WORD *term, WORD *pattern, WORD power)
648 WORD nt, *fill, nq, mt;
649 WORD *q, *subterm, *tcoef, oldval1 = 0, newval3, i = 0;
650 WORD PutExpr = 0, sign = 0;
651 TemTerm = AT.WorkPointer;
652 if ( ( (WORD *)(((UBYTE *)(AT.WorkPointer)) + AM.MaxTer*2) ) > AT.WorkTop ) {
653 MLOCK(ErrorMessageLock);
655 MUNLOCK(ErrorMessageLock);
664 tstop = t - ABS(*t) + 1;
669 if ( m < mstop ) {
do {
673 if ( *m == SYMBOL ) {
676 while ( *t != SYMBOL && t < tstop ) {
680 if ( t >= tstop )
goto SubCoef;
687 if ( *m == *t && t < xstop ) {
690 if ( mt >= 2*MAXPOWER ) {
691 if ( CheckWild(BHEAD mt-2*MAXPOWER,SYMTONUM,-MAXPOWER,&newval3) ) {
696 else if ( mt <= -2*MAXPOWER ) {
697 if ( CheckWild(BHEAD -mt-2*MAXPOWER,SYMTONUM,-MAXPOWER,&newval3) ) {
711 else if ( *m >= 2*MAXPOWER ) {
712 while ( t < xstop ) { *fill++ = *t++; *fill++ = *t++; }
713 nq = WORDDIF(fill,subterm);
716 if ( !CheckWild(BHEAD *m-2*MAXPOWER,SYMTOSYM,*fill,&newval3) ) {
718 if ( mt >= 2*MAXPOWER ) {
719 if ( CheckWild(BHEAD mt-2*MAXPOWER,SYMTONUM,-MAXPOWER,&newval3) ) {
720 if ( fill[1] -= AN.oldvalue )
goto SubsL2;
723 else if ( mt <= -2*MAXPOWER ) {
724 if ( CheckWild(BHEAD -mt-2*MAXPOWER,SYMTONUM,-MAXPOWER,&newval3) ) {
725 if ( fill[1] += AN.oldvalue )
goto SubsL2;
729 if ( fill[1] -= mt * power ) {
742 while ( --nq >= 0 ) *fill++ = *q++;
746 else if ( *m < *t || t >= xstop ) { m += 2; }
747 else { *fill++ = *t++; *fill++ = *t++; }
748 }
while ( m < ystop );
749 while ( t < xstop ) *fill++ = *t++;
750 nq = WORDDIF(fill,subterm);
755 else { fill = subterm; fill -= 2; }
761 else if ( *m == DOTPRODUCT ) {
764 while ( *t > DOTPRODUCT && t < tstop ) {
768 if ( t >= tstop )
goto SubCoef;
769 if ( *t != DOTPRODUCT ) {
773 *fill++ = DOTPRODUCT;
779 if ( *m == *t && m[1] == t[1] && t < xstop ) {
782 if ( mt >= 2*MAXPOWER ) {
783 if ( CheckWild(BHEAD mt-2*MAXPOWER,SYMTONUM,-MAXPOWER,&newval3) ) {
788 else if ( mt <= -2*MAXPOWER ) {
789 if ( CheckWild(BHEAD -mt-2*MAXPOWER,SYMTONUM,-MAXPOWER,&newval3) ) {
806 else if ( *m >= (AM.OffsetVector+WILDOFFSET) ) {
807 while ( t < xstop ) {
808 *fill++ = *t++; *fill++ = *t++; *fill++ = *t++;
813 else if ( m[1] >= (AM.OffsetVector+WILDOFFSET) ) {
814 while ( *m >= *t && t < xstop ) {
815 *fill++ = *t++; *fill++ = *t++; *fill++ = *t++;
818SubsL4: nq = WORDDIF(fill,subterm);
821 if ( ( oldval1 && ( (
822 !CheckWild(BHEAD *m-WILDOFFSET,VECTOVEC,*fill,&newval3)
823 && !CheckWild(BHEAD m[1]-WILDOFFSET,VECTOVEC,fill[1],&newval3)
825 !CheckWild(BHEAD m[1]-WILDOFFSET,VECTOVEC,*fill,&newval3)
826 && !CheckWild(BHEAD *m-WILDOFFSET,VECTOVEC,fill[1],&newval3)
827 ) ) ) || ( !oldval1 && ( (
829 && !CheckWild(BHEAD m[1]-WILDOFFSET,VECTOVEC,fill[1],&newval3)
831 !CheckWild(BHEAD m[1]-WILDOFFSET,VECTOVEC,*fill,&newval3)
832 && *m == fill[1] ) ) ) ) {
834 if ( mt >= 2*MAXPOWER ) {
835 if ( CheckWild(BHEAD mt-2*MAXPOWER,SYMTONUM,-MAXPOWER,&newval3) ) {
836 if ( fill[2] -= AN.oldvalue )
840 else if ( mt <= -2*MAXPOWER ) {
841 if ( CheckWild(BHEAD -mt-2*MAXPOWER,SYMTONUM,-MAXPOWER,&newval3) ) {
842 if ( fill[2] += AN.oldvalue )
847 if ( fill[2] -= mt * power ) {
860 while ( --nq >= 0 ) *fill++ = *q++;
863 else if ( t >= xstop || *m < *t || ( *m == *t && m[1] < t[1] ) )
866 *fill++ = *t++; *fill++ = *t++; *fill++ = *t++;
868 }
while ( m < ystop );
869 while ( t < xstop ) *fill++ = *t++;
870 nq = WORDDIF(fill,subterm);
875 else { fill = subterm; fill -= 2; }
881 else if ( *m >= FUNCTION ) {
882 while ( *t >= FUNCTION || *t == SUBEXPRESSION ) {
883 nt = WORDDIF(t,term);
884 for ( mt = 0; mt < AN.RepFunNum; mt += 2 ) {
885 if ( nt == AN.RepFunList[mt] )
break;
887 if ( mt >= AN.RepFunNum ) {
893 if ( *m == GAMMA && m[1] != FUNHEAD+1 ) {
895 if ( ( i = AN.RepFunList[mt+1] ) > 0 ) {
897 *fill++ = i + FUNHEAD+1;
905 else if ( ( *t == LEVICIVITA ) || ( *t >= FUNCTION
906 && (functions[*t-FUNCTION].symmetric & ~REVERSEORDER) == ANTISYMMETRIC )
907 ) sign += AN.RepFunList[mt+1];
908 else if ( *m >= FUNCTION+WILDOFFSET
909 && (functions[*m-FUNCTION-WILDOFFSET].symmetric & ~REVERSEORDER) == ANTISYMMETRIC
910 ) sign += AN.RepFunList[mt+1];
921 if ( *m == GAMMA && m[1] != FUNHEAD+1 ) {
922 i = oldt[1] - m[1] - i;
925 *fill++ = i + FUNHEAD+1;
927 *fill++ = oldt[FUNHEAD];
941 else if ( *m == VECTOR ) {
942 while ( *t > VECTOR ) {
954 if ( *m == *t && m[1] == t[1] ) {
957 else if ( *m >= (AM.OffsetVector+WILDOFFSET) ) {
958 while ( t < xstop ) *fill++ = *t++;
959 nq = WORDDIF(fill,subterm);
961 if ( m[1] < (AM.OffsetIndex+WILDOFFSET) ) {
963 if ( m[1] == fill[1] &&
964 !CheckWild(BHEAD *m-WILDOFFSET,VECTOVEC,*fill,&newval3) )
972 if ( !CheckWild(BHEAD m[1]-WILDOFFSET,INDTOIND,fill[1],&newval3)
973 && !CheckWild(BHEAD *m-WILDOFFSET,VECTOVEC,*fill,&newval3) )
975 if ( *fill == oldval1 && fill[1] == AN.oldvalue )
break;
982 if ( nq > 0 ) { NCOPY(fill,q,nq); }
985 else if ( *m <= *t &&
986 m[1] >= (AM.OffsetIndex + WILDOFFSET) ) {
987 while ( *m == *t && t < xstop )
988 { *fill++ = *t++; *fill++ = *t++; }
989 nq = WORDDIF(fill,subterm);
993 !CheckWild(BHEAD m[1]-WILDOFFSET,INDTOIND,fill[1],&newval3) )
1000 if ( nq > 0 ) { NCOPY(fill,q,nq); }
1003 else { *fill++ = *t++; *fill++ = *t++; }
1004 }
while ( m < ystop );
1005 while ( t < xstop ) *fill++ = *t++;
1006 nq = WORDDIF(fill,subterm);
1011 else { fill = subterm; fill -= 2; }
1019 else if ( *m == INDEX ) {
1020 while ( *t > INDEX ) {
1035 else if ( *m >= (AM.OffsetIndex+WILDOFFSET) ) {
1036 while ( t < xstop ) *fill++ = *t++;
1037 nq = WORDDIF(fill, subterm);
1040 if ( !CheckWild(BHEAD *m-WILDOFFSET,INDTOIND,*fill,&newval3) ) {
1056 }
while ( m < ystop );
1057 while ( t < xstop ) *fill++ = *t++;
1058 nq = WORDDIF(fill,subterm);
1063 else { fill = subterm; fill -= 2; }
1069 else if ( *m == DELTA ) {
1070 while ( *t > DELTA ) {
1082 if ( *t == *m && t[1] == m[1] ) { m += 2; t += 2; }
1083 else if ( *m >= (AM.OffsetIndex+WILDOFFSET) ) {
1084 while ( t < xstop ) *fill++ = *t++;
1089 else if ( m[1] >= (AM.OffsetIndex+WILDOFFSET) ) {
1090 while ( (*m == *t || *m == t[1] ) && ( t < xstop ) ) {
1091 *fill++ = *t++; *fill++ = *t++;
1094SubsL6: nq = WORDDIF(fill,subterm);
1097 if ( ( oldval1 && ( (
1098 !CheckWild(BHEAD *m-WILDOFFSET,INDTOIND,*fill,&newval3)
1099 && !CheckWild(BHEAD m[1]-WILDOFFSET,INDTOIND,fill[1],&newval3)
1101 !CheckWild(BHEAD m[1]-WILDOFFSET,INDTOIND,*fill,&newval3)
1102 && !CheckWild(BHEAD *m-WILDOFFSET,INDTOIND,fill[1],&newval3)
1103 ) ) ) || ( !oldval1 && ( (
1105 && !CheckWild(BHEAD m[1]-WILDOFFSET,INDTOIND,fill[1],&newval3)
1108 && !CheckWild(BHEAD m[1]-WILDOFFSET,INDTOIND,*fill,&newval3)
1121 *fill++ = *t++; *fill++ = *t++;
1123 }
while ( m < ystop );
1124 while ( t < xstop ) *fill++ = *t++;
1125 nq = WORDDIF(fill,subterm);
1130 else { fill = subterm; fill -= 2; }
1136 }
while ( m < mstop ); }
1137 while ( t < tstop ) *fill++ = *t++;
1149 nq = WORDDIF(fill,TemTerm);
1156 if ( ( sign & 1 ) != 0 ) fill[-1] = -fill[-1];
1158 if ( AT.WorkPointer < fill ) AT.WorkPointer = fill;
1197int FindAll(PHEAD WORD *term, WORD *pattern, WORD level, WORD *par)
1200 WORD *t, *m, *r, *mm, rnum;
1201 WORD *tstop, *mstop, *TwoProto, *vwhere = 0, oldv, oldvv, vv, level2;
1202 WORD v, nq, OffNum = AM.OffsetVector + WILDOFFSET, i, ii = 0, jj;
1203 WORD fromindex, *intens, notflag1 = 0, notflag2 = 0;
1205 C = cbuf+AM.rbufnum;
1217 if ( *t == VECTOR ) {
1221 while ( r < tstop ) {
1223 if ( v >= OffNum ) {
1224 vwhere = AN.FullProto + 3 + SUBEXPSIZE;
1225 if ( vwhere[1] == FROMSET || vwhere[1] == SETTONUM ) {
1226 WORD *afirst, *alast, j;
1228 if ( j > WILDOFFSET ) { j -= 2*WILDOFFSET; notflag1 = 1; }
1229 else { notflag1 = 0; }
1230 afirst = SetElements + Sets[j].first;
1231 alast = SetElements + Sets[j].last;
1233 if ( notflag1 == 0 ) {
1235 if ( *afirst == *r ) {
1236 if ( vwhere[1] == SETTONUM ) {
1237 AN.FullProto[8+SUBEXPSIZE] = SYMTONUM;
1238 AN.FullProto[11+SUBEXPSIZE] = ii;
1240 else if ( vwhere[4] >= 0 ) {
1241 oldv = *(afirst - Sets[j].first
1242 + Sets[vwhere[4]].first);
1247 }
while ( ++afirst < alast );
1251 if ( *afirst == *r )
break;
1252 }
while ( ++afirst < alast );
1253 if ( afirst >= alast )
goto DoVect;
1258 else if ( v == *r ) {
1259DoVect: m = AT.WorkPointer;
1263 do { *m++ = *t++; }
while ( t < tstop );
1270 if ( fromindex == 1 ) m[-1] = FUNNYVEC;
1272 if ( v >= OffNum ) vwhere[3+SUBEXPSIZE] = oldv;
1273 if ( vwhere[1] > 12+SUBEXPSIZE ) {
1274 vwhere[11+SUBEXPSIZE] = ii;
1275 vwhere[8+SUBEXPSIZE] = SYMTONUM;
1277 if ( t[1] > fromindex+2 ) {
1279 *m++ = *t++ - fromindex;
1280 while ( t < r ) *m++ = *t++;
1284 do { *m++ = *t++; }
while ( t < mstop );
1285 *AT.WorkPointer = nq = WORDDIF(m,AT.WorkPointer);
1299 else if ( *t == DOTPRODUCT ) {
1303 if ( ( i = r[2] ) < 0 )
goto NextDot;
1307TwoVec: m = AT.WorkPointer;
1311 do { *m++ = *t++; }
while ( t < tstop );
1318 m[-1] = ++AR.CurDum;
1319 if ( v >= OffNum ) vwhere[3+SUBEXPSIZE] = oldv;
1320 }
while ( --i > 0 );
1325 while ( t < r ) *m++ = *t++;
1329 do { *m++ = *t++; }
while ( t < mstop );
1330 *AT.WorkPointer = nq = WORDDIF(m,AT.WorkPointer);
1337 else if ( v >= OffNum ) {
1338 vwhere = AN.FullProto + 3+SUBEXPSIZE;
1339 if ( vwhere[1] == FROMSET || vwhere[1] == SETTONUM ) {
1340 WORD *afirst, *alast, j;
1342 if ( j > WILDOFFSET ) { j -= 2*WILDOFFSET; notflag1 = 1; }
1343 else { notflag1 = 0; }
1344 afirst = SetElements + Sets[j].first;
1345 alast = SetElements + Sets[j].last;
1347 if ( notflag1 == 0 ) {
1349 if ( *afirst == *r ) {
1350 if ( vwhere[1] == SETTONUM ) {
1351 AN.FullProto[8+SUBEXPSIZE] = SYMTONUM;
1352 AN.FullProto[11+SUBEXPSIZE] = ii;
1354 else if ( vwhere[4] >= 0 ) {
1355 oldv = *(afirst - Sets[j].first
1356 + Sets[vwhere[4]].first);
1361 }
while ( ++afirst < alast );
1365 if ( *afirst == *r )
break;
1366 }
while ( ++afirst < alast );
1367 if ( afirst >= alast )
goto TwoVec;
1374 if ( v == r[1] ) { r[1] = *r; *r = v; }
1378 if ( !par ) {
while ( ++level <= AR.Cnumlhs
1379 && C->
lhs[level][0] == TYPEIDOLD ) {
1382 if ( m[-IDHEAD+2] == SUBVECTOR ) {
1383 if ( ( vv = m[m[1]+3] ) == r[1] ) {
1384OnePV: TwoProto = AN.FullProto;
1385TwoPV: m = AT.WorkPointer;
1389 do { *m++ = *t++; }
while ( t < tstop );
1392 vwhere = m + 3 +SUBEXPSIZE;
1396 m[-1] = ++AR.CurDum;
1397 if ( v >= OffNum ) *vwhere = oldv;
1398 if ( vwhere[-2-SUBEXPSIZE] > 12+SUBEXPSIZE ) {
1400 vwhere[5] = SYMTONUM;
1403 vwhere = m + 3+SUBEXPSIZE;
1412 mm[2] = C->
lhs[level][IDHEAD+2];
1413 mm[4] = C->
lhs[level][IDHEAD+4];
1415 if ( vv >= OffNum ) *vwhere = oldvv;
1416 }
while ( --i > 0 );
1419 else if ( vv > OffNum ) {
1420 vwhere = AN.FullProto + 3+SUBEXPSIZE;
1421 if ( vwhere[1] == FROMSET || vwhere[1] == SETTONUM ) {
1422 WORD *afirst, *alast, j;
1424 if ( j > WILDOFFSET ) { j -= 2*WILDOFFSET; notflag1 = 1; }
1425 else { notflag1 = 0; }
1426 afirst = SetElements + Sets[j].first;
1427 alast = SetElements + Sets[j].last;
1428 if ( notflag1 == 0 ) {
1431 if ( *afirst == r[1] ) {
1432 if ( vwhere[1] == SETTONUM ) {
1433 AN.FullProto[8+SUBEXPSIZE] = SYMTONUM;
1434 AN.FullProto[11+SUBEXPSIZE] = ii;
1436 else if ( vwhere[4] >= 0 ) {
1437 oldvv = *(afirst - Sets[j].first
1438 + Sets[vwhere[4]].first);
1443 }
while ( ++afirst < alast );
1447 if ( *afirst == *r )
break;
1448 }
while ( ++afirst < alast );
1449 if ( afirst >= alast )
goto OnePV;
1462OneOnly: m = AT.WorkPointer;
1466 do { *m++ = *t++; }
while ( t < tstop );
1474 if ( v >= OffNum ) vwhere[3+SUBEXPSIZE] = oldv;
1477 else if ( v >= OffNum ) {
1478 vwhere = AN.FullProto + 3+SUBEXPSIZE;
1479 if ( vwhere[1] == FROMSET || vwhere[1] == SETTONUM ) {
1480 WORD *afirst, *alast, *bfirst, *blast, j;
1482 if ( j > WILDOFFSET ) { j -= 2*WILDOFFSET; notflag1 = 1; }
1483 else { notflag1 = 0; }
1484 afirst = SetElements + Sets[j].first;
1485 alast = SetElements + Sets[j].last;
1487 if ( notflag1 == 0 ) {
1489 if ( *afirst == *r ) {
1490 if ( vwhere[1] == SETTONUM ) {
1491 AN.FullProto[8+SUBEXPSIZE] = SYMTONUM;
1492 AN.FullProto[11+SUBEXPSIZE] = ii;
1494 else if ( vwhere[4] >= 0 ) {
1495 oldv = *(afirst - Sets[j].first
1496 + Sets[vwhere[4]].first);
1498Hitlevel1: level2 = level;
1500 if ( !par ) m = C->
lhs[level2];
1503 if ( m[-IDHEAD+2] == SUBVECTOR ) {
1504 if ( ( vv = m[m[1]+3] ) == r[1] )
1506 else if ( vv >= OffNum ) {
1507 if ( m[SUBEXPSIZE+4] != FROMSET &&
1508 m[SUBEXPSIZE+4] != SETTONUM )
goto OnePV;
1509 j = m[SUBEXPSIZE+6];
1510 if ( j > WILDOFFSET ) { j -= 2*WILDOFFSET; notflag2 = 1; }
1511 else { notflag2 = 0; }
1512 bfirst = SetElements + Sets[j].first;
1513 blast = SetElements + Sets[j].last;
1515 if ( notflag2 == 0 ) {
1517 if ( *bfirst == r[1] ) {
1518 if ( m[SUBEXPSIZE+4] == SETTONUM ) {
1519 m[SUBEXPSIZE+8] = SYMTONUM;
1520 m[SUBEXPSIZE+11] = jj;
1522 else if ( m[SUBEXPSIZE+7] >= 0 ) {
1523 oldvv = *(bfirst - Sets[j].first
1524 + Sets[m[SUBEXPSIZE+7]].first);
1529 }
while ( ++bfirst < blast );
1533 if ( *bfirst == r[1] )
break;
1534 }
while ( ++bfirst < blast );
1535 if ( bfirst >= blast )
goto OnePV;
1539 }
while ( ++level2 < AR.Cnumlhs &&
1540 C->
lhs[level2][0] == TYPEIDOLD );
1544 else if ( *afirst == r[1] ) {
1545 if ( vwhere[1] == SETTONUM ) {
1546 AN.FullProto[8+SUBEXPSIZE] = SYMTONUM;
1547 AN.FullProto[11+SUBEXPSIZE] = ii;
1549 else if ( vwhere[4] >= 0 ) {
1550 oldv = *(afirst - Sets[j].first
1551 + Sets[vwhere[4]].first);
1553Hitlevel2: level2 = level;
1554 while ( ++level2 < AR.Cnumlhs &&
1555 C->
lhs[level2][0] == TYPEIDOLD ) {
1556 if ( !par ) m = C->
lhs[level2];
1559 if ( m[-IDHEAD+2] == SUBVECTOR ) {
1560 if ( ( vv = m[6] ) == *r )
1562 else if ( vv >= OffNum ) {
1563 if ( m[SUBEXPSIZE+4] != FROMSET && m[SUBEXPSIZE+4]
1570 j = m[SUBEXPSIZE+6];
1571 bfirst = SetElements + Sets[j].first;
1572 blast = SetElements + Sets[j].last;
1575 if ( *bfirst == *r ) {
1576 if ( m[SUBEXPSIZE+4] == SETTONUM ) {
1577 m[SUBEXPSIZE+8] = SYMTONUM;
1578 m[SUBEXPSIZE+11] = jj;
1580 else if ( m[SUBEXPSIZE+7] >= 0 ) {
1581 oldvv = *(bfirst - Sets[j].first
1582 + Sets[m[SUBEXPSIZE+7]].first);
1587 j = oldv; oldv = oldvv; oldvv = j;
1591 }
while ( ++bfirst < blast );
1595 jj = *r; *r = r[1]; r[1] = jj;
1596 jj = oldv; oldv = oldvv; oldvv = j;
1601 }
while ( ++afirst < alast );
1605 if ( *afirst == *r )
break;
1606 }
while ( ++afirst < alast );
1607 if ( afirst >= alast )
goto Hitlevel1;
1609 if ( *afirst == r[1] )
break;
1610 }
while ( ++afirst < alast );
1611 if ( afirst >= alast )
goto Hitlevel2;
1616 TwoProto = AN.FullProto;
1622 }
while ( r < tstop );
1628 else if ( *t == LEVICIVITA ) {
1633 while ( r < tstop ) {
1635 if ( v >= OffNum && *r < -10 ) {
1636 vwhere = AN.FullProto + 3+SUBEXPSIZE;
1637 if ( vwhere[1] == FROMSET || vwhere[1] == SETTONUM ) {
1638 WORD *afirst, *alast, j;
1640 if ( j > WILDOFFSET ) { j -= 2*WILDOFFSET; notflag1 = 1; }
1641 else { notflag1 = 0; }
1642 afirst = SetElements + Sets[j].first;
1643 alast = SetElements + Sets[j].last;
1645 if ( notflag1 == 0 ) {
1647 if ( *afirst == *r ) {
1648 if ( vwhere[1] == SETTONUM ) {
1649 AN.FullProto[8+SUBEXPSIZE] = SYMTONUM;
1650 AN.FullProto[11+SUBEXPSIZE] = ii;
1652 else if ( vwhere[4] >= 0 ) {
1653 oldv = *(afirst - Sets[j].first
1654 + Sets[vwhere[4]].first);
1659 }
while ( ++afirst < alast );
1663 if ( *afirst == *r )
break;
1664 }
while ( ++afirst < alast );
1665 if ( afirst >= alast )
goto DoVect;
1670 else if ( v == *r ) {
1671LeVect: m = AT.WorkPointer;
1672 mstop = term + *term;
1675 if ( intens ) *intens = DIRTYSYMFLAG;
1676 do { *m++ = *t++; }
while ( t < tstop );
1680 if ( v >= OffNum ) *vwhere = oldv;
1684 do { *m++ = *t++; }
while ( t < mstop );
1685 *AT.WorkPointer = nq = WORDDIF(m,AT.WorkPointer);
1699 else if ( *t == GAMMA ) {
1703 if ( r < tstop )
goto OneVect;
1709 else if ( *t == INDEX ) {
1719 else if ( *t >= FUNCTION ) {
1721 && functions[*t-FUNCTION].spec >= TENSORFUNCTION
1722 && t[1] > FUNHEAD ) {
1748int TestSelect(WORD *term, WORD *setp)
1750 WORD *tstop, *t, *s, *el, *elstop, *termstop, *tt, n, ns;
1751 GETSTOP(term,tstop);
1753 while ( term < tstop ) {
1761 while ( --ns >= 0 ) {
1762 if ( Sets[*s].type != CSYMBOL ) { s++;
continue; }
1763 el = SetElements + Sets[*s].first;
1764 elstop = SetElements + Sets[*s].last;
1765 while ( el < elstop ) {
1766 if ( *el++ == *t )
return(1);
1780 while ( --ns >= 0 ) {
1781 if ( Sets[*s].type != CVECTOR ) { s++;
continue; }
1782 el = SetElements + Sets[*s].first;
1783 elstop = SetElements + Sets[*s].last;
1784 while ( el < elstop ) {
1785 if ( *el++ == *t )
return(1);
1792 while ( --ns >= 0 ) {
1793 if ( Sets[*s].type != CINDEX
1794 && Sets[*s].type != CNUMBER ) { s++;
continue; }
1795 el = SetElements + Sets[*s].first;
1796 elstop = SetElements + Sets[*s].last;
1797 while ( el < elstop ) {
1798 if ( *el++ == *t )
return(1);
1816 while ( --ns >= 0 ) {
1817 if ( Sets[*s].type != CVECTOR ) { s++;
continue; }
1818 el = SetElements + Sets[*s].first;
1819 elstop = SetElements + Sets[*s].last;
1820 while ( el < elstop ) {
1821 if ( *el++ == *t )
return(1);
1828 while ( --ns >= 0 ) {
1829 if ( Sets[*s].type != CVECTOR ) { s++;
continue; }
1830 el = SetElements + Sets[*s].first;
1831 elstop = SetElements + Sets[*s].last;
1832 while ( el < elstop ) {
1833 if ( *el++ == *t )
return(1);
1846 if ( *term < FUNCTION )
break;
1849 while ( --ns >= 0 ) {
1850 if ( Sets[*s].type != CFUNCTION ) { s++;
continue; }
1851 el = SetElements + Sets[*s].first;
1852 elstop = SetElements + Sets[*s].last;
1853 while ( el < elstop ) {
1854 if ( *el++ == *term )
return(1);
1858 if ( functions[*term-FUNCTION].spec > 0 ) {
1859 n = term[1] - FUNHEAD;
1865 while ( --ns >= 0 ) {
1866 if ( *t < MINSPEC ) {
1867 if ( Sets[*s].type != CVECTOR ) { s++;
continue; }
1869 else if ( *t >= 0 ) {
1870 if ( Sets[*s].type != CINDEX
1871 && Sets[*s].type != CNUMBER ) { s++;
continue; }
1873 else { s++;
continue; }
1874 el = SetElements + Sets[*s].first;
1875 elstop = SetElements + Sets[*s].last;
1876 while ( el < elstop ) {
1877 if ( *el++ == *t )
return(1);
1886 termstop = term + term[1];
1887 tt = term + FUNHEAD;
1888 while ( tt < termstop ) {
1890 if ( *tt == -SYMBOL ) {
1893 while ( --ns >= 0 ) {
1894 if ( Sets[*s].type != CSYMBOL ) { s++;
continue; }
1895 el = SetElements + Sets[*s].first;
1896 elstop = SetElements + Sets[*s].last;
1897 while ( el < elstop ) {
1898 if ( *el++ == tt[1] )
return(1);
1904 else if ( *tt == -VECTOR || *tt == -MINVECTOR ) {
1907 while ( --ns >= 0 ) {
1908 if ( Sets[*s].type != CVECTOR ) { s++;
continue; }
1909 el = SetElements + Sets[*s].first;
1910 elstop = SetElements + Sets[*s].last;
1911 while ( el < elstop ) {
1912 if ( *el++ == tt[1] )
return(1);
1918 else if ( *tt == -INDEX ) {
1921 while ( --ns >= 0 ) {
1922 if ( Sets[*s].type != CINDEX
1923 && Sets[*s].type != CNUMBER ) { s++;
continue; }
1924 el = SetElements + Sets[*s].first;
1925 elstop = SetElements + Sets[*s].last;
1926 while ( el < elstop ) {
1927 if ( *el++ == tt[1] )
return(1);
1933 else if ( *tt <= -FUNCTION ) {
1936 while ( --ns >= 0 ) {
1937 if ( Sets[*s].type != CFUNCTION ) { s++;
continue; }
1938 el = SetElements + Sets[*s].first;
1939 elstop = SetElements + Sets[*s].last;
1940 while ( el < elstop ) {
1941 if ( *el++ == -(*tt) )
return(1);
1953 if ( TestSelect(t,setp) )
return(1);
1982void SubsInAll(PHEAD0)
1987 WORD *tstop, *mstop, *xstop;
1988 WORD nt, *fill, nq, mt;
1990 WORD PutExpr = 0, sign = 0;
1997 TemTerm = AT.WorkPointer;
1998 if ( ( (WORD *)(((UBYTE *)(AT.WorkPointer)) + AM.MaxTer*2) ) > AT.WorkTop ) {
1999 MLOCK(ErrorMessageLock);
2001 MUNLOCK(ErrorMessageLock);
2004 m = AN.patternbuffer + IDHEAD; m += m[1];
2007 term = AN.termbuffer;
2008 tstop = term + *term; tcoef = tstop-1; tstop -= ABS(tstop[-1]);
2013 while ( m < mstop ) {
2014 while ( t < tstop ) {
2015 nt = WORDDIF(t,term);
2016 for ( mt = 0; mt < AN.RepFunNum; mt += 2 ) {
2017 if ( nt == AN.RepFunList[mt] )
break;
2019 if ( mt >= AN.RepFunNum ) {
2025 if ( *m == GAMMA && m[1] != FUNHEAD+1 ) {
2027 if ( ( i = AN.RepFunList[mt+1] ) > 0 ) {
2029 *fill++ = i + FUNHEAD+1;
2037 else if ( ( *t == LEVICIVITA ) || ( *t >= FUNCTION
2038 && (functions[*t-FUNCTION].symmetric & ~REVERSEORDER) == ANTISYMMETRIC )
2039 ) sign += AN.RepFunList[mt+1];
2040 else if ( *m >= FUNCTION+WILDOFFSET
2041 && (functions[*m-FUNCTION-WILDOFFSET].symmetric & ~REVERSEORDER) == ANTISYMMETRIC
2042 ) sign += AN.RepFunList[mt+1];
2044 WORD *pstart = fill, *p, *w, *ww;
2060 p = pstart + SUBEXPSIZE;
2061 while ( p < fill ) {
2068 w = cbuf[AT.ebufnum].rhs[p[3]];
2069 ww = cbuf[AT.ebufnum].rhs[p[3]+1];
2077 AddNtoC(AT.aebufnum,ww-w,w,11);
2078 p[3] = cbuf[AT.aebufnum].numrhs;
2079 cbuf[AT.aebufnum].rhs[p[3]+1] = cbuf[AT.aebufnum].Pointer;
2095 if ( *m == GAMMA && m[1] != FUNHEAD+1 ) {
2096 i = oldt[1] - m[1] - i;
2099 *fill++ = i + FUNHEAD+1;
2101 *fill++ = oldt[FUNHEAD];
2111 while ( t < tstop ) *fill++ = *t++;
2123 if ( ( sign & 1 ) != 0 ) fill[-1] = -fill[-1];
2125 *TemTerm = fill-TemTerm;
2129 AddNtoC(AT.allbufnum,TemTerm[0],TemTerm,12);
2130 cbuf[AT.allbufnum].Pointer[0] = 0;
2143void TransferBuffer(
int from,
int to,
int spectator)
2145 CBUF *C = cbuf + spectator;
2146 CBUF *Cf = cbuf + from;
2147 CBUF *Ct = cbuf + to;
2148 int offset = Ct->numrhs;
2150 WORD *t, *tt, *ttt, *tstop, size;
2151 for ( i = 1; i <= Cf->numrhs; i++ ) {
2152 size = Cf->
rhs[i+1]-Cf->
rhs[i];
2161 t = C->
rhs[C->numrhs];
2164 tstop = t-ABS(t[-1]);
2165 while ( tt < tstop ) {
2166 if ( *tt == SUBEXPRESSION ) {
2167 ttt = tt+SUBEXPSIZE; tt += tt[1];
2168 while ( ttt < tt ) {
2193#define PutInBuffers(pow) \
2194 AddRHS(AT.ebufnum,1); \
2195 *out++ = SUBEXPRESSION; \
2196 *out++ = SUBEXPSIZE; \
2197 *out++ = C->numrhs; \
2199 *out++ = AT.ebufnum; \
2201 r = AT.pWorkSpace[rhs+i]; \
2203 oldinr = r[*r]; r[*r] = 0; \
2204 AddNtoC(AT.ebufnum,(*r+1-ARGHEAD),(r+ARGHEAD),14); \
2208 ToGeneral(r,buffer,1); \
2209 buffer[buffer[0]] = 0; \
2210 AddNtoC(AT.ebufnum,buffer[0]+1,buffer,15); \
2213int TakeIDfunction(PHEAD WORD *term)
2215 WORD *tstop, *t, *r, *m, *f, *nextf, *funstop, *left, *l, *newterm;
2216 WORD *out, oldinr, pow;
2218 int i, ii, j, numsub, numfound = 0, first;
2221 GETSTOP(term,tstop);
2222 for ( t = term+1; t < tstop; t += t[1] ) {
if ( *t == IDFUNCTION )
break; }
2223 if ( t >= tstop )
return(0);
2227 funstop = t + t[1]; f = t + FUNHEAD;
2228 left = term + *term;
2229 l = left+1; numsub = 0;
2230 while ( f < funstop ) {
2231 nextf = f; NEXTARG(nextf)
2232 if ( nextf >= funstop ) {
return(0); }
2233 if ( *f == -SYMBOL ) { *l++ = SYMBOL; *l++ = 4; *l++ = f[1]; *l++ = 1; }
2234 else if ( *f < -FUNCTION ) { *l++ = *f; *l++ = FUNHEAD; FILLFUN(l) }
2235 else if ( *f > 0 ) {
2236 if ( *f != f[ARGHEAD]+ARGHEAD )
goto noaction;
2237 if ( nextf[-1] != 3 || nextf[-2] != 1 || nextf[-3] != 1 )
goto noaction;
2238 if ( f[ARGHEAD] <= 4 )
goto noaction;
2239 if ( f[ARGHEAD] != f[ARGHEAD+2]+4 )
goto noaction;
2240 if ( f[ARGHEAD] == 8 && f[ARGHEAD+1] == SYMBOL ) {
2241 for ( i = 0; i < 4; i++ ) *l++ = f[ARGHEAD+1+i];
2243 else if ( f[ARGHEAD] == 9 && f[ARGHEAD+1] == DOTPRODUCT ) {
2244 for ( i = 0; i < 5; i++ ) *l++ = f[ARGHEAD+1+i];
2246 else if ( f[ARGHEAD+1] >= FUNCTION ) {
2247 for ( i = 0; i < f[ARGHEAD+1]-4; i++ ) *l++ = f[ARGHEAD+1+i];
2256 C = cbuf+AT.ebufnum;
2262 WantAddPointers(2*numsub);
2263 lhs = AT.pWorkPointer;
2265 AT.pWorkPointer = rhs+numsub;
2266 f = t + FUNHEAD; l = left+1;
2267 for ( i = 0; i < numsub; i++ ) {
2268 AT.pWorkSpace[lhs+i] = l; l += l[1];
2270 AT.pWorkSpace[rhs+i] = f;
2279 t = term+1; newterm = AT.WorkPointer; out = newterm+1;
2280 while ( t < tstop ) {
2281 if ( *t == IDFUNCTION && first ) { first = 0; t += t[1];
continue; }
2282 if ( *t >= FUNCTION ) {
2283 for ( i = 0; i < numsub; i++ ) {
2284 m = AT.pWorkSpace[lhs+i];
2285 if ( *m != *t )
continue;
2286 for ( j = 1; j < t[1]; j++ ) {
2287 if ( m[j] != t[j] )
break;
2289 if ( j != t[1] )
continue;
2298 if ( i == numsub ) {
2299 j = t[1]; NCOPY(out,t,j)
2302 else if ( *t == SYMBOL ) {
2303 for ( i = 0; i < numsub; i++ ) {
2304 m = AT.pWorkSpace[lhs+i];
2305 if ( *m != SYMBOL )
continue;
2306 for ( ii = 2; ii < t[1]; ii += 2 ) {
2307 if ( m[2] != t[ii] )
continue;
2309 if ( pow <= 0 )
continue;
2310 t[ii+1] = t[ii+1]%m[3];
2322 m = out; *out++ = t[0]; *out++ = t[1];
2323 for ( ii = 2; ii < t[1]; ii += 2 ) {
2324 if ( t[ii+1] ) { *out++ = t[ii]; *out++ = t[ii+1]; }
2327 if ( m[1] == 2 ) out = m;
2330 else if ( *t == DOTPRODUCT ) {
2331 for ( i = 0; i < numsub; i++ ) {
2332 m = AT.pWorkSpace[lhs+i];
2333 if ( *m != DOTPRODUCT )
continue;
2334 for ( ii = 2; ii < t[1]; ii += 3 ) {
2335 if ( m[2] != t[ii] || m[3] != t[ii+1] )
continue;
2337 if ( pow <= 0 )
continue;
2338 t[ii+2] = t[ii+2]%m[4];
2350 m = out; *out++ = t[0]; *out++ = t[1];
2351 for ( ii = 2; ii < t[1]; ii += 3 ) {
2352 if ( t[ii+2] ) { *out++ = t[ii]; *out++ = t[ii+1]; *out++ = t[ii+2]; }
2355 if ( m[1] == 2 ) out = m;
2359 j = t[1]; NCOPY(out,t,j)
2365 t = tstop; r = term+*term;
while ( t < r ) *out++ = *t++;
2366 *newterm = out-newterm;
2371 t = term; r = newterm; NCOPY(t,r,i)
2376 AT.pWorkPointer = lhs;
LONG EndSort(PHEAD WORD *, int)
int Generator(PHEAD WORD *, WORD)
void LowerSortLevel(void)
int TestMatch(PHEAD WORD *term, WORD *level)