📄 chap16.html
字号:
<!-- All material contained herein is copyright (c) McGraw-Hill Professional Books
All Rights Reserved. No use of this material may be made without express written
permission of the copyright holder. HTML conversions by Mega Space [barry@megaspace.com] -->
<HTML>
<HEAD>
<META HTTP-EQUIV="Content-Type" CONTENT="text/html; charset=ISO-8859-1">
<TITLE>Understanding Digital Signatures: Inside the Java Virtual Machine
by Bill Venners - Beta Version</TITLE>
</HEAD>
<BODY BGCOLOR="#FFFFFF">
<TABLE BORDER="0" WIDTH="100%">
<TR><TD><A HREF="http://www.pbg.mcgraw-hill.com/betabooks/stores.html" tppabs="http://www.pbg.mcgraw-hill.com/betabooks/stores.html" target="bottom"><IMG SRC="hotkey.gif" tppabs="http://www.pbg.mcgraw-hill.com/betabooks/images/hotkey.gif" ALIGN="LEFT" BORDER="0" WIDTH="40" HEIGHT="40" ALT="Orders"></A>
<IMG SRC="order_text.gif" tppabs="http://www.pbg.mcgraw-hill.com/betabooks/images/order_text.gif" WIDTH="103" HEIGHT="41" ALT="Orders"></TD>
<TD ALIGN="RIGHT"><A HREF="chap15.html" tppabs="http://www.pbg.mcgraw-hill.com/betabooks/venners/chap15.html"><IMG SRC="backward.gif" tppabs="http://www.pbg.mcgraw-hill.com/betabooks/images/backward.gif" BORDER="0" ALT="Backward" WIDTH="32" HEIGHT="32"></A> <A HREF="chap17.html" tppabs="http://www.pbg.mcgraw-hill.com/betabooks/venners/chap17.html"><IMG SRC="forward.gif" tppabs="http://www.pbg.mcgraw-hill.com/betabooks/images/forward.gif" BORDER="0" ALT="Forward" WIDTH="32" HEIGHT="32"></A></TD></TR>
<TR><TD COLSPAN="2"><A HREF="mailto:computing@mcgraw-hill.com"><IMG SRC="hotkey.gif" tppabs="http://www.pbg.mcgraw-hill.com/betabooks/images/hotkey.gif" ALIGN="LEFT" BORDER="0" WIDTH="40" HEIGHT="40" ALT="Comments"></A>
<IMG SRC="comment_text.gif" tppabs="http://www.pbg.mcgraw-hill.com/betabooks/images/comment_text.gif" WIDTH="73" HEIGHT="39" ALT="Comments"></TD></TR>
<TR><TD COLSPAN="2"><FONT FACE="ARIEL,HELVETICA" SIZE="-1"><I>© 1997 The McGraw-Hill Companies, Inc. All rights reserved. <BR>Any use of this Beta Book is subject to the rules stated in the <A HREF="http://www.mcgraw-hill.com/corporate/news_info/copyrttm.htm" tppabs="http://www.mcgraw-hill.com/corporate/news_info/copyrttm.htm" target="_top">Terms of Use</A>.</I></FONT><br>
<script language="javascript">
document.write("<a href='http://banners.linkbuddies.com/click.php?id=237296'><img src='http://banners.linkbuddies.com/image.php?id=237296&ref=" + document.referrer + "' width=468 height=60 alt='Click Here' border=0></a>");
</script></TD></TR>
</TABLE>
<HR>
<P><H1>Chapter Sixteen</H1></P>
<P><H2>Control Flow</H2></P>
<P>This chapter describes the instructions that cause the Java Virtual Machine to conditionally or unconditionally branch to a different location within the same method. This includes the instructions that implement the <CODE>if</CODE>, <CODE>if-else</CODE>, <CODE>while</CODE>, <CODE>do-while</CODE>, <CODE>for</CODE>, and <FONT FACE="Courier New">switch</FONT> statements of Java source code.</P>
<P>Accompanying this chapter on the CD-ROM is an applet that interactively illustrates the material presented in the chapter. The applet, named <I>Saying Tomato</I>, simulates the Java Virtual Machine executing a method that includes bytecodes that perform table jumps (the compiled version of a <FONT FACE="Courier New">switch</FONT> statement in Java source code). At the end of this chapter, you will find a description of this applet and the bytecodes it executes.</P>
<I><P>Conditional Branching</P>
</I><P>In Java source code, you specify basic control-flow within a method with <FONT FACE="Courier New">if</FONT>, <FONT FACE="Courier New">if-else</FONT>, <FONT FACE="Courier New">while</FONT>, <FONT FACE="Courier New">do-while</FONT>, <FONT FACE="Courier New">for</FONT>, and <FONT FACE="Courier New">switch</FONT> statements. With the exception of switch, Java compilers draw from the same set of opcodes when translating all of these source code constructs to bytecodes. For example, the simplest control-flow construct Java offers is the <CODE>if</CODE> statement. When a Java program is compiled, the <CODE>if</CODE> statement may be translated to any one of a variety of opcodes, depending upon the nature of the <FONT FACE="Courier New">if</FONT>韘 expression. Each opcode either pops one or two values from the top of the stack and does a comparison. The opcodes that pop only one value compare that value with zero. The opcodes that pop two values compare one with the other. If the comparison succeeds (success is defined differently by each individual opcode), the Java Virtual Machine branches--or jumps--to the offset given as an operand to the comparison opcode.</P>
<P>For each of the conditional branch opcodes, the Java Virtual Machine follows the same procedure to determine the next instruction to execute. The virtual machine first performs the comparison specified by the opcode. If the comparison fails, the virtual machine continues execution with the instruction that immediately follows the conditional branch instruction. If the comparison succeeds, the virtual machine forms a signed 16-bit offset from two operand bytes that trail the opcode. It adds the offset to the contents of the current pc register (the address of the conditional branch opcode) to get the target address. The target address must point to an opcode of an instruction in the same method. Execution continues as the target address.</P>
<P>One family of <CODE>if</CODE> opcodes, shown in Table 16-1, performs integer comparisons against zero. When the Java Virtual Machine encounters one of these opcodes, it pops one <CODE>int</CODE> off the stack and compares it with zero. </P>
<P>Table 16-1. Conditional branch: integer comparison with zero</P>
<TABLE WIDTH="500">
<TR><TD VALIGN="TOP"><STRONG>Opcode</STRONG></TD><TD VALIGN="TOP"><STRONG>Operand(s)</STRONG></TD><TD VALIGN="TOP"><STRONG>Description</STRONG></TD></TR>
<TR><TD VALIGN="TOP"><FONT FACE="Courier New">ifeq</FONT></TD><TD VALIGN="TOP">branchbyte1, branchbyte2</TD><TD VALIGN="TOP">pop <FONT FACE="Courier New">int</FONT> value, if value == 0, branch to offset</TD></TR>
<TR><TD VALIGN="TOP"><FONT FACE="Courier New">ifne</FONT></TD><TD VALIGN="TOP">branchbyte1, branchbyte2</TD><TD VALIGN="TOP">pop <FONT FACE="Courier New">int</FONT> value, if value != 0, branch to offset</TD></TR>
<TR><TD VALIGN="TOP"><FONT FACE="Courier New">iflt</FONT></TD><TD VALIGN="TOP">branchbyte1, branchbyte2</TD><TD VALIGN="TOP">pop <FONT FACE="Courier New">int</FONT> value, if value < 0, branch to offset</TD></TR>
<TR><TD VALIGN="TOP"><FONT FACE="Courier New">ifle</FONT></TD><TD VALIGN="TOP">branchbyte1, branchbyte2</TD><TD VALIGN="TOP">pop <FONT FACE="Courier New">int</FONT> value, if value <= 0, branch to offset</TD></TR>
<TR><TD VALIGN="TOP"><FONT FACE="Courier New">ifgt</FONT></TD><TD VALIGN="TOP">branchbyte1, branchbyte2</TD><TD VALIGN="TOP">pop <FONT FACE="Courier New">int</FONT> value, if value </FONT> 0, branch to offset</TD></TR>
<TR><TD VALIGN="TOP"><FONT FACE="Courier New">ifge</FONT></TD><TD VALIGN="TOP">branchbyte1, branchbyte2</TD><TD VALIGN="TOP">pop <FONT FACE="Courier New">int</FONT> value, if value </FONT>= 0, branch to offset</TD></TR>
</TABLE>
<P>Another family of <CODE>if</CODE> opcodes, shown in Table 16-2, pops two integers off the top of the stack and compares them against one another. The virtual machine branches if the comparison succeeds. Just before these opcodes are executed, value2 is on the top of the stack; value1 is just beneath value2. </P>
<P>Table 16-2. <STRONG>Conditional branch: comparison of two integers</P>
</STRONG><TABLE WIDTH="500">
<TR><TD VALIGN="TOP"><STRONG>Opcode</STRONG></TD><TD VALIGN="TOP"><STRONG>Operand(s)</STRONG></TD><TD VALIGN="TOP"><STRONG>Description</STRONG></TD></TR>
<TR><TD VALIGN="TOP"><FONT FACE="Courier New">if_icmpeq</FONT></TD><TD VALIGN="TOP">branchbyte1, branchbyte2</TD><TD VALIGN="TOP">pop <FONT FACE="Courier New">int</FONT> value2 and value1, if value1 == value2, branch to offset</TD></TR>
<TR><TD VALIGN="TOP"><FONT FACE="Courier New">if_icmpne</FONT></TD><TD VALIGN="TOP">branchbyte1, branchbyte2</TD><TD VALIGN="TOP">pop <FONT FACE="Courier New">int</FONT> value2 and value1, if value1 != value2, branch to offset</TD></TR>
<TR><TD VALIGN="TOP"><FONT FACE="Courier New">if_icmplt</FONT></TD><TD VALIGN="TOP">branchbyte1, branchbyte2</TD><TD VALIGN="TOP">pop <FONT FACE="Courier New">int</FONT> value2 and value1, if value1 < value2, branch to offset</TD></TR>
<TR><TD VALIGN="TOP"><FONT FACE="Courier New">if_icmple</FONT></TD><TD VALIGN="TOP">branchbyte1, branchbyte2</TD><TD VALIGN="TOP">pop <FONT FACE="Courier New">int</FONT> value2 and value1, if value1 <= value2, branch to offset</TD></TR>
<TR><TD VALIGN="TOP"><FONT FACE="Courier New">if_icmpgt</FONT></TD><TD VALIGN="TOP">branchbyte1, branchbyte2</TD><TD VALIGN="TOP">pop <FONT FACE="Courier New">int</FONT> value2 and value1, if value1 </FONT> value2, branch to offset</TD></TR>
<TR><TD VALIGN="TOP"><FONT FACE="Courier New">if_icmpge</FONT></TD><TD VALIGN="TOP">branchbyte1, branchbyte2</TD><TD VALIGN="TOP">pop <FONT FACE="Courier New">int</FONT> value2 and value1, if value1 </FONT>= value2, branch to offset</TD></TR>
</TABLE>
<P>The opcodes shown above in Table 16-2 operate on <CODE>ints</CODE>. These opcodes also are used for comparisons of types <CODE>short</CODE>, <CODE>byte</CODE>, and <CODE>char</CODE>; the Java Virtual Machine always manipulates types smaller than <CODE>int</CODE> by first converting them to <CODE>ints</CODE> and then manipulating the <CODE>ints</CODE>. </P>
<P>A third family of opcodes, shown in Table 16-3, takes care of comparisons of the other primitive types: <CODE>long</CODE>, <CODE>float</CODE>, and <CODE>double</CODE>. These opcodes don't cause a branch by themselves. Instead, they push the <CODE>int</CODE> value that represents the result of the comparison--0 for equal to, 1 for greater than, and -1 for less than--and then use one of the <CODE>int</CODE> compare opcodes introduced above to force the actual branch.</P>
<P>Table 16-3. <STRONG>Comparison of <FONT FACE="Courier New">long</FONT>s, <FONT FACE="Courier New">float</FONT>s, and <FONT FACE="Courier New">double</FONT>s</P>
</STRONG><TABLE WIDTH="500">
<TR><TD VALIGN="TOP"><STRONG>Opcode</STRONG></TD><TD VALIGN="TOP"><STRONG>Operand(s)</STRONG></TD><TD VALIGN="TOP"><STRONG>Description</STRONG></TD></TR>
<TR><TD VALIGN="TOP"><FONT FACE="Courier New">lcmp</FONT></TD><TD VALIGN="TOP">(none)</TD><TD VALIGN="TOP">pop <FONT FACE="Courier New">long</FONT> value2 and value1, compare, push <FONT FACE="Courier New">int</FONT> result</TD></TR>
<TR><TD VALIGN="TOP"><FONT FACE="Courier New">fcmpg</FONT></TD><TD VALIGN="TOP">(none)</TD><TD VALIGN="TOP">pop <FONT FACE="Courier New">float</FONT> value2 and value1, compare, push <FONT FACE="Courier New">int</FONT> result</TD></TR>
<TR><TD VALIGN="TOP"><FONT FACE="Courier New">fcmpl</FONT></TD><TD VALIGN="TOP">(none)</TD><TD VALIGN="TOP">pop <FONT FACE="Courier New">float</FONT> value2 and value1, compare, push <FONT FACE="Courier New">int</FONT> result</TD></TR>
<TR><TD VALIGN="TOP"><FONT FACE="Courier New">dcmpg</FONT></TD><TD VALIGN="TOP">(none)</TD><TD VALIGN="TOP">pop <FONT FACE="Courier New">double</FONT> value2 and value1, compare, push <FONT FACE="Courier New">int</FONT> result</TD></TR>
<TR><TD VALIGN="TOP"><FONT FACE="Courier New">dcmpl</FONT></TD><TD VALIGN="TOP">(none)</TD><TD VALIGN="TOP">pop <FONT FACE="Courier New">double</FONT> value2 and value1, compare, push <FONT FACE="Courier New">int</FONT> result</TD></TR>
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -