summaryrefslogtreecommitdiff
path: root/misc/Obsoleted/arch/8051/src/up_head.S
diff options
context:
space:
mode:
Diffstat (limited to 'misc/Obsoleted/arch/8051/src/up_head.S')
-rw-r--r--misc/Obsoleted/arch/8051/src/up_head.S471
1 files changed, 471 insertions, 0 deletions
diff --git a/misc/Obsoleted/arch/8051/src/up_head.S b/misc/Obsoleted/arch/8051/src/up_head.S
new file mode 100644
index 000000000..d4e2ba6e7
--- /dev/null
+++ b/misc/Obsoleted/arch/8051/src/up_head.S
@@ -0,0 +1,471 @@
+/************************************************************
+ * arch/8051/src/up_head.S
+ *
+ * Copyright (C) 2007, 2014 Gregory Nutt. All rights reserved.
+ * Author: Gregory Nutt <gnutt@nuttx.org>
+ *
+ * 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.
+ * 3. Neither the name Gregory Nutt nor the names of its contributors may be
+ * used to endorse or promote products derived from this software
+ * without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS 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
+ * COPYRIGHT OWNER 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.
+ *
+ ************************************************************/
+
+/************************************************************
+ * Included Files
+ ************************************************************/
+
+#include <nuttx/config.h>
+#include <nuttx/irq.h>
+#include "up_internal.h"
+
+ .module up_head
+ .optsdcc -mmcs51 --model-large
+
+/************************************************************
+ * Private Data
+ ************************************************************/
+
+ .area REG_BANK_0 (REL,OVR,DATA)
+ .ds 8
+
+#ifndef CONFIG_ARCH_8051_NOSYSTIMER
+ .area XSEG
+_g_timer0tick:
+ .ds 1
+#endif
+
+/************************************************************
+ * Public Data
+ ************************************************************/
+
+ .globl _g_irqtos
+ .globl _g_irqcontext
+ .globl _g_irqregs
+
+/************************************************************
+ * Public Functions
+ ************************************************************/
+
+ .globl _irq_dispatch
+ .globl _up_restoreregisters
+
+/************************************************************
+ * Program entry points
+ ************************************************************/
+
+/* Program entry is through PROGRAM_BASE. This is just a
+ * branch to our start up logic.
+ */
+
+ .area CODE1 (ABS)
+ .org PROGRAM_BASE
+ ljmp start
+
+/* These are indirect interrupt vectors. Logic in PAULMON2,
+ * captures the interrupt vectors (near address 0x0000) and
+ * re-routes them through the following entry points.
+ *
+ * Each of these saves acc and ie then passes the IRQ number
+ * to higher level logic in a
+ */
+
+ .org PM2_VECTOR_EXTINT0
+ push acc
+ mov a, #EXT_INT0_IRQ
+ ljmp _up_interrupt
+
+ .org PM2_VECTOR_TIMER0
+ push acc
+#ifdef CONFIG_ARCH_8051_NOSYSTIMER
+ mov a, #TIMER0_IRQ
+ ljmp _up_interrupt
+#else
+ ljmp _up_timer0
+#endif
+ .org PM2_VECTOR_EXTINT1
+ push acc
+ mov a, #EXT_INT1_IRQ
+ ljmp _up_interrupt
+
+ .org PM2_VECTOR_TIMER1
+ push acc
+ mov a, #TIMER1_IRQ
+ ljmp _up_interrupt
+
+ .org PM2_VECTOR_UART
+ push acc
+ mov a, #UART_IRQ
+ ljmp _up_interrupt
+
+ .org PM2_VECTOR_TIMER2
+ push acc
+ mov a, #TIMER2_IRQ
+ ljmp _up_interrupt
+
+/************************************************************
+ * Name: start
+ *
+ * Description:
+ * This is the initial entry point into NuttX
+ *
+ ************************************************************/
+
+start:
+ mov sp, #(STACK_BASE-1)
+
+#ifdef CONFIG_ARCH_LEDS
+ lcall _board_led_initialize
+#endif
+
+ ljmp _os_start
+
+/************************************************************
+ * Name: up_timer0
+ *
+ * Description:
+ * Timer 0, mode 0 can be used as a system timer. In that
+ * mode, the 1.8432 MHz clock is divided by 32. A single
+ * 8-bit value is incremented at 57600 Hz, which results
+ * in 225 Timer 0 overflow interrupts per second.
+ *
+ * The Timer0 interrupt vectors to this point which then
+ * does a software divide by 2 to get a system timer of
+ * 112.5Hz.
+ *
+ * On Entry:
+ *
+ * (1) acc on the stack and
+ * (2) the IRQ number(TIMER0_IRQ) in the accumulator
+ *
+ ************************************************************/
+
+#ifndef CONFIG_ARCH_8051_NOSYSTIMER
+_up_timer0:
+ ar2 = 0x02
+ ar3 = 0x03
+ ar4 = 0x04
+ ar5 = 0x05
+ ar6 = 0x06
+ ar7 = 0x07
+ ar0 = 0x00
+ ar1 = 0x01
+
+ /* ACC already on the stack; push IE. Then disable interrupts */
+
+ push ie
+ clr ea
+
+ /* Save the remaining registers with interrupts disabled
+ *
+ * a, ie, and dptr go on the stack.
+ */
+
+ push dpl
+ push dph
+
+ /* Increment the tick counter */
+
+ mov dptr, #_g_timer0tick
+ movx a, @dptr
+ inc a
+ movx @dptr, a
+
+ /* If bit 0 is '0', then just return from the interrupt */
+
+ anl a, #0x01
+ jnz 00101$
+ ljmp _up_timer0exit
+
+ /* If bit 0 is '1', then process the interrupt */
+
+00101$:
+ mov a, #TIMER0_IRQ
+ sjmp _up_timer0join
+#endif
+
+/************************************************************
+ * Name: up_interrupt
+ *
+ * Description:
+ * All interrupts vector to this point with:
+ *
+ * (1) acc on the stack and
+ * (2) the IRQ number in the accumulator
+ *
+ ************************************************************/
+
+_up_interrupt:
+ ar2 = 0x02
+ ar3 = 0x03
+ ar4 = 0x04
+ ar5 = 0x05
+ ar6 = 0x06
+ ar7 = 0x07
+ ar0 = 0x00
+ ar1 = 0x01
+
+ /* ACC already on the stack; push IE. Then disable interrupts */
+
+ push ie
+ clr ea
+
+ /* Save the remaining registers with interrupts disabled
+ *
+ * a, ie, and dptr go on the stack.
+ */
+
+ push dpl
+ push dph
+
+_up_timer0join:
+ /* Other registers go into the IRQ register save area */
+
+ push acc
+ mov dptr, #_g_irqregs
+ lcall _up_saveregisters
+
+ /* Show interrupt status on the LEDs */
+
+#ifdef CONFIG_ARCH_LEDS
+ mov dpl, #LED_INIRQ
+ lcall _board_led_on
+#endif
+
+ /* Save the IRQ number in r2 */
+
+ pop ar2
+
+ /* Mark that we are in an interrupt and provide the top
+ * of stack pointer to the context switching logic.
+ */
+
+ mov dptr, #_g_irqtos
+ mov a, sp
+ movx @dptr, a
+
+ /* Nullify the context pointer. If a context switch is
+ * needed, this will be set to the address of the context
+ * structure.
+ */
+
+ mov dptr, #_g_irqcontext
+ clr a
+ movx @dptr,a
+ inc dptr
+ movx @dptr,a
+
+ /* Now call void irq_dispatch(int irq, FAR void *context)
+ *
+ * First, create the first argument as (int)irqno
+ */
+
+ mov dpl, r2
+ mov dph, #0
+
+ /* Create the second argument (void *context) on the stack */
+
+ push sp
+ clr a
+ push acc
+
+ /* Then dispatch the IRQ. */
+
+ lcall _irq_dispatch
+ pop acc
+ pop acc
+
+ /* Indicate that we are no longer in an interrupt */
+
+ mov dptr, #_g_irqtos
+ clr a
+ movx @dptr, a
+
+ /* Check if a context switch is pending */
+
+ mov dptr,#_g_irqcontext
+ movx a, @dptr
+ mov r2, a
+ inc dptr
+ movx a, @dptr
+ mov r3, a
+
+ orl a, r2
+ jnz 00001$
+
+ /* No context switch is pending. Restore registers
+ * from the interrupt register save area.
+ */
+
+ mov dptr, #_g_irqregs
+ sjmp 00004$
+
+00001$: /****************************************************/
+
+ /* A context switch is pending, clear g_irqcontext */
+
+ mov dpl, r2
+ mov dph, r3
+ clr a
+ movx @dptr, a
+ inc dptr
+ movx @dptr, a
+
+#ifdef CONFIG_INTERRUPT_FRAME_DUMP
+ mov dpl, r2
+ mov dph, r3
+ push ar2
+ push ar3
+ lcall _up_dumpframe
+ pop ar3
+ pop ar2
+#endif
+
+ /* Register usage in the following:
+ *
+ * R0 - Holds working the 8-bit IRAM pointer
+ * R1 - Not used
+ * R2-3 - Holds the working 16-bit XRAM pointer
+ * R4 - Holds the working byte count
+ * R5 - Holds the new stack pointer
+ * R6-7 - Not used
+ */
+
+ /* Fetch r4 = context->nbytes */
+
+ mov dpl, r2
+ mov dph, r3
+ movx a, @dptr
+ mov r4, a
+
+ /* Save the new stack pointer in r5 */
+
+ add a, #(STACK_BASE-1)
+ mov r5, a
+
+ /* Save r2-3 = &context->stack */
+
+ inc dptr
+ push dpl
+ push dph
+ mov r2, dpl
+ mov r3, dph
+
+ /* Set r0 = stack base address */
+
+ mov r0, #STACK_BASE
+
+ /* Top of the copy loop */
+00002$:
+ mov a, r4 /* a = bytes left to transfer */
+ dec r4 /* (for next time through the loop) */
+ jz 00003$ /* Jump if a = 0 (done) */
+
+ /* Fetch the next byte from context->stack */
+
+ mov dpl, r2
+ mov dph, r3
+ movx a,@dptr
+
+ /* Increment the XRAM pointer */
+
+ inc dptr
+ mov r2, dpl
+ mov r3, dph
+
+ /* Save the next byte into IRAM */
+
+ mov @r0, a
+
+ /* Increment the IRAM pointer */
+
+ inc r0
+ sjmp 00002$
+
+ /* The entire stack has been copied from XRAM into
+ * IRAM. Set the new stack pointer
+ */
+
+00003$:
+ pop dph
+ pop dpl
+ mov sp, r5
+
+#ifdef CONFIG_INTERRUPT_FRAME_DUMP
+ push dpl
+ push dph
+ lcall _up_dumpstack
+ pop dph
+ pop dpl
+#endif
+ /* Get the pointer to the register save area */
+
+ mov a, #STACK_SIZE
+ add a, dpl
+ mov dpl, a
+ clr a
+ addc a, dph
+ mov dph, a
+
+00004$: /****************************************************/
+
+ /* Restore the context from the register save area
+ * and return from the interrupt. At this point, dptr
+ * holds the pointer to the memory region that holds
+ * the register save area. This could be either
+ * g_irqregs (no context switch) or &g_irqcontext->regs
+ * (context switch).
+ */
+
+#ifdef CONFIG_ARCH_LEDS
+ push dpl
+ push dph
+ mov dpl, #LED_INIRQ
+ lcall _board_led_off
+ pop dph
+ pop dpl
+#endif
+ /* Restore registers from the register save area */
+
+ lcall _up_restoreregisters
+
+_up_timer0exit:
+ /* Restore registers from the stack and return */
+
+ pop dph
+ pop dpl
+
+ /* Restore the interrupt state per the stored IE value */
+
+ pop acc
+ jb acc.7,00005$
+ clr ie.7
+ sjmp 00006$
+00005$:
+ setb ie.7
+
+00006$:
+ pop acc
+ reti