handouts/ho07.tex
changeset 374 0e25fb72d339
parent 373 b018234c9126
child 375 bf36664a3196
equal deleted inserted replaced
373:b018234c9126 374:0e25fb72d339
   492 \multicolumn{3}{l}{$\qquad\phantom{(}@\; \text{goto}\;l_{wbegin}$}\\
   492 \multicolumn{3}{l}{$\qquad\phantom{(}@\; \text{goto}\;l_{wbegin}$}\\
   493 \multicolumn{3}{l}{$\qquad\phantom{(}@\;L_{wend}:, E')$}\\
   493 \multicolumn{3}{l}{$\qquad\phantom{(}@\;L_{wend}:, E')$}\\
   494 \end{tabular}
   494 \end{tabular}
   495 \end{center}
   495 \end{center}
   496 
   496 
   497 Next we need to consider the statement \pcode{write x}, which 
   497 Next we need to consider the statement \pcode{write x}, which
   498 can be used to write out the content of a variable. For this 
   498 can be used to write out the content of a variable. For this
   499 we need to use a Java library function. In order to avoid
   499 we need to use a Java library function. In order to avoid
   500 having to generate a lot of code for each 
   500 having to generate a lot of code for each
   501 \pcode{write}-command, we use a separate method and just call
   501 \pcode{write}-command, we use a separate method and just call
   502 this method with an appropriate stack.
   502 this method with an argument (which needs to be placed on the
       
   503 stack). The code is as follows.
       
   504 
   503 
   505 
   504 \begin{lstlisting}[language=JVMIS]
   506 \begin{lstlisting}[language=JVMIS]
   505 .method public static write(I)V 
   507 .method public static write(I)V 
   506     .limit locals 5 
   508     .limit locals 1 
   507     .limit stack 5  
   509     .limit stack 2 
   508     getstatic java/lang/System/out Ljava/io/PrintStream; 
   510     getstatic java/lang/System/out Ljava/io/PrintStream; 
   509     iload 0
   511     iload 0
   510     invokevirtual java/io/PrintStream/println(I)V 
   512     invokevirtual java/io/PrintStream/println(I)V 
   511     return 
   513     return 
   512 .end method
   514 .end method
   513 \end{lstlisting}
   515 \end{lstlisting}
   514 
   516 
       
   517 \noindent The first line marks the beginning of the method,
       
   518 called \pcode{write}. It takes a single integer argument
       
   519 indicated by the \pcode{(I)} and returns no result, indicated
       
   520 by the \pcode{V}. Since the method has only one argument, we
       
   521 only need a single local variable (Line~2) and a stack with
       
   522 two cells will be sufficient (Line 3). Line 4 instructs the
       
   523 JVM to get the value of the field \pcode{out} of the class
       
   524 \pcode{java/lang/System}. It expects the value to be of type
       
   525 \pcode{java/io/PrintStream}. A reference to this value will be
       
   526 placed on the stack. Line~5 copies the integer we want to
       
   527 print out onto the stack. In the next line we call the method
       
   528 \pcode{println} (from the class \pcode{java/io/PrintStream}).
       
   529 We want to print out an integer and do not expect anything
       
   530 back (that is why the type annotation \pcode{(I)V}). The
       
   531 \pcode{return}-instruction in the next line changes the
       
   532 control-flow back to the place from where \pcode{write} was
       
   533 called. This method needs to be part of a header that is
       
   534 included in any code we generate. The method \pcode{write} can
       
   535 be invoked with the two instructions
       
   536 
       
   537 \begin{lstlisting}[mathescape,language=JVMIS]
       
   538 iload $E(x)$ 
       
   539 invokestatic XXX/XXX/write(I)V
       
   540 \end{lstlisting}
       
   541 
       
   542 \noindent where we first place the variable to be printed on
       
   543 the stack and then call \pcode{write}. The \pcode{XXX} need to
       
   544 be replaced by appropriate class name (this will be explained
       
   545 shortly).
       
   546 
       
   547 
       
   548 \begin{figure}[t]
       
   549 \begin{lstlisting}[mathescape,language=JVMIS]
       
   550 .class public XXX.XXX
       
   551 .super java/lang/Object
       
   552 
       
   553 .method public <init>()V
       
   554     aload_0
       
   555     invokenonvirtual java/lang/Object/<init>()V
       
   556     return
       
   557 .end method
       
   558 
       
   559 .method public static main([Ljava/lang/String;)V
       
   560     .limit locals 200
       
   561     .limit stack 200
       
   562 
       
   563       $\textit{\ldots{}here comes the compiled code\ldots}$
       
   564 
       
   565     return
       
   566 .end method
       
   567 \end{lstlisting}
       
   568 \caption{Boilerplate code needed for running generated code.\label{boiler}}
       
   569 \end{figure}
       
   570 
       
   571 
       
   572 By generating code for a While-program, we end up with a list
       
   573 of (JVM assembly) instructions. Unfortunately, there is a bit
       
   574 more boilerplate code needed before these instructions can be
       
   575 run. The code is shown in Figure~\ref{boiler}. This
       
   576 boilerplate code is very specific to the JVM. Lines 4 to 8 
       
   577 contains a method for object creation in the JVM and is called 
       
   578 \emph{before} the \pcode{main}-method in Lines 10 to 17. 
       
   579 Interesting are the Lines 11 and 12 where we hardwire that the 
       
   580 stack of our program will never be larger than 200 and that 
       
   581 the maximum number of variables is also 200. This seem 
       
   582 conservative default values that allow is to run some simple
       
   583 While-programs. In a real compiler, we would of course need to
       
   584 work harder and find out appropriate values for the stack and 
       
   585 local variables.
       
   586 
       
   587 
   515 \end{document}
   588 \end{document}
   516 
   589 
   517 %%% Local Variables: 
   590 %%% Local Variables: 
   518 %%% mode: latex  
   591 %%% mode: latex  
   519 %%% TeX-master: t
   592 %%% TeX-master: t