xref: /openbsd-src/lib/libc/arch/sh/gen/setjmp.S (revision 0ee2ce6736ef33439268a7e79bce705365b9c499)
1*0ee2ce67Sguenther/*	$OpenBSD: setjmp.S,v 1.4 2022/12/08 02:11:27 guenther Exp $	*/
2cf252584Smiod/*	$NetBSD: setjmp.S,v 1.10 2006/01/05 19:21:37 uwe Exp $	*/
3cf252584Smiod
4cf252584Smiod/*-
5cf252584Smiod * Copyright (c) 1990 The Regents of the University of California.
6cf252584Smiod * All rights reserved.
7cf252584Smiod *
8cf252584Smiod * This code is derived from software contributed to Berkeley by
9cf252584Smiod * William Jolitz.
10cf252584Smiod *
11cf252584Smiod * Redistribution and use in source and binary forms, with or without
12cf252584Smiod * modification, are permitted provided that the following conditions
13cf252584Smiod * are met:
14cf252584Smiod * 1. Redistributions of source code must retain the above copyright
15cf252584Smiod *    notice, this list of conditions and the following disclaimer.
16cf252584Smiod * 2. Redistributions in binary form must reproduce the above copyright
17cf252584Smiod *    notice, this list of conditions and the following disclaimer in the
18cf252584Smiod *    documentation and/or other materials provided with the distribution.
19cf252584Smiod * 3. Neither the name of the University nor the names of its contributors
20cf252584Smiod *    may be used to endorse or promote products derived from this software
21cf252584Smiod *    without specific prior written permission.
22cf252584Smiod *
23cf252584Smiod * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
24cf252584Smiod * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
25cf252584Smiod * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
26cf252584Smiod * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
27cf252584Smiod * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
28cf252584Smiod * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
29cf252584Smiod * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
30cf252584Smiod * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
31cf252584Smiod * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
32cf252584Smiod * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
33cf252584Smiod * SUCH DAMAGE.
34cf252584Smiod *
35cf252584Smiod *	from: @(#)setjmp.s	5.1 (Berkeley) 4/23/90
36cf252584Smiod */
37cf252584Smiod
3895146ac7Smiod#include "SYS.h"
3995146ac7Smiod
40cf252584Smiod#include <machine/setjmp.h>
41cf252584Smiod
42cf252584Smiod/*
43cf252584Smiod * C library -- setjmp, longjmp
44cf252584Smiod *
45cf252584Smiod *	longjmp(a,v)
46cf252584Smiod * will generate a "return(v)" from the last call to
47cf252584Smiod *	setjmp(a)
48cf252584Smiod * by restoring registers from the stack.
49cf252584Smiod * The previous signal state is restored.
50cf252584Smiod */
51cf252584Smiod
52cf252584SmiodENTRY(setjmp)
53cf252584Smiod	PIC_PROLOGUE(.L_got_1)
54cf252584Smiod	sts.l	pr,	@-sp
55cf252584Smiod	mov.l	r4,	@-sp
56cf252584Smiod
57cf252584Smiod	mov.l	.L_sigprocmask_1, r0
58cf252584Smiod	mov	r4,	r6
59cf252584Smiod	mov	#1,	r4		/* how = SIG_BLOCK */
60cf252584Smiod	mov	#0,	r5		/* new = NULL */
61cf252584Smiod1:	CALL	r0
62243b5df4Smiod	 add	#4,	r6		/* old = &sigmask */
63cf252584Smiod
64cf252584Smiod	mov.l	@sp+,	r4
65cf252584Smiod	lds.l	@sp+,	pr
66cf252584Smiod	PIC_EPILOGUE
67cf252584Smiod
68243b5df4Smiod	/* identical to _setjmp except that the first word is non-zero */
69243b5df4Smiod#if defined(__SH4__) && !defined(__SH4_NOFPU__)
70243b5df4Smiod	add	#(_JBLEN * 4), r4
71243b5df4Smiod	sts	fpscr,	r1
72243b5df4Smiod	xor	r0,	r0
73243b5df4Smiod	mov.l	r1,	@-r4
74243b5df4Smiod	lds	r0,	fpscr
75243b5df4Smiod	sts.l	fpul,	@-r4
76243b5df4Smiod	fmov.s	fr15,	@-r4
77243b5df4Smiod	fmov.s	fr14,	@-r4
78243b5df4Smiod	fmov.s	fr13,	@-r4
79243b5df4Smiod	fmov.s	fr12,	@-r4
80243b5df4Smiod	frchg
81243b5df4Smiod	fmov.s	fr15,	@-r4
82243b5df4Smiod	fmov.s	fr14,	@-r4
83243b5df4Smiod	fmov.s	fr13,	@-r4
84243b5df4Smiod	fmov.s	fr12,	@-r4
85243b5df4Smiod	lds	r1,	fpscr
86243b5df4Smiod#else
87243b5df4Smiod	add	#((_JBLEN - 10) * 4), r4
88243b5df4Smiod#endif
89243b5df4Smiod	sts.l	mach,	@-r4
90243b5df4Smiod	sts.l	macl,	@-r4
91cf252584Smiod	mov.l	r15,	@-r4
92cf252584Smiod	mov.l	r14,	@-r4
93cf252584Smiod	mov.l	r13,	@-r4
94cf252584Smiod	mov.l	r12,	@-r4
95cf252584Smiod	mov.l	r11,	@-r4
96cf252584Smiod	mov.l	r10,	@-r4
97cf252584Smiod	mov.l	r9,	@-r4
98cf252584Smiod	mov.l	r8,	@-r4
99cf252584Smiod	sts.l	pr,	@-r4
100243b5df4Smiod	add	#-4,	r4		/* skip signal mask */
101243b5df4Smiod	mov	#1,	r0
102243b5df4Smiod	mov.l	r0,	@-r4		/* has signal mask */
103cf252584Smiod	rts
104cf252584Smiod	 xor	r0,	r0
105cf252584Smiod
106cf252584Smiod	.align	2
107cf252584Smiod.L_got_1:		PIC_GOT_DATUM
108*0ee2ce67Sguenther.L_sigprocmask_1:	CALL_DATUM(_HIDDEN(sigprocmask), 1b)
109cf252584Smiod	SET_ENTRY_SIZE(setjmp)
110cf252584Smiod
111cf252584SmiodENTRY(longjmp)
112cf252584Smiod	/* we won't return here, so we don't need to save pr and r12 */
113cf252584Smiod	PIC_PROLOGUE_NOSAVE(.L_got_2)
114cf252584Smiod	mov.l	r5,	@-sp
115cf252584Smiod	mov.l	r4,	@-sp
116cf252584Smiod
117cf252584Smiod	mov.l	.L_sigprocmask_2, r0
118cf252584Smiod	mov	r4,	r5
119cf252584Smiod	mov	#3,	r4		/* how = SIG_SETMASK */
120243b5df4Smiod	add	#4,	r5		/* new = &sigmask */
121cf252584Smiod1:	CALL	r0
122cf252584Smiod	 mov	#0,	r6		/* old = NULL */
123cf252584Smiod
124cf252584Smiod	mov.l	@sp+,	r4
125cf252584Smiod	mov.l	@sp+,	r5
126cf252584Smiod
127cf252584Smiod	/* identical to _longjmp */
128243b5df4Smiod	add	#8,	r4
129cf252584Smiod	lds.l	@r4+,	pr
130cf252584Smiod	mov.l	@r4+,	r8
131cf252584Smiod	mov.l	@r4+,	r9
132cf252584Smiod	mov.l	@r4+,	r10
133cf252584Smiod	mov.l	@r4+,	r11
134cf252584Smiod	mov.l	@r4+,	r12
135cf252584Smiod	mov.l	@r4+,	r13
136cf252584Smiod	mov.l	@r4+,	r14
137cf252584Smiod	mov.l	@r4+,	r15
138243b5df4Smiod	lds.l	@r4+,	macl
139243b5df4Smiod	lds.l	@r4+,	mach
140243b5df4Smiod#if defined(__SH4__) && !defined(__SH4_NOFPU__)
141243b5df4Smiod	xor	r0, 	r0
142243b5df4Smiod	lds	r0,	fpscr
143243b5df4Smiod	frchg
144243b5df4Smiod	fmov.s	@r4+,	fr12
145243b5df4Smiod	fmov.s	@r4+,	fr13
146243b5df4Smiod	fmov.s	@r4+,	fr14
147243b5df4Smiod	fmov.s	@r4+,	fr15
148243b5df4Smiod	frchg
149243b5df4Smiod	fmov.s	@r4+,	fr12
150243b5df4Smiod	fmov.s	@r4+,	fr13
151243b5df4Smiod	fmov.s	@r4+,	fr14
152243b5df4Smiod	fmov.s	@r4+,	fr15
153243b5df4Smiod	lds.l	@r4+,	fpul
154243b5df4Smiod	lds.l	@r4+,	fpscr
155243b5df4Smiod#endif
156cf252584Smiod
157cf252584Smiod	mov	r5,	r0
158cf252584Smiod	tst	r0,	r0	/* make sure return value is non-zero */
159cf252584Smiod	bf	.L0
160cf252584Smiod	add	#1,	r0
161cf252584Smiod.L0:
162cf252584Smiod	rts
163cf252584Smiod	 nop
164cf252584Smiod
165cf252584Smiod	.align	2
166cf252584Smiod.L_got_2:		PIC_GOT_DATUM
167*0ee2ce67Sguenther.L_sigprocmask_2:	CALL_DATUM(_HIDDEN(sigprocmask), 1b)
168cf252584Smiod	SET_ENTRY_SIZE(longjmp)
169