source: git/Singular/silink.cc @ b7808e

spielwiese
Last change on this file since b7808e was b7808e, checked in by Olaf Bachmann <obachman@…>, 27 years ago
Sat Mar 29 16:01:39 1997 Olaf Bachmann <obachman@ratchwum.mathematik.uni-kl.de (Olaf Bachmann)> * silink.cc (DumpQring): Takes care of dumping a Qring git-svn-id: file:///usr/local/Singular/svn/trunk@126 2c84dea3-7e68-4137-9b89-c4e89433aadc
  • Property mode set to 100644
File size: 14.6 KB
Line 
1/****************************************
2*  Computer Algebra System SINGULAR     *
3****************************************/
4/*
5* ABSTRACT
6*/
7/* $Log: not supported by cvs2svn $
8// Revision 1.4  1997/03/28  21:44:36  obachman
9// Fri Mar 28 14:12:05 1997  Olaf Bachmann
10// <obachman@ratchwum.mathematik.uni-kl.de (Olaf Bachmann)>
11//
12//      * Added routines dump(link) and getdump(link) for ascii and MP
13//        links
14//
15//      * ipconv.cc (dConvertTypes): added int->module conversion so that
16//        'module m = 0' works
17//
18//      * iparith.cc (jjVAR1): added LINK_CMD to list of typeof(...)
19//
20// Revision 1.3  1997/03/26  14:58:02  obachman
21// Wed Mar 26 14:02:15 1997  Olaf Bachmann
22// <obachman@ratchwum.mathematik.uni-kl.de (Olaf Bachmann)>
23//
24//      * added reference counter to links, updated slKill, slCopy, slInit
25//      * various small bug fixes for Batch mode
26//
27// Revision 1.1.1.1  1997/03/19  13:18:42  obachman
28// Imported Singular sources
29//
30*/
31
32#include <stdio.h>
33#include <string.h>
34#include "mod2.h"
35#include "tok.h"
36#include "mmemory.h"
37#include "febase.h"
38#include "subexpr.h"
39#include "ipid.h"
40#include "silink.h"
41#include "ipshell.h"
42#include "ring.h"
43#include "lists.h"
44#include "ideals.h"
45#include "numbers.h"
46
47/* declarations */
48static BOOLEAN DumpAscii(FILE *fd, idhdl h);
49static BOOLEAN DumpAsciiIdhdl(FILE *fd, idhdl h);
50static char* GetIdString(idhdl h);
51static int DumpRhs(FILE *fd, idhdl h);
52static BOOLEAN DumpQring(FILE *fd, idhdl h, char *type_str);
53
54/* =============== general utilities ====================================== */
55void GetCmdArgs(int *argc, char ***argv, char *str)
56{
57  int i = 0, sl = strlen(str)+1, j;
58  char *s2=mstrdup(str);
59
60#ifdef HAVE_MPSR
61  char *appl = strstr(s2, "-MPapplication");
62  if (appl != NULL)
63  {
64    *(appl-1) = '\0';
65    i = 2;
66  }
67#endif
68
69  if (strtok(s2, " ") != NULL)
70  {
71    i++;
72    while (strtok(NULL," ") != NULL) i++;
73  }
74  *argc = i;
75  if (i>0)
76  {
77    *argv = (char **) Alloc0(i*sizeof(char *));
78#ifdef HAVE_MPSR
79    if (appl != NULL) i -= 2;
80#endif
81    if (i>0)
82    {
83      strcpy(s2,str);
84      *argv[0] = mstrdup(strtok(s2, " "));
85      for(j = 1; j <i; j++)
86        (*argv)[j] = mstrdup(strtok(NULL, " "));
87    }
88  }
89  else
90    *argv = NULL;
91
92#ifdef HAVE_MPSR
93  if (appl != NULL)
94  {
95    (*argv)[*argc -2] = mstrdup("-MPapplication");
96    (*argv)[*argc -1] = mstrdup(&(appl[14]));
97  }
98#endif
99
100  FreeL(s2);
101}
102/* ====================================================================== */
103si_link_extension si_link_root=NULL;
104BOOLEAN slInit(si_link l, char *istr)
105{
106  char **argv;
107  int argc;
108
109  if (istr!=NULL)
110  {
111    GetCmdArgs(&argc, &argv, istr);
112    // let's parse the results
113    if ( argc <2 )
114    {
115      if (argc == 0)
116      {
117        argv = (char **) Alloc(2*sizeof(char *));
118        argv[0]=mstrdup("");
119      }
120      else if (argc == 1)
121      {
122        char *n=argv[0];
123        Free((ADDRESS)argv,sizeof(char *));
124        argv = (char **) Alloc(2*sizeof(char *));
125        argv[0]=n;
126      }
127      argv[1]=mstrdup("ascii");
128      argc=2;
129    }
130    l->argc = argc;
131    l->argv = argv;
132  }
133  if (l->name==NULL)
134    l->name = mstrdup(argv[0]);
135
136  l->ref = 0;
137
138  BOOLEAN not_found=TRUE;
139  si_link_extension s=si_link_root;
140  while (s!=NULL)
141  {
142    if (!(not_found=s->Init(l,s)))
143    {
144      l->m=s;
145      l->linkType=s->index;
146      break;
147    }
148    s=s->next;
149  }
150  if (not_found) Werror("unknown link type `%s`",argv[1]);
151  return not_found;
152}
153
154void slCleanUp(si_link l)
155{
156  (l->ref)--;
157  if (l->ref < 0)
158  {
159    if (SI_LINK_OPEN_P(l)) slClose(l);
160    if (l->name != NULL) FreeL((ADDRESS)l->name);
161    l->name=NULL;
162    if (l->argc!=0 && l->argv != NULL)
163    {
164      int i=l->argc-1;
165      while(i>=0)
166      {
167        if (l->argv[i] != NULL) FreeL((ADDRESS)l->argv[i]);
168        i--;
169      }
170      Free((ADDRESS)l->argv,l->argc*sizeof(char *));
171    }
172    l->argv=NULL;
173    l->argc=0;
174    l->ref=0;
175  }
176}
177
178 
179void slKill(si_link l)
180{
181  if (l->ref == 0)
182  {
183    slCleanUp(l);
184    Free((ADDRESS)l, sizeof(ip_link));
185  }
186  else
187   slCleanUp(l); 
188}
189
190//--------------------------------------------------------------------------
191BOOLEAN slOpenRead(si_link l)
192{
193  if(SI_LINK_R_OPEN_P(l)) return FALSE; // already open r
194  si_link_extension s=si_link_root;
195  while ((s!=NULL) && (s->index!=l->linkType)) s=s->next;
196  if ((s==NULL)||(s->OpenRead==NULL))
197     return TRUE;
198  l->m=s;   
199  return  s->OpenRead(l);   
200}
201
202BOOLEAN slOpenWrite(si_link l)
203{
204  if(SI_LINK_W_OPEN_P(l)) return FALSE; // already open w
205  si_link_extension s=si_link_root;
206  while ((s!=NULL) && (s->index!=l->linkType)) s=s->next;
207  if ((s==NULL)||(s->OpenWrite==NULL))
208     return TRUE;
209  l->m=s;   
210  return  s->OpenWrite(l);   
211}
212
213BOOLEAN slClose(si_link l)
214{
215  if(! SI_LINK_OPEN_P(l)) return FALSE; // already closed
216  si_link_extension s=l->m;
217  if (s==NULL)
218  {
219    s=si_link_root;
220    while ((s!=NULL) && (s->index!=l->linkType)) s=s->next;
221  } 
222  if ((s==NULL)||(s->Close==NULL))
223    return TRUE;
224  return  s->Close(l);   
225}
226
227leftv slRead(si_link l,leftv a)
228{
229  leftv v = NULL;
230  if( ! SI_LINK_R_OPEN_P(l)) // open r ?
231  {
232    if (slOpenRead(l)) return NULL;
233  }
234  if ((SI_LINK_R_OPEN_P(l))&&(l->m!=NULL))
235  { // open r
236    if (a==NULL)
237    {
238      if (l->m->Read!=NULL)
239        v=l->m->Read(l);
240    }
241    else
242    {
243      if (l->m->Read2!=NULL)
244        v=l->m->Read2(l,a);
245    }
246  }
247  // here comes the eval:
248  if (v != NULL) 
249  {
250    v->Eval();
251  }
252  return v;
253}
254
255BOOLEAN slWrite(si_link l, leftv v)
256{
257  if(! SI_LINK_W_OPEN_P(l)) // open w ?
258  {
259    if (slOpenWrite(l)) return TRUE;
260  }
261  if((SI_LINK_W_OPEN_P(l))&&(l->m!=NULL))
262  { // now open w
263    if (l->m->Write!=NULL)
264      return l->m->Write(l,v);
265  }
266  return TRUE;
267}
268
269BOOLEAN slDump(si_link l)
270{
271  if(! SI_LINK_W_OPEN_P(l)) // open w ?
272  {
273    if (slOpenWrite(l)) return TRUE;
274  }
275  if((SI_LINK_W_OPEN_P(l))&&(l->m!=NULL))
276  { // now open w
277    if (l->m->Dump!=NULL)
278      return l->m->Dump(l);
279  }
280  return TRUE;
281}
282
283BOOLEAN slGetDump(si_link l)
284{
285  if(! SI_LINK_R_OPEN_P(l)) // open w ?
286  {
287    if (slOpenRead(l)) return TRUE;
288  }
289  if((SI_LINK_R_OPEN_P(l))&&(l->m!=NULL))
290  { // now open w
291    if (l->m->GetDump!=NULL)
292      return l->m->GetDump(l);
293  }
294  return TRUE;
295}
296
297/* =============== ASCII ============================================= */
298BOOLEAN slOpenWriteAscii(si_link l)
299{
300  if(SI_LINK_R_OPEN_P(l)&&(l->name[0]!='\0'))
301  {
302    Werror("cannot open input file %s as output file",l->name);
303    return TRUE; // already open r
304  }
305  FILE *outfile;
306  char *mode="a";
307  char *filename=l->name;
308  if(filename[0]=='\0')
309  {
310    SI_LINK_SET_W_OPEN_P(l); /*open, write */
311    l->data=(void *)stdout;
312    return FALSE;
313  }
314  else if(filename[0]=='>')
315  {
316    if (filename[1]=='>')
317      filename+=2;
318    else
319    {
320      filename++;
321      mode="w";
322    }
323  }
324  int i=2;
325  while (i<l->argc)
326  {
327    if(strncmp(l->argv[i],"mode:",5)==0)
328      mode=l->argv[i]+5;
329    else if(strcmp(l->argv[i],"showPath")!=0)
330      Warn("ignore link property %s",l->argv[i]);
331    i++;
332  }
333  outfile=fopen(filename,mode);
334  if (outfile!=NULL)
335  {
336    SI_LINK_SET_W_OPEN_P(l); /*open, write */
337    l->data=(void *)outfile;
338    return FALSE;
339  }
340  return TRUE;
341}
342BOOLEAN slOpenReadAscii(si_link l)
343{
344  if(SI_LINK_W_OPEN_P(l))
345  {
346    Werror("cannot open output file %s as input file",l->name);
347    return TRUE; // already open w
348  }
349  if (l->name[0]!='\0')
350  {
351    char *where=NULL;
352    int i=2;
353    while (i<l->argc)
354    {
355      if(strcmp(l->argv[i],"showPath")==0)
356        where=(char *)Alloc(120);
357      else if(strncmp(l->argv[i],"mode:",5)!=0)
358        Warn("ignore link property %s",l->argv[i]);
359      i++;
360    }
361    FILE *rfile=feFopen(l->name,"r",where);
362    if (where!=NULL)
363    {
364      Print("open %s, success:%d\n",where,rfile!=NULL);
365      Free((ADDRESS)where,120);
366    }
367    if (rfile!=NULL)
368    {
369      l->data=(void *)rfile;
370      SI_LINK_SET_R_OPEN_P(l);
371      return FALSE;
372    }
373    Werror("cannot open %s",l->name);
374    l->data=NULL;
375    return TRUE;
376  }
377  SI_LINK_SET_R_OPEN_P(l);
378  return FALSE;
379}
380BOOLEAN slCloseAscii(si_link l)
381{
382  SI_LINK_SET_CLOSE_P(l);
383  if (l->name[0]!='\0')
384  {
385    return (fclose((FILE *)l->data)!=0);
386  }
387  return FALSE;
388}
389leftv slReadAscii(si_link l)
390{
391  FILE * fp=(FILE *)l->data;
392  char * buf=NULL;
393  if (fp!=NULL)
394  {
395    fseek(fp,0L,SEEK_END);
396    long len=ftell(fp);
397    fseek(fp,0L,SEEK_SET);
398    buf=(char *)AllocL((int)len+1);
399    if (BVERBOSE(V_READING)) Print("//Reading %d chars\n",len);
400    fread( buf, len, 1, fp);
401    buf[len]='\0';
402  }
403  else
404  {
405    PrintS("? "); mflush();
406    buf=(char *)AllocL(80);
407    fe_fgets_stdin(buf,80);
408  }
409  leftv v=(leftv)Alloc0(sizeof(sleftv));
410  v->rtyp=STRING_CMD;
411  v->data=buf;
412  return v;
413}
414BOOLEAN slWriteAscii(si_link l, leftv v)
415{
416  FILE *outfile=(FILE *)l->data;
417  BOOLEAN err=FALSE;
418  char *s;
419  while (v!=NULL)
420  {
421    s = v->String();
422    // free v ??
423    if (s!=NULL)
424    {
425      fprintf(outfile,"%s\n",s);
426      FreeL((ADDRESS)s);
427    }
428    else
429    {
430      Werror("cannot convert to string");
431      err=TRUE;
432    }
433    v = v->next;
434  }
435  fflush(outfile);
436  return err;
437}
438
439BOOLEAN slInitALink(si_link l,si_link_extension s)
440{
441  if (strcmp(l->argv[1], s->name) == 0)
442  {
443    return FALSE;
444  }
445  return TRUE;
446}
447
448BOOLEAN slDumpAscii(si_link l)
449{
450  FILE *fd = (FILE *) l->data;
451  idhdl h = idroot, rh = currRingHdl;
452  BOOLEAN status = DumpAscii(fd, h);
453
454  if (currRingHdl != rh) rSetHdl(rh, TRUE);
455  fflush(fd);
456 
457  return status;
458}
459
460// we do that recursively, to dump ids in the the order in which they
461// were actually defined
462static BOOLEAN DumpAscii(FILE *fd, idhdl h)
463{
464  if (h == NULL) return FALSE;
465
466  if (DumpAscii(fd, IDNEXT(h))) return TRUE;
467
468  // need to set the ring before writing it, othersie we get in
469  // trouble with minpoly
470  if (IDTYP(h) == RING_CMD || IDTYP(h) == QRING_CMD)
471    rSetHdl(h, TRUE);
472
473  if (DumpAsciiIdhdl(fd, h)) return TRUE;
474
475  if (IDTYP(h) == RING_CMD || IDTYP(h) == QRING_CMD)
476  {
477    rSetHdl(h, TRUE);
478    return DumpAscii(fd, IDRING(h)->idroot);
479  }
480  else
481    return FALSE;
482}
483
484static BOOLEAN DumpAsciiIdhdl(FILE *fd, idhdl h)
485{
486  char *type_str = GetIdString(h);
487  idtyp type_id = IDTYP(h);
488
489  // we do not throw an error if a wrong type was attempted to be dumped
490  if (type_str == NULL) return FALSE;
491
492  // handle qrings separately
493  if (type_id == QRING_CMD) return DumpQring(fd, h, type_str);
494 
495  // put type and name
496  if (fprintf(fd, "%s %s", type_str, IDID(h)) == EOF) return TRUE;
497
498  // for matricies, append the dimension
499  if (type_id == MATRIX_CMD)
500  {
501    ideal id = IDIDEAL(h);
502    if (fprintf(fd, "[%d][%d]", id->nrows, id->ncols)== EOF) return TRUE;
503  }
504
505  // check for empty list;
506  if ( ! (type_id == LIST_CMD && IDLIST(h)->nr < 0))
507  {
508    // write the equal sign
509    if (fprintf(fd, " = ") == EOF) return TRUE;
510    // and the right hand side
511    if (DumpRhs(fd, h) == EOF) return TRUE;
512  }
513 
514  // semicolon und tschuess
515  if (fprintf(fd, ";\n") == EOF) return TRUE;
516
517  return FALSE;
518}
519
520static char* GetIdString(idhdl h)
521{
522  idtyp type = IDTYP(h);
523 
524  switch(type)
525  {
526      case LIST_CMD:
527      {
528        lists l = IDLIST(h);
529        int i, nl = l->nr + 1;
530        char *name;
531
532        for (i=0; i<nl; i++)
533          if (GetIdString((idhdl) &(l->m[i])) == NULL) return NULL;
534      }
535      case INT_CMD:
536      case INTVEC_CMD:
537      case INTMAT_CMD:
538      case STRING_CMD:
539      case RING_CMD:
540      case QRING_CMD:
541      case PROC_CMD:
542      case NUMBER_CMD:
543      case POLY_CMD:
544      case IDEAL_CMD:
545      case VECTOR_CMD:
546      case MODUL_CMD:
547      case MATRIX_CMD:
548      case MAP_CMD:
549        return Tok2Cmdname(type);
550       
551      case LINK_CMD:
552        return NULL;
553
554      default:
555       Warn("Can not dump data of type %s", Tok2Cmdname(IDTYP(h)));
556       return NULL;
557  }
558}
559
560static BOOLEAN DumpQring(FILE *fd, idhdl h, char *type_str)
561{
562  char *ideal_str = iiStringMatrix((matrix) IDRING(h)->qideal, 1);
563
564  if (ideal_str == NULL) return TRUE;
565  if (fprintf(fd, "%s temp_ideal = %s;\n", Tok2Cmdname(IDEAL_CMD), ideal_str)
566      == EOF) return TRUE;
567  if (fprintf(fd, "attrib(temp_ideal, \"isSB\", 1);\n") == EOF) return TRUE;
568  if (fprintf(fd, "%s %s = temp_ideal;\n", type_str, IDID(h)) == EOF)
569    return TRUE;
570  else
571    return FALSE;
572}
573
574 
575static int DumpRhs(FILE *fd, idhdl h)
576{
577  idtyp type_id = IDTYP(h);
578
579  if (type_id == LIST_CMD)
580  {
581    lists l = IDLIST(h);
582    int i, nl = l->nr;
583    idhdl h2;
584
585    for (i=0; i<nl; i++)
586    {
587      h2 = (idhdl) &(l->m[i]);
588     
589      if ( ! (IDTYP(h2) == LIST_CMD && IDLIST(h2)->nr < 0))
590      {
591        if (DumpRhs(fd, h2) == EOF) return EOF;
592        fprintf(fd,", ");
593      }
594    }
595    h2 = (idhdl) &(l->m[i]);
596    if ( ! (IDTYP(h2) == LIST_CMD && IDLIST(h2)->nr < 0))
597    { 
598      if (DumpRhs(fd, h2) == EOF) return EOF;
599    }
600  }
601  else  if (type_id == PROC_CMD)
602  {
603    char *pstr = IDSTRING(h), c;
604    fputc('"', fd);
605    while (*pstr != '\0')
606    {
607      if (*pstr == '"') fputc('\\', fd);
608      fputc(*pstr, fd);
609      pstr++;
610    }
611    fputc('"', fd);
612  }
613  else
614  {
615    char *rhs = ((leftv) h)->String();
616
617    if (rhs == NULL) return EOF;
618
619    if (type_id == STRING_CMD) fprintf(fd,"\"");
620    if (type_id == MAP_CMD) fprintf(fd, "%s,", IDMAP(h)->preimage);
621
622    if (fprintf(fd, "%s", rhs) == EOF) return EOF;
623    FreeL(rhs);
624
625    if (type_id == STRING_CMD) fprintf(fd,"\"");
626    if ((type_id == RING_CMD || type_id == QRING_CMD) &&
627        IDRING(h)->minpoly != NULL)
628    {
629      StringSetS("");
630      nWrite(IDRING(h)->minpoly);
631      rhs = StringAppend("");
632      if (fprintf(fd, "; minpoly = %s", rhs) == EOF) return EOF;
633    }
634  }
635  return 1;
636}
637   
638BOOLEAN slGetDumpAscii(si_link l)
639{
640  if (l->name[0] == '\0')
641  {
642    Werror("Can not get dump from stdin");
643    return TRUE;
644  }
645  else
646  {
647    BOOLEAN status = iiPStart(NULL, l->name, NULL);
648
649    if (status)
650      return TRUE;
651    else
652    {
653      // lets reset the file pointer to the beginning to reflect that
654      // we are finished with reading
655      FILE *f = (FILE *) l->data;
656      fseek(f, 0L, SEEK_END);
657      return FALSE;
658    }
659  }
660}
661
662/*-------------------------------------------------------------------*/
663void slExtensionInit(si_link_extension s)
664{
665  s->index=si_link_root->index+10;
666  s->next=si_link_root;
667  si_link_root=s;
668}
669
670#ifdef HAVE_DBM
671#include "sing_dbm.h"
672#endif
673
674#ifdef HAVE_MPSR
675#include "sing_mp.h"
676#endif 
677
678void slStandardInit()
679{
680  si_link_root=(si_link_extension)Alloc0(sizeof(*si_link_root));
681  si_link_root->Init=slInitALink;
682  si_link_root->OpenRead=slOpenReadAscii;
683  si_link_root->OpenWrite=slOpenWriteAscii;
684  si_link_root->Close=slCloseAscii;
685  si_link_root->Read=slReadAscii;
686  //si_link_root->Read2=NULL;
687  si_link_root->Write=slWriteAscii;
688  si_link_root->Dump=slDumpAscii;
689  si_link_root->GetDump=slGetDumpAscii;
690  si_link_root->name="ascii";
691  si_link_root->index=1;
692#ifdef HAVE_DBM
693#ifndef HAVE_MODULE_DBM
694  slExtensionInit(dbInit());
695#endif
696#endif
697#ifdef HAVE_MPSR
698  slExtensionInit(slInitMPFile());
699  slExtensionInit(slInitMPTcp());
700#endif 
701}
Note: See TracBrowser for help on using the repository browser.