source: git/Singular/febase.cc @ 400884

spielwiese
Last change on this file since 400884 was 620e99, checked in by Olaf Bachmann <obachman@…>, 27 years ago
* fixed bug in feFopen: strlen(NULL) is undefined under Linux! git-svn-id: file:///usr/local/Singular/svn/trunk@251 2c84dea3-7e68-4137-9b89-c4e89433aadc
  • Property mode set to 100644
File size: 19.6 KB
Line 
1/****************************************
2*  Computer Algebra System SINGULAR     *
3****************************************/
4/* $Id: febase.cc,v 1.18 1997-05-05 21:12:02 obachman Exp $ */
5/*
6* ABSTRACT: i/o system, handling of 'voices'
7*/
8
9#include <stdlib.h>
10#include <string.h>
11#include <stdio.h>
12#include <limits.h>
13#include <stdarg.h>
14#ifndef macintosh
15#include <unistd.h>
16#endif
17#ifdef NeXT
18#include <sys/file.h>
19#endif
20#include "mod2.h"
21#include "tok.h"
22#include "febase.h"
23#include "mmemory.h"
24#include "subexpr.h"
25#include "ipshell.h"
26
27#define fePutChar(c) fputc((uchar)(c),stdout)
28/*0 implementation */
29
30char fe_promptstr[]
31#ifdef macintosh
32                   =" \n";
33#else
34                   ="  ";
35#endif
36
37class Voices
38{
39  private:
40    void Init()
41    {
42      memset(this,0,sizeof(*this));
43      v_lineno = 1;
44    }
45  public:
46    int    v_lineno;        // lineno, to restore in recursion
47    int    v_oldlineno;     // lineno, to restore at exit
48    int    typ;             // buffer type: see BT_..
49    int    v_echo;          // echo, to restore in recursion
50    int    v_fileVoice;     // to be restored in recursion
51    int    v_inputswitch;   // ??
52    FILE * files;           // file handle
53    long   fptr;            // file | buffer seek
54    char*  filename;        // file name
55    char * buffer;          // buffer pointer
56
57  void Next();
58  Voices() { Init(); }
59  Voices * VFile(char* fname);
60  Voices * Buffer(char* buf, int t);
61  int Exit();
62} ;
63
64
65extern FILE* yyin;
66
67#define INITIAL_PRINT_BUFFER 24*1024
68static int feBufferLength=INITIAL_PRINT_BUFFER;
69static char * feBuffer=(char *)Alloc(INITIAL_PRINT_BUFFER);
70
71#define START_LEVMAX 32
72int     levmax       = START_LEVMAX;
73Voices *currentVoice = NULL;
74Voices *FileAttribs  =(Voices *)Alloc0(START_LEVMAX*sizeof(Voices));
75short  *ifswitch     =(short *)Alloc0(START_LEVMAX*sizeof(short));
76        /*1 ifswitch==0: no if statement, else is invalid
77        *           ==1: if (0) processed, execute else
78        *           ==2: if (1) processed, else allowed but not executed
79        */
80int     si_echo = 0;
81int     printlevel = 0;
82int     fileVoice = 0;
83#ifndef macintosh
84int     pagelength = 24;
85#else
86int     pagelength = -1;
87#endif
88int     colmax = 80;
89int     voice = 0;
90int     inputswitch = 0;
91int     blocklineno = 0;
92char    prompt_char = '>'; /*1 either '>' or '.'*/
93BITSET  verbose = 1
94                  | Sy_bit(V_REDEFINE)
95                  | Sy_bit(V_LOAD_LIB)
96                  | Sy_bit(V_SHOW_USE)
97                  | Sy_bit(V_PROMPT)
98//                  | Sy_bit(V_DEBUG_MEM)
99                  ;
100BOOLEAN errorreported = FALSE;
101BOOLEAN feBatch;
102char *  feErrors=NULL;
103int     feErrorsLen=0;
104
105BOOLEAN feProt = FALSE;
106FILE*   feProtFile;
107BOOLEAN tclmode=FALSE;
108/* TCL-Protocoll (Singular -x): <char type>:<int length>:<string> \n
109*  E:l:s  error - not implemented yet (use N)
110*  W:l:s  warning
111*  N:l:s  stdout
112*  Q:0:   quit
113*  P:0:   prompt >
114*  P:1:   prompt .
115*  R:l:<ring-name> ring change
116* plan:
117*  O:l:<option/no-option> option change (option)
118*  V:l:<option/no-option> option change (verbose)
119*/
120
121/*2
122* fopen, but use 'SINGULARPATH' from environment and SINGULARDATADIR
123* as set by configure
124*/
125#ifdef macintosh
126#  define  FS_SEP ','
127#  define  DIR_SEP ':'
128#  define  DIR_SEPP ":"
129#else
130#ifdef MSDOS
131#  define  FS_SEP ';'
132#  define  DIR_SEP '\\'
133#  define  DIR_SEPP "\\"
134#else
135#ifdef atarist
136#  define  FS_SEP ';'
137#  define  DIR_SEP '\\'
138#  define  DIR_SEPP "\\"
139#else  /* unix */
140#  define  FS_SEP ':'
141#  define  DIR_SEP '/'
142#  define  DIR_SEPP "/"
143#endif  /* atarist */
144#endif  /* MSDOS */
145#endif  /* macintosh */
146
147FILE * feFopen(char *path, char *mode, char *where,int useWerror)
148{
149  FILE * f=fopen(path,mode);
150  if (where!=NULL) strcpy(where,path);
151  if ((*mode=='r') && (path[0]!=DIR_SEP)&&(path[0]!='.')
152  &&(f==NULL))
153  {
154    char found = 0;
155    #ifdef MSDOS
156      char *env=getenv("SPATH");
157    #else
158      char *env=getenv("SINGULARPATH");
159    #endif
160    char *s;
161    #ifndef macintosh
162    // extend path by SINGULAR_DATADIR
163    s = (char*) AllocL((env != NULL ? strlen(env) : 0)
164                       +strlen(SINGULAR_DATADIR)+2);
165    if (env != NULL)
166    {
167      strcpy(s, env);
168      s[strlen(env)] = FS_SEP;
169      s[strlen(env)+1] = '\0';
170      strcat(s, SINGULAR_DATADIR);
171    }
172    else strcpy(s, SINGULAR_DATADIR);
173    env = s;
174    #endif
175    if (where==NULL) s=(char *)AllocL(250);
176    else             s=where;
177    if (env!=NULL)
178    {
179      char *p,*q;
180      p = env;
181      while( (q=strchr(p, FS_SEP)) != NULL)
182      {
183        *q = '\0';
184        strcpy(s,p);
185        *q = FS_SEP;
186        strcat(s, DIR_SEPP);
187        strcat(s, path);
188        #ifndef macintosh
189          if(!access(s, R_OK)) { found++; break; }
190        #else
191          f=fopen(s,mode);
192          if (f!=NULL)  { found++; fclose(f); break; }
193        #endif
194        p = q+1;
195      }
196      if(!found)
197      {
198        strcpy(s,p);
199        strcat(s, DIR_SEPP);
200        strcat(s, path);
201      }
202      f=fopen(s,mode);
203      if (f!=NULL)
204      {
205        if (where==NULL) FreeL((ADDRESS)s);
206        return f;
207      }
208    }
209    else
210    {
211      if (where!=NULL) strcpy(s/*where*/,path);
212      f=fopen(path,mode);
213    }
214    #ifndef macintosh
215    FreeL(env);
216    #endif
217    if (where==NULL) FreeL((ADDRESS)s);
218  }
219  if ((f==NULL)&&(useWerror))
220    Werror("cannot open `%s`",path);
221  return f;
222}
223
224/*2
225* the name of the current 'voice': the procname (or filename)
226*/
227const char * VoiceName()
228{
229  if (FileAttribs[fileVoice].filename!=NULL)
230    return FileAttribs[fileVoice].filename;
231  return sNoName;
232}
233
234/*2
235* the name of the 'voice' number 'i': the procname (or filename)
236*/
237const char * VoiceName(int i)
238{
239  if (FileAttribs[i].filename!=NULL)
240    return FileAttribs[i].filename;
241  return sNoName;
242}
243
244/*2
245* the type of the current voice:BT_proc, BT_example, BT_file
246*/
247int VoiceType()
248{
249  int i=fileVoice;
250  while ((FileAttribs[i].typ!=BT_proc)
251  &&(FileAttribs[i].typ!=BT_example)
252  &&(FileAttribs[i].typ!=BT_file)
253  &&(i>0))
254    i--;
255  return FileAttribs[i].typ;
256}
257/*2
258* start the file 'fname' (STDIN is stdin) in the current voice (cf.newVoice)
259*/
260Voices * Voices::VFile(char* fname)
261{
262  if (strcmp(fname,"STDIN") == 0)
263  {
264    yyin = stdin;
265    v_inputswitch = 0;
266  }
267  else
268  {
269    yyin = feFopen(fname,"r",NULL,TRUE);
270    v_inputswitch = -1;
271  }
272  files      = yyin;
273  filename   = mstrdup(fname);
274  v_echo     = si_echo;
275  fileVoice  = voice;
276  yylineno   = 1;
277  if (files==NULL)
278  {
279    inputswitch = 0;
280    exitVoice();
281    return NULL;
282  }
283  inputswitch= v_inputswitch;
284  return this;
285}
286
287/*3
288* increment voice counter, allocate new memory
289*/
290static inline void inc_voice()
291{
292  voice++;
293  if (voice >= levmax)
294  {
295    FileAttribs=(Voices *)ReAlloc(FileAttribs,
296                          levmax*sizeof(Voices),
297                          (levmax+16)*sizeof(Voices));
298    memset(&FileAttribs[levmax],0,16*sizeof(Voices));
299    ifswitch=(short *)ReAlloc(ifswitch,
300                          levmax*sizeof(short),
301                          (levmax+16)*sizeof(short));
302    memset(&ifswitch[levmax],0,16*sizeof(short));
303    levmax+=16;
304  }
305}
306
307/*2
308* init a new voice similiar to the current
309*/
310void Voices::Next()
311{
312  v_oldlineno = yylineno;
313  v_echo      = si_echo;
314  v_fileVoice = fileVoice;
315  inc_voice();
316
317  currentVoice = &FileAttribs[voice];
318  currentVoice->Init();
319}
320
321/*2
322* start the file 'fname' (STDIN is stdin) as a new voice (cf.VFile)
323*/
324int newVoice(char* s)
325{
326  currentVoice->Next();
327  return (int)currentVoice->VFile((char *)s);
328}
329
330void newBuffer(char* s, int t, char* pname)
331{
332  currentVoice->Next();
333  currentVoice->Buffer(s,t);
334  if (pname) currentVoice->filename = mstrdup(pname);
335  //printf("start buffer %d typ %d\n",voice,t);
336}
337
338Voices * Voices::Buffer(char* buf, int t)
339{
340  inputswitch = v_inputswitch = t;
341  buffer      = buf;
342  typ         = t;
343  //si_echo        = 0;
344  switch (t)
345  {
346    case BT_example:
347    case BT_proc:    v_lineno = yylineno; ::yylineno = 3;     break;
348    case BT_file:    v_lineno = yylineno; ::yylineno = 1;     break;
349    case BT_if:
350    case BT_else:    ::yylineno = v_lineno = blocklineno - 1; break;
351    case BT_break:   ::yylineno = v_lineno = blocklineno - 2; break;
352  }
353  return this;
354}
355
356/*2
357* after leaving a voice:
358* setup everything from the this level
359*/
360int Voices::Exit()
361{
362  if (voice >= 0)
363  {
364    si_echo          = v_echo;
365    fileVoice     = v_fileVoice;
366    yyin          = files;
367    yylineno      = v_oldlineno;
368    inputswitch   = v_inputswitch;
369    return 0;
370  }
371  //Print("Exit:%d\n",voice);
372  return 1;
373}
374
375/*2
376* exit Buffer of type 'typ':
377* returns 1 if buffer type could not be found
378*/
379int exitBuffer(int typ)
380{
381  //printf("exitBuffer: %d\n",typ);
382  if (typ == BT_break)  // valid inside for, while. may skip if, else
383  {
384    /*4 first check for valid buffer type, skip if/else*/
385    for (int i=voice; i>0; i--)
386    {
387      if ((FileAttribs[i].typ == BT_if)
388        ||(FileAttribs[i].typ == BT_else)) continue;
389      if (FileAttribs[i].typ == BT_break /*typ*/)
390      {
391        while ((/*typ*/ BT_break != currentVoice->typ)
392        && (voice > 0))
393        {
394          exitVoice();
395        }
396        return exitVoice();
397      }
398      else return 1;
399    }
400    /*4 break not inside a for/while: return an error*/
401    if (/*typ*/ BT_break != currentVoice->typ) return 1;
402    return exitVoice();
403  }
404
405  if ((typ == BT_proc)
406  || (typ == BT_example))
407  {
408    for (int i=voice; i>0; i--)
409    {
410      if (FileAttribs[i].typ == 0) break;
411      if ((FileAttribs[i].typ == BT_proc)
412      || (FileAttribs[i].typ == BT_example))
413      {
414        while ((BT_proc != currentVoice->typ)
415          && (BT_example != currentVoice->typ)
416        && (voice > 0))
417        {
418          exitVoice();
419        }
420        return exitVoice();
421      }
422    }
423  }
424  /*4 return not inside a proc: return an error*/
425  return 1;
426}
427
428/*2
429* jump to the beginning of a buffer
430*/
431int contBuffer(int typ)
432{
433  if (typ == BT_break)  // valid inside for, while. may skip if, else
434  {
435    // first check for valid buffer type
436    for (int i=voice; i>0; i--)
437    {
438      if ((FileAttribs[i].typ == BT_if)
439        ||(FileAttribs[i].typ == BT_else)) continue;
440      if (FileAttribs[i].typ == BT_break /*typ*/)
441      {
442        while (/*typ*/ BT_break != currentVoice->typ && (voice > i))
443        {
444          exitVoice();
445        }
446        currentVoice->fptr = 0L;
447        yylineno = currentVoice->v_lineno;
448        return 0;
449      }
450      else return 1;
451    }
452  }
453  return 1;
454}
455
456/*2
457* leave a voice: kill local variables
458* setup everything from the previous level (via Exit)
459*/
460int exitVoice()
461{
462  if (voice <= 0)   m2_end(0);
463  //printf("exitVoice %d, typ %d\n",voice,FileAttribs[voice].typ);
464  if (FileAttribs[voice].typ==BT_if)
465  {
466    ifswitch[voice-1]=2;
467  }
468  else
469  {
470    ifswitch[voice-1]=0;
471    //if ((FileAttribs[voice].typ==BT_proc)
472    //||(FileAttribs[voice].typ==BT_example)
473    //||(FileAttribs[voice].typ==0))
474    //{
475    //  killlocals(myynest);
476    //  printf("killlocals %d\n",myynest);
477    //}
478  }
479  if (inputswitch == -1)
480  {
481    fclose(yyin);
482  }
483  else if (inputswitch > 0)
484  {
485    if (FileAttribs[voice].filename!=NULL)
486    {
487      FreeL((ADDRESS)FileAttribs[voice].filename);
488      FileAttribs[voice].filename=NULL;
489    }
490    if (FileAttribs[voice].buffer!=NULL)
491    {
492      FreeL((ADDRESS)FileAttribs[voice].buffer);
493      FileAttribs[voice].buffer=NULL;
494    }
495  }
496  currentVoice = &FileAttribs[--voice];
497  return currentVoice->Exit();
498}
499
500int readbuf(char* buf, int l)
501{
502  char *s;
503  char * t = buf;
504  int i = 0;
505  long fl = currentVoice->fptr;
506  if (fl == -1L)
507  {
508    t[0] = '\0';
509    exitVoice();
510    return 0;
511  }
512
513  s = currentVoice->buffer + fl;
514  while (l > 0)
515  {
516    fl++;
517    i++;
518    l--;
519    *t++ = *s;
520    if (*s == '\n')
521    {
522      *t = '\0';
523      if ((si_echo > voice) || (inputswitch == 0) || (traceit&TRACE_SHOW_LINE)
524      || (traceit&TRACE_SHOW_LINE1))
525      {
526        if (currentVoice->filename==NULL)
527          Print("(none) %3d%c ",yylineno,prompt_char);
528        else if (VoiceType()!=BT_example)
529          Print("%s %3d%c ",currentVoice->filename,yylineno,prompt_char);
530        prompt_char = '.';
531      }
532      if (*(s+1) == '\0')
533      {
534        currentVoice->fptr = -1;
535        FreeL((ADDRESS)(currentVoice->buffer));
536        currentVoice->buffer=NULL;
537        FileAttribs[voice].buffer = NULL;
538        exitVoice();
539      }
540      else
541        currentVoice->fptr = fl;
542      return i;
543    }
544    else if (*s == '\0')
545    {
546      if ((si_echo > voice) || (inputswitch == 0) || (traceit&TRACE_SHOW_LINE)
547      || (traceit&TRACE_SHOW_LINE1))
548      {
549        if (currentVoice->filename==NULL)
550          Print("(none) %3d%c ",yylineno,prompt_char);
551        else
552          Print("%s %3d%c ",currentVoice->filename,yylineno,prompt_char);
553        prompt_char = '.';
554      }
555      currentVoice->fptr = -1;
556      FreeL((ADDRESS)(currentVoice->buffer));
557      currentVoice->buffer = NULL;
558      exitVoice();
559      return i-1;
560    }
561    s++;
562  }
563  currentVoice->fptr = fl;
564  return i;
565}
566
567/*2
568* init all data structures
569*/
570void I_FEbase(void)
571{
572  currentVoice = FileAttribs[0].VFile("STDIN");
573}
574
575static char * feBufferStart;
576  /* only used in StringSet(S)/StringAppend(S)*/
577char * StringAppend(char *fmt, ...)
578{
579  va_list ap;
580  char *s = feBufferStart; /*feBuffer + strlen(feBuffer);*/
581  int more;
582  va_start(ap, fmt);
583  if ((more=feBufferStart-feBuffer+strlen(fmt)+100)>feBufferLength)
584  {
585    more = ((more + (4*1024-1))/(4*1024))*(4*1024);
586    int l=s-feBuffer;
587    feBuffer=(char *)ReAlloc((ADDRESS)feBuffer,feBufferLength,
588                                                     more);
589    feBufferLength=more;
590    s=feBuffer+l;
591#ifndef BSD_SPRINTF
592    feBufferStart=s;
593#endif
594  }
595#ifdef BSD_SPRINTF
596  vsprintf(s, fmt, ap);
597  while (*s!='\0') s++;
598  feBufferStart =s;
599#else
600  feBufferStart += vsprintf(s, fmt, ap);
601#endif
602  va_end(ap);
603  return feBuffer;
604}
605
606char * StringAppendS(char *st)
607{
608  /* feBufferStart is feBuffer + strlen(feBuffer);*/
609  int more,l;
610  int ll=feBufferStart-feBuffer;
611  if ((more=ll+2+(l=strlen(st)))>feBufferLength)
612  {
613    more = ((more + (4*1024-1))/(4*1024))*(4*1024);
614    feBuffer=(char *)ReAlloc((ADDRESS)feBuffer,feBufferLength,
615                                                     more);
616    feBufferLength=more;
617    feBufferStart=feBuffer+ll;
618  }
619  strcat(feBufferStart, st);
620  feBufferStart +=l;
621  return feBuffer;
622}
623
624char * StringSet(char *fmt, ...)
625{
626  va_list ap;
627  char *s = feBuffer;
628  va_start(ap, fmt);
629#ifdef BSD_SPRINTF
630  vsprintf(s, fmt, ap);
631  while (*s!='\0') s++;
632  feBufferStart = s;
633#else
634  feBufferStart = feBuffer + vsprintf(s, fmt, ap);
635#endif
636  va_end(ap);
637  return feBuffer;
638}
639
640char * StringSetS(char *st)
641{
642  int more,l;
643  if ((l=strlen(st))>feBufferLength)
644  {
645    more = ((l + (4*1024-1))/(4*1024))*(4*1024);
646    feBuffer=(char *)ReAlloc((ADDRESS)feBuffer,feBufferLength,
647                                                     more);
648    feBufferLength=more;
649  }
650  strcpy(feBuffer,st);
651  feBufferStart=feBuffer+l;
652  return feBuffer;
653}
654
655void PrintTCLS(char c, char *s)
656{
657#ifndef macintosh
658  int l=strlen(s);
659  if (l>0) PrintTCL(c,l,s);
660#endif
661}
662
663void WerrorS(char *s)
664{
665#ifdef HAVE_MPSR
666  if (feBatch)
667  {
668    if (feErrors==NULL)
669    {
670      feErrors=(char *)Alloc(256);
671      feErrorsLen=256;
672      strcpy(feErrors,s);
673    }
674    else
675    {
676      if (((int)(strlen(s)+strlen(feErrors)))>=feErrorsLen)
677      {
678        feErrors=(char *)ReAlloc(feErrors,feErrorsLen,feErrorsLen+256);
679        feErrorsLen+=256;
680      }
681      strcat(feErrors,s);
682    }
683    strcat(feErrors,"\n");
684  }
685  else
686#endif
687  {
688#ifdef HAVE_TCL
689    if (tclmode)
690    {
691      //PrintTCLS('E',s);
692      //PrintTCLS('E',"\n");
693      PrintTCLS('N',s);
694      PrintTCLS('N',"\n");
695    }
696    else
697#endif
698    {
699      fwrite("   ? ",1,5,stderr);
700      fwrite(s,1,strlen(s),stderr);
701      fwrite("\n",1,1,stderr);
702      fflush(stderr);
703      if (feProt&PROT_O)
704      {
705        fwrite("   ? ",1,5,feProtFile);
706        fwrite(s,1,strlen(s),feProtFile);
707        fwrite("\n",1,1,feProtFile);
708      }
709    }
710  }
711  errorreported = TRUE;
712}
713
714extern "C" {
715void Werror(char *fmt, ...)
716{
717  va_list ap;
718  va_start(ap, fmt);
719  char *s=(char *)Alloc(256);
720  vsprintf(s, fmt, ap);
721  WerrorS(s);
722  Free(s,256);
723  va_end(ap);
724}
725}
726
727void WarnS(char *s)
728{
729#ifdef HAVE_TCL
730  if (tclmode)
731  {
732    PrintTCLS('W',s);
733  }
734  else
735#endif
736  {
737    fwrite("// ** ",1,6,stdout);
738    fwrite(s,1,strlen(s),stdout);
739    fwrite("\n",1,1,stdout);
740    fflush(stdout);
741    if (feProt&PROT_O)
742    {
743      fwrite("// ** ",1,6,feProtFile);
744      fwrite(s,1,strlen(s),feProtFile);
745      fwrite("\n",1,1,feProtFile);
746    }
747  }
748}
749
750void Warn(char *fmt, ...)
751{
752  va_list ap;
753  va_start(ap, fmt);
754  char *s=(char *)Alloc(256);
755  vsprintf(s, fmt, ap);
756  WarnS(s);
757  Free(s,256);
758  va_end(ap);
759}
760
761#ifdef macintosh
762static  int lines = 0;
763static  int cols = 0;
764void mwrite(uchar c)
765{
766  if (c == '\n')
767  {
768    cols = 0;
769    if (lines == pagelength)
770    {
771      lines = 0;
772      fePause();
773    }
774    else
775    {
776      lines++;
777      fePutChar(c);
778    }
779  }
780  else
781  {
782    fePutChar(c);
783    cols++;
784    if (cols == colmax)
785    {
786//      cols = 0;   //will be done by mwrite('\n');
787      mwrite('\n');
788    }
789  }
790}
791#endif
792
793void PrintS(char *s)
794{
795#ifdef macintosh
796  char c;
797  while ('\0' != (c = *s++))
798  {
799    mwrite(c);
800  }
801#else
802#ifdef HAVE_TCL
803  if (tclmode)
804  {
805    PrintTCLS('N',s);
806  }
807  else
808#endif
809  {
810    fwrite(s,1,strlen(s),stdout);
811    fflush(stdout);
812    if (feProt&PROT_O)
813    {
814      fwrite(s,1,strlen(s),feProtFile);
815    }
816  }
817#endif
818}
819
820void Print(char *fmt, ...)
821{
822  va_list ap;
823  va_start(ap, fmt);
824#ifdef HAVE_TCL
825  if(tclmode)
826#endif
827#if (defined(HAVE_TCL) || defined(macintosh))
828  {
829    char *s=(char *)Alloc(strlen(fmt)+256);
830    vsprintf(s,fmt, ap);
831#ifdef HAVE_TCL
832    PrintTCLS('N',s);
833#endif
834#ifdef macintosh
835  char c;
836  while ('\0' != (c = *s++))
837  {
838    mwrite(c);
839  }
840  if (feProt&PROT_O)
841  {
842    vfprintf(feProtFile,fmt,ap);
843  }
844#endif
845  }
846#endif
847#if !defined(macintosh) || defined(HAVE_TCL)
848#ifdef HAVE_TCL
849  else
850#endif
851  {
852    vfprintf(stdout, fmt, ap);
853    fflush(stdout);
854    if (feProt&PROT_O)
855    {
856      vfprintf(feProtFile,fmt,ap);
857    }
858  }
859#endif
860  va_end(ap);
861}
862
863void PrintLn()
864{
865  PrintS("\n");
866}
867
868void fePause()
869{
870  uchar c;
871  mflush();
872#ifndef macintosh
873  fputs("pause>",stderr);
874#else
875  fputs("pause>\n",stderr);
876#endif
877  c = fgetc(stdin);
878  if (((c == '\003') || (c == 'C')) || (c == 'c'))
879  {
880    m2_end(1);
881  }
882}
883
884/*2
885* print input lines (si_echo or TRACE), set prompt_char
886*/
887void showInput(void)
888{
889  if ((inputswitch <= 0) || (traceit&TRACE_SHOW_LINE)
890  || (traceit&TRACE_SHOW_LINE1))
891  {
892    if ((si_echo > voice) || (inputswitch == 0) || (traceit&TRACE_SHOW_LINE)
893    || (traceit&TRACE_SHOW_LINE1))
894    {
895#ifdef HAVE_TCL
896      if (tclmode)
897      {
898         PrintTCL('P',(prompt_char=='>')? 0 : 1,NULL);
899      }
900      else
901#endif
902      if (BVERBOSE(V_PROMPT))
903      {
904        if (inputswitch == 0)
905        {
906          fe_promptstr[0]=prompt_char;
907#ifndef HAVE_READLINE
908          PrintS(fe_promptstr);
909#endif
910        }
911        else
912        {
913          if (currentVoice->filename==NULL)
914            Print("(none) %3d%c ",yylineno,prompt_char);
915          else
916            Print("%s %3d%c ",currentVoice->filename,yylineno,prompt_char);
917        }
918        prompt_char = '.';
919        mflush();
920      }
921#ifdef macintosh
922      cols = 0;
923#endif
924    }
925  }
926}
927
928void monitor(char* s, int mode)
929{
930  if (feProt)
931  {
932    fclose(feProtFile);
933  }
934  if ((s!=NULL) && (*s!='\0'))
935  {
936    feProtFile = fopen(s,"w");
937    if (feProtFile==NULL)
938    {
939      Werror("cannot open %s",s);
940    }
941    else
942      feProt = (BOOLEAN)mode;
943  }
944}
945
946
947char* eati(char *s, int *i)
948{
949  int l=0;
950
951  if    (*s >= '0' && *s <= '9')
952  {
953    *i = 0;
954    while (*s >= '0' && *s <= '9')
955    {
956      *i *= 10;
957      *i += *s++ - '0';
958      l++;
959      if ((l>MAX_INT_LEN)||((*i) <0))
960      {
961        s-=l;
962        Werror("`%s` greater than %d(max. integer representation)",
963                s,INT_MAX);
964        return s;
965      }
966    }
967  }
968  else *i = 1;
969  return s;
970}
971
Note: See TracBrowser for help on using the repository browser.