mirror of https://github.com/rusefi/bldc.git
Merge commit '78ca6b2cb3358e39e729507b50c7eaefbbaaf978'
This commit is contained in:
commit
84daf396e0
|
@ -3,6 +3,8 @@
|
||||||
|
|
||||||
\section sec_intro Introduction
|
\section sec_intro Introduction
|
||||||
|
|
||||||
|
WORK IN PROGRESS
|
||||||
|
|
||||||
LispBM is a lisp-like language implemented by a non-lisper. The inspiration for LispBM came from watching the <a
|
LispBM is a lisp-like language implemented by a non-lisper. The inspiration for LispBM came from watching the <a
|
||||||
href="https://www.youtube.com/watch?v=-J_xL4IGhJA&list=PLE18841CABEA24090">
|
href="https://www.youtube.com/watch?v=-J_xL4IGhJA&list=PLE18841CABEA24090">
|
||||||
SICP course on youtube </a> and a tiny amount of experimenting with EMACS
|
SICP course on youtube </a> and a tiny amount of experimenting with EMACS
|
||||||
|
|
|
@ -1066,6 +1066,92 @@ Example where a process waits for an i28
|
||||||
\endcode
|
\endcode
|
||||||
|
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
\section sec_macros Macros
|
||||||
|
|
||||||
|
lispBM macros are created using the <code>macro</code> keyword. A macro
|
||||||
|
is quite similar to <a href="lambda">lambda</a> in lispBM except that
|
||||||
|
arguments are passed in unevaluated. Together with the code-splicing
|
||||||
|
capabilities given by <a href="sec_quote">quasiquotation</a>, this
|
||||||
|
provides a powerful code-generation tool.
|
||||||
|
|
||||||
|
A macro application is run through the interpreted two times. Once to
|
||||||
|
evaluate the body of the macro on the unevaluated arguments. The result of
|
||||||
|
this first application should be a program. The resulting program then goes
|
||||||
|
through the interpreter again to compute final values.
|
||||||
|
|
||||||
|
Given this repeated evaluation, macros is not a performance boost in lispbm.
|
||||||
|
It is really a feature to invent new programming abstractions in cases where
|
||||||
|
it is ok to pay a little for the overhead for benefits in expressivity.
|
||||||
|
|
||||||
|
<a name="macro"> <h3>macro</h3> </a>
|
||||||
|
|
||||||
|
The form of a <code>macro</code> expression is: <code>(macro args body)</code>
|
||||||
|
|
||||||
|
\note
|
||||||
|
Some lisps provide a <code>defun</code> operation for defining functions
|
||||||
|
with a bit less typing. The example below defines a <code>defun</code> macro.
|
||||||
|
\code
|
||||||
|
(define defun (macro (name args body)
|
||||||
|
`(define ,name (lambda ,args ,body))))
|
||||||
|
\endcode
|
||||||
|
With this macro the function <code>inc</code> that adds 1 to its argument
|
||||||
|
can be defined as:
|
||||||
|
\code
|
||||||
|
(defun inc (x) (+ x 1))
|
||||||
|
\endcode
|
||||||
|
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
\section sec_cc Call With Current Continuation
|
||||||
|
|
||||||
|
"Call with current continuation" is called <code>call-cc</code> in LBM.
|
||||||
|
Call with current continuation saves the "current continuation", which encodes what
|
||||||
|
the evaluator will do next, into an object in the language. This encoded
|
||||||
|
continuation object behaves as a function taking one argument.
|
||||||
|
|
||||||
|
The <code>call-cc</code> should be given a function, <code>f</code>, as the single argument. This
|
||||||
|
function, <code>f</code>, should also take a single argument, the continuation.
|
||||||
|
At any point in the body of <code>f</code> the continuation can be applied to
|
||||||
|
a value, in essense replacing the entire <code>call-cc</code> with that value.
|
||||||
|
|
||||||
|
\note
|
||||||
|
The example below creates a macro for a <code>progn</code> facility that
|
||||||
|
allows returning at an arbitrary point.
|
||||||
|
\code
|
||||||
|
(define do (macro (body)
|
||||||
|
`(call-cc (lambda (return) (progn ,@body)))))
|
||||||
|
\endcode
|
||||||
|
The example using <code>do</code> below makes use of <code>print</code> which is not a
|
||||||
|
built-in feature of lispBM. There are just to many different ways a programmer may
|
||||||
|
want to implement <code>print</code> on an microcontroller. Use the lispBM extensions
|
||||||
|
framework to implement your own version of <code>print</code>
|
||||||
|
\code
|
||||||
|
(do ((print 10)
|
||||||
|
(return 't)
|
||||||
|
(print 20)))
|
||||||
|
\endcode
|
||||||
|
In the example above only "10" will be printed.
|
||||||
|
Below is an example that conditionally returns.
|
||||||
|
\code
|
||||||
|
(define f (lambda (x)
|
||||||
|
(do ((print "hello world" \#newline)
|
||||||
|
(if (= x 1)
|
||||||
|
(return 't)
|
||||||
|
nil)
|
||||||
|
(print "Gizmo!" \#newline)))))
|
||||||
|
\endcode
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
\section sec_unparse Unparsable symbols
|
\section sec_unparse Unparsable symbols
|
||||||
|
|
||||||
|
|
|
@ -25,10 +25,13 @@
|
||||||
/** LBM minor version */
|
/** LBM minor version */
|
||||||
#define LBM_MINOR_VERSION 4
|
#define LBM_MINOR_VERSION 4
|
||||||
/** LBM patch revision */
|
/** LBM patch revision */
|
||||||
#define LBM_PATCH_VERSION 0
|
#define LBM_PATCH_VERSION 1
|
||||||
|
|
||||||
/* Change log */
|
/* Change log */
|
||||||
|
|
||||||
|
/* Feb 21 2022: Version (0.4.1)
|
||||||
|
- Bug fixes in gc related to arrays
|
||||||
|
*/
|
||||||
|
|
||||||
/* Feb 20 2022: Version (0.4.0)
|
/* Feb 20 2022: Version (0.4.0)
|
||||||
- Adds support for macros.
|
- Adds support for macros.
|
||||||
|
|
|
@ -57,8 +57,9 @@
|
||||||
#define SYM_SEND 0x14
|
#define SYM_SEND 0x14
|
||||||
#define SYM_RECEIVE 0x15
|
#define SYM_RECEIVE 0x15
|
||||||
#define SYM_MACRO 0x16
|
#define SYM_MACRO 0x16
|
||||||
#define SYM_CALLCC 0x17
|
#define SYM_MACRO_EXPAND 0x17
|
||||||
#define SYM_CONT 0x18
|
#define SYM_CALLCC 0x18
|
||||||
|
#define SYM_CONT 0x19
|
||||||
|
|
||||||
#define SYM_ARRAY_TYPE 0x20
|
#define SYM_ARRAY_TYPE 0x20
|
||||||
#define SYM_BOXED_I_TYPE 0x21
|
#define SYM_BOXED_I_TYPE 0x21
|
||||||
|
|
|
@ -951,6 +951,7 @@ static inline void eval_progn(eval_context_t *ctx) {
|
||||||
lbm_value env = ctx->curr_env;
|
lbm_value env = ctx->curr_env;
|
||||||
|
|
||||||
if (lbm_type_of(exps) == LBM_VAL_TYPE_SYMBOL && exps == NIL) {
|
if (lbm_type_of(exps) == LBM_VAL_TYPE_SYMBOL && exps == NIL) {
|
||||||
|
printf("the nil case\n");
|
||||||
ctx->r = NIL;
|
ctx->r = NIL;
|
||||||
ctx->app_cont = true;
|
ctx->app_cont = true;
|
||||||
return;
|
return;
|
||||||
|
@ -1173,6 +1174,7 @@ static inline void cont_progn_rest(eval_context_t *ctx) {
|
||||||
lbm_value env;
|
lbm_value env;
|
||||||
lbm_pop_u32_2(&ctx->K, &rest, &env);
|
lbm_pop_u32_2(&ctx->K, &rest, &env);
|
||||||
if (lbm_type_of(rest) == LBM_VAL_TYPE_SYMBOL && rest == NIL) {
|
if (lbm_type_of(rest) == LBM_VAL_TYPE_SYMBOL && rest == NIL) {
|
||||||
|
printf("cont: rest is nil\n");
|
||||||
ctx->app_cont = true;
|
ctx->app_cont = true;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
|
@ -57,22 +57,22 @@ bool lbm_array_extensions_init(void) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
bool res = true;
|
bool res = true;
|
||||||
res = res && lbm_add_extension("unsafe-free", array_extension_unsafe_free_array);
|
res = res && lbm_add_extension("free", array_extension_unsafe_free_array);
|
||||||
res = res && lbm_add_extension("buffer-append-i8", array_extension_buffer_append_i8);
|
res = res && lbm_add_extension("bufset-i8", array_extension_buffer_append_i8);
|
||||||
res = res && lbm_add_extension("buffer-append-i16", array_extension_buffer_append_i16);
|
res = res && lbm_add_extension("bufset-i16", array_extension_buffer_append_i16);
|
||||||
res = res && lbm_add_extension("buffer-append-i32", array_extension_buffer_append_i32);
|
res = res && lbm_add_extension("bufset-i32", array_extension_buffer_append_i32);
|
||||||
res = res && lbm_add_extension("buffer-append-u8", array_extension_buffer_append_u8);
|
res = res && lbm_add_extension("bufset-u8", array_extension_buffer_append_u8);
|
||||||
res = res && lbm_add_extension("buffer-append-u16", array_extension_buffer_append_u16);
|
res = res && lbm_add_extension("bufset-u16", array_extension_buffer_append_u16);
|
||||||
res = res && lbm_add_extension("buffer-append-u32", array_extension_buffer_append_u32);
|
res = res && lbm_add_extension("bufset-u32", array_extension_buffer_append_u32);
|
||||||
res = res && lbm_add_extension("buffer-append-f32", array_extension_buffer_append_f32);
|
res = res && lbm_add_extension("bufset-f32", array_extension_buffer_append_f32);
|
||||||
|
|
||||||
res = res && lbm_add_extension("buffer-get-i8", array_extension_buffer_get_i8);
|
res = res && lbm_add_extension("bufget-i8", array_extension_buffer_get_i8);
|
||||||
res = res && lbm_add_extension("buffer-get-i16", array_extension_buffer_get_i16);
|
res = res && lbm_add_extension("bufget-i16", array_extension_buffer_get_i16);
|
||||||
res = res && lbm_add_extension("buffer-get-i32", array_extension_buffer_get_i32);
|
res = res && lbm_add_extension("bufget-i32", array_extension_buffer_get_i32);
|
||||||
res = res && lbm_add_extension("buffer-get-u8", array_extension_buffer_get_u8);
|
res = res && lbm_add_extension("bufget-u8", array_extension_buffer_get_u8);
|
||||||
res = res && lbm_add_extension("buffer-get-u16", array_extension_buffer_get_u16);
|
res = res && lbm_add_extension("bufget-u16", array_extension_buffer_get_u16);
|
||||||
res = res && lbm_add_extension("buffer-get-u32", array_extension_buffer_get_u32);
|
res = res && lbm_add_extension("bufget-u32", array_extension_buffer_get_u32);
|
||||||
res = res && lbm_add_extension("buffer-get-f32", array_extension_buffer_get_f32);
|
res = res && lbm_add_extension("bufget-f32", array_extension_buffer_get_f32);
|
||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -24,7 +24,7 @@
|
||||||
|
|
||||||
#include "symrepr.h"
|
#include "symrepr.h"
|
||||||
|
|
||||||
#define NUM_SPECIAL_SYMBOLS 109
|
#define NUM_SPECIAL_SYMBOLS 110
|
||||||
#define NAME 0
|
#define NAME 0
|
||||||
#define ID 1
|
#define ID 1
|
||||||
#define NEXT 2
|
#define NEXT 2
|
||||||
|
@ -53,6 +53,7 @@ special_sym const special_symbols[NUM_SPECIAL_SYMBOLS] = {
|
||||||
{"send" , SYM_SEND},
|
{"send" , SYM_SEND},
|
||||||
{"recv" , SYM_RECEIVE},
|
{"recv" , SYM_RECEIVE},
|
||||||
{"macro" , SYM_MACRO},
|
{"macro" , SYM_MACRO},
|
||||||
|
{"macro-expand" , SYM_MACRO_EXPAND},
|
||||||
{"call-cc" , SYM_CALLCC},
|
{"call-cc" , SYM_CALLCC},
|
||||||
{"continuation" , SYM_CONT},
|
{"continuation" , SYM_CONT},
|
||||||
|
|
||||||
|
@ -198,7 +199,7 @@ const char *lookup_symrepr_name_memory(lbm_uint id) {
|
||||||
|
|
||||||
// Lookup symbol name given a symbol id
|
// Lookup symbol name given a symbol id
|
||||||
const char *lbm_get_name_by_symbol(lbm_uint id) {
|
const char *lbm_get_name_by_symbol(lbm_uint id) {
|
||||||
if (id < NUM_SPECIAL_SYMBOLS) {
|
if (id < SPECIAL_SYMBOLS_END) {
|
||||||
for (int i = 0; i < NUM_SPECIAL_SYMBOLS; i ++) {
|
for (int i = 0; i < NUM_SPECIAL_SYMBOLS; i ++) {
|
||||||
if (id == special_symbols[i].id) {
|
if (id == special_symbols[i].id) {
|
||||||
return (special_symbols[i].name);
|
return (special_symbols[i].name);
|
||||||
|
|
|
@ -1,23 +1,23 @@
|
||||||
(define arr (array-create type-byte 10))
|
(define arr (array-create type-byte 10))
|
||||||
|
|
||||||
(buffer-append-i8 arr 70 0)
|
(bufset-i8 arr 70 0)
|
||||||
(buffer-append-i8 arr 69 1)
|
(bufset-i8 arr 69 1)
|
||||||
(buffer-append-i8 arr 68 2)
|
(bufset-i8 arr 68 2)
|
||||||
(buffer-append-i8 arr 67 3)
|
(bufset-i8 arr 67 3)
|
||||||
(buffer-append-i8 arr 66 4)
|
(bufset-i8 arr 66 4)
|
||||||
(buffer-append-i8 arr 65 5)
|
(bufset-i8 arr 65 5)
|
||||||
(buffer-append-i8 arr 64 6)
|
(bufset-i8 arr 64 6)
|
||||||
(buffer-append-i8 arr 63 7)
|
(bufset-i8 arr 63 7)
|
||||||
(buffer-append-i8 arr 62 8)
|
(bufset-i8 arr 62 8)
|
||||||
(buffer-append-i8 arr 61 9)
|
(bufset-i8 arr 61 9)
|
||||||
|
|
||||||
(and (= (buffer-get-i8 arr 0) 70)
|
(and (= (bufget-i8 arr 0) 70)
|
||||||
(= (buffer-get-i8 arr 1) 69)
|
(= (bufget-i8 arr 1) 69)
|
||||||
(= (buffer-get-i8 arr 2) 68)
|
(= (bufget-i8 arr 2) 68)
|
||||||
(= (buffer-get-i8 arr 3) 67)
|
(= (bufget-i8 arr 3) 67)
|
||||||
(= (buffer-get-i8 arr 4) 66)
|
(= (bufget-i8 arr 4) 66)
|
||||||
(= (buffer-get-i8 arr 5) 65)
|
(= (bufget-i8 arr 5) 65)
|
||||||
(= (buffer-get-i8 arr 6) 64)
|
(= (bufget-i8 arr 6) 64)
|
||||||
(= (buffer-get-i8 arr 7) 63)
|
(= (bufget-i8 arr 7) 63)
|
||||||
(= (buffer-get-i8 arr 8) 62)
|
(= (bufget-i8 arr 8) 62)
|
||||||
(= (buffer-get-i8 arr 9) 61))
|
(= (bufget-i8 arr 9) 61))
|
||||||
|
|
|
@ -1,24 +1,24 @@
|
||||||
(define arr (array-create type-byte 10))
|
(define arr (array-create type-byte 10))
|
||||||
|
|
||||||
(buffer-append-u8 arr 70 0)
|
(bufset-u8 arr 70 0)
|
||||||
(buffer-append-u8 arr 69 1)
|
(bufset-u8 arr 69 1)
|
||||||
(buffer-append-u8 arr 68 2)
|
(bufset-u8 arr 68 2)
|
||||||
(buffer-append-u8 arr 67 3)
|
(bufset-u8 arr 67 3)
|
||||||
(buffer-append-u8 arr 66 4)
|
(bufset-u8 arr 66 4)
|
||||||
(buffer-append-u8 arr 65 5)
|
(bufset-u8 arr 65 5)
|
||||||
(buffer-append-u8 arr 64 6)
|
(bufset-u8 arr 64 6)
|
||||||
(buffer-append-u8 arr 63 7)
|
(bufset-u8 arr 63 7)
|
||||||
(buffer-append-u8 arr 62 8)
|
(bufset-u8 arr 62 8)
|
||||||
(buffer-append-u8 arr 61 9)
|
(bufset-u8 arr 61 9)
|
||||||
|
|
||||||
(= (buffer-get-u8 arr 0) 70u28)
|
(= (bufget-u8 arr 0) 70u28)
|
||||||
(and (num-eq (buffer-get-u8 arr 0) 70)
|
(and (num-eq (bufget-u8 arr 0) 70)
|
||||||
(num-eq (buffer-get-u8 arr 1) 69)
|
(num-eq (bufget-u8 arr 1) 69)
|
||||||
(num-eq (buffer-get-u8 arr 2) 68)
|
(num-eq (bufget-u8 arr 2) 68)
|
||||||
(num-eq (buffer-get-u8 arr 3) 67)
|
(num-eq (bufget-u8 arr 3) 67)
|
||||||
(num-eq (buffer-get-u8 arr 4) 66)
|
(num-eq (bufget-u8 arr 4) 66)
|
||||||
(num-eq (buffer-get-u8 arr 5) 65)
|
(num-eq (bufget-u8 arr 5) 65)
|
||||||
(num-eq (buffer-get-u8 arr 6) 64)
|
(num-eq (bufget-u8 arr 6) 64)
|
||||||
(num-eq (buffer-get-u8 arr 7) 63)
|
(num-eq (bufget-u8 arr 7) 63)
|
||||||
(num-eq (buffer-get-u8 arr 8) 62)
|
(num-eq (bufget-u8 arr 8) 62)
|
||||||
(num-eq (buffer-get-u8 arr 9) 61))
|
(num-eq (bufget-u8 arr 9) 61))
|
||||||
|
|
|
@ -1,14 +1,14 @@
|
||||||
|
|
||||||
(define arr (array-create type-byte 16))
|
(define arr (array-create type-byte 16))
|
||||||
|
|
||||||
(buffer-append-u32 arr 16777215 0)
|
(bufset-u32 arr 16777215 0)
|
||||||
(buffer-append-u32 arr 0xFFFFFFFF 4)
|
(bufset-u32 arr 0xFFFFFFFF 4)
|
||||||
(buffer-append-u32 arr 10 8)
|
(bufset-u32 arr 10 8)
|
||||||
(buffer-append-u32 arr 0xDEADBEEF 12)
|
(bufset-u32 arr 0xDEADBEEF 12)
|
||||||
|
|
||||||
(and (num-eq (buffer-get-u32 arr 0) 16777215)
|
(and (num-eq (bufget-u32 arr 0) 16777215)
|
||||||
(num-eq (buffer-get-u32 arr 4) 0xFFFFFFFF)
|
(num-eq (bufget-u32 arr 4) 0xFFFFFFFF)
|
||||||
(num-eq (buffer-get-u32 arr 8) 10)
|
(num-eq (bufget-u32 arr 8) 10)
|
||||||
(num-eq (buffer-get-u32 arr 12) 0xDEADBEEF))
|
(num-eq (bufget-u32 arr 12) 0xDEADBEEF))
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -1,11 +1,11 @@
|
||||||
(define arr (array-create type-byte 16))
|
(define arr (array-create type-byte 16))
|
||||||
|
|
||||||
(buffer-append-i32 arr 16777215 0)
|
(bufset-i32 arr 16777215 0)
|
||||||
(buffer-append-i32 arr 0xFFFFFFFF 4)
|
(bufset-i32 arr 0xFFFFFFFF 4)
|
||||||
(buffer-append-i32 arr 10 8)
|
(bufset-i32 arr 10 8)
|
||||||
(buffer-append-i32 arr 0xDEADBEEF 12)
|
(bufset-i32 arr 0xDEADBEEF 12)
|
||||||
|
|
||||||
(and (num-eq (buffer-get-i32 arr 0) 16777215)
|
(and (num-eq (bufget-i32 arr 0) 16777215)
|
||||||
(num-eq (buffer-get-i32 arr 4) 0xFFFFFFFF)
|
(num-eq (bufget-i32 arr 4) 0xFFFFFFFF)
|
||||||
(num-eq (buffer-get-i32 arr 8) 10)
|
(num-eq (bufget-i32 arr 8) 10)
|
||||||
(num-eq (buffer-get-i32 arr 12) 0xDEADBEEF))
|
(num-eq (bufget-i32 arr 12) 0xDEADBEEF))
|
||||||
|
|
|
@ -1,11 +1,11 @@
|
||||||
(define arr (array-create type-byte 16))
|
(define arr (array-create type-byte 16))
|
||||||
|
|
||||||
(buffer-append-f32 arr 3.14 0)
|
(bufset-f32 arr 3.14 0)
|
||||||
(buffer-append-f32 arr 666.666 4)
|
(bufset-f32 arr 666.666 4)
|
||||||
(buffer-append-f32 arr 100 8)
|
(bufset-f32 arr 100 8)
|
||||||
(buffer-append-f32 arr 42 12)
|
(bufset-f32 arr 42 12)
|
||||||
|
|
||||||
(and (num-eq (buffer-get-f32 arr 0) 3.14)
|
(and (num-eq (bufget-f32 arr 0) 3.14)
|
||||||
(num-eq (buffer-get-f32 arr 4) 666.666)
|
(num-eq (bufget-f32 arr 4) 666.666)
|
||||||
(num-eq (buffer-get-f32 arr 8) 100)
|
(num-eq (bufget-f32 arr 8) 100)
|
||||||
(num-eq (buffer-get-f32 arr 12) 42))
|
(num-eq (bufget-f32 arr 12) 42))
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
|
|
||||||
(define arr (array-create type-byte 16))
|
(define arr (array-create type-byte 16))
|
||||||
|
|
||||||
(unsafe-free arr)
|
(free arr)
|
||||||
|
|
||||||
(and (= (car arr) nil)
|
(and (= (car arr) nil)
|
||||||
(= (cdr arr) nil))
|
(= (cdr arr) nil))
|
||||||
|
|
Loading…
Reference in New Issue