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

Annotation of OpenXM/src/ox_toolkit/mathcap.c, Revision 1.6

1.1       ohara       1: /* -*- mode: C; coding: euc-japan -*- */
1.6     ! ohara       2: /* $OpenXM: OpenXM/src/ox_toolkit/mathcap.c,v 1.5 2000/11/24 05:49:26 ohara Exp $ */
1.1       ohara       3:
                      4: /* This module includes functions for handling mathcap databases. */
                      5:
                      6: #include <stdlib.h>
1.5       ohara       7: #include <string.h>
1.1       ohara       8: #include "ox_toolkit.h"
                      9:
1.5       ohara      10: #define MATHCAP_FLAG_DENY   0
                     11: #define MATHCAP_FLAG_ALLOW  1
1.3       ohara      12:
1.5       ohara      13: static void table_init(table *m, int key);
                     14: static table *new_table(int *src);
                     15: static table *table_lookup(table *tbl, int tag);
                     16: static void table_ctl(table *tbl, int tag, int flag);
                     17: static void table_ctl_all(table *tbl, int flag);
                     18: static cmo_list *table_get_all(table *tbl);
                     19: static void table_allow(table *tbl, int tag);
                     20: static void table_deny(table *tbl, int tag);
                     21: static void table_update(table *cmotbl, cmo_list* types);
                     22: static int table_allowQ_tag(table *tbl, int tag);
                     23: static int table_allowQ_cmo_list(table *cmotbl, cmo_list *ob);
                     24: static int table_allowQ_cmo_monomial32(table *cmotbl, cmo_monomial32 *ob);
                     25: static int table_allowQ_cmo_mathcap(table *cmotbl, cmo_mathcap *ob);
                     26: static int table_allowQ_cmo(table *cmotbl, cmo *ob);
                     27: static cmo_list *sysinfo_get();
1.3       ohara      28: static char *new_string(char *s);
1.5       ohara      29: static int *new_int_array(int *array);
                     30: static cmo_list *get_messagetypes(cmo_list *ob, int type);
1.3       ohara      31: static cmo_list *cmo_mathcap_get_cmotypes(cmo_mathcap *mc);
1.2       ohara      32:
1.5       ohara      33: static int cmotbl_a[] = {
1.3       ohara      34:     CMO_NULL,
                     35:     CMO_INT32,
                     36:     CMO_DATUM,
                     37:     CMO_STRING,
                     38:     CMO_MATHCAP,
                     39:     CMO_LIST,
                     40:     CMO_MONOMIAL32,
                     41:     CMO_ZZ,
                     42:     CMO_ZERO,
                     43:     CMO_DMS_GENERIC,
                     44:     CMO_RING_BY_NAME,
                     45:     CMO_INDETERMINATE,
                     46:     CMO_DISTRIBUTED_POLYNOMIAL,
                     47:     CMO_ERROR2,
                     48:     0,
1.1       ohara      49: };
                     50:
1.5       ohara      51: static int smtbl_a[] = {
1.3       ohara      52:     SM_popCMO,
                     53:     SM_popString,
                     54:     SM_mathcap,
                     55:     SM_pops,
                     56:     SM_executeStringByLocalParser,
                     57:     SM_executeFunction,
                     58:     SM_setMathCap,
                     59:     SM_shutdown,
                     60:     SM_control_kill,
                     61:     SM_control_reset_connection,
1.5       ohara      62:     SM_control_spawn_server,
                     63:     SM_control_terminate_server,
1.3       ohara      64:     0,
1.1       ohara      65: };
                     66:
1.5       ohara      67: static struct {
                     68:     int  version;
                     69:     char *version_string;
                     70:     char *sysname;
                     71:     char *hosttype;
                     72:     int  *cmo_tags;
                     73:     int  *sm_cmds;
                     74: } sysinfo = {0, "NO VERSION", "NONAME", "UNKNOWN", cmotbl_a, smtbl_a};
                     75:
1.3       ohara      76: __inline__
1.5       ohara      77: static void table_init(table *m, int key)
1.3       ohara      78: {
                     79:     m->tag  = key;
                     80:     m->flag = MATHCAP_FLAG_ALLOW;
                     81: }
1.2       ohara      82:
1.5       ohara      83: static table *new_table(int *src)
1.2       ohara      84: {
1.5       ohara      85:     table *new;
1.3       ohara      86:     int len=0;
                     87:     int i;
                     88:     while (src[len++] != 0) {
                     89:     }
1.5       ohara      90:     new = malloc(sizeof(table)*len);
1.3       ohara      91:     for(i=0; i<len; i++) {
1.5       ohara      92:         table_init(new+i, src[i]);
1.3       ohara      93:     }
                     94:     return new;
1.2       ohara      95: }
                     96:
                     97: /* 次の tag についてのキーを探す */
1.5       ohara      98: static table *table_lookup(table *tbl, int tag)
1.2       ohara      99: {
1.5       ohara     100:     while (tbl->tag != 0) {
                    101:         if (tbl->tag == tag) {
                    102:             return tbl;
1.2       ohara     103:         }
1.5       ohara     104:         tbl++;
1.2       ohara     105:     }
                    106:     return NULL;
                    107: }
                    108:
                    109: /* tag に対する送信制御 */
1.5       ohara     110: static void table_ctl(table *tbl, int tag, int flag)
1.2       ohara     111: {
1.5       ohara     112:     table *e = table_lookup(tbl, tag);
1.2       ohara     113:     if (e != NULL) {
                    114:         e->flag = flag;
                    115:     }
                    116: }
                    117:
                    118: /* 全データに対する送信制御 */
1.5       ohara     119: static void table_ctl_all(table *tbl, int flag)
1.2       ohara     120: {
1.5       ohara     121:     while (tbl->tag != 0) {
                    122:         tbl->flag = flag;
                    123:         tbl++;
1.2       ohara     124:     }
                    125: }
                    126:
                    127: /* 送信許可されている tag のリストを得る */
1.5       ohara     128: static cmo_list *table_get_all(table *tbl)
1.2       ohara     129: {
                    130:     cmo_list *list = new_cmo_list();
1.5       ohara     131:     while (tbl->tag != 0) {
                    132:         if (tbl->flag == MATHCAP_FLAG_ALLOW) {
                    133:             list_append(list, (cmo *)new_cmo_int32(tbl->tag));
1.2       ohara     134:         }
1.5       ohara     135:         tbl++;
1.2       ohara     136:     }
                    137:     return list;
                    138: }
                    139:
1.5       ohara     140: /* 次の tag をもつ cmo or sm_cmd の送信を許可する */
                    141: __inline__
                    142: static void table_allow(table *tbl, int tag)
                    143: {
                    144:     table_ctl(tbl, tag, MATHCAP_FLAG_ALLOW);
                    145: }
                    146:
                    147: /* 次の tag をもつ cmo or sm_cmd の送信を不許可にする */
                    148: __inline__
                    149: static void table_deny(table *tbl, int tag)
                    150: {
                    151:     table_ctl(tbl, tag, MATHCAP_FLAG_DENY);
                    152: }
                    153:
                    154: static void table_update(table *cmotbl, cmo_list* types)
                    155: {
                    156:     cell *el = list_first(types);
                    157:     cmo_int32 *ob;
                    158:     while(!list_endof(types, el)) {
                    159:         ob = (cmo_int32 *)el->cmo;
                    160:         if (ob->tag == CMO_INT32) {
                    161:             table_allow(cmotbl, ob->i);
                    162:         }
                    163:         el = list_next(el);
                    164:     }
                    165: }
1.1       ohara     166:
1.5       ohara     167: /* 次の tag をもつ cmo or sm_cmd の送信が許可されているかを調べる */
                    168: static int table_allowQ_tag(table *tbl, int tag)
1.1       ohara     169: {
1.5       ohara     170:     while (tbl->tag != 0 && tbl->tag != tag) {
                    171:         tbl++;
1.1       ohara     172:     }
1.5       ohara     173:     return tbl->flag;
1.1       ohara     174: }
                    175:
1.5       ohara     176: static int table_allowQ_cmo_list(table *cmotbl, cmo_list *ob)
1.1       ohara     177: {
                    178:     cell *el;
1.5       ohara     179:     if (table_allowQ_tag(cmotbl, ob->tag)) {
1.1       ohara     180:         el = list_first(ob);
                    181:         while (!list_endof(ob, el)) {
1.5       ohara     182:             if (!table_allowQ_cmo(cmotbl, el->cmo)) {
1.1       ohara     183:                 return MATHCAP_FLAG_DENY;
                    184:             }
                    185:             el = list_next(el);
                    186:         }
                    187:         return MATHCAP_FLAG_ALLOW;
                    188:     }
                    189:     return MATHCAP_FLAG_DENY;
                    190: }
                    191:
1.2       ohara     192: __inline__
1.5       ohara     193: static int table_allowQ_cmo_monomial32(table *cmotbl, cmo_monomial32 *ob)
1.1       ohara     194: {
1.5       ohara     195:     return table_allowQ_tag(cmotbl, ob->tag)
                    196:         && table_allowQ_cmo(cmotbl, ob->coef);
1.1       ohara     197: }
                    198:
1.2       ohara     199: __inline__
1.5       ohara     200: static int table_allowQ_cmo_mathcap(table *cmotbl, cmo_mathcap *ob)
1.1       ohara     201: {
1.5       ohara     202:     return table_allowQ_tag(cmotbl, ob->tag)
                    203:         && table_allowQ_cmo(cmotbl, ob->ob);
1.1       ohara     204: }
                    205:
                    206: /* 次の cmo の送信が許可されているかを調べる */
1.5       ohara     207: static int table_allowQ_cmo(table *cmotbl, cmo *ob)
1.1       ohara     208: {
                    209:     int tag = ob->tag;
                    210:     switch(tag) {
                    211:     case CMO_LIST:
                    212:     case CMO_DISTRIBUTED_POLYNOMIAL:
1.5       ohara     213:         return table_allowQ_cmo_list(cmotbl, (cmo_list *)ob);
1.1       ohara     214:     case CMO_MATHCAP:
                    215:     case CMO_ERROR2:
                    216:     case CMO_RING_BY_NAME:
                    217:     case CMO_INDETERMINATE:
1.5       ohara     218:         return table_allowQ_cmo_mathcap(cmotbl, (cmo_mathcap *)ob);
1.1       ohara     219:     case CMO_MONOMIAL32:
1.5       ohara     220:         return table_allowQ_cmo_monomial32(cmotbl, (cmo_monomial32 *)ob);
1.1       ohara     221:     default:
1.5       ohara     222:         return table_allowQ_tag(cmotbl, tag);
1.1       ohara     223:     }
                    224: }
                    225:
                    226: /* システム情報を得る */
1.5       ohara     227: static cmo_list *sysinfo_get()
1.1       ohara     228: {
                    229:     cmo_list *syslist = new_cmo_list();
1.3       ohara     230:     cmo_int32 *ver    = new_cmo_int32(sysinfo.version);
                    231:     cmo_string *vers  = new_cmo_string(sysinfo.version_string);
                    232:     cmo_string *host  = new_cmo_string(sysinfo.hosttype);
                    233:     cmo_string *sname = new_cmo_string(sysinfo.sysname);
                    234:     return list_appendl(syslist, ver, sname, vers, host, NULL);
1.1       ohara     235: }
                    236:
                    237: static char *new_string(char *s)
                    238: {
                    239:     char *t = malloc(sizeof(s)+1);
                    240:     strcpy(t, s);
                    241:     return t;
                    242: }
                    243:
1.5       ohara     244: static int *new_int_array(int *array)
                    245: {
                    246:     int *new_array;
                    247:     int length = 0;
                    248:     while(array[length++] != 0)
                    249:         ;
                    250:     new_array = malloc(sizeof(int)*length);
                    251:     return memcpy(new_array, array, sizeof(int)*length);
                    252: }
                    253:
                    254: void mathcap_init(int ver, char *vstr, char *sysname, int cmos[], int sms[])
1.1       ohara     255: {
                    256:     char *host = getenv("HOSTTYPE");
1.3       ohara     257:     sysinfo.hosttype = (host != NULL)? new_string(host): "UNKNOWN";
                    258:     sysinfo.sysname  = new_string(sysname);
                    259:     sysinfo.version_string = new_string(vstr);
1.5       ohara     260:     sysinfo.version  = ver;
                    261:     if (cmos != NULL) {
                    262:         sysinfo.cmo_tags = new_int_array(cmos);
                    263:     }
                    264:     if (sms != NULL) {
                    265:         sysinfo.sm_cmds = new_int_array(sms);
                    266:     }
1.3       ohara     267: }
1.1       ohara     268:
1.5       ohara     269: mathcap *new_mathcap()
1.3       ohara     270: {
1.5       ohara     271:     mathcap *new = malloc(sizeof(mathcap));
                    272:     new->cmotbl = new_table(sysinfo.cmo_tags);
                    273:     new->smtbl  = new_table(sysinfo.sm_cmds);
                    274:     return new;
1.1       ohara     275: }
                    276:
                    277: /* データベースから cmo_mathcap を生成する */
1.3       ohara     278: cmo_mathcap* mathcap_get(mathcap *this)
1.1       ohara     279: {
                    280:     cmo_list *mc = new_cmo_list();
                    281:     cmo_list *l3 = new_cmo_list();
1.3       ohara     282:     list_append(l3, list_appendl(new_cmo_list(),
                    283:                                  new_cmo_int32(OX_DATA),
1.5       ohara     284:                                  table_get_all(this->cmotbl), NULL));
                    285:     list_appendl(mc, (cmo *)sysinfo_get(),
                    286:                  (cmo *)table_get_all(this->smtbl), (cmo *)l3, NULL);
1.1       ohara     287:     return new_cmo_mathcap((cmo *)mc);
                    288: }
                    289:
                    290: /* ( ..., ( type, (...) ), (cmo_int32, (...) ), ... )  */
                    291: /*                ^^^^^ Here!                          */
                    292: static cmo_list *get_messagetypes(cmo_list *ob, int type)
                    293: {
                    294:     cmo_list  *c;
                    295:     cell *el;
                    296:
                    297:     for (el = list_first(ob); !list_endof(ob, el); el = list_next(el)) {
                    298:         c = (cmo_list *)el->cmo;
                    299:         if (((cmo_int32 *)list_nth(c, 0))->i == type) {
                    300:             return (cmo_list *)list_nth(c, 1);
                    301:         }
                    302:     }
                    303:     return NULL;
                    304: }
                    305:
                    306: /* cmo_mathcap->ob = ( (...), (...), ( ( cmo_int32, (...) ), ...), ...) */
                    307: /*                                              ^^^^^ Here!         */
1.2       ohara     308: __inline__
1.1       ohara     309: static cmo_list *cmo_mathcap_get_cmotypes(cmo_mathcap *mc)
                    310: {
                    311:     cmo_list *ob = (cmo_list *)list_nth((cmo_list *)mc->ob, 2);
                    312:     return get_messagetypes(ob, OX_DATA);
                    313: }
                    314:
                    315: /* 受信した mathcap データを反映させる */
1.3       ohara     316: /* this == NULL のとき、はじめて mathcap* オブジェクトをせいせいする */
                    317: mathcap *mathcap_update(mathcap *this, cmo_mathcap *mc)
1.1       ohara     318: {
                    319:     cmo_list *types;
1.5       ohara     320:     types = cmo_mathcap_get_cmotypes(mc);
                    321:     if (types != NULL) {
                    322:         /* すべての cmo の送信を禁止 */
                    323:         table_ctl_all(this->cmotbl, MATHCAP_FLAG_DENY);
                    324:         table_update(this->cmotbl, types);
1.1       ohara     325:     }
1.5       ohara     326:
                    327:     return this;
                    328: }
                    329:
                    330: int mathcap_allowQ_cmo(mathcap *this, cmo *ob)
                    331: {
                    332:     return table_allowQ_cmo(this->cmotbl, ob);
1.1       ohara     333: }

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