]> code.bitgloo.com Git - bitgloo/alee-forth.git/commitdiff
no more cstring; 16mhz/115200 msp430; fix dict init
authorClyne Sullivan <clyne@bitgloo.com>
Sun, 12 Nov 2023 19:38:30 +0000 (14:38 -0500)
committerClyne Sullivan <clyne@bitgloo.com>
Sun, 12 Nov 2023 19:38:30 +0000 (14:38 -0500)
alee.cpp
libalee/corewords.hpp
libalee/ctype.hpp
libalee/dictionary.cpp
libalee/parser.cpp
libalee/state.cpp
msp430/alee-msp430.cpp
msp430/msp430fr2476.ld
splitmemdictrw.hpp

index a1540172a0556ecaa55fbbdf2de95b3dd643e62d..5aba8510552ea0d31358cb0f91dee06ac89c3411 100644 (file)
--- a/alee.cpp
+++ b/alee.cpp
@@ -25,7 +25,6 @@
 #include <vector>
 
 #ifdef ALEE_MSP430
-#include <cstring>
 #include "lzss.h"
 static const
 #include "msp430fr2476_all.h"
@@ -190,7 +189,7 @@ Error findword(State& state, Word word)
         if (c != LZSS_MAGIC_SEPARATOR) {
             *lzptr++ = (char)c;
         } else {
-            if (lzwlen == lzptr - lzbuf - 2 && strncmp(lzword, lzbuf, lzptr - lzbuf - 2) == 0) {
+            if (lzwlen == lzptr - lzbuf - 2 && std::equal(lzbuf, lzptr - 2, lzword)) {
                 lzwlen = (*(lzptr - 2) << 8) | *(lzptr - 1);
                 return 1;
             } else {
index 25f6a6ec2ab5a716283b836c98b07a0113f2a3ac..d5c35eaf3541735e8d1d9187c33ab62596855c60 100644 (file)
 #ifndef ALEEFORTH_COREWORDS_HPP
 #define ALEEFORTH_COREWORDS_HPP
 
+#include "ctype.hpp"
 #include "types.hpp"
 #include "state.hpp"
 
-#include <cstring>
-
 /**
  * To be implemented by the user, this function is called when the `sys` word
  * is executed.
@@ -42,7 +41,7 @@ public:
      */
     static Cell findi(State&, Word);
     consteval static Cell findi(const char *word) {
-        return findi(word, std::strlen(word));
+        return findi(word, strlen(word));
     }
 
     /**
@@ -67,7 +66,7 @@ private:
         const char *ptr = CoreWords::wordsarr;
 
         for (Cell wordsi = 0; wordsi < WordCount; ++wordsi) {
-            std::size_t wordsize = std::strlen(ptr);
+            std::size_t wordsize = strlen(ptr);
 
             if (wordsize == size && Dictionary::equal(ptr, ptr + wordsize, it))
                 return wordsi;
index 878c747329d0a3e5b3639e0ff2792f77ddd3a5ca..499a90fe1afe3467323b22a0e2b0508fe5d83e41 100644 (file)
 
 #include <cstdint>
 
+constexpr inline unsigned strlen(const char * const s) {
+    unsigned i = 0;
+    while (s[i]) i++;
+    return i;
+}
+
 constexpr inline bool isspace(uint8_t c) {
     return c == ' ' || c == '\t' || c == '\r' || c == '\n';
 }
index 6c359bd0210747acaf095c6ceffb8ed15183d467..a86531da7b6cbf7adca89cbb8ac73ebe21f49f74 100644 (file)
@@ -18,8 +18,6 @@
 
 #include "dictionary.hpp"
 
-#include <cstring>
-
 void Dictionary::initialize()
 {
     write(Base, 10);
index 3236ae223e4b6c56f6917452745961e1ea4a8428..19aa5f7420a1c58d279a7c0cb14c24e963c4b517 100644 (file)
 #include "ctype.hpp"
 #include "parser.hpp"
 
-#include <algorithm>
-#include <cstring>
-
 Error (*Parser::customParse)(State&, Word) = nullptr;
 
 Error Parser::parse(State& state, const char *str)
 {
     auto addr = Dictionary::Input;
 
-    const auto len = static_cast<Cell>(std::strlen(str));
+    const auto len = static_cast<Cell>(strlen(str));
     state.dict.write(addr, 0);
     state.dict.write(Dictionary::SourceLen, len);
 
@@ -95,7 +92,7 @@ Error Parser::parseNumber(State& state, Word word)
         ++it;
 
     const auto end = word.end(&state.dict);
-    for (char c; it != end; ++it) {
+    for (uint8_t c; it != end; ++it) {
         c = *it;
 
         if (isdigit(c)) {
index 6e129999af210c9330f872c559660fe6baf6cd50..df785e0891b5c38dfe2d434f8d9f4f11ce82b111 100644 (file)
@@ -19,7 +19,6 @@
 #include "corewords.hpp"
 #include "state.hpp"
 
-#include <cstring>
 #include <iterator>
 
 bool State::compiling() const
index c2706129d2cca3cf92b3a70d50b0d6fa4726a60e..07ad80b0d62596a4b0973bd6d03d23a43d54dc8a 100644 (file)
@@ -22,7 +22,6 @@
 static const
 #include "msp430fr2476_all.h"
 
-#include <cstring>
 #include <msp430.h>
 
 #include "splitmemdictrw.hpp"
@@ -40,9 +39,9 @@ static void initGPIO();
 static void initClock();
 static void initUART();
 static void Software_Trim();
-#define MCLK_FREQ_MHZ (8)    // MCLK = 8MHz
+#define MCLK_FREQ_MHZ (16)
 
-#define ALEE_RODICTSIZE (9200)
+#define ALEE_RODICTSIZE (9400)
 __attribute__((section(".lodict")))
 #include "core.fth.h"
 
@@ -50,10 +49,8 @@ static bool exitLpm;
 static Addr isr_list[24] = {};
 
 using DictType = SplitMemDictRW<ALEE_RODICTSIZE, 32767>;
-
-alignas(DictType)
-static unsigned char dictbuf[sizeof(DictType)];
-static auto dict = reinterpret_cast<DictType *>(dictbuf);
+extern char __dict[sizeof(DictType)];
+static auto& dict = *(new (__dict) DictType (alee_dat, 0x10000));
 
 int main()
 {
@@ -64,9 +61,7 @@ int main()
     SYSCFG0 = FRWPPW;
 
     (void)alee_dat_len;
-    dict->lodict = alee_dat;
-    dict->hidict = 0x10000;
-    State state (*dict, readchar);
+    State state (dict, readchar);
     Parser::customParse = findword;
 
     serputs("alee forth\n\r");
@@ -203,17 +198,17 @@ void user_sys(State& state)
 
 #define LZSS_MAGIC_SEPARATOR (0xFB)
 
-static char lzword[32];
+static uint8_t lzword[32];
 static int lzwlen;
-static char lzbuf[32];
-static char *lzptr;
+static uint8_t lzbuf[32];
+static uint8_t *lzptr;
 
 Error findword(State& state, Word word)
 {
-    char *ptr = lzword;
+    uint8_t *ptr = lzword;
     for (auto it = word.begin(&state.dict); it != word.end(&state.dict); ++it) {
         *ptr = *it;
-        if (islower(*ptr))
+        if (!isupper(*ptr))
             *ptr -= 32;
         ++ptr;
     }
@@ -224,9 +219,9 @@ Error findword(State& state, Word word)
 
     auto ret = decode([](int c) {
         if (c != LZSS_MAGIC_SEPARATOR) {
-            *lzptr++ = (char)c;
+            *lzptr++ = (uint8_t)c;
         } else {
-            if (lzwlen == lzptr - lzbuf - 2 && strncmp(lzword, lzbuf, lzptr - lzbuf - 2) == 0) {
+            if (lzwlen == lzptr - lzbuf - 2 && std::equal(lzbuf, lzptr - 2, lzword)) {
                 lzwlen = (*(lzptr - 2) << 8) | *(lzptr - 1);
                 return 1;
             } else {
@@ -271,35 +266,47 @@ void initGPIO()
 
 void initClock()
 {
-    __bis_SR_register(SCG0);                 // disable FLL
-    CSCTL3 |= SELREF__REFOCLK;               // Set REFO as FLL reference source
-    CSCTL1 = DCOFTRIMEN_1 | DCOFTRIM0 | DCOFTRIM1 | DCORSEL_3;// DCOFTRIM=3, DCO Range = 8MHz
-    CSCTL2 = FLLD_0 + 243;                   // DCODIV = 8MHz
+    static_assert(MCLK_FREQ_MHZ == 16);
+
+    // Configure one FRAM waitstate as required by the device datasheet for MCLK
+    // operation beyond 8MHz _before_ configuring the clock system.
+    FRCTL0 = FRCTLPW | NWAITS_1;
+
+    P2SEL0 |= BIT0 | BIT1;                       // P2.0~P2.1: crystal pins
+    do
+    {
+        CSCTL7 &= ~(XT1OFFG | DCOFFG);           // Clear XT1 and DCO fault flag
+        SFRIFG1 &= ~OFIFG;
+    } while (SFRIFG1 & OFIFG);                   // Test oscillator fault flag
+
+    __bis_SR_register(SCG0);                     // disable FLL
+    CSCTL3 |= SELREF__XT1CLK;                    // Set XT1 as FLL reference source
+    CSCTL1 = DCOFTRIMEN_1 | DCOFTRIM0 | DCOFTRIM1 | DCORSEL_5;// DCOFTRIM=5, DCO Range = 16MHz
+    CSCTL2 = FLLD_0 + 487;                       // DCOCLKDIV = 16MHz
     __delay_cycles(3);
-    __bic_SR_register(SCG0);                // enable FLL
-    Software_Trim();                        // Software Trim to get the best DCOFTRIM value
+    __bic_SR_register(SCG0);                     // enable FLL
+    Software_Trim();                             // Software Trim to get the best DCOFTRIM value
+
+    CSCTL4 = SELMS__DCOCLKDIV | SELA__XT1CLK;    // set XT1 (~32768Hz) as ACLK source, ACLK = 32768Hz
+                                                 // default DCOCLKDIV as MCLK and SMCLK source
 
-    CSCTL4 = SELMS__DCOCLKDIV | SELA__REFOCLK; // set default REFO(~32768Hz) as ACLK source, ACLK = 32768Hz
-                                               // default DCODIV as MCLK and SMCLK source
 }
 
 void initUART()
 {
     // Configure UART pins
-    P5SEL0 |= BIT1 | BIT2;                    // set 2-UART pin as second function
-    SYSCFG3|=USCIA0RMP;                       //Set the remapping source
-    // Configure UART
+    P5SEL0 |= BIT1 | BIT2;
+    SYSCFG3 |= USCIA0RMP; // Set the remapping source
+
     UCA0CTLW0 |= UCSWRST;
-    UCA0CTLW0 |= UCSSEL__SMCLK;
+    UCA0CTLW0 |= UCSSEL__SMCLK; // 16 MHz
 
     // Baud Rate calculation
-    // 8000000/(16*9600) = 52.083
-    // Fractional portion = 0.083
-    // User's Guide Table 17-4: UCBRSx = 0x49
-    // UCBRFx = int ( (52.083-52)*16) = 1
-    UCA0BR0 = 52;                             // 8000000/16/9600
-    UCA0BR1 = 0x00;
-    UCA0MCTLW = 0x4900 | UCOS16 | UCBRF_1;
+    // N = 16MHz / 115200 = 138.888
+    // OS16 = 1, UCBRx = INT(N/16) = 8(.6806)
+    // UCBRFx = INT( ((N/16) - UCBRx) * 16) = 10(.8896)
+    UCA0BRW = 8;
+    UCA0MCTLW = 0xD600 | 0x00A0 | UCOS16;
 
     UCA0CTLW0 &= ~UCSWRST;                    // Initialize eUSCI
 }
@@ -378,7 +385,7 @@ bool alee_isr_handle(unsigned index)
     const Addr isr = isr_list[index];
 
     if (isr != 0) {
-        State isrstate (*dict, readchar);
+        State isrstate (dict, readchar);
         exitLpm = false;
         isrstate.execute(isr);
         return exitLpm;
@@ -418,3 +425,6 @@ DEFINE_ISR(TIMER1_A0_VECTOR, 21)
 DEFINE_ISR(TIMER0_A1_VECTOR, 22)
 DEFINE_ISR(TIMER0_A0_VECTOR, 23)
 
+// Override newlib's free to save hundreds of bytes
+extern "C" void free(void *) {}
+
index 08b0299f3484d53360124a6b162740dbcc9a37b1..574a76bcf7b813c594761f3c05b104206fa2977f 100644 (file)
@@ -214,7 +214,9 @@ SECTIONS
     KEEP (*(.dtors))\r
   } > FRAM\r
 \r
-  .tinyram : {} > TINYRAM\r
+  .tinyram : {\r
+    PROVIDE (__dict = .);\r
+  } > TINYRAM\r
 \r
   .data :\r
   {\r
index 7fcb5cd5b41846746bbe230983e757666a1aeb20..dc02ab945ffabc3ab8b71353e7df811b4d7a6708 100644 (file)
@@ -40,7 +40,6 @@ public:
         return *this;
     }
 
-
     virtual Cell read(Addr addr) const noexcept final {
         if (addr < LON)
             return *reinterpret_cast<const Cell *>(lodict + addr);
@@ -72,6 +71,9 @@ public:
     virtual unsigned long int capacity() const noexcept final {
         return LON + HIN;
     }
+
+private:
+    virtual ~SplitMemDictRW() override {};
 };
 
 #endif // ALEEFORTH_SPLITMEMDICTRW_HPP