From d36bb13f52b3899fd0f57e38f00d97e2c3a0f627 Mon Sep 17 00:00:00 2001 From: Clyne Sullivan Date: Sat, 18 Mar 2023 12:40:46 -0400 Subject: [PATCH] -Wconversion --- Makefile | 3 +- alee-standalone.cpp | 6 +-- alee.cpp | 6 +-- libalee/corewords.cpp | 95 +++++++++++++++++++++--------------------- libalee/corewords.hpp | 10 ++--- libalee/ctype.cpp | 16 ------- libalee/ctype.hpp | 7 ---- libalee/dictionary.cpp | 51 ++++++++++++++--------- libalee/dictionary.hpp | 1 + libalee/parser.cpp | 29 +++++++------ libalee/state.cpp | 4 +- libalee/types.cpp | 2 +- libalee/types.hpp | 14 +++++-- memdict.hpp | 4 ++ msp430/alee-msp430.cpp | 2 +- splitmemdict.hpp | 24 ++++++----- 16 files changed, 142 insertions(+), 132 deletions(-) diff --git a/Makefile b/Makefile index 3ae2e23..9deec8b 100644 --- a/Makefile +++ b/Makefile @@ -1,5 +1,5 @@ CXXFLAGS += -std=c++17 -g3 -ggdb -O0 \ - -pedantic -Wall -Wextra -Werror -Weffc++ \ + -pedantic -Wall -Wextra -Werror -Weffc++ -Wconversion \ -fno-exceptions -fno-threadsafe-statics -fno-rtti #-fstack-usage CXXFILES := $(wildcard libalee/*.cpp) @@ -10,6 +10,7 @@ all: alee msp430: CXX := msp430-elf32-g++ msp430: AR := msp430-elf32-gcc-ar +msp430: CXXFLAGS += -I. msp430: CXXFLAGS += -Os -mmcu=msp430g2553 -ffunction-sections -fdata-sections msp430: CXXFLAGS += -DMEMDICTSIZE=200 -flto msp430: LDFLAGS += -L/opt/msp430-elf32/include -Tmsp430/msp430g2553.ld -Wl,-gc-sections diff --git a/alee-standalone.cpp b/alee-standalone.cpp index 5c9f8a8..488d3ba 100644 --- a/alee-standalone.cpp +++ b/alee-standalone.cpp @@ -51,10 +51,10 @@ int main(int argc, char *argv[]) static void readchar(State& state) { - auto idx = state.dict.read(Dictionary::Input); + Addr idx = state.dict.read(Dictionary::Input); Addr addr = Dictionary::Input + sizeof(Cell) + idx; - auto c = std::cin.get(); + auto c = static_cast(std::cin.get()); if (isupper(c)) c += 32; state.dict.writebyte(addr, c ? c : ' '); @@ -76,7 +76,7 @@ static void load(State& state) Addr i = 0; while (file.good()) - state.dict.writebyte(i++, file.get()); + state.dict.writebyte(i++, file.get() & 0xFFu); } void user_sys(State& state) diff --git a/alee.cpp b/alee.cpp index dfe85d1..c7c9ddf 100644 --- a/alee.cpp +++ b/alee.cpp @@ -54,9 +54,9 @@ int main(int argc, char *argv[]) static void readchar(State& state) { auto idx = state.dict.read(Dictionary::Input); - Addr addr = Dictionary::Input + sizeof(Cell) + idx; + auto addr = static_cast(Dictionary::Input + sizeof(Cell) + idx); - auto c = std::cin.get(); + auto c = static_cast(std::cin.get()); if (isupper(c)) c += 32; state.dict.writebyte(addr, c ? c : ' '); @@ -77,7 +77,7 @@ static void load(State& state) std::ifstream file ("alee.dat", std::ios::binary); for (Addr i = 0; file.good(); i++) - state.dict.writebyte(i, file.get()); + state.dict.writebyte(i, file.get() & 0xFFu); } void user_sys(State& state) diff --git a/libalee/corewords.cpp b/libalee/corewords.cpp index 9fef7b1..1344ca0 100644 --- a/libalee/corewords.cpp +++ b/libalee/corewords.cpp @@ -54,11 +54,25 @@ void find(State& state, Word word) } } -void CoreWords::run(unsigned int index, State& state) +void CoreWords::run(Cell ins, State& state) { Cell cell; DoubleCell dcell; + Addr index = ins; + + auto popd = [](State& s) { + DoubleCell dcell = s.pop(); + dcell <<= sizeof(Cell) * 8; + dcell |= static_cast(s.pop()); + return dcell; + }; + + auto pushd = [](State& s, DoubleCell d) { + s.push(static_cast(d)); + s.push(static_cast(d >> (sizeof(Cell) * 8))); + }; + execute: if (index >= Dictionary::Begin) { // must be calling a defined subroutine @@ -95,22 +109,17 @@ execute: case 8: // mul ( n n -- d ) cell = state.pop(); dcell = state.pop() * cell; - state.push(dcell); - state.push(dcell >> (sizeof(Cell) * 8)); + pushd(state, dcell); break; case 9: // div ( d n -- n ) cell = state.pop(); - dcell = state.pop(); - dcell <<= sizeof(Cell) * 8; - dcell |= static_cast(state.pop()); - state.push(dcell / cell); + dcell = popd(state); + state.push(static_cast(dcell / cell)); break; case 10: // mod ( d n -- n ) cell = state.pop(); - dcell = state.pop(); - dcell <<= sizeof(Cell) * 8; - dcell |= static_cast(state.pop()); - state.push(dcell % cell); + dcell = popd(state); + state.push(static_cast(dcell % cell)); break; case 11: // peek if (state.pop()) @@ -123,7 +132,7 @@ execute: if (auto addr = state.pop(); cell) state.dict.write(addr, state.pop()); else - state.dict.writebyte(addr, state.pop()); + state.dict.writebyte(addr, state.pop() & 0xFFu); break; case 13: // pushr state.pushr(state.pop()); @@ -175,16 +184,14 @@ execute: std::longjmp(state.jmpbuf, static_cast(Error::exit)); break; case 26: // semic - { state.dict.add(findi("exit")); state.compiling(false); - auto addr = state.pop(); - state.dict.write(addr, - (state.dict.read(addr) & 0x1F) | - ((addr - state.dict.latest()) << 6)); - state.dict.latest(addr); - } + cell = state.pop(); + dcell = (cell - state.dict.latest()) << 6; + state.dict.write(cell, + (state.dict.read(cell) & 0x1F) | static_cast(dcell)); + state.dict.latest(cell); break; case 27: // _jmp0 if (state.pop()) { @@ -196,10 +203,10 @@ execute: state.ip = state.beyondip(); return; case 29: // depth - state.push(state.size()); + state.push(static_cast(state.size())); break; case 30: // _rdepth - state.push(state.rsize()); + state.push(static_cast(state.rsize())); break; case 31: // _in state.input(state); @@ -213,26 +220,19 @@ execute: } break; case 33: // find - { - const Addr caddr = state.pop(); - const Word word { - static_cast(caddr + 1), - static_cast(caddr + 1 + state.dict.readbyte(caddr)) - }; - find(state, word); - } + cell = state.pop(); + find(state, + Word::fromLength(static_cast(cell + 1), + state.dict.readbyte(cell))); break; case 34: // _uma { const auto plus = state.pop(); cell = state.pop(); - dcell = state.pop(); - dcell <<= sizeof(Cell) * 8; - dcell |= static_cast(state.pop()); + dcell = popd(state); dcell *= static_cast(cell); dcell += static_cast(plus); - state.push(dcell); - state.push(dcell >> (sizeof(Cell) * 8)); + pushd(state, dcell); } break; case 35: // u< @@ -242,17 +242,17 @@ execute: break; case 36: // um/mod cell = state.pop(); - dcell = state.pop(); - dcell <<= sizeof(Cell) * 8; - dcell |= static_cast(state.pop()); + dcell = popd(state); - state.push(static_cast(dcell) % - static_cast(cell)); - state.push(static_cast(dcell) / - static_cast(cell)); + state.push(static_cast( + static_cast(dcell) % + static_cast(cell))); + state.push(static_cast( + static_cast(dcell) / + static_cast(cell))); break; default: - state.push(index - WordCount); + state.push(ins - WordCount); break; } @@ -260,17 +260,18 @@ execute: } template -int findi(Iter it, int size) +Cell findi(Iter it, std::size_t size) { auto ptr = CoreWords::wordsarr; - int wordsi = 0; + Cell wordsi = 0; while (ptr < CoreWords::wordsarr + sizeof(CoreWords::wordsarr)) { auto end = ptr; while (*end) ++end; - if (end - ptr == size && Dictionary::equal(ptr, end, it)) + std::size_t wordsize = end - ptr; + if (wordsize == size && Dictionary::equal(ptr, end, it)) return wordsi; ++wordsi; @@ -280,12 +281,12 @@ int findi(Iter it, int size) return -1; } -int CoreWords::findi(const char *word) +Cell CoreWords::findi(const char *word) { return ::findi(word, strlen(word)); } -int CoreWords::findi(State& state, Word word) +Cell CoreWords::findi(State& state, Word word) { return ::findi(word.begin(&state.dict), word.size()); } diff --git a/libalee/corewords.hpp b/libalee/corewords.hpp index 993a420..d4d7ef2 100644 --- a/libalee/corewords.hpp +++ b/libalee/corewords.hpp @@ -31,20 +31,20 @@ void user_sys(State&); class CoreWords { public: - constexpr static std::size_t WordCount = 37; - constexpr static int Semicolon = 26; + constexpr static Cell WordCount = 37; + constexpr static Cell Semicolon = 26; /** * Finds execution token that corresponds to the given word. * Returns -1 if not found. */ - static int findi(const char *); - static int findi(State&, Word); + static Cell findi(const char *); + static Cell findi(State&, Word); /** * Executes the given CoreWord execution token using the given state. */ - static void run(unsigned int, State&); + static void run(Cell, State&); constexpr static char wordsarr[] = "_lit\0drop\0dup\0swap\0pick\0sys\0" diff --git a/libalee/ctype.cpp b/libalee/ctype.cpp index a0c8dc1..547cd11 100644 --- a/libalee/ctype.cpp +++ b/libalee/ctype.cpp @@ -22,31 +22,15 @@ bool isspace(uint8_t c) { return c == ' ' || c == '\t' || c == '\r' || c == '\n'; } -bool isspace(char c) { - return isspace(static_cast(c)); -} - bool isdigit(uint8_t c) { return c >= '0' && c <= '9'; } -bool isdigit(char c) { - return isdigit(static_cast(c)); -} - bool isalpha(uint8_t c) { return isupper(c) || (c >= 'a' && c <= 'z'); } -bool isalpha(char c) { - return isalpha(static_cast(c)); -} - bool isupper(uint8_t c) { return c >= 'A' && c <= 'Z'; } -bool isupper(char c) { - return isupper(static_cast(c)); -} - diff --git a/libalee/ctype.hpp b/libalee/ctype.hpp index dfc6f50..5842dfb 100644 --- a/libalee/ctype.hpp +++ b/libalee/ctype.hpp @@ -26,16 +26,9 @@ #include bool isspace(uint8_t); -bool isspace(char); - bool isdigit(uint8_t); -bool isdigit(char); - bool isalpha(uint8_t); -bool isalpha(char); - bool isupper(uint8_t); -bool isupper(char); #endif // ALEEFORTH_CTYPE_HPP diff --git a/libalee/dictionary.cpp b/libalee/dictionary.cpp index 81b5c64..7ae0043 100644 --- a/libalee/dictionary.cpp +++ b/libalee/dictionary.cpp @@ -33,7 +33,14 @@ void Dictionary::initialize() Addr Dictionary::allot(Cell amount) noexcept { Addr old = here(); - here(old + amount); + decltype(capacity()) neww = old + amount; + + if (neww < capacity()) { + write(Here, static_cast(neww)); + } else { + // TODO + } + return old; } @@ -44,9 +51,11 @@ void Dictionary::add(Cell value) noexcept Addr Dictionary::aligned(Addr addr) const noexcept { - auto unaligned = addr & (sizeof(Cell) - sizeof(uint8_t)); - if (unaligned) - addr += sizeof(Cell) - unaligned; + Addr unaligned = addr & (sizeof(Cell) - sizeof(uint8_t)); + if (unaligned) { + addr += sizeof(Cell); + addr -= unaligned; + } return addr; } @@ -59,7 +68,9 @@ Addr Dictionary::alignhere() noexcept void Dictionary::addDefinition(Word word) noexcept { - add(word.size()); + Cell wsize = word.size(); + add(wsize); + for (auto w = word.start; w != word.wend; ++w) writebyte(allot(1), readbyte(w)); @@ -70,12 +81,11 @@ Addr Dictionary::find(Word word) noexcept { Addr lt = latest(); for (;;) { - const auto l = static_cast(read(lt)); + const Addr l = read(lt); const Addr len = l & 0x1F; - const Word lw { - static_cast(lt + sizeof(Cell)), - static_cast(lt + sizeof(Cell) + len) - }; + Word lw; + lw.start = lt + sizeof(Cell); + lw.wend = lw.start + len; if (equal(word, lw)) return lt; @@ -90,20 +100,21 @@ Addr Dictionary::find(Word word) noexcept Addr Dictionary::getexec(Addr addr) noexcept { - const auto len = read(addr) & 0x1F; - return aligned(addr + sizeof(Cell) + len); + const Addr len = read(addr) & 0x1Fu; + addr += sizeof(Cell); + addr += len; + return aligned(addr); } Word Dictionary::input() noexcept { - const auto src = read(Dictionary::Source); - const auto end = read(Dictionary::SourceLen); - auto idx = read(Dictionary::Input); + const Addr src = read(Dictionary::Source); + const Addr end = read(Dictionary::SourceLen); + uint8_t idx = read(Dictionary::Input) & 0xFFu; - Word word { - static_cast(src + idx), - static_cast(src + idx) - }; + Word word; + word.start = src + idx; + word.wend = word.start; while (idx < end) { auto ch = readbyte(word.wend); @@ -121,7 +132,7 @@ Word Dictionary::input() noexcept ++idx; } - writebyte(Dictionary::Input, idx + 1); + writebyte(Dictionary::Input, ++idx); return word; } diff --git a/libalee/dictionary.hpp b/libalee/dictionary.hpp index 02fb1cc..2f17a77 100644 --- a/libalee/dictionary.hpp +++ b/libalee/dictionary.hpp @@ -64,6 +64,7 @@ public: virtual void write(Addr, Cell) noexcept = 0; virtual uint8_t readbyte(Addr) const noexcept = 0; virtual void writebyte(Addr, uint8_t) noexcept = 0; + virtual unsigned long int capacity() const noexcept = 0; /** * Does initial dictionary setup, required before use for execution. diff --git a/libalee/parser.cpp b/libalee/parser.cpp index 464bc2f..cdec1a5 100644 --- a/libalee/parser.cpp +++ b/libalee/parser.cpp @@ -20,13 +20,16 @@ #include "ctype.hpp" #include "parser.hpp" -#include - Error Parser::parse(State& state, const char *str) { auto addr = Dictionary::Input; + + Cell len = 0; + for (auto ptr = str; *ptr; ++ptr) + ++len; + state.dict.write(addr, 0); - state.dict.write(Dictionary::SourceLen, std::strlen(str)); + state.dict.write(Dictionary::SourceLen, len); addr += sizeof(Cell); while (*str) @@ -53,17 +56,18 @@ Error Parser::parseSource(State& state) Error Parser::parseWord(State& state, Word word) { - int ins, imm; + bool imm; + Addr ins = state.dict.find(word); - ins = state.dict.find(word); + if (ins == 0) { + auto cw = CoreWords::findi(state, word); - if (ins <= 0) { - ins = CoreWords::findi(state, word); - - if (ins < 0) + if (cw < 0) { return parseNumber(state, word); - else + } else { + ins = cw; imm = ins == CoreWords::Semicolon; + } } else { imm = state.dict.read(ins) & Dictionary::Immediate; ins = state.dict.getexec(ins); @@ -107,11 +111,12 @@ Error Parser::parseNumber(State& state, Word word) if (inv) result *= -1; - Cell value = static_cast(result); + auto value = static_cast(result); if (state.compiling()) { auto ins = CoreWords::findi("_lit"); - if (value >= 0 && value < static_cast(Dictionary::Begin - CoreWords::WordCount)) { + const Cell maxlit = Dictionary::Begin - CoreWords::WordCount; + if (value >= 0 && value < maxlit) { state.dict.add(value + CoreWords::WordCount); } else { state.dict.add(ins); diff --git a/libalee/state.cpp b/libalee/state.cpp index bfd29d1..b19d291 100644 --- a/libalee/state.cpp +++ b/libalee/state.cpp @@ -81,11 +81,11 @@ void State::reset() std::size_t State::size() const noexcept { - return std::distance(dstack, static_cast(dsp)); + return dsp - dstack; } std::size_t State::rsize() const noexcept { - return std::distance(rstack, static_cast(rsp)); + return rsp - rstack; } diff --git a/libalee/types.cpp b/libalee/types.cpp index fe6210e..baaa5ce 100644 --- a/libalee/types.cpp +++ b/libalee/types.cpp @@ -19,7 +19,7 @@ #include "dictionary.hpp" #include "types.hpp" -unsigned Word::size() const noexcept +Addr Word::size() const noexcept { return wend - start; } diff --git a/libalee/types.hpp b/libalee/types.hpp index f23f92e..95daee6 100644 --- a/libalee/types.hpp +++ b/libalee/types.hpp @@ -52,14 +52,20 @@ enum class Error : int { */ struct Word { - struct iterator; + Addr start; + Addr wend; + + constexpr explicit Word(Addr s = 0, Addr e = 0): + start(s), wend(e) {} - Addr start = 0; - Addr wend = 0; + static constexpr Word fromLength(Addr s, Addr l) { + return Word(s, s + l); + } - unsigned size() const noexcept; + Addr size() const noexcept; // Iterators provided for std::equal. + struct iterator; iterator begin(const Dictionary *); iterator end(const Dictionary *); diff --git a/memdict.hpp b/memdict.hpp index 22841c5..c88bc7d 100644 --- a/memdict.hpp +++ b/memdict.hpp @@ -46,6 +46,10 @@ public: virtual void writebyte(Addr addr, uint8_t value) noexcept final { dict[addr] = value; } + + virtual unsigned long int capacity() const noexcept final { + return sizeof(dict); + } }; #endif // ALEEFORTH_MEMDICT_HPP diff --git a/msp430/alee-msp430.cpp b/msp430/alee-msp430.cpp index 0ec6c88..b4f1b04 100644 --- a/msp430/alee-msp430.cpp +++ b/msp430/alee-msp430.cpp @@ -153,7 +153,7 @@ void user_sys(State& state) break; case 3: { auto addr = state.pop(); - *reinterpret_cast(addr) = state.pop(); } + *reinterpret_cast(addr) = state.pop() & 0xFFu; } break; case 4: state.push(*reinterpret_cast(state.pop())); diff --git a/splitmemdict.hpp b/splitmemdict.hpp index 45a9ee1..730d103 100644 --- a/splitmemdict.hpp +++ b/splitmemdict.hpp @@ -35,6 +35,10 @@ class SplitMemDict : public Dictionary uint8_t rwdict[MemDictSize - Dictionary::Begin] = {0}; uint8_t extra[Dictionary::Begin]; + Addr convertAddress(Addr addr) const noexcept { + return addr < RON ? addr : static_cast(addr - RON); + } + public: constexpr explicit SplitMemDict(const uint8_t *rod): rodict(rod) @@ -51,14 +55,12 @@ public: virtual Cell read(Addr addr) const noexcept final { const uint8_t *dict; - if (addr < RON) { + if (addr < RON) dict = addr < Dictionary::Begin ? extra : rodict; - } else { + else dict = rwdict; - addr -= RON; - } - return *reinterpret_cast(dict + addr); + return *reinterpret_cast(dict + convertAddress(addr)); } virtual void write(Addr addr, Cell value) noexcept final { @@ -70,14 +72,12 @@ public: virtual uint8_t readbyte(Addr addr) const noexcept final { const uint8_t *dict; - if (addr < RON) { + if (addr < RON) dict = addr < Dictionary::Begin ? extra : rodict; - } else { + else dict = rwdict; - addr -= RON; - } - return dict[addr]; + return dict[convertAddress(addr)]; } virtual void writebyte(Addr addr, uint8_t value) noexcept final { @@ -86,6 +86,10 @@ public: else if (addr < Dictionary::Begin) extra[addr] = value; } + + virtual unsigned long int capacity() const noexcept final { + return RON + sizeof(extra) + sizeof(rwdict); + } }; #endif // ALEEFORTH_SPLITMEMDICT_HPP