source: git/Singular/newstruct.cc @ 56aaae

spielwiese
Last change on this file since 56aaae was 56aaae, checked in by Hans Schoenemann <hannes@…>, 10 years ago
fix: handle undefined rings in ssi (from master)
  • Property mode set to 100644
File size: 18.9 KB
RevLine 
[5c3bc3]1#include <ctype.h>
2
[16f511]3#ifdef HAVE_CONFIG_H
[ba5e9e]4#include "singularconfig.h"
[16f511]5#endif /* HAVE_CONFIG_H */
[f5b40a]6#include <kernel/mod2.h>
[5c3bc3]7#include <Singular/ipid.h>
8#include <Singular/blackbox.h>
9#include <Singular/lists.h>
10#include <Singular/ipid.h>
11#include <Singular/ipshell.h>
12#include <Singular/newstruct.h>
13
14struct newstruct_member_s;
15typedef struct newstruct_member_s *newstruct_member;
16struct  newstruct_member_s
17{
18  newstruct_member next;
19  char *         name;
20  int            typ;
21  int            pos;
22};
23
[06c0b3]24struct newstruct_proc_s;
25typedef struct newstruct_proc_a *newstruct_proc;
26struct  newstruct_proc_a
27{
28  newstruct_proc next;
29  int            t; /*tok id */
30  int            args; /* number of args */
31  procinfov      p;
32};
33
[5c3bc3]34struct newstruct_desc_s
35{
36  newstruct_member member;
[64cf44]37  newstruct_desc   parent;
[06c0b3]38  newstruct_proc   procs;
[5c3bc3]39  int            size; // number of mebers +1
[64cf44]40  int            id;   // the type id assigned to this bb
[5c3bc3]41};
42
[8357e21]43int newstruct_desc_size()
[b2aa08]44{
45  return sizeof(newstruct_desc_s);
46}
[5c3bc3]47
48char * newstruct_String(blackbox *b, void *d)
49{
50  if (d==NULL) return omStrDup("oo");
51  else
52  {
[7f581e]53    newstruct_desc ad=(newstruct_desc)(b->data);
[3877fe]54
55    newstruct_proc p=ad->procs;
56    while((p!=NULL)&&(p->t!=STRING_CMD))
57      p=p->next;
58
59    if (p!=NULL)
60    {
[5edb77]61      BOOLEAN sl;
[3877fe]62      sleftv tmp;
63      memset(&tmp,0,sizeof(tmp));
64      tmp.rtyp=ad->id;
65      void * newstruct_Copy(blackbox*, void *); //forward declaration
66      tmp.data=(void*)newstruct_Copy(b,d);
67      idrec hh;
68      memset(&hh,0,sizeof(hh));
69      hh.id=Tok2Cmdname(p->t);
70      hh.typ=PROC_CMD;
71      hh.data.pinf=p->p;
72      sl=iiMake_proc(&hh,NULL,&tmp);
73
[e3b071]74      if ((!sl)&& (iiRETURNEXPR.Typ() == STRING_CMD))
[3877fe]75      {
[e3b071]76        char *res = omStrDup((char*)iiRETURNEXPR.CopyD());
[5edb77]77        iiRETURNEXPR.CleanUp();
[f92a39]78        iiRETURNEXPR.Init();
[3877fe]79        return res;
80      }
[5edb77]81      iiRETURNEXPR.CleanUp();
[f92a39]82      iiRETURNEXPR.Init();
[3877fe]83    }
84
[5c3bc3]85    lists l=(lists)d;
86    newstruct_member a=ad->member;
87    StringSetS("");
88    loop
89    {
90      StringAppendS(a->name);
[538512]91      StringAppendS("=");
[5c3bc3]92      if ((!RingDependend(a->typ))
93      || ((l->m[a->pos-1].data==(void *)currRing)
94         && (currRing!=NULL)))
95      {
[64cf44]96        if (l->m[a->pos].rtyp==LIST_CMD)
97        {
98          StringAppendS("<list>");
99        }
[5d84a4]100        else
[64cf44]101        {
102          char *tmp2=omStrDup(l->m[a->pos].String());
[a8f29f]103          if ((strlen(tmp2)>80)||(strchr(tmp2,'\n')!=NULL))
104          {
[73c359d]105            StringAppendS("<");
106            StringAppendS(Tok2Cmdname(l->m[a->pos].rtyp));
107            StringAppendS(">");
[a8f29f]108          }
109          else StringAppendS(tmp2);
[64cf44]110          omFree(tmp2);
111        }
[5c3bc3]112      }
113      else StringAppendS("??");
114      if (a->next==NULL) break;
115      StringAppendS("\n");
116      if(errorreported) break;
117      a=a->next;
118    }
[538512]119    return StringEndS();
[5c3bc3]120  }
121}
[a2faa3]122lists lCopy_newstruct(lists L)
123{
124  lists N=(lists)omAlloc0Bin(slists_bin);
125  int n=L->nr;
126  ring save_ring=currRing;
127  N->Init(n+1);
128  for(;n>=0;n--)
129  {
[5e147a]130    if (RingDependend(L->m[n].rtyp))
[a2faa3]131    {
[5e147a]132      assume((L->m[n-1].rtyp==RING_CMD) || (L->m[n-1].data==NULL));
133      if(L->m[n-1].data!=NULL)
134      {
135        if (L->m[n-1].data!=(void*)currRing)
136          rChangeCurrRing((ring)(L->m[n-1].data));
137        N->m[n].Copy(&L->m[n]);
138      }
139      else
140      {
141        N->m[n].rtyp=L->m[n].rtyp;
142        N->m[n].data=idrecDataInit(L->m[n].rtyp);
143      }
144    }
[06c0b3]145    else if(L->m[n].rtyp==LIST_CMD)
[5e147a]146    {
147      N->m[n].rtyp=L->m[n].rtyp;
[06c0b3]148      N->m[n].data=(void *)lCopy((lists)(L->m[n].data));
[a2faa3]149    }
[06c0b3]150    else if(L->m[n].rtyp>MAX_TOK)
[46eef0]151    {
152      N->m[n].rtyp=L->m[n].rtyp;
[06c0b3]153      blackbox *b=getBlackboxStuff(N->m[n].rtyp);
154      N->m[n].data=(void *)b->blackbox_Copy(b,L->m[n].data);
[46eef0]155    }
[a2faa3]156    else
157      N->m[n].Copy(&L->m[n]);
158  }
159  if (currRing!=save_ring) rChangeCurrRing(save_ring);
160  return N;
161}
[06c0b3]162void * newstruct_Copy(blackbox*, void *d)
[5c3bc3]163{
164  lists n1=(lists)d;
[a2faa3]165  return (void*)lCopy_newstruct(n1);
[5c3bc3]166}
167
[a04a05]168// Used by newstruct_Assign for overloaded '='
169BOOLEAN newstruct_equal(int op, leftv l, leftv r)
170{
171  blackbox *ll=getBlackboxStuff(op);
172  assume(ll->data != NULL);
173  newstruct_desc nt=(newstruct_desc)ll->data;
174  newstruct_proc p=nt->procs;
[f92a39]175
[a04a05]176  while( (p!=NULL) && ((p->t!='=')||(p->args!=1)) ) p=p->next;
177
178  if (p!=NULL)
179  {
[5edb77]180    BOOLEAN sl;
[a04a05]181    idrec hh;
182    memset(&hh,0,sizeof(hh));
183    hh.id=Tok2Cmdname(p->t);
184    hh.typ=PROC_CMD;
185    hh.data.pinf=p->p;
186    sleftv tmp;
187    memset(&tmp,0,sizeof(sleftv));
188    tmp.Copy(r);
[5edb77]189    sl = iiMake_proc(&hh, NULL, &tmp);
190    if (!sl)
[a04a05]191    {
[5edb77]192      if (iiRETURNEXPR.Typ() == op)
[f92a39]193      {
[5edb77]194        l->Copy(&iiRETURNEXPR);
[f92a39]195        iiRETURNEXPR.Init();
196        return FALSE;
197      }
[5edb77]198      iiRETURNEXPR.CleanUp();
[f92a39]199      iiRETURNEXPR.Init();
[a04a05]200    }
201  }
202  return TRUE;
203}
204
[bf7dfc]205void lClean_newstruct(lists l)
206{
207  if (l->nr>=0)
208  {
209    int i;
210    ring r=NULL;
211    for(i=l->nr;i>=0;i--)
212    {
213      if ((i>0) && (l->m[i-1].rtyp==RING_CMD))
214        r=(ring)(l->m[i-1].data);
215      else
216        r=NULL;
217      l->m[i].CleanUp(r);
218    }
219    omFreeSize((ADDRESS)l->m, (l->nr+1)*sizeof(sleftv));
220    l->nr=-1;
221  }
222  omFreeBin((ADDRESS)l,slists_bin);
223}
224
[5c3bc3]225BOOLEAN newstruct_Assign(leftv l, leftv r)
226{
227  if (r->Typ()>MAX_TOK)
228  {
229    blackbox *rr=getBlackboxStuff(r->Typ());
[64cf44]230    if (l->Typ()!=r->Typ())
231    {
232      newstruct_desc rrn=(newstruct_desc)rr->data;
[90707f]233
234      if (!rrn)
235      {
[3d69257]236        Werror("custom type %s(%d) cannot be assigned to newstruct %s(%d)",
[90707f]237               Tok2Cmdname(r->Typ()), r->Typ(), Tok2Cmdname(l->Typ()), l->Typ());
238        return TRUE;
239      }
240
[64cf44]241      newstruct_desc rrp=rrn->parent;
242      while ((rrp!=NULL)&&(rrp->id!=l->Typ())) rrp=rrp->parent;
243      if (rrp!=NULL)
244      {
245        if (l->rtyp==IDHDL)
246        {
247          IDTYP((idhdl)l->data)=r->Typ();
248        }
249        else
250        {
251          l->rtyp=r->Typ();
252        }
253      }
[ed47aab]254      else                      // unrelated types - look for custom conversion
255      {
256        sleftv tmp;
257        BOOLEAN newstruct_Op1(int, leftv, leftv);  // forward declaration
258        if (! newstruct_Op1(l->Typ(), &tmp, r))  return newstruct_Assign(l, &tmp);
259      }
[64cf44]260    }
[5c3bc3]261    if (l->Typ()==r->Typ())
262    {
263      if (l->Data()!=NULL)
264      {
265        lists n1=(lists)l->Data();
[bf7dfc]266        lClean_newstruct(n1);
[5c3bc3]267      }
[a2faa3]268      lists n2=(lists)r->Data();
269      n2=lCopy_newstruct(n2);
[5c3bc3]270      if (l->rtyp==IDHDL)
271      {
272        IDDATA((idhdl)l->data)=(char *)n2;
273      }
274      else
275      {
276        l->data=(void *)n2;
277      }
278      return FALSE;
279    }
280  }
[7b156fb]281
[5edb77]282  else
[7b156fb]283  {
[a04a05]284    assume(l->Typ() > MAX_TOK);
285    sleftv tmp;
286    if(!newstruct_equal(l->Typ(), &tmp, r)) return newstruct_Assign(l, &tmp);
[7b156fb]287  }
[5c3bc3]288  Werror("assign %s(%d) = %s(%d)",
289        Tok2Cmdname(l->Typ()),l->Typ(),Tok2Cmdname(r->Typ()),r->Typ());
290  return TRUE;
291}
292
[0a64d50]293BOOLEAN newstruct_Op1(int op, leftv res, leftv arg)
294{
295  // interpreter: arg is newstruct
296  blackbox *a=getBlackboxStuff(arg->Typ());
297  newstruct_desc nt=(newstruct_desc)a->data;
298  newstruct_proc p=nt->procs;
299
300  while((p!=NULL) &&( (p->t!=op) || (p->args!=1) )) p=p->next;
301
302  if (p!=NULL)
303  {
[5edb77]304    BOOLEAN sl;
[0a64d50]305    sleftv tmp;
306    memset(&tmp,0,sizeof(sleftv));
307    tmp.Copy(arg);
308    idrec hh;
309    memset(&hh,0,sizeof(hh));
310    hh.id=Tok2Cmdname(p->t);
311    hh.typ=PROC_CMD;
312    hh.data.pinf=p->p;
313    sl=iiMake_proc(&hh,NULL,&tmp);
[5edb77]314    if (sl) return TRUE;
[0a64d50]315    else
316    {
[5edb77]317      res->Copy(&iiRETURNEXPR);
[f92a39]318      iiRETURNEXPR.Init();
[0a64d50]319      return FALSE;
320    }
321  }
322  return blackboxDefaultOp1(op,res,arg);
323}
324
325
326
[5c3bc3]327BOOLEAN newstruct_Op2(int op, leftv res, leftv a1, leftv a2)
328{
[06c0b3]329  // interpreter: a1 or a2 is newstruct
[5c3bc3]330  blackbox *a=getBlackboxStuff(a1->Typ());
[06c0b3]331  newstruct_desc nt;
[5c3bc3]332  lists al=(lists)a1->Data();
[06c0b3]333  if (a!=NULL)
[5c3bc3]334  {
[06c0b3]335    nt=(newstruct_desc)a->data;
336    switch(op)
[5c3bc3]337    {
[06c0b3]338      case '.':
[5c3bc3]339      {
[06c0b3]340        if (a2->name!=NULL)
[5c3bc3]341        {
[06c0b3]342          BOOLEAN search_ring=FALSE;
343          newstruct_member nm=nt->member;
344          while ((nm!=NULL)&&(strcmp(nm->name,a2->name)!=0)) nm=nm->next;
345          if ((nm==NULL) && (strncmp(a2->name,"r_",2)==0))
[5e147a]346          {
[06c0b3]347            nm=nt->member;
348            while ((nm!=NULL)&&(strcmp(nm->name,a2->name+2)!=0)) nm=nm->next;
349            if ((nm!=NULL)&&(RingDependend(nm->typ)))
350              search_ring=TRUE;
351            else
352              nm=NULL;
[5e147a]353          }
[06c0b3]354          if (nm==NULL)
355          {
[56aaae]356            Werror("member %s not found", a2->name);
[06c0b3]357            return TRUE;
358          }
359          if (search_ring)
[5c3bc3]360          {
[06c0b3]361            ring r;
362            res->rtyp=RING_CMD;
363            res->data=al->m[nm->pos-1].data;
364            r=(ring)res->data;
365            if (r==NULL) { res->data=(void *)currRing; r=currRing; }
366            if (r!=NULL) r->ref++;
367            else Werror("ring of this member is not set and no basering found");
368            return r==NULL;
369          }
370          else if (RingDependend(nm->typ))
371          {
372            if (al->m[nm->pos].data==NULL)
373            {
374              // NULL belongs to any ring
375              ring r=(ring)al->m[nm->pos-1].data;
376              if (r!=NULL)
377              {
378                r->ref--;
379                al->m[nm->pos-1].data=NULL;
380                al->m[nm->pos-1].rtyp=DEF_CMD;
381              }
382            }
383            else
384            {
385              //Print("checking ring at pos %d for dat at pos %d\n",nm->pos-1,nm->pos);
386              if ((al->m[nm->pos-1].data!=(void *)currRing)
387              &&(al->m[nm->pos-1].data!=(void*)0L))
388              {
389                Werror("different ring %lx(data) - %lx(basering)",
390                  (long unsigned)(al->m[nm->pos-1].data),(long unsigned)currRing);
391                return TRUE;
392              }
393            }
394            if ((currRing!=NULL)&&(al->m[nm->pos-1].data==NULL))
[5c3bc3]395            {
[06c0b3]396              // remember the ring, if not already set
397              al->m[nm->pos-1].data=(void *)currRing;
398              al->m[nm->pos-1].rtyp=RING_CMD;
399              currRing->ref++;
[5c3bc3]400            }
401          }
[06c0b3]402          Subexpr r=(Subexpr)omAlloc0Bin(sSubexpr_bin);
403          r->start = nm->pos+1;
404          memcpy(res,a1,sizeof(sleftv));
405          memset(a1,0,sizeof(sleftv));
406          if (res->e==NULL) res->e=r;
407          else
[5e147a]408          {
[06c0b3]409            Subexpr sh=res->e;
410            while (sh->next != NULL) sh=sh->next;
411            sh->next=r;
[5e147a]412          }
[06c0b3]413          return FALSE;
[5c3bc3]414        }
415        else
416        {
[06c0b3]417          WerrorS("name expected");
418          return TRUE;
[5c3bc3]419        }
420      }
421    }
422  }
[06c0b3]423  else
424  {
425    a=getBlackboxStuff(a2->Typ());
426    nt=(newstruct_desc)a->data;
427    al=(lists)a2->Data();
428  }
429  newstruct_proc p=nt->procs;
[2262ab]430  while((p!=NULL) && ( (p->t!=op) || (p->args!=2) )) p=p->next;
[06c0b3]431  if (p!=NULL)
432  {
[5edb77]433    BOOLEAN sl;
[06c0b3]434    sleftv tmp;
435    memset(&tmp,0,sizeof(sleftv));
436    tmp.Copy(a1);
437    tmp.next=(leftv)omAlloc0(sizeof(sleftv));
438    tmp.next->Copy(a2);
439    idrec hh;
440    memset(&hh,0,sizeof(hh));
441    hh.id=Tok2Cmdname(p->t);
442    hh.typ=PROC_CMD;
443    hh.data.pinf=p->p;
444    sl=iiMake_proc(&hh,NULL,&tmp);
[5edb77]445    if (sl) return TRUE;
[06c0b3]446    else
447    {
[5edb77]448      res->Copy(&iiRETURNEXPR);
[f92a39]449      iiRETURNEXPR.Init();
[06c0b3]450      return FALSE;
451    }
452  }
[5c3bc3]453  return blackboxDefaultOp2(op,res,a1,a2);
454}
[a2faa3]455
[5c3bc3]456// BOOLEAN opM(int op, leftv res, leftv args)
457BOOLEAN newstruct_OpM(int op, leftv res, leftv args)
458{
459  // interpreter: args->1. arg is newstruct
460  blackbox *a=getBlackboxStuff(args->Typ());
[06c0b3]461  newstruct_desc nt=(newstruct_desc)a->data;
[5c3bc3]462  switch(op)
463  {
464    case STRING_CMD:
465    {
466      res->data=(void *)a->blackbox_String(a,args->Data());
467      res->rtyp=STRING_CMD;
468      return FALSE;
469    }
470    default:
471      break;
472  }
[06c0b3]473  newstruct_proc p=nt->procs;
[8357e21]474
[2262ab]475  while((p!=NULL) &&( (p->t!=op) || (p->args!=4) )) p=p->next;
476
[06c0b3]477  if (p!=NULL)
478  {
[5edb77]479    BOOLEAN sl;
[06c0b3]480    sleftv tmp;
481    memset(&tmp,0,sizeof(sleftv));
482    tmp.Copy(args);
483    idrec hh;
484    memset(&hh,0,sizeof(hh));
485    hh.id=Tok2Cmdname(p->t);
486    hh.typ=PROC_CMD;
487    hh.data.pinf=p->p;
488    sl=iiMake_proc(&hh,NULL,&tmp);
[5edb77]489    if (sl) return TRUE;
[06c0b3]490    else
491    {
[5edb77]492      res->Copy(&iiRETURNEXPR);
[f92a39]493      iiRETURNEXPR.Init();
[06c0b3]494      return FALSE;
495    }
496  }
497  return blackbox_default_OpM(op,res,args);
498}
499
[2e4ec14]500void newstruct_destroy(blackbox */*b*/, void *d)
[5c3bc3]501{
502  if (d!=NULL)
503  {
504    lists n=(lists)d;
[06c0b3]505    lClean_newstruct(n);
[5c3bc3]506  }
507}
508
509void *newstruct_Init(blackbox *b)
510{
511  newstruct_desc n=(newstruct_desc)b->data;
512  lists l=(lists)omAlloc0Bin(slists_bin);
513  l->Init(n->size);
514  newstruct_member nm=n->member;
515  while (nm!=NULL)
516  {
517    l->m[nm->pos].rtyp=nm->typ;
[56aaae]518    if (RingDependend(nm->typ))
519      l->m[nm->pos-1].rtyp=RING_CMD;
[5c3bc3]520    l->m[nm->pos].data=idrecDataInit(nm->typ);
521    nm=nm->next;
522  }
523  return l;
524}
525
[2e4ec14]526BOOLEAN newstruct_CheckAssign(blackbox */*b*/, leftv L, leftv R)
[8357e21]527{
528  int lt=L->Typ();
529  int rt=R->Typ();
530  if ((lt!=DEF_CMD)&&(lt!=rt))
531  {
532    Werror("can not assign %s(%d) to member of type %s(%d)",
533            Tok2Cmdname(rt),rt,
534            Tok2Cmdname(lt),lt);
535    return TRUE;
536  }
537  return FALSE;
538}
539
540/* check internal structure:
541* BOOLEAN newstruct_Check(blackbox *b, void *d)
[5c3bc3]542{
543  newstruct_desc n=(newstruct_desc)b->data;
544  lists l=(lists)d;
545  newstruct_member nm=n->member;
546  while (nm!=NULL)
547  {
548    if ((l->m[nm->pos].rtyp!=nm->typ)
549    &&( nm->typ!=DEF_CMD))
550    {
551      Werror("type change in member %s (%s(%d) -> %s(%d))",nm->name,
552          Tok2Cmdname(nm->typ),nm->typ,
[5e147a]553          Tok2Cmdname(l->m[nm->pos].rtyp),l->m[nm->pos].rtyp);
[5c3bc3]554      return TRUE;
555    }
556    nm=nm->next;
557  }
558  return FALSE;
559}
[8357e21]560*/
[a2faa3]561
[f84c3b]562BOOLEAN newstruct_serialize(blackbox *b, void *d, si_link f)
563{
564  newstruct_desc dd=(newstruct_desc)b->data;
[a088a12]565  sleftv l;
566  memset(&l,0,sizeof(l));
567  l.rtyp=STRING_CMD;
568  l.data=(void*)getBlackboxName(dd->id);
569  f->m->Write(f, &l);
[f84c3b]570  lists ll=(lists)d;
[a088a12]571  memset(&l,0,sizeof(l));
572  l.rtyp=LIST_CMD;
573  l.data=ll;
574  f->m->Write(f, &l);
[f84c3b]575  return FALSE;
576}
577
[2e4ec14]578BOOLEAN newstruct_deserialize(blackbox **/*b*/, void **d, si_link f)
[f84c3b]579{
[a088a12]580  // newstruct is serialiazed as a list,
581  // just read a list and take data,
582  // rtyp must be set correctly (to the blackbox id) by routine calling
583  // newstruct_deserialize
584  leftv l=f->m->Read(f);
585  //newstruct_desc n=(newstruct_desc)b->data;
586  //TODO: check compatibility of list l->data with description in n
587  *d=l->data;
588  return FALSE;
[f84c3b]589}
590
[06c0b3]591void newstruct_Print(blackbox *b,void *d)
592{
593  newstruct_desc dd=(newstruct_desc)b->data;
594  newstruct_proc p=dd->procs;
595  while((p!=NULL)&&(p->t!=PRINT_CMD))
596    p=p->next;
597  if (p!=NULL)
598  {
[5edb77]599    BOOLEAN sl;
[06c0b3]600    sleftv tmp;
601    memset(&tmp,0,sizeof(tmp));
602    tmp.rtyp=dd->id;
603    tmp.data=(void*)newstruct_Copy(b,d);
604    idrec hh;
605    memset(&hh,0,sizeof(hh));
606    hh.id=Tok2Cmdname(p->t);
607    hh.typ=PROC_CMD;
608    hh.data.pinf=p->p;
609    sl=iiMake_proc(&hh,NULL,&tmp);
[5edb77]610    if (!sl) iiRETURNEXPR.CleanUp();
[f92a39]611    iiRETURNEXPR.Init();
[06c0b3]612  }
613  else
614    blackbox_default_Print(b,d);
615}
[5c3bc3]616void newstruct_setup(const char *n, newstruct_desc d )
617{
618  blackbox *b=(blackbox*)omAlloc0(sizeof(blackbox));
619  // all undefined entries will be set to default in setBlackboxStuff
[06c0b3]620  // the default Print is quite useful,
[5c3bc3]621  // all other are simply error messages
622  b->blackbox_destroy=newstruct_destroy;
623  b->blackbox_String=newstruct_String;
[06c0b3]624  b->blackbox_Print=newstruct_Print;//blackbox_default_Print;
[5c3bc3]625  b->blackbox_Init=newstruct_Init;
626  b->blackbox_Copy=newstruct_Copy;
627  b->blackbox_Assign=newstruct_Assign;
[0a64d50]628  b->blackbox_Op1=newstruct_Op1;
[5c3bc3]629  b->blackbox_Op2=newstruct_Op2;
630  //b->blackbox_Op3=blackbox_default_Op3;
631  b->blackbox_OpM=newstruct_OpM;
[8357e21]632  b->blackbox_CheckAssign=newstruct_CheckAssign;
[f84c3b]633  b->blackbox_serialize=newstruct_serialize;
634  b->blackbox_deserialize=newstruct_deserialize;
[5c3bc3]635  b->data=d;
636  b->properties=1; // list_like
637  int rt=setBlackboxStuff(b,n);
[64cf44]638  d->id=rt;
[114346]639  //Print("create type %d (%s)\n",rt,n);
[5c3bc3]640}
641
[64cf44]642static newstruct_desc scanNewstructFromString(const char *s, newstruct_desc res)
[5c3bc3]643{
644  char *ss=omStrDup(s);
645  char *p=ss;
646  char *start;
647  int t;
648  char c;
649  newstruct_member elem;
[64cf44]650
[5c3bc3]651  idhdl save_ring=currRingHdl;
652  currRingHdl=(idhdl)1; // fake ring detection
653  loop
654  {
655    // read type:
656    while (*p==' ') p++;
657    start=p;
658    while (isalpha(*p)) p++;
659    *p='\0';
660    IsCmd(start,t);
661    if (t==0)
662    {
663      Werror("unknown type `%s`",start);
664      omFree(ss);
665      omFree(res);
666      currRingHdl=save_ring;
667      return NULL;
668    }
669    if (RingDependend(t))
670      res->size++;    // one additional field for the ring (before the data)
671    //Print("found type %s at real-pos %d",start,res->size);
672    elem=(newstruct_member)omAlloc0(sizeof(*elem));
673    // read name:
674    p++;
675    while (*p==' ') p++;
676    start=p;
677    while (isalpha(*p)) p++;
678    c=*p;
679    *p='\0';
680    elem->typ=t;
681    elem->pos=res->size;
682    if (*start=='\0') /*empty name*/
683    {
684      WerrorS("empty name for element");
[4878eb]685      goto error_in_newstruct_def;
[5c3bc3]686    }
687    elem->name=omStrDup(start);
688    //Print(" name:%s\n",start);
689    elem->next=res->member;
690    res->member=elem;
691    res->size++;
692
693    // next ?
694    *p=c;
695    while (*p==' ') p++;
[eb5526e]696    if (*p!=',')
[4878eb]697    {
[eb5526e]698      if (*p!='\0')
699      {
700        Werror("unknown character in newstruct:>>%s<<",p);
701        goto error_in_newstruct_def;
702      }
703      break; // end-of-list
[4878eb]704    }
[5c3bc3]705    p++;
706  }
707  omFree(ss);
708  currRingHdl=save_ring;
[64cf44]709  //Print("new type with %d elements\n",res->size);
[5c3bc3]710  return res;
[4878eb]711error_in_newstruct_def:
712   omFree(elem);
713   omFree(ss);
714   omFree(res);
715   currRingHdl=save_ring;
716   return NULL;
[5c3bc3]717}
[eff324]718newstruct_desc newstructFromString(const char *s)
[64cf44]719{
720  newstruct_desc res=(newstruct_desc)omAlloc0(sizeof(*res));
721  res->size=0;
722
[eff324]723  return scanNewstructFromString(s,res);
[64cf44]724}
725newstruct_desc newstructChildFromString(const char *parent, const char *s)
[a2faa3]726{
[64cf44]727  // find parent:
728  int parent_id=0;
729  blackboxIsCmd(parent,parent_id);
730  if (parent_id<MAX_TOK)
731  {
732    Werror(">>%s< not found",parent);
733    return NULL;
734  }
735  blackbox *parent_bb=getBlackboxStuff(parent_id);
736  // check for the correct type:
737  if (parent_bb->blackbox_destroy!=newstruct_destroy)
738  {
739    Werror(">>%s< is not a user defined type",parent);
740    return NULL;
741  }
742  // setup for scanNewstructFromString:
743  newstruct_desc res=(newstruct_desc)omAlloc0(sizeof(*res));
744  newstruct_desc parent_desc=(newstruct_desc)parent_bb->data;
745  res->size=parent_desc->size;
746  res->member=parent_desc->member;
747  res->parent=parent_desc;
748
749  return scanNewstructFromString(s,res);
[a2faa3]750}
[06c0b3]751void newstructShow(newstruct_desc d)
752{
753  newstruct_member elem;
754  Print("id: %d\n",d->id);
755  elem=d->member;
756  while (elem!=NULL)
757  {
[56aaae]758    Print(">>%s<< at pos %d, type %d (%s)\n",elem->name,elem->pos,elem->typ,Tok2Cmdname(elem->typ));
759    if (RingDependend(elem->typ))
760      Print(">>r_%s<< at pos %d, shadow ring\n",elem->name,elem->pos-1);
[06c0b3]761    elem=elem->next;
762  }
763}
764
765BOOLEAN newstruct_set_proc(const char *bbname,const char *func, int args,procinfov pr)
766{
767  int id=0;
768  blackboxIsCmd(bbname,id);
769  blackbox *bb=getBlackboxStuff(id);
770  newstruct_desc desc=(newstruct_desc)bb->data;
771  newstruct_proc p=(newstruct_proc)omAlloc(sizeof(*p));
772  p->next=desc->procs; desc->procs=p;
[632c3a]773
774  idhdl save_ring=currRingHdl;
775  currRingHdl=(idhdl)1; // fake ring detection
776
[06c0b3]777  if(!IsCmd(func,p->t))
778  {
779    int t=0;
780    if (func[1]=='\0') p->t=func[0];
781    else if((t=iiOpsTwoChar(func))!=0)
782    {
783      p->t=t;
784    }
785    else
786    {
787      Werror(">>%s<< is not a kernel command",func);
[632c3a]788      currRingHdl = save_ring;
[06c0b3]789      return TRUE;
790    }
791  }
792  p->args=args;
793  p->p=pr; pr->ref++;
[632c3a]794  currRingHdl = save_ring;
[06c0b3]795  return FALSE;
796}
Note: See TracBrowser for help on using the repository browser.