Decompilation works again.
[forth.jl.git] / src / lib_8_decompiler.4th
index d9c9f3a..90ba109 100644 (file)
@@ -1,13 +1,61 @@
 \ Decompilation
 
-: >NAME
-        BEGIN
-                1- DUP @
-                NFA_MARK AND
-        NFA_MARK = UNTIL
+: VCFA>LATEST
+        1+ @
 ;
 
-: >LFA  >NAME 1- ;
+: CLOSESTLINK ( addr vcfa -- lfa )
+
+        vcfa>latest dup         ( addr link link )
+        rot dup -rot            ( link addr link addr )
+        < if
+                2drop
+                0 exit
+        then
+
+        swap    ( addr link )
+        0 -rot  ( 0 addr link )
+        
+        begin
+                rot drop        ( addr link )
+                dup -rot @      ( link addr nextlink )
+                2dup            ( link addr nextlink addr nextlink)
+        > until
+
+        2drop
+;
+
+: MIN           ( n m -- max )
+        2dup - 0> if
+                swap drop
+        else
+                drop
+        then
+;
+
+: BODYLEN ( cfa -- len )
+
+        here swap ( clink addr )
+        context dup #context @ + swap
+        do
+                dup i @
+
+                closestlink ( clink addr clink' )
+
+                ?dup 0> if
+                        rot min
+                        swap
+                then
+        loop
+
+        -
+;
+
+: ?IMMEDIATE
+        1+              ( skip over the link pointer )
+        @               ( get the flags/length byte )
+        F_IMMED AND     ( mask the F_IMMED flag and return it (as a truth value) )
+;
 
 : SEE
         BL WORD FIND    ( find the dictionary entry to decompile )
                 EXIT
         THEN
 
-        >LFA
-
-        ( Now we search again, looking for the next word in the dictionary.  This gives us
-          the length of the word that we will be decompiling.  (Well, mostly it does). )
-        HERE          ( address of the end of the last compiled word )
-        LATEST @        ( word last curr )
-        BEGIN
-                2 PICK          ( word last curr word )
-                OVER            ( word last curr word curr )
-                <>              ( word last curr word<>curr? )
-        WHILE                   ( word last curr )
-                NIP             ( word curr )
-                DUP @           ( word curr prev (which becomes: word last curr) )
-        REPEAT
-
-        DROP            ( at this point, the stack is: start-of-word end-of-word )
-        SWAP            ( end-of-word start-of-word )
+        DUP DUP BODYLEN + SWAP >LINK
 
-        DUP >CFA @ CASE
+        DUP LINK> @ CASE
                 DOCOL OF
                         \ Colon definition
                         [CHAR] : EMIT SPACE DUP 1+ .NAME SPACE
@@ -61,7 +93,7 @@
 
         4 SPACES
 
-        >CFA >BODY            ( get the data address, ie. points after DOCOL | end-of-word start-of-data )
+        LINK> >BODY            ( get the data address, ie. points after DOCOL | end-of-word start-of-data )
 
         ( now we start decompiling until we hit the end of the word )
         BEGIN           ( end start )