Back to index

wims  3.65+svn20090927
msg2wims.c
Go to the documentation of this file.
00001 /*    Copyright (C) 1998-2003 XIAO, Gang of Universite de Nice - Sophia Antipolis
00002  *
00003  *  This program is free software; you can redistribute it and/or modify
00004  *  it under the terms of the GNU General Public License as published by
00005  *  the Free Software Foundation; either version 2 of the License, or
00006  *  (at your option) any later version.
00007  *
00008  *  This program is distributed in the hope that it will be useful,
00009  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
00010  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00011  *  GNU General Public License for more details.
00012  *
00013  *  You should have received a copy of the GNU General Public License
00014  *  along with this program; if not, write to the Free Software
00015  *  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
00016  */
00017 
00018  /* This program translates oef format exercises into wims internal data format. */
00019 
00020 #define MAX_TITLEN  40
00021 #define MAX_PROMPTLEN 32
00022 #define MAX_PARM    6
00023 #define MAX_PARAM   256
00024 #define MAX_DEFINE  1024
00025 #define elsechar '\001'
00026 #define endifchar '\002'
00027 #define nextchar '\003'
00028 #define whilechar '\004'
00029 #define string_modify string_modify2
00030 
00031 #include "../Lib/libwims.h"
00032 
00033 struct {
00034     char *name;
00035     int serial;
00036     int type;
00037 } param[MAX_PARAM+32];
00038 
00039 char *inbuf;
00040 FILE *inf, *outf;
00041 int inlen=0,outlen=0;
00042 int primserial=1;
00043 char *primitive_dir="docu/primitives";
00044 
00045 void internal_warn(char *p)
00046 {}
00047 
00048 #include "lines.c"
00049 #include "compare.c"
00050 #include "def.c"
00051 #include "doc.c"
00052 
00053 void get_inf(char *fname)
00054 {
00055     int i,l;
00056     inf=fopen(fname,"r");
00057     if(inf==NULL) bailout(0,0,"");
00058     fseek(inf,0,SEEK_END); l=ftell(inf); fseek(inf,0,SEEK_SET);
00059     if(l<=0) bailout(0,0,"");
00060     inbuf=xmalloc(l+16);
00061     l=fread(inbuf,1,l,inf); 
00062     if(l<=0) bailout(0,0,"error opening input file");
00063     else inbuf[l]=0;
00064     fclose(inf); inlen=l;
00065     for(i=0;i<l;i++)
00066       if(inbuf[i]==elsechar || inbuf[i]==endifchar ||
00067         inbuf[i]==nextchar || inbuf[i]==whilechar) inbuf[i]=' ';
00068 }
00069 
00070 void open_outf(char *fname)
00071 {
00072     outf=fopen(fname,"w");
00073     if(outf==NULL) bailout(inlen,0,"error opening output file");
00074 }
00075 
00076 void process_formula(char *p)
00077 {
00078     char *p3, bf[MAX_LINELEN+1];
00079     
00080     if(strlen(p)>=MAX_LINELEN)
00081       bailout(inlen,0,"formula too long");
00082     while((p3=strstr(p,"&lt;"))!=NULL) memmove(p3," <  ",4);
00083     while((p3=strstr(p,"&gt;"))!=NULL) memmove(p3," >  ",4);
00084     for(p3=strchr(p,'\n'); p3!=NULL; p3=strchr(p3,'\n')) *p3=' ';
00085     snprintf(bf,sizeof(bf),"%s",p); 
00086     if(strchr(bf,'\\')==NULL && strchr(bf,'}')==NULL && strlen(bf)>2) {
00087        for(p3=strstr(bf,".."); p3!=NULL; p3=strstr(p3,"..")) {
00088            if(*(p3+2)=='.' || *(p3+2)==',') {
00089               do p3++; while(*p3=='.'); continue;
00090            }
00091            *p3=','; *(p3+1)=' ';
00092        }
00093     }
00094     fprintf(outf,"\n!insmath %s\n",bf);
00095 }
00096 
00097 int main(int argc, char *argv[])
00098 {
00099     char *p, *p1, *p2, *tend;
00100 
00101     substitute=substit;
00102     if(argc==2 && strcmp(argv[1],"table")==0) {
00103 /*     if(verify_order(directives, dir_no, sizeof(directives[0]))) return -1;
00104 */     if(verify_order(specialfn, specialfn_no, sizeof(specialfn[0]))) return -1;
00105        puts("Table orders OK."); return 0;
00106     }
00107     p=getenv("w_msg2wims_primitives"); if(p!=NULL) {
00108        snprintf(primbuf,sizeof(primbuf),"%s",p);
00109        for(p=primbuf; *p; p++) if(!isalnum(*p)) *p=' ';
00110        p=find_word_start(primbuf);
00111        for(primcnt=0; primcnt<256 && *p; primcnt++, p=find_word_start(p1)) {
00112            p1=find_word_end(p); if(*p1) *p1++=0;
00113            primitive[primcnt]=p;
00114        }
00115        if(primcnt>0) qsort(primitive,primcnt,sizeof(primitive[0]),_scmp);
00116     }
00117     if(argc<3) bailout(0,0,"missing file names");
00118     p1=argv[1]; p2=argv[2];
00119     get_inf(p1); open_outf(p2);
00120     for(p=tend=inbuf;*p;p++) {
00121        switch(*p) {
00122            case '$': fputs("&#36;",outf); break;
00123            case '!': fputs("&#33;",outf); break;
00124            case ':': fputs("&#58;",outf); break;
00125            
00126            case elsechar: {
00127               if(primcnt>0) fputs("\n!else\n",outf);
00128               else fputc(*p,outf);
00129               break;
00130            }
00131            case endifchar: {
00132               if(primcnt>0) fputs("\n!endif\n",outf);
00133               else fputc(*p,outf);
00134               break;
00135            }
00136            case nextchar: {
00137               if(primcnt>0) fputs("\n!next\n",outf);
00138               else fputc(*p,outf);
00139               break;
00140            }
00141            case whilechar: {
00142               if(primcnt>0) fputs("\n!endwhile\n",outf);
00143               else fputc(*p,outf);
00144               break;
00145            }
00146            
00147            case '\n': {
00148               if(*(p+1)=='>') {
00149                   pre: p++; fputs("\n<i><small><pre wrap>",outf);
00150                   for(p1=strchr(p,'\n'); p1!=NULL && *(p1+1)=='>';
00151                      p1=strchr(++p1,'\n'));
00152                   if(p1!=NULL) *p1++=0; else p1=p+strlen(p);
00153                   for(p2=p;*p2;p2++) {
00154                      if(*p2!='<') fputc(*p2,outf);
00155                      else fputs("&lt;",outf);
00156                   }
00157                   fputs("</pre></small></i>\n",outf);
00158                   p=p1-1; break;
00159               }
00160               if(*(p+1)!='\n') {fputc(*p,outf);break;}
00161               p++; fputs("\n<p>\n",outf);
00162               while(*(p+1)=='\n') p++;
00163               if(*(p+1)=='>') goto pre;
00164               break;
00165            }
00166            
00167            case '<': {
00168               char *p2;
00169               if(tend>p || (!isalpha(*(p+1)) && *(p+1)!='!')) {
00170                   fputc(*p,outf); break;
00171               }
00172               p2=find_tag_end(p);
00173               if(!*p2) {error("open_tag"); p2--;}
00174               tend=p2;
00175               fputc(*p, outf); break;
00176            }
00177            
00178            case '\\': {
00179               char *pe;
00180               p++; 
00181               if(isalpha(*p)) {
00182                   if(primcnt>0) {
00183                      pe=doccheck(p);
00184                      if(pe>p) {p=pe-1; break;}
00185                   }
00186                   for(pe=p;isalnum(*pe) || *pe=='_';pe++);
00187                   if(*pe=='[') {
00188                      char *pv=find_matching(pe+1,']');
00189                      if(pv!=NULL) {
00190                          char c=*p;
00191                          memmove(p,p+1,pv-p); *pv=')';
00192                          fprintf(outf,"$(m_%c",c); p--; break;
00193                      }
00194                   }
00195                   fprintf(outf,"$m_%c",*p); break;
00196               }
00197               switch(*p) {
00198                   case '\\': fputc(*p,outf); break;
00199                   case '{':
00200                   case '(': {
00201                      char *p2, *p3, c;
00202                      if(*p=='{') c='}'; else c=')';
00203                      p++; p2=find_matching(p,c);
00204                      if(c==')') p3=strstr(p,"\\)");
00205                      else p3=strstr(p,"\\}");
00206                      if((p2==NULL && p3!=NULL) ||
00207                         (p2!=NULL && p3!=NULL && p3<p2)) p2=p3+1;
00208                      if(p2==NULL) fputc(*p,outf);
00209                      else {
00210                          *p2=0; if(*(p2-1)=='\\') *(p2-1)=0;
00211                          process_formula(p); p=p2;
00212                      }
00213                      break;
00214                   }
00215                   default: fputc(*p,outf); break;
00216               }
00217               break;
00218            }
00219            
00220            default: fputc(*p,outf); break;
00221        }
00222     }
00223     fputc('\n',outf);
00224     outlen=ftell(outf);  fclose(outf); bailout(inlen,outlen,"");
00225     return 0;
00226 }
00227