xref: /minix3/common/lib/libc/arch/arm/quad/__aeabi_uldivmod.S (revision 0a6a1f1d05b60e214de2f05a7310ddd1f0e590e7)
1f14fb602SLionel Sambuc/*-
2f14fb602SLionel Sambuc * Copyright (c) 2012 The NetBSD Foundation, Inc.
3f14fb602SLionel Sambuc * All rights reserved.
4f14fb602SLionel Sambuc *
5f14fb602SLionel Sambuc * This code is derived from software contributed to The NetBSD Foundation
6f14fb602SLionel Sambuc * by Matt Thomas of 3am Software Foundry.
7f14fb602SLionel Sambuc *
8f14fb602SLionel Sambuc * Redistribution and use in source and binary forms, with or without
9f14fb602SLionel Sambuc * modification, are permitted provided that the following conditions
10f14fb602SLionel Sambuc * are met:
11f14fb602SLionel Sambuc * 1. Redistributions of source code must retain the above copyright
12f14fb602SLionel Sambuc *    notice, this list of conditions and the following disclaimer.
13f14fb602SLionel Sambuc * 2. Redistributions in binary form must reproduce the above copyright
14f14fb602SLionel Sambuc *    notice, this list of conditions and the following disclaimer in the
15f14fb602SLionel Sambuc *    documentation and/or other materials provided with the distribution.
16f14fb602SLionel Sambuc *
17f14fb602SLionel Sambuc * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
18f14fb602SLionel Sambuc * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
19f14fb602SLionel Sambuc * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
20f14fb602SLionel Sambuc * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
21f14fb602SLionel Sambuc * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
22f14fb602SLionel Sambuc * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
23f14fb602SLionel Sambuc * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
24f14fb602SLionel Sambuc * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
25f14fb602SLionel Sambuc * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
26f14fb602SLionel Sambuc * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27f14fb602SLionel Sambuc * POSSIBILITY OF SUCH DAMAGE.
28f14fb602SLionel Sambuc */
29f14fb602SLionel Sambuc
30f14fb602SLionel Sambuc#include <machine/asm.h>
31f14fb602SLionel Sambuc
32*0a6a1f1dSLionel SambucRCSID("$NetBSD: __aeabi_uldivmod.S,v 1.9 2014/05/06 16:02:11 joerg Exp $")
33f14fb602SLionel Sambuc
34f14fb602SLionel Sambuc/*
35f14fb602SLionel Sambuc * typedef struct { unsigned long long quo, rem } ulldiv_t;
36f14fb602SLionel Sambuc * __value_in_regs ulldiv_t __aeabi_uldivmod(unsigned long long n,
37f14fb602SLionel Sambuc *	unsigned long long d);
38f14fb602SLionel Sambuc */
39f14fb602SLionel Sambuc
40f14fb602SLionel SambucENTRY(__aeabi_uldivmod)
4184d9c625SLionel Sambuc#ifdef __ARM_EABI__
42*0a6a1f1dSLionel Sambuc# if !defined(__ARM_DWARF_EH__)
4384d9c625SLionel Sambuc	.fnstart
44*0a6a1f1dSLionel Sambuc#endif
4584d9c625SLionel Sambuc	.cfi_startproc
4684d9c625SLionel Sambuc#endif
4784d9c625SLionel Sambuc#if !defined(_KERNEL) && !defined(_STANDALONE)
4884d9c625SLionel Sambuc#if !defined(__thumb__)
4984d9c625SLionel Sambuc	orrs	ip, r2, r3
5084d9c625SLionel Sambuc	beq	.Ldivbyzero
5184d9c625SLionel Sambuc#elif defined(_ARM_ARCH_T2)
5284d9c625SLionel Sambuc	cbnz	r2, 1f
5384d9c625SLionel Sambuc	cbz	r3, .Ldivbyzero
5484d9c625SLionel Sambuc1:
5584d9c625SLionel Sambuc#else
5684d9c625SLionel Sambuc	cmp	r2, #0
5784d9c625SLionel Sambuc	bne	1f
5884d9c625SLionel Sambuc	cmp	r3, #0
5984d9c625SLionel Sambuc	beq	.Ldivbyzero
6084d9c625SLionel Sambuc1:
6184d9c625SLionel Sambuc#endif
6284d9c625SLionel Sambuc#endif
6384d9c625SLionel Sambuc
64f14fb602SLionel Sambuc	push	{r4,lr}
6584d9c625SLionel Sambuc#ifdef __ARM_EABI__
66*0a6a1f1dSLionel Sambuc# if !defined(__ARM_DWARF_EH__)
6784d9c625SLionel Sambuc	.save	{r4,lr}
68*0a6a1f1dSLionel Sambuc# endif
6984d9c625SLionel Sambuc	.cfi_def_cfa_offset 8
7084d9c625SLionel Sambuc	.cfi_offset 14, -4
7184d9c625SLionel Sambuc	.cfi_offset 4, -8
7284d9c625SLionel Sambuc#endif
7384d9c625SLionel Sambuc	sub	sp, sp, #16
7484d9c625SLionel Sambuc#ifdef __ARM_EABI__
7584d9c625SLionel Sambuc	.cfi_def_cfa_offset 24
7684d9c625SLionel Sambuc#endif
7784d9c625SLionel Sambuc#if !defined(__thumb__) || defined(_ARM_ARCH_T2)
7884d9c625SLionel Sambuc	add	r4, sp, #8
7984d9c625SLionel Sambuc#else
80f14fb602SLionel Sambuc	mov	r4, sp
8184d9c625SLionel Sambuc	adds	r4, r4, #8
8284d9c625SLionel Sambuc#endif
8384d9c625SLionel Sambuc	str	r4, [sp]
84f14fb602SLionel Sambuc	bl	PLT_SYM(__qdivrem)
8584d9c625SLionel Sambuc	add	sp, sp, #8
8684d9c625SLionel Sambuc#ifdef __ARM_EABI__
8784d9c625SLionel Sambuc	.cfi_def_cfa_offset 16
8884d9c625SLionel Sambuc	.cfi_offset 3, -12
8984d9c625SLionel Sambuc	.cfi_offset 2, -16
9084d9c625SLionel Sambuc#endif
91f14fb602SLionel Sambuc	/*
92f14fb602SLionel Sambuc	 * The remainder is already on the stack just waiting to be popped
93f14fb602SLionel Sambuc	 * into r2/r3.
94f14fb602SLionel Sambuc	 */
9584d9c625SLionel Sambuc	pop	{r2-r4,pc}
9684d9c625SLionel Sambuc
9784d9c625SLionel Sambuc#if !defined(_KERNEL) && !defined(_STANDALONE)
9884d9c625SLionel Sambuc.Ldivbyzero:
9984d9c625SLionel Sambuc	push	{r0-r1,r4,lr}
10084d9c625SLionel Sambuc#ifdef __ARM_EABI__
101*0a6a1f1dSLionel Sambuc# if !defined(__ARM_DWARF_EH__)
10284d9c625SLionel Sambuc	.save	{r0-r1,r4,lr}
103*0a6a1f1dSLionel Sambuc# endif
10484d9c625SLionel Sambuc	.cfi_def_cfa_offset 16
10584d9c625SLionel Sambuc	.cfi_offset 14, -4
10684d9c625SLionel Sambuc	.cfi_offset 4, -8
10784d9c625SLionel Sambuc#endif
10884d9c625SLionel Sambuc#ifdef __thumb__
10984d9c625SLionel Sambuc	movs	r0, #0
11084d9c625SLionel Sambuc	mvns	r0, r0
11184d9c625SLionel Sambuc#else
11284d9c625SLionel Sambuc	mvn	r0, #0
11384d9c625SLionel Sambuc#endif
114*0a6a1f1dSLionel Sambuc	movs	r1, r0
11584d9c625SLionel Sambuc	bl	PLT_SYM(__aeabi_ldiv0)
11684d9c625SLionel Sambuc	pop	{r2-r4,pc}
11784d9c625SLionel Sambuc#endif
11884d9c625SLionel Sambuc#ifdef __ARM_EABI__
11984d9c625SLionel Sambuc	.cfi_endproc
120*0a6a1f1dSLionel Sambuc# if !defined(__ARM_DWARF_EH__)
12184d9c625SLionel Sambuc	.fnend
12284d9c625SLionel Sambuc# endif
123*0a6a1f1dSLionel Sambuc#endif
124f14fb602SLionel SambucEND(__aeabi_uldivmod)
125