WAM book: How is code generated when dealing with argument registers (L1)?

153 Views Asked by At

I am working through Hassan Ait-Kaci's book Warren's Abstract Machine - A Tutorial Reconstruction. Currently I am stuck on section 2.4, "Argument Registers".

To be precise, what I don't understand is how to get from these register assignments (p.22) (for query p(Z,h(Z,W),f(W))):

A1 = Z
A2 = h(A1,X4)
A3 = f(X4)
X4 = W

to these instructions (p.24):

put_variable X4,A1
put_structure h/2,A2
set_value X4
set_variable X5
put_structure f/1,A3
set_value X5
call p/3

Like, where does X5 come from all of a sudden? In the register assignments, X4 refers to variable W, and there's no X5. But in the instructions, X5 refers to (what is/was essentially) W, and X4 now refers to Z. I am not seeing an explanation in the book. What am I missing?

1

There are 1 best solutions below

0
On

I tried to understand this but to no avail. Nothing in the errata. Here are some notes:

Instruction review

  • put_structure f/n,Xi: push a new STR (and adjoining functor) cell onto the heap and copy that cell into the allocated register address;
  • set_variable Xi: push a new REF cell onto the heap containing its own address, and copy it into the given register;
  • set_value Xi: push a new cell onto the heap and copy into the register's value.
  • In case of query:
    • put_variable Xn,Ai: the first occurrence of a variable in i-th argument position pushes a new unbound REF cell onto the heap and copies it into that variable's register as well as argument register Ai; and
    • put_value Xn,Ai (used for query): a later occurrence copies its value into argument register Ai.
  • In case of fact:
    • get_variable Xn,Ai: the first occurrence of a variable in i-th argument position sets it to the value of argument register Ai; and
    • get_value Xn,Ai: a later occurrence unifies with the value of Ai.

So, about that query

p(Z,h(Z,W),f(W)))

It seems to be coded differently on pages 17 and 19

Page 17 in the print edition    Page 19 in the print edition
(given as is)                   (translated by me from the WAM code)

A1 = Z                          A1 = Z
A2 = h(A1,X4)                   A2 = h(X4,X5)
A3 = f(X4)                      A3 = f(X5)
X4 = W                          X4 = Z
                                X5 = W

Edit: It seems the code on the left allows variables appearing in non-root-positions to be in "argument registers" which is disallowed on the right, hence indirection.

The code

The Ai are the argument registers, the Xi are some value registers.

put_variable X4,A1       Z is a argument root freshvar created in X4
                         and also goes into A1
put_structure h/2,A2     h/2 functor goes into A2
                         (1)
set_value X4             New (empty) cell is created, goes into the 
                         value of X4 
                         (2)
set_variable X5          W is a non-root freshvar created in X5
                         (3)
put_structure f/1,A3     f/1 functor goes into A3
set_value X5             New (empty) cell is created, goes into the 
                         value of X5 
                         (4)
call p/3                 Go!

At position (1), so far, so good. X4 and X5 seem to implicitly be the first and second arguments of the h/2 in A2 (is that right?)

X4 ----+---> [unbound REF] = Z (variable appearing at root)
       |
A1 ----+

A2 --------> [h/2] = h(X4,X5)

At (2)

X4 ----+---> [] = Z (variable appearing at root)
       |
A1 ----+

A2 --------> [h/2] = h(X4,X5)

At (3)

X4 ----+---> [] = Z (variable appearing at root)
       |
A1 ----+

A2 --------> [h/2] = h(X4,X5)

X5 --------> [myself REF] (variable not appearing at root)

At (4)

X4 ----+---> [] = Z (variable appearing at root)
       |
A1 ----+

A2 --------> [h/2] = h(X4,X5)

A3 --------> [f/1] = f(X5)

X5 --------> [] = W