diff options
author | mrb0nk500 <b0nk@b0nk.xyz> | 2022-01-18 10:40:18 -0400 |
---|---|---|
committer | mrb0nk500 <b0nk@b0nk.xyz> | 2022-01-18 10:40:18 -0400 |
commit | bb9dba22d81c5a2af6754a4377377cb3b38c7c37 (patch) | |
tree | c9bb976f151976809a77854c6e9a726359e21c00 | |
parent | 30d38265c2e868e141ed3b7f747d44ccfa146259 (diff) |
Add support for getting an inverted addressing mode
bitmask in `opcode-bitmask-gen`.
-rw-r--r-- | opcode-bitmask-gen.c | 14 |
1 files changed, 11 insertions, 3 deletions
diff --git a/opcode-bitmask-gen.c b/opcode-bitmask-gen.c index 3fe26fa..c4fa446 100644 --- a/opcode-bitmask-gen.c +++ b/opcode-bitmask-gen.c @@ -417,17 +417,25 @@ void set_extension(int *ext, int ext2, int force, const char *reason, ...) { } uint32_t get_addr_mode_bits(const char **list, int *ext) { + const uint32_t max_addr_mode_mask = -(uint32_t)1 >> (32-AMT_LEN); uint32_t addr_modes = 0; + int is_ext = 0; for (int i = 0; list[i] != NULL; ++i) { - const char *str = list[i]; + const int is_inv = (list[i][0] == '~'); + const char *str = list[i]+is_inv; + const uint32_t ext_mask = (AM_ORTHO|AM_ORTHO2|AM_EIND|AM_EIND2|AM_AIND|AM_AINDX|AM_AINDY); + uint32_t bits = 0; for (int j = 0; j < AMT_LEN; ++j) { if (!strcasecmp(str, adrmode[j])) { //printf("i: %i, str: %s, adrmode: %s\n", i, str, adrmode[i]); - addr_modes |= (1 << j); + bits |= (1 << j); } } + is_ext = (bits & ext_mask) ? 1 : is_ext; + addr_modes |= (is_inv) ? ~(bits) & (max_addr_mode_mask & (is_ext) ? -1 : ~ext_mask) : bits; + addr_modes &= (is_ext && (bits & ~(AM_ORTHO|AM_ORTHO2))) ? ~(AM_ORTHO|AM_ORTHO2) : -1; } - if (addr_modes & (AM_ORTHO|AM_ORTHO2|AM_EIND|AM_EIND2|AM_AIND|AM_AINDX|AM_AINDY)) { + if (is_ext) { const int ext2 = (addr_modes & AM_ORTHO) ? ORTHO : EXT; const char *addr_mode_reason = (ext2 == ORTHO) ? "was set to ortho" : "is a base extension addressing mode"; set_extension(ext, ext2, 1, "The addressing mode %s.\n", addr_mode_reason); |