11da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/*
21da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds *  linux/arch/m32r/lib/memset.S
31da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds *
41da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds *  Copyright (C) 2001,2002  Hiroyuki Kondo, and Hirokazu Takata
51da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds *  Copyright (C) 2004  Hirokazu Takata
61da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds *
71da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds *  void *memset(void *dst, int val, int len);
81da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds *
91da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds *        dst: r0
101da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds *        val: r1
111da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds *        len: r2
121da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds *        ret: r0
131da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds *
141da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */
151da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds
161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	.text
171da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	.global	memset
181da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds
191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#ifdef CONFIG_ISA_DUAL_ISSUE
201da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds
211da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	.align 4
221da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsmemset:
231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	mv      r4, r0		    ||	cmpz	r2
241da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	jc	r14
251da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	cmpui	r2, #16
261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bnc	qword_align_check
271da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	cmpui	r2, #4
281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bc	byte_set
291da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsword_align_check:			/* len >= 4 */
301da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	and3	r3, r4, #3
311da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	beqz	r3, word_set
321da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r3, #-4
331da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	neg	r3, r3			/* r3 = -(r3 - 4) */
341da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsalign_word:
351da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	stb	r1, @r4		    ||	addi	r4, #1
361da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r2, #-1		    ||	addi	r3, #-1
371da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bnez	r3, align_word
381da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	cmpui	r2, #4
391da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bc	byte_set
401da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsword_set:
411da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	and3	r1, r1, #0x00ff		/* r1: abababab <-- ??????ab */
421da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	sll3	r3, r1, #8
431da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	or	r1, r3		    ||	addi	r4, #-4
441da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	sll3	r3, r1, #16
451da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	or	r1, r3		    ||	addi	r2, #-4
461da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsword_set_loop:
471da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	st	r1, @+r4	    ||	addi	r2, #-4
481da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bgtz	r2, word_set_loop
491da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bnez	r2, byte_set_wrap
501da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	st	r1, @+r4
511da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	jmp	r14
521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds
531da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsqword_align_check:			/* len >= 16 */
541da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	and3	r3, r4, #15
551da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bnez	r3, word_align_check
561da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsqword_set:
571da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	and3	r1, r1, #0x00ff		/* r1: abababab <-- ??????ab */
581da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	sll3	r3, r1, #8
591da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	or	r1, r3		    ||	addi	r4, #-4
601da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	sll3	r3, r1, #16
611da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	or	r1, r3		    ||	ldi	r5, #16
621da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsqword_set_loop:
631da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	ld	r3, @(4,r4)		/* cache line allocate */
641da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	st	r1, @+r4	    ||	addi	r2, #-16
651da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	st	r1, @+r4	    ||	cmpu	r2, r5
661da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	st	r1, @+r4
671da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	st	r1, @+r4
681da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bnc	qword_set_loop	    ||  cmpz	r2
691da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	jc	r14
701da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsset_remainder:
711da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	cmpui	r2, #4
721da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bc	byte_set_wrap1
731da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r2, #-4
741da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bra	word_set_loop
751da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds
761da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsbyte_set_wrap:
771da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r2, #4
781da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	cmpz	r2
791da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	jc	r14
801da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsbyte_set_wrap1:
811da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r4, #4
821da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#if defined(CONFIG_ISA_M32R2)
831da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsbyte_set:
841da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r2, #-1		    ||	stb	r1, @r4+
851da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bnez	r2, byte_set
861da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#elif defined(CONFIG_ISA_M32R)
871da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsbyte_set:
881da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r2, #-1		    ||	stb	r1, @r4
891da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r4, #1
901da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bnez	r2, byte_set
911da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#else
921da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#error unknown isa configuration
931da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#endif
941da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsend_memset:
951da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	jmp	r14
961da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds
971da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#else /* not CONFIG_ISA_DUAL_ISSUE */
981da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds
991da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	.align 4
1001da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsmemset:
1011da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	mv      r4, r0
1021da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	beqz	r2, end_memset
1031da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	cmpui	r2, #16
1041da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bnc	qword_align_check
1051da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	cmpui	r2, #4
1061da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bc	byte_set
1071da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsword_align_check:			/* len >= 4 */
1081da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	and3	r3, r4, #3
1091da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	beqz	r3, word_set
1101da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r3, #-4
1111da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	neg	r3, r3			/* r3 = -(r3 - 4) */
1121da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsalign_word:
1131da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	stb	r1, @r4
1141da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r4, #1
1151da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r2, #-1
1161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r3, #-1
1171da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bnez	r3, align_word
1181da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	cmpui	r2, #4
1191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bc	byte_set
1201da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsword_set:
1211da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	and3	r1, r1, #0x00ff		/* r1: abababab <-- ??????ab */
1221da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	sll3	r3, r1, #8
1231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	or	r1, r3
1241da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	sll3	r3, r1, #16
1251da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	or	r1, r3
1261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r2, #-4
1271da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r4, #-4
1281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsword_set_loop:
1291da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	st	r1, @+r4
1301da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r2, #-4
1311da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bgtz    r2, word_set_loop
1321da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bnez	r2, byte_set_wrap
1331da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	st	r1, @+r4
1341da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	jmp	r14
1351da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds
1361da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsqword_align_check:			/* len >= 16 */
1371da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	and3	r3, r4, #15
1381da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bnez	r3, word_align_check
1391da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsqword_set:
1401da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	and3	r1, r1, #0x00ff		/* r1: abababab <-- ??????ab */
1411da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	sll3	r3, r1, #8
1421da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	or	r1, r3
1431da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	sll3	r3, r1, #16
1441da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	or	r1, r3
1451da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r4, #-4
1461da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsqword_set_loop:
1471da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	ld	r3, @(4,r4)		/* cache line allocate */
1481da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r2, #-16
1491da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	st	r1, @+r4
1501da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	st	r1, @+r4
1511da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	cmpui	r2, #16
1521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	st	r1, @+r4
1531da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	st	r1, @+r4
1541da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bnc	qword_set_loop
1551da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bnez	r2, set_remainder
1561da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	jmp	r14
1571da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsset_remainder:
1581da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	cmpui	r2, #4
1591da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bc	byte_set_wrap1
1601da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r2, #-4
1611da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bra	word_set_loop
1621da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds
1631da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsbyte_set_wrap:
1641da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r2, #4
1651da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	beqz	r2, end_memset
1661da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsbyte_set_wrap1:
1671da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r4, #4
1681da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsbyte_set:
1691da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r2, #-1
1701da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	stb	r1, @r4
1711da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	addi	r4, #1
1721da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	bnez	r2, byte_set
1731da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsend_memset:
1741da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	jmp	r14
1751da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds
1761da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#endif /* not CONFIG_ISA_DUAL_ISSUE */
1771da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds
1781da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds	.end
179