abrash-black-book/07-03.html
2013-12-30 12:21:49 +11:00

160 lines
6.3 KiB
HTML

<HTML>
<HEAD>
<META name=vsisbn content="1576101746">
<META name=vstitle content="Michael Abrash's Graphics Programming Black Book, Special Edition">
<META name=vsauthor content="Michael Abrash">
<META name=vspublisher content="The Coriolis Group">
<META name=vspubdate content="07/01/97">
<META name=vscategory content="Web and Software Development: Game Development,Web and Software Development: Graphics and Multimedia Development">
<TITLE>Michael Abrash's Graphics Programming Black Book Special Edition: Local Optimization</TITLE>
<!-- HEADER -->
<!-- Empty Reference Subhead -->
<!--ISBN=1576101746//-->
<!--TITLE=Michael Abrash's Graphics Programming Black Book Special Edition//-->
<!--AUTHOR=Michael Abrash//-->
<!--PUBLISHER=The Coriolis Group, Inc.//-->
<!--CHAPTER=07//-->
<!--PAGES=141-143//-->
<!--UNASSIGNED1//-->
<!--UNASSIGNED2//--></HEAD><BODY LINK=#0000FF ALINK=#000099 VLINK=#0000FF BGCOLOR=#FFFFFF>
<CENTER>
<TABLE BORDER>
<TR>
<TD><A HREF="07-02.html">Previous</A></TD>
<TD><A HREF="index.html">Table of Contents</A></TD>
<TD><A HREF="07-04.html">Next</A></TD>
</TR>
</TABLE>
</CENTER>
<P><BR></P>
<P><B>LISTING 7.1 L7-1.ASM</B></P>
<!-- CODE //-->
<PRE>
; Program to illustrate searching through a buffer of a specified
; length until either a specified byte or a zero byte is
; encountered.
; A standard loop terminated with LOOP is used.
.model small
.stack 100h
.data
; Sample string to search through.
SampleString labelbyte
db &#145;This is a sample string of a long enough length &#146;
db &#145;so that raw searching speed can outweigh any &#146;
db &#145;extra set-up time that may be required.&#146;,0
SAMPLE_STRING_LENGTH equ $-SampleString
; User prompt.
Prompt db &#145;Enter character to search for:$&#146;
; Result status messages.
ByteFoundMsg db 0dh,0ah
db &#145;Specified byte found.&#146;,0dh,0ah,&#145;$&#146;
ZeroByteFoundMsg db 0dh, 0ah
db &#145;Zero byte encountered.&#146;,0dh,0ah,&#145;$&#146;
NoByteFoundMsg db 0dh,0ah
db &#145;Buffer exhausted with no match.&#146;, 0dh, 0ah, &#145;$&#146;
.code
Startprocnear
mov ax,@data ;point to standard data segment
mov ds,ax
mov dx,offset Prompt
mov ah,9 ;DOS print string function
int 21h ;prompt the user
mov ah,1 ;DOS get key function
int 21h ;get the key to search for
mov ah,al ;put character to search for in AH
mov cx,SAMPLE_STRING_LENGTH ;# of bytes to search
mov si,offset SampleString ;point to buffer to search
call SearchMaxLength ;search the buffer
mov dx,offset ByteFoundMsg ;assume we found the byte
jc PrintStatus ;we did find the byte
;we didn&#146;t find the byte, figure out
;whether we found a zero byte or
;ran out of buffer
mov dx,offset NoByteFoundMsg
;assume we didn&#146;t find a zero byte
jcxz PrintStatus ;we didn&#146;t find a zero byte
mov dx,offset ZeroByteFoundMsg ;we found a zero byte
PrintStatus:
mov ah,9 ;DOS print string function
int 21h ;report status
mov ah,4ch ;return to DOS
int 21h
Startendp
; Function to search a buffer of a specified length until either a
; specified byte or a zero byte is encountered.
; Input:
; AH = character to search for
; CX = maximum length to be searched (must be &gt 0)
; DS:SI = pointer to buffer to be searched
; Output:
; CX = 0 if and only if we ran out of bytes without finding
; either the desired byte or a zero byte
; DS:SI = pointer to searched-for byte if found, otherwise byte
; after zero byte if found, otherwise byte after last
; byte checked if neither searched-for byte nor zero
; byte is found
; Carry Flag = set if searched-for byte found, reset otherwise
SearchMaxLengthprocnear
cld
SearchMaxLengthLoop:
lodsb ;get the next byte
cmp al,ah ;is this the byte we want?
jz ByteFound ;yes, we&#146;re done with success
and al,al ;is this the terminating 0 byte?
jz ByteNotFound ;yes, we&#146;re done with failure
loop SearchMaxLengthLoop ;it&#146;s neither, so check the next
;byte, if any
ByteNotFound:
clc ;return &#147;not found&#148; status
ret
ByteFound:
dec si ;point back to the location at which
;we found the searched-for byte
stc ;return &#147;found&#148; status
ret
SearchMaxLengthendp
end Start
</PRE>
<!-- END CODE //-->
<H3><A NAME="Heading7"></A><FONT COLOR="#000077">Unrolling Loops</FONT></H3>
<P>Listing 7.2 takes a different tack, unrolling the loop so that four bytes are checked for each <B>LOOP</B> performed. The same instructions are used inside the loop in each listing, but Listing 7.2 is arranged so that three-quarters of the <B>LOOP</B>s are eliminated. Listings 7.1 and 7.2 perform exactly the same task, and they use the same instructions in the loop&#151;the searching algorithm hasn&#146;t changed in any way&#151;but we have sequenced the instructions differently in Listing 7.2, and that makes all the difference.</P><P><BR></P>
<CENTER>
<TABLE BORDER>
<TR>
<TD><A HREF="07-02.html">Previous</A></TD>
<TD><A HREF="index.html">Table of Contents</A></TD>
<TD><A HREF="07-04.html">Next</A></TD>
</TR>
</TABLE>
</CENTER>
<hr width="90%" size="1" noshade>
<div align="center">
<font face="Verdana,sans-serif" size="1">Graphics Programming Black Book &copy; 2001 Michael Abrash</font>
</div>
<!-- all of the reference materials (books) have the footer and subfoot reveresed -->
<!-- reference_subfoot = footer -->
<!-- reference_footer = subfoot -->
<!-- BEGIN SUB FOOTER -->
</BODY>
</HTML>
<!-- END FOOTER -->