/* -*-c-*-
*
- * $Id: bascat.c,v 1.1 1998/03/16 15:21:37 mdw Exp $
+ * $Id: bascat.c,v 1.2 1998/06/26 11:29:28 mdw Exp $
*
* Display BBC BASIC programs more or less anywhere
*
/*----- Revision history --------------------------------------------------*
*
* $Log: bascat.c,v $
+ * Revision 1.2 1998/06/26 11:29:28 mdw
+ * Added support for line-numbers.
+ *
* Revision 1.1 1998/03/16 15:21:37 mdw
* Files placed under CVS control.
*
s_comment, /* In a command (or literal *cmd) */
s_quote, /* Inside a quoted string */
s_c6, s_c7, s_c8, /* Various shift states */
+ s_linex, s_liney, s_linez, /* Line number states */
s_dummy
};
-static bc__state = s_normal; /* Current detokenisation state */
+static int bc__state = s_normal; /* Current detokenisation state */
+static unsigned int bc__lineno; /* Line number */
enum {
f_highlight = 1, /* Highlight keywords and things */
static int bc__decode(int byte, FILE * fp)
{
switch (bc__state) {
+
+ /* --- Tokenised states --- */
+
case s_keyword:
if (byte == '*')
bc__state = s_comment;
else
bc__state = s_normal;
/* Fall through here */
+
case s_normal:
if (byte >= 0x7F) {
switch (byte) {
case 0xC8:
bc__state = s_c8;
break;
+ case 0x8D:
+ bc__state = s_linex;
+ break;
case 0x8B: /* ELSE */
case 0x8C: /* THEN */
case 0xF5: /* REPEAT (a funny one) */
bc__state = s_keyword;
- bc__keyword(bcTok__base[byte - 0x7F], fp);
+ goto keyword;
break;
case 0xDC: /* DATA */
case 0xF4: /* REM */
bc__state = s_comment;
/* Fall through here */
default:
+ keyword:
bc__keyword(bcTok__base[byte - 0x7F], fp);
break;
}
fputc(byte, fp);
}
break;
+
+ /* --- Non-tokenised states --- */
+
case s_quote:
if (byte == '"')
bc__state = s_normal;
/* Fall through here */
+
case s_comment:
fputc(byte, fp);
break;
+
+ /* --- Double-byte token states --- */
+
case s_c6:
return (bc__mbtok(byte, bcTok__c6, ITEMS(bcTok__c6), fp));
break;
+
case s_c7:
return (bc__mbtok(byte, bcTok__c7, ITEMS(bcTok__c7), fp));
break;
+
case s_c8:
return (bc__mbtok(byte, bcTok__c8, ITEMS(bcTok__c8), fp));
break;
+
+ /* --- Encoded line number states --- */
+
+ case s_linex:
+ bc__lineno = ((((byte << 2) | (byte << 12)) & 0xc0c0u) ^ 0x4040u);
+ bc__state++;
+ break;
+
+ case s_liney:
+ bc__lineno |= byte & 0x3fu;
+ bc__state++;
+ break;
+
+ case s_linez:
+ bc__lineno |= (byte << 8) & 0x3fu;
+ fprintf(fp, "%u", bc__lineno);
+ bc__state = s_normal;
+ break;
+
}
return (0);
}
bc__state = s_normal;
while (len) {
byte = getc(in);
- D( fprintf(stderr, "state == %i, byte == %i\n", \
- bc__state, byte); )
+ D( fprintf(stderr, "state == %i, byte == %i\n",
+ bc__state, byte); )
if (byte == EOF)
goto eof;
bc__decode(byte, out);