aboutsummaryrefslogtreecommitdiff
path: root/test10.c
blob: d1b3af3253b6b7de68c6e57efa2afa75f207a293 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
/* Test exception handling registers
 */
#include "armv7m.h"
#include "testme.h"

static
unsigned testseq;

#define SEQ() __atomic_add_fetch(&testseq, 1, __ATOMIC_RELAXED)

static
void pendsv(void)
{
    unsigned test = SEQ();
    switch(test) {
    case 2:
        testDiag("In PendSV");
        /* RETTOBASE not set */
        testEqI(0x0000000e, in32(SCB(0xd04)), "ICSR");
        testEqI(0x00000480, in32(SCB(0xd24)), "SHCSR");
        break;
    default:
        puts("Unexpected PendSV\n");
        abort();
    }
}

static
void svc(void)
{
    unsigned test = SEQ();
    switch(test) {
    case 1:
        testDiag("In SVC");
        /* RETTOBASE set */
        testEqI(0x0000080b, in32(SCB(0xd04)), "ICSR");
        testEqI(0x00000080, in32(SCB(0xd24)), "SHCSR");
        rmw(32, SCB(0xd04), 1<<28, 1<<28); /* Pend PendSV */
        testDiag("Back in SVC");
        test = SEQ();
        testEqI(3, test, "Back in SVC");
        break;
    default:
        testFail("Unexpected SVC");
        abort();
    }
}

void main(void)
{
    run_table.svc = &svc;
    run_table.pendsv = &pendsv;
    
    testInit(10);

    {
        /* attempt to detect the number of usable
         * bits in the priority fields.
         */
        uint32_t val = 0xff;
        __asm__ ("msr BASEPRI, %0" :: "r"(val) :);
        __asm__ ("mrs %0, BASEPRI" : "=r"(val) ::);
        puts("# BASEPRI mask ");
        puthex(val);
        val = 0;
        __asm__ ("msr BASEPRI, %0" :: "r"(val) :);
        rmw(32, SCB(0xd20), 0xff, 0xff);
        val = in32(SCB(0xd20))&0xff;
        rmw(32, SCB(0xd20), 0xff, 0);
        puts("\n# DEBUG prio ");
        puthex(val);
        putc('\n');
    }

    out32(SCB(0xd0c), 0x05fa0000 | (PRIGROUP<<8));
    out32(SCB(0xd1c), PRIO(2,0)<<24); /* SVC prio 2 */
    out32(SCB(0xd20), PRIO(1,0)<<16); /* PendSV prio 1 */

    /* RETTOBASE is UNKNOWN here */
    testEqI(0x00000000, in32(SCB(0xd04)) & ~ICSR_RETTOBASE, "ICSR");
    testEqI(0x00000000, in32(SCB(0xd24)), "SHCSR");
    testDiag("Call SVC");
    SVC(42);
    testDiag("Back in main");
    testEqI(4, SEQ(), "Back in SVC");
    testEqI(0x00000000, in32(SCB(0xd04)) & ~ICSR_RETTOBASE, "ICSR");
    testEqI(0x00000000, in32(SCB(0xd24)), "SHCSR");

    testDiag("Done");
}