source: mainline/arch/mips32/src/drivers/arc.c@ dd14cced

lfn serial ticket/834-toolchain-update topic/msim-upgrade topic/simplify-dev-export
Last change on this file since dd14cced was 7a8c866a, checked in by Ondrej Palkovsky <ondrap@…>, 20 years ago

Move all MIPS exceptions to generic dispatcher.
Align size in malloc() to native size, some architectures
don't like it unaligned.

  • Property mode set to 100644
File size: 6.1 KB
Line 
1/*
2 * Copyright (C) 2005 Ondrej Palkovsky
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 *
9 * - Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer.
11 * - Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
14 * - The name of the author may not be used to endorse or promote products
15 * derived from this software without specific prior written permission.
16 *
17 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
18 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
19 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
20 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
21 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
22 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
26 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 */
28
29#include <arch/drivers/arc.h>
30#include <arch/mm/page.h>
31#include <print.h>
32#include <arch.h>
33#include <arch/byteorder.h>
34#include <arch/mm/frame.h>
35#include <mm/frame.h>
36#include <interrupt.h>
37
38/* This is a good joke, SGI HAS different types than NT bioses... */
39/* Here is the SGI type */
40static char *basetypes[] = {
41 "ExceptionBlock",
42 "SystemParameterBlock",
43 "FreeContiguous",
44 "FreeMemory",
45 "BadMemory",
46 "LoadedProgram",
47 "FirmwareTemporary",
48 "FirmwarePermanent"
49};
50
51static char *ctypes[] = {
52 "ARC_type",
53 "CPU_type",
54 "FPU_type",
55 "PrimaryICache",
56 "PrimaryDCache",
57 "SecondaryICache",
58 "SecondaryDCache",
59 "SecondaryCache",
60 "Memory",
61 "EISAAdapter",
62 "TCAdapter",
63 "SCSIAdapter",
64 "DTIAdapter",
65 "MultiFunctionAdapter",
66 "DiskController",
67 "TapeController",
68 "CDROMController",
69 "WORMController",
70 "SerialController",
71 "NetworkController",
72 "DisplayController",
73 "ParallelController",
74 "PointerController",
75 "KeyboardController",
76 "AudioController",
77 "OtherController",
78 "DiskPeripheral",
79 "FloppyDiskPeripheral",
80 "TapePeripheral",
81 "ModemPeripheral",
82 "MonitorPeripheral",
83 "PrinterPeripheral",
84 "PointerPeripheral",
85 "KeyboardPeripheral",
86 "TerminalPeripheral",
87 "OtherPeripheral",
88 "LinePeripheral",
89 "NetworkPeripheral"
90 "OtherPeripheral",
91 "XTalkAdapter",
92 "PCIAdapter",
93 "GIOAdapter",
94 "TPUAdapter",
95 "Anonymous"
96};
97
98static arc_sbp *sbp = (arc_sbp *)PA2KA(0x1000);
99static arc_func_vector_t *arc_entry;
100
101
102static void arc_putchar(char ch);
103
104/** Return true if ARC is available */
105int arc_enabled(void)
106{
107 return sbp != NULL;
108}
109
110static void arc_print_component(arc_component *c)
111{
112 int i;
113
114 printf("%s: ",ctypes[c->type]);
115 for (i=0;i < c->identifier_len;i++)
116 arc_putchar(c->identifier[i]);
117 arc_putchar('\n');
118}
119
120void arc_print_devices(void)
121{
122 arc_component *c,*next;
123
124 if (!arc_enabled())
125 return;
126
127 c = arc_entry->getchild(NULL);
128 while (c) {
129 arc_print_component(c);
130 next = arc_entry->getchild(c);
131 while (!next) {
132 next = arc_entry->getpeer(c);
133 if (!next)
134 c = arc_entry->getparent(c);
135 if (!c)
136 return;
137 }
138 c = next;
139 }
140}
141
142void arc_print_memory_map(void)
143{
144 arc_memdescriptor_t *desc;
145
146 if (!arc_enabled())
147 return;
148
149 printf("Memory map:\n");
150
151 desc = arc_entry->getmemorydescriptor(NULL);
152 while (desc) {
153 printf("%s: %d (size: %dKB)\n",basetypes[desc->type],
154 desc->basepage * ARC_FRAME,
155 desc->basecount*ARC_FRAME/1024);
156 desc = arc_entry->getmemorydescriptor(desc);
157 }
158}
159
160/** Print charactor to console */
161static void arc_putchar(char ch)
162{
163 __u32 cnt;
164 ipl_t ipl;
165
166 /* TODO: Should be spinlock? */
167 ipl = interrupts_disable();
168 arc_entry->write(1, &ch, 1, &cnt);
169 interrupts_restore(ipl);
170
171}
172
173/** Initialize ARC structure
174 *
175 * @return 0 - ARC OK, -1 - ARC does not exist
176 */
177int arc_init(void)
178{
179 if (sbp->signature != ARC_MAGIC) {
180 sbp = NULL;
181 return -1;
182 }
183 arc_entry = sbp->firmwarevector;
184
185 arc_putchar('A');
186 arc_putchar('R');
187 arc_putchar('C');
188 arc_putchar('\n');
189}
190
191static bool kbd_polling_enabled;
192static chardev_t console;
193
194/** Try to get character, return character or -1 if not available */
195static void arc_keyboard_poll(void)
196{
197 char ch;
198 __u32 count;
199 long result;
200
201 if (! kbd_polling_enabled)
202 return;
203
204 if (arc_entry->getreadstatus(0))
205 return;
206 result = arc_entry->read(0, &ch, 1, &count);
207 if (result || count!=1) {
208 return;
209 }
210 if (ch == '\r')
211 ch = '\n';
212 if (ch == 0x7f)
213 ch = '\b';
214
215 chardev_push_character(&console, ch);
216}
217
218static void arc_write(chardev_t *dev, const char ch)
219{
220 arc_putchar(ch);
221}
222
223static void arc_enable(chardev_t *dev)
224{
225 kbd_polling_enabled = true;
226}
227
228static void arc_disable(chardev_t *dev)
229{
230 kbd_polling_enabled = false;
231}
232
233static chardev_operations_t arc_ops = {
234 .resume = arc_enable,
235 .suspend = arc_disable,
236 .write = arc_write
237};
238
239iroutine old_timer;
240/** Do polling on timer interrupt */
241static void timer_replace(int n, void *stack)
242{
243 arc_keyboard_poll();
244 old_timer(n, stack);
245 arc_keyboard_poll();
246}
247
248
249chardev_t * arc_console(void)
250{
251 kbd_polling_enabled = true;
252
253 chardev_initialize("arc_console", &console, &arc_ops);
254 old_timer = int_register(TIMER_IRQ, "arc_kb_poll", timer_replace);
255 return &console;
256}
257
258/* Initialize frame zones from ARC firmware.
259 * In the future we may use even the FirmwareTemporary regions,
260 * currently we use the FreeMemory (what about the LoadedProgram?)
261 */
262void arc_frame_init(void)
263{
264 arc_memdescriptor_t *desc;
265 int total = 0;
266
267 desc = arc_entry->getmemorydescriptor(NULL);
268 while (desc) {
269 if (desc->type == FreeMemory ||
270 desc->type == FreeContiguous) {
271 total += desc->basecount*ARC_FRAME;
272 zone_create_in_region(desc->basepage*ARC_FRAME,
273 desc->basecount*ARC_FRAME);
274 }
275 desc = arc_entry->getmemorydescriptor(desc);
276 }
277
278 config.memory_size = total;
279}
280
Note: See TracBrowser for help on using the repository browser.