Skip to content

Commit

Permalink
[Arduino] Fix pseudo instruction lookup on Arduino
Browse files Browse the repository at this point in the history
  • Loading branch information
tgtakaoka committed Oct 7, 2024
1 parent 4b9a337 commit 549cbc0
Show file tree
Hide file tree
Showing 4 changed files with 29 additions and 28 deletions.
34 changes: 18 additions & 16 deletions src/arduino_example.h
Original file line number Diff line number Diff line change
Expand Up @@ -140,22 +140,20 @@ struct Example {
_cli.println(F("unknown CPU"));
return true;
}
if (strcasecmp_P(line, PSTR("ORG")) == 0 || strncasecmp_P(line, PSTR("ORG "), 4) == 0) {
if (!isAsm() && strncasecmp_P(line, PSTR("ORG "), 4) == 0) {
const auto org = skipSpaces(line + 3);
if (*org) {
uint32_t addr;
const auto p = StrMemory::readNumber(org, &addr);
if (p == org) {
_cli.println(F("illegal ORG address"));
return true;
}
const auto max = addrMax();
if (max && addr >= max) {
_cli.println(F("ORG overflow range"));
return true;
}
_origin = addr;
uint32_t addr;
const auto p = StrMemory::readNumber(org, &addr);
if (p == org) {
_cli.println(F("illegal ORG address"));
return true;
}
const auto max = addrMax();
if (max && addr >= max) {
_cli.println(F("ORG overflow range"));
return true;
}
_origin = addr;
printAddress(_origin);
_cli.println();
return true;
Expand Down Expand Up @@ -302,8 +300,12 @@ struct Example {
printAddress(insn.address(), ':');
printBytes(insn.bytes(), insn.length());
_cli.println();
_origin += insn.length() / addrUnit();
_origin &= max - 1;
if (insn.address() == _origin) {
_origin += insn.length() / addrUnit();
_origin &= max - 1;
} else {
_origin = insn.address();
}
}
}

Expand Down
4 changes: 2 additions & 2 deletions src/asm_base.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ PROGMEM constexpr Pseudos PSEUDO_TABLE{ARRAY_RANGE(PSEUDOS)};
Assembler::Assembler(
const ValueParser::Plugins &plugins, const Pseudos &pseudos, const OptionBase *option)
: _parser(plugins),
_pseudos(pseudos),
_pseudos(&pseudos),
_commonOptions(&_opt_listRadix),
_options(option),
_opt_listRadix(this, &Assembler::setListRadix, OPT_INT_LIST_RADIX, OPT_DESC_LIST_RADIX,
Expand Down Expand Up @@ -103,7 +103,7 @@ Error Assembler::encode(const char *line, Insn &insn, const SymbolTable *symtab)
}

Error Assembler::processPseudo(StrScanner &scan, Insn &insn) {
const auto *p = _pseudos.search(insn);
const auto *p = _pseudos->search(insn);
if (p == nullptr)
p = PSEUDO_TABLE.search(insn);
return p ? p->invoke(this, scan, insn) : UNKNOWN_DIRECTIVE;
Expand Down
2 changes: 1 addition & 1 deletion src/asm_base.h
Original file line number Diff line number Diff line change
Expand Up @@ -91,7 +91,7 @@ struct Assembler {

protected:
const ValueParser _parser;
const pseudo::Pseudos _pseudos;
const pseudo::Pseudos *const _pseudos;
const Options _commonOptions;
const Options _options;
const IntOption<Assembler> _opt_listRadix;
Expand Down
17 changes: 8 additions & 9 deletions src/pseudos.h
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ struct Pseudo {
using Handler = Error (Assembler::*)(StrScanner &scan, Insn &insn, uint8_t);

constexpr Pseudo(const /*PROGMEM*/ char *name_P, Handler handler, uint8_t extra = 0)
: _name_P(name_P), _handler(handler), _extra(extra) {}
: _name_P(name_P), _handler_P(handler), _extra_P(extra) {}

const /*PROGMEM*/ char *name_P() const {
return reinterpret_cast<const char *>(pgm_read_ptr(&_name_P));
Expand All @@ -45,24 +45,23 @@ struct Pseudo {

private:
const /*PROGMEM*/ char *const _name_P;
const Handler _handler;
const uint8_t _extra;
const Handler _handler_P;
const uint8_t _extra_P;

Handler handler() const {
Handler h;
memcpy_P(&h, &_handler, sizeof(Handler));
memcpy_P(&h, &_handler_P, sizeof(Handler));
return h;
}

uint8_t extra() const { return pgm_read_byte(&_extra); }
uint8_t extra() const { return pgm_read_byte(&_extra_P); }
};

struct Pseudos {
constexpr Pseudos(const /*PROGMEM*/ Pseudo *table, const /*PROGMEM*/ Pseudo *end) : _table(table, end) {}
constexpr Pseudos(const /*PROGMEM*/ Pseudo *table_P, const /*PROGMEM*/ Pseudo *end_P)
: _table(table_P, end_P) {}

const Pseudo *search(const Insn &insn) const {
return _table.binarySearch(insn, comparator);
}
const Pseudo *search(const Insn &insn) const { return _table.binarySearch(insn, comparator); }

private:
const table::Table<Pseudo> _table;
Expand Down

0 comments on commit 549cbc0

Please sign in to comment.