ObjFW  forwarding-powerpc64-elf-v2.S at [f6cc2092af]

File src/forwarding/forwarding-powerpc64-elf-v2.S artifact 3dd02eb036 part of check-in f6cc2092af


/*
 * Copyright (c) 2008-2024 Jonathan Schleifer <js@nil.im>
 *
 * All rights reserved.
 *
 * This program is free software: you can redistribute it and/or modify it
 * under the terms of the GNU Lesser General Public License version 3.0 only,
 * as published by the Free Software Foundation.
 *
 * This program is distributed in the hope that it will be useful, but WITHOUT
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License
 * version 3.0 for more details.
 *
 * You should have received a copy of the GNU Lesser General Public License
 * version 3.0 along with this program. If not, see
 * <https://www.gnu.org/licenses/>.
 */

#include "config.h"

#include "platform.h"

.abiversion 2

.globl OFForward
.globl OFForward_stret

.section .text
OFForward:
	.cfi_startproc
	addis	%r2, %r12, .TOC.-OFForward@ha
	addi	%r2, %r2, .TOC.-OFForward@l
.localentry OFForward, .-OFForward
	mflr	%r0
	std	%r0, 16(%r1)
	stdu	%r1, -160(%r1)
	.cfi_def_cfa_offset 160
	.cfi_offset lr, 16
	std	%r2, 24(%r1)

	/* Save all arguments */
	std	%r3, 32(%r1)
	std	%r4, 40(%r1)
	std	%r5, 48(%r1)
	std	%r6, 56(%r1)
	std	%r7, 64(%r1)
	std	%r8, 72(%r1)
	std	%r9, 80(%r1)
	std	%r10, 88(%r1)

	/* Save all floating point arguments */
	stfd	%f1, 96(%r1)
	stfd	%f2, 104(%r1)
	stfd	%f3, 112(%r1)
	stfd	%f4, 120(%r1)
	stfd	%f5, 128(%r1)
	stfd	%f6, 136(%r1)
	stfd	%f7, 144(%r1)
	stfd	%f8, 152(%r1)

	bl	object_getClass
	nop

	addis	%r4, %r2, .Lsel_forwardingTargetForSelector_@toc@ha
	addi	%r4, %r4, .Lsel_forwardingTargetForSelector_@toc@l
	bl	class_respondsToSelector
	nop

	cmpdi	%r3, 0
	beq-	0f

	ld	%r3, 32(%r1)
	addis	%r4, %r2, .Lsel_forwardingTargetForSelector_@toc@ha
	addi	%r4, %r4, .Lsel_forwardingTargetForSelector_@toc@l
	bl	objc_msg_lookup
	nop
	mr	%r12, %r3

	ld	%r3, 32(%r1)
	addis	%r4, %r2, .Lsel_forwardingTargetForSelector_@toc@ha
	addi	%r4, %r4, .Lsel_forwardingTargetForSelector_@toc@l
	ld	%r5, 40(%r1)
	mtctr	%r12
	bctrl
	ld	%r2, 24(%r1)

	cmpdi	%r3, 0
	beq-	0f
	ld	%r4, 32(%r1)
	cmpw	%r3, %r4
	beq-	0f

	std	%r3, 32(%r1)

	ld	%r4, 40(%r1)
	bl	objc_msg_lookup
	nop
	mr	%r12, %r3

	/* Restore all arguments */
	ld	%r3, 32(%r1)
	ld	%r4, 40(%r1)
	ld	%r5, 48(%r1)
	ld	%r6, 56(%r1)
	ld	%r7, 64(%r1)
	ld	%r8, 72(%r1)
	ld	%r9, 80(%r1)
	ld	%r10, 88(%r1)

	/* Restore all floating point arguments */
	lfd	%f1, 96(%r1)
	lfd	%f2, 104(%r1)
	lfd	%f3, 112(%r1)
	lfd	%f4, 120(%r1)
	lfd	%f5, 128(%r1)
	lfd	%f6, 136(%r1)
	lfd	%f7, 144(%r1)
	lfd	%f8, 152(%r1)

	addi	%r1, %r1, 160
	ld	%r0, 16(%r1)
	mtlr	%r0

	mtctr	%r12
	bctr

0:
	ld	%r3, 32(%r1)
	ld	%r4, 40(%r1)

	bl	OFMethodNotFound
	nop

	addi	%r1, %r1, 160
	lwz	%r0, 16(%r1)
	mtlr	%r0

	blr
	.cfi_endproc
.type OFForward, @function
.size OFForward, .-OFForward

OFForward_stret:
	.cfi_startproc
	addis	%r2, %r12, .TOC.-OFForward_stret@ha
	addi	%r2, %r2, .TOC.-OFForward_stret@l
.localentry OFForward_stret, .-OFForward_stret
	mflr	%r0
	std	%r0, 16(%r1)
	stdu	%r1, -160(%r1)
	.cfi_def_cfa_offset 160
	.cfi_offset lr, 16
	std	%r2, 24(%r1)

	/* Save all arguments */
	std	%r3, 32(%r1)
	std	%r4, 40(%r1)
	std	%r5, 48(%r1)
	std	%r6, 56(%r1)
	std	%r7, 64(%r1)
	std	%r8, 72(%r1)
	std	%r9, 80(%r1)
	std	%r10, 88(%r1)

	/* Save all floating point arguments */
	stfd	%f1, 96(%r1)
	stfd	%f2, 104(%r1)
	stfd	%f3, 112(%r1)
	stfd	%f4, 120(%r1)
	stfd	%f5, 128(%r1)
	stfd	%f6, 136(%r1)
	stfd	%f7, 144(%r1)
	stfd	%f8, 152(%r1)

	mr	%r3, %r4
	bl	object_getClass
	nop

	addis	%r4, %r2, .Lsel_forwardingTargetForSelector_@toc@ha
	addi	%r4, %r4, .Lsel_forwardingTargetForSelector_@toc@l
	bl	class_respondsToSelector
	nop

	cmpdi	%r3, 0
	beq-	0f

	ld	%r3, 40(%r1)
	addis	%r4, %r2, .Lsel_forwardingTargetForSelector_@toc@ha
	addi	%r4, %r4, .Lsel_forwardingTargetForSelector_@toc@l
	bl	objc_msg_lookup
	nop
	mr	%r12, %r3

	ld	%r3, 40(%r1)
	addis	%r4, %r2, .Lsel_forwardingTargetForSelector_@toc@ha
	addi	%r4, %r4, .Lsel_forwardingTargetForSelector_@toc@l
	ld	%r5, 48(%r1)
	mtctr	%r12
	bctrl
	ld	%r2, 24(%r1)

	cmpdi	%r3, 0
	beq-	0f
	ld	%r4, 40(%r1)
	cmpw	%r3, %r4
	beq-	0f

	std	%r3, 40(%r1)

	ld	%r4, 48(%r1)
	bl	objc_msg_lookup_stret
	nop
	mr	%r12, %r3

	/* Restore all arguments */
	ld	%r3, 32(%r1)
	ld	%r4, 40(%r1)
	ld	%r5, 48(%r1)
	ld	%r6, 56(%r1)
	ld	%r7, 64(%r1)
	ld	%r8, 72(%r1)
	ld	%r9, 80(%r1)
	ld	%r10, 88(%r1)

	/* Restore all floating point arguments */
	lfd	%f1, 96(%r1)
	lfd	%f2, 104(%r1)
	lfd	%f3, 112(%r1)
	lfd	%f4, 120(%r1)
	lfd	%f5, 128(%r1)
	lfd	%f6, 136(%r1)
	lfd	%f7, 144(%r1)
	lfd	%f8, 152(%r1)

	addi	%r1, %r1, 160
	ld	%r0, 16(%r1)
	mtlr	%r0

	mtctr	%r12
	bctr

0:
	ld	%r3, 32(%r1)
	ld	%r4, 40(%r1)
	ld	%r5, 48(%r1)

	bl	OFMethodNotFound_stret
	nop

	addi	%r1, %r1, 160
	lwz	%r0, 16(%r1)
	mtlr	%r0

	blr
	.cfi_endproc
.type OFForward_stret, @function
.size OFForward_stret, .-OFForward_stret

.Linit:
	addis	%r2, %r12, .TOC.-.Linit@ha
	addi	%r2, %r2, .TOC.-.Linit@l
.localentry .Linit, .-.Linit
	mflr	%r0
	std	%r0, 16(%r1)
	stdu	%r1, -32(%r1)

	addis	%r3, %r2, .Lmodule@toc@ha
	addi	%r3, %r3, .Lmodule@toc@l
	bl	__objc_exec_class
	nop

	addi	%r1, %r1, 32
	ld	%r0, 16(%r1)

	mtlr	%r0
	blr

.section .ctors, "aw", @progbits
	.quad .Linit

.section .rodata
.Lstr_forwardingTargetForSelector_:
	.asciz "forwardingTargetForSelector:"

.section .data
.Lsel_forwardingTargetForSelector_:
	.quad .Lstr_forwardingTargetForSelector_, 0
	.quad 0, 0
.Lsymtab:
	.quad 0, .Lsel_forwardingTargetForSelector_
	.short 0, 0
	.long 0
	.quad 0
.Lmodule:
	.quad 8, 32, 0, .Lsymtab

#if defined(OF_LINUX) || defined(OF_HAIKU) || defined(OF_HURD)
.section .note.GNU-stack, "", @progbits
#endif