summaryrefslogtreecommitdiff
path: root/rs422lib/sysctl.c
blob: ea055873ecb2676462f5a32646aa9aa4cc176f7e (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
/*
 * sysctl.c
 *
 *  Created on: 2014-4-26
 *      Author: Tuowen
 */

#include<msp430g2553.h>
#include"sysctl.h"

syshdlr sysarr[8];

volatile unsigned char syscall=0;

void sysctl_void()
{
	// This is the default routine
	// I don't want some monkey just come and call some random places in the text!!!!!
}

void sysroutine()
// << Drawback: interrupt may happen between else and CPUOFF
//		Critical section -> unlikely to have a race condition
{
	if (!syscall)
		_BIS_SR(CPUOFF);
	switch ((syscall & (-syscall))) // This is used to get the lowest bit
	{
	case SYS_BIT7:
		syscall=syscall&(~SYS_BIT7);
		sysarr[7]();
		break;
	case SYS_BIT6:
		syscall=syscall&(~SYS_BIT6);
		sysarr[6]();
		break;
	case SYS_BIT5:
		syscall=syscall&(~SYS_BIT5);
		sysarr[5]();
		break;
	case SYS_BIT4:
		syscall=syscall&(~SYS_BIT4);
		sysarr[4]();
		break;
	case SYS_BIT3:
		syscall=syscall&(~SYS_BIT3);
		sysarr[3]();
		break;
	case SYS_BIT2:
		syscall=syscall&(~SYS_BIT2);
		sysarr[2]();
		break;
	case SYS_BIT1:
		syscall=syscall&(~SYS_BIT1);
		sysarr[1]();
		break;
	case SYS_BIT0:
		syscall=syscall&(~SYS_BIT0);
		sysarr[0]();
		break;
	}

}

inline int sys_b2i(int bit)
{
	int i=0;
	while (bit>1){bit>>=1;++i;}
	return i;
}

void sysctl_reghdlr(unsigned int bit,syshdlr rot)
{
	bit=sys_b2i(bit);
	sysarr[bit]=rot;
}

void sysctl_rmhdlr(unsigned int bit)
{
	bit=sys_b2i(bit);
	sysarr[bit]=&sysctl_void;
}

void sysctl_init()
{
	unsigned int i;
	for (i=0;i<8;++i)
		sysarr[i]=&sysctl_void;
}