NetBSD-5.0.2/lib/libpthread/arch/hppa/_context_u.S

Compare this file to the similar file:
Show the results in this format:

/*	$NetBSD: _context_u.S,v 1.4 2008/08/11 21:45:24 skrll Exp $	*/

/*
 * Copyright (c) 2001 The NetBSD Foundation, Inc.
 * All rights reserved.
 *
 * This code is derived from software contributed to The NetBSD Foundation
 * by Wayne Knowles
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 * 1. Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer.
 * 2. Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in the
 *    documentation and/or other materials provided with the distribution.
 *
 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
 * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
 * POSSIBILITY OF SUCH DAMAGE.
 */

#include <machine/asm.h>
#include <machine/mcontext.h>
#include "assym.h"

/*
 * Define:
 *	int _getcontext_u(ucontext_t *ctx)
 *		Store the current context in the provided ctx structure.
 *		[only store the callee-saved registers]
 *	int _setcontext_u(const ucontext_t *ctx)
 *		Restore the current context from the provided ctx structure.
 *	int _swapcontext_u(ucontext_t *from_ctx, const ucontext_t *to_ctx)
 *		First, store the current context into from_ctx and then
 *		restore the current context from the to_ctx.
 */

/* Macro to Save the callee-save register set */
#define GETC(reg)					! \
	stw	%r3,  (UC_REGS +  3 * SZREG)(reg)	! \
	stw	%r4,  (UC_REGS +  4 * SZREG)(reg)	! \
	stw	%r5,  (UC_REGS +  5 * SZREG)(reg)	! \
	stw	%r6,  (UC_REGS +  6 * SZREG)(reg)	! \
	stw	%r7,  (UC_REGS +  7 * SZREG)(reg)	! \
	stw	%r8,  (UC_REGS +  8 * SZREG)(reg)	! \
	stw	%r9,  (UC_REGS +  9 * SZREG)(reg)	! \
	stw	%r10, (UC_REGS + 10 * SZREG)(reg)	! \
	stw	%r11, (UC_REGS + 11 * SZREG)(reg)	! \
	stw	%r12, (UC_REGS + 12 * SZREG)(reg)	! \
	stw	%r13, (UC_REGS + 13 * SZREG)(reg)	! \
	stw	%r14, (UC_REGS + 14 * SZREG)(reg)	! \
	stw	%r15, (UC_REGS + 15 * SZREG)(reg)	! \
	stw	%r16, (UC_REGS + 16 * SZREG)(reg)	! \
	stw	%r17, (UC_REGS + 17 * SZREG)(reg)	! \
	stw	%r18, (UC_REGS + 18 * SZREG)(reg)	! \
	stw	%dp,  (UC_REGS + 27 * SZREG)(reg)	! \
	stw	%sp,  (UC_REGS + 30 * SZREG)(reg)	! \
	stw	%rp,  (UC_REGS +  2 * SZREG)(reg)	! \
	stw	%rp,  (UC_REGS + 35 * SZREG)(reg)	! \
	ldil	L%_UC_USER, %r1				! \
	ldo	_UC_CPU(%r1), %r1 			! \
	stw	%r1, (UC_FLAGS)(reg)

#ifdef PIC
#define LDADDR						! \
	addil	LT%_C_LABEL(setcontext), %r19		! \
	ldo	RT%_C_LABEL(setcontext)(%r1), %r1	! \
	bb,<,n	%r1, 30, 99f				! \
	depi	0, 31, 2, %r1				! \
	ldw	0(%r1), %rp				! \
	ldw	4(%r1), %r19				! \
99:
#else
#define LDADDR						! \
	ldil	L%_C_LABEL(setcontext), %rp		! \
	ldo	R%_C_LABEL(setcontext)(%rp), %rp
#endif

#define SETC(reg)					! \
	ldw	(UC_FLAGS)(reg), %r1			! \
	bb,>=,n	%r1, (31 - _UC_USER_BIT), 1f		! \
	ldw	(UC_REGS +  3 * SZREG)(reg), %r3	! \
	ldw	(UC_REGS +  4 * SZREG)(reg), %r4	! \
	ldw	(UC_REGS +  5 * SZREG)(reg), %r5	! \
	ldw	(UC_REGS +  6 * SZREG)(reg), %r6	! \
	ldw	(UC_REGS +  7 * SZREG)(reg), %r7	! \
	ldw	(UC_REGS +  8 * SZREG)(reg), %r8	! \
	ldw	(UC_REGS +  9 * SZREG)(reg), %r9	! \
	ldw	(UC_REGS + 10 * SZREG)(reg), %r10	! \
	ldw	(UC_REGS + 11 * SZREG)(reg), %r11	! \
	ldw	(UC_REGS + 12 * SZREG)(reg), %r12	! \
	ldw	(UC_REGS + 13 * SZREG)(reg), %r13	! \
	ldw	(UC_REGS + 14 * SZREG)(reg), %r14	! \
	ldw	(UC_REGS + 15 * SZREG)(reg), %r15	! \
	ldw	(UC_REGS + 16 * SZREG)(reg), %r16	! \
	ldw	(UC_REGS + 17 * SZREG)(reg), %r17	! \
	ldw	(UC_REGS + 18 * SZREG)(reg), %r18	! \
	ldw	(UC_REGS + 27 * SZREG)(reg), %dp	! \
	ldw	(UC_REGS + 30 * SZREG)(reg), %sp	! \
	ldw	(UC_REGS +  2 * SZREG)(reg), %rp	! \
	/* part procedure call, part RET */		! \
	ldw	(UC_REGS + _REG_PCOQH * SZREG)(reg), %r1! \
	bv,n	%r0(%r1)				! \
	/* NOTREACHED */				! \
							! \
1:							! \
	LDADDR						! \
	bv,n	%r0(%rp)				! \
	/* NOTREACHED */

ENTRY(_getcontext_u, 0)
	GETC(%arg0)
	bv	%r0(%rp)
	copy	%r0, %ret0
EXIT(_getcontext_u)

ENTRY(_setcontext_u, 0)
	SETC(%arg0)
EXIT(_setcontext_u)

ENTRY(_swapcontext_u, 0)
	GETC(%arg0)
	SETC(%arg1)
EXIT(_swapcontext_u)

LEAF_ENTRY(pthread__ras_simple_lock_init)
	ldi	1,%ret0			/* 1 == unlocked */
	stw	%ret0,0(%arg0)
	stw	%ret0,4(%arg0)
	stw	%ret0,8(%arg0)
	stw	%ret0,12(%arg0)
	bv,n	%r0(%rp)
EXIT(pthread__ras_simple_lock_init)

	.global pthread__lock_ras_start
	.global pthread__lock_ras_end

LEAF_ENTRY(pthread__ras_simple_lock_try)
	ldo	15(%arg0),%arg0
	depi	0,31,4,%arg0

pthread__lock_ras_start:
	ldw	0(%arg0),%ret0
	stw	%r0,0(%arg0)		/* 0 == locked */
pthread__lock_ras_end:

	comiclr,= 0,%ret0,%ret0		/* if locked return 0 */
	ldi	1,%ret0			/* else return 1 */
	bv,n	%r0(%rp)
EXIT(pthread__ras_simple_lock_try)


LEAF_ENTRY(pthread__ras_simple_unlock)
	ldo	15(%arg0),%arg0
	depi	0,31,4,%arg0
	ldi	1,%ret0			/* 1 == unlocked */
	bv	%r0(%rp)
	stw	%ret0,0(%arg0)
EXIT(pthread__ras_simple_unlock)