1//===-- divsi3.S - 32-bit signed integer divide ---------------------------===// 2// 3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4// See https://llvm.org/LICENSE.txt for license information. 5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6// 7//===----------------------------------------------------------------------===// 8// 9// This file implements the __divsi3 (32-bit signed integer divide) function 10// for the ARM architecture as a wrapper around the unsigned routine. 11// 12//===----------------------------------------------------------------------===// 13 14#include "../assembly.h" 15 16#define ESTABLISH_FRAME \ 17 push {r4, r7, lr} ;\ 18 add r7, sp, #4 19#define CLEAR_FRAME_AND_RETURN \ 20 pop {r4, r7, pc} 21 22 .syntax unified 23 .text 24 DEFINE_CODE_STATE 25 26 .p2align 3 27// Ok, APCS and AAPCS agree on 32 bit args, so it's safe to use the same routine. 28DEFINE_AEABI_FUNCTION_ALIAS(__aeabi_idiv, __divsi3) 29 30@ int __divsi3(int divident, int divisor) 31@ Calculate and return the quotient of the (signed) division. 32 33DEFINE_COMPILERRT_FUNCTION(__divsi3) 34#if __ARM_ARCH_EXT_IDIV__ 35 tst r1,r1 36 beq LOCAL_LABEL(divzero) 37 sdiv r0, r0, r1 38 bx lr 39LOCAL_LABEL(divzero): 40 // Use movs for compatibility with v8-m.base. 41 movs r0,#0 42 bx lr 43#else 44ESTABLISH_FRAME 45// Set aside the sign of the quotient. 46# if defined(USE_THUMB_1) 47 movs r4, r0 48 eors r4, r1 49# else 50 eor r4, r0, r1 51# endif 52// Take absolute value of a and b via abs(x) = (x^(x >> 31)) - (x >> 31). 53# if defined(USE_THUMB_1) 54 asrs r2, r0, #31 55 asrs r3, r1, #31 56 eors r0, r2 57 eors r1, r3 58 subs r0, r0, r2 59 subs r1, r1, r3 60# else 61 eor r2, r0, r0, asr #31 62 eor r3, r1, r1, asr #31 63 sub r0, r2, r0, asr #31 64 sub r1, r3, r1, asr #31 65# endif 66// abs(a) / abs(b) 67 bl SYMBOL_NAME(__udivsi3) 68// Apply sign of quotient to result and return. 69# if defined(USE_THUMB_1) 70 asrs r4, #31 71 eors r0, r4 72 subs r0, r0, r4 73# else 74 eor r0, r0, r4, asr #31 75 sub r0, r0, r4, asr #31 76# endif 77 CLEAR_FRAME_AND_RETURN 78#endif 79END_COMPILERRT_FUNCTION(__divsi3) 80 81NO_EXEC_STACK_DIRECTIVE 82 83