cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

udivsi3.S (1958B)


      1/* SPDX-License-Identifier: GPL-2.0 */
      2#include <linux/linkage.h>
      3
      4/*
      5* Unsigned divide operation.
      6*	Input :	Divisor in Reg r5
      7*		Dividend in Reg r6
      8*	Output: Result in Reg r3
      9*/
     10
     11	.text
     12	.globl	__udivsi3
     13	.type __udivsi3, @function
     14	.ent __udivsi3
     15
     16__udivsi3:
     17
     18	.frame	r1, 0, r15
     19
     20	addik	r1, r1, -12
     21	swi	r29, r1, 0
     22	swi	r30, r1, 4
     23	swi	r31, r1, 8
     24
     25	beqi	r6, div_by_zero /* div_by_zero /* division error */
     26	beqid	r5, result_is_zero /* result is zero */
     27	addik	r30, r0, 0 /* clear mod */
     28	addik	r29, r0, 32 /* initialize the loop count */
     29
     30/* check if r6 and r5 are equal - if yes, return 1 */
     31	rsub	r18, r5, r6
     32	beqid	r18, return_here
     33	addik	r3, r0, 1
     34
     35/* check if (uns)r6 is greater than (uns)r5. in that case, just return 0 */
     36	xor	r18, r5, r6
     37	bgeid	r18, 16
     38	add	r3, r0, r0 /* we would anyways clear r3 */
     39	blti	r6, return_here /* r6[bit 31 = 1] hence is greater */
     40	bri	checkr6
     41	rsub	r18, r6, r5 /* microblazecmp */
     42	blti	r18, return_here
     43
     44/* if r6 [bit 31] is set, then return result as 1 */
     45checkr6:
     46	bgti	r6, div0
     47	brid	return_here
     48	addik	r3, r0, 1
     49
     50/* first part try to find the first '1' in the r5 */
     51div0:
     52	blti	r5, div2
     53div1:
     54	add	r5, r5, r5 /* left shift logical r5 */
     55	bgtid	r5, div1
     56	addik	r29, r29, -1
     57div2:
     58/* left shift logical r5 get the '1' into the carry */
     59	add	r5, r5, r5
     60	addc	r30, r30, r30 /* move that bit into the mod register */
     61	rsub	r31, r6, r30 /* try to subtract (r30 a r6) */
     62	blti	r31, mod_too_small
     63/* move the r31 to mod since the result was positive */
     64	or	r30, r0, r31
     65	addik	r3, r3, 1
     66mod_too_small:
     67	addik	r29, r29, -1
     68	beqi	r29, loop_end
     69	add	r3, r3, r3 /* shift in the '1' into div */
     70	bri	div2 /* div2 */
     71loop_end:
     72	bri	return_here
     73div_by_zero:
     74result_is_zero:
     75	or	r3, r0, r0 /* set result to 0 */
     76return_here:
     77/* restore values of csrs and that of r3 and the divisor and the dividend */
     78	lwi	r29, r1, 0
     79	lwi	r30, r1, 4
     80	lwi	r31, r1, 8
     81	rtsd	r15, 8
     82	addik	r1, r1, 12
     83
     84.size __udivsi3, . - __udivsi3
     85.end __udivsi3