/*    IPREQ SMTP Reqdir/Reqfil Server for TCP/IP    */
/*    v0.2c  930208                                 */
/*    by Mats Petersson                             */


#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <conio.h>
#include <time.h>
#include <dos.h>
#include <bios.h>
#include <dir.h>
#include <string.h>
#include <process.h>
#include <cursor.c>

FILE* tempfile;
FILE* outfile;
FILE* reqdatf;
char fstr[80];
char commandstr[80];
char roepnaam[80];
char tzstr[80];
char basedir[80],aan[80],dir[80],fulldir[80];
char maildir[80],mqueuedir[80];
char bidstr[10];
char outfname[80];
char fname[MAXFILE];
char direnv[80];
int direnvset;
int bid;
int cnt;

struct ffblk ffblk;

void interrupt (*oldhandler)(void);

char *version = "0.2c";

logo()
{
    printf("IPREQ SMTP Reqdir/Reqfil Server v%s\n\nPress <ESC> to quit\n",version);
}


extract(char *s, int p)
{
char *i;

    strcpy(s,&fstr[p]);
    while((s[0] == '\x20') || (s[0] == '\x09')) strcpy(s,&s[1]);

    while( (i = strrchr(s,'\x20')) || (i = strrchr(s,'\x09'))) i[0] = 0;

    if( (i != 0)  || (i = strrchr(s,'\n')) )
         i[0] = 0;
}

getdata(FILE* fp)
{
         strcpy(aan,"");
         strcpy(dir,"");
         while(fgets(fstr,80,fp))
         {
              if( (strlen(fstr) == 1) && (aan[0] != 0) ) return;
              if(! strnicmp(fstr,"From: ",6)) extract(aan,5);
              if(! strnicmp(fstr,"Subject: ",9)) extract(dir,8);
              if(! strnicmp(fstr,"Reply-To: ",10)) extract(aan,9);
         }
}

makehdr(char *ftype, char *reqtype)
{
struct tm *tbl;
time_t t;
char datestr[80];
static char *wday[] = {"Sun","Mon", "Tue", "Wed", "Thu", "Fri",
                "Sat"};
static char *mon[] = {"Jan", "Feb", "Mar", "Apr", "May", "Jun",
              "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"};

         reqdatf = fopen("ipreq.seq","rt");
         if(fscanf(reqdatf,"%s",bidstr) > 0) bid = atoi(bidstr);
         else
         {
             bid = 0;
             strcpy(bidstr,"0");
         }
         fclose(reqdatf);

         time(&t);
         tbl = localtime(&t);
         sprintf(datestr,"%s, %d %s %d %02d:%02d:%02d %s",
            wday[tbl->tm_wday],tbl->tm_mday,mon[tbl->tm_mon],tbl->tm_year,
            tbl->tm_hour,tbl->tm_min,tbl->tm_sec,strupr(tzstr));

         sprintf(outfname,"%s\\%s.txt",mqueuedir,bidstr);
         outfile = fopen(outfname,"wt");

         fprintf(outfile,"Date: %s\n",datestr);
         fprintf(outfile,"Message-Id: <%s-%s@%s>\n",bidstr,reqtype,roepnaam);
         fprintf(outfile,"From: %s@%s\n",reqtype,roepnaam);
         fprintf(outfile,"To: %s\n",aan);
         fprintf(outfile,"Subject: %s %s\n",ftype,strupr(dir));
         fprintf(outfile,"X-Mailer: IPREQ SMTP Reqdir/Reqfil server v%s\n",version);
         fprintf(outfile,"\n");
}


makewrkfile(char *reqtype)
{
    sprintf(outfname,"%s\\%s.wrk",mqueuedir,bidstr);
    outfile = fopen(outfname,"wt");

    fprintf(outfile,"%s\n",roepnaam);
    fprintf(outfile,"%s@%s\n",reqtype,roepnaam);
    fprintf(outfile,"%s\n",aan);
    fclose(outfile);

    bid += 2;
    sprintf(bidstr,"%u\n",bid);
    reqdatf = fopen("ipreq.seq","wt");
    fputs(bidstr,reqdatf);
    fclose(reqdatf);
}

reqdir(FILE* rdfile)
{
int nosuchdir;

    while(1)
    {
         nosuchdir = 0;
         getdata(rdfile);

         if((feof(rdfile)) && (aan[0] == 0))
         {
              fclose(rdfile);
              sprintf(fstr,"%s\\reqdir.txt",maildir);
              remove(fstr);
              remove("temp.$$$");
              return;
         }

         if(dir[0] == '\\') strcpy(dir,&dir[1]);
         if(! strstr(dir,"*.")) strcat(dir,"\\*.*");

         sprintf(fulldir,"%s\\%s",basedir,dir);
         makehdr("Directory","reqdir");

         if(findfirst(fulldir,&ffblk,FA_DIREC))
              nosuchdir = 1;

         if (! nosuchdir)
         {
              sprintf(commandstr,"dir %s > temp.$$$",fulldir);
              system(commandstr);
              tempfile = fopen("temp.$$$","rt");

              while(fgets(fstr,80,tempfile))
                 if((fstr[0] != '\x20') && (fstr[0] != '.')
                 && (fstr[0] != '\x0A')) fputs(fstr,outfile);

              fclose(tempfile);
         }
         else
         {
              fprintf(outfile,"Sorry, I can't find %s\n\n",strupr(dir));
              fprintf(outfile,"73's de IPREQ");
         }
         fclose(outfile);
         makewrkfile("reqdir");
    }
}


makecor(FILE* fp)
{
int result;
char *p,errfname[12],corfname[12];
FILE* errfile;
FILE* corfile;

    sprintf(fulldir,"%s\\%s",basedir,dir);
    fnsplit(fulldir,NULL,NULL,fname,NULL);

    (strrchr(fulldir,'\\')+1)[0] = 0;

    sprintf(errfname,"%s.err",fname);
    errfile = fopen(errfname,"wt");

    do
    {
         fgets(fstr,80,fp);
         fputs(fstr,errfile);
         if((! strnicmp(fstr,"From ",5)) || (feof(fp)))
         {
              fclose(errfile);
              remove(errfname);
              return;
         }
    } while(! strstr(fstr," stop_text."));

    fclose(errfile);

    result = spawnlp(P_WAIT, "7plus.exe", "",
                    errfname, fulldir,NULL);
    remove(errfname);

    if(! result)
    {
         sprintf(corfname,"%s.cor",fname);
         strcpy(dir,strupr(corfname));
         makehdr("Correction file","reqfil");

         corfile = fopen(corfname,"rt");
         while(fgets(fstr,80,corfile)) fputs(fstr,outfile);
         fclose(corfile);
         fclose(outfile);
         remove(corfname);
    }
    else
    {
         strcpy(dir,"Error");
         makehdr("Correction","reqfil");

         fprintf(outfile,"Error in correction request\n");
         fprintf(outfile,"Either wrong directory or bad filename\n\n");
         fprintf(outfile,"73's de IPREQ");
         fclose(outfile);
    }
    makewrkfile("reqfil");
    clrscr();
    logo();
}


splitfile()
{
    tempfile = fopen("temp.$$$","rt");

    while(fgets(fstr,80,tempfile))
    {
         if(strstr(fstr," go_7+"))
         {
              makehdr("File","reqfil");
              fputs(fstr,outfile);
              do{
                   fgets(fstr,80,tempfile);
                   fputs(fstr,outfile);
              } while(! strstr(fstr," stop_7+"));
              fclose(outfile);
              makewrkfile("reqfil");
         }
    }
    fclose(tempfile);
}

reqfil(FILE* rffile)
{
FILE* reqfile;
unsigned char val1,val2;
char sevenfname[12];
int result, i;
int nosuchfile;

    while(1)
    {
         getdata(rffile);

         if((feof(rffile)) && (aan[0] == 0))
         {
              fclose(rffile);
              sprintf(fstr,"%s\\reqfil.txt",maildir);
              remove(fstr);
              remove("temp.$$$");
              return;
         }

         if(dir[0] == '\\') strcpy(dir,&dir[1]);

         if(strstr(strlwr(dir),".err"))
         {
              makecor(rffile);
              goto next;
         }

         nosuchfile = 0;


         sprintf(fulldir,"%s\\%s",basedir,dir);

         if(findfirst(fulldir,&ffblk,0))
              nosuchfile = 1;

         if (! nosuchfile)
         {
              reqfile = fopen(fulldir,"rt");           /* BINARY FILE check */
              val1 = val2 = 0;
              for(i = 0;i<300;i++){
                   fread(&val1,1,1,reqfile);
                   if(val1 > val2) val2 = val1;
              }
              fclose(reqfile);

              if(val2 > 127)
              {
                    result = spawnlp(P_WAIT, "7plus.exe", "",
                                    fulldir, NULL);

                    fnsplit(fulldir,NULL,NULL,fname,NULL);
                    sprintf(sevenfname,"%s.p??",fname);

                    if(! findfirst(sevenfname,&ffblk,0))
                    {
                        sprintf(commandstr,"copy %s temp.$$$ >NUL:",sevenfname);
                        system(commandstr);
                        sprintf(commandstr,"del %s",sevenfname);
                        system(commandstr);
                    }
                    else
                    {
                        strcat(fname,".7pl");
                        sprintf(commandstr,"copy %s temp.$$$ >NUL:",fname);
                        system(commandstr);
                        sprintf(commandstr,"del %s",fname);
                        system(commandstr);
                    }
                    splitfile();
                    clrscr();
                    logo();
              }
              else
              {
                   makehdr("File","reqfil");
                   sprintf(commandstr,"copy %s temp.$$$ >NUL:",fulldir);
                   system(commandstr);
                   tempfile = fopen("temp.$$$","rt");

                   while(fgets(fstr,80,tempfile))
                        fputs(fstr,outfile);

                   fclose(tempfile);
                   fclose(outfile);
                   makewrkfile("reqfil");
              }
         }
         else
         {
              makehdr("File","reqfil");
              fprintf(outfile,"Sorry, I can't find %s\n\n",strupr(dir));
              fprintf(outfile,"73's de IPREQ");
              fclose(outfile);
              makewrkfile("reqfil");
         }
    next:
    ;
    }
}

void interrupt int1c_handler(void)
{
       cnt++;
       oldhandler();
}

check()
{
FILE* reqdirf;
FILE* reqfilf;

    sprintf(fstr,"%s\\reqdir.txt",maildir);
    if(reqdirf = fopen(fstr,"rt")) reqdir(reqdirf);
    sprintf(fstr,"%s\\reqfil.txt",maildir);
    if(reqfilf = fopen(fstr,"rt")) reqfil(reqfilf);

    cnt = 0;
}


err(char *s)
{
    printf("Error: %s\n",s);
    delay(2000);
    exit(1);
}

dircheck(char *s)
{
int i;
char errstr[80];

    if(s[(i = strlen(s)-1)] == '\\') s[i] = 0;

    if(findfirst(s,&ffblk,FA_DIREC))
    {
         sprintf(errstr,"Invalid directory %s in IPREQ.CNF",s);
         err(errstr);
    }
}

init()
{
FILE* cfgfile;
char *p;
union REGS regs;


    if(! searchpath("7plus.exe"))
    {
         err("file 7PLUS.EXE not in DOS PATH");
         delay(2000);
         exit(1);
    }

    if(! (cfgfile = fopen("ipreq.cnf","rt")))
    {
         err("missing file IPREQ.CNF");
         delay(2000);
         exit(1);
    }

    roepnaam[0] = basedir[0] = tzstr[0] = maildir[0] = mqueuedir[0] = 0;

    while(fgets(fstr,80,cfgfile))
    {
         if(! strnicmp(strlwr(fstr),"call ",5)) extract(roepnaam,4);
         if(! strnicmp(strlwr(fstr),"basedir ",8)) extract(basedir,7);
         if(! strnicmp(strlwr(fstr),"tzone ",6)) extract(tzstr,5);
         if(! strnicmp(strlwr(fstr),"mail ",5)) extract(maildir,4);
         if(! strnicmp(strlwr(fstr),"mqueue ",7)) extract(mqueuedir,6);
    }
    fclose(cfgfile);

    if(! roepnaam[0])  err("missing parameter 'call' in IPREQ.CNF");
    if(! basedir[0])   err("missing parameter 'basedir' in IPREQ.CNF");
    if(! tzstr[0])     err("missing parameter 'tzone' in IPREQ.CNF");
    if(! maildir[0])   err("missing parameter 'mail' in IPREQ.CNF");
    if(! mqueuedir[0]) err("missing parameter 'mqueue' in IPREQ.CNF");

    dircheck(basedir);
    dircheck(maildir);
    dircheck(mqueuedir);

    if(!(reqdatf = fopen("ipreq.seq","rt")))
    {
         reqdatf = fopen("ipreq.seq","wt");
         fclose(reqdatf);
    }
    else fclose(reqdatf);

    direnvset = 0;
    if(p = getenv("DIRCMD"))
    {
         strcpy(direnv,p);
         sprintf(direnv,"DIRCMD=%s",direnv);
         putenv("DIRCMD=");
         direnvset = 1;
    }
/*
    regs.h.ah = 0xDE;
    regs.h.al = 0x0F;
    int86(0x15,&regs,&regs);
*/
    clrscr();
    HideCur();
    logo();
}

main(int argc,char **argv)
{
int ch;
int time_int;

    if(argc >= 2)
    {
         init();

         check();

         time_int = atoi(argv[1]) * 18;

         if(time_int > 0)
         {
              cnt = 0;

              oldhandler = getvect(0x1c);
              setvect(0x1c,int1c_handler);

              do{
                 if(cnt == (time_int)) check();
                 if(bioskey(1)) ch = bioskey(0) & 0xff;
              } while(ch != 27);

              setvect(0x1c,oldhandler);
         }
         if(direnvset) putenv(direnv);
         ShowCur();
    }
    else
    {
         printf("IPREQ SMTP Reqdir/Reqfil Server v%s\n",version);
         printf("usage: ipreq <interval>\n");
    }
}