1/* Callee-saved register spill and fill routines for RISC-V. 2 3 Copyright (C) 2016-2022 Free Software Foundation, Inc. 4 5This file is part of GCC. 6 7GCC is free software; you can redistribute it and/or modify it under 8the terms of the GNU General Public License as published by the Free 9Software Foundation; either version 3, or (at your option) any later 10version. 11 12GCC is distributed in the hope that it will be useful, but WITHOUT ANY 13WARRANTY; without even the implied warranty of MERCHANTABILITY or 14FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 15for more details. 16 17Under Section 7 of GPL version 3, you are granted additional 18permissions described in the GCC Runtime Library Exception, version 193.1, as published by the Free Software Foundation. 20 21You should have received a copy of the GNU General Public License and 22a copy of the GCC Runtime Library Exception along with this program; 23see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 24<http://www.gnu.org/licenses/>. */ 25 26#include "riscv-asm.h" 27 28 .text 29 30#if __riscv_xlen == 64 31 32FUNC_BEGIN (__riscv_save_12) 33 .cfi_startproc 34 # __riscv_save_* routine use t0/x5 as return address 35 .cfi_return_column 5 36 addi sp, sp, -112 37 .cfi_def_cfa_offset 112 38 li t1, 0 39 sd s11, 8(sp) 40 .cfi_offset 27, -104 41 j .Ls10 42 43FUNC_BEGIN (__riscv_save_11) 44FUNC_BEGIN (__riscv_save_10) 45 .cfi_restore 27 46 addi sp, sp, -112 47 .cfi_def_cfa_offset 112 48 li t1, 1 49.Ls10: 50 sd s10, 16(sp) 51 .cfi_offset 26, -96 52 sd s9, 24(sp) 53 .cfi_offset 25, -88 54 j .Ls8 55 56FUNC_BEGIN (__riscv_save_9) 57FUNC_BEGIN (__riscv_save_8) 58 .cfi_restore 25 59 .cfi_restore 26 60 .cfi_restore 27 61 addi sp, sp, -112 62 .cfi_def_cfa_offset 112 63 li t1, 2 64.Ls8: 65 sd s8, 32(sp) 66 .cfi_offset 24, -80 67 sd s7, 40(sp) 68 .cfi_offset 23, -72 69 j .Ls6 70 71FUNC_BEGIN (__riscv_save_7) 72FUNC_BEGIN (__riscv_save_6) 73 .cfi_restore 23 74 .cfi_restore 24 75 .cfi_restore 25 76 .cfi_restore 26 77 .cfi_restore 27 78 addi sp, sp, -112 79 .cfi_def_cfa_offset 112 80 li t1, 3 81.Ls6: 82 sd s6, 48(sp) 83 .cfi_offset 22, -64 84 sd s5, 56(sp) 85 .cfi_offset 21, -56 86 j .Ls4 87 88FUNC_BEGIN (__riscv_save_5) 89FUNC_BEGIN (__riscv_save_4) 90 .cfi_restore 21 91 .cfi_restore 22 92 .cfi_restore 24 93 .cfi_restore 25 94 .cfi_restore 26 95 .cfi_restore 27 96 .cfi_restore 24 97 .cfi_restore 25 98 .cfi_restore 26 99 .cfi_restore 27 100 addi sp, sp, -112 101 .cfi_def_cfa_offset 112 102 li t1, 4 103.Ls4: 104 sd s4, 64(sp) 105 .cfi_offset 20, -48 106 sd s3, 72(sp) 107 .cfi_offset 19, -40 108 j .Ls2 109 110FUNC_BEGIN (__riscv_save_3) 111FUNC_BEGIN (__riscv_save_2) 112 .cfi_restore 19 113 .cfi_restore 20 114 .cfi_restore 21 115 .cfi_restore 22 116 .cfi_restore 24 117 .cfi_restore 25 118 .cfi_restore 26 119 .cfi_restore 27 120 .cfi_restore 24 121 .cfi_restore 25 122 .cfi_restore 26 123 .cfi_restore 27 124 addi sp, sp, -112 125 .cfi_def_cfa_offset 112 126 li t1, 5 127.Ls2: 128 sd s2, 80(sp) 129 .cfi_offset 18, -32 130 sd s1, 88(sp) 131 .cfi_offset 9, -24 132 sd s0, 96(sp) 133 .cfi_offset 8, -16 134 sd ra, 104(sp) 135 .cfi_offset 1, -8 136 slli t1, t1, 4 137 # CFA info is not correct in next 2 instruction since t1's 138 # value is depend on how may register really save. 139 add sp, sp, t1 140 jr t0 141 .cfi_endproc 142FUNC_END (__riscv_save_12) 143FUNC_END (__riscv_save_11) 144FUNC_END (__riscv_save_10) 145FUNC_END (__riscv_save_9) 146FUNC_END (__riscv_save_8) 147FUNC_END (__riscv_save_7) 148FUNC_END (__riscv_save_6) 149FUNC_END (__riscv_save_5) 150FUNC_END (__riscv_save_4) 151FUNC_END (__riscv_save_3) 152FUNC_END (__riscv_save_2) 153 154FUNC_BEGIN (__riscv_save_1) 155FUNC_BEGIN (__riscv_save_0) 156 .cfi_startproc 157 # __riscv_save_* routine use t0/x5 as return address 158 .cfi_return_column 5 159 addi sp, sp, -16 160 .cfi_def_cfa_offset 16 161 sd s0, 0(sp) 162 .cfi_offset 8, -16 163 sd ra, 8(sp) 164 .cfi_offset 1, -8 165 jr t0 166 .cfi_endproc 167FUNC_END (__riscv_save_1) 168FUNC_END (__riscv_save_0) 169 170FUNC_BEGIN (__riscv_restore_12) 171 .cfi_startproc 172 .cfi_def_cfa_offset 112 173 .cfi_offset 27, -104 174 .cfi_offset 26, -96 175 .cfi_offset 25, -88 176 .cfi_offset 24, -80 177 .cfi_offset 23, -72 178 .cfi_offset 22, -64 179 .cfi_offset 21, -56 180 .cfi_offset 20, -48 181 .cfi_offset 19, -40 182 .cfi_offset 18, -32 183 .cfi_offset 9, -24 184 .cfi_offset 8, -16 185 .cfi_offset 1, -8 186 ld s11, 8(sp) 187 .cfi_restore 27 188 addi sp, sp, 16 189 190FUNC_BEGIN (__riscv_restore_11) 191FUNC_BEGIN (__riscv_restore_10) 192 .cfi_restore 27 193 .cfi_def_cfa_offset 96 194 ld s10, 0(sp) 195 .cfi_restore 26 196 ld s9, 8(sp) 197 .cfi_restore 25 198 addi sp, sp, 16 199 200FUNC_BEGIN (__riscv_restore_9) 201FUNC_BEGIN (__riscv_restore_8) 202 .cfi_restore 25 203 .cfi_restore 26 204 .cfi_restore 27 205 .cfi_def_cfa_offset 80 206 ld s8, 0(sp) 207 .cfi_restore 24 208 ld s7, 8(sp) 209 .cfi_restore 23 210 addi sp, sp, 16 211 212FUNC_BEGIN (__riscv_restore_7) 213FUNC_BEGIN (__riscv_restore_6) 214 .cfi_restore 23 215 .cfi_restore 24 216 .cfi_restore 25 217 .cfi_restore 26 218 .cfi_restore 27 219 .cfi_def_cfa_offset 64 220 ld s6, 0(sp) 221 .cfi_restore 22 222 ld s5, 8(sp) 223 .cfi_restore 21 224 addi sp, sp, 16 225 226FUNC_BEGIN (__riscv_restore_5) 227FUNC_BEGIN (__riscv_restore_4) 228 .cfi_restore 21 229 .cfi_restore 22 230 .cfi_restore 23 231 .cfi_restore 24 232 .cfi_restore 25 233 .cfi_restore 26 234 .cfi_restore 27 235 .cfi_def_cfa_offset 48 236 ld s4, 0(sp) 237 .cfi_restore 20 238 ld s3, 8(sp) 239 .cfi_restore 19 240 addi sp, sp, 16 241 242FUNC_BEGIN (__riscv_restore_3) 243FUNC_BEGIN (__riscv_restore_2) 244 .cfi_restore 19 245 .cfi_restore 20 246 .cfi_restore 21 247 .cfi_restore 22 248 .cfi_restore 23 249 .cfi_restore 24 250 .cfi_restore 25 251 .cfi_restore 26 252 .cfi_restore 27 253 .cfi_def_cfa_offset 32 254 ld s2, 0(sp) 255 .cfi_restore 18 256 ld s1, 8(sp) 257 .cfi_restore 9 258 addi sp, sp, 16 259 260FUNC_BEGIN (__riscv_restore_1) 261FUNC_BEGIN (__riscv_restore_0) 262 .cfi_restore 9 263 .cfi_restore 18 264 .cfi_restore 19 265 .cfi_restore 20 266 .cfi_restore 21 267 .cfi_restore 22 268 .cfi_restore 23 269 .cfi_restore 24 270 .cfi_restore 25 271 .cfi_restore 26 272 .cfi_restore 27 273 .cfi_def_cfa_offset 16 274 ld s0, 0(sp) 275 .cfi_restore 8 276 ld ra, 8(sp) 277 .cfi_restore 1 278 addi sp, sp, 16 279 .cfi_def_cfa_offset 0 280 ret 281 .cfi_endproc 282FUNC_END (__riscv_restore_12) 283FUNC_END (__riscv_restore_11) 284FUNC_END (__riscv_restore_10) 285FUNC_END (__riscv_restore_9) 286FUNC_END (__riscv_restore_8) 287FUNC_END (__riscv_restore_7) 288FUNC_END (__riscv_restore_6) 289FUNC_END (__riscv_restore_5) 290FUNC_END (__riscv_restore_4) 291FUNC_END (__riscv_restore_3) 292FUNC_END (__riscv_restore_2) 293FUNC_END (__riscv_restore_1) 294FUNC_END (__riscv_restore_0) 295 296#else 297 298#ifdef __riscv_32e 299FUNC_BEGIN(__riscv_save_2) 300FUNC_BEGIN(__riscv_save_1) 301FUNC_BEGIN(__riscv_save_0) 302 .cfi_startproc 303 # __riscv_save_* routine use t0/x5 as return address 304 .cfi_return_column 5 305 addi sp, sp, -12 306 .cfi_def_cfa_offset 12 307 sw s1, 0(sp) 308 .cfi_offset 9, -12 309 sw s0, 4(sp) 310 .cfi_offset 8, -8 311 sw ra, 8(sp) 312 .cfi_offset 1, 0 313 jr t0 314 .cfi_endproc 315FUNC_END(__riscv_save_2) 316FUNC_END(__riscv_save_1) 317FUNC_END(__riscv_save_0) 318 319FUNC_BEGIN(__riscv_restore_2) 320FUNC_BEGIN(__riscv_restore_1) 321FUNC_BEGIN(__riscv_restore_0) 322 .cfi_startproc 323 .cfi_def_cfa_offset 14 324 lw s1, 0(sp) 325 .cfi_restore 9 326 lw s0, 4(sp) 327 .cfi_restore 8 328 lw ra, 8(sp) 329 .cfi_restore 1 330 addi sp, sp, 12 331 .cfi_def_cfa_offset 0 332 ret 333 .cfi_endproc 334FUNC_END(__riscv_restore_2) 335FUNC_END(__riscv_restore_1) 336FUNC_END(__riscv_restore_0) 337 338#else 339 340FUNC_BEGIN (__riscv_save_12) 341 .cfi_startproc 342 # __riscv_save_* routine use t0/x5 as return address 343 .cfi_return_column 5 344 addi sp, sp, -64 345 .cfi_def_cfa_offset 64 346 li t1, 0 347 sw s11, 12(sp) 348 .cfi_offset 27, -52 349 j .Ls10 350 351FUNC_BEGIN (__riscv_save_11) 352FUNC_BEGIN (__riscv_save_10) 353FUNC_BEGIN (__riscv_save_9) 354FUNC_BEGIN (__riscv_save_8) 355 .cfi_restore 27 356 addi sp, sp, -64 357 .cfi_def_cfa_offset 64 358 li t1, -16 359.Ls10: 360 sw s10, 16(sp) 361 .cfi_offset 26, -48 362 sw s9, 20(sp) 363 .cfi_offset 25, -44 364 sw s8, 24(sp) 365 .cfi_offset 24, -40 366 sw s7, 28(sp) 367 .cfi_offset 23, -36 368 j .Ls6 369 370FUNC_BEGIN (__riscv_save_7) 371FUNC_BEGIN (__riscv_save_6) 372FUNC_BEGIN (__riscv_save_5) 373FUNC_BEGIN (__riscv_save_4) 374 .cfi_restore 23 375 .cfi_restore 24 376 .cfi_restore 25 377 .cfi_restore 26 378 .cfi_restore 27 379 addi sp, sp, -64 380 .cfi_def_cfa_offset 64 381 li t1, -32 382.Ls6: 383 sw s6, 32(sp) 384 .cfi_offset 22, -32 385 sw s5, 36(sp) 386 .cfi_offset 21, -28 387 sw s4, 40(sp) 388 .cfi_offset 20, -24 389 sw s3, 44(sp) 390 .cfi_offset 19, -20 391 sw s2, 48(sp) 392 .cfi_offset 18, -16 393 sw s1, 52(sp) 394 .cfi_offset 9, -12 395 sw s0, 56(sp) 396 .cfi_offset 8, -8 397 sw ra, 60(sp) 398 .cfi_offset 1, -4 399 # CFA info is not correct in next 2 instruction since t1's 400 # value is depend on how may register really save. 401 sub sp, sp, t1 402 jr t0 403 .cfi_endproc 404FUNC_END (__riscv_save_12) 405FUNC_END (__riscv_save_11) 406FUNC_END (__riscv_save_10) 407FUNC_END (__riscv_save_9) 408FUNC_END (__riscv_save_8) 409FUNC_END (__riscv_save_7) 410FUNC_END (__riscv_save_6) 411FUNC_END (__riscv_save_5) 412FUNC_END (__riscv_save_4) 413 414FUNC_BEGIN (__riscv_save_3) 415FUNC_BEGIN (__riscv_save_2) 416FUNC_BEGIN (__riscv_save_1) 417FUNC_BEGIN (__riscv_save_0) 418 .cfi_startproc 419 # __riscv_save_* routine use t0/x5 as return address 420 .cfi_return_column 5 421 addi sp, sp, -16 422 .cfi_def_cfa_offset 16 423 sw s2, 0(sp) 424 sw s1, 4(sp) 425 .cfi_offset 9, -16 426 sw s0, 8(sp) 427 .cfi_offset 8, -8 428 sw ra, 12(sp) 429 .cfi_offset 1, -4 430 jr t0 431 .cfi_endproc 432FUNC_END (__riscv_save_3) 433FUNC_END (__riscv_save_2) 434FUNC_END (__riscv_save_1) 435FUNC_END (__riscv_save_0) 436 437FUNC_BEGIN (__riscv_restore_12) 438 .cfi_startproc 439 .cfi_def_cfa_offset 64 440 .cfi_offset 27, -52 441 .cfi_offset 26, -48 442 .cfi_offset 25, -44 443 .cfi_offset 24, -40 444 .cfi_offset 23, -36 445 .cfi_offset 22, -32 446 .cfi_offset 21, -28 447 .cfi_offset 20, -24 448 .cfi_offset 19, -20 449 .cfi_offset 18, -16 450 .cfi_offset 9, -12 451 .cfi_offset 8, -8 452 .cfi_offset 1, -4 453 lw s11, 12(sp) 454 .cfi_restore 27 455 addi sp, sp, 16 456 457FUNC_BEGIN (__riscv_restore_11) 458FUNC_BEGIN (__riscv_restore_10) 459FUNC_BEGIN (__riscv_restore_9) 460FUNC_BEGIN (__riscv_restore_8) 461 .cfi_restore 27 462 .cfi_def_cfa_offset 48 463 lw s10, 0(sp) 464 .cfi_restore 26 465 lw s9, 4(sp) 466 .cfi_restore 25 467 lw s8, 8(sp) 468 .cfi_restore 24 469 lw s7, 12(sp) 470 .cfi_restore 23 471 addi sp, sp, 16 472 473FUNC_BEGIN (__riscv_restore_7) 474FUNC_BEGIN (__riscv_restore_6) 475FUNC_BEGIN (__riscv_restore_5) 476FUNC_BEGIN (__riscv_restore_4) 477 .cfi_restore 23 478 .cfi_restore 24 479 .cfi_restore 25 480 .cfi_restore 26 481 .cfi_restore 27 482 .cfi_def_cfa_offset 32 483 lw s6, 0(sp) 484 .cfi_restore 22 485 lw s5, 4(sp) 486 .cfi_restore 21 487 lw s4, 8(sp) 488 .cfi_restore 20 489 lw s3, 12(sp) 490 .cfi_restore 19 491 addi sp, sp, 16 492 493FUNC_BEGIN (__riscv_restore_3) 494FUNC_BEGIN (__riscv_restore_2) 495FUNC_BEGIN (__riscv_restore_1) 496FUNC_BEGIN (__riscv_restore_0) 497 .cfi_restore 19 498 .cfi_restore 20 499 .cfi_restore 21 500 .cfi_restore 22 501 .cfi_restore 24 502 .cfi_restore 25 503 .cfi_restore 26 504 .cfi_restore 27 505 .cfi_def_cfa_offset 16 506 lw s2, 0(sp) 507 .cfi_restore 18 508 lw s1, 4(sp) 509 .cfi_restore 9 510 lw s0, 8(sp) 511 .cfi_restore 8 512 lw ra, 12(sp) 513 .cfi_restore 1 514 addi sp, sp, 16 515 .cfi_def_cfa_offset 0 516 ret 517 .cfi_endproc 518FUNC_END (__riscv_restore_12) 519FUNC_END (__riscv_restore_11) 520FUNC_END (__riscv_restore_10) 521FUNC_END (__riscv_restore_9) 522FUNC_END (__riscv_restore_8) 523FUNC_END (__riscv_restore_7) 524FUNC_END (__riscv_restore_6) 525FUNC_END (__riscv_restore_5) 526FUNC_END (__riscv_restore_4) 527FUNC_END (__riscv_restore_3) 528FUNC_END (__riscv_restore_2) 529FUNC_END (__riscv_restore_1) 530FUNC_END (__riscv_restore_0) 531 532#endif /* __riscv_32e */ 533 534#endif /* __riscv_xlen == 64 */ 535