11#define SHI_STACK_SIZE 256
14#define SHI_ERASED_WORD 0xFFFFFFFF
17#define SHI_ENABLE_NUMBER_PREFIX 1
20#define SHI_ENABLE_PRINT 1
23#define SHI_ENABLE_REDEFINITION 0
27#define SHI_ENABLE_STORE 1
28#define SHI_ENABLE_TICK 1
29#define SHI_ENABLE_TIMES 1
30#define SHI_ENABLE_TIMES_DIV 1
31#define SHI_ENABLE_TIMES_DIV_MOD 1
32#define SHI_ENABLE_PLUS 1
33#define SHI_ENABLE_PLUS_STORE 1
34#define SHI_ENABLE_PLUS_LOOP 1
35#define SHI_ENABLE_COMMA 1
36#define SHI_ENABLE_MINUS 1
37#define SHI_ENABLE_DIV 1
38#define SHI_ENABLE_DIV_MOD 1
39#define SHI_ENABLE_ZERO_LESS 1
40#define SHI_ENABLE_ZERO_EQUAL 1
41#define SHI_ENABLE_ONE_PLUS 1
42#define SHI_ENABLE_ONE_MINUS 1
43#define SHI_ENABLE_TWO_STORE 1
44#define SHI_ENABLE_TWO_TIMES 1
45#define SHI_ENABLE_TWO_DIV 1
46#define SHI_ENABLE_TWO_FETCH 1
47#define SHI_ENABLE_TWO_DROP 1
48#define SHI_ENABLE_TWO_DUP 1
49#define SHI_ENABLE_TWO_OVER 1
50#define SHI_ENABLE_TWO_SWAP 1
51#define SHI_ENABLE_COLON 1
52#define SHI_ENABLE_SEMI 1
53#define SHI_ENABLE_LESS 1
54#define SHI_ENABLE_EQUAL 1
55#define SHI_ENABLE_MORE 1
56#define SHI_ENABLE_TO_BODY 1
57#define SHI_ENABLE_TO_IN 1
58#define SHI_ENABLE_TO_R 1
59#define SHI_ENABLE_Q_DUP 1
60#define SHI_ENABLE_FETCH 1
61#define SHI_ENABLE_ABS 1
62#define SHI_ENABLE_ALIGN 1
63#define SHI_ENABLE_ALIGNED 1
64#define SHI_ENABLE_ALLOT 1
65#define SHI_ENABLE_AND 1
66#define SHI_ENABLE_BASE 1
67#define SHI_ENABLE_BEGIN 1
68#define SHI_ENABLE_C_STORE 1
69#define SHI_ENABLE_C_COMMA 1
70#define SHI_ENABLE_C_FETCH 1
71#define SHI_ENABLE_CELL_PLUS 1
72#define SHI_ENABLE_CELLS 1
73#define SHI_ENABLE_CHAR_PLUS 1
74#define SHI_ENABLE_CHARS 1
75#define SHI_ENABLE_CONSTANT 1
76#define SHI_ENABLE_CREATE 1
77#define SHI_ENABLE_DECIMAL 1
78#define SHI_ENABLE_DEPTH 1
79#define SHI_ENABLE_DO 1
80#define SHI_ENABLE_DOES 1
81#define SHI_ENABLE_DROP 1
82#define SHI_ENABLE_DUP 1
83#define SHI_ENABLE_ELSE 1
84#define SHI_ENABLE_EXECUTE 1
85#define SHI_ENABLE_EXIT 1
86#define SHI_ENABLE_FILL 1
87#define SHI_ENABLE_FIND 1
88#define SHI_ENABLE_FM_DIV_MOD 1
89#define SHI_ENABLE_HERE 1
91#define SHI_ENABLE_IF 1
92#define SHI_ENABLE_IMMEDIATE 1
93#define SHI_ENABLE_INVERT 1
95#define SHI_ENABLE_LEAVE 1
96#define SHI_ENABLE_LITERAL 1
97#define SHI_ENABLE_LOOP 1
98#define SHI_ENABLE_LSHIFT 1
99#define SHI_ENABLE_M_TIMES 1
100#define SHI_ENABLE_MAX 1
101#define SHI_ENABLE_MIN 1
102#define SHI_ENABLE_MOD 1
103#define SHI_ENABLE_MOVE 1
104#define SHI_ENABLE_NEGATE 1
105#define SHI_ENABLE_OR 1
106#define SHI_ENABLE_OVER 1
107#define SHI_ENABLE_POSTPONE 1
108#define SHI_ENABLE_R_FROM 1
109#define SHI_ENABLE_R_FETCH 1
110#define SHI_ENABLE_RECURSE 1
111#define SHI_ENABLE_REPEAT 1
112#define SHI_ENABLE_ROT 1
113#define SHI_ENABLE_RSHIFT 1
114#define SHI_ENABLE_S_TO_D 1
115#define SHI_ENABLE_SIGN 1
116#define SHI_ENABLE_SM_DIV_REM 1
117#define SHI_ENABLE_SOURCE 1
118#define SHI_ENABLE_STATE 1
119#define SHI_ENABLE_SWAP 1
120#define SHI_ENABLE_THEN 1
121#define SHI_ENABLE_U_LESS 1
122#define SHI_ENABLE_UM_TIMES 1
123#define SHI_ENABLE_UM_DIV_MOD 1
124#define SHI_ENABLE_UNLOOP 1
125#define SHI_ENABLE_UNTIL 1
126#define SHI_ENABLE_VARIABLE 1
127#define SHI_ENABLE_WHILE 1
128#define SHI_ENABLE_XOR 1
129#define SHI_ENABLE_BRACKET_LEFT 1
130#define SHI_ENABLE_BRACKET_TICK 1
131#define SHI_ENABLE_BRACKET_RIGHT 1
132#define SHI_ENABLE_ZERO_NE 1
133#define SHI_ENABLE_ZERO_MORE 1
134#define SHI_ENABLE_TWO_TO_R 1
135#define SHI_ENABLE_TWO_R_FROM 1
136#define SHI_ENABLE_TWO_R_FETCH 1
137#define SHI_ENABLE_NE 1
138#define SHI_ENABLE_Q_DO 1
139#define SHI_ENABLE_ACTION_OF 1
140#define SHI_ENABLE_AGAIN 1
141#define SHI_ENABLE_BUFFER_COLON 1
142#define SHI_ENABLE_CASE 1
143#define SHI_ENABLE_COMPILE_COMMA 1
144#define SHI_ENABLE_ENDCASE 1
145#define SHI_ENABLE_ENDOF 1
146#define SHI_ENABLE_ERASE 1
147#define SHI_ENABLE_FALSE 1
148#define SHI_ENABLE_HEX 1
149#define SHI_ENABLE_NIP 1
150#define SHI_ENABLE_OF 1
151#define SHI_ENABLE_PARSE_NAME 1
152#define SHI_ENABLE_PICK 1
153#define SHI_ENABLE_ROLL 1
154#define SHI_ENABLE_TRUE 1
155#define SHI_ENABLE_TUCK 1
156#define SHI_ENABLE_U_MORE 1
157#define SHI_ENABLE_UNUSED 1
158#define SHI_ENABLE_VALUE 1
159#define SHI_ENABLE_WITHIN 1
162#define SHI_ENABLE_H_STORE 1
163#define SHI_ENABLE_H_FETCH 1
164#define SHI_ENABLE_INLINE 1
165#define SHI_ENABLE_TO_TEXT_Q 1
166#define SHI_ENABLE_TO_DATA_Q 1
167#define SHI_ENABLE_TO_TEXT 1
168#define SHI_ENABLE_TO_DATA 1
195 asm volatile(
"ldr r0, [%0] \n"
196 "str %1, [r0, #-4]! \n"
207 asm volatile(
"ldr r0, [%0] \n"
208 "ldrd r1, r2, [%1] \n"
209 "strd r2, r1, [r0, #-8]! \n"
213 :
"memory",
"r0",
"r1",
"r2");
221 asm volatile(
"ldr r0, [%0] \n"
225 "str r1, [r0, #-4] \n"
235 "ldrb r3, [r2, #-1]! \n"
236 "strb r3, [r0, #-1]! \n"
242 :
"cc",
"memory",
"r0",
"r1",
"r2",
"r3");
251 asm volatile(
"ldr r0, [%1] \n"
252 "ldr %0, [r0], #4 \n"
267 asm volatile(
"ldr r0, [%0] \n"
268 "ldrd r1, r2, [r0], #8 \n"
269 "strd r2, r1, [%1] \n"
273 :
"memory",
"r0",
"r1",
"r2");
283 asm volatile(
"ldr r0, [%0] \n"
291 "ldrb r3, [r0], #1 \n"
292 "strb r3, [r2], #1 \n"
296 "1: add r0, r0, #3 \n"
301 :
"cc",
"memory",
"r0",
"r1",
"r2",
"r3");
311 asm volatile(
"ldr r0, [%1] \n"
312 "ldr %0, [r0, %2, lsl #2] \n"
327 asm volatile(
"ldr r0, [%0] \n"
328 "add r0, r0, %2, lsl #2 \n"
329 "ldrd r1, r2, [r0] \n"
330 "strd r2, r1, [%1] \n"
333 :
"memory",
"r0",
"r1",
"r2");
343 asm volatile(
"ldr r0, [%1] \n"
344 "add %0, r0, %2, lsl #2 \n"
356 asm volatile(
"ldr r0, [%1] \n"
460 asm volatile(
"ldrd r7, r8, [%0] \n"
461 "ldr r6, [r7], #4 \n"
465 "str r6, [r7, #-4]! \n"
466 "strd r7, r8, [%0] \n"
469 :
"cc",
"memory",
"r6",
"r7",
"r8",
"lr");
475# include <type_traits>
476# include <functional>
483 using type = std::remove_cv_t<std::remove_reference_t<T>>;
504 asm volatile(
"ldr r0, [%1] \n"
528 using std::addressof, std::is_arithmetic_v, std::is_pointer_v;
531 if constexpr (
sizeof(V) <= 4 && (is_arithmetic_v<V> || is_pointer_v<V> ||
533 asm volatile(
"ldr r0, [%0] \n"
534 "str %1, [r0, #-4]! \n"
539 else if constexpr (
sizeof(V) == 8 && is_arithmetic_v<V>)
540 asm volatile(
"ldr r0, [%0] \n"
541 "ldrd r1, r2, [%1] \n"
542 "strd r2, r1, [r0, #-8]! \n"
546 :
"memory",
"r0",
"r1",
"r2");
549 asm volatile(
"ldr r0, [%0] \n"
553 "str r1, [r0, #-4] \n"
563 "ldrb r3, [r2, #-1]! \n"
564 "strb r3, [r0, #-1]! \n"
569 :
"r"(&
shi_context),
"r"(addressof(t)),
"r"(
sizeof(V))
570 :
"cc",
"memory",
"r0",
"r1",
"r2",
"r3");
578template<
typename... Ts>
584 (
push(forward<Ts>(ts)), ...);
591template<
typename T =
int32_t>
593 using std::addressof, std::is_arithmetic_v, std::is_pointer_v;
597 if constexpr (
sizeof(T) <= 4 && (is_arithmetic_v<T> || is_pointer_v<T> ||
599 asm volatile(
"ldr r0, [%1] \n"
600 "ldr %0, [r0], #4 \n"
605 else if constexpr (
sizeof(T) == 8 && is_arithmetic_v<T>)
606 asm volatile(
"ldr r0, [%0] \n"
607 "ldrd r1, r2, [r0], #8 \n"
608 "strd r2, r1, [%1] \n"
612 :
"memory",
"r0",
"r1",
"r2");
615 asm volatile(
"ldr r0, [%0] \n"
623 "ldrb r3, [r0], #1 \n"
624 "strb r3, [r2], #1 \n"
628 "1: add r0, r0, #3 \n"
632 :
"r"(&
shi_context),
"r"(addressof(t)),
"r"(
sizeof(T))
633 :
"cc",
"memory",
"r0",
"r1",
"r2",
"r3");
643template<
typename... Ts,
typename = std::enable_if_t<(
sizeof...(Ts) > 1)>>
649 return tuple<Ts...>{
pop<Ts>()...};
658template<
typename T =
int32_t>
659decltype(
auto)
top(
size_t offset = 0) {
660 using std::add_lvalue_reference_t, std::addressof, std::is_arithmetic_v,
663 if constexpr (
sizeof(T) <= 4 && (is_arithmetic_v<T> || is_pointer_v<T> ||
666 asm volatile(
"ldr r0, [%1] \n"
667 "ldr %0, [r0, %2, lsl #2] \n"
672 }
else if constexpr (
sizeof(T) == 8 && is_arithmetic_v<T>) {
674 asm volatile(
"ldr r0, [%0] \n"
675 "add r0, r0, %2, lsl #2 \n"
676 "ldrd r1, r2, [r0] \n"
677 "strd r2, r1, [%1] \n"
679 :
"r"(&
shi_context),
"r"(addressof(t)),
"r"(offset)
680 :
"memory",
"r0",
"r1",
"r2");
685 asm volatile(
"ldr r0, [%1] \n"
686 "add %0, r0, %2, lsl #2 \n"
690 return add_lvalue_reference_t<T>(*t);
734 using std::is_pointer_v;
736 static_assert(
sizeof(T) == 4 &&
751 using std::is_pointer_v;
753 static_assert(
sizeof(T) == 4 &&
793 template<
typename... Ts>
798 push(forward<Ts>(ts)...);
800 asm volatile(
"ldrd r7, r8, [%0] \n"
801 "ldr r6, [r7], #4 \n"
805 "str r6, [r7, #-4]! \n"
806 "strd r7, r8, [%0] \n"
809 :
"cc",
"memory",
"r6",
"r7",
"r8",
"lr");
822 template<
typename... Ts>
823 operator std::tuple<Ts...>() {
837inline void operator"" _s(
char const* str,
size_t len) {
846inline auto operator""_v(
char const* str,
size_t len) {
847 return [=](
auto adr) {
848 using std::is_pointer_v;
850 static_assert(
sizeof(adr) == 4 && (is_pointer_v<
decltype(adr)> ||
863template<
typename T, T... Cs>
865 static constexpr char c[]{Cs...};
866 static Word word{c,
sizeof...(Cs)};
void evaluate(char const *str)
Definition shi.hpp:715
decltype(auto) top(size_t offset=0)
Definition shi.hpp:659
typename remove_cvref< T >::type remove_cvref_t
Definition shi.hpp:487
size_t depth()
Definition shi.hpp:501
constexpr bool is_reference_wrapper_v
Definition shi.hpp:496
void variable(T adr, char const *str)
Definition shi.hpp:733
void init(Init s)
Definition shi.hpp:708
size_t size()
Definition shi.hpp:518
void shi_init_asm(Init &)
void push(T &&t)
Definition shi.hpp:527
void clear()
Clear stack.
Definition shi.hpp:761
T pop()
Definition shi.hpp:592
void_fp tick(char const *str)
Definition shi.hpp:769
void_fp shi_tick_asm(char const *str, size_t len)
static void shi_top_struct(void **t, size_t offset)
Definition shi.hpp:342
static void shi_push_double(int64_t t)
Definition shi.hpp:206
static void shi_evaluate(char const *str)
Definition shi.hpp:395
static size_t shi_depth()
Definition shi.hpp:353
void shi_variable_asm(char const *name, size_t len)
void(* void_fp)()
Definition shi.hpp:179
static void shi_pop_struct(void *t, size_t n)
Definition shi.hpp:282
#define SHI_STACK_SIZE
Data-stack size (must be a multiple of 4 bytes)
Definition shi.hpp:11
static void shi_init(Shi_init s)
Definition shi.hpp:388
static size_t shi_size()
Definition shi.hpp:370
void shi_evaluate_asm(char const *str, size_t len)
void shi_init_asm(Shi_init *)
static void shi_word(Word w)
Definition shi.hpp:458
static void shi_evaluate_len(char const *str, size_t len)
Definition shi.hpp:403
static void shi_clear()
Clear stack.
Definition shi.hpp:427
static void shi_variable_len(void *adr, char const *str, size_t len)
Definition shi.hpp:421
static Word shi_tick(char const *str)
Definition shi.hpp:440
static int64_t shi_top_double(size_t offset)
Definition shi.hpp:324
static void shi_push_number(int32_t t)
Definition shi.hpp:194
static void shi_variable(void *adr, char const *str)
Definition shi.hpp:411
static int64_t shi_pop_double()
Definition shi.hpp:264
static Word shi_tick_len(char const *str, size_t len)
Definition shi.hpp:450
static void shi_push_struct(void *t, size_t n)
Definition shi.hpp:220
static int32_t shi_top_number(size_t offset)
Definition shi.hpp:308
static int32_t shi_pop_number()
Definition shi.hpp:248
Init struct.
Definition shi.hpp:375
uint32_t data_end
Definition shi.hpp:377
uint32_t text_begin
Definition shi.hpp:378
uint32_t text_end
Definition shi.hpp:379
uint8_t text_p2align
Definition shi.hpp:380
uint32_t data_begin
Definition shi.hpp:376
Word.
Definition shi.hpp:432
void_fp fp
Definition shi.hpp:433
Init struct.
Definition shi.hpp:695
uint32_t text_end
Definition shi.hpp:699
uint32_t text_begin
Definition shi.hpp:698
uint32_t data_end
Definition shi.hpp:697
uint32_t data_begin
Definition shi.hpp:696
uint8_t text_p2align
Definition shi.hpp:700
Word.
Definition shi.hpp:783
Word & operator()(Ts &&... ts)
Definition shi.hpp:794
Word(char const *str, size_t len)
Definition shi.hpp:786
Word(char const *str)
Definition shi.hpp:785
void_fp fp
Definition shi.hpp:828
Word(void_fp fp)
Definition shi.hpp:787
std::remove_cv_t< std::remove_reference_t< T > > type
Definition shi.hpp:483