[BACK]Return to Z.c CVS log [TXT][DIR] Up to [local] / OpenXM_contrib2 / asir2000 / engine

Annotation of OpenXM_contrib2/asir2000/engine/Z.c, Revision 1.4

1.4     ! noro        1: #if 1
1.1       noro        2: #include "ca.h"
                      3: #include "inline.h"
1.2       noro        4: #endif
1.1       noro        5:
                      6: typedef struct oZ {
                      7:        int p;
                      8:        unsigned int b[1];
                      9: } *Z;
                     10:
1.3       noro       11: #define IMM_MAX 1073741823
                     12: #define IMM_MIN -1073741823
                     13:
                     14: /* immediate int -> Z */
1.4     ! noro       15: #define IMMTOZ(c,n) (n)=((c)>=IMM_MIN&&(c)<=IMM_MAX?((Z)(((c)<<1)|1)):immtoz(c))
1.3       noro       16: /* immediate Z ? */
                     17: #define IS_IMM(c) (((unsigned int)c)&1)
                     18: /* Z can be conver to immediate ? */
                     19: #define IS_IMMZ(n) (SL(n) == 1&&BD(n)[0]<=IMM_MAX)
                     20: /* Z -> immediate Z */
1.4     ! noro       21: #define IMMZTOZ(n,z) (z)=(Z)(SL(n)<0?(((-BD(n)[0])<<1)|1):(((BD(n)[0])<<1)|1))
1.3       noro       22: /* Z -> immediate int */
                     23: #define ZTOIMM(c) (((int)(c))>>1)
1.1       noro       24: #define ZALLOC(d) ((Z)MALLOC_ATOMIC(TRUESIZE(oZ,(d)-1,int)))
                     25: #define SL(n) ((n)->p)
                     26:
1.3       noro       27: Z immtoz(int c);
1.1       noro       28: Z qtoz(Q n);
                     29: Q ztoq(Z n);
                     30: Z chsgnz(Z n);
                     31: Z dupz(Z n);
                     32: Z addz(Z n1,Z n2);
                     33: Z subz(Z n1,Z n2);
                     34: Z mulz(Z n1,Z n2);
                     35: Z divsz(Z n1,Z n2);
                     36: Z divz(Z n1,Z n2,Z *rem);
                     37: Z gcdz(Z n1,Z n2);
                     38: Z gcdz_cofactor(Z n1,Z n2,Z *c1,Z *c2);
                     39: Z estimate_array_gcdz(Z *a,int n);
                     40: Z array_gcdz(Z *a,int n);
1.2       noro       41: void mkwcz(int k,int l,Z *t);
1.1       noro       42: int remzi(Z n,int m);
                     43: inline void _addz(Z n1,Z n2,Z nr);
                     44: inline void _subz(Z n1,Z n2,Z nr);
                     45: inline void _mulz(Z n1,Z n2,Z nr);
                     46: inline int _addz_main(unsigned int *m1,int d1,unsigned int *m2,int d2,unsigned int *mr);
                     47: inline int _subz_main(unsigned int *m1,int d1,unsigned int *m2,int d2,unsigned int *mr);
                     48:
1.3       noro       49: Z immtoz(int c)
                     50: {
                     51:        Z z;
                     52:
                     53:        z = ZALLOC(1);
                     54:        if ( c < 0 ) {
                     55:                SL(z) = -1; BD(z)[0] = -c;
                     56:        } else {
                     57:                SL(z) = 1; BD(z)[0] = c;
                     58:        }
                     59:        return z;
                     60: }
                     61:
                     62: int sgnz(Z n)
1.2       noro       63: {
                     64:        if ( !n ) return 0;
1.3       noro       65:        else if ( IS_IMM(n) ) return ZTOIMM(n)>0?1:1;
1.2       noro       66:        else if ( SL(n) < 0 ) return -1;
                     67:        else return 1;
                     68: }
                     69:
1.1       noro       70: z_mag(Z n)
                     71: {
1.4     ! noro       72:        int c,i;
1.3       noro       73:
                     74:        if ( !n ) return 0;
                     75:        else if ( IS_IMM(n) ) {
                     76:                c = ZTOIMM(n);
                     77:                if ( c < 0 ) c = -c;
                     78:                for ( i = 0; c; c >>= 1, i++ );
                     79:                return i;
                     80:        }
                     81:        else return n_bits((N)n);
1.1       noro       82: }
                     83:
                     84: Z qtoz(Q n)
                     85: {
1.3       noro       86:        Z r,t;
1.4     ! noro       87:        int c;
1.1       noro       88:
                     89:        if ( !n ) return 0;
                     90:        else if ( !INT(n) )
                     91:                error("qtoz : invalid input");
                     92:        else {
1.3       noro       93:                t = (Z)NM(n);
                     94:                if ( IS_IMMZ(t) ) {
1.4     ! noro       95:                        c = SGN(n) < 0 ? -BD(t)[0] : BD(t)[0];
        !            96:                        IMMTOZ(c,r);
1.3       noro       97:                } else {
                     98:                        r = dupz((Z)t);
1.4     ! noro       99:                        if ( SGN(n) < 0 ) SL(r) = -SL(r);
1.3       noro      100:                }
1.1       noro      101:                return r;
                    102:        }
                    103: }
                    104:
                    105: Q ztoq(Z n)
                    106: {
                    107:        Q r;
                    108:        Z nm;
1.3       noro      109:        int sgn,c;
1.1       noro      110:
                    111:        if ( !n ) return 0;
1.3       noro      112:        else if ( IS_IMM(n) ) {
                    113:                c = ZTOIMM(n);
                    114:                STOQ(c,r);
                    115:                return r;
                    116:        } else {
1.1       noro      117:                nm = dupz(n);
                    118:                if ( SL(nm) < 0 ) {
                    119:                        sgn = -1;
                    120:                        SL(nm) = -SL(nm);
                    121:                } else
                    122:                        sgn = 1;
                    123:                NTOQ((N)nm,sgn,r);
                    124:                return r;
                    125:        }
                    126: }
                    127:
                    128: Z dupz(Z n)
                    129: {
                    130:        Z nr;
                    131:        int sd,i;
                    132:
                    133:        if ( !n ) return 0;
1.3       noro      134:        else if ( IS_IMM(n) ) return n;
                    135:        else {
                    136:                if ( (sd = SL(n)) < 0 ) sd = -sd;
                    137:                nr = ZALLOC(sd);
                    138:                SL(nr) = SL(n);
                    139:                for ( i = 0; i < sd; i++ ) BD(nr)[i] = BD(n)[i];
                    140:                return nr;
                    141:        }
1.1       noro      142: }
                    143:
                    144: Z chsgnz(Z n)
                    145: {
                    146:        Z r;
1.3       noro      147:        int c;
1.1       noro      148:
                    149:        if ( !n ) return 0;
1.3       noro      150:        else if ( IS_IMM(n) ) {
                    151:                c = -ZTOIMM(n);
                    152:                IMMTOZ(c,r);
                    153:                return r;
                    154:        } else {
1.1       noro      155:                r = dupz(n);
                    156:                SL(r) = -SL(r);
                    157:                return r;
                    158:        }
                    159: }
                    160:
1.3       noro      161:
1.1       noro      162: Z addz(Z n1,Z n2)
                    163: {
1.3       noro      164:        int d1,d2,d,c;
                    165:        Z r,r1;
                    166:        struct oZ t;
1.1       noro      167:
                    168:        if ( !n1 ) return dupz(n2);
                    169:        else if ( !n2 ) return dupz(n1);
1.3       noro      170:        else if ( IS_IMM(n1) ) {
                    171:                if ( IS_IMM(n2) ) {
                    172:                        c = ZTOIMM(n1)+ZTOIMM(n2);
                    173:                        IMMTOZ(c,r);
                    174:                        return r;
                    175:                } else {
                    176:                        c = ZTOIMM(n1);
                    177:                        if ( c < 0 ) {
                    178:                                t.p = -1; t.b[0] = -c;
1.1       noro      179:                        } else {
1.3       noro      180:                                t.p = 1; t.b[0] = c;
1.1       noro      181:                        }
1.3       noro      182:                        if ( (d2 = SL(n2)) < 0 ) d2 = -d2;
                    183:                        r = ZALLOC(d2+1);
                    184:                        _addz(&t,n2,r);
                    185:                        return r;
                    186:                }
                    187:        } else if ( IS_IMM(n2) ) {
                    188:                c = ZTOIMM(n2);
                    189:                if ( c < 0 ) {
                    190:                        t.p = -1; t.b[0] = -c;
1.1       noro      191:                } else {
1.3       noro      192:                        t.p = 1; t.b[0] = c;
                    193:                }
                    194:                if ( (d1 = SL(n1)) < 0 ) d1 = -d1;
                    195:                r = ZALLOC(d1+1);
                    196:                _addz(n1,&t,r);
                    197:                return r;
                    198:        } else {
                    199:                if ( (d1 = SL(n1)) < 0 ) d1 = -d1;
                    200:                if ( (d2 = SL(n2)) < 0 ) d2 = -d2;
                    201:                d = MAX(d1,d2)+1;
                    202:                r = ZALLOC(d);
                    203:                _addz(n1,n2,r);
                    204:                if ( !SL(r) ) r = 0;
                    205:                else if ( IS_IMMZ(r) ) {
                    206:                        IMMZTOZ(r,r1); r = r1;
1.1       noro      207:                }
1.3       noro      208:                return r;
1.1       noro      209:        }
                    210: }
                    211:
                    212: Z subz(Z n1,Z n2)
                    213: {
1.3       noro      214:        int d1,d2,d,c;
                    215:        Z r,r1;
                    216:        struct oZ t;
1.1       noro      217:
1.3       noro      218:        if ( !n1 ) {
                    219:                r = dupz(n2);
                    220:                SL(r) = -SL(r);
                    221:                return r;
                    222:        } else if ( !n2 ) return dupz(n1);
                    223:        else if ( IS_IMM(n1) ) {
                    224:                if ( IS_IMM(n2) ) {
                    225:                        c = ZTOIMM(n1)-ZTOIMM(n2);
                    226:                        IMMTOZ(c,r);
                    227:                        return r;
                    228:                } else {
                    229:                        c = ZTOIMM(n1);
                    230:                        if ( c < 0 ) {
                    231:                                t.p = -1; t.b[0] = -c;
                    232:                        } else {
                    233:                                t.p = 1; t.b[0] = c;
                    234:                        }
                    235:                        if ( (d2 = SL(n2)) < 0 ) d2 = -d2;
                    236:                        r = ZALLOC(d2+1);
                    237:                        _subz(&t,n2,r);
                    238:                        return r;
                    239:                }
                    240:        } else if ( IS_IMM(n2) ) {
                    241:                c = ZTOIMM(n2);
                    242:                if ( c < 0 ) {
                    243:                        t.p = -1; t.b[0] = -c;
                    244:                } else {
                    245:                        t.p = 1; t.b[0] = c;
                    246:                }
                    247:                if ( (d1 = SL(n1)) < 0 ) d1 = -d1;
                    248:                r = ZALLOC(d1+1);
                    249:                _subz(n1,&t,r);
                    250:                return r;
                    251:        } else {
                    252:                if ( (d1 = SL(n1)) < 0 ) d1 = -d1;
                    253:                if ( (d2 = SL(n2)) < 0 ) d2 = -d2;
                    254:                d = MAX(d1,d2)+1;
                    255:                r = ZALLOC(d);
                    256:                _subz(n1,n2,r);
                    257:                if ( !SL(r) ) r = 0;
                    258:                else if ( IS_IMMZ(r) ) {
                    259:                        IMMZTOZ(r,r1); r = r1;
1.1       noro      260:                }
1.3       noro      261:                return r;
1.1       noro      262:        }
                    263: }
                    264:
                    265: Z mulz(Z n1,Z n2)
                    266: {
1.3       noro      267:        int d1,d2,sgn,i;
1.1       noro      268:        unsigned int u1,u2,u,l;
1.3       noro      269:        Z r;
1.1       noro      270:
                    271:        if ( !n1 || !n2 ) return 0;
1.3       noro      272:
                    273:        if ( IS_IMM(n1) ) {
                    274:                sgn = 1;
                    275:                u1 = ZTOIMM(n1); if ( u1 < 0 ) { sgn = -sgn; u1 = -u1; }
                    276:                if ( IS_IMM(n2) ) {
                    277:                        u2 = ZTOIMM(n2); if ( u2 < 0 ) { sgn = -sgn; u2 = -u2; }
1.1       noro      278:                        DM(u1,u2,u,l);
1.3       noro      279:                        if ( !u ) {
                    280:                                IMMTOZ(l,r);
1.1       noro      281:                        } else {
1.3       noro      282:                                r = ZALLOC(2); SL(r) = 2; BD(r)[1] = u; BD(r)[0] = l;
1.1       noro      283:                        }
                    284:                } else {
1.3       noro      285:                        if ( (d2 = SL(n2)) < 0 ) { sgn = -sgn; d2 = -d2; }
                    286:                        r = ZALLOC(d2+1);
                    287:                        for ( i = d2; i >= 0; i-- ) BD(r)[i] = 0;
                    288:                        muln_1(BD(n2),d2,u1,BD(r));
                    289:                        SL(r) = BD(r)[d2]?d2+1:d2;
1.1       noro      290:                }
1.3       noro      291:        } else if ( IS_IMM(n2) ) {
                    292:                sgn = 1;
                    293:                u2 = ZTOIMM(n2); if ( u2 < 0 ) { sgn = -sgn; u2 = -u2; }
                    294:                if ( (d1 = SL(n1)) < 0 ) { sgn = -sgn; d1 = -d1; }
                    295:                r = ZALLOC(d1+1);
                    296:                for ( i = d1; i >= 0; i-- ) BD(r)[i] = 0;
                    297:                muln_1(BD(n1),d1,u2,BD(r));
                    298:                SL(r) = BD(r)[d1]?d1+1:d1;
                    299:        } else {
                    300:                sgn = 1;
                    301:                if ( (d1 = SL(n1)) < 0 ) { sgn = -sgn; d1 = -d1; }
                    302:                if ( (d2 = SL(n2)) < 0 ) { sgn = -sgn; d2 = -d2; }
                    303:                r = ZALLOC(d1+d2);
                    304:                _mulz(n1,n2,r);
1.1       noro      305:        }
1.3       noro      306:        if ( sgn < 0 ) SL(r) = -SL(r);
                    307:        return r;
1.1       noro      308: }
                    309:
1.3       noro      310: /* kokokara */
1.4     ! noro      311: #if 0
1.1       noro      312: Z divsz(Z n1,Z n2)
                    313: {
1.3       noro      314:        int sgn,d1,d2;
                    315:        Z q;
1.1       noro      316:
                    317:        if ( !n2 ) error("divsz : division by 0");
1.3       noro      318:        if ( !n1 ) return 0;
                    319:
                    320:        if ( IS_IMM(n1) ) {
                    321:                if ( !IS_IMM(n2) )
                    322:                        error("divsz : cannot happen");
                    323:                c = ZTOIMM(n1)/ZTOIMM(n2);
                    324:                IMMTOZ(c,q);
                    325:                return q;
1.1       noro      326:        }
1.3       noro      327:        if ( IS_IMM(n2) ) {
                    328:                sgn = 1;
                    329:                u2 = ZTOIMM(n2); if ( u2 < 0 ) { sgn = -sgn; u2 = -u2; }
                    330:                diviz(n1,u2,&q);
                    331:                if ( sgn < 0 ) SL(q) = -SL(q);
                    332:                return q;
                    333:        }
                    334:
                    335:        sgn = 1;
                    336:        if ( (d2 = SL(n2)) < 0 ) { sgn = -sgn; d2 = -d2; }
                    337:        if ( d2 == 1 ) {
                    338:                diviz(n1,BD(u2)[0],&q);
                    339:                if ( sgn < 0 ) SL(q) = -SL(q);
                    340:                return q;
                    341:        }
                    342:        if ( (d1 = SL(n1)) < 0 ) { sgn = -sgn; d1 = -d1; }
                    343:        if ( d1 < d2 ) error("divsz : cannot happen");
                    344:        return q;
1.1       noro      345: }
                    346:
                    347: Z gcdz(Z n1,Z n2)
                    348: {
1.3       noro      349:        int d1,d2;
1.1       noro      350:        N gcd;
                    351:
                    352:        if ( !n1 ) return n2;
                    353:        else if ( !n2 ) return n1;
                    354:
                    355:        n1 = dupz(n1);
                    356:        if ( SL(n1) < 0 ) SL(n1) = -SL(n1);
                    357:        n2 = dupz(n2);
                    358:        if ( SL(n2) < 0 ) SL(n2) = -SL(n2);
                    359:        gcdn((N)n1,(N)n2,&gcd);
                    360:        return (Z)gcd;
                    361: }
                    362:
                    363: int remzi(Z n,int m)
                    364: {
                    365:        unsigned int *x;
                    366:        unsigned int t,r;
                    367:        int i;
                    368:
                    369:        if ( !n ) return 0;
                    370:        i = SL(n);
                    371:        if ( i < 0 ) i = -i;
                    372:        for ( i--, x = BD(n)+i, r = 0; i >= 0; i--, x-- ) {
                    373: #if defined(sparc)
                    374:                r = dsa(m,r,*x);
                    375: #else
                    376:                DSAB(m,r,*x,t,r);
                    377: #endif
                    378:        }
                    379:        return r;
                    380: }
                    381:
                    382: Z gcdz_cofactor(Z n1,Z n2,Z *c1,Z *c2)
                    383: {
                    384:        Z gcd;
                    385:
                    386:        gcd = gcdz(n1,n2);
                    387:        *c1 = divsz(n1,gcd);
                    388:        *c2 = divsz(n2,gcd);
                    389:        return gcd;
                    390: }
                    391:
                    392: Z estimate_array_gcdz(Z *b,int n)
                    393: {
                    394:        int m,i,j,sd;
                    395:        Z *a;
                    396:        Z s,t;
                    397:
                    398:        a = (Z *)ALLOCA(n*sizeof(Z));
                    399:        for ( i = j = 0; i < n; i++ ) if ( b[i] ) a[j++] = b[i];
                    400:        n = j;
                    401:        if ( !n ) return 0;
                    402:        if ( n == 1 ) return a[0];
                    403:
                    404:        m = n/2;
                    405:        for ( i = 0, s = 0; i < m; i++ ) {
                    406:                if ( !a[i] ) continue;
                    407:                else s = (SL(a[i])<0)?subz(s,a[i]):addz(s,a[i]);
                    408:        }
                    409:        for ( t = 0; i < n; i++ ) {
                    410:                if ( !a[i] ) continue;
                    411:                else t = (SL(a[i])<0)?subz(t,a[i]):addz(t,a[i]);
                    412:        }
                    413:        return gcdz(s,t);
                    414: }
                    415:
                    416: Z array_gcdz(Z *b,int n)
                    417: {
                    418:        int m,i,j,sd;
                    419:        Z *a;
                    420:        Z gcd;
                    421:
                    422:        a = (Z *)ALLOCA(n*sizeof(Z));
                    423:        for ( i = j = 0; i < n; i++ ) if ( b[i] ) a[j++] = b[i];
                    424:        n = j;
                    425:        if ( !n ) return 0;
                    426:        if ( n == 1 ) return a[0];
                    427:        gcd = a[0];
                    428:        for ( i = 1; i < n; i++ )
                    429:                gcd = gcdz(gcd,a[i]);
                    430:        return gcd;
                    431: }
1.4     ! noro      432: #endif
1.1       noro      433:
                    434: void _copyz(Z n1,Z n2)
                    435: {
                    436:        int n,i;
                    437:
                    438:        if ( !n1 || !SL(n1) ) SL(n2) = 0;
                    439:        else {
                    440:                n = SL(n2) = SL(n1);
                    441:                if ( n < 0 ) n = -n;
                    442:                for ( i = 0; i < n; i++ ) BD(n2)[i] = BD(n1)[i];
                    443:        }
                    444: }
                    445:
                    446: void _addz(Z n1,Z n2,Z nr)
                    447: {
1.3       noro      448:        int d1,d2;
1.1       noro      449:
                    450:        if ( !n1 || !SL(n1) ) _copyz(n2,nr);
                    451:        else if ( !n2 || !SL(n2) ) _copyz(n1,nr);
1.3       noro      452:        else if ( (d1=SL(n1)) > 0 )
                    453:                if ( (d2=SL(n2)) > 0 )
                    454:                        SL(nr) = _addz_main(BD(n1),d1,BD(n2),d2,BD(nr));
1.1       noro      455:                else
1.3       noro      456:                        SL(nr) = _subz_main(BD(n1),d1,BD(n2),-d2,BD(nr));
                    457:        else if ( (d2=SL(n2)) > 0 )
                    458:                SL(nr) = _subz_main(BD(n2),d2,BD(n1),-d1,BD(nr));
1.1       noro      459:        else
1.3       noro      460:                SL(nr) = -_addz_main(BD(n1),-d1,BD(n2),-d2,BD(nr));
1.1       noro      461: }
                    462:
                    463: void _subz(Z n1,Z n2,Z nr)
                    464: {
1.3       noro      465:        int d1,d2;
1.1       noro      466:
                    467:        if ( !n1 || !SL(n1) ) _copyz(n2,nr);
                    468:        else if ( !n2 || !SL(n2) ) {
                    469:                _copyz(n1,nr);
                    470:                SL(nr) = -SL(nr);
1.3       noro      471:        } else if ( (d1=SL(n1)) > 0 )
                    472:                if ( (d2=SL(n2)) > 0 )
                    473:                        SL(nr) = _subz_main(BD(n1),d1,BD(n2),d2,BD(nr));
1.1       noro      474:                else
1.3       noro      475:                        SL(nr) = _addz_main(BD(n1),d1,BD(n2),-d2,BD(nr));
                    476:        else if ( (d2=SL(n2)) > 0 )
                    477:                SL(nr) = -_addz_main(BD(n1),-d1,BD(n2),d2,BD(nr));
1.1       noro      478:        else
1.3       noro      479:                SL(nr) = -_subz_main(BD(n1),-d1,BD(n2),-d2,BD(nr));
1.1       noro      480: }
                    481:
                    482: void _mulz(Z n1,Z n2,Z nr)
                    483: {
1.3       noro      484:        int d1,d2;
1.1       noro      485:        int i,d,sgn;
                    486:        unsigned int mul;
                    487:        unsigned int *m1,*m2;
                    488:
                    489:        if ( !n1 || !SL(n1) || !n2 || !SL(n2) )
                    490:                SL(nr) = 0;
                    491:        else {
1.3       noro      492:                d1 = SL(n1); d2 = SL(n2);
1.1       noro      493:                sgn = 1;
1.3       noro      494:                if ( d1 < 0 ) { sgn = -sgn; d1 = -d1; }
                    495:                if ( d2 < 0 ) { sgn = -sgn; d2 = -d2; }
                    496:                d = d1+d2;
1.1       noro      497:                for ( i = d-1, m1 = BD(nr); i >= 0; i-- ) *m1++ = 0;
1.3       noro      498:                for ( i = 0, m1 = BD(n1), m2 = BD(n2); i < d2; i++, m2++ )
                    499:                        if ( mul = *m2 ) muln_1(m1,d1,mul,BD(nr)+i);
1.1       noro      500:                SL(nr) = sgn*(BD(nr)[d-1]?d:d-1);
                    501:        }
                    502: }
                    503:
                    504: int _addz_main(unsigned int *m1,int d1,unsigned int *m2,int d2,unsigned int *mr)
                    505: {
                    506:        int d,i;
                    507:        unsigned int tmp,c;
                    508:        unsigned int *t;
                    509:
                    510:        if ( d2 > d1 ) {
                    511:                t = m1; m1 = m2; m2 = t;
                    512:                d = d1; d1 = d2; d2 = d;
                    513:        }
                    514: #if defined(VISUAL)
                    515:        __asm {
                    516:        push    esi
                    517:        push    edi
                    518:        mov esi,m1
                    519:        mov edi,m2
                    520:        mov ebx,mr
                    521:        mov ecx,d2
                    522:        xor     eax,eax
                    523:        Lstart__addz:
                    524:        mov eax,DWORD PTR [esi]
                    525:        mov edx,DWORD PTR [edi]
                    526:        adc eax,edx
                    527:        mov DWORD PTR [ebx],eax
                    528:        lea esi,DWORD PTR [esi+4]
                    529:        lea edi,DWORD PTR [edi+4]
                    530:        lea ebx,DWORD PTR [ebx+4]
                    531:        dec ecx
                    532:        jnz Lstart__addz
                    533:        pop     edi
                    534:        pop     esi
                    535:        mov eax,0
                    536:        adc eax,eax
                    537:        mov c,eax
                    538:        }
                    539: #elif defined(i386)
                    540:        asm volatile("\
                    541:        movl    %1,%%esi;\
                    542:        movl    %2,%%edi;\
                    543:        movl    %3,%%ebx;\
                    544:        movl    %4,%%ecx;\
                    545:        testl   %%eax,%%eax;\
                    546:        Lstart__addz:;\
                    547:        movl    (%%esi),%%eax;\
                    548:        movl    (%%edi),%%edx;\
                    549:        adcl    %%edx,%%eax;\
                    550:        movl    %%eax,(%%ebx);\
                    551:        leal    4(%%esi),%%esi;\
                    552:        leal    4(%%edi),%%edi;\
                    553:        leal    4(%%ebx),%%ebx;\
                    554:        decl    %%ecx;\
                    555:        jnz Lstart__addz;\
                    556:        movl    $0,%%eax;\
                    557:        adcl    %%eax,%%eax;\
                    558:        movl    %%eax,%0"\
                    559:        :"=m"(c)\
                    560:        :"m"(m1),"m"(m2),"m"(mr),"m"(d2)\
                    561:        :"eax","ebx","ecx","edx","esi","edi");
                    562: #else
                    563:        for ( i = 0, c = 0, mr = BD(nr); i < d2; i++, m1++, m2++, mr++ ) {
                    564:                tmp = *m1 + *m2;
                    565:                if ( tmp < *m1 ) {
                    566:                        tmp += c;
                    567:                        c = 1;
                    568:                } else {
                    569:                        tmp += c;
                    570:                        c = tmp < c ? 1 : 0;
                    571:                }
                    572:                *mr = tmp;
                    573:        }
                    574: #endif
                    575:        for ( i = d2, m1 += d2, mr += d2; (i < d1) && c ; i++ ) {
                    576:                tmp = *m1++ + c;
                    577:                c = tmp < c ? 1 : 0;
                    578:                *mr++ = tmp;
                    579:        }
                    580:        for ( ; i < d1; i++ )
                    581:                        *mr++ = *m1++;
                    582:        *mr = c;
                    583:        return (c?d1+1:d1);
                    584: }
                    585:
                    586: int _subz_main(unsigned int *m1,int d1,unsigned int *m2,int d2,unsigned int *mr)
                    587: {
                    588:        int d,i,sgn;
                    589:        unsigned int t,tmp,br;
                    590:        unsigned int *m;
                    591:
                    592:        if ( d1 > d2 ) sgn = 1;
                    593:        else if ( d1 < d2 ) sgn = -1;
                    594:        else {
                    595:                for ( i = d1-1; i >= 0 && m1[i] == m2[i]; i-- );
                    596:                if ( i < 0 ) return 0;
                    597:                if ( m1[i] > m2[i] ) sgn = 1;
                    598:                else if ( m1[i] < m2[i] ) sgn = -1;
                    599:        }
                    600:        if ( sgn < 0 ) {
                    601:                m = m1; m1 = m2; m2 = m;
                    602:                d = d1; d1 = d2; d2 = d;
                    603:        }
                    604: #if defined(VISUAL)
                    605:        __asm {
                    606:        push    esi
                    607:        push    edi
                    608:        mov esi,m1
                    609:        mov edi,m2
                    610:        mov ebx,mr
                    611:        mov ecx,d2
                    612:        xor     eax,eax
                    613:        Lstart__subz:
                    614:        mov eax,DWORD PTR [esi]
                    615:        mov edx,DWORD PTR [edi]
                    616:        sbb eax,edx
                    617:        mov DWORD PTR [ebx],eax
                    618:        lea esi,DWORD PTR [esi+4]
                    619:        lea edi,DWORD PTR [edi+4]
                    620:        lea ebx,DWORD PTR [ebx+4]
                    621:        dec ecx
                    622:        jnz Lstart__subz
                    623:        pop     edi
                    624:        pop     esi
                    625:        mov eax,0
                    626:        adc eax,eax
                    627:        mov br,eax
                    628:        }
                    629: #elif defined(i386)
                    630:        asm volatile("\
                    631:        movl    %1,%%esi;\
                    632:        movl    %2,%%edi;\
                    633:        movl    %3,%%ebx;\
                    634:        movl    %4,%%ecx;\
                    635:        testl   %%eax,%%eax;\
                    636:        Lstart__subz:;\
                    637:        movl    (%%esi),%%eax;\
                    638:        movl    (%%edi),%%edx;\
                    639:        sbbl    %%edx,%%eax;\
                    640:        movl    %%eax,(%%ebx);\
                    641:        leal    4(%%esi),%%esi;\
                    642:        leal    4(%%edi),%%edi;\
                    643:        leal    4(%%ebx),%%ebx;\
                    644:        decl    %%ecx;\
                    645:        jnz Lstart__subz;\
                    646:        movl    $0,%%eax;\
                    647:        adcl    %%eax,%%eax;\
                    648:        movl    %%eax,%0"\
                    649:        :"=m"(br)\
                    650:        :"m"(m1),"m"(m2),"m"(mr),"m"(d2)\
                    651:        :"eax","ebx","ecx","edx","esi","edi");
                    652: #else
                    653:        for ( i = 0, br = 0, mr = BD(nr); i < d2; i++, mr++ ) {
                    654:                t = *m1++;
                    655:                tmp = *m2++ + br;
                    656:                if ( br > 0 && !tmp ) {
                    657:                        /* tmp = 2^32 => br = 1 */
                    658:                }else {
                    659:                        tmp = t-tmp;
                    660:                        br = tmp > t ? 1 : 0;
                    661:                        *mr = tmp;
                    662:                }
                    663:        }
                    664: #endif
                    665:        for ( i = d2, m1 += d2, mr += d2; (i < d1) && br; i++ ) {
                    666:                t = *m1++;
                    667:                tmp = t - br;
                    668:                br = tmp > t ? 1 : 0;
                    669:                *mr++ = tmp;
                    670:        }
                    671:        for ( ; i < d1; i++ )
                    672:                *mr++ = *m1++;
                    673:        for ( i = d1-1, mr--; i >= 0 && !*mr--; i-- );
                    674:        return sgn*(i+1);
                    675: }
                    676:
                    677: /* XXX */
                    678:
                    679: void printz(Z n)
                    680: {
1.4     ! noro      681:        int sd,u;
1.1       noro      682:
                    683:        if ( !n )
                    684:                fprintf(asir_out,"0");
1.4     ! noro      685:        else if ( IS_IMM(n) ) {
        !           686:                u = ZTOIMM(n);
        !           687:                fprintf(asir_out,"%d",u);
        !           688:        } else {
1.1       noro      689:                if ( (sd = SL(n)) < 0 ) { SL(n) = -SL(n); fprintf(asir_out,"-"); }
                    690:                printn((N)n);
                    691:                if ( sd < 0 ) SL(n) = -SL(n);
1.2       noro      692:        }
                    693: }
                    694:
                    695: /*
                    696:  *  Dx^k*x^l = W(k,l,0)*x^l*Dx^k+W(k,l,1)*x^(l-1)*x^(k-1)*+...
                    697:  *
                    698:  *  t = [W(k,l,0) W(k,l,1) ... W(k,l,min(k,l)]
                    699:  *  where W(k,l,i) = i! * kCi * lCi
                    700:  */
                    701:
                    702: void mkwcz(int k,int l,Z *t)
                    703: {
                    704:        int i,n,up,low;
                    705:        N nm,d,c;
                    706:
                    707:        n = MIN(k,l);
                    708:        for ( t[0] = (Z)ONEN, i = 1; i <= n; i++ ) {
                    709:                DM(k-i+1,l-i+1,up,low);
                    710:                if ( up ) {
                    711:                        nm = NALLOC(2); PL(nm) = 2; BD(nm)[0] = low; BD(nm)[1] = up;
                    712:                } else {
                    713:                        nm = NALLOC(1); PL(nm) = 1; BD(nm)[0] = low;
                    714:                }
                    715:                kmuln((N)t[i-1],nm,&d); divin(d,i,&c); t[i] = (Z)c;
1.1       noro      716:        }
                    717: }

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>