Merge git://git.kernel.org/pub/scm/linux/kernel/git/davem/ide-2.6
[pandora-kernel.git] / arch / blackfin / lib / memset.S
1 /*
2  * Copyright 2004-2009 Analog Devices Inc.
3  *
4  * Licensed under the ADI BSD license or the GPL-2 (or later)
5  */
6
7 #include <linux/linkage.h>
8
9 .align 2
10
11 #ifdef CONFIG_MEMSET_L1
12 .section .l1.text
13 #else
14 .text
15 #endif
16
17 /*
18  * C Library function MEMSET
19  * R0 = address (leave unchanged to form result)
20  * R1 = filler byte
21  * R2 = count
22  * Favours word aligned data.
23  * The strncpy assumes that I0 and I1 are not used in this function
24  */
25
26 ENTRY(_memset)
27         P0 = R0 ;              /* P0 = address */
28         P2 = R2 ;              /* P2 = count   */
29         R3 = R0 + R2;          /* end          */
30         CC = R2 <= 7(IU);
31         IF CC JUMP  .Ltoo_small;
32         R1 = R1.B (Z);         /* R1 = fill char */
33         R2 =  3;
34         R2 = R0 & R2;          /* addr bottom two bits */
35         CC =  R2 == 0;             /* AZ set if zero.   */
36         IF !CC JUMP  .Lforce_align ;  /* Jump if addr not aligned. */
37
38 .Laligned:
39         P1 = P2 >> 2;          /* count = n/4        */
40         R2 = R1 <<  8;         /* create quad filler */
41         R2.L = R2.L + R1.L(NS);
42         R2.H = R2.L + R1.H(NS);
43         P2 = R3;
44
45         LSETUP (.Lquad_loop , .Lquad_loop) LC0=P1;
46 .Lquad_loop:
47         [P0++] = R2;
48
49         CC = P0 == P2;
50         IF !CC JUMP .Lbytes_left;
51         RTS;
52
53 .Lbytes_left:
54         R2 = R3;                /* end point */
55         R3 = P0;                /* current position */
56         R2 = R2 - R3;           /* bytes left */
57         P2 = R2;
58
59 .Ltoo_small:
60         CC = P2 == 0;           /* Check zero count */
61         IF CC JUMP .Lfinished;    /* Unusual */
62
63 .Lbytes:
64         LSETUP (.Lbyte_loop , .Lbyte_loop) LC0=P2;
65 .Lbyte_loop:
66         B[P0++] = R1;
67
68 .Lfinished:
69         RTS;
70
71 .Lforce_align:
72         CC = BITTST (R0, 0);  /* odd byte */
73         R0 = 4;
74         R0 = R0 - R2;
75         P1 = R0;
76         R0 = P0;                    /* Recover return address */
77         IF !CC JUMP .Lskip1;
78         B[P0++] = R1;
79 .Lskip1:
80         CC = R2 <= 2;          /* 2 bytes */
81         P2 -= P1;              /* reduce count */
82         IF !CC JUMP .Laligned;
83         B[P0++] = R1;
84         B[P0++] = R1;
85         JUMP .Laligned;
86
87 ENDPROC(_memset)