This commit is contained in:
marketideas 2019-11-12 00:15:47 -08:00
parent 665702b31b
commit 20ea010256
8 changed files with 275 additions and 99 deletions

View File

@ -2,7 +2,7 @@ cmake_minimum_required(VERSION 3.0)
set (CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} "${CMAKE_SOURCE_DIR}/cmake/") set (CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} "${CMAKE_SOURCE_DIR}/cmake/")
set(CMAKE_BUILD_TYPE Debug) set(CMAKE_BUILD_TYPE Debug)
set(APPVERSION "1.0.0") set(APPVERSION "1.0.1")
set(LIBRARY_NAME pal) set(LIBRARY_NAME pal)
include(./lib${LIBRARY_NAME}/cmake/CMakeHeader.txt) include(./lib${LIBRARY_NAME}/cmake/CMakeHeader.txt)
@ -39,4 +39,3 @@ include(./lib${LIBRARY_NAME}/cmake/CMakeCommands.txt)

140
asm.cpp
View File

@ -60,11 +60,11 @@ void CLASS::print(uint32_t lineno)
} }
int b = 4; int b = 4;
printf("%02X ", addressmode); //printf("%02X ", addressmode);
printf("%6d", lineno + 1); //printf("%6d", lineno + 1);
if (!empty) if (!empty)
{ {
printf(" %02X/%04X:", (startpc >> 16), startpc & 0xFFFF); printf("%02X/%04X:", (startpc >> 16), startpc & 0xFFFF);
} }
else else
{ {
@ -80,6 +80,23 @@ void CLASS::print(uint32_t lineno)
printf(" "); printf(" ");
} }
if ((getBool("asm.showmx", false)))
{
if (outbytect > 0)
{
printf("%%%c%c ", linemx & 02 ? '1' : '0', linemx & 01 ? '1' : '0');
}
else
{
printf(" ");
}
}
if (isDebug())
{
printf("%02X ", addressmode);
}
printf("%6d ", lineno + 1);
if (empty) if (empty)
{ {
printf("%s", comment.c_str()); printf("%s", comment.c_str());
@ -115,12 +132,12 @@ void CLASS::clear()
operand_expr = ""; operand_expr = "";
operand_expr2 = ""; operand_expr2 = "";
addrtext = ""; addrtext = "";
linemx = 0;
bytect = 0; bytect = 0;
opflags = 0; opflags = 0;
pass0bytect = 0; pass0bytect = 0;
startpc = 0; startpc = 0;
errorcode = 0; errorcode = 0;
inbytect = 0;
outbytect = 0; outbytect = 0;
lineno = 0; lineno = 0;
outbytes.clear(); outbytes.clear();
@ -280,6 +297,7 @@ void CLASS::init(void)
void CLASS::complete(void) void CLASS::complete(void)
{ {
uint64_t n = GetTickCount(); uint64_t n = GetTickCount();
if (isDebug()) if (isDebug())
{ {
@ -434,9 +452,11 @@ TSymbol *CLASS::findSymbol(std::string symname)
{ {
TSymbol *res = NULL; TSymbol *res = NULL;
//printf("finding: %s\n",symname.c_str());
auto itr = symbols.find(Poco::toUpper(symname)); auto itr = symbols.find(Poco::toUpper(symname));
if (itr != symbols.end()) if (itr != symbols.end())
{ {
//printf("Found: %s 0x%08X\n",itr->second.name.c_str(),itr->second.value);
res = &itr->second; res = &itr->second;
return (res); return (res);
@ -458,6 +478,7 @@ TSymbol *CLASS::addSymbol(std::string sym, uint32_t val, bool replace)
if (fnd != NULL) if (fnd != NULL)
{ {
//printf("replacing symbol: %s %08X\n",sym.c_str(),val);
fnd->value = val; fnd->value = val;
return (fnd); return (fnd);
} }
@ -468,6 +489,7 @@ TSymbol *CLASS::addSymbol(std::string sym, uint32_t val, bool replace)
s.namelc = Poco::toLower(sym); s.namelc = Poco::toLower(sym);
s.stype = 0; s.stype = 0;
s.value = val; s.value = val;
s.used=false;
s.cb = NULL; s.cb = NULL;
std::pair<std::string, TSymbol> p(Poco::toUpper(sym), s); std::pair<std::string, TSymbol> p(Poco::toUpper(sym), s);
symbols.insert(p); symbols.insert(p);
@ -475,12 +497,39 @@ TSymbol *CLASS::addSymbol(std::string sym, uint32_t val, bool replace)
return (res); return (res);
} }
void CLASS::showSymbolTable(void) // set alpha to true to print table sorted by name or
// false to print by value;
void CLASS::showSymbolTable(bool alpha)
{ {
std::map<std::string, uint32_t> alphamap;
std::map<uint32_t, std::string> nummap;
for (auto itr = symbols.begin(); itr != symbols.end(); itr++) for (auto itr = symbols.begin(); itr != symbols.end(); itr++)
{ {
TSymbol ptr = itr->second; TSymbol ptr = itr->second;
printf("Sym: %-24s 0x%08X\n", ptr.name.c_str(), ptr.value); alphamap.insert(pair<std::string, uint32_t>(ptr.name, ptr.value));
nummap.insert(pair<uint32_t, std::string>(ptr.value, ptr.name));
//printf("Sym: %-24s 0x%08X\n", ptr.name.c_str(), ptr.value);
}
if (alpha)
{
printf("\nSymbol table sorted alphabetically:\n");
for (auto itr = alphamap.begin(); itr != alphamap.end(); ++itr)
{
printf("%-16s 0x%08X\n", itr->first.c_str(), itr->second);
}
}
else
{
printf("\nSymbol table sorted numerically:\n");
for (auto itr = nummap.begin(); itr != nummap.end(); ++itr)
{
printf("0x%08X %-16s\n", itr->first, itr->second.c_str());
}
} }
} }
@ -510,11 +559,6 @@ int CLASS::callOpCode(std::string op, MerlinLine &line)
TSymbol s = itr->second; TSymbol s = itr->second;
if (s.cb != NULL) if (s.cb != NULL)
{ {
if (s.stype & OP_ONEBYTE)
{
line.inbytes[0] = (s.opcode);
line.inbytect = 1;
}
res = s.cb(line, s); res = s.cb(line, s);
if (res == -1) if (res == -1)
{ {
@ -539,6 +583,9 @@ typedef struct
// these are the regular expressions that determine the addressing mode // these are the regular expressions that determine the addressing mode
// and extract the 'expr' part of the addr-mode // and extract the 'expr' part of the addr-mode
// ^([_,a-z,A-Z,0-9:\]].+)\,[s,S]{1}$ // might be a better syn_s
TaddrMode addrRegEx[] = TaddrMode addrRegEx[] =
{ {
{ "^(?'expr'.+)\\,[s,S]{1}$", syn_s, "e,s"}, // expr,s { "^(?'expr'.+)\\,[s,S]{1}$", syn_s, "e,s"}, // expr,s
@ -594,29 +641,85 @@ void CLASS::init(void)
void CLASS::initpass(void) void CLASS::initpass(void)
{ {
casesen = true; std::string s;
relocatable = false;
listing = true; casesen = getBool("asm.casesen",true);
listing = getBool("asm.lst", true);
skiplist = false; skiplist = false;
origin = 0x8000; origin = 0x8000;
currentpc = origin; currentpc = origin;
s = getConfig("asm.cpu", "M65816");
s = Poco::trim(Poco::toUpper(s));
cpumode = MODE_65816; cpumode = MODE_65816;
mx = 0x00; mx = 0x00;
if (s == "M65816")
{
cpumode = MODE_65816;
mx = 0x00;
}
else if (s == "M65C02")
{
cpumode = MODE_65C02;
mx = 0x03;
}
else if (s == "M6502")
{
cpumode = MODE_6502;
mx = 0x03;
}
else
{
printf("Unknown CPU type in .ini\n");
}
relocatable = false;
currentsym = NULL; currentsym = NULL;
totalbytes = 0; totalbytes = 0;
lineno = 0; lineno = 0;
errorct = 0; errorct = 0;
passcomplete = false; passcomplete = false;
savepath = "";
} }
void CLASS::complete(void) void CLASS::complete(void)
{ {
printf("=== Assembly Complete: %d bytes %u errors.\n", totalbytes, errorct); printf("\n\n=== Assembly Complete: %d bytes %u errors.\n", totalbytes, errorct);
if (savepath != "")
{
if (errorct == 0)
{
MerlinLine *line;
std::ofstream f(savepath);
uint32_t lineno = 0;
uint32_t l = lines.size();
while (lineno < l)
{
line = &lines[lineno++];
if (line->outbytect > 0)
{
for (uint32_t i = 0; i < line->outbytect; i++)
{
f.put(line->outbytes[i]);
}
}
}
}
else
{
printf("\nErrors in assembly. Output not SAVED.\n\n");
}
}
if (listing) if (listing)
{ {
showSymbolTable(); showSymbolTable(true);
showSymbolTable(false);
} }
TFileProcessor::complete(); TFileProcessor::complete();
} }
@ -646,7 +749,7 @@ int CLASS::evaluate(std::string expr, int64_t &value)
return res; return res;
} }
int CLASS::getAddrMode(MerlinLine &line) int CLASS::getAddrMode(MerlinLine & line)
{ {
int res = -1; int res = -1;
uint16_t mode = syn_none; uint16_t mode = syn_none;
@ -728,7 +831,7 @@ int CLASS::getAddrMode(MerlinLine &line)
return (res); return (res);
} }
int CLASS::parseOperand(MerlinLine &line) int CLASS::parseOperand(MerlinLine & line)
{ {
int res = -1; int res = -1;
@ -772,6 +875,7 @@ void CLASS::process(void)
op = Poco::toLower(line->opcode); op = Poco::toLower(line->opcode);
operand = Poco::toLower(line->operand); operand = Poco::toLower(line->operand);
line->startpc = currentpc; line->startpc = currentpc;
line->linemx = mx;
line->bytect = 0; line->bytect = 0;
if ((line->lable != "") && (pass == 0)) if ((line->lable != "") && (pass == 0))

20
asm.h
View File

@ -15,7 +15,6 @@
#define OP_65C02 0x02 #define OP_65C02 0x02
#define OP_65816 0x04 #define OP_65816 0x04
#define OP_PSUEDO 0x08 #define OP_PSUEDO 0x08
#define OP_ONEBYTE 0x10
#define OP_SPECIAL 0x20 #define OP_SPECIAL 0x20
#define OP_CLASS0 0x0000 #define OP_CLASS0 0x0000
#define OP_CLASS1 0x0100 #define OP_CLASS1 0x0100
@ -40,11 +39,12 @@ enum asmErrors
errBadBranch, errBadBranch,
errUnimplemented, errUnimplemented,
errForwardReference, errForwardReference,
errNoRedefinition,
errMAX errMAX
}; };
#ifdef ADD_ERROR_STRINGS #ifdef ADD_ERROR_STRINGS
std::string errStrings[errMAX] = { std::string errStrings[errMAX+1] = {
"No Error", "No Error",
"Warning", "Warning",
"Unfinished Opcode", "Unfinished Opcode",
@ -53,9 +53,12 @@ std::string errStrings[errMAX] = {
"Unknown Opcode", "Unknown Opcode",
"Opcode not available under CPU mode", "Opcode not available under CPU mode",
"Byte output differs between passes", "Byte output differs between passes",
"Relative branch offset too large" "Relative branch offset too large",
"Unimplemented Instruction", "Unimplemented Instruction",
"Forward Reference to symbol" "Forward Reference to symbol",
"Unable to redefine symbol",
""
}; };
#else #else
extern std::string errStrings[errMAX]; extern std::string errStrings[errMAX];
@ -99,6 +102,7 @@ public:
std::string operand_expr2; std::string operand_expr2;
std::string comment; std::string comment;
std::string addrtext; std::string addrtext;
uint8_t linemx;
uint32_t lineno; uint32_t lineno;
uint32_t flags; uint32_t flags;
uint16_t opflags; uint16_t opflags;
@ -106,8 +110,6 @@ public:
uint32_t addressmode; uint32_t addressmode;
int32_t expr_value; int32_t expr_value;
uint32_t errorcode; uint32_t errorcode;
uint8_t inbytect;
uint8_t inbytes[256];
uint16_t pass0bytect; uint16_t pass0bytect;
uint16_t bytect; uint16_t bytect;
@ -152,11 +154,13 @@ public:
uint32_t value; uint32_t value;
uint16_t stype; uint16_t stype;
uint8_t opcode; uint8_t opcode;
bool used;
TOpCallback cb; TOpCallback cb;
Poco::HashMap<std::string, TSymbol>locals; Poco::HashMap<std::string, TSymbol>locals;
TSymbol() TSymbol()
{ {
used=false;
locals.clear(); locals.clear();
}; };
}; };
@ -176,6 +180,7 @@ protected:
uint32_t origin; uint32_t origin;
uint8_t mx; uint8_t mx;
uint8_t cpumode; // 0=6502, 1=65C02, 2=65816 uint8_t cpumode; // 0=6502, 1=65C02, 2=65816
std::string savepath;
TSymbol *currentsym; TSymbol *currentsym;
std::vector<MerlinLine> lines; std::vector<MerlinLine> lines;
Poco::HashMap<std::string, TSymbol>opcodes; Poco::HashMap<std::string, TSymbol>opcodes;
@ -201,7 +206,7 @@ public:
TSymbol *addSymbol(std::string sym, uint32_t val, bool replace); TSymbol *addSymbol(std::string sym, uint32_t val, bool replace);
void initpass(void); void initpass(void);
void showSymbolTable(void); void showSymbolTable(bool alpha);
int evaluate(std::string expr, int64_t &value); int evaluate(std::string expr, int64_t &value);
@ -218,6 +223,7 @@ public:
int doAddress(MerlinLine &line, TSymbol &sym); int doAddress(MerlinLine &line, TSymbol &sym);
int doNoPattern(MerlinLine &line, TSymbol &sym); int doNoPattern(MerlinLine &line, TSymbol &sym);
int doMVN(MerlinLine &line, TSymbol &sym); int doMVN(MerlinLine &line, TSymbol &sym);
int doPER(MerlinLine &line, TSymbol &sym);
int doEQU(MerlinLine &line, TSymbol &sym); int doEQU(MerlinLine &line, TSymbol &sym);
int doXC(MerlinLine &line, TSymbol &sym); int doXC(MerlinLine &line, TSymbol &sym);

View File

@ -160,7 +160,7 @@ std::deque<Token> CLASS::exprToTokens(const std::string& expr)
numexpect = false; numexpect = false;
} }
else if ((c >= 'A') && (c <= 'A')) else if ((c >= 'A') && (c <= 'Z'))
{ {
state = 20; state = 20;
ident += c; ident += c;
@ -214,7 +214,6 @@ std::deque<Token> CLASS::shuntingYard(const std::deque<Token>& tokens)
{ {
case Token::Type::Symbol: case Token::Type::Symbol:
token.type = Token::Type::Number; token.type = Token::Type::Number;
if (token.str == "*") if (token.str == "*")
{ {
sprintf(buff, "%u", assembler.currentpc); sprintf(buff, "%u", assembler.currentpc);
@ -222,10 +221,14 @@ std::deque<Token> CLASS::shuntingYard(const std::deque<Token>& tokens)
} }
else else
{ {
//printf("symbol find |%s|\n",token.str.c_str());
sym = assembler.findSymbol(token.str); sym = assembler.findSymbol(token.str);
if (sym != NULL) if (sym != NULL)
{ {
sprintf(buff, "%u", sym->value); sym->used=true;
//printf("symbol found\n");
sprintf(buff, "%d", sym->value);
token.str = buff; token.str = buff;
} }
else else
@ -518,7 +521,8 @@ int CLASS::evaluate(std::string & e, int64_t &res)
{ {
case Token::Type::Symbol: case Token::Type::Symbol:
stack.push_back(std::stoi((char *)"0")); stack.push_back(std::stoi((char *)"0"));
//op = "Push " + token.str; op = "Push " + token.str;
//printf("shouldn't get this kind of token\n");
break; break;
case Token::Type::Number: case Token::Type::Number:
val = 0; val = 0;
@ -528,7 +532,7 @@ int CLASS::evaluate(std::string & e, int64_t &res)
val = -1; val = -1;
} }
stack.push_back(val); stack.push_back(val);
//op = "Push " + token.str; op = "Push " + token.str;
break; break;
case Token::Type::Operator: case Token::Type::Operator:
@ -546,6 +550,10 @@ int CLASS::evaluate(std::string & e, int64_t &res)
lhs = stack.back(); lhs = stack.back();
stack.pop_back(); stack.pop_back();
} }
else
{
printf("not enough parameters for the operator\n");
}
switch (token.str[0]) switch (token.str[0])
{ {
@ -580,11 +588,12 @@ int CLASS::evaluate(std::string & e, int64_t &res)
break; break;
case '&': case '&':
stack.push_back(lhs & rhs); stack.push_back(lhs & rhs);
break;
break; case '.': break; case '.':
stack.push_back(lhs | rhs); stack.push_back(lhs | rhs);
break; break;
} }
//op = "Push " + std::to_string(lhs) + " " + token.str + " " + std::to_string(rhs); op = "Push " + std::to_string(lhs) + " " + token.str + " " + std::to_string(rhs);
} }
break; break;
@ -596,7 +605,7 @@ int CLASS::evaluate(std::string & e, int64_t &res)
//debugReport(token, queue, stack, op); //debugReport(token, queue, stack, op);
} }
int64_t v = -1; int64_t v = 700;
if (stack.size() > 0) if (stack.size() > 0)
{ {
v = stack.back(); v = stack.back();

2
libpal
View File

@ -1 +1 @@
/projects/SQ/projects/pocoproj/libpal ../libpal

View File

@ -6,6 +6,7 @@ enum
{ {
P_ORG = 1, P_ORG = 1,
P_LST, P_LST,
P_SAV,
P_MAX P_MAX
}; };
@ -38,6 +39,9 @@ int CLASS::doPSEUDO(MerlinLine &line, TSymbol &sym)
case P_ORG: case P_ORG:
currentpc = line.expr_value; currentpc = line.expr_value;
break; break;
case P_SAV:
savepath = line.operand;
break;
case P_LST: case P_LST:
if (pass > 0) if (pass > 0)
{ {
@ -69,7 +73,7 @@ int CLASS::doXC(MerlinLine &line, TSymbol &sym)
std::string s; std::string s;
int res = 0; int res = 0;
if (cpumode < 2) if (cpumode < MODE_65816)
{ {
cpumode++; cpumode++;
} }
@ -87,8 +91,15 @@ int CLASS::doXC(MerlinLine &line, TSymbol &sym)
int CLASS::doMX(MerlinLine &line, TSymbol &sym) int CLASS::doMX(MerlinLine &line, TSymbol &sym)
{ {
mx = (uint8_t)(line.expr_value & 0xFF); if (cpumode < MODE_65816)
//printf("setting MX=%02X\n",mx); {
line.setError(errIncompatibleOpcode);
}
else
{
mx = (uint8_t)(line.expr_value & 0x03);
line.linemx = mx;
}
return (0); return (0);
} }
@ -127,6 +138,37 @@ int CLASS::doUNK(MerlinLine &line, TSymbol &sym)
return (res); return (res);
} }
// PER is a special case because it does strange address calcs
int CLASS::doPER(MerlinLine &line, TSymbol &sym)
{
int res;
int32_t value = 0;;
res = 0;
if ((line.addressmode == syn_abs) || (line.addressmode == syn_imm))
{
res = 3;
if (pass > 0)
{
// SGQ should check under/over flows
value = line.expr_value;
value -= line.startpc + 3;
//printf("addr calc=%08X %08X %08X\n",line.expr_value,line.startpc+3,value);
setOpcode(line, sym.opcode);
line.outbytes.push_back(value & 0xFF);
line.outbytes.push_back((value >> 8) & 0xFF);
line.outbytect = res;
}
}
if (res == 0)
{
line.setError(errBadAddressMode);
}
return (res);
}
int CLASS::doMVN(MerlinLine &line, TSymbol &sym) int CLASS::doMVN(MerlinLine &line, TSymbol &sym)
{ {
int res; int res;
@ -305,7 +347,10 @@ int CLASS::doJMP(MerlinLine &line, TSymbol &sym)
{ {
op = 0; // can't do these without an '816 op = 0; // can't do these without an '816
} }
res++; if (op == 0x5C)
{
res++;
}
} }
} }
@ -360,6 +405,9 @@ int CLASS::doBRANCH(MerlinLine & line, TSymbol & sym)
int64_t o64 = line.expr_value; int64_t o64 = line.expr_value;
int32_t o32 = (int32_t)(o64 & 0xFFFFFFFF); int32_t o32 = (int32_t)(o64 & 0xFFFFFFFF);
int32_t offset = o32 - line.startpc - res; int32_t offset = o32 - line.startpc - res;
// SGQ should check under/over flows
//printf("offset %d\n", offset); //printf("offset %d\n", offset);
setOpcode(line, op); setOpcode(line, op);
for (i = 0; i < (res - 1); i++) for (i = 0; i < (res - 1); i++)
@ -621,10 +669,8 @@ int CLASS::doEND(MerlinLine & line, TSymbol & sym)
int CLASS::doBYTE(MerlinLine & line, TSymbol & sym) int CLASS::doBYTE(MerlinLine & line, TSymbol & sym)
{ {
int res = -1; int res = 1;
res = line.inbytect;
//printf("inbytes=%d %02X\n",res,line.inbytes[0]);
if (pass > 0) if (pass > 0)
{ {
setOpcode(line, sym.opcode); setOpcode(line, sym.opcode);
@ -641,7 +687,7 @@ void CLASS::insertOpcodes(void)
pushopcode("ENT", 0x00, OP_PSUEDO, OPHANDLER(&CLASS::doPSEUDO)); pushopcode("ENT", 0x00, OP_PSUEDO, OPHANDLER(&CLASS::doPSEUDO));
pushopcode("ORG", P_ORG, OP_PSUEDO, OPHANDLER(&CLASS::doPSEUDO)); pushopcode("ORG", P_ORG, OP_PSUEDO, OPHANDLER(&CLASS::doPSEUDO));
pushopcode("DSK", 0x00, OP_PSUEDO, OPHANDLER(&CLASS::doPSEUDO)); pushopcode("DSK", 0x00, OP_PSUEDO, OPHANDLER(&CLASS::doPSEUDO));
pushopcode("SAV", 0x00, OP_PSUEDO, OPHANDLER(&CLASS::doPSEUDO)); pushopcode("SAV", P_SAV, OP_PSUEDO, OPHANDLER(&CLASS::doPSEUDO));
pushopcode("DS", 0x00, OP_PSUEDO, OPHANDLER(&CLASS::doPSEUDO)); pushopcode("DS", 0x00, OP_PSUEDO, OPHANDLER(&CLASS::doPSEUDO));
pushopcode("REL", 0x00, OP_PSUEDO, OPHANDLER(&CLASS::doPSEUDO)); pushopcode("REL", 0x00, OP_PSUEDO, OPHANDLER(&CLASS::doPSEUDO));
pushopcode("OBJ", 0x00, OP_PSUEDO, OPHANDLER(&CLASS::doPSEUDO)); pushopcode("OBJ", 0x00, OP_PSUEDO, OPHANDLER(&CLASS::doPSEUDO));
@ -711,25 +757,25 @@ void CLASS::insertOpcodes(void)
pushopcode("BNE", 0x03, OP_6502, OPHANDLER(&CLASS::doBRANCH)); pushopcode("BNE", 0x03, OP_6502, OPHANDLER(&CLASS::doBRANCH));
pushopcode("BPL", 0x00, OP_6502, OPHANDLER(&CLASS::doBRANCH)); pushopcode("BPL", 0x00, OP_6502, OPHANDLER(&CLASS::doBRANCH));
pushopcode("BRA", 0x40, OP_65816, OPHANDLER(&CLASS::doBRANCH)); pushopcode("BRA", 0x40, OP_65816, OPHANDLER(&CLASS::doBRANCH));
pushopcode("BRK", 0x00, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("BRK", 0x00, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("BRL", 0x20, OP_65816, OPHANDLER(&CLASS::doBRANCH)); pushopcode("BRL", 0x20, OP_65816, OPHANDLER(&CLASS::doBRANCH));
pushopcode("BVC", 0x01, OP_6502, OPHANDLER(&CLASS::doBRANCH)); pushopcode("BVC", 0x01, OP_6502, OPHANDLER(&CLASS::doBRANCH));
pushopcode("BVS", 0x81, OP_6502, OPHANDLER(&CLASS::doBRANCH)); pushopcode("BVS", 0x81, OP_6502, OPHANDLER(&CLASS::doBRANCH));
pushopcode("CLC", 0x18, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("CLC", 0x18, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("CLD", 0xD8, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("CLD", 0xD8, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("CLI", 0x58, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("CLI", 0x58, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("CLV", 0xB8, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("CLV", 0xB8, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("CMP", 0x06, OP_STD, OPHANDLER(&CLASS::doBase6502)); pushopcode("CMP", 0x06, OP_STD, OPHANDLER(&CLASS::doBase6502));
pushopcode("COP", 0x02, 1, OPHANDLER(&CLASS::doAddress)); pushopcode("COP", 0x02, 1, OPHANDLER(&CLASS::doAddress));
pushopcode("CPX", 0x07, OP_C0, OPHANDLER(&CLASS::doBase6502)); pushopcode("CPX", 0x07, OP_C0, OPHANDLER(&CLASS::doBase6502));
pushopcode("CPY", 0x06, OP_C0, OPHANDLER(&CLASS::doBase6502)); pushopcode("CPY", 0x06, OP_C0, OPHANDLER(&CLASS::doBase6502));
pushopcode("DEC", 0x06, OP_STX | OP_SPECIAL, OPHANDLER(&CLASS::doBase6502)); pushopcode("DEC", 0x06, OP_STX | OP_SPECIAL, OPHANDLER(&CLASS::doBase6502));
pushopcode("DEX", 0xCA, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("DEX", 0xCA, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("DEY", 0x88, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("DEY", 0x88, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("EOR", 0x02, OP_STD, OPHANDLER(&CLASS::doBase6502)); pushopcode("EOR", 0x02, OP_STD, OPHANDLER(&CLASS::doBase6502));
pushopcode("INC", 0x07, OP_STX | OP_SPECIAL, OPHANDLER(&CLASS::doBase6502)); pushopcode("INC", 0x07, OP_STX | OP_SPECIAL, OPHANDLER(&CLASS::doBase6502));
pushopcode("INX", 0xE8, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("INX", 0xE8, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("INY", 0xC8, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("INY", 0xC8, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("JML", 0x00, OP_65816, OPHANDLER(&CLASS::doJMP)); pushopcode("JML", 0x00, OP_65816, OPHANDLER(&CLASS::doJMP));
pushopcode("JMP", 0x01, OP_6502, OPHANDLER(&CLASS::doJMP)); pushopcode("JMP", 0x01, OP_6502, OPHANDLER(&CLASS::doJMP));
pushopcode("JSL", 0x02, OP_65816, OPHANDLER(&CLASS::doJMP)); pushopcode("JSL", 0x02, OP_65816, OPHANDLER(&CLASS::doJMP));
@ -740,58 +786,58 @@ void CLASS::insertOpcodes(void)
pushopcode("LSR", 0x02, OP_ASL, OPHANDLER(&CLASS::doBase6502)); pushopcode("LSR", 0x02, OP_ASL, OPHANDLER(&CLASS::doBase6502));
pushopcode("MVN", 0x00, OP_6502, OPHANDLER(&CLASS::doMVN)); pushopcode("MVN", 0x00, OP_6502, OPHANDLER(&CLASS::doMVN));
pushopcode("MVP", 0x01, OP_6502, OPHANDLER(&CLASS::doMVN)); pushopcode("MVP", 0x01, OP_6502, OPHANDLER(&CLASS::doMVN));
pushopcode("NOP", 0xEA, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("NOP", 0xEA, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("ORA", 0x00, OP_STD, OPHANDLER(&CLASS::doBase6502)); pushopcode("ORA", 0x00, OP_STD, OPHANDLER(&CLASS::doBase6502));
pushopcode("PEA", 0xF4, 2, OPHANDLER(&CLASS::doAddress)); pushopcode("PEA", 0xF4, 2, OPHANDLER(&CLASS::doAddress));
pushopcode("PEI", 0xD4, 1, OPHANDLER(&CLASS::doAddress)); pushopcode("PEI", 0xD4, 1, OPHANDLER(&CLASS::doAddress));
pushopcode("PER", 0x62, 2, OPHANDLER(&CLASS::doAddress)); pushopcode("PER", 0x62, 2, OPHANDLER(&CLASS::doPER));
pushopcode("PHA", 0x48, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("PHA", 0x48, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("PHB", 0x8B, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("PHB", 0x8B, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("PHD", 0x0B, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("PHD", 0x0B, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("PHK", 0x4B, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("PHK", 0x4B, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("PHP", 0x08, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("PHP", 0x08, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("PHX", 0xDA, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("PHX", 0xDA, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("PHY", 0x5A, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("PHY", 0x5A, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("PLA", 0x68, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("PLA", 0x68, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("PLB", 0xAB, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("PLB", 0xAB, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("PLD", 0x2B, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("PLD", 0x2B, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("PLP", 0x28, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("PLP", 0x28, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("PLX", 0xFA, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("PLX", 0xFA, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("PLY", 0x7A, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("PLY", 0x7A, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("REP", 0xC2, 1, OPHANDLER(&CLASS::doAddress)); pushopcode("REP", 0xC2, 1, OPHANDLER(&CLASS::doAddress));
pushopcode("ROL", 0x01, OP_ASL, OPHANDLER(&CLASS::doBase6502)); pushopcode("ROL", 0x01, OP_ASL, OPHANDLER(&CLASS::doBase6502));
pushopcode("ROR", 0x03, OP_ASL, OPHANDLER(&CLASS::doBase6502)); pushopcode("ROR", 0x03, OP_ASL, OPHANDLER(&CLASS::doBase6502));
pushopcode("RTI", 0x40, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("RTI", 0x40, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("RTL", 0x6B, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("RTL", 0x6B, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("RTS", 0x60, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("RTS", 0x60, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("SBC", 0x07, OP_STD, OPHANDLER(&CLASS::doBase6502)); pushopcode("SBC", 0x07, OP_STD, OPHANDLER(&CLASS::doBase6502));
pushopcode("SEC", 0x38, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("SEC", 0x38, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("SED", 0xF8, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("SED", 0xF8, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("SEI", 0x78, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("SEI", 0x78, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("SEP", 0xE2, 1, OPHANDLER(&CLASS::doAddress)); pushopcode("SEP", 0xE2, 1, OPHANDLER(&CLASS::doAddress));
pushopcode("STP", 0xDB, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("STP", 0xDB, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("STA", 0x04, OP_STD, OPHANDLER(&CLASS::doBase6502)); pushopcode("STA", 0x04, OP_STD, OPHANDLER(&CLASS::doBase6502));
pushopcode("STX", 0x04, OP_STX, OPHANDLER(&CLASS::doBase6502)); pushopcode("STX", 0x04, OP_STX, OPHANDLER(&CLASS::doBase6502));
pushopcode("STY", 0x04, OP_C0, OPHANDLER(&CLASS::doBase6502)); pushopcode("STY", 0x04, OP_C0, OPHANDLER(&CLASS::doBase6502));
pushopcode("STZ", 0x01, OP_6502, OPHANDLER(&CLASS::doNoPattern)); pushopcode("STZ", 0x01, OP_6502, OPHANDLER(&CLASS::doNoPattern));
pushopcode("TAX", 0xAA, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("TAX", 0xAA, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("TAY", 0xA8, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("TAY", 0xA8, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("TCD", 0x5B, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("TCD", 0x5B, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("TCS", 0x1B, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("TCS", 0x1B, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("TDC", 0x7B, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("TDC", 0x7B, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("TRB", 0x03, OP_6502, OPHANDLER(&CLASS::doNoPattern)); pushopcode("TRB", 0x03, OP_6502, OPHANDLER(&CLASS::doNoPattern));
pushopcode("TSB", 0x02, OP_6502, OPHANDLER(&CLASS::doNoPattern)); pushopcode("TSB", 0x02, OP_6502, OPHANDLER(&CLASS::doNoPattern));
pushopcode("TSC", 0x3B, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("TSC", 0x3B, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("TSX", 0xBA, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("TSX", 0xBA, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("TXA", 0x8A, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("TXA", 0x8A, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("TXS", 0x9A, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("TXS", 0x9A, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("TXY", 0x9B, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("TXY", 0x9B, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("TYA", 0x98, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("TYA", 0x98, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("TYX", 0xBB, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("TYX", 0xBB, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("WAI", 0xCB, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("WAI", 0xCB, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("WDM", 0x42, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("WDM", 0x42, 1, OPHANDLER(&CLASS::doAddress));
pushopcode("XBA", 0xEB, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("XBA", 0xEB, OP_6502, OPHANDLER(&CLASS::doBYTE));
pushopcode("XCE", 0xFB, OP_6502 | OP_ONEBYTE, OPHANDLER(&CLASS::doBYTE)); pushopcode("XCE", 0xFB, OP_6502, OPHANDLER(&CLASS::doBYTE));
} }
#undef CLASS #undef CLASS

View File

@ -9,7 +9,7 @@ debug=on
[application] [application]
timezone=America/Los_Angeles timezone=America/Los_Angeles
[qasm] [global]
path1= path1=
path2= path2=
path3= path3=
@ -17,7 +17,12 @@ path4=
path5= path5=
[asm] [asm]
casesen=0 casesen=true
showmx=true
lst=true
# can be M6502, M65C02, M65816
cpu=M6502
trackrep=false

View File

@ -1,8 +1,11 @@
lst off ;lst off
xc off xc off
xc xc
xc xc
mx %00
MXX = $00
mx MXX
org $4000 org $4000
dp = $A5 dp = $A5
@ -11,7 +14,8 @@ lexpr = $010203
immed = $123456 immed = $123456
neg equ -16 neg equ -16
lst
;lst off
start00 start00
brk ;$00 brk ;$00
ora (dp,x) ora (dp,x)
@ -87,7 +91,7 @@ start30
start40 start40
rti rti
eor (dp,x) eor (dp,x)
wdm wdm $01
eor dp,s eor dp,s
mvp dp,dp+1 mvp dp,dp+1
eor dp eor dp
@ -123,7 +127,7 @@ start50
start60 start60
rts rts
adc (dp,x) adc (dp,x)
per expr per start60
adc dp,s adc dp,s
stz dp stz dp
adc dp adc dp
@ -213,7 +217,7 @@ startA0
startB0 startB0
bcs startB0 bcs startB0
lda (dp),y lda (dp),y
lda (dp,s) lda dp,s
lda (dp,s),y lda (dp,s),y
ldy dp,x ldy dp,x
lda dp,x lda dp,x
@ -232,6 +236,7 @@ startC0
cpy #immed cpy #immed
cmp (dp,x) cmp (dp,x)
rep #$FF rep #$FF
mx MXX
cmp dp,s cmp dp,s
cpy dp cpy dp
cmp dp cmp dp
@ -268,6 +273,7 @@ startE0
cpx #immed cpx #immed
sbc (dp,x) sbc (dp,x)
sep #$FF sep #$FF
mx MXX
sbc dp,s sbc dp,s
cpx dp cpx dp
sbc dp sbc dp
@ -302,7 +308,8 @@ down
sbc expr,x sbc expr,x
inc expr,x inc expr,x
sbcl lexpr,x sbcl lexpr,x
;lst ;lst
;chk ;chk
lst off lst off
sav ./test.bin