You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@mynewt.apache.org by ma...@apache.org on 2016/11/22 16:20:52 UTC

[7/9] incubator-mynewt-core git commit: tested with basic multithreaded app

tested with basic multithreaded app


Project: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/commit/8d6b13e6
Tree: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/tree/8d6b13e6
Diff: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/diff/8d6b13e6

Branch: refs/heads/develop
Commit: 8d6b13e631ea831fd0a47dd7de682b62558d9150
Parents: 61a406f
Author: julian <ju...@imgtec.com>
Authored: Tue Oct 18 15:02:16 2016 +0100
Committer: julian <ju...@imgtec.com>
Committed: Mon Nov 21 11:07:25 2016 +0000

----------------------------------------------------------------------
 libs/os/src/arch/mips/asm/ctx.S      | 32 +++++++++++-------
 libs/os/src/arch/mips/os_arch_mips.c | 56 +++++++++++--------------------
 2 files changed, 40 insertions(+), 48 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/8d6b13e6/libs/os/src/arch/mips/asm/ctx.S
----------------------------------------------------------------------
diff --git a/libs/os/src/arch/mips/asm/ctx.S b/libs/os/src/arch/mips/asm/ctx.S
index c5a36fd..a851f90 100644
--- a/libs/os/src/arch/mips/asm/ctx.S
+++ b/libs/os/src/arch/mips/asm/ctx.S
@@ -34,6 +34,7 @@
 #include <mips/hal.h>
 
 # note that k0 is not saved when using these macros.
+# The cause register is saved but not resored.
 
 # saves to location k0
 .macro _gpctx_save
@@ -83,6 +84,8 @@
 	REG_S	$9, CTX_BADVADDR(k0)
     mfc0	$9, C0_SR
 	sw	    $9, CTX_STATUS(k0)
+    mfc0    $9, C0_CR
+    sw      $9, CTX_CAUSE(k0)
 
     move	$11, $0
 	move	$12, $0
@@ -169,21 +172,26 @@ get_global_pointer:
 .global _mips_isr_sw0
 .ent _mips_isr_sw0
 _mips_isr_sw0:
-    /* context switch */
+    # context switch
     .set noat
-    /* save k0 */
-    REG_S $26, (CTX_REG(25) - CTX_SIZE) (sp)
-    addi k0, sp, 0 - CTX_SIZE
-    _gpctx_save                     /* save the context to sp - CTX_SIZE */
+    # save k0
+    REG_S   $26, (CTX_REG(25) - CTX_SIZE) (sp)
+    addi    k0, sp, -((((CTX_SIZE - 1) / 8) + 1) * 8)
+    _gpctx_save                     # save the context
     .set at
-    lw t0, g_current_task           /* get current task */
-    beqz t0, 1f
-    sw k0, 0(t0)                    /* update stored sp */
+    lw      t0, g_current_task      # get current task
+    beqz    t0, 1f
+    sw      k0, 0(t0)               # update stored sp
 1:
-    lw t1, g_os_run_list            /* get new task */
-    sw t1, g_current_task           /* g_current_task = g_os_run_list */
-    lw a0, 0(t1)
+    lw      t1, g_os_run_list       # get new task
+    sw      t1, g_current_task      # g_current_task = g_os_run_list
+    mfc0    k0, C0_CR
+    andi    k0, k0, 0xfeff          # clear interrupt in cause register
+    lui     k1, 0x0080              # make sure IV is set
+    or      k0, k0, k1
+    mtc0    k0, C0_CR
+    lw      a0, 0(t1)
     .set noat
-    _gpctx_load                     /* update actual sp */
+    _gpctx_load                     # updates actual sp
     eret
 .end

http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/8d6b13e6/libs/os/src/arch/mips/os_arch_mips.c
----------------------------------------------------------------------
diff --git a/libs/os/src/arch/mips/os_arch_mips.c b/libs/os/src/arch/mips/os_arch_mips.c
index 3ca779b..7ac01a9 100644
--- a/libs/os/src/arch/mips/os_arch_mips.c
+++ b/libs/os/src/arch/mips/os_arch_mips.c
@@ -27,61 +27,43 @@
 #include <mips/hal.h>
 #include <mips/uhi_syscalls.h>
 
+#include <string.h>
+
 extern void SVC_Handler(void);
 extern void PendSV_Handler(void);
 extern void SysTick_Handler(void);
 
-/* XXX: determine how we will deal with running un-privileged */
+/* XXX: determine how to deal with running un-privileged */
 /* only priv currently supported */
 uint32_t os_flags = OS_RUN_PRIV;
 
-/* fucntion to call from syscall */
-void (* volatile os_ftc)(void) = 0;
 extern struct os_task g_idle_task;
-/* exception handler */
-void
-_mips_handle_exception (struct gpctx* ctx, int exception)
-{
-    switch (exception) {
-        case EXC_SYS:
-            if (os_ftc != 0) {
-                os_ftc();
-                os_ftc = 0;
-                return;
-            }
-    }
-    /* default handler for anything not handled above */
-    __exception_handle(ctx, exception);
-}
-
 
 /* core timer interrupt */
 void __attribute__((interrupt, keep_interrupts_masked))
 _mips_isr_hw5(void)
 {
+    mips_setcompare(mips_getcompare() + 273000);
     timer_handler();
 }
 
 static int
 os_in_isr(void)
 {
-    /* check the EXL bit XXX: Actually, that breaks it for some reason. */
-    return 0; //(mips_getsr() & (1 << 1)) ? 1 : 0;
+    /* check the EXL bit */
+    return (mips_getsr() & (1 << 1)) ? 1 : 0;
 }
 
 void
 timer_handler(void)
 {
-    /* This actually does the context switch by calling the below function if
-       necessary */
     os_time_advance(1);
 }
 
 void
 os_arch_ctx_sw(struct os_task *t)
 {
-    if ((os_sched_get_current_task() != 0) && (t != 0))
-    {
+    if ((os_sched_get_current_task() != 0) && (t != 0)) {
         os_sched_ctx_sw_hook(t);
     }
 
@@ -111,26 +93,27 @@ os_arch_in_critical(void)
 
 reg_t get_global_pointer(void);
 
+/* assumes stack_top will be 8 aligned */
+
 os_stack_t *
 os_arch_task_stack_init(struct os_task *t, os_stack_t *stack_top, int size)
 {
-    const size_t frame_size = sizeof(struct gpctx);
-    os_stack_t *s = stack_top - frame_size;
+    os_stack_t *s = stack_top - ((((sizeof(struct gpctx) - 1) /
+        OS_STACK_ALIGNMENT) + 1) * 2);
 
     struct gpctx ctx = {
         .r = {
             [3] = (reg_t)t->t_arg,
             [27] = get_global_pointer(),
-            [28] = (reg_t)stack_top
+            [28] = (reg_t)(stack_top - 4)
         },
-        /* XXX: copying the status register from when the task was created
-         * seems like a modreately sensible thing to do? */
         .status = mips_getsr(),
+        .cause = mips_getcr(),
         .epc = (reg_t)t->t_func
     };
 
     /* copy struct onto the stack */
-    *((struct gpctx*)s) = ctx;
+    memcpy(s, &ctx, sizeof(struct gpctx));
 
     return (s);
 }
@@ -138,6 +121,7 @@ os_arch_task_stack_init(struct os_task *t, os_stack_t *stack_top, int size)
 void
 os_arch_init(void)
 {
+    mips_bissr((1 << 15) | (1 << 8));
     os_init_idle_task();
 }
 
@@ -168,13 +152,13 @@ os_arch_start(void)
     t = os_sched_next_task();
 
     /* set the core timer compare register */
-    /* XXX: take this magic number (for a 1ms tick from a 550MHz clock) and put
+    /* XXX: take this magic number (for a 1ms tick from a 546MHz clock) and put
     ** it in bsp or mcu somewhere
     */
-    mips_setcompare(275000);
+    mips_setcompare(mips_getcount() + 273000);
 
-    /* enable core timer and software0 interupts and global enable */
-    mips_bissr((1 << 15) | (1 << 8) | 1);
+    /* global interrupt enable */
+    mips_bissr(1);
 
     /* Mark the OS as started, right before we run our first task */
     g_os_started = 1;
@@ -191,7 +175,7 @@ os_arch_os_start(void)
     os_error_t err;
 
     err = OS_ERR_IN_ISR;
-    if (os_in_isr() == 0) { // cause
+    if (os_in_isr() == 0) {
         err = OS_OK;
         /* should be in kernel mode here */
         os_arch_start();