Apply %restore_fcommon macro for Address Sanitizer
[platform/upstream/nettle.git] / arm / neon / chacha-core-internal.asm
1 C arm/neon/chacha-core-internal.asm
2
3 ifelse(<
4    Copyright (C) 2013, 2015 Niels Möller
5
6    This file is part of GNU Nettle.
7
8    GNU Nettle is free software: you can redistribute it and/or
9    modify it under the terms of either:
10
11      * the GNU Lesser General Public License as published by the Free
12        Software Foundation; either version 3 of the License, or (at your
13        option) any later version.
14
15    or
16
17      * the GNU General Public License as published by the Free
18        Software Foundation; either version 2 of the License, or (at your
19        option) any later version.
20
21    or both in parallel, as here.
22
23    GNU Nettle is distributed in the hope that it will be useful,
24    but WITHOUT ANY WARRANTY; without even the implied warranty of
25    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
26    General Public License for more details.
27
28    You should have received copies of the GNU General Public License and
29    the GNU Lesser General Public License along with this program.  If
30    not, see http://www.gnu.org/licenses/.
31 >)
32
33         .file "chacha-core-internal.asm"
34         .fpu    neon
35
36 define(<DST>, <r0>)
37 define(<SRC>, <r1>)
38 define(<ROUNDS>, <r2>)
39
40 define(<X0>, <q0>)
41 define(<X1>, <q1>)
42 define(<X2>, <q2>)
43 define(<X3>, <q3>)
44 define(<T0>, <q8>)
45 define(<S0>, <q12>)
46 define(<S1>, <q13>)
47 define(<S2>, <q14>)
48 define(<S3>, <q15>)
49
50 define(<QROUND>, <
51         C x0 += x1, x3 ^= x0, x3 lrot 16
52         C x2 += x3, x1 ^= x2, x1 lrot 12
53         C x0 += x1, x3 ^= x0, x3 lrot 8
54         C x2 += x3, x1 ^= x2, x1 lrot 7
55
56         vadd.i32        $1, $1, $2
57         veor            $4, $4, $1
58         vshl.i32        T0, $4, #16
59         vshr.u32        $4, $4, #16
60         veor            $4, $4, T0
61
62         vadd.i32        $3, $3, $4
63         veor            $2, $2, $3
64         vshl.i32        T0, $2, #12
65         vshr.u32        $2, $2, #20
66         veor            $2, $2, T0
67
68         vadd.i32        $1, $1, $2
69         veor            $4, $4, $1
70         vshl.i32        T0, $4, #8
71         vshr.u32        $4, $4, #24
72         veor            $4, $4, T0
73
74         vadd.i32        $3, $3, $4
75         veor            $2, $2, $3
76         vshl.i32        T0, $2, #7
77         vshr.u32        $2, $2, #25
78         veor            $2, $2, T0
79 >)
80
81         .text
82         .align 4
83         C _chacha_core(uint32_t *dst, const uint32_t *src, unsigned rounds)
84
85 PROLOGUE(_nettle_chacha_core)
86         vldm    SRC, {X0,X1,X2,X3}
87
88         vmov    S0, X0
89         vmov    S1, X1
90         vmov    S2, X2
91         vmov    S3, X3
92
93         C Input rows:
94         C        0  1  2  3     X0
95         C        4  5  6  7     X1
96         C        8  9 10 11     X2
97         C       12 13 14 15     X3
98
99 .Loop:
100         QROUND(X0, X1, X2, X3)
101
102         C Rotate rows, to get
103         C        0  1  2  3
104         C        5  6  7  4  >>> 3
105         C       10 11  8  9  >>> 2
106         C       15 12 13 14  >>> 1
107         vext.32 X1, X1, X1, #1
108         vext.32 X2, X2, X2, #2
109         vext.32 X3, X3, X3, #3
110
111         QROUND(X0, X1, X2, X3)
112
113         subs    ROUNDS, ROUNDS, #2
114         C Inverse rotation
115         vext.32 X1, X1, X1, #3
116         vext.32 X2, X2, X2, #2
117         vext.32 X3, X3, X3, #1
118
119         bhi     .Loop
120
121         vadd.u32        X0, X0, S0
122         vadd.u32        X1, X1, S1
123         vadd.u32        X2, X2, S2
124         vadd.u32        X3, X3, S3
125
126         vstm    DST, {X0,X1,X2,X3}
127         bx      lr
128 EPILOGUE(_nettle_chacha_core)
129
130 divert(-1)
131 define chachastate
132 p/x $q0.u32
133 p/x $q1.u32
134 p/x $q2.u32
135 p/x $q3.u32
136 end