]> git.sur5r.net Git - cc65/blob - libsrc/pce/memset.s
Added a version of memset() that uses the HuC6280's TII instruction to get more speed.
[cc65] / libsrc / pce / memset.s
1 ;
2 ; This file, instead of "common/memset.s", will be assembled for the pce
3 ; target.  This version is smaller and faster because it uses a HuC6280
4 ; block-copy instruction.
5 ;
6 ; 1998-05-29, Ullrich von Bassewitz
7 ; 2015-11-06, Greg King
8 ;
9 ; void* __fastcall__ _bzero (void* ptr, size_t n);
10 ; void  __fastcall__  bzero (void* ptr, size_t n);
11 ; void* __fastcall__ memset (void* ptr, int c, size_t n);
12 ;
13 ; NOTE: bzero() will return its first argument, as memset() does.  It is no
14 ;       problem to declare the return value as void, because it can be ignored.
15 ;       _bzero() (note the leading underscore) is declared with the proper
16 ;       return type because the compiler will replace memset() by _bzero() if
17 ;       the fill value is zero; and, the optimizer looks at the return type
18 ;       to see if the value in .XA is of any use.
19 ;
20 ; NOTE: This function uses entry points from "pce/memcpy.s"!
21 ;
22
23         .export         __bzero, _bzero, _memset
24
25         .import         memcpy_getparams, memcpy_increment
26         .import         pushax, popax
27         .importzp       ptr1, ptr2, ptr3
28
29         .macpack        longbranch
30
31
32 ; ----------------------------------------------------------------------
33 __bzero:
34 _bzero: pha
35         cla                             ; fill with zeros
36         jsr     pushax                  ; (high byte isn't important)
37         pla
38
39 _memset:
40         jsr     memcpy_getparams
41
42 ; The fill byte is put at the beginning of the buffer; then, the buffer is
43 ; copied to a second buffer that starts one byte above the start of the first
44 ; buffer.  Normally, we would use memmove() to avoid trouble; but here, we
45 ; exploit that overlap, by using memcpy().  Therefore, the fill value is copied
46 ; from each byte to the next byte, all the way to the end of the buffer.
47
48         lda     ptr1                    ; get fill value
49         sta     (ptr2)
50
51         lda     ptr3                    ; count first byte
52         bne     @L3
53         dec     ptr3+1
54 @L3:    dec     a
55         sta     ptr3
56         ora     ptr3+1
57         jeq     popax                   ; return ptr. if no more bytes
58
59         lda     ptr2                    ; point to first buffer
60         ldx     ptr2+1
61         sta     ptr1
62         stx     ptr1+1
63         inc     ptr2                    ; point to second buffer
64         bne     @L2
65         inc     ptr2+1
66
67 @L2:    jmp     memcpy_increment