home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
The C Users' Group Library 1994 August
/
wc-cdrom-cusersgrouplibrary-1994-08.iso
/
listings
/
v_06_03
/
v6n3039a.txt
< prev
next >
Wrap
Text File
|
1989-09-28
|
4KB
|
175 lines
;
; David D. Clark
;
; 9 May 1987
; 11 December 1987 -- changes for DLC 3.12 (save DI and SI registers)
;
Include macros.asm
begcode
;
; memmove -- move a block of data len bytes long from src to dest.
; The function determines whether the move should be done from
; the left or right end of the blocks. After deciding, a jump is
; made into either moveleft() or moveright(), as appropriate, to
; actually perform word optimized moves. A pointer to dest is
; returned.
;
; The Datalight C declaration would look like:
;
; void *memmove(dest, src, len)
; void *dest, *src;
; unsigned int len;
;
Public memmove
func memmove
PUSH BP ; save old frame pointer
MOV BP,SP ; set new frame pointer
PUSH DI ; NEW with DLC 3.12
PUSH SI ; " "
MOV CX,P+SIZEPTR+SIZEPTR[BP] ; len
If SPTR
MOV DI,P+[BP] ; ES:DI = dest
MOV SI,P+SIZEPTR[BP]; DS:SI = src
MOV AX,DI ; original dest is returned
ELSE
LES DI,P+[BP] ; ES:DI = dest
PUSH DS ; save data segment
LDS SI,P+SIZEPTR[BP]; DS:SI = src
MOV AX,ES
MOV BX,DI ; AX:BX = original value of dest
ENDIF
CMP SI,DI ; is src above dest?
JAE ml1 ; move from left
JMP Short mr1 ; move from right
memmove EndP
;
; moveleft -- move a block of data len bytes long from src to dest
; starting at the left end. The move is optimized to word moves
; and a (possible) single byte move. A pointer to dest is returned.
;
; The Datalight C declaration would look like:
;
; void *moveleft(dest, src, len)
; void *dest, *src;
; unsigned int len;
;
Public moveleft
func moveleft
PUSH BP ; save old frame pointer
MOV BP,SP ; set new frame pointer
PUSH DI ; NEW with DLC 3.12
PUSH SI ; " "
MOV CX,P+SIZEPTR+SIZEPTR[BP] ; len
If SPTR
MOV DI,P+[BP] ; ES:DI = dest
MOV SI,P+SIZEPTR[BP]; DS:SI = src
MOV AX,DI ; original dest is returned
ELSE
LES DI,P+[BP] ; ES:DI = dest
PUSH DS ; save data segment
LDS SI,P+SIZEPTR[BP]; DS:SI = src
MOV AX,ES
MOV BX,DI ; AX:BX = original value of dest
ENDIF
ml1: ; alternate entry point
CLD ; set direction forward (needed?)
SHR CX,1 ; convert bytes to words
JZ mlb ; jump if no full words to move
REP MOVSW ; move the words
mlb: JNC mldone ; no bytes to move
MOVSB ; move the left over byte
mldone:
If LPTR
POP DS ; recover DS
ENDIF
POP SI ; NEW with DLC 3.12
POP DI ; " "
POP BP ; restore old frame pointer
RET
moveleft EndP
;
; moveright -- move a block of data len bytes long from src to dest
; starting at the right end. The move is optimized to word moves
; and a (possible) single byte move. A pointer to dest is returned.
;
; The Datalight C declaration would look like:
;
; void *moveright(dest, src, len)
; void *dest. *src;
; unsigned int len;
;
Public moveright
func moveright
PUSH BP ; save old frame pointer
MOV BP,SP ; set new frame pointer
PUSH DI ; NEW with DLC 3.12
PUSH SI ; " "
MOV CX,P+SIZEPTR+SIZEPTR[BP] ; len
If SPTR
MOV DI,P+[BP] ; ES:DI = dest
MOV SI,P+SIZEPTR[BP]; DS:SI = src
MOV AX,DI ; original dest is returned
ELSE
LES DI,P+[BP] ; ES:DI = dest
PUSH DS ; save data segment
LDS SI,P+SIZEPTR[BP]; DS:SI = src
MOV AX,ES
MOV BX,DI ; AX:BX = original value of dest
ENDIF
mr1: ; alternate entry point
ADD SI,CX ; start at high (right) end
DEC SI ; last source byte
DEC SI ; last source word
ADD DI,CX ; start at high (right) end
DEC DI ; last target byte
DEC DI ; last target word
STD ; set direction backward
SHR CX,1 ; convert bytes to words
JZ mrb ; jump if no full words to move
REP MOVSW ; move the words
mrb: JNC mrdone ; no bytes to move
INC SI ; point to source byte
INC DI ; point to target byte
MOVSB ; move the left over byte
mrdone: CLD ; reset direction flag before exit
If LPTR
POP DS ; recover DS
ENDIF
POP SI ; NEW with DLC 3.12
POP DI ; " "
POP BP ; restore old frame pointer
RET
moveright EndP
endcode
End