xref: /nrf52832-nimble/rt-thread/libcpu/mips/x1000/stack.c (revision 104654410c56c573564690304ae786df310c91fc)
1 /*
2  * File      : stack.c
3  * This file is part of RT-Thread RTOS
4  * COPYRIGHT (C) 2008 - 2012, RT-Thread Development Team
5  *
6  *  This program is free software; you can redistribute it and/or modify
7  *  it under the terms of the GNU General Public License as published by
8  *  the Free Software Foundation; either version 2 of the License, or
9  *  (at your option) any later version.
10  *
11  *  This program is distributed in the hope that it will be useful,
12  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
13  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  *  GNU General Public License for more details.
15  *
16  *  You should have received a copy of the GNU General Public License along
17  *  with this program; if not, write to the Free Software Foundation, Inc.,
18  *  51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
19  *
20  * Change Logs:
21  * Date           Author       Notes
22  * 2016��9��8��     Urey         the first version
23  */
24 
25 #include <rtthread.h>
26 
27 #include "../common/mips.h"
28 
29 register U32 $GP __asm__ ("$28");
30 
rt_hw_stack_init(void * tentry,void * parameter,rt_uint8_t * stack_addr,void * texit)31 rt_uint8_t *rt_hw_stack_init(void *tentry, void *parameter, rt_uint8_t *stack_addr, void *texit)
32 {
33     static rt_uint32_t wSR=0;
34     static rt_uint32_t wGP;
35 
36 	mips_reg_ctx	*regCtx;
37 	mips_arg_ctx	*argCtx;
38 	rt_uint32_t i;
39 
40 	if (wSR == 0)
41 	{
42 		wSR = read_c0_status();
43 		wSR &= 0xfffffffe;
44 		wSR |= 0x0403;
45 
46 		wGP = $GP;
47 	}
48 
49 	if ((rt_uint32_t) stack_addr & 0x7)
50 	{
51 		stack_addr = (rt_uint8_t *)((rt_uint32_t)stack_addr - 4);
52 	}
53 
54 	argCtx = (mips_arg_ctx *)((rt_uint32_t)stack_addr - sizeof(mips_arg_ctx));
55 	regCtx = (mips_reg_ctx *)((rt_uint32_t)stack_addr - sizeof(mips_arg_ctx) - sizeof(mips_reg_ctx));
56 
57 	for (i = 0; i < 4; ++i)
58 	{
59 		argCtx->args[i] = i;
60 	}
61 
62 	//����ͨ�üĴ���
63 	for (i = 0; i < 32; ++i)
64 	{
65 		regCtx->regs[i] = i;
66 	}
67 
68 	regCtx->regs[REG_SP] = (rt_uint32_t)stack_addr;
69 	regCtx->regs[REG_A0] = (rt_uint32_t)parameter;
70 	regCtx->regs[REG_GP] = (rt_uint32_t)wGP;
71 	regCtx->regs[REG_FP] = (rt_uint32_t)0x0;
72 	regCtx->regs[REG_RA] = (rt_uint32_t)texit;
73 
74     regCtx->CP0DataLO	= 0x00;
75     regCtx->CP0DataHI	= 0x00;
76     regCtx->CP0Cause	= read_c0_cause();
77     regCtx->CP0Status	= wSR;
78     regCtx->CP0EPC		= (rt_uint32_t)tentry;
79     regCtx->CP0BadVAddr= 0x00;
80 
81 	return (rt_uint8_t *)(regCtx);
82 }
83