This source file includes following definitions.
- get_ioport_list
- find_gap
- request_region
- snarf_region
- release_region
- check_region
- reserve_setup
1
2
3
4
5
6
7
8
9
10 #include <linux/sched.h>
11 #include <linux/kernel.h>
12 #include <linux/errno.h>
13 #include <linux/types.h>
14 #include <linux/ioport.h>
15
16 #define IOTABLE_SIZE 64
17
18 typedef struct resource_entry_t {
19 u_long from, num;
20 const char *name;
21 struct resource_entry_t *next;
22 } resource_entry_t;
23
24 static resource_entry_t iolist = { 0, 0, "", NULL };
25
26 static resource_entry_t iotable[IOTABLE_SIZE];
27
28
29
30
31 int get_ioport_list(char *buf)
32 {
33 resource_entry_t *p;
34 int len = 0;
35
36 for (p = iolist.next; (p) && (len < 4000); p = p->next)
37 len += sprintf(buf+len, "%04lx-%04lx : %s\n",
38 p->from, p->from+p->num-1, p->name);
39 if (p)
40 len += sprintf(buf+len, "4K limit reached!\n");
41 return len;
42 }
43
44
45
46
47 static resource_entry_t *find_gap(resource_entry_t *root,
48 u_long from, u_long num)
49 {
50 unsigned long flags;
51 resource_entry_t *p;
52
53 if (from > from+num-1)
54 return NULL;
55 save_flags(flags);
56 cli();
57 for (p = root; ; p = p->next) {
58 if ((p != root) && (p->from+p->num-1 >= from)) {
59 p = NULL;
60 break;
61 }
62 if ((p->next == NULL) || (p->next->from > from+num-1))
63 break;
64 }
65 restore_flags(flags);
66 return p;
67 }
68
69
70
71
72 void request_region(unsigned int from, unsigned int num, const char *name)
73 {
74 resource_entry_t *p;
75 int i;
76
77 for (i = 0; i < IOTABLE_SIZE; i++)
78 if (iotable[i].num == 0)
79 break;
80 if (i == IOTABLE_SIZE)
81 printk("warning: ioport table is full\n");
82 else {
83 p = find_gap(&iolist, from, num);
84 if (p == NULL)
85 return;
86 iotable[i].name = name;
87 iotable[i].from = from;
88 iotable[i].num = num;
89 iotable[i].next = p->next;
90 p->next = &iotable[i];
91 return;
92 }
93 }
94
95
96
97
98
99 void snarf_region(unsigned int from, unsigned int num)
100 {
101 request_region(from,num,"No name given.");
102 }
103
104
105
106
107 void release_region(unsigned int from, unsigned int num)
108 {
109 resource_entry_t *p, *q;
110
111 for (p = &iolist; ; p = q) {
112 q = p->next;
113 if (q == NULL)
114 break;
115 if ((q->from == from) && (q->num == num)) {
116 q->num = 0;
117 p->next = q->next;
118 return;
119 }
120 }
121 }
122
123
124
125
126 int check_region(unsigned int from, unsigned int num)
127 {
128 return (find_gap(&iolist, from, num) == NULL) ? -EBUSY : 0;
129 }
130
131
132 void reserve_setup(char *str, int *ints)
133 {
134 int i;
135
136 for (i = 1; i < ints[0]; i += 2)
137 request_region(ints[i], ints[i+1], "reserved");
138 }