🚀 go-pugleaf

RetroBBS NetNews Server

Inspired by RockSolid Light RIP Retro Guy

Article View: comp.sys.atari.st
Article #24778

Uemail source (10 of 12)

#24778
From: RDROYA01
Date: Thu, 05 Feb 1987 19:46
913 lines
34192 bytes
#       This is a shell archive.
#       Remove everything above and including the cut line.
#       Then run the rest of the file through sh.
#----cut here-----cut here-----cut here-----cut here----#
#!/bin/sh
# shar: Shell Archiver
#       Run the following text with /bin/sh to create:
#       cc.c
#       cc.ini
#       extmac.c
#       ueasm.s
#       xemacs.lnk
# This archive created: Tue Feb  3 18:04:08 1987
cat << \SHAR_EOF > cc.c
/* FILE:         cc.c
 * DATE:         27-Jan-1987
 *               Updated 07-01-1987 to allow wildcards and linking multiple
 *               files.
 *               Updated 27-01-1987 to allow assembling and/or compiling and
 *               to allow linking without compiling.
 * AUTHOR:       Robert Royar rdroya01@bitnet
 * SYSTEM:       Atari ST
 * COMPILER:     Alcyon v. 4.14
 * PURPOSE:      A simple minded compiler driver, no frills. (well, almost)
 * USAGE:        cc filename[s] (path must agree with cc.ini)
 *               the command line may contain wildcards as long as all
 *               source files are on the drive designated as the sdir in
 *               this file.  Using the link option will cause the linker to
 *               look for a command file on the source directory.  That link
 *               file should be named `foo.lnk' where `foo' is the name in
 *               the cc.ini file associated with the lnkfile value.  The
 *               link file should tell the linker to place the output on the
 *               source dir if the relocation program is to find the
 *               `foo.68k' file and successfully create a `foo.prg' file.
 *               Calling the program without a command line and with dolink=1
 *               will force it to try to link the file `linkfile.68k' and
 *               then call relmod.  Giving it a filename with an .s extent
 *               will skip the compiling and assemble the file.  Files with
 *               .s extents and .c extents may be mixed on a line.
 * DISTRIBUTION: Public Domain.  Do with it what you will.  Just leave
 *               the header intact.
 */
#include <stdio.h>
#include <osbind.h>
#include <ctype.h>
#include <errno.h>
 
unsigned long _STKSIZ = 16284;  /* keep 16K */
 
/* These are the defaults.  All of them can be over-ridden by values
 * in the cc.ini file if that file is on the default drive and directory.
 */
char sdir[81] = "e:\\"; /* where the source files are */
char include[81] = "d:\\stdlib.h\\"; /* include files */
char tdir[81] = "m:\\"; /* temporary files (all of them) */
char bin[81] = "c:\\bin\\";     /* compiler directory */
char symb[81] = "c:\\bin\\";    /* as68 symbols */
char floflag[12] = " ";         /* float ?      */
char delflag[12] = "1";         /* delete temporary files */
char lnkflag[12] = "0";         /* link file[s] if == "1" */
char warn[12] = " ";            /* make it -w to suppress warnings */
char syslib[81] = "c:\\bin\\";  /* drive to log for linker */
char lnk[81] = "out";           /* .68K and .lnk filename */
char fprg[81] = "out";          /* final output name */
char pname[81];
char command[81];
char source[81];
int temdrv;
char delfile[80];
int delete = 1;
int dolink = 0;
int doasm  = FALSE;
char path[128];
int exec;
int curdrv;
char author[30] = "Robert Royar";
 
main(argc,argv)
register int argc;
char *argv[];
{
        register char c, *ptr;
        register int argnum;
        char *index();
 
        argnum = 1;
        curdrv = (int)Dgetdrv(); /* 0 = A */
        Dgetpath(path,(1+curdrv)); /* 1 = A */
        if (access("cc.ini",4) != -1)
                if (!inivar())
                        exit(-1);
        if (argc == 1 && dolink == FALSE)
                {
                fprintf(stderr,"usage: %s filename[s]\n",argv[0]);
                exit(-1);
                }
        if (argc == 1)
                {
                exec = linkfil();
                goto out;
                }
        if (tdir[1] == ':')
                {
                c = (char)toupper(tdir[0]);
                temdrv = (int)(c - 'A');
                Dsetdrv(temdrv);        /* Log into temp drive */
                }
        if((exec=(int)Dsetpath(tdir))!=0)
                goto out;
        while(--argc)
                {
                strcpy(source,argv[argnum++]);
                if ((ptr=index(source,':'))!=NULL)
                        strcpy(source,++ptr);
                /* If the file has an .s extent, then assemble it.
                 * Check the source dir first.  If it's not there,
                 * check the temp dir.  Set the doasm flag to fit
                 * the outcome, or break if no file found.
                 */
                if ((ptr=index(source,'.'))!=NULL)
                        {
                        *ptr = '\0';    /* don't let the extension through */
                        /* delete any existing .o files */
                        sprintf(delfile,"%s%s.o",tdir,source);
                        if (access(delfile,4)==NULL)
                                unlink(delfile);
                        ++ptr;
                        if (*ptr != '\0')
                                {
                                *ptr = tolower(*ptr);
                                if (strcmp(ptr,"s")==NULL) /* assemb only */
                                        {
                                        sprintf(command,"%s%s.s",sdir,source);
                                        if ((exec=access(command,4)) == -1)
                                                {
                                                sprintf(command,"%s%s.s",
                                                       tdir,source);
                                                if ((exec=access(command,4))
                                                     == -1)
                                                        continue;
                                                else /* this is a tdir file */
                                                        doasm = FALSE;
                                                }
                                        else    /* this asm file is on sdir */
                                                doasm = TRUE;
                                        if ((exec=as())!=NULL)
                                                goto out;
                                        else
                                                continue;
                                        }
                                }
                        }
                /* delete any existing .o files */
                sprintf(delfile,"%s%s.o",tdir,source);
                if (access(delfile,4)==NULL)
                        unlink(delfile);
                doasm = FALSE;
                sprintf(command,"%s%s.c",sdir,source);
                if ((exec=access(command,4)) == -1)
                        break;
                if ((exec=cc())!=NULL)
                        break;
                }
        if (dolink && (exec == NULL))
                exec = linkfil();
out:    Dsetdrv(curdrv);
        Dsetpath(path);
        exit(exec);
}
 
cc()
{
        fprintf(stderr,"\nCompiling : %s%s.c\n",sdir,source);
        sprintf(&command[1],"-i %s %s%s.c %s%s.i ",
                include,sdir,source,tdir,source);
        command[0] = (char)strlen(&command[1]);
        sprintf(pname,"%sCP68.PRG",bin);
        if((exec=(int)Pexec(0,pname,command,0L))!=0)
                return(exec);
        sprintf(&command[1],"%s%s.i %s%s.1 %s%s.2 %s%s.3 %s %s",
                tdir,source,tdir,source,tdir,source,tdir,source,floflag,warn);
        command[0] = (char)strlen(&command[1]);
        sprintf(pname,"%sC068.PRG",bin);
        if((exec=(int)Pexec(0,pname,command,0L))!=0)
                return(exec);
        if (delete)
                {
                sprintf(command,"%s%s.i",tdir,source);
                unlink(command);
                }
        sprintf(&command[1],"%s%s.1 %s%s.2 %s%s.s",
        tdir,source,tdir,source,tdir,source);
        command[0] = (char)strlen(&command[1]);
        sprintf(pname,"%sC168.PRG",bin);
        if((exec=(int)Pexec(0,pname,command,0L))!=0)
                return(exec);
        sprintf(command,"%s%s.1",tdir,source);
        unlink(command);
        sprintf(command,"%s%s.2",tdir,source);
        unlink(command);
        exec = as();
        return(exec);
}
 
as()
{
        if (!doasm)
                {
                fprintf(stderr,"\nAssembling : %s%s.s\n",tdir,source);
                sprintf(&command[1],"-l -u -s %s %s%s.s",bin,tdir,source);
                }
        else
                {
                fprintf(stderr,"\nAssembling : %s%s.s\n",sdir,source);
                sprintf(&command[1],"-l -u -s %s %s%s.s",bin,sdir,source);
                }
        command[0] = (char)strlen(&command[1]);
        sprintf(pname,"%sAS68.PRG",bin);
        if((exec=(int)Pexec(0,pname,command,0L))!=0)
                return(exec);
        sprintf(command,"%s%s.o",tdir,source);
        if ((exec=access(command,4))==NULL)
                if (delete)
                        {
                        sprintf(command,"%s%s.s",tdir,source);
                        unlink(command);
                        }
        return(exec);
}
 
linkfil()
{
        register char c;
 
        if (syslib[1] == ':')
                {
                c = (char)toupper(syslib[0]);
                temdrv = (int) (c - 'A');
                Dsetdrv(temdrv);
                }
        else
                Dsetdrv(curdrv);
        Dsetpath(syslib);
        /* save disk write errors */
        sprintf(delfile,"%s%s.68k",sdir,lnk);
        if (access(delfile,4)==NULL)
                unlink(delfile);
        sprintf(delfile,"%s%s.prg",tdir,lnk);
        if (access(delfile,4)==NULL)
                unlink(delfile);
        sprintf(source,"%s%s",sdir,lnk);
        sprintf(pname,"%s%s",bin,"link68.ttp");
        sprintf(&command[1],"[co[%s.lnk]]",source);
        command[0] = (char)strlen(&command[1]);
        if ((exec=Pexec(0,pname,command,0L))!=0)
                return(exec);
        sprintf(source,"%s%s.68K",sdir,lnk);
        if ((exec=access(source,4))!=NULL)
                return(exec);
        sprintf(pname,"%s%s",tdir,lnk);
        sprintf(&command[1],"%s %s",source,pname);
        sprintf(pname,"%s%s",bin,"relmod.ttp");
        command[0] = (char)strlen(&command[1]);
        if ((exec=Pexec(0,pname,command,0L))!=0)
                return(exec);
        if ((exec=access(delfile,4))==NULL)
                if (delete)
                        unlink(source);
        return(exec);
}
 
inivar()
{
        FILE *freopen();
        char *gets(), *index();
        register char *ptr;
        static char line[81];
 
        if (freopen("cc.ini","r",stdin) != stdin)
                {
                fprintf(stderr,"cc: cannot open %scc.ini\n",path);
                return(0);
                }
        while (gets(line))
                {
                if ((ptr=index(line,' '))!=(char *)NULL)
                        *ptr = '\0';
                if ((ptr=index(line,'\t'))!=(char *)NULL)
                        *ptr = '\0';
                if ((ptr=index(line,'='))!=(char *)NULL)
                        *ptr = '\0';
                else
                        continue;
                ++ptr;
                if (strcmp(line,"source")==NULL)
                        strncpy(sdir,ptr,80);
                else if (strcmp(line,"include")==NULL)
                        strncpy(include,ptr,80);
                else if (strcmp(line,"temp")==NULL)
                        strncpy(tdir,ptr,80);
                else if (strcmp(line,"bin")==NULL)
                        strncpy(bin,ptr,80);
                else if (strcmp(line,"symb")==NULL)
                        strncpy(symb,ptr,80);
                else if (strcmp(line,"syslib")==NULL)
                        strncpy(syslib,ptr,80);
                else if (strcmp(line,"linkfile")==NULL)
                        strncpy(lnk,ptr,80);
                else if (strcmp(line,"float")==NULL)
                        strncpy(floflag,ptr,3);
                else if (strcmp(line,"warn")==NULL)
                        strncpy(warn,ptr,3);
                else if (strcmp(line,"delete")==NULL)
                        {
                        strncpy(delflag,ptr,2);
                        if (strncmp(delflag,"0",1)==NULL)
                                delete = FALSE;
                        }
                else if (strcmp(line,"dolink")==NULL)
                        {
                        strncpy(lnkflag,ptr,2);
                        if (strncmp(lnkflag,"1",1)==NULL)
                                dolink = TRUE;
                        }
                else if (feof(stdin))
                        break;
                }
        return(1);
}
SHAR_EOF
cat << \SHAR_EOF > cc.ini
/* cc.ini file for cc.prg and uemail.prg
 * the first ten are used by the cc or link commands. the aliases must
 * be spelled as they are here and must be in lower case. change the
 * path names to match your set-up.
 */
source=e:\                      /* C, lnk, and 68K files        */
include=d:\stdlib.h\            /* headers      */
temp=m:\                        /* temporary files, o files, and final prg  */
symb=c:\bin\                    /* as68symb.dat */
bin=c:\bin\                     /* compilers, assembler, linker, and loader */
syslib=c:\bin\                  /* library directory    */
linkfile=xemacs                 /* filename of link command file        */
float=                          /* flag for floating point -f, -e or nil*/
warn=
dolink=0                        /* if 1, call linker after compiling file[s] */
delete=1                        /* delete I, S, 68K files? 1==YES       */
/* the next two are used by shell */
shell=c:\util\pcommand.prg      /* shell program        */
xmodem=c:\comm\bmodem.ttp       /* xmodem program       */
cc=c:\bin\cc.prg
extmac=c:\uemail\extmac.prg
/* these are not used and if not needed, may be deleted */
home=c:\uemail\                 /* where it all began   */
root=c:\                        /* boot directory       */
assembly=d:\assembly.s\         /* assembly sources     */
etc=c:\util\                    /* utility programs     */
comm=c:\comm\                   /* communications       */
arc=c:\util\arc.ttp             /* arc cruncher         */
vt100=c:\comm\vt100.tos         /* small vt100 prog     */
/* set up colors the way I like. aliases and color names must be lower
 * case.  additional colors are grey, magenta, teal, green, yellow, and
 * white. cobalt is a deep blue. if colors are not aliased, you get
 * white on black as default.
 */
border=black                    /* color #0             */
cursor=red                      /* color #1             */
desk=cobalt                     /* color #2             */
letter=black                    /* color #3             */
/* function key bindings for uemail.ttp The F must be upper case */
F1=setmark                      /* sets the mark */
F2=listbuffers                  /* lists current buffers */
F3=filename                     /* change current filename */
F4=writeregion                  /* write text between point and mark to file */
F5=fileinsert                   /* insert file at point */
F6=fileread                     /* read file into current buffer */
F7=filevisit                    /* visit (find) a file */
F8=filewrite                    /* write out buffer to named file */
F9=filesave                     /* save current buffer if changed */
F10=quickexit                   /* save all changed buffers and exit */
/* Number pad bindings for uemail.ttp. the N must be upper case as must
 * the word NENTER.
 */
N(=backword                     /* backward word */
N)=forwword                     /* forward word */
N/=grtw                         /* globally remove trailing whitespace */
N*=retversion                   /* return current version to message line */
N7=gotobol                      /* goto beginning of line */
N8=gotoeol                      /* goto end of line */
N9=rettpa                       /* return usage to message line */
N-=pageback                     /* back by one text page (60 lines default) */
N4=backsent                     /* goto beginning of sentence */
N5=forwsent                     /* goto end of sentence */
N6=unkncom                      /* unknown */
N+=pageforw                     /* forward by one text page */
N1=gotbop                       /* goto beginning of paragraph (blank line) */
N2=goteop                       /* goto end of paragraph (blank line) */
N3=unkncom                      /* unknown */
N.=forwdel                      /* delete character under cursor */
NENTER=indent                   /* newline and indent */
SHAR_EOF
cat << \SHAR_EOF > extmac.c
/* EXTMAC.C support program for uemail.ttp.  Reads macro files created
 * in uemail format and creates C source prototypes.
 */
 
#include <stdio.h>
 
#define NFILEN  80                      /* # of bytes, file name        */
#define NBUFN   16                      /* # of bytes, buffer name      */
#define NLINE   256                     /* # of bytes, line             */
#define NKBDM   256                     /* # of strokes, keyboard macro */
#define NPAT    80                      /* # of bytes, pattern          */
#define HUGE    1000                    /* Huge number                  */
#define CTRL    0x0100                  /* Control flag, or'ed in       */
#define META    0x0200                  /* Meta flag, or'ed in          */
#define CTLX    0x0400                  /* ^X flag, or'ed in            */
#define SPEC    0x0800                  /* Special scancode keys        */
#define FLEN    15
 
short *kbdmop;
short kbdm[NKBDM];
FILE  *bmacrp, *fopen();
 
unsigned long _STKSIZ = 32 * 1024;
typedef struct KEYTAB {
        short   k_code;
        char    k_mfunc[FLEN];
} KEYTAB;
/*
 * Command table.
 * This table  is *roughly* in ASCII
 * order, left to right across the characters
 * of the command. This expains the funny
 * location of the control-X commands.
 */
KEYTAB  keytab[] = {
        CTRL|'@',       "setmark",
        CTRL|'A',       "gotobol",
        CTRL|'B',       "backchar",
        CTRL|'C',       "shell",
        CTRL|'D',       "forwdel",
        CTRL|'E',       "gotoeol",
        CTRL|'F',       "forwchar",
        CTRL|'G',       "ctrlg",
        CTRL|'H',       "backchar",
        CTRL|'I',       "tab",
        CTRL|'J',       "indent",
        CTRL|'K',       "mdeleln",
        CTRL|'L',       "refresh",
        CTRL|'M',       "newline",
        CTRL|'N',       "forwline",
        CTRL|'O',       "openline",
        CTRL|'P',       "backline",
        CTRL|'Q',       "quote",
        CTRL|'R',       "backsearch",
        CTRL|'S',       "forwsearch",
        CTRL|'T',       "twiddle",
        CTRL|'V',       "forwpage",
        CTRL|'W',       "killregion",
        CTRL|'Y',       "yank",
        CTRL|'Z',       "quickexit",
        CTRL|'\\',      "unkncom",
        CTRL|'_',       "kermit",
        CTRL|'^',       "unkncom",
        CTLX|CTRL|'A',  "unkncom",
        CTLX|CTRL|'B',  "listbuffers",
        CTLX|CTRL|'C',  "quit",
        CTLX|CTRL|'D',  "unkncom",
        CTLX|CTRL|'E',  "commfil",
        CTLX|CTRL|'F',  "filename",
        CTLX|CTRL|'G',  "ctrlg",
        CTLX|CTRL|'H',  "unkncom",
        CTLX|CTRL|'I',  "print",
        CTLX|CTRL|'J',  "unkncom",
        CTLX|CTRL|'K',  "unkncom",
        CTLX|CTRL|'L',  "lowerregion",
        CTLX|CTRL|'M',  "unkncom",
        CTLX|CTRL|'N',  "mvdnwind",
        CTLX|CTRL|'O',  "deblank",
        CTLX|CTRL|'P',  "mvupwind",
        CTLX|CTRL|'Q',  "unkncom",
        CTLX|CTRL|'R',  "fileread",
        CTLX|CTRL|'S',  "filesave",
        CTLX|CTRL|'T',  "showtime",
        CTLX|CTRL|'U',  "upperregion",
        CTLX|CTRL|'V',  "filevisit",
        CTLX|CTRL|'W',  "filewrite",
        CTLX|CTRL|'X',  "swapmark",
        CTLX|CTRL|'Y',  "unkncom",
        CTLX|CTRL|'Z',  "shrinkwind",
        CTLX|'!',       "paginate",
        CTLX|'#',       "setpage",
        CTLX|'+',       "pageforw",
        CTLX|'-',       "pageback",
        CTLX|'.',       "setindcol",
        CTLX|'(',       "ctlxlp",
        CTLX|')',       "ctlxrp",
        CTLX|'*',       "retversion",
        CTLX|'<',       "btopunct",
        CTLX|'=',       "showcpos",
        CTLX|'>',       "ftopunct",
        CTLX|'0',       "unkncom",
        CTLX|'1',       "onlywind",
        CTLX|'2',       "splitwind",
        CTLX|'3',       "unkncom",
        CTLX|'4',       "unkncom",
        CTLX|'5',       "unkncom",
        CTLX|'6',       "unkncom",
        CTLX|'7',       "unkncom",
        CTLX|'8',       "unkncom",
        CTLX|'9',       "unkncom",
        CTLX|'A',       "unkncom",
        CTLX|'B',       "usebuffer",
        CTLX|'C',       "paintbuffer",
        CTLX|'D',       "setpath",
        CTLX|'E',       "ctlxe",
        CTLX|'F',       "setfillcol",
        CTLX|'H',       "unkncom",
        CTLX|'I',       "fileinsert",
        CTLX|'J',       "unkncom",
        CTLX|'K',       "killbuffer",
        CTLX|'L',       "unkncom",
        CTLX|'M',       "setmode",
        CTLX|'N',       "nextwind",
        CTLX|'O',       "prevwind",
        CTLX|'P',       "prevwind",
        CTLX|'Q',       "unkncom",
        CTLX|'R',       "writereg",
        CTLX|'S',       "gospell",
        CTLX|'T',       "unkncom",
        CTLX|'U',       "unkncom",
        CTLX|'V',       "unkncom",
        CTLX|'W',       "wc",
        CTLX|'Y',       "unkncom",
        CTLX|'Z',       "enlargewind",
        CTLX|'\\',      "grtw",
        CTLX|'`',       "getmacro",
        CTLX|'~',       "shell",
        CTLX|SPEC|'p',  "swapmark",
        META|CTRL|'B',  "backword",
        META|CTRL|'C',  "mcenter",
        META|CTRL|'F',  "forwword",
        META|CTRL|'G',  "ctrlg",
        META|CTRL|'H',  "backword",
        META|CTRL|'I',  "kill",
        META|CTRL|'K',  "mdelwln",
        META|CTRL|'M',  "unkncom",
        META|CTRL|'N',  "enumerate",
        META|CTRL|'O',  "clowsp",
        META|CTRL|'P',  "tglcase",
        META|CTRL|'R',  "mrflush",
        META|CTRL|'S',  "forwisearch",
        META|CTRL|'T',  "backisearch",
        META|'!',       "reposition",
        META|'.',       "gotoeob",
        META|',',       "gotobob",
        META|'>',       "gotoeob",
        META|'<',       "gotobob",
        META|' ',       "setmark",
        META|'@',       "rettpa",
        META|'A',       "backsent",
        META|'B',       "backword",
        META|'C',       "capword",
        META|'D',       "delfword",
        META|'E',       "forwsent",
        META|'F',       "forwword",
        META|'G',       "goline",
        META|'H',       "markpar",
        META|'I',       "unkncom",
        META|'J',       "mindnl",
        META|'K',       "killsent",
        META|'L',       "lowerword",
        META|'M',       "sglmode",
        META|'N',       "goteop",
        META|'O',       "mdropln",
        META|'P',       "gotbop",
        META|'Q',       "fillpar",
        META|'R',       "replace",
        META|'S',       "unkncom",
        META|'T',       "twaddle",
        META|'U',       "upperword",
        META|'V',       "backpage",
        META|'W',       "copyregion",
        META|'X',       "mdoncom",
        META|'Y',       "unkncom",
        META|'Z',       "unkncom",
        META|'\\',      "mdelind",
        META|'~',       "clearflag",
        META|0x7F,      "delbword",
        SPEC|'H',       "backline",
        SPEC|'P',       "forwline",
        SPEC|'K',       "backchar",
        SPEC|'M',       "forwchar",
        SPEC|'b',       "kermit",
        SPEC|'a',       "yank",
        SPEC|'R',       "openline",
        SPEC|'S',       "backdel",
        SPEC|'G',       "refresh",
        SPEC|'q',       "forwdel",
        SPEC|'r',       "indent",
        SPEC|'c',       "backword",
        SPEC|'d',       "forwword",
        SPEC|'e',       "grtw",
        SPEC|'f',       "retversion",
        SPEC|'g',       "gotobol",
        SPEC|'h',       "gotoeol",
        SPEC|'i',       "unkncom",
        SPEC|'J',       "pageback",
        SPEC|'N',       "pageforw",
        SPEC|'j',       "backsent",
        SPEC|'k',       "forwsent",
        SPEC|'l',       "unkncom",
        SPEC|'m',       "gotbop",
        SPEC|'n',       "goteop",
        SPEC|'o',       "unkncom",
        SPEC|'D',       "quickexit",
        SPEC|'C',       "filesave",
        SPEC|'B',       "filewrite",
        SPEC|'A',       "filevisit",
        SPEC|'@',       "fileread",
        SPEC|'?',       "fileinsert",
        SPEC|'>',       "writereg",
        SPEC|'=',       "filename",
        SPEC|'<',       "listbuffers",
        SPEC|';',       "setmark",
        0x60,           "putmacro",
        0x7F,           "backdel"
};
 
#define NKEYTAB (sizeof(keytab)/sizeof(keytab[0]))
 
main(argc,argv)
int argc;
char *argv[];
{
        register int err;
 
        if (argc < 3)
                {
                fprintf(stderr,"usage: %s infile outfile\n",argv[0]);
                exit(-1);
                }
        if ((bmacrp=fopen(argv[2], "w"))==NULL)
                {
                err = perror("open failure");
                exit(err);
                }
        err=loadmac(argv[1]);
        fclose(bmacrp);
        exit(err);
}
 
/* LOADMAC read a uemail macro file and produce a prototype C source file.
 */
loadmac(macfile)
char macfile[];
{
        register int d,i;
        register short s;
        register FILE   *mp;
        extern void extrct_macro();
 
        if ((mp=fopen(macfile,"r"))==NULL)
                {
                fprintf(stderr,"Cannot open %s",macfile);
                return(-1);
                }
        if ((s=getw(mp))!=(CTLX|'('))
                {
                fprintf(stderr,"Macro file format error: %s",macfile);
                fclose(mp);
                return(-1);
                }
        while((d=fgetc(mp))!=EOF)
                {
                i=0;
                while ((s=getw(mp))!=(CTLX|')'))
                        {
                        if (feof(mp))
                                {
                                fprintf(stderr,"Read error on: %s",macfile);
                                fclose(mp);
                                return(-11);    /* read error */
                                }
                        kbdm[i++]=s;
                        }
                kbdm[i] = CTLX|')';
                extrct_macro(d);
                }
        fclose(mp);
        return(NULL);
}
 
/* Look at the current keyboard macro.  Send each bitcode to writmacro()
 * so it can look up the function calling sequence in the KEYTAB.  These
 * functions allow you to record keyboard macros in C source code for
 * later compilation.
 */
void
extrct_macro(d)
{
        register int    c;
        register int    an;
        register int    s;
 
        fprintf(bmacrp,"%c(f,n)\n",d);
        fputs("int f,n;\n",bmacrp);     /* default uEmail parameters */
        fputs("{\n",bmacrp);            /* begin definition */
        fputs("        if (n < 0)\n",bmacrp);
        fputs("                return(0);\n",bmacrp);
        fputs("        while(n--)\n",bmacrp);
        fputs("                {\n",bmacrp);
        kbdmop = &kbdm[0];
        do
                {
                an = 1;
                if ((c = *kbdmop++) == (CTRL|'U'))
                        {
                        an = *kbdmop++;
                        c  = *kbdmop++;
                        }
                s = TRUE;
                } while (c!=(CTLX|')') && (s=writmacro(c,an))==TRUE);
        kbdmop = NULL;
        fputs("                }\n",bmacrp);    /* end the while statement */
        fputs("        return(1);\n",bmacrp);
        fputs("}\n\n",bmacrp);
        return;
}
 
/* Look up function name based on bitcode found in extrct_macro().  No errors
 * because a running macro that uses one of the "get-string" routines would
 * return an error and extrct_macro() would abort.  Watch when using with
 * functions that use mlreply() or readpattern() that the read-in text does
 * not return FALSE.
 */
 
writmacro(c,n)
register int c,n;
{
 
        char funam[FLEN];
        register int f;
 
        if (n != 1)
                f = TRUE;
        else
                f = FALSE;
        if(getfname((short)c,funam)!=FALSE)
                fprintf(bmacrp,"                if(!%s(%d,%d))\n",funam,f,n);
        else
                fprintf(bmacrp,"                if(!linsert(%d,'%c'))\n",n,c);
        fputs("                        return(0);\n",bmacrp);
        return(TRUE);   /* bad keycode, but we want it anyway */
}
 
/* given a keycode value, return TRUE
 * and get the function's name into `name'.
 */
getfname(kcode,name)
register short kcode;
char name[];
{
        register KEYTAB *ktp;
 
        ktp = &keytab[0];       /* the function to find */
        /* look through to find keytab assoc with "code" */
        while (ktp < &keytab[NKEYTAB]) {
                if (ktp->k_code == kcode)
                        {
                        strcpy(name,ktp->k_mfunc);
                        return(TRUE);
                        }
                ++ktp;
        }
        return(FALSE);  /* not found */
}
SHAR_EOF
cat << \SHAR_EOF > ueasm.s
*************************************************************************
* Add all of this to your gemstart.s file.  You will need the latest
* version.  It is copyrighted, or I would include it also.  You need
* the stack variable to allow shell commands.  The __BDOS function is
* a bug fix.  The copy function handles screens in the terminal section.
* The getmem function is for rettpa.  I include gemdos-xbios in my
* startup so that link68 does not have to load osbind.o.
*************************************************************************
*
* STACK variable summary:
*       -1=keep all
*        0=keep MINSTACK bytes
*        1=keep 1/4 of free memory
*        2=keep 2/4
*        3=keep 3/4
*        4=use _STKSIZ: keep (if >0) or give up (if <0) _STKSIZ bytes.
*    other=keep that many bytes (positive) or give back that many (negative)
 
STACK=4                 * CHANGE THIS VARIABLE TO CHOOSE A MEMORY MODEL
*
* Surprise, the trap #2 vector is largely a do nothing routine.
* Redirecting the basic calls may help solve a few problems.
*
        .globl ___BDOS
 
___BDOS:
        link    A6,#-4
        cmpi.w  #9,$8(A6)
        beq     togem
        cmpi.w  #2,$8(A6)
        beq     togem
        cmpi.w  #1,$8(A6)
        beq     togem
        cmpi.w  #26,$8(A6)
        bne     bdos
togem:
        move.l  $a(A6),(sp)     * value
        move.w  $8(A6),-(sp)    * function
        bsr     _gemdos
        addq.l  #2,sp
        bra     out
bdos:
        move.l  $a(A6),d1       * value
        move.w  $8(A6),d0       * function
        trap    #2              * Enter BDOS
        cmpa.l  __break,sp      * Check for stack ovf
        bcs     __sovf          * overflow! print msg and abort
 
out:    unlk    A6              * no error; return
        rts                     * Back to caller
 
*
*       GEMDOS, BIOS, and XBIOS calls
*
        .globl  _gemdos
        .globl  _bios
        .globl  _xbios
_gemdos:
        move.l  (sp)+,biosret
        trap    #1
        move.l  biosret,-(sp)
        rts
*
_bios:  move.l  (sp)+,biosret
        trap    #13
        move.l  biosret,-(sp)
        rts
*
_xbios: move.l  (sp)+,biosret
        trap    #14
        move.l  biosret,-(sp)
        rts
*       from _Programming the 68000_ by Steve Williams
*       copy(src,dst,length);
*       char    *src;
*       char    *dst;
*       int     length;
*
        .globl  _copy
_copy:  move.l  4(a7),a0
        move.l  8(a7),a1
        move.w  12(a7),d0
        sub.w   #1,d0
loop:   move.b  (a0)+,(a1)+
        dbra    d0,loop
        rts
*
*       getmem function to return present top of memory
*
        .globl  _getmem
_getmem:
        move.l  a7,d0   * real simple and it works
        rts
        .bss
        .even
biosret:        .ds.l   1
 
SHAR_EOF
cat << \SHAR_EOF > xemacs.lnk
[tem[m:]]e:xemacs.68k=gemsnew,
m:main,
m:basic,
m:buffer,
m:file,
m:fileio,
m:line,
m:random,
m:misc,
m:region,
m:search,
m:word,
m:wc,
m:kermit,
m:kertrans,
m:kerrec,
m:kertty,
m:page,
m:print,
m:window,
m:display,
m:termio,
m:ttgetc,
m:tty,
m:shell,
m:path,
m:macros,
m:keybrd,
gemlib[in[_nobinary],in[_nofilesz],in[_nottyin],in[_maxfiles],in[_nowildc]],
libm
SHAR_EOF
#       End of shell archive
exit 0
%NONAME-W-NOMSG, Message number 00000000
Technical Details
Message-ID: <8702052106.AA14358@ucbvax.Berkeley.EDU>
Path: arc1-ca.pugleaf.net!utzoo!watmath!clyde!cbatt!ucbvax!ULKYVX.BITNET!RDROYA01

Show Full Headers
Complete Article Headers
Relay-Version: version B 2.10 5/3/83; site utzoo.UUCP
Path: arc1-ca.pugleaf.net!utzoo!watmath!clyde!cbatt!ucbvax!ULKYVX.BITNET!RDROYA01
From: RDROYA01@ULKYVX.BITNET.UUCP
Newsgroups: comp.sys.atari.st
Subject: Uemail source (10 of 12)
Message-ID: <8702052106.AA14358@ucbvax.Berkeley.EDU>
Date: Thu, 5-Feb-87 14:46:00 EST
Article-I.D.: ucbvax.8702052106.AA14358
Posted: Thu Feb  5 14:46:00 1987
Date-Received: Sat, 7-Feb-87 14:45:35 EST
Sender: daemon@ucbvax.BERKELEY.EDU
Organization: University of Louisville
Lines: 913