stak.c revision 527:cb400a149efa
1/*
2 * CDDL HEADER START
3 *
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License, Version 1.0 only
6 * (the "License").  You may not use this file except in compliance
7 * with the License.
8 *
9 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
10 * or http://www.opensolaris.org/os/licensing.
11 * See the License for the specific language governing permissions
12 * and limitations under the License.
13 *
14 * When distributing Covered Code, include this CDDL HEADER in each
15 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
16 * If applicable, add the following below this CDDL HEADER, with the
17 * fields enclosed by brackets "[]" replaced with your own identifying
18 * information: Portions Copyright [yyyy] [name of copyright owner]
19 *
20 * CDDL HEADER END
21 */
22/*
23 * Copyright 1992 Sun Microsystems, Inc.  All rights reserved.
24 * Use is subject to license terms.
25 */
26
27/*	Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T	*/
28/*	  All Rights Reserved  	*/
29
30#pragma ident	"%Z%%M%	%I%	%E% SMI"
31/*
32 * UNIX shell
33 */
34
35#include	"defs.h"
36
37
38/* ========	storage allocation	======== */
39
40unsigned char *
41getstak(asize)			/* allocate requested stack */
42int	asize;
43{
44	unsigned char	*oldstak;
45	int		size;
46
47	size = round(asize, BYTESPERWORD);
48	oldstak = stakbot;
49	staktop = stakbot += size;
50	if (staktop >= brkend)
51		growstak(staktop);
52	return(oldstak);
53}
54
55/*
56 * set up stack for local use
57 * should be followed by `endstak'
58 */
59unsigned char *
60locstak()
61{
62	if (brkend - stakbot < BRKINCR)
63	{
64		if (setbrk(brkincr) == -1)
65			error(nostack);
66		if (brkincr < BRKMAX)
67			brkincr += 256;
68	}
69	return(stakbot);
70}
71
72void
73growstak(newtop)
74unsigned char	*newtop;
75{
76	unsigned	incr;
77
78	incr = (unsigned)round(newtop - brkend + 1, BYTESPERWORD);
79	if (brkincr > incr)
80		incr = brkincr;
81	if (setbrk(incr) == -1)
82		error(nospace);
83}
84
85unsigned char *
86savstak()
87{
88	assert(staktop == stakbot);
89	return(stakbot);
90}
91
92unsigned char *
93endstak(unsigned char *argp)		/* tidy up after `locstak' */
94{
95	unsigned char	*oldstak;
96
97	if (argp >= brkend)
98		growstak(argp);
99	*argp++ = 0;
100	oldstak = stakbot;
101	stakbot = staktop = (unsigned char *)round(argp, BYTESPERWORD);
102	if (staktop >= brkend)
103		growstak(staktop);
104	return(oldstak);
105}
106
107void
108tdystak(unsigned char	*x)		/* try to bring stack back to x */
109{
110	while ((unsigned char *)stakbsy > x)
111	{
112		free(stakbsy);
113		stakbsy = stakbsy->word;
114	}
115	staktop = stakbot = max(x, stakbas);
116	rmtemp(x);
117}
118
119void
120stakchk(void)
121{
122	if ((brkend - stakbas) > BRKINCR + BRKINCR)
123		setbrk(-BRKINCR);
124}
125
126unsigned char *
127cpystak(x)
128unsigned char	*x;
129{
130	return(endstak(movstrstak(x, locstak())));
131}
132
133unsigned char *
134movstrstak(unsigned char *a, unsigned char *b)
135{
136	do
137	{
138		if (b >= brkend)
139			growstak(b);
140	}
141	while (*b++ = *a++);
142	return(--b);
143}
144
145/*
146 * Copy s2 to s1, always copy n bytes.
147 * Return s1
148 */
149unsigned char *
150memcpystak(unsigned char *s1, unsigned char *s2, int n)
151{
152	unsigned char *os1 = s1;
153
154	while (--n >= 0) {
155		if (s1 >= brkend)
156			growstak(s1);
157		*s1++ = *s2++;
158	}
159	return (os1);
160}
161