;
==================== source-file :_nd_search.asm ===================
;
;
This source-code is part of the:
; "32-bit Assembly Language and 'C' Extensions for
Visual Prolog"
;
;
( Copyright: See the comment at the end of this file. )
;
COMMENT
~
;
Purpose: non-deterministic search for a character, sub-string or
sub-binary,
; inside a string or a binary.
;
Produces all the positions where a certain character or
sub-string or sub-
;
binary is found inside a string or a binary at each non-deterministic
call;
;
it then fails, after all positions have been found.
;
;
NOTE: Can be called with "findall/3", to find ALL the positions where a
; char, sub-string, or sub-binary is located, inside
a string or a binary.
IDEAL
P586
MODEL FLAT
DATASEG
ALIGN
4
extrn ctb:dword
CODESEG
ALIGN
4
;
======= first two variants deal with strings only (most common):
public _nd_search_0 ;(STRING,CHAR,posx)
public _nd_search_1 ;(STRING,STRING,posx)
;
======= next three variants deal with binaries:
public _nd_search_2 ;(BINARY,CHAR,posx)
public _nd_search_3 ;(BINARY,STRING,posx)
public _nd_search_4 ;(BINARY,BINARY,posx)
;
======= next two variants accept an "initial position"(arg 3):
public _nd_search_5 ;(STRING,CHAR,inpos,posx)
public _nd_search_6 ;(STRING,STRING,inpos,posx)
;
======= next three variants deal with binaries, accepting "initial
position"(arg 3):
public _nd_search_7 ;(BINARY,CHAR,inpos,posx)
public _nd_search_8 ;(BINARY,STRING,inpos,posx)
public _nd_search_9 ;(BINARY,BINARY,inpos,posx)
;
======= next two variants take a "case char-table"(arg 4), and
init_pos(arg 3):
public _nd_search_10 ;(STRING,CHAR,inpos,case,posx)
public _nd_search_11 ;(STRING,STRING,inpos,case,posx)
;
======= next 3 variants take "case" and "initial position" but deal
with binaries:
public _nd_search_12 ;(BINARY,CHAR,inpos,case,posx)
public _nd_search_13 ;(BINARY,STRING,inpos,case,posx)
public _nd_search_14 ;(BINARY,BINARY,inpos,case,posx)
Macro
pushx3
push esi
push edi
push ebx
endm
Macro
popx3
pop ebx
pop edi
pop esi
ret
endm
extrn _MEM_AllocGStack:near
extrn _MEM_AdjustGStackAlloc:near
extrn _RUN_Fail:near
extrn _RUN_JmpReturn:near
extrn _RUN_StackBTrack:near
extrn _RUN_JmpReturn1:near
extrn _MEM_MakeBinaryGStack:near
PROC
_nd_search_0 near ;
(STRING,CHAR,UNSIGNED) -(i,i,o)
ENTER
12,0 ;
ARG
strg1:dword,char1:byte,outpx:dword
pushx3
mov esi,[strg1] ; string input.............. ARG-1(input)
mov [ebp-8], esi ;
mov ah,[char1] ; char ..................... ARG-2(input)
mov [ebp-4], eax ;
;
-------------------
@@LP0:
mov eax,[ebp-4] ;
@@LP0a:
lodsb
;
cmp al,ah ;
jz @@ok1 ;
or al,al ;
jz @@XZ1 ; if zero, fail at
end of string
jmp @@LP0a ; else repeat THIS loop
;
=========================
@@ok1:
mov [ebp-8],esi
; store it
call _RUN_StackBTrack ; stack a 'backtrack point' in Visual Prolog
mov esi,[ebp-8] ; recover ESI
or eax,eax ; is
the result (of StackBTrack) zero?
jne @@LP0 ; if
not, read more...
;
-------------------------
mov eax,esi ;
return right_hand_side string (after the char)
mov ecx,eax ;
mov ebx,[strg1] ; string
input.............. ARG-1(input)
sub ecx,ebx ;
mov edx,[outpx] ; give Position of Char
.... ARG-3(output)
mov [edx],ecx ;
call _RUN_JmpReturn1 ; call Visual Prolog function
"_RUN_JmpReturn1"
mov esi,[ebp-8] ;
jmp @@LP0
; repeat big loop
;
=========================
@@XZ1:
call _RUN_Fail ; FAIL
popx3
LEAVE
ENDP
_nd_search_0
PROC
_nd_search_1 near ; (STRING,STRING,POSITION)
-(i,i,o)
ENTER
16,0 ;
ARG
strg1:dword,substr:dword,outpx:dword
pushx3
mov edi,[substr] ; substring................
ARG-2(input)
cmp [byte ptr edi],0 ; special case of substr=""?
jnz @@Laa
; if not so, normal processing
;
------------------------
jmp @@XZ1
; else, fail
mov edi,[strg1] ;
xor eax,eax ;
mov ecx,eax ;
not ecx
;
repne scasb ;
not ecx
;
mov edx,[outpx] ; give Position of
substring.... ARG-3(output)
mov [edx],ecx ;
jmp @@XZ2 ;
;
========================
@@Laa:
mov esi,[strg1]; string input..............ARG-1(input)
mov [ebp-8], esi ;
mov [ebp-4], edi ;
@@LP0:
mov edi,[ebp-4] ;
mov ah,[byte ptr edi]; first char of substring in AH
@@LP0a:
lodsb ;
cmp al,ah ;
jz @@ok1
;
or al,al
;
jz @@XZ1
; if zero, fail at end of string
jmp @@LP0a ;
else repeat THIS loop
;
========================
@@ok1:
push esi ;
@@ok2:
inc edi ;
lodsb
;
cmp al,[byte ptr edi]
jz @@ok2
;
mov al,[byte ptr edi]
or al,al
;
jz @@ok3
;
pop esi
;
jmp @@LP0 ;
@@ok3:
mov
ebx,esi ;
pop esi
;
mov [ebp-8],esi ; store esi
mov [ebp-12],ebx ; store right_hand_string
after the substring
call _RUN_StackBTrack; stack a 'backtrack point' in Visual Prolog
mov esi,[ebp-8] ; recover ESI
or eax,eax ; is
the result (of StackBTrack) zero?
jne @@LP0
; if not, read more...
;
------------------------
@@ZZ:
mov eax,[ebp-12] ; return
right_hand_side string (after the char)
mov ecx,esi ;
mov ebx,[strg1] ; string
input.................. ARG-1(input)
sub ecx,ebx ;
mov edx,[outpx] ; give Position of
substring.... ARG-3(output)
mov [edx],ecx ;
call _RUN_JmpReturn1 ; call Visual Prolog function "_RUN_JmpReturn1"
mov esi,[ebp-8] ;
jmp @@LP0
; repeat big loop
;
========================
@@XZ1:
call _RUN_Fail ; FAIL
@@XZ2:
popx3
LEAVE
ENDP
_nd_search_1
PROC
_nd_search_2 near ; (BINARY,CHAR,UNSIGNED) -(i,i,o)
ENTER
16,0 ;
ARG
binary:dword,char1:byte,outpx:dword
pushx3
mov esi,[binary] ; binary input..............
ARG-1(input)
mov ecx,[dword ptr esi-4] ;
dec ecx ;
dec ecx ;
dec ecx ;
dec ecx ;
mov [ebp-8], esi ;
mov ah,[char1] ; char
..................... ARG-2(input)
mov [ebp-4], eax ;
mov [ebp-12],ecx ;
@@LP0:
mov eax,[ebp-4] ;
mov ecx,[ebp-12] ;
@@LP0a:
lodsb ;
cmp al,ah ;
jz @@ok1 ;
or al,al ;
jz @@XZ1 ; if
zero, fail at end of string
jmp @@LP0a ;
else repeat THIS loop
;
===============================
@@ok1:
mov [ebp-8],esi ; store it
mov [ebp-12],ecx ;
call _RUN_StackBTrack ; stack a 'backtrack point' in
Visual Prolog
mov esi,[ebp-8] ; recover ESI
or eax,eax ; is
the result (of StackBTrack) zero?
jne @@LP0 ; if
not, read more...
;
-------------------------------
mov eax,esi ;
return right_hand_side string (after the char)
mov ecx,eax ;
mov ebx,[binary] ; string
input.............. ARG-1(input)
sub ecx,ebx ;
dec ecx ;
binaries start at zero
mov edx,[outpx] ; give Position of
Char .... ARG-3(output)
mov [edx],ecx ;
call _RUN_JmpReturn1 ; call Visual Prolog function
"_RUN_JmpReturn1"
mov esi,[ebp-8] ;
jmp @@LP0 ;
repeat big loop
;
===============================
@@XZ1:
call _RUN_Fail ; FAIL
popx3
LEAVE
ENDP
_nd_search_2
PROC
_nd_search_3 near ;
(BINARY,STRING,POSITION) -(i,i,o)
ENTER
20,0 ;
ARG
strg1:dword,substr:dword,outpx:dword
pushx3
mov edi,[substr] ; substring................
ARG-2(input)
mov esi,[strg1] ; BINARY
input..............ARG-1(input)
mov [ebp-8], esi ;
mov [ebp-4], edi ;
mov ecx,[dword ptr esi-4] ;
dec ecx
dec ecx
dec ecx
mov [ebp-16],ecx ; length of binary
in local variable
@@LP0:
mov edi,[ebp-4] ;
mov ah,[byte ptr edi] ; first char of substring in AH
@@LP0a:
lodsb ;
cmp al,ah ;
jz @@ok1 ;
;or
al,al ;
;jz
@@XZ1 ; if zero, fail at end of
string
dec ecx ;
or ecx,ecx ;
jz @@XZ1 ;
jmp @@LP0a ;
else repeat THIS loop
;
===============================
@@ok1:
dec ecx ;
or ecx,ecx ;
jz @@XZ1 ;
mov [ebp-16],ecx ;
push esi ;
@@ok2:
inc edi ;
lodsb ;
cmp al,[byte ptr edi]
jz @@ok2 ;
mov al,[byte ptr edi]
or al,al ;
jz @@ok3 ;
pop esi ;
jmp @@LP0 ;
;
===============================
@@ok3:
mov ebx,esi
;
pop esi ;
mov [ebp-8],esi ; store esi
mov [ebp-12],ebx ; store
right_hand_string after the substring
mov [ebp-16],ecx ; remaining length
recovered
call _RUN_StackBTrack ; stack a 'backtrack point' in
Visual Prolog
mov ecx,[ebp-16] ; remaining length
recovered
mov esi,[ebp-8] ; recover ESI
or eax,eax ; is
the result (of StackBTrack) zero?
jne @@LP0 ; if
not, read more...
;
-------------------------------
@@ZZ:
mov eax,[ebp-12] ; return
right_hand_side string (after the char)
mov ecx,esi ;
mov ebx,[strg1] ; string
input.................. ARG-1(input)
sub ecx,ebx ;
mov edx,[outpx] ; give Position of
substring.... ARG-3(output)
dec ecx ;
binaries start at zero
mov [edx],ecx ;
call _RUN_JmpReturn1 ; call Visual Prolog function
"_RUN_JmpReturn1"
mov esi,[ebp-8] ;
mov ecx,[ebp-16] ; remaining length
recovered
jmp @@LP0 ;
repeat big loop
;
===============================
@@XZ1:
mov [ebp-16],ecx ;
call _RUN_Fail ; FAIL
@@XZ2:
popx3
LEAVE
ENDP
_nd_search_3
PROC
_nd_search_4 near ; (BINARY,BINARY,POSITION) -(i,i,o)
ENTER
24,0
ARG
binary:dword,subbin:dword,outpx:dword
pushx3
mov edi,[subbin] ; sub-binary...............
ARG-2(input)
mov ecx,[dword ptr edi-4] ; "true length" of sub-binary in ECX
dec ecx ;
dec ecx ;
dec ecx ;
dec ecx ; length
of sub_binary_array in ECX
dec ecx ; minus 1
mov [ebp-20],ecx ; store length of
sub-binary-1 in local variable
mov edx,ecx ;
copy it also to EDX
mov esi,[binary] ; binary
input..............ARG-1(input)
mov ecx,[dword ptr esi-4] ; "true length" of binary in ECX
dec ecx ;
dec ecx ;
dec ecx ;
dec ecx ; length
of binary_array in ECX
dec ecx ;
mov [ebp-8], esi ;
sub ecx,edx ;
subtrack sub_bin_length from binary length!
dec ecx
mov [ebp-16],ecx ; store length of
binary in local variable
mov [ebp-4], edi ;
@@LP0:
;;or
ecx,ecx ;
;;jz
@@XZ1 ;
mov edi,[ebp-4] ;
or ecx,ecx ;
jz @@XZ1 ;
mov ah,[byte ptr edi] ; first char of subbinary in AH
@@LP0a:
lodsb ;
cmp al,ah ;
jz @@ok1 ;
loop @@LP0a ;
jmp @@XZ1 ; if
exhausted, fail
;
===============================
@@ok1:
dec ecx ;
or ecx,ecx ;
jz @@XZ1 ;
push esi ;
push ecx ;
mov ecx,[ebp-20] ; length of
subbinary recovered from local var.
jmp @@ok2
;
@@ok2a:
dec ecx ;
jz @@ok3 ;
@@ok2:
inc edi ;
lodsb ;
cmp al,[byte ptr edi] ;
jz @@ok2a
;
pop ecx ;
pop esi ;
jmp @@LP0 ;
;
===============================
@@ok3:
mov ebx,esi
;
pop ecx ;
pop esi ;
or ecx,ecx ;
jz @@XZ1 ;
mov [ebp-8],esi ; store esi
mov [ebp-12],ebx ; store
right_hand_string after the substring
mov [ebp-16],ecx ; store length in
local variable
;or
ecx,ecx ;
;jz
@@XZ1 ;
call _RUN_StackBTrack ; stack a 'backtrack point' in
Visual Prolog
mov ecx,[ebp-16] ; store length in
local variable
mov esi,[ebp-8] ; recover ESI
or eax,eax ; is
the result (of StackBTrack) zero?
jne @@LP0 ; if
not, read more...
;
-------------------------------
mov eax,[ebp-12] ; return
right_hand_side string (after the sub-bin)
mov ecx,esi ;
mov ebx,[binary] ; binary input..................
ARG-1(input)
sub ecx,ebx ;
dec ecx ;
binaries start at zero
mov edx,[outpx] ; give Position of
substring.... ARG-3(output)
mov [edx],ecx ;
call _RUN_JmpReturn1 ; call Visual Prolog function
"_RUN_JmpReturn1"
mov esi,[ebp-8] ;
mov ecx,[ebp-16] ; recover length
from local variable
jmp @@LP0 ;
repeat big loop
;
===============================
@@XZ1:
call _RUN_Fail ; FAIL
popx3
LEAVE
ENDP
_nd_search_4
PROC
_nd_search_5 near ;
(STRING,CHAR,inpos,posx) -(i,i,i,o)
ENTER
12,0 ;
ARG
strg1:dword,char1:byte,inpos:dword,outpx:dword
pushx3
mov esi,[strg1] ; string
input.............. ARG-1(input)
mov eax,[inpos] ; initial
position.......... ARG-2(input)
dec eax ; minus
one, because Prolog strings start at 1
add esi,eax ;
add the position to the string pointer
mov [ebp-8], esi ;
mov ah,[char1] ; char
..................... ARG-3(input)
mov [ebp-4], eax ;
;
-------------------------------
@@LP0:
mov eax,[ebp-4] ;
@@LP0a:
lodsb ;
cmp al,ah ;
jz @@ok1 ;
or al,al ;
jz @@XZ1 ; if
zero, fail at end of string
jmp @@LP0a ;
else repeat THIS loop
;
===============================
@@ok1:
mov [ebp-8],esi ; store it
call _RUN_StackBTrack ; stack a 'backtrack point' in
Visual Prolog
mov esi,[ebp-8] ; recover ESI
or eax,eax ; is
the result (of StackBTrack) zero?
jne @@LP0 ; if
not, read more...
;
-------------------------------
mov eax,esi ;
return right_hand_side string (after the char)
mov ecx,eax ;
mov ebx,[strg1] ; string
input.............. ARG-1(input)
sub ecx,ebx ;
mov edx,[outpx] ; give Position of
Char .... ARG-3(output)
mov [edx],ecx ;
call _RUN_JmpReturn1 ; call Visual Prolog function
"_RUN_JmpReturn1"
mov esi,[ebp-8] ;
jmp @@LP0 ;
repeat big loop
;
===============================
@@XZ1:
call _RUN_Fail ; FAIL
popx3
LEAVE
ENDP
_nd_search_5
PROC
_nd_search_6 near ;
(STRING,STRING,INIPOS,POSITION) -(i,i,i,o)
ENTER
16,0 ;
ARG
strg1:dword,substr:dword,inpos:dword,outpx:dword
pushx3
mov esi,[strg1] ; string
input..............ARG-1 (input)
mov [ebp-8], esi ;
mov edi,[substr] ; substring................ ARG-2
(input)
mov eax,[inpos] ; initial
position......... ARG-3 (input)
dec eax ; minus
1, since Prolog strings start with 1
add esi,eax ;
add initial position to the string
mov [ebp-4], edi ;
@@LP0:
mov edi,[ebp-4] ;
mov ah,[byte ptr edi] ; first char of substring in AH
@@LP0a:
lodsb ;
cmp al,ah ;
jz @@ok1 ;
or al,al ;
jz @@XZ1 ; if
zero, fail at end of string
jmp @@LP0a ;
else repeat THIS loop
;
===============================
@@ok1:
push esi ;
@@ok2:
inc edi ;
lodsb ;
cmp al,[byte ptr edi] ;
jz @@ok2 ;
mov al,[byte ptr edi] ;
or al,al ;
jz @@ok3 ;
pop esi ;
jmp @@LP0 ;
@@ok3:
mov ebx,esi
;
pop esi ;
mov [ebp-8],esi ; store esi
mov [ebp-12],ebx ; store
right_hand_string after the substring
call _RUN_StackBTrack ; stack a 'backtrack point' in
Visual Prolog
mov esi,[ebp-8] ; recover ESI
or eax,eax ; is
the result (of StackBTrack) zero?
jne @@LP0 ; if
not, read more...
;
-------------------------------
mov eax,[ebp-12] ; return
right_hand_side string (after the char)
mov ecx,esi ;
mov ebx,[strg1] ; string
input.................. ARG-1(input)
sub ecx,ebx ;
mov edx,[outpx] ; give Position of
substring.... ARG-3(output)
mov [edx],ecx ;
call _RUN_JmpReturn1 ; call Visual Prolog function
"_RUN_JmpReturn1"
mov esi,[ebp-8] ;
jmp @@LP0 ;
repeat big loop
;
===============================
@@XZ1:
call _RUN_Fail ; FAIL
popx3
LEAVE
ENDP
_nd_search_6
PROC
_nd_search_7 near ;
(BINARY,CHAR,inpos,posx) -(i,i,i,o)
ENTER
16,0 ;
ARG
binary:dword,char1:byte,inpos:dword,outpx:dword
pushx3
mov esi,[binary] ; binary input..............
ARG-1(input)
mov ecx,[dword ptr esi-4] ;
dec ecx ;
dec ecx ;
dec ecx ;
dec ecx ;
mov eax,[inpos] ; initial
position.......... ARG-2(input)
add esi,eax ;
add initial position to binary pointer
sub ecx,eax ;
subtract init_pos from binary length
mov [ebp-8], esi ;
mov ah,[char1] ; char
..................... ARG-3(input)
mov [ebp-4], eax ;
mov [ebp-12],ecx ;
@@LP0:
mov eax,[ebp-4] ;
mov ecx,[ebp-12] ;
@@LP0a:
lodsb ;
cmp al,ah ;
jz @@ok1 ;
or al,al ;
jz @@XZ1 ; if
zero, fail at end of string
jmp @@LP0a ;
else repeat THIS loop
;
===============================
@@ok1:
mov [ebp-8],esi ; store it
mov [ebp-12],ecx ;
call _RUN_StackBTrack ; stack a 'backtrack point' in
Visual Prolog
mov esi,[ebp-8] ; recover ESI
or eax,eax ; is
the result (of StackBTrack) zero?
jne @@LP0 ; if
not, read more...
;
-------------------------------
mov eax,esi ;
return right_hand_side string (after the char)
mov ecx,eax ;
mov ebx,[strg1] ; string
input.............. ARG-1(input)
sub ecx,ebx ;
dec ecx ;
binaries start at zero
mov edx,[outpx] ; give Position of
Char .... ARG-3(output)
mov [edx],ecx ;
call _RUN_JmpReturn1 ; call Visual Prolog function
"_RUN_JmpReturn1"
mov esi,[ebp-8] ;
jmp @@LP0 ;
repeat big loop
;
===============================
@@XZ1:
call _RUN_Fail ; FAIL
popx3
LEAVE
ENDP
_nd_search_7
PROC
_nd_search_8 near ;
(BINARY,STRING,INIPOS,POSITION) -(i,i,i,o)
ENTER
20,0 ;
ARG
binary:dword,substr:dword,inpos:dword,outpx:dword
pushx3
mov esi,[binary] ; binary input..............ARG-1
(input)
mov ecx,[dword ptr esi-4] ;
dec ecx ;
dec ecx ;
dec ecx ;
dec ecx ; ecx is
now length of binary
mov [ebp-8], esi ;
mov edi,[substr] ; substring................ ARG-2
(input)
mov eax,[inpos] ; initial
position......... ARG-3 (input)
add esi,eax ;
add initial position to the string
sub ecx,eax ;
subtract it from the length
mov [ebp-4], edi ;
mov [ebp-16],ecx ; store the length
as a local variable
@@LP0:
mov edi,[ebp-4] ;
mov ecx,[ebp-16] ; restore the
length from local variable
mov ah,[byte ptr edi] ; first char of substring in AH
@@LP0a:
lodsb ;
cmp al,ah ;
jz @@ok1 ;
dec ecx ;
jz @@XZ1 ; if at
the end, fail
jmp @@LP0a ;
else repeat THIS loop
;
===============================
@@ok1:
push esi ;