1 /* SPDX-License-Identifier: GPL-2.0-or-later */ 2 /* 3 * include/asm/xor.h 4 * 5 * Optimized RAID-5 checksumming functions for 32-bit Sparc. 6 */ 7 8 /* 9 * High speed xor_block operation for RAID4/5 utilizing the 10 * ldd/std SPARC instructions. 11 * 12 * Copyright (C) 1999 Jakub Jelinek (jj@ultra.linux.cz) 13 */ 14 15 static void 16 sparc_2(unsigned long bytes, unsigned long * __restrict p1, 17 const unsigned long * __restrict p2) 18 { 19 int lines = bytes / (sizeof (long)) / 8; 20 21 do { 22 __asm__ __volatile__( 23 "ldd [%0 + 0x00], %%g2\n\t" 24 "ldd [%0 + 0x08], %%g4\n\t" 25 "ldd [%0 + 0x10], %%o0\n\t" 26 "ldd [%0 + 0x18], %%o2\n\t" 27 "ldd [%1 + 0x00], %%o4\n\t" 28 "ldd [%1 + 0x08], %%l0\n\t" 29 "ldd [%1 + 0x10], %%l2\n\t" 30 "ldd [%1 + 0x18], %%l4\n\t" 31 "xor %%g2, %%o4, %%g2\n\t" 32 "xor %%g3, %%o5, %%g3\n\t" 33 "xor %%g4, %%l0, %%g4\n\t" 34 "xor %%g5, %%l1, %%g5\n\t" 35 "xor %%o0, %%l2, %%o0\n\t" 36 "xor %%o1, %%l3, %%o1\n\t" 37 "xor %%o2, %%l4, %%o2\n\t" 38 "xor %%o3, %%l5, %%o3\n\t" 39 "std %%g2, [%0 + 0x00]\n\t" 40 "std %%g4, [%0 + 0x08]\n\t" 41 "std %%o0, [%0 + 0x10]\n\t" 42 "std %%o2, [%0 + 0x18]\n" 43 : 44 : "r" (p1), "r" (p2) 45 : "g2", "g3", "g4", "g5", 46 "o0", "o1", "o2", "o3", "o4", "o5", 47 "l0", "l1", "l2", "l3", "l4", "l5"); 48 p1 += 8; 49 p2 += 8; 50 } while (--lines > 0); 51 } 52 53 static void 54 sparc_3(unsigned long bytes, unsigned long * __restrict p1, 55 const unsigned long * __restrict p2, 56 const unsigned long * __restrict p3) 57 { 58 int lines = bytes / (sizeof (long)) / 8; 59 60 do { 61 __asm__ __volatile__( 62 "ldd [%0 + 0x00], %%g2\n\t" 63 "ldd [%0 + 0x08], %%g4\n\t" 64 "ldd [%0 + 0x10], %%o0\n\t" 65 "ldd [%0 + 0x18], %%o2\n\t" 66 "ldd [%1 + 0x00], %%o4\n\t" 67 "ldd [%1 + 0x08], %%l0\n\t" 68 "ldd [%1 + 0x10], %%l2\n\t" 69 "ldd [%1 + 0x18], %%l4\n\t" 70 "xor %%g2, %%o4, %%g2\n\t" 71 "xor %%g3, %%o5, %%g3\n\t" 72 "ldd [%2 + 0x00], %%o4\n\t" 73 "xor %%g4, %%l0, %%g4\n\t" 74 "xor %%g5, %%l1, %%g5\n\t" 75 "ldd [%2 + 0x08], %%l0\n\t" 76 "xor %%o0, %%l2, %%o0\n\t" 77 "xor %%o1, %%l3, %%o1\n\t" 78 "ldd [%2 + 0x10], %%l2\n\t" 79 "xor %%o2, %%l4, %%o2\n\t" 80 "xor %%o3, %%l5, %%o3\n\t" 81 "ldd [%2 + 0x18], %%l4\n\t" 82 "xor %%g2, %%o4, %%g2\n\t" 83 "xor %%g3, %%o5, %%g3\n\t" 84 "xor %%g4, %%l0, %%g4\n\t" 85 "xor %%g5, %%l1, %%g5\n\t" 86 "xor %%o0, %%l2, %%o0\n\t" 87 "xor %%o1, %%l3, %%o1\n\t" 88 "xor %%o2, %%l4, %%o2\n\t" 89 "xor %%o3, %%l5, %%o3\n\t" 90 "std %%g2, [%0 + 0x00]\n\t" 91 "std %%g4, [%0 + 0x08]\n\t" 92 "std %%o0, [%0 + 0x10]\n\t" 93 "std %%o2, [%0 + 0x18]\n" 94 : 95 : "r" (p1), "r" (p2), "r" (p3) 96 : "g2", "g3", "g4", "g5", 97 "o0", "o1", "o2", "o3", "o4", "o5", 98 "l0", "l1", "l2", "l3", "l4", "l5"); 99 p1 += 8; 100 p2 += 8; 101 p3 += 8; 102 } while (--lines > 0); 103 } 104 105 static void 106 sparc_4(unsigned long bytes, unsigned long * __restrict p1, 107 const unsigned long * __restrict p2, 108 const unsigned long * __restrict p3, 109 const unsigned long * __restrict p4) 110 { 111 int lines = bytes / (sizeof (long)) / 8; 112 113 do { 114 __asm__ __volatile__( 115 "ldd [%0 + 0x00], %%g2\n\t" 116 "ldd [%0 + 0x08], %%g4\n\t" 117 "ldd [%0 + 0x10], %%o0\n\t" 118 "ldd [%0 + 0x18], %%o2\n\t" 119 "ldd [%1 + 0x00], %%o4\n\t" 120 "ldd [%1 + 0x08], %%l0\n\t" 121 "ldd [%1 + 0x10], %%l2\n\t" 122 "ldd [%1 + 0x18], %%l4\n\t" 123 "xor %%g2, %%o4, %%g2\n\t" 124 "xor %%g3, %%o5, %%g3\n\t" 125 "ldd [%2 + 0x00], %%o4\n\t" 126 "xor %%g4, %%l0, %%g4\n\t" 127 "xor %%g5, %%l1, %%g5\n\t" 128 "ldd [%2 + 0x08], %%l0\n\t" 129 "xor %%o0, %%l2, %%o0\n\t" 130 "xor %%o1, %%l3, %%o1\n\t" 131 "ldd [%2 + 0x10], %%l2\n\t" 132 "xor %%o2, %%l4, %%o2\n\t" 133 "xor %%o3, %%l5, %%o3\n\t" 134 "ldd [%2 + 0x18], %%l4\n\t" 135 "xor %%g2, %%o4, %%g2\n\t" 136 "xor %%g3, %%o5, %%g3\n\t" 137 "ldd [%3 + 0x00], %%o4\n\t" 138 "xor %%g4, %%l0, %%g4\n\t" 139 "xor %%g5, %%l1, %%g5\n\t" 140 "ldd [%3 + 0x08], %%l0\n\t" 141 "xor %%o0, %%l2, %%o0\n\t" 142 "xor %%o1, %%l3, %%o1\n\t" 143 "ldd [%3 + 0x10], %%l2\n\t" 144 "xor %%o2, %%l4, %%o2\n\t" 145 "xor %%o3, %%l5, %%o3\n\t" 146 "ldd [%3 + 0x18], %%l4\n\t" 147 "xor %%g2, %%o4, %%g2\n\t" 148 "xor %%g3, %%o5, %%g3\n\t" 149 "xor %%g4, %%l0, %%g4\n\t" 150 "xor %%g5, %%l1, %%g5\n\t" 151 "xor %%o0, %%l2, %%o0\n\t" 152 "xor %%o1, %%l3, %%o1\n\t" 153 "xor %%o2, %%l4, %%o2\n\t" 154 "xor %%o3, %%l5, %%o3\n\t" 155 "std %%g2, [%0 + 0x00]\n\t" 156 "std %%g4, [%0 + 0x08]\n\t" 157 "std %%o0, [%0 + 0x10]\n\t" 158 "std %%o2, [%0 + 0x18]\n" 159 : 160 : "r" (p1), "r" (p2), "r" (p3), "r" (p4) 161 : "g2", "g3", "g4", "g5", 162 "o0", "o1", "o2", "o3", "o4", "o5", 163 "l0", "l1", "l2", "l3", "l4", "l5"); 164 p1 += 8; 165 p2 += 8; 166 p3 += 8; 167 p4 += 8; 168 } while (--lines > 0); 169 } 170 171 static void 172 sparc_5(unsigned long bytes, unsigned long * __restrict p1, 173 const unsigned long * __restrict p2, 174 const unsigned long * __restrict p3, 175 const unsigned long * __restrict p4, 176 const unsigned long * __restrict p5) 177 { 178 int lines = bytes / (sizeof (long)) / 8; 179 180 do { 181 __asm__ __volatile__( 182 "ldd [%0 + 0x00], %%g2\n\t" 183 "ldd [%0 + 0x08], %%g4\n\t" 184 "ldd [%0 + 0x10], %%o0\n\t" 185 "ldd [%0 + 0x18], %%o2\n\t" 186 "ldd [%1 + 0x00], %%o4\n\t" 187 "ldd [%1 + 0x08], %%l0\n\t" 188 "ldd [%1 + 0x10], %%l2\n\t" 189 "ldd [%1 + 0x18], %%l4\n\t" 190 "xor %%g2, %%o4, %%g2\n\t" 191 "xor %%g3, %%o5, %%g3\n\t" 192 "ldd [%2 + 0x00], %%o4\n\t" 193 "xor %%g4, %%l0, %%g4\n\t" 194 "xor %%g5, %%l1, %%g5\n\t" 195 "ldd [%2 + 0x08], %%l0\n\t" 196 "xor %%o0, %%l2, %%o0\n\t" 197 "xor %%o1, %%l3, %%o1\n\t" 198 "ldd [%2 + 0x10], %%l2\n\t" 199 "xor %%o2, %%l4, %%o2\n\t" 200 "xor %%o3, %%l5, %%o3\n\t" 201 "ldd [%2 + 0x18], %%l4\n\t" 202 "xor %%g2, %%o4, %%g2\n\t" 203 "xor %%g3, %%o5, %%g3\n\t" 204 "ldd [%3 + 0x00], %%o4\n\t" 205 "xor %%g4, %%l0, %%g4\n\t" 206 "xor %%g5, %%l1, %%g5\n\t" 207 "ldd [%3 + 0x08], %%l0\n\t" 208 "xor %%o0, %%l2, %%o0\n\t" 209 "xor %%o1, %%l3, %%o1\n\t" 210 "ldd [%3 + 0x10], %%l2\n\t" 211 "xor %%o2, %%l4, %%o2\n\t" 212 "xor %%o3, %%l5, %%o3\n\t" 213 "ldd [%3 + 0x18], %%l4\n\t" 214 "xor %%g2, %%o4, %%g2\n\t" 215 "xor %%g3, %%o5, %%g3\n\t" 216 "ldd [%4 + 0x00], %%o4\n\t" 217 "xor %%g4, %%l0, %%g4\n\t" 218 "xor %%g5, %%l1, %%g5\n\t" 219 "ldd [%4 + 0x08], %%l0\n\t" 220 "xor %%o0, %%l2, %%o0\n\t" 221 "xor %%o1, %%l3, %%o1\n\t" 222 "ldd [%4 + 0x10], %%l2\n\t" 223 "xor %%o2, %%l4, %%o2\n\t" 224 "xor %%o3, %%l5, %%o3\n\t" 225 "ldd [%4 + 0x18], %%l4\n\t" 226 "xor %%g2, %%o4, %%g2\n\t" 227 "xor %%g3, %%o5, %%g3\n\t" 228 "xor %%g4, %%l0, %%g4\n\t" 229 "xor %%g5, %%l1, %%g5\n\t" 230 "xor %%o0, %%l2, %%o0\n\t" 231 "xor %%o1, %%l3, %%o1\n\t" 232 "xor %%o2, %%l4, %%o2\n\t" 233 "xor %%o3, %%l5, %%o3\n\t" 234 "std %%g2, [%0 + 0x00]\n\t" 235 "std %%g4, [%0 + 0x08]\n\t" 236 "std %%o0, [%0 + 0x10]\n\t" 237 "std %%o2, [%0 + 0x18]\n" 238 : 239 : "r" (p1), "r" (p2), "r" (p3), "r" (p4), "r" (p5) 240 : "g2", "g3", "g4", "g5", 241 "o0", "o1", "o2", "o3", "o4", "o5", 242 "l0", "l1", "l2", "l3", "l4", "l5"); 243 p1 += 8; 244 p2 += 8; 245 p3 += 8; 246 p4 += 8; 247 p5 += 8; 248 } while (--lines > 0); 249 } 250 251 static struct xor_block_template xor_block_SPARC = { 252 .name = "SPARC", 253 .do_2 = sparc_2, 254 .do_3 = sparc_3, 255 .do_4 = sparc_4, 256 .do_5 = sparc_5, 257 }; 258 259 /* For grins, also test the generic routines. */ 260 #include <asm-generic/xor.h> 261 262 #undef XOR_TRY_TEMPLATES 263 #define XOR_TRY_TEMPLATES \ 264 do { \ 265 xor_speed(&xor_block_8regs); \ 266 xor_speed(&xor_block_32regs); \ 267 xor_speed(&xor_block_SPARC); \ 268 } while (0) 269