]> Git Repo - qemu.git/blob - target-arm/crypto_helper.c
target-arm: A64: Use PMULL feature bit for PMULL
[qemu.git] / target-arm / crypto_helper.c
1 /*
2  * crypto_helper.c - emulate v8 Crypto Extensions instructions
3  *
4  * Copyright (C) 2013 - 2014 Linaro Ltd <[email protected]>
5  *
6  * This library is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2 of the License, or (at your option) any later version.
10  */
11
12 #include <stdlib.h>
13
14 #include "cpu.h"
15 #include "exec/exec-all.h"
16 #include "exec/helper-proto.h"
17
18 union CRYPTO_STATE {
19     uint8_t    bytes[16];
20     uint32_t   words[4];
21     uint64_t   l[2];
22 };
23
24 void HELPER(crypto_aese)(CPUARMState *env, uint32_t rd, uint32_t rm,
25                          uint32_t decrypt)
26 {
27     static uint8_t const sbox[][256] = { {
28         /* S-box for encryption */
29         0x63, 0x7c, 0x77, 0x7b, 0xf2, 0x6b, 0x6f, 0xc5,
30         0x30, 0x01, 0x67, 0x2b, 0xfe, 0xd7, 0xab, 0x76,
31         0xca, 0x82, 0xc9, 0x7d, 0xfa, 0x59, 0x47, 0xf0,
32         0xad, 0xd4, 0xa2, 0xaf, 0x9c, 0xa4, 0x72, 0xc0,
33         0xb7, 0xfd, 0x93, 0x26, 0x36, 0x3f, 0xf7, 0xcc,
34         0x34, 0xa5, 0xe5, 0xf1, 0x71, 0xd8, 0x31, 0x15,
35         0x04, 0xc7, 0x23, 0xc3, 0x18, 0x96, 0x05, 0x9a,
36         0x07, 0x12, 0x80, 0xe2, 0xeb, 0x27, 0xb2, 0x75,
37         0x09, 0x83, 0x2c, 0x1a, 0x1b, 0x6e, 0x5a, 0xa0,
38         0x52, 0x3b, 0xd6, 0xb3, 0x29, 0xe3, 0x2f, 0x84,
39         0x53, 0xd1, 0x00, 0xed, 0x20, 0xfc, 0xb1, 0x5b,
40         0x6a, 0xcb, 0xbe, 0x39, 0x4a, 0x4c, 0x58, 0xcf,
41         0xd0, 0xef, 0xaa, 0xfb, 0x43, 0x4d, 0x33, 0x85,
42         0x45, 0xf9, 0x02, 0x7f, 0x50, 0x3c, 0x9f, 0xa8,
43         0x51, 0xa3, 0x40, 0x8f, 0x92, 0x9d, 0x38, 0xf5,
44         0xbc, 0xb6, 0xda, 0x21, 0x10, 0xff, 0xf3, 0xd2,
45         0xcd, 0x0c, 0x13, 0xec, 0x5f, 0x97, 0x44, 0x17,
46         0xc4, 0xa7, 0x7e, 0x3d, 0x64, 0x5d, 0x19, 0x73,
47         0x60, 0x81, 0x4f, 0xdc, 0x22, 0x2a, 0x90, 0x88,
48         0x46, 0xee, 0xb8, 0x14, 0xde, 0x5e, 0x0b, 0xdb,
49         0xe0, 0x32, 0x3a, 0x0a, 0x49, 0x06, 0x24, 0x5c,
50         0xc2, 0xd3, 0xac, 0x62, 0x91, 0x95, 0xe4, 0x79,
51         0xe7, 0xc8, 0x37, 0x6d, 0x8d, 0xd5, 0x4e, 0xa9,
52         0x6c, 0x56, 0xf4, 0xea, 0x65, 0x7a, 0xae, 0x08,
53         0xba, 0x78, 0x25, 0x2e, 0x1c, 0xa6, 0xb4, 0xc6,
54         0xe8, 0xdd, 0x74, 0x1f, 0x4b, 0xbd, 0x8b, 0x8a,
55         0x70, 0x3e, 0xb5, 0x66, 0x48, 0x03, 0xf6, 0x0e,
56         0x61, 0x35, 0x57, 0xb9, 0x86, 0xc1, 0x1d, 0x9e,
57         0xe1, 0xf8, 0x98, 0x11, 0x69, 0xd9, 0x8e, 0x94,
58         0x9b, 0x1e, 0x87, 0xe9, 0xce, 0x55, 0x28, 0xdf,
59         0x8c, 0xa1, 0x89, 0x0d, 0xbf, 0xe6, 0x42, 0x68,
60         0x41, 0x99, 0x2d, 0x0f, 0xb0, 0x54, 0xbb, 0x16
61     }, {
62         /* S-box for decryption */
63         0x52, 0x09, 0x6a, 0xd5, 0x30, 0x36, 0xa5, 0x38,
64         0xbf, 0x40, 0xa3, 0x9e, 0x81, 0xf3, 0xd7, 0xfb,
65         0x7c, 0xe3, 0x39, 0x82, 0x9b, 0x2f, 0xff, 0x87,
66         0x34, 0x8e, 0x43, 0x44, 0xc4, 0xde, 0xe9, 0xcb,
67         0x54, 0x7b, 0x94, 0x32, 0xa6, 0xc2, 0x23, 0x3d,
68         0xee, 0x4c, 0x95, 0x0b, 0x42, 0xfa, 0xc3, 0x4e,
69         0x08, 0x2e, 0xa1, 0x66, 0x28, 0xd9, 0x24, 0xb2,
70         0x76, 0x5b, 0xa2, 0x49, 0x6d, 0x8b, 0xd1, 0x25,
71         0x72, 0xf8, 0xf6, 0x64, 0x86, 0x68, 0x98, 0x16,
72         0xd4, 0xa4, 0x5c, 0xcc, 0x5d, 0x65, 0xb6, 0x92,
73         0x6c, 0x70, 0x48, 0x50, 0xfd, 0xed, 0xb9, 0xda,
74         0x5e, 0x15, 0x46, 0x57, 0xa7, 0x8d, 0x9d, 0x84,
75         0x90, 0xd8, 0xab, 0x00, 0x8c, 0xbc, 0xd3, 0x0a,
76         0xf7, 0xe4, 0x58, 0x05, 0xb8, 0xb3, 0x45, 0x06,
77         0xd0, 0x2c, 0x1e, 0x8f, 0xca, 0x3f, 0x0f, 0x02,
78         0xc1, 0xaf, 0xbd, 0x03, 0x01, 0x13, 0x8a, 0x6b,
79         0x3a, 0x91, 0x11, 0x41, 0x4f, 0x67, 0xdc, 0xea,
80         0x97, 0xf2, 0xcf, 0xce, 0xf0, 0xb4, 0xe6, 0x73,
81         0x96, 0xac, 0x74, 0x22, 0xe7, 0xad, 0x35, 0x85,
82         0xe2, 0xf9, 0x37, 0xe8, 0x1c, 0x75, 0xdf, 0x6e,
83         0x47, 0xf1, 0x1a, 0x71, 0x1d, 0x29, 0xc5, 0x89,
84         0x6f, 0xb7, 0x62, 0x0e, 0xaa, 0x18, 0xbe, 0x1b,
85         0xfc, 0x56, 0x3e, 0x4b, 0xc6, 0xd2, 0x79, 0x20,
86         0x9a, 0xdb, 0xc0, 0xfe, 0x78, 0xcd, 0x5a, 0xf4,
87         0x1f, 0xdd, 0xa8, 0x33, 0x88, 0x07, 0xc7, 0x31,
88         0xb1, 0x12, 0x10, 0x59, 0x27, 0x80, 0xec, 0x5f,
89         0x60, 0x51, 0x7f, 0xa9, 0x19, 0xb5, 0x4a, 0x0d,
90         0x2d, 0xe5, 0x7a, 0x9f, 0x93, 0xc9, 0x9c, 0xef,
91         0xa0, 0xe0, 0x3b, 0x4d, 0xae, 0x2a, 0xf5, 0xb0,
92         0xc8, 0xeb, 0xbb, 0x3c, 0x83, 0x53, 0x99, 0x61,
93         0x17, 0x2b, 0x04, 0x7e, 0xba, 0x77, 0xd6, 0x26,
94         0xe1, 0x69, 0x14, 0x63, 0x55, 0x21, 0x0c, 0x7d
95     } };
96     static uint8_t const shift[][16] = {
97         /* ShiftRows permutation vector for encryption */
98         { 0,  5, 10, 15, 4, 9, 14,  3, 8, 13, 2,  7, 12, 1, 6, 11 },
99         /* ShiftRows permutation vector for decryption */
100         { 0, 13, 10,  7, 4, 1, 14, 11, 8,  5, 2, 15, 12, 9, 6,  3 },
101     };
102     union CRYPTO_STATE rk = { .l = {
103         float64_val(env->vfp.regs[rm]),
104         float64_val(env->vfp.regs[rm + 1])
105     } };
106     union CRYPTO_STATE st = { .l = {
107         float64_val(env->vfp.regs[rd]),
108         float64_val(env->vfp.regs[rd + 1])
109     } };
110     int i;
111
112     assert(decrypt < 2);
113
114     /* xor state vector with round key */
115     rk.l[0] ^= st.l[0];
116     rk.l[1] ^= st.l[1];
117
118     /* combine ShiftRows operation and sbox substitution */
119     for (i = 0; i < 16; i++) {
120         st.bytes[i] = sbox[decrypt][rk.bytes[shift[decrypt][i]]];
121     }
122
123     env->vfp.regs[rd] = make_float64(st.l[0]);
124     env->vfp.regs[rd + 1] = make_float64(st.l[1]);
125 }
126
127 void HELPER(crypto_aesmc)(CPUARMState *env, uint32_t rd, uint32_t rm,
128                           uint32_t decrypt)
129 {
130     static uint32_t const mc[][256] = { {
131         /* MixColumns lookup table */
132         0x00000000, 0x03010102, 0x06020204, 0x05030306,
133         0x0c040408, 0x0f05050a, 0x0a06060c, 0x0907070e,
134         0x18080810, 0x1b090912, 0x1e0a0a14, 0x1d0b0b16,
135         0x140c0c18, 0x170d0d1a, 0x120e0e1c, 0x110f0f1e,
136         0x30101020, 0x33111122, 0x36121224, 0x35131326,
137         0x3c141428, 0x3f15152a, 0x3a16162c, 0x3917172e,
138         0x28181830, 0x2b191932, 0x2e1a1a34, 0x2d1b1b36,
139         0x241c1c38, 0x271d1d3a, 0x221e1e3c, 0x211f1f3e,
140         0x60202040, 0x63212142, 0x66222244, 0x65232346,
141         0x6c242448, 0x6f25254a, 0x6a26264c, 0x6927274e,
142         0x78282850, 0x7b292952, 0x7e2a2a54, 0x7d2b2b56,
143         0x742c2c58, 0x772d2d5a, 0x722e2e5c, 0x712f2f5e,
144         0x50303060, 0x53313162, 0x56323264, 0x55333366,
145         0x5c343468, 0x5f35356a, 0x5a36366c, 0x5937376e,
146         0x48383870, 0x4b393972, 0x4e3a3a74, 0x4d3b3b76,
147         0x443c3c78, 0x473d3d7a, 0x423e3e7c, 0x413f3f7e,
148         0xc0404080, 0xc3414182, 0xc6424284, 0xc5434386,
149         0xcc444488, 0xcf45458a, 0xca46468c, 0xc947478e,
150         0xd8484890, 0xdb494992, 0xde4a4a94, 0xdd4b4b96,
151         0xd44c4c98, 0xd74d4d9a, 0xd24e4e9c, 0xd14f4f9e,
152         0xf05050a0, 0xf35151a2, 0xf65252a4, 0xf55353a6,
153         0xfc5454a8, 0xff5555aa, 0xfa5656ac, 0xf95757ae,
154         0xe85858b0, 0xeb5959b2, 0xee5a5ab4, 0xed5b5bb6,
155         0xe45c5cb8, 0xe75d5dba, 0xe25e5ebc, 0xe15f5fbe,
156         0xa06060c0, 0xa36161c2, 0xa66262c4, 0xa56363c6,
157         0xac6464c8, 0xaf6565ca, 0xaa6666cc, 0xa96767ce,
158         0xb86868d0, 0xbb6969d2, 0xbe6a6ad4, 0xbd6b6bd6,
159         0xb46c6cd8, 0xb76d6dda, 0xb26e6edc, 0xb16f6fde,
160         0x907070e0, 0x937171e2, 0x967272e4, 0x957373e6,
161         0x9c7474e8, 0x9f7575ea, 0x9a7676ec, 0x997777ee,
162         0x887878f0, 0x8b7979f2, 0x8e7a7af4, 0x8d7b7bf6,
163         0x847c7cf8, 0x877d7dfa, 0x827e7efc, 0x817f7ffe,
164         0x9b80801b, 0x98818119, 0x9d82821f, 0x9e83831d,
165         0x97848413, 0x94858511, 0x91868617, 0x92878715,
166         0x8388880b, 0x80898909, 0x858a8a0f, 0x868b8b0d,
167         0x8f8c8c03, 0x8c8d8d01, 0x898e8e07, 0x8a8f8f05,
168         0xab90903b, 0xa8919139, 0xad92923f, 0xae93933d,
169         0xa7949433, 0xa4959531, 0xa1969637, 0xa2979735,
170         0xb398982b, 0xb0999929, 0xb59a9a2f, 0xb69b9b2d,
171         0xbf9c9c23, 0xbc9d9d21, 0xb99e9e27, 0xba9f9f25,
172         0xfba0a05b, 0xf8a1a159, 0xfda2a25f, 0xfea3a35d,
173         0xf7a4a453, 0xf4a5a551, 0xf1a6a657, 0xf2a7a755,
174         0xe3a8a84b, 0xe0a9a949, 0xe5aaaa4f, 0xe6abab4d,
175         0xefacac43, 0xecadad41, 0xe9aeae47, 0xeaafaf45,
176         0xcbb0b07b, 0xc8b1b179, 0xcdb2b27f, 0xceb3b37d,
177         0xc7b4b473, 0xc4b5b571, 0xc1b6b677, 0xc2b7b775,
178         0xd3b8b86b, 0xd0b9b969, 0xd5baba6f, 0xd6bbbb6d,
179         0xdfbcbc63, 0xdcbdbd61, 0xd9bebe67, 0xdabfbf65,
180         0x5bc0c09b, 0x58c1c199, 0x5dc2c29f, 0x5ec3c39d,
181         0x57c4c493, 0x54c5c591, 0x51c6c697, 0x52c7c795,
182         0x43c8c88b, 0x40c9c989, 0x45caca8f, 0x46cbcb8d,
183         0x4fcccc83, 0x4ccdcd81, 0x49cece87, 0x4acfcf85,
184         0x6bd0d0bb, 0x68d1d1b9, 0x6dd2d2bf, 0x6ed3d3bd,
185         0x67d4d4b3, 0x64d5d5b1, 0x61d6d6b7, 0x62d7d7b5,
186         0x73d8d8ab, 0x70d9d9a9, 0x75dadaaf, 0x76dbdbad,
187         0x7fdcdca3, 0x7cdddda1, 0x79dedea7, 0x7adfdfa5,
188         0x3be0e0db, 0x38e1e1d9, 0x3de2e2df, 0x3ee3e3dd,
189         0x37e4e4d3, 0x34e5e5d1, 0x31e6e6d7, 0x32e7e7d5,
190         0x23e8e8cb, 0x20e9e9c9, 0x25eaeacf, 0x26ebebcd,
191         0x2fececc3, 0x2cededc1, 0x29eeeec7, 0x2aefefc5,
192         0x0bf0f0fb, 0x08f1f1f9, 0x0df2f2ff, 0x0ef3f3fd,
193         0x07f4f4f3, 0x04f5f5f1, 0x01f6f6f7, 0x02f7f7f5,
194         0x13f8f8eb, 0x10f9f9e9, 0x15fafaef, 0x16fbfbed,
195         0x1ffcfce3, 0x1cfdfde1, 0x19fefee7, 0x1affffe5,
196     }, {
197         /* Inverse MixColumns lookup table */
198         0x00000000, 0x0b0d090e, 0x161a121c, 0x1d171b12,
199         0x2c342438, 0x27392d36, 0x3a2e3624, 0x31233f2a,
200         0x58684870, 0x5365417e, 0x4e725a6c, 0x457f5362,
201         0x745c6c48, 0x7f516546, 0x62467e54, 0x694b775a,
202         0xb0d090e0, 0xbbdd99ee, 0xa6ca82fc, 0xadc78bf2,
203         0x9ce4b4d8, 0x97e9bdd6, 0x8afea6c4, 0x81f3afca,
204         0xe8b8d890, 0xe3b5d19e, 0xfea2ca8c, 0xf5afc382,
205         0xc48cfca8, 0xcf81f5a6, 0xd296eeb4, 0xd99be7ba,
206         0x7bbb3bdb, 0x70b632d5, 0x6da129c7, 0x66ac20c9,
207         0x578f1fe3, 0x5c8216ed, 0x41950dff, 0x4a9804f1,
208         0x23d373ab, 0x28de7aa5, 0x35c961b7, 0x3ec468b9,
209         0x0fe75793, 0x04ea5e9d, 0x19fd458f, 0x12f04c81,
210         0xcb6bab3b, 0xc066a235, 0xdd71b927, 0xd67cb029,
211         0xe75f8f03, 0xec52860d, 0xf1459d1f, 0xfa489411,
212         0x9303e34b, 0x980eea45, 0x8519f157, 0x8e14f859,
213         0xbf37c773, 0xb43ace7d, 0xa92dd56f, 0xa220dc61,
214         0xf66d76ad, 0xfd607fa3, 0xe07764b1, 0xeb7a6dbf,
215         0xda595295, 0xd1545b9b, 0xcc434089, 0xc74e4987,
216         0xae053edd, 0xa50837d3, 0xb81f2cc1, 0xb31225cf,
217         0x82311ae5, 0x893c13eb, 0x942b08f9, 0x9f2601f7,
218         0x46bde64d, 0x4db0ef43, 0x50a7f451, 0x5baafd5f,
219         0x6a89c275, 0x6184cb7b, 0x7c93d069, 0x779ed967,
220         0x1ed5ae3d, 0x15d8a733, 0x08cfbc21, 0x03c2b52f,
221         0x32e18a05, 0x39ec830b, 0x24fb9819, 0x2ff69117,
222         0x8dd64d76, 0x86db4478, 0x9bcc5f6a, 0x90c15664,
223         0xa1e2694e, 0xaaef6040, 0xb7f87b52, 0xbcf5725c,
224         0xd5be0506, 0xdeb30c08, 0xc3a4171a, 0xc8a91e14,
225         0xf98a213e, 0xf2872830, 0xef903322, 0xe49d3a2c,
226         0x3d06dd96, 0x360bd498, 0x2b1ccf8a, 0x2011c684,
227         0x1132f9ae, 0x1a3ff0a0, 0x0728ebb2, 0x0c25e2bc,
228         0x656e95e6, 0x6e639ce8, 0x737487fa, 0x78798ef4,
229         0x495ab1de, 0x4257b8d0, 0x5f40a3c2, 0x544daacc,
230         0xf7daec41, 0xfcd7e54f, 0xe1c0fe5d, 0xeacdf753,
231         0xdbeec879, 0xd0e3c177, 0xcdf4da65, 0xc6f9d36b,
232         0xafb2a431, 0xa4bfad3f, 0xb9a8b62d, 0xb2a5bf23,
233         0x83868009, 0x888b8907, 0x959c9215, 0x9e919b1b,
234         0x470a7ca1, 0x4c0775af, 0x51106ebd, 0x5a1d67b3,
235         0x6b3e5899, 0x60335197, 0x7d244a85, 0x7629438b,
236         0x1f6234d1, 0x146f3ddf, 0x097826cd, 0x02752fc3,
237         0x335610e9, 0x385b19e7, 0x254c02f5, 0x2e410bfb,
238         0x8c61d79a, 0x876cde94, 0x9a7bc586, 0x9176cc88,
239         0xa055f3a2, 0xab58faac, 0xb64fe1be, 0xbd42e8b0,
240         0xd4099fea, 0xdf0496e4, 0xc2138df6, 0xc91e84f8,
241         0xf83dbbd2, 0xf330b2dc, 0xee27a9ce, 0xe52aa0c0,
242         0x3cb1477a, 0x37bc4e74, 0x2aab5566, 0x21a65c68,
243         0x10856342, 0x1b886a4c, 0x069f715e, 0x0d927850,
244         0x64d90f0a, 0x6fd40604, 0x72c31d16, 0x79ce1418,
245         0x48ed2b32, 0x43e0223c, 0x5ef7392e, 0x55fa3020,
246         0x01b79aec, 0x0aba93e2, 0x17ad88f0, 0x1ca081fe,
247         0x2d83bed4, 0x268eb7da, 0x3b99acc8, 0x3094a5c6,
248         0x59dfd29c, 0x52d2db92, 0x4fc5c080, 0x44c8c98e,
249         0x75ebf6a4, 0x7ee6ffaa, 0x63f1e4b8, 0x68fcedb6,
250         0xb1670a0c, 0xba6a0302, 0xa77d1810, 0xac70111e,
251         0x9d532e34, 0x965e273a, 0x8b493c28, 0x80443526,
252         0xe90f427c, 0xe2024b72, 0xff155060, 0xf418596e,
253         0xc53b6644, 0xce366f4a, 0xd3217458, 0xd82c7d56,
254         0x7a0ca137, 0x7101a839, 0x6c16b32b, 0x671bba25,
255         0x5638850f, 0x5d358c01, 0x40229713, 0x4b2f9e1d,
256         0x2264e947, 0x2969e049, 0x347efb5b, 0x3f73f255,
257         0x0e50cd7f, 0x055dc471, 0x184adf63, 0x1347d66d,
258         0xcadc31d7, 0xc1d138d9, 0xdcc623cb, 0xd7cb2ac5,
259         0xe6e815ef, 0xede51ce1, 0xf0f207f3, 0xfbff0efd,
260         0x92b479a7, 0x99b970a9, 0x84ae6bbb, 0x8fa362b5,
261         0xbe805d9f, 0xb58d5491, 0xa89a4f83, 0xa397468d,
262     } };
263     union CRYPTO_STATE st = { .l = {
264         float64_val(env->vfp.regs[rm]),
265         float64_val(env->vfp.regs[rm + 1])
266     } };
267     int i;
268
269     assert(decrypt < 2);
270
271     for (i = 0; i < 16; i += 4) {
272         st.words[i >> 2] = cpu_to_le32(
273             mc[decrypt][st.bytes[i]] ^
274             rol32(mc[decrypt][st.bytes[i + 1]], 8) ^
275             rol32(mc[decrypt][st.bytes[i + 2]], 16) ^
276             rol32(mc[decrypt][st.bytes[i + 3]], 24));
277     }
278
279     env->vfp.regs[rd] = make_float64(st.l[0]);
280     env->vfp.regs[rd + 1] = make_float64(st.l[1]);
281 }
282
283 /*
284  * SHA-1 logical functions
285  */
286
287 static uint32_t cho(uint32_t x, uint32_t y, uint32_t z)
288 {
289     return (x & (y ^ z)) ^ z;
290 }
291
292 static uint32_t par(uint32_t x, uint32_t y, uint32_t z)
293 {
294     return x ^ y ^ z;
295 }
296
297 static uint32_t maj(uint32_t x, uint32_t y, uint32_t z)
298 {
299     return (x & y) | ((x | y) & z);
300 }
301
302 void HELPER(crypto_sha1_3reg)(CPUARMState *env, uint32_t rd, uint32_t rn,
303                               uint32_t rm, uint32_t op)
304 {
305     union CRYPTO_STATE d = { .l = {
306         float64_val(env->vfp.regs[rd]),
307         float64_val(env->vfp.regs[rd + 1])
308     } };
309     union CRYPTO_STATE n = { .l = {
310         float64_val(env->vfp.regs[rn]),
311         float64_val(env->vfp.regs[rn + 1])
312     } };
313     union CRYPTO_STATE m = { .l = {
314         float64_val(env->vfp.regs[rm]),
315         float64_val(env->vfp.regs[rm + 1])
316     } };
317
318     if (op == 3) { /* sha1su0 */
319         d.l[0] ^= d.l[1] ^ m.l[0];
320         d.l[1] ^= n.l[0] ^ m.l[1];
321     } else {
322         int i;
323
324         for (i = 0; i < 4; i++) {
325             uint32_t t;
326
327             switch (op) {
328             case 0: /* sha1c */
329                 t = cho(d.words[1], d.words[2], d.words[3]);
330                 break;
331             case 1: /* sha1p */
332                 t = par(d.words[1], d.words[2], d.words[3]);
333                 break;
334             case 2: /* sha1m */
335                 t = maj(d.words[1], d.words[2], d.words[3]);
336                 break;
337             default:
338                 g_assert_not_reached();
339             }
340             t += rol32(d.words[0], 5) + n.words[0] + m.words[i];
341
342             n.words[0] = d.words[3];
343             d.words[3] = d.words[2];
344             d.words[2] = ror32(d.words[1], 2);
345             d.words[1] = d.words[0];
346             d.words[0] = t;
347         }
348     }
349     env->vfp.regs[rd] = make_float64(d.l[0]);
350     env->vfp.regs[rd + 1] = make_float64(d.l[1]);
351 }
352
353 void HELPER(crypto_sha1h)(CPUARMState *env, uint32_t rd, uint32_t rm)
354 {
355     union CRYPTO_STATE m = { .l = {
356         float64_val(env->vfp.regs[rm]),
357         float64_val(env->vfp.regs[rm + 1])
358     } };
359
360     m.words[0] = ror32(m.words[0], 2);
361     m.words[1] = m.words[2] = m.words[3] = 0;
362
363     env->vfp.regs[rd] = make_float64(m.l[0]);
364     env->vfp.regs[rd + 1] = make_float64(m.l[1]);
365 }
366
367 void HELPER(crypto_sha1su1)(CPUARMState *env, uint32_t rd, uint32_t rm)
368 {
369     union CRYPTO_STATE d = { .l = {
370         float64_val(env->vfp.regs[rd]),
371         float64_val(env->vfp.regs[rd + 1])
372     } };
373     union CRYPTO_STATE m = { .l = {
374         float64_val(env->vfp.regs[rm]),
375         float64_val(env->vfp.regs[rm + 1])
376     } };
377
378     d.words[0] = rol32(d.words[0] ^ m.words[1], 1);
379     d.words[1] = rol32(d.words[1] ^ m.words[2], 1);
380     d.words[2] = rol32(d.words[2] ^ m.words[3], 1);
381     d.words[3] = rol32(d.words[3] ^ d.words[0], 1);
382
383     env->vfp.regs[rd] = make_float64(d.l[0]);
384     env->vfp.regs[rd + 1] = make_float64(d.l[1]);
385 }
386
387 /*
388  * The SHA-256 logical functions, according to
389  * http://csrc.nist.gov/groups/STM/cavp/documents/shs/sha256-384-512.pdf
390  */
391
392 static uint32_t S0(uint32_t x)
393 {
394     return ror32(x, 2) ^ ror32(x, 13) ^ ror32(x, 22);
395 }
396
397 static uint32_t S1(uint32_t x)
398 {
399     return ror32(x, 6) ^ ror32(x, 11) ^ ror32(x, 25);
400 }
401
402 static uint32_t s0(uint32_t x)
403 {
404     return ror32(x, 7) ^ ror32(x, 18) ^ (x >> 3);
405 }
406
407 static uint32_t s1(uint32_t x)
408 {
409     return ror32(x, 17) ^ ror32(x, 19) ^ (x >> 10);
410 }
411
412 void HELPER(crypto_sha256h)(CPUARMState *env, uint32_t rd, uint32_t rn,
413                             uint32_t rm)
414 {
415     union CRYPTO_STATE d = { .l = {
416         float64_val(env->vfp.regs[rd]),
417         float64_val(env->vfp.regs[rd + 1])
418     } };
419     union CRYPTO_STATE n = { .l = {
420         float64_val(env->vfp.regs[rn]),
421         float64_val(env->vfp.regs[rn + 1])
422     } };
423     union CRYPTO_STATE m = { .l = {
424         float64_val(env->vfp.regs[rm]),
425         float64_val(env->vfp.regs[rm + 1])
426     } };
427     int i;
428
429     for (i = 0; i < 4; i++) {
430         uint32_t t = cho(n.words[0], n.words[1], n.words[2]) + n.words[3]
431                      + S1(n.words[0]) + m.words[i];
432
433         n.words[3] = n.words[2];
434         n.words[2] = n.words[1];
435         n.words[1] = n.words[0];
436         n.words[0] = d.words[3] + t;
437
438         t += maj(d.words[0], d.words[1], d.words[2]) + S0(d.words[0]);
439
440         d.words[3] = d.words[2];
441         d.words[2] = d.words[1];
442         d.words[1] = d.words[0];
443         d.words[0] = t;
444     }
445
446     env->vfp.regs[rd] = make_float64(d.l[0]);
447     env->vfp.regs[rd + 1] = make_float64(d.l[1]);
448 }
449
450 void HELPER(crypto_sha256h2)(CPUARMState *env, uint32_t rd, uint32_t rn,
451                              uint32_t rm)
452 {
453     union CRYPTO_STATE d = { .l = {
454         float64_val(env->vfp.regs[rd]),
455         float64_val(env->vfp.regs[rd + 1])
456     } };
457     union CRYPTO_STATE n = { .l = {
458         float64_val(env->vfp.regs[rn]),
459         float64_val(env->vfp.regs[rn + 1])
460     } };
461     union CRYPTO_STATE m = { .l = {
462         float64_val(env->vfp.regs[rm]),
463         float64_val(env->vfp.regs[rm + 1])
464     } };
465     int i;
466
467     for (i = 0; i < 4; i++) {
468         uint32_t t = cho(d.words[0], d.words[1], d.words[2]) + d.words[3]
469                      + S1(d.words[0]) + m.words[i];
470
471         d.words[3] = d.words[2];
472         d.words[2] = d.words[1];
473         d.words[1] = d.words[0];
474         d.words[0] = n.words[3 - i] + t;
475     }
476
477     env->vfp.regs[rd] = make_float64(d.l[0]);
478     env->vfp.regs[rd + 1] = make_float64(d.l[1]);
479 }
480
481 void HELPER(crypto_sha256su0)(CPUARMState *env, uint32_t rd, uint32_t rm)
482 {
483     union CRYPTO_STATE d = { .l = {
484         float64_val(env->vfp.regs[rd]),
485         float64_val(env->vfp.regs[rd + 1])
486     } };
487     union CRYPTO_STATE m = { .l = {
488         float64_val(env->vfp.regs[rm]),
489         float64_val(env->vfp.regs[rm + 1])
490     } };
491
492     d.words[0] += s0(d.words[1]);
493     d.words[1] += s0(d.words[2]);
494     d.words[2] += s0(d.words[3]);
495     d.words[3] += s0(m.words[0]);
496
497     env->vfp.regs[rd] = make_float64(d.l[0]);
498     env->vfp.regs[rd + 1] = make_float64(d.l[1]);
499 }
500
501 void HELPER(crypto_sha256su1)(CPUARMState *env, uint32_t rd, uint32_t rn,
502                               uint32_t rm)
503 {
504     union CRYPTO_STATE d = { .l = {
505         float64_val(env->vfp.regs[rd]),
506         float64_val(env->vfp.regs[rd + 1])
507     } };
508     union CRYPTO_STATE n = { .l = {
509         float64_val(env->vfp.regs[rn]),
510         float64_val(env->vfp.regs[rn + 1])
511     } };
512     union CRYPTO_STATE m = { .l = {
513         float64_val(env->vfp.regs[rm]),
514         float64_val(env->vfp.regs[rm + 1])
515     } };
516
517     d.words[0] += s1(m.words[2]) + n.words[1];
518     d.words[1] += s1(m.words[3]) + n.words[2];
519     d.words[2] += s1(d.words[0]) + n.words[3];
520     d.words[3] += s1(d.words[1]) + m.words[0];
521
522     env->vfp.regs[rd] = make_float64(d.l[0]);
523     env->vfp.regs[rd + 1] = make_float64(d.l[1]);
524 }
This page took 0.051852 seconds and 4 git commands to generate.