[BACK]Return to ox.c CVS log [TXT][DIR] Up to [local] / OpenXM / src / ox_toolkit

Annotation of OpenXM/src/ox_toolkit/ox.c, Revision 1.44

1.1       ohara       1: /* -*- mode: C; coding: euc-japan -*- */
1.44    ! noro        2: /* $OpenXM: OpenXM/src/ox_toolkit/ox.c,v 1.43 2015/08/17 05:18:35 noro Exp $ */
1.1       ohara       3:
1.8       ohara       4: /*
                      5:    This module includes functions for sending/receiveng CMO's.
                      6:    Some commnets is written in Japanese by the EUC-JP coded
                      7:    character set.
1.1       ohara       8: */
                      9:
                     10: #include <stdio.h>
                     11: #include <stdlib.h>
1.20      ohara      12: #include <stdarg.h>
1.1       ohara      13: #include <string.h>
                     14: #include <unistd.h>
                     15: #include <fcntl.h>
1.5       ohara      16: #include <sys/file.h>
1.13      ohara      17: #include <time.h>
1.1       ohara      18:
1.38      noro       19: #include <mpfr.h>
                     20: /* XXX : defined in mpfr-impl.h */
                     21: #define MPFR_PREC(x)      ((x)->_mpfr_prec)
                     22: #define MPFR_EXP(x)       ((x)->_mpfr_exp)
                     23: #define MPFR_MANT(x)      ((x)->_mpfr_d)
                     24: #define MPFR_LAST_LIMB(x) ((MPFR_PREC (x) - 1) / GMP_NUMB_BITS)
                     25: #define MPFR_LIMB_SIZE(x) (MPFR_LAST_LIMB (x) + 1)
                     26:
                     27: #if SIZEOF_LONG==4
                     28: typedef long long L64;
                     29: typedef unsigned long long UL64;
                     30: #else
                     31: typedef long L64;
                     32: typedef unsigned long UL64;
                     33: #endif
                     34:
1.1       ohara      35: #include "mysocket.h"
1.12      ohara      36: #include "ox_toolkit.h"
1.1       ohara      37: #include "parse.h"
                     38:
1.20      ohara      39: static FILE *ox_stderr = NULL;
                     40:
1.17      ohara      41: /* sorting by the value of CMO_xxx.  (for debugging) */
1.13      ohara      42: static cmo_null*         receive_cmo_null(OXFILE *oxfp);
                     43: static cmo_int32*        receive_cmo_int32(OXFILE *oxfp);
                     44: static cmo_string*       receive_cmo_string(OXFILE *oxfp);
                     45: static cmo_mathcap*      receive_cmo_mathcap(OXFILE *oxfp);
                     46: static cmo_list*         receive_cmo_list(OXFILE *oxfp);
                     47: static cmo_monomial32*   receive_cmo_monomial32(OXFILE *oxfp);
                     48: static cmo_zero*         receive_cmo_zero(OXFILE *oxfp);
                     49: static cmo_dms_generic*  receive_cmo_dms_generic(OXFILE *oxfp);
                     50: static cmo_ring_by_name* receive_cmo_ring_by_name(OXFILE *oxfp);
                     51: static cmo_distributed_polynomial* receive_cmo_distributed_polynomial(OXFILE *oxfp);
1.26      ohara      52: static cmo_recursive_polynomial* receive_cmo_recursive_polynomial(OXFILE *oxfp);
                     53: static cmo_polynomial_in_one_variable* receive_cmo_polynomial_in_one_variable(OXFILE *oxfp);
1.32      ohara      54: static cmo_double*       receive_cmo_double(OXFILE *oxfp);
1.13      ohara      55: static cmo_error2*       receive_cmo_error2(OXFILE *oxfp);
                     56:
                     57: static int          send_cmo_null(OXFILE *oxfp, cmo_null* c);
                     58: static int          send_cmo_int32(OXFILE *oxfp, cmo_int32* m);
                     59: static int          send_cmo_string(OXFILE *oxfp, cmo_string* m);
                     60: static int          send_cmo_mathcap(OXFILE *oxfp, cmo_mathcap* c);
                     61: static int          send_cmo_list(OXFILE *oxfp, cmo_list* c);
                     62: static int          send_cmo_monomial32(OXFILE *oxfp, cmo_monomial32* c);
1.32      ohara      63: static int          send_cmo_double(OXFILE *oxfp, cmo_double* c);
1.22      ohara      64: static int          send_cmo_error2(OXFILE *oxfp, cmo_error2* c);
                     65: static int          send_cmo_distributed_polynomial(OXFILE *oxfp, cmo_distributed_polynomial* c);
1.26      ohara      66: static int send_cmo_polynomial_in_one_variable(OXFILE *oxfp, cmo_polynomial_in_one_variable* c);
                     67: static int send_cmo_recursive_polynomial(OXFILE *oxfp, cmo_recursive_polynomial* c);
1.22      ohara      68:
                     69: static cmo_zz*      receive_cmo_zz(OXFILE *oxfp);
                     70: static void         receive_mpz(OXFILE *oxfp, mpz_ptr mpz);
1.13      ohara      71: static int          send_cmo_zz(OXFILE *oxfp, cmo_zz* c);
                     72: static int          send_mpz(OXFILE *oxfp, mpz_ptr mpz);
1.38      noro       73: static void         receive_mpfr(OXFILE *oxfp, mpfr_ptr mpfr);
                     74: static int          send_mpfr(OXFILE *oxfp, mpfr_ptr mpfr);
1.3       ohara      75:
1.8       ohara      76: /* hook functions. (yet not implemented) */
1.2       ohara      77: static hook_t hook_before_send_cmo = NULL;
                     78: static hook_t hook_after_send_cmo  = NULL;
                     79:
                     80: int add_hook_before_send_cmo(hook_t func)
                     81: {
1.13      ohara      82:     hook_before_send_cmo = func;
                     83:     return 0;
1.2       ohara      84: }
                     85:
                     86: int add_hook_after_send_cmo(hook_t func)
                     87: {
1.13      ohara      88:     hook_after_send_cmo = func;
                     89:     return 0;
1.2       ohara      90: }
                     91:
1.13      ohara      92: static cmo *call_hook_before_send_cmo(OXFILE *oxfp, cmo *c)
1.2       ohara      93: {
1.13      ohara      94:     if (hook_before_send_cmo != NULL) {
                     95:         return hook_before_send_cmo(oxfp, c);
                     96:     }
                     97:     return c;
1.2       ohara      98: }
                     99:
1.13      ohara     100: static cmo *call_hook_after_send_cmo(OXFILE *oxfp, cmo *c)
1.2       ohara     101: {
1.13      ohara     102:     if (hook_after_send_cmo != NULL) {
                    103:         return hook_after_send_cmo(oxfp, c);
                    104:     }
                    105:     return c;
1.2       ohara     106: }
1.1       ohara     107:
1.7       ohara     108: /* Handling an error. */
1.1       ohara     109: static int current_received_serial = 0;
                    110:
1.7       ohara     111: /* If an error object be needed, then a server call the following function. */
1.1       ohara     112: cmo_error2* make_error_object(int err_code, cmo *ob)
                    113: {
                    114:     cmo_list* li = new_cmo_list();
1.13      ohara     115:     list_append(li, (cmo *)new_cmo_int32(current_received_serial));
                    116:     list_append(li, (cmo *)new_cmo_int32(err_code));
                    117:     list_append(li, ob);
1.1       ohara     118:     return new_cmo_error2((cmo *)li);
                    119: }
                    120:
1.7       ohara     121: /* getting a next serial number. */
1.13      ohara     122: int next_serial(OXFILE *oxfp)
1.1       ohara     123: {
1.13      ohara     124:     return oxfp->serial_number++;
1.1       ohara     125: }
                    126:
1.7       ohara     127: /* sending an object of int32 type. (not equal to cmo_int32 type)  */
1.13      ohara     128: int send_int32(OXFILE *oxfp, int int32)
1.1       ohara     129: {
1.13      ohara     130:     return oxfp->send_int32(oxfp, int32);
1.1       ohara     131: }
                    132:
1.13      ohara     133: /* receiving an object of int32 type. (not equal to cmo_int32 type)  */
                    134: int receive_int32(OXFILE *oxfp)
1.1       ohara     135: {
1.13      ohara     136:     return oxfp->receive_int32(oxfp);
1.1       ohara     137: }
                    138:
1.32      ohara     139: /* sending an object of int32 type. (not equal to cmo_int32 type)  */
                    140: int send_double(OXFILE *oxfp, double d)
                    141: {
                    142:     return oxfp->send_double(oxfp, d);
                    143: }
                    144:
                    145: /* receiving an object of int32 type. (not equal to cmo_int32 type)  */
                    146: double receive_double(OXFILE *oxfp)
                    147: {
                    148:     return oxfp->receive_double(oxfp);
                    149: }
                    150:
1.13      ohara     151: /* receiving an (OX_tag, serial number)  */
                    152: int receive_ox_tag(OXFILE *oxfp)
1.1       ohara     153: {
1.13      ohara     154:     int tag = receive_int32(oxfp);
1.16      ohara     155:     oxfp->received_serial_number = receive_int32(oxfp);
1.13      ohara     156:     return tag;
1.1       ohara     157: }
                    158:
1.13      ohara     159: /* sending an (OX_tag, serial number)  */
                    160: int send_ox_tag(OXFILE *oxfp, int tag)
1.3       ohara     161: {
1.13      ohara     162:     send_int32(oxfp, tag);
                    163:     return send_int32(oxfp, next_serial(oxfp));
1.1       ohara     164: }
                    165:
1.7       ohara     166: /* functions named receive_cmo_*. */
1.13      ohara     167: static cmo_null* receive_cmo_null(OXFILE *oxfp)
1.1       ohara     168: {
                    169:     return new_cmo_null();
                    170: }
                    171:
1.13      ohara     172: static cmo_int32* receive_cmo_int32(OXFILE *oxfp)
1.1       ohara     173: {
1.13      ohara     174:     int i = receive_int32(oxfp);
1.1       ohara     175:     return new_cmo_int32(i);
                    176: }
                    177:
1.13      ohara     178: static cmo_string* receive_cmo_string(OXFILE *oxfp)
1.1       ohara     179: {
1.13      ohara     180:     int len = receive_int32(oxfp);
1.25      ohara     181:     char* s = MALLOC(len+1);
1.1       ohara     182:     memset(s, '\0', len+1);
                    183:     if (len > 0) {
1.13      ohara     184:         oxf_read(s, 1, len, oxfp);
1.1       ohara     185:     }
                    186:     return new_cmo_string(s);
                    187: }
                    188:
1.13      ohara     189: static cmo_mathcap* receive_cmo_mathcap(OXFILE *oxfp)
1.1       ohara     190: {
1.13      ohara     191:     cmo* ob = receive_cmo(oxfp);
1.1       ohara     192:     return new_cmo_mathcap(ob);
                    193: }
                    194:
1.13      ohara     195: static cmo_list* receive_cmo_list(OXFILE *oxfp)
1.1       ohara     196: {
                    197:     cmo* ob;
                    198:     cmo_list* c = new_cmo_list();
1.13      ohara     199:     int len = receive_int32(oxfp);
1.1       ohara     200:
                    201:     while (len>0) {
1.13      ohara     202:         ob = receive_cmo(oxfp);
                    203:         list_append(c, ob);
1.1       ohara     204:         len--;
                    205:     }
                    206:     return c;
                    207: }
                    208:
1.13      ohara     209: static cmo_monomial32* receive_cmo_monomial32(OXFILE *oxfp)
1.1       ohara     210: {
                    211:     int i;
1.13      ohara     212:     int len = receive_int32(oxfp);
1.1       ohara     213:     cmo_monomial32* c = new_cmo_monomial32(len);
                    214:
                    215:     for(i=0; i<len; i++) {
1.13      ohara     216:         c->exps[i] = receive_int32(oxfp);
1.1       ohara     217:     }
1.13      ohara     218:     c->coef = receive_cmo(oxfp);
1.1       ohara     219:     return c;
                    220: }
                    221:
1.13      ohara     222: static cmo_zz* receive_cmo_zz(OXFILE *oxfp)
1.1       ohara     223: {
                    224:     cmo_zz* c = new_cmo_zz();
1.13      ohara     225:     receive_mpz(oxfp, c->mpz);
1.1       ohara     226:     return c;
                    227: }
                    228:
1.33      ohara     229: static cmo_qq* receive_cmo_qq(OXFILE *oxfp)
                    230: {
1.34      ohara     231:     mpz_t num, den;
                    232:     mpz_init(num);
                    233:     mpz_init(den);
                    234:     receive_mpz(oxfp, num);
                    235:     receive_mpz(oxfp, den);
                    236:     return new_cmo_qq_set_mpz(num, den);
1.33      ohara     237: }
                    238:
1.38      noro      239: static cmo_bf* receive_cmo_bf(OXFILE *oxfp)
                    240: {
                    241:     mpfr_t num;
                    242:     mpfr_init(num);
                    243:     receive_mpfr(oxfp, num);
                    244:     return new_cmo_bf_set_mpfr(num);
                    245: }
                    246:
1.44    ! noro      247: static cmo_complex* receive_cmo_complex(OXFILE *oxfp)
        !           248: {
        !           249:     cmo *re, *im;
        !           250:
        !           251:     re = receive_cmo(oxfp);
        !           252:     im = receive_cmo(oxfp);
        !           253:     return new_cmo_complex_set_re_im(re,im);
        !           254: }
        !           255:
        !           256:
1.13      ohara     257: static cmo_zero* receive_cmo_zero(OXFILE *oxfp)
1.1       ohara     258: {
                    259:     return new_cmo_zero();
                    260: }
                    261:
1.13      ohara     262: static cmo_dms_generic* receive_cmo_dms_generic(OXFILE *oxfp)
1.1       ohara     263: {
                    264:     return new_cmo_dms_generic();
                    265: }
                    266:
1.13      ohara     267: static cmo_ring_by_name* receive_cmo_ring_by_name(OXFILE *oxfp)
1.1       ohara     268: {
1.13      ohara     269:     cmo* ob = receive_cmo(oxfp);
                    270:     /* We need to check semantics but yet ... */
1.1       ohara     271:     return new_cmo_ring_by_name(ob);
                    272: }
                    273:
1.26      ohara     274: static cmo_recursive_polynomial* receive_cmo_recursive_polynomial(OXFILE *oxfp)
                    275: {
1.27      ohara     276:        cmo_list* ringdef = (cmo_list *)receive_cmo(oxfp);
                    277:        cmo* coef         = receive_cmo(oxfp);
1.26      ohara     278:     return new_cmo_recursive_polynomial(ringdef, coef);
                    279: }
                    280:
1.13      ohara     281: static cmo_distributed_polynomial* receive_cmo_distributed_polynomial(OXFILE *oxfp)
1.1       ohara     282: {
                    283:     cmo* ob;
                    284:     cmo_distributed_polynomial* c = new_cmo_distributed_polynomial();
1.13      ohara     285:     int len = receive_int32(oxfp);
                    286:     c->ringdef = receive_cmo(oxfp);
1.1       ohara     287:
                    288:     while (len>0) {
1.13      ohara     289:         ob = receive_cmo(oxfp);
                    290:         list_append((cmo_list *)c, ob);
1.1       ohara     291:         len--;
                    292:     }
                    293:     return c;
                    294: }
                    295:
1.26      ohara     296: static cmo_polynomial_in_one_variable* receive_cmo_polynomial_in_one_variable(OXFILE *oxfp)
                    297: {
                    298:     cmo* coef;
                    299:     cmo_polynomial_in_one_variable* c;
                    300:     int len = receive_int32(oxfp);
                    301:     int var = receive_int32(oxfp);
                    302:     int exp;
                    303:     c = new_cmo_polynomial_in_one_variable(var);
                    304:     while (len>0) {
                    305:         exp  = receive_int32(oxfp);
                    306:         coef = receive_cmo(oxfp);
1.27      ohara     307:         list_append_monomial((cmo_list *)c, coef, exp);
1.26      ohara     308:         len--;
                    309:     }
                    310:     return c;
                    311: }
                    312:
1.32      ohara     313: static cmo_double* receive_cmo_double(OXFILE *oxfp)
                    314: {
                    315:        double d = receive_double(oxfp);
                    316:        return new_cmo_double(d);
                    317: }
                    318:
1.29      ohara     319: static cmo_indeterminate* receive_cmo_indeterminate(OXFILE *oxfp)
                    320: {
                    321:     cmo* ob = receive_cmo(oxfp);
                    322:     return new_cmo_indeterminate(ob);
                    323: }
                    324:
1.28      ohara     325: static cmo_tree* receive_cmo_tree(OXFILE *oxfp)
                    326: {
                    327:     cmo_string* name = (cmo_string *)receive_cmo(oxfp);
                    328:     cmo_list* attrib = (cmo_list *)receive_cmo(oxfp);
                    329:     cmo_list* leaves = (cmo_list *)receive_cmo(oxfp);
                    330:     return new_cmo_tree(name, attrib, leaves);
                    331: }
                    332:
                    333: static cmo_lambda* receive_cmo_lambda(OXFILE *oxfp)
                    334: {
                    335:     cmo_list* args = (cmo_list *)receive_cmo(oxfp);
                    336:     cmo_tree* body = (cmo_tree *)receive_cmo(oxfp);
                    337:     return new_cmo_lambda(args, body);
                    338: }
                    339:
1.13      ohara     340: static cmo_error2* receive_cmo_error2(OXFILE *oxfp)
1.1       ohara     341: {
1.13      ohara     342:     cmo* ob = receive_cmo(oxfp);
1.1       ohara     343:     return new_cmo_error2(ob);
                    344: }
                    345:
1.17      ohara     346: /* receive_cmo() is called after receive_ox_tag(). */
1.13      ohara     347: cmo* receive_cmo(OXFILE *oxfp)
1.1       ohara     348: {
1.24      ohara     349:     int tag = receive_int32(oxfp);
                    350:     return receive_cmo_tag(oxfp, tag);
                    351: }
                    352:
                    353: cmo *receive_cmo_tag(OXFILE *oxfp, int tag)
                    354: {
1.1       ohara     355:     cmo* m;
                    356:     switch(tag) {
                    357:     case CMO_NULL:
1.13      ohara     358:         m = receive_cmo_null(oxfp);
1.1       ohara     359:         break;
                    360:     case CMO_INT32:
1.13      ohara     361:         m = (cmo *)receive_cmo_int32(oxfp);
1.1       ohara     362:         break;
                    363:     case CMO_STRING:
1.13      ohara     364:         m = (cmo *)receive_cmo_string(oxfp);
1.1       ohara     365:         break;
                    366:     case CMO_MATHCAP:
1.13      ohara     367:         m = (cmo *)receive_cmo_mathcap(oxfp);
1.1       ohara     368:         break;
                    369:     case CMO_LIST:
1.13      ohara     370:         m = (cmo *)receive_cmo_list(oxfp);
1.1       ohara     371:         break;
                    372:     case CMO_MONOMIAL32:
1.13      ohara     373:         m = (cmo *)receive_cmo_monomial32(oxfp);
1.1       ohara     374:         break;
                    375:     case CMO_ZZ:
1.13      ohara     376:         m = (cmo *)receive_cmo_zz(oxfp);
1.1       ohara     377:         break;
1.33      ohara     378:     case CMO_QQ:
                    379:         m = (cmo *)receive_cmo_qq(oxfp);
                    380:         break;
1.38      noro      381:     case CMO_BIGFLOAT:
                    382:         m = (cmo *)receive_cmo_bf(oxfp);
                    383:         break;
1.44    ! noro      384:     case CMO_COMPLEX:
        !           385:         m = (cmo *)receive_cmo_complex(oxfp);
        !           386:         break;
1.1       ohara     387:     case CMO_ZERO:
1.13      ohara     388:         m = (cmo *)receive_cmo_zero(oxfp);
1.1       ohara     389:         break;
                    390:     case CMO_DMS_GENERIC:
1.13      ohara     391:         m = (cmo *)receive_cmo_dms_generic(oxfp);
1.1       ohara     392:         break;
                    393:     case CMO_RING_BY_NAME:
1.13      ohara     394:         m = (cmo *)receive_cmo_ring_by_name(oxfp);
1.1       ohara     395:         break;
                    396:     case CMO_DISTRIBUTED_POLYNOMIAL:
1.13      ohara     397:         m = (cmo *)receive_cmo_distributed_polynomial(oxfp);
1.1       ohara     398:         break;
1.26      ohara     399:     case CMO_RECURSIVE_POLYNOMIAL:
                    400:         m = (cmo *)receive_cmo_recursive_polynomial(oxfp);
                    401:         break;
                    402:     case CMO_POLYNOMIAL_IN_ONE_VARIABLE:
                    403:         m = (cmo *)receive_cmo_polynomial_in_one_variable(oxfp);
1.29      ohara     404:         break;
1.32      ohara     405:        case CMO_64BIT_MACHINE_DOUBLE:
                    406:        case CMO_IEEE_DOUBLE_FLOAT:
                    407:         m = (cmo *)receive_cmo_double(oxfp);
                    408:         break;
1.29      ohara     409:     case CMO_INDETERMINATE:
                    410:         m = (cmo *)receive_cmo_indeterminate(oxfp);
1.28      ohara     411:         break;
                    412:     case CMO_TREE:
                    413:         m = (cmo *)receive_cmo_tree(oxfp);
                    414:         break;
                    415:     case CMO_LAMBDA:
                    416:         m = (cmo *)receive_cmo_lambda(oxfp);
                    417:         break;
1.1       ohara     418:     case CMO_ERROR2:
1.13      ohara     419:         m = (cmo *)receive_cmo_error2(oxfp);
1.1       ohara     420:         break;
                    421:     case CMO_DATUM:
                    422:     default:
1.13      ohara     423:         m = NULL;
1.20      ohara     424:         ox_printf("the CMO (%d) is not implemented.\n", tag);
1.1       ohara     425:     }
                    426:     return m;
                    427: }
                    428:
1.13      ohara     429: static void receive_mpz(OXFILE *oxfp, mpz_ptr mpz)
1.1       ohara     430: {
                    431:     int i;
1.36      iwane     432:     int n = sizeof(mpz->_mp_d[0]) / sizeof(int);
1.13      ohara     433:     int size  = receive_int32(oxfp);
1.1       ohara     434:     int len   = abs(size);
1.36      iwane     435:     int *ptr;
                    436:     if (n == 1) {
                    437:         resize_mpz(mpz, size);
1.37      iwane     438:     } else if (size >= 0) {
                    439:         resize_mpz(mpz, (size+1) / n);
1.36      iwane     440:     } else {
1.37      iwane     441:         resize_mpz(mpz, (size-1) / n);
1.36      iwane     442:     }
                    443:
                    444:     ptr = (int *)mpz->_mp_d;
                    445:     for(i=0; i<len; i++) {
                    446:         ptr[i] = receive_int32(oxfp);
                    447:     }
1.1       ohara     448: }
                    449:
1.13      ohara     450: void send_ox_command(OXFILE *oxfp, int sm_command)
1.1       ohara     451: {
1.13      ohara     452:     send_ox_tag(oxfp, OX_COMMAND);
                    453:     send_int32(oxfp, sm_command);
                    454:     oxf_flush(oxfp);
1.1       ohara     455: }
                    456:
1.13      ohara     457: void ox_close(OXFILE *sv)
1.1       ohara     458: {
1.13      ohara     459:     send_ox_command(oxf_control(sv), SM_control_kill);
1.7       ohara     460:     sleep(2);
1.13      ohara     461:     /* We wait thar an OpenXM server terminates. */
1.20      ohara     462:     ox_printf("I have closed the connection to an Open XM server.\n");
1.1       ohara     463: }
                    464:
1.13      ohara     465: void ox_shutdown(OXFILE *sv)
1.3       ohara     466: {
1.13      ohara     467:     /* We need to use SM_shutdown but yet ... */
                    468:     ox_close(sv);
1.3       ohara     469: }
                    470:
1.13      ohara     471: void ox_cmo_rpc(OXFILE *sv, char *function, int argc, cmo *argv[])
1.3       ohara     472: {
1.13      ohara     473:     int i = argc;
                    474:     while(i-- > 0) {
                    475:         send_ox_cmo(sv, argv[i]);
                    476:     }
                    477:     send_ox_cmo(sv, (cmo *)new_cmo_int32(argc));
                    478:     send_ox_cmo(sv, (cmo *)new_cmo_string(function));
                    479:     send_ox_command(sv, SM_executeFunction);
1.3       ohara     480: }
                    481:
1.13      ohara     482: void ox_execute_string(OXFILE *sv, char* s)
1.3       ohara     483: {
1.13      ohara     484:     send_ox_cmo(sv, (cmo *)new_cmo_string(s));
                    485:     send_ox_command(sv, SM_executeStringByLocalParser);
1.3       ohara     486: }
                    487:
1.13      ohara     488: void ox_push_cmd(OXFILE *sv, int sm_code)
1.1       ohara     489: {
1.13      ohara     490:     send_ox_command(sv, sm_code);
1.1       ohara     491: }
                    492:
1.13      ohara     493: cmo_mathcap* ox_mathcap(OXFILE *sv)
1.1       ohara     494: {
1.13      ohara     495:     send_ox_command(sv, SM_mathcap);
                    496:     send_ox_command(sv, SM_popCMO);
                    497:     receive_ox_tag(sv);          /* OX_DATA */
                    498:     return (cmo_mathcap *)receive_cmo(sv);
1.1       ohara     499: }
                    500:
1.13      ohara     501: char* ox_popString(OXFILE *sv)
1.1       ohara     502: {
                    503:     cmo_string* m = NULL;
                    504:
1.13      ohara     505:     send_ox_command(sv, SM_popString);
                    506:     receive_ox_tag(sv); /* OX_DATA */
                    507:     m = (cmo_string *)receive_cmo(sv);
1.1       ohara     508:     return m->s;
                    509: }
                    510:
1.13      ohara     511: void ox_pops(OXFILE *sv, int num)
1.3       ohara     512: {
1.13      ohara     513:     send_ox_cmo(sv, (cmo *)new_cmo_int32(num));
                    514:     send_ox_command(sv, SM_pops);
1.3       ohara     515: }
                    516:
1.13      ohara     517: cmo* ox_pop_cmo(OXFILE *sv)
1.3       ohara     518: {
1.13      ohara     519:     send_ox_command(sv, SM_popCMO);
                    520:     receive_ox_tag(sv); /* OX_DATA */
                    521:     return receive_cmo(sv);
1.3       ohara     522: }
                    523:
1.13      ohara     524: void ox_push_cmo(OXFILE *sv, cmo *c)
1.3       ohara     525: {
1.13      ohara     526:     send_ox_cmo(sv, c);
1.3       ohara     527: }
                    528:
1.7       ohara     529: /* a dummy function for flushing a connection. */
1.13      ohara     530: int ox_flush(OXFILE *sv)
1.5       ohara     531: {
1.13      ohara     532:     return 1;
1.5       ohara     533: }
                    534:
1.13      ohara     535: void ox_reset(OXFILE *sv)
1.1       ohara     536: {
1.13      ohara     537:     send_ox_command(oxf_control(sv), SM_control_reset_connection);
1.31      iwane     538:     while(receive_ox_tag(sv) != OX_SYNC_BALL) {
                    539:         receive_cmo(sv); /* skipping a message. */
1.1       ohara     540:     }
                    541:
1.13      ohara     542:     send_ox_tag(sv, OX_SYNC_BALL);
1.20      ohara     543:     ox_printf("I have reset an Open XM server.\n");
1.1       ohara     544: }
                    545:
1.13      ohara     546: void send_ox(OXFILE *oxfp, ox *m)
1.1       ohara     547: {
                    548:     switch(m->tag) {
1.13      ohara     549:     case OX_DATA:
                    550:         send_ox_cmo(oxfp, ((ox_data *)m)->cmo);
1.1       ohara     551:         break;
1.13      ohara     552:     case OX_COMMAND:
                    553:         send_ox_command(oxfp, ((ox_command *)m)->command);
1.1       ohara     554:         break;
                    555:     default:
                    556:         /* CMO?? */
1.13      ohara     557:         send_ox_cmo(oxfp, (cmo *)m);
1.1       ohara     558:     }
                    559: }
                    560:
1.13      ohara     561: void send_ox_cmo(OXFILE *oxfp, cmo* m)
1.1       ohara     562: {
1.13      ohara     563:     send_ox_tag(oxfp, OX_DATA);
                    564:     send_cmo(oxfp, m);
                    565:     oxf_flush(oxfp);
1.1       ohara     566: }
                    567:
1.8       ohara     568: /* send_cmo_* functions */
1.13      ohara     569: static int send_cmo_null(OXFILE *oxfp, cmo_null* c)
1.1       ohara     570: {
                    571:     return 0;
                    572: }
                    573:
1.13      ohara     574: static int send_cmo_int32(OXFILE *oxfp, cmo_int32* m)
1.1       ohara     575: {
1.13      ohara     576:     return send_int32(oxfp, m->i);
1.1       ohara     577: }
                    578:
1.13      ohara     579: static int send_cmo_string(OXFILE *oxfp, cmo_string* m)
1.1       ohara     580: {
                    581:     int len = (m->s != NULL)? strlen(m->s): 0;
1.13      ohara     582:     send_int32(oxfp, len);
1.1       ohara     583:     if (len > 0) {
1.13      ohara     584:         oxf_write(m->s, 1, len, oxfp);
1.1       ohara     585:     }
                    586:     return 0;
                    587: }
                    588:
1.13      ohara     589: static int send_cmo_mathcap(OXFILE *oxfp, cmo_mathcap* c)
1.1       ohara     590: {
1.13      ohara     591:     send_cmo(oxfp, c->ob);
1.1       ohara     592:     return 0;
                    593: }
                    594:
1.13      ohara     595: static int send_cmo_list(OXFILE *oxfp, cmo_list* c)
1.1       ohara     596: {
1.13      ohara     597:     cell* el = list_first(c);
                    598:     int len = list_length(c);
                    599:     send_int32(oxfp, len);
                    600:
                    601:     while(!list_endof(c, el)) {
                    602:         send_cmo(oxfp, el->cmo);
                    603:         el = list_next(el);
1.1       ohara     604:     }
                    605:     return 0;
                    606: }
                    607:
1.13      ohara     608: static int send_cmo_distributed_polynomial(OXFILE *oxfp, cmo_distributed_polynomial* c)
1.1       ohara     609: {
1.13      ohara     610:     cell* el = list_first((cmo_list *)c);
                    611:     int len = list_length((cmo_list *)c);
                    612:     send_int32(oxfp, len);
                    613:     send_cmo(oxfp, c->ringdef);
                    614:     while(!list_endof((cmo_list *)c, el)) {
                    615:         send_cmo(oxfp, el->cmo);
                    616:         el = list_next(el);
1.1       ohara     617:     }
                    618:     return 0;
                    619: }
                    620:
1.26      ohara     621: static int send_cmo_polynomial_in_one_variable(OXFILE *oxfp, cmo_polynomial_in_one_variable* c)
                    622: {
1.27      ohara     623:     cell* el = list_first((cmo_list *)c);
                    624:     int len = list_length((cmo_list *)c);
1.26      ohara     625:     send_int32(oxfp, len);
                    626:        send_int32(oxfp, c->var);
                    627:
1.27      ohara     628:     while(!list_endof((cmo_list *)c, el)) {
                    629:         send_int32(oxfp, el->exp);
1.26      ohara     630:         send_cmo(oxfp, el->cmo);
                    631:         el = list_next(el);
                    632:     }
                    633:     return 0;
                    634: }
                    635:
1.32      ohara     636: static int send_cmo_double(OXFILE *oxfp, cmo_double* c)
                    637: {
                    638:     return send_double(oxfp, c->d);
                    639: }
                    640:
1.13      ohara     641: static int send_cmo_monomial32(OXFILE *oxfp, cmo_monomial32* c)
1.1       ohara     642: {
                    643:     int i;
                    644:     int len = c->length;
1.13      ohara     645:     send_int32(oxfp, len);
1.1       ohara     646:     for(i=0; i<len; i++) {
1.13      ohara     647:         send_int32(oxfp, c->exps[i]);
1.1       ohara     648:     }
1.13      ohara     649:     send_cmo(oxfp, c->coef);
1.1       ohara     650:     return 0;
                    651: }
                    652:
1.13      ohara     653: static int send_cmo_zz(OXFILE *oxfp, cmo_zz* c)
1.1       ohara     654: {
1.13      ohara     655:     send_mpz(oxfp, c->mpz);
1.1       ohara     656:     return 0;
                    657: }
                    658:
1.33      ohara     659: static int send_cmo_qq(OXFILE *oxfp, cmo_qq* c)
                    660: {
1.34      ohara     661:     send_mpz(oxfp, mpq_numref(c->mpq));
                    662:     send_mpz(oxfp, mpq_denref(c->mpq));
1.33      ohara     663:     return 0;
                    664: }
                    665:
1.38      noro      666: static int send_cmo_bf(OXFILE *oxfp, cmo_bf* c)
                    667: {
                    668:     send_mpfr(oxfp, c->mpfr);
                    669:     return 0;
                    670: }
                    671:
1.44    ! noro      672: static int send_cmo_complex(OXFILE *oxfp, cmo_complex* c)
        !           673: {
        !           674:     send_cmo(oxfp, c->re);
        !           675:     send_cmo(oxfp, c->im);
        !           676:     return 0;
        !           677: }
        !           678:
1.26      ohara     679: static int send_cmo_recursive_polynomial(OXFILE *oxfp, cmo_recursive_polynomial* c)
                    680: {
1.27      ohara     681:        send_cmo(oxfp, (cmo *)c->ringdef);
1.26      ohara     682:     send_cmo(oxfp, c->coef);
                    683:     return 0;
                    684: }
                    685:
1.28      ohara     686: static int send_cmo_tree(OXFILE *oxfp, cmo_tree *c)
                    687: {
                    688:     send_cmo(oxfp, (cmo *)c->name);
                    689:     send_cmo(oxfp, (cmo *)c->attributes);
                    690:     send_cmo(oxfp, (cmo *)c->leaves);
                    691:     return 0;
                    692: }
                    693:
                    694: static int send_cmo_lambda(OXFILE *oxfp, cmo_lambda *c)
                    695: {
                    696:     send_cmo(oxfp, (cmo *)c->args);
                    697:     send_cmo(oxfp, (cmo *)c->body);
                    698:     return 0;
                    699: }
                    700:
1.13      ohara     701: static int send_cmo_error2(OXFILE *oxfp, cmo_error2* c)
1.1       ohara     702: {
1.13      ohara     703:     send_cmo(oxfp, c->ob);
1.1       ohara     704:     return 0;
                    705: }
                    706:
1.8       ohara     707: /* sending a CMO.  (Remarks: OX_tag is already sent.) */
1.13      ohara     708: void send_cmo(OXFILE *oxfp, cmo* c)
1.1       ohara     709: {
                    710:     int tag = c->tag;
                    711:
1.13      ohara     712:     c = call_hook_before_send_cmo(oxfp, c);
1.2       ohara     713:
1.13      ohara     714:     send_int32(oxfp, tag);
1.1       ohara     715:     switch(tag) {
                    716:     case CMO_NULL:
                    717:     case CMO_ZERO:
                    718:     case CMO_DMS_GENERIC:
1.13      ohara     719:         send_cmo_null(oxfp, c);  /* empty function. */
1.1       ohara     720:         break;
                    721:     case CMO_INT32:
1.13      ohara     722:         send_cmo_int32(oxfp, (cmo_int32 *)c);
1.1       ohara     723:         break;
                    724:     case CMO_STRING:
1.13      ohara     725:         send_cmo_string(oxfp, (cmo_string *)c);
1.1       ohara     726:         break;
                    727:     case CMO_MATHCAP:
                    728:     case CMO_ERROR2:
                    729:     case CMO_RING_BY_NAME:
                    730:     case CMO_INDETERMINATE:
1.13      ohara     731:         send_cmo_mathcap(oxfp, (cmo_mathcap *)c);
1.1       ohara     732:         break;
                    733:     case CMO_LIST:
1.13      ohara     734:         send_cmo_list(oxfp, (cmo_list *)c);
1.1       ohara     735:         break;
                    736:     case CMO_MONOMIAL32:
1.13      ohara     737:         send_cmo_monomial32(oxfp, (cmo_monomial32 *)c);
1.1       ohara     738:         break;
                    739:     case CMO_ZZ:
1.13      ohara     740:         send_cmo_zz(oxfp, (cmo_zz *)c);
1.33      ohara     741:         break;
                    742:     case CMO_QQ:
                    743:         send_cmo_qq(oxfp, (cmo_qq *)c);
1.1       ohara     744:         break;
1.38      noro      745:     case CMO_BIGFLOAT:
                    746:         send_cmo_bf(oxfp, (cmo_bf *)c);
                    747:         break;
1.44    ! noro      748:     case CMO_COMPLEX:
        !           749:         send_cmo_complex(oxfp, (cmo_complex *)c);
        !           750:         break;
1.1       ohara     751:     case CMO_DISTRIBUTED_POLYNOMIAL:
1.13      ohara     752:         send_cmo_distributed_polynomial(oxfp, (cmo_distributed_polynomial *)c);
1.26      ohara     753:         break;
                    754:     case CMO_RECURSIVE_POLYNOMIAL:
                    755:         send_cmo_recursive_polynomial(oxfp, (cmo_recursive_polynomial *)c);
                    756:         break;
                    757:     case CMO_POLYNOMIAL_IN_ONE_VARIABLE:
                    758:         send_cmo_polynomial_in_one_variable(oxfp, (cmo_polynomial_in_one_variable *)c);
1.28      ohara     759:         break;
1.32      ohara     760:        case CMO_64BIT_MACHINE_DOUBLE:
                    761:        case CMO_IEEE_DOUBLE_FLOAT:
                    762:                send_cmo_double(oxfp, (cmo_double *)c);
                    763:                break;
1.28      ohara     764:     case CMO_TREE:
                    765:         send_cmo_tree(oxfp, (cmo_tree *)c);
                    766:         break;
                    767:     case CMO_LAMBDA:
                    768:         send_cmo_lambda(oxfp, (cmo_lambda *)c);
1.1       ohara     769:         break;
                    770:     default:
1.13      ohara     771:         call_hook_after_send_cmo(oxfp, c);
1.1       ohara     772:     }
                    773: }
                    774:
1.13      ohara     775: static int send_mpz(OXFILE *oxfp, mpz_ptr mpz)
1.1       ohara     776: {
                    777:     int i;
1.35      iwane     778:        int n = sizeof(mpz->_mp_d[0]) / sizeof(int);
                    779:     int len = abs(mpz->_mp_size) * n;
                    780:        int *ptr = (int *)mpz->_mp_d;
1.37      iwane     781:     int size;
                    782:     if (len > 0 && ptr[len-1] == 0) {
                    783:         len--;
                    784:     }
                    785:     size = mpz->_mp_size < 0 ? -len : len;
                    786:     send_int32(oxfp, size);
1.1       ohara     787:     for(i=0; i<len; i++) {
1.35      iwane     788:         send_int32(oxfp, ptr[i]);
1.1       ohara     789:     }
                    790:     return 0;
                    791: }
                    792:
1.41      noro      793: int send_int64(OXFILE *oxfp,UL64 a)
1.38      noro      794: {
1.41      noro      795:   return oxfp->send_double(oxfp,((double *)&a)[0]);
1.38      noro      796: }
                    797:
                    798: UL64 receive_int64(OXFILE *oxfp)
                    799: {
1.41      noro      800:        double d = receive_double(oxfp);
                    801:   return ((UL64 *)&d)[0];
1.38      noro      802: }
                    803:
                    804: static void receive_mpfr(OXFILE *oxfp, mpfr_ptr mpfr)
                    805: {
                    806:   int sgn,prec,len,i;
1.42      noro      807:   unsigned int hi,lo;
                    808:   unsigned long *ptr;
1.38      noro      809:   L64 exp;
                    810:
                    811:   sgn  = receive_int32(oxfp);
                    812:   prec  = receive_int32(oxfp);
1.43      noro      813:   exp = receive_int64(oxfp);
1.38      noro      814:   /* len = length as an int array (int = 4bytes) */
                    815:   len  = receive_int32(oxfp);
                    816:
                    817:   mpfr_init2(mpfr,prec);
                    818:   MPFR_SIGN(mpfr) = sgn;
                    819:   ptr = mpfr->_mpfr_d;
                    820:   mpfr->_mpfr_exp = exp;
                    821: #if SIZEOF_LONG==4
                    822:   for ( i = 0; i < len; i++ )
                    823:     ptr[i] = receive_int32(oxfp);
                    824: #else
1.42      noro      825:   if ( len%2 ) {
                    826:     hi = receive_int32(oxfp);
                    827:     ptr[0] = (((UL64)hi)<<32);
                    828:        i = 1;
                    829:   } else
                    830:     i = 0;
                    831:   len = (len+1)/2;
                    832:   for ( ; i < len; i ++ ) {
                    833:     lo = (unsigned int)receive_int32(oxfp);
                    834:     hi = (unsigned int)receive_int32(oxfp);
                    835:     ptr[i] = (((UL64)hi)<<32)|((UL64)lo);
                    836:   }
1.38      noro      837: #endif
                    838: }
                    839:
                    840: static int send_mpfr(OXFILE *oxfp, mpfr_ptr mpfr)
                    841: {
                    842:
1.42      noro      843:   int i,len,t;
                    844:   unsigned long *ptr;
1.43      noro      845:   UL64 uexp;
1.38      noro      846:
                    847:   send_int32(oxfp, MPFR_SIGN(mpfr));
                    848:   send_int32(oxfp, MPFR_PREC(mpfr));
                    849:   send_int64(oxfp, MPFR_EXP(mpfr));
                    850:   len = MPFR_LIMB_SIZE(mpfr);
                    851:   ptr = MPFR_MANT(mpfr);
                    852: #if SIZEOF_LONG==4
                    853:   send_int32(oxfp, len);
                    854:   for ( i = 0; i < len; i++ )
                    855:     send_int32(oxfp,ptr[i]);
                    856: #else /* SIZEOF_LONG==8 */
1.42      noro      857:   t = (MPFR_PREC(mpfr)+31)/32;
                    858:   send_int32(oxfp, t);
                    859:   if ( t%2 ) {
                    860:        send_int32(oxfp,(unsigned int)(ptr[0]>>32));
                    861:     i = 1;
                    862:   } else
                    863:     i = 0;
                    864:   t = (t+1)/2;
                    865:   for ( ; i < len; i++ ) {
                    866:        send_int32(oxfp,(unsigned int)(ptr[i]&0xffffffff));
                    867:        send_int32(oxfp,(unsigned int)(ptr[i]>>32));
                    868:   }
1.38      noro      869: #endif
                    870:     return 0;
                    871: }
                    872:
1.1       ohara     873: ox_data* new_ox_data(cmo* c)
                    874: {
1.25      ohara     875:     ox_data* m = MALLOC(sizeof(ox_data));
1.1       ohara     876:     m->tag = OX_DATA;
                    877:     m->cmo = c;
                    878:     return m;
                    879: }
                    880:
                    881: ox_command* new_ox_command(int sm_code)
                    882: {
1.25      ohara     883:     ox_command* m = MALLOC(sizeof(ox_command));
1.1       ohara     884:     m->tag = OX_COMMAND;
                    885:     m->command = sm_code;
                    886:     return m;
                    887: }
                    888:
                    889: ox_sync_ball* new_ox_sync_ball()
                    890: {
1.25      ohara     891:     ox_sync_ball *m = MALLOC(sizeof(ox_sync_ball));
1.1       ohara     892:     m->tag = OX_SYNC_BALL;
                    893:     return m;
1.19      ohara     894: }
                    895:
                    896: int ox_stderr_init(FILE *fp)
                    897: {
1.21      ohara     898:     ox_stderr = fp;
                    899:     if (ox_stderr != NULL) {
                    900:         setbuf(ox_stderr, NULL);
                    901:     }
1.27      ohara     902:     return 0;
1.20      ohara     903: }
                    904:
                    905: int ox_printf(char *format, ...)
                    906: {
1.21      ohara     907:     if (ox_stderr != NULL) {
                    908:         va_list ap;
                    909:         va_start(ap, format);
                    910:         vfprintf(ox_stderr, format, ap);
                    911:     }
1.27      ohara     912:     return 0;
1.1       ohara     913: }

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