home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Crawly Crypt Collection 1
/
crawlyvol1.bin
/
program
/
compiler
/
nasm20b
/
nasm_src
/
de_mac.c
< prev
next >
Wrap
C/C++ Source or Header
|
1993-01-19
|
13KB
|
581 lines
/* ---------------------------------------------------------------------- */
/* Copyright (C) 1992 by Natürlich! */
/* This file is copyrighted! */
/* Refer to the documentation for details. */
/* ---------------------------------------------------------------------- */
/* rev. history 1.0 -- */
/* 1.1 -- */
/* 1.2 -- removed NIL crashes on faulty MAC65 */
/* 1.3 -- -c option searches directory */
/* 1.4 -- faulty M65 files are treated kinder */
/* 1.5 -- no real changes */
/* ---------------------------------------------------------- */
#include "defines.h"
#if __NSTDC__ && __TURBOC__
#pragma warn -pia /* Don't want those if( foo = bar) warnings */
#endif
#include <stdio.h>
#include <string.h>
#include <stddef.h>
#include <stdlib.h>
#include <setjmp.h>
#define __BIG_GENERATOR__
#include OSBIND
#include "code.h"
#define COMMENTPAD 24
#define MACROPAD 06
#define INSTRPAD 06
#define DATAPAD 12
#if OS == TOS
struct
{
char reserved[ 21];
byte attribs;
word time,
date;
lword len;
char name[ 14];
} dir;
#endif
void convert(),
nflush(),
io(),
label(),
nput(),
nprint(),
comment(),
padto();
struct
{
word fefe,
len;
} header;
#ifdef NIL
#undef NIL
#endif
#define NIL (char *) 0
#define TAB1SIZE 95
char *table1[] =
{
"error -", ".if", ".else", ".endif", ".macro",
".endm", ".title", NIL, ".page", ".word",
".error", ".byte", ".sbyte", ".dbyte", ".end",
".opt", ".tab", ".include", ".ds", ".org",
".equ", "bra", "trb", "tsb", ".float",
".cbyte", "", ".local", ".set", "*=",
"=", ".=", "jsr", "jmp", "dec",
"inc", "ldx", "ldy", "stx", "sty",
"cpx", "cpy", "bit", "brk", "clc",
"cld", "cli", "clv", "dex", "dey",
"inx", "iny", "nop", "pha", "php",
"pla", "plp", "rti", "rts", "sec",
"sed", "sei", "tax", "tay", "tsx",
"txa", "txs", "tya", "bcc", "bcs",
"beq", "bmi", "bne", "bpl", "bvc",
"bvs", "ora", "and", "eor", "adc",
"sta", "lda", "cmp", "sbc", "asl",
"rol", "lsr", "ror", NIL, "stz",
"dea", "ina", "phx", "phy", "plx",
"ply"
};
static char ref[] = ".ref ", and[] = ".and ", not[]= ".not ",
or[] = ".or ", def[] = ".def ";
#define TAB2SIZE 78
char otable2[] = /* 0 - 77 */
{
0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 1, 1, 1, 0, 0,
0, 0, 1, 1, 1, 1, 1, 0,
1, 1, 1, 1, 1, 1, 1, 1,
1, 0, 0, 0, 1, 1, 0, 1,
0, 0, 0, 0, 0, 0, 0, 1,
1, 1, 1, 1, 1, 1, 1, 1,
1, 1, 1, 0, 0, 1, 1, 1,
1, 1, 1, 1, 1, 1, 1, 1,
1, 1, 1, 1, 1, 1
};
char *table2[] = /* 0 - 77 */
{
NIL, NIL, NIL, NIL, NIL, NIL, NIL, NIL,
NIL, NIL, NIL, "%$", "%", "*", " ", " ",
"a", "q", "+", "-", "*", "/", "&", NIL,
"=", "<=", ">=", "<>", ">", "<", "-", "[",
"]", or, and, not, "!", "^", ref, "\\",
NIL, NIL, NIL, NIL, "Edit", "What!", "Text:", ref,
def, not, and, or, "<", ">", ",x)", "),y",
",y", ",x", ")", NIL, NIL, ",", "#", "a",
"(", "\"", "$", NIL, NIL, "no ", "obj ", "err ",
"eject ","list ", "xref ", "mlist ","clist ","num "
};
#define tolower( c) ((c) >= 'A' && (c) <= 'Z' ? (c) + 32 : (c))
#if OS == TOS
int tossable;
#endif
char *currfile = "[none]";
jmp_buf errjmp;
static char tiny[8],
infile[ 256],
outfile[256];
word __x;
byte huge *p;
long len;
int fp,
forceit,
delete;
FILE *fq;
void nferror( s)
char *s;
{
fprintf( stderr, "demac65: \"%s\" Fatal error - %s\n", currfile, s);
exit(1);
}
void nerror( s)
char *s;
{
fprintf( stderr, "demac65: \"%s\" Error - %s\n", currfile, s);
Fclose( fp);
if( outfile[ 0])
fclose( fq);
longjmp( errjmp, 1);
}
unsigned int lines;
void nwarning( s)
char *s;
{
fprintf( stderr, "demac65: \"%s\" ca. line %d, Warning - %s\n",
currfile, lines + 1, s);
}
void complete( filename, ext, force)
char *filename, *ext;
{
char *x;
if( x = strrchr( filename, '.'))
{
if( strchr( x, DIRSLASH) > x)
goto dis;
if( force)
while( *++x = *++ext);
}
else
dis:
strcat( filename, ext);
}
int chk_ext( filename, ext)
char *filename, *ext;
{
char *x;
if( x = strrchr( filename, '.'))
if( strchr( x, DIRSLASH) <= x)
return( strcmp( x + 1, ext));
return( 1);
}
int main( argc, argv)
int argc;
char *argv[];
{
int i = 0;
fq = stdout; /* done here for some bogus Amiga CC */
while( ++i < argc)
{
if( *argv[i] == '-')
switch( argv[i][1])
{
#if OS == TOS
case 'T' :
case 't' :
tossable = ! tossable;
break;
#endif
case 'D' :
case 'd' :
delete = ! delete;
break;
case 'C' :
case 'c' :
forceit = ! forceit;
break;
#ifdef __DATE__
case ':' :
fputs( __DATE__, stderr);
# ifdef __TIME__
fprintf( stderr, " %s", __TIME__);
# endif
putc( '\n', stderr);
break;
#endif
case 'V' :
case 'v' :
fprintf( stderr, "demac65 v1.5 (c) 1992 by Natuerlich! -- detokenizes MAC65 files\n");
break;
}
else
if( ! infile[0])
strcpy( infile, argv[i]);
else
if( ! outfile[0])
strcpy( outfile, argv[i]);
else
goto usage;
}
if( ! infile[0])
goto usage;
if( ! setjmp( errjmp))
{
if( forceit)
{
strcpy( outfile, infile);
complete( outfile, ".s65", 1);
#if OS == TOS
if( strchr( infile, '*')) /* doesn't work well but works */
{
Fsetdta( (void *) &dir);
if( Fsfirst( infile, 0))
nferror( "No MaTcH"); /* waste user lifetime */
do
if( chk_ext( dir.name, "S65"))
{
strcpy( outfile, dir.name);
complete( outfile, ".s65", 1);
if( ! setjmp( errjmp))
io( dir.name, outfile);
}
while( ! Fsnext());
return( 0);
}
#endif
}
io( infile, outfile);
return( 0);
}
return( 1);
usage:
#if OS == TOS
fprintf( stderr, "usage: demac65 [-{td}]{-c <filemask>|[-c] <infile> \
[outfile]}\n");
fputs(
"\t-c <filemask> : convert 1 or more files, f.e. -c '*.*' converts all\n",
stderr);
#else
fprintf( stderr, "usage: demac65 [-{cd}] <infile> [outfile]\n");
#endif
fputs( "\
\t-c <infile> : convert <infile> to <infile>.S65\n\
\t-d : delete after conversion\n\
\t-v : version\n", stderr);
#if OS == TOS
fputs( "\t-t : wait for keypress before exiting\n", stderr);
keypress();
#endif
return(1);
}
void io( in, out)
char *in, *out;
{
static char buf[256];
currfile = in;
if( (fp = (int) Fopen( in, 0)) < 0)
{
sprintf( buf, "Couldn't open source file \"%s\"", in);
nferror( buf);
}
if( Fread( fp, 4L, &header) < 4)
nerror("File trunctated");
if( header.fefe != 0xFEFE)
nerror("Not a MAC65 token file");
if( len = dpeek( &header.len))
{
if( ! (p = (byte huge *) Malloc( len)))
nferror("Out of memory");
if( Fread( fp, len, p) < len)
nerror("Source file truncated");
if( out[0] && ! (fq = fopen( out, "w")))
{
sprintf( buf, "Couldn't create output file \"%s\"", out);
nferror( buf);
}
convert();
if( delete && ! unlink( in))
fprintf( stderr, "Deleted \"%s\"\n", in);
if( out[0])
fclose( fq);
}
Fclose( fp);
}
int indent,
pad,
i,
inquotes;
byte c, d;
void convert()
{
lines = 1;
indent = inquotes = 0;
while( len)
{
pad = 0; /* start from left */
p += 2; /* ignore lineno */
i = (word) *p++ - 3; /* line length */
len -= 3 + i; /* minus lineno + linelength + linebyte */
while( i)
{
i--;
c = *p & 0x7F;
if( c != *p++)
{
label( 0);
nput( ' ');
continue;
}
switch( c)
{
case 0 :
nprint( table1[0]); /* am i lazy... */
comment();
break;
case 7 :
padto(MACROPAD);
c = *p++ & 0x7F;
i--;
label(1);
nput(' ');
if( xconvert())
goto salvage;
break;
case 88 :
comment();
break;
default :
d = c;
if( d == 2 || d == 3 || d == 5) /* .ELSE .ENDIF .ENDM*/
indent -= 3;
padto( INSTRPAD);
if( c >= TAB1SIZE)
{
nerror("Got an totally unknown instr. token");
salvage:
p += i;
i = 0;
break;
}
else
nprint( table1[ c]);
nput(' ');
if( xconvert())
goto salvage;
if( d == 1 || d == 2 || d == 4)
indent += 3;
}
}
nput( '\n');
lines++;
}
}
xconvert()
{
inquotes = 0;
if( i)
padto( DATAPAD);
while( i)
{
i--;
c = *p & 0x7F;
if( c != *p++)
{
label( inquotes);
continue;
}
switch( c)
{
case 1 :
case 3 :
case 5 :
sprintf( tiny, "$%X", ((word) p[1] << 8) | (word) *p);
p += 2;
i -= 2;
nprint( tiny);
break;
case 0 :
case 2 :
case 4 :
case 6 :
sprintf( tiny, "$%X", (word) *p++);
i--;
nprint( tiny);
break;
case 7 :
case 9 :
sprintf( tiny, "%u", ((word) p[1] << 8) | *p);
p += 2;
i -= 2;
nprint( tiny);
break;
case 8 :
sprintf( tiny, "%u", *p++);
i--;
nprint( tiny);
break;
case 10 :
nput('\'');
nput( (int) *p++);
i--;
break;
case 59 :
padto( COMMENTPAD);
if( *p != ';')
nput( ';');
comment();
break;
case 65 :
inquotes = ! inquotes;
default :
{
if( c >= TAB2SIZE)
{
nerror("Got an undetokenizable token");
return( 1);
}
else
{
if( ! otable2[ c])
nwarning("Unusual token");
nprint( table2[ c]);
}
}
}
}
return( 0);
}
/* Vot = 0 lower case */
void label( vot)
{
char v;
int x = c;
i -= c;
while( x)
{
x--;
v = *p++;
nput( (int) (vot ? v : tolower(v)));
}
}
void comment()
{
while( i)
{
i--;
nput( (int) *p++);
}
}
void padto(to)
int to;
{
to += indent;
while( pad < to)
nput(' ');
}
void nput( c)
int c;
{
putc( c, fq);
pad++;
}
void nprint( s)
char *s;
{
int i;
if( s)
{
i = (int) strlen( s);
if( fputs( s, fq))
nferror("Disk full ?");
pad += i;
}
else
nerror("Got an undetokenizable token");
}
keypress()
{
#if OS == TOS
if( tossable)
{
while( Bconstat( 2))
Bconin( 2);
Bconin( 2);
}
#endif
}