summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--core.e6
-rw-r--r--transform.e51
2 files changed, 46 insertions, 11 deletions
diff --git a/core.e b/core.e
index 2aabc6f..bbe1ba8 100644
--- a/core.e
+++ b/core.e
@@ -1209,7 +1209,7 @@ here !
   ~ (output point, source, destination, length)
   memcopy ;
 
-~ (output point, alignment byte count -- output point)
+~ (output point, alignment byte width -- output point)
 : packalign
   { 2dup /% drop { drop exit } unless
     swap 0 pack8 swap } forever ;
@@ -1231,7 +1231,7 @@ here !
 : unpack16 dup 16@ swap 2 + swap ;
 : unpack8 dup 8@ swap 1 + swap ;
 
-~ (proposed size, alignment byte count -- adjusted size)
+~ (proposed size, alignment byte width -- adjusted size)
 : align-size
   dup 3unroll dup 3unroll
   ~ (alignment, alignment, proposed size, alignment)
@@ -1240,7 +1240,7 @@ here !
 ~   You might think this would be identical to packalign, but packalign has
 ~ side effects.
 ~
-~ (input point, alignment byte count -- input point)
+~ (input point, alignment byte width -- input point)
 : unpackalign align-size ;
 
 
diff --git a/transform.e b/transform.e
index 26f4adb..9605341 100644
--- a/transform.e
+++ b/transform.e
@@ -2879,6 +2879,41 @@ allocate-transformation-state s" transformation-state" variable
 
 ~   By overriding colon, we can special-case the definitions of particular
 ~ words. It's very metacircular.
+~
+~   This lets us prepend trap code to the original definition. For those not
+~ familiar, a "trap" in systems programming is code that runs instead of some
+~ other, pre-existing code, by violating the usual abstractions in some way.
+~ We implement our traps by creating the word header, including the docol
+~ pointer, then compiling the trap code before we return from the colon
+~ alternate, so that it's already been output before the original word's body
+~ starts to compile.
+~
+~   Prepending our trap code to the original code like this can also be used
+~ to get the effect of replacing the original code entirely by calling "exit"
+~ at the end of our trap. The original code will still be compiled, after the
+~ trap code, but doing this will make sure it doesn't run. Most of the time,
+~ though, we do want to run the original code, so we allow the trap to fall
+~ through to it. We carefully note fall-through with comments, to make the
+~ traps easier to maintain.
+~
+~   The kinds of side-effects we care about can all be written this way,
+~ though occasionally we wind up having to compute an intermediate value that
+~ the code we're trapping will then compute independently, and it's important
+~ to keep those implementations in sync.
+~
+~   The most significant challenge is that, because our trap will be defined
+~ at the same point in loading as the original word would be, it can only use
+~ words that are available at that point. Occasionally this results in some
+~ awkwardness.
+~
+~   Code for these traps winds up looking a lot like code written for log-load
+~ alternates, in that we have to do the dictionary lookups and other
+~ compilation ourselves.
+~
+~   At times, we also need to trap words that are implemented in assembler.
+~ The most notable of these is "sys-write", which is fundamental to what the
+~ hex transform does. The details of how we make our traps work with assembler
+~ words are explained below, as they arise.
 : hex-colon-alternate
   word value@
 
@@ -3045,7 +3080,7 @@ allocate-transformation-state s" transformation-state" variable
     s" docol" find entry-to-execution-token execute ,
     make-hidden
 
-    ~ (output point, alignment byte count)
+    ~ (output point, alignment byte width)
     s" 2dup" find entry-to-execution-token ,
 
     ~   We can't use unpackalign because this patch happens at the time
@@ -3062,7 +3097,7 @@ allocate-transformation-state s" transformation-state" variable
     s" swap" find entry-to-execution-token ,
     s" drop" find entry-to-execution-token ,
     s" *" find entry-to-execution-token ,
-    ~ (output point, alignment byte count, padding end)
+    ~ (output point, alignment byte width, padding end)
 
     ~ We can't use pick, either.
     s" 3roll" find entry-to-execution-token ,
@@ -3071,15 +3106,15 @@ allocate-transformation-state s" transformation-state" variable
     s" lit" find entry-to-execution-token ,
     5 ,
     s" unroll" find entry-to-execution-token ,
-    ~ (output point, alignment byte count, padding end, output point,
+    ~ (output point, alignment byte width, padding end, output point,
     ~  output point)
 
     s" 3unroll" find entry-to-execution-token ,
     s" -" find entry-to-execution-token ,
-    ~ (output point, alignment byte count, padding start, padding length)
+    ~ (output point, alignment byte width, padding start, padding length)
 
     ' hex-output-metadata-entry-type-alignment entry-to-execution-token ,
-    ~ (output point, alignment byte count, padding start, padding length,,
+    ~ (output point, alignment byte width, padding start, padding length,,
     ~  entry type)
 
     ~ Again, no pick.
@@ -3091,10 +3126,10 @@ allocate-transformation-state s" transformation-state" variable
     5 ,
     s" unroll" find entry-to-execution-token ,
 
-    ~ (output point, alignment byte count, padding start, padding length,
-    ~  entry type, alignment byte count)
+    ~ (output point, alignment byte width, padding start, padding length,
+    ~  entry type, alignment byte width)
     ' add-hex-output-metadata-entry entry-to-execution-token ,
-    ~ (output point, alignment byte count)
+    ~ (output point, alignment byte width)
     ~ Fall through to the inner implementation.
 
     ' ] entry-to-execution-token execute