home *** CD-ROM | disk | FTP | other *** search
- ;
- ; szSearch - An example of 32 bit assembly programming using MASM 6.1
- ;
- ; Purpose: search a buffer (rgbSearch) of length cbSearch for the
- ; first occurance of szTok (null terminated string).
- ;
- ; Method: A variation of the Boyer-Moore method.
- ; Determine length of szTok (n)
- ; set array of flags (rgfInTok) to true for each character in
- ; szTok
- ; set current position of search to rgbSearch (pbCur)
- ;
- ; compare current position to szTok by searching backwards from
- ; nth position. When a comparison fails at position
- ; (m), check to see if the current character in
- ; rgbSearch is in szTok by using rgfInTok. If not, set
- ; pbCur to pbCur+(m)+1 and restart compare. If pbCur is
- ; reached, increment pbCur and restart compare.
- ;
- ; reset rgfInTok to all 0 for next instantiation of the routine.
-
- .386
- .model flat,stdcall
-
- FALSE EQU 0
- TRUE EQU NOT FALSE
-
- .data
- ; flags buffer - data initialized to FALSE. We will
- ; set the appropriate flags to TRUE during initialization
- ; of szSearch and reset them to FALSE before exit.
- rgfInTok db 256 dup(FALSE);
-
- .code
-
- PBYTE TYPEDEF PTR BYTE
-
- szSearch PROC PUBLIC USES esi edi,
- rgbSearch:PBYTE,
- cbSearch:DWORD,
- szTok:PBYTE
-
- ; Initialize flags buffer. This tells us if a character is in
- ; the search token - Note how we use eax as an index
- ; register. This can be done with all extended registers.
- mov esi,szTok
- xor eax,eax
- .REPEAT
- lodsb
- mov BYTE PTR rgfInTok[eax],TRUE
- .UNTIL (!AL)
-
- ; save count of szTok bytes in edx
- mov edx,esi
- sub edx,szTok
- dec edx
-
- ; esi will always point to beginning of szTok
- mov esi,szTok
-
- ; edi will point to current search position
- ; it will also contain the return value
- mov edi,rgbSearch
-
- ; store pointer to end of rgbSearch in ebx
- mov ebx,edi
- add ebx,cbSearch
- sub ebx,edx
-
- ; initialize ecx with length of szTok
- mov ecx,edx
- .WHILE ( ecx != 0 )
- ; mov index to current characters to compare
- dec ecx
- mov al,[edi+ecx]
-
- ; if the current byte in the buffer doesn't exist in the
- ; search token, increment buffer pointer to current position
- ; +1 and start over. This can skip up to 'edx'
- ; bytes and reduce search time.
- .IF !(rgfInTok[eax])
- add edi,ecx
- inc edi
- ; initialize ecx with length of szTok
- mov ecx,edx
- ; otherwise, if the characters match, continue on as if
- ; we have a matching token
- .ELSEIF (al == [esi+ecx])
- .CONTINUE
- ; finally, if we have searched all szTok characters,
- ; and land here, we have a mismatch and we increment
- ; our pointer into rgbSearch by one and start over.
- .ELSEIF (!ecx)
- inc edi
- mov ecx,edx
- .ENDIF
-
- ; verify that we haven't searched beyond the buffer.
- .IF (edi > ebx)
- ; error value
- mov edi,0
- .BREAK
- .ENDIF
- .ENDW
-
- ; restore flags in rgfInTok to 0 (for next time).
- mov esi,szTok
- xor eax,eax
- .REPEAT
- lodsb
- mov BYTE PTR rgfInTok[eax],FALSE
- .UNTIL !AL
-
- ; put return value in eax
- mov eax,edi
- ret
- szSearch ENDP
-
- end
-
-