1 /*****************************************************************************
2 * sdladrv.c SDLA Support Module. Main module.
4 * This module is a library of common hardware-specific functions
5 * used by all Sangoma drivers.
7 * Author: Gene Kozin <genek@compuserve.com>
9 * Copyright: (c) 1995-1996 Sangoma Technologies Inc.
11 * This program is free software; you can redistribute it and/or
12 * modify it under the terms of the GNU General Public License
13 * as published by the Free Software Foundation; either version
14 * 2 of the License, or (at your option) any later version.
15 * ============================================================================
16 * May 19, 1999 Arnaldo Melo wanpipe_init belongs to sdlamain.c
17 * Dec 20, 1996 Gene Kozin Version 3.0.0. Complete overhaul.
18 * Jul 12, 1996 Gene Kozin Changes for Linux 2.0 compatibility.
19 * Jun 12, 1996 Gene Kozin Added support for S503 card.
20 * Apr 30, 1996 Gene Kozin SDLA hardware interrupt is acknowledged before
21 * calling protocolspecific ISR.
22 * Register I/O ports with Linux kernel.
23 * Miscellaneous bug fixes.
24 * Dec 20, 1995 Gene Kozin Fixed a bug in interrupt routine.
25 * Oct 14, 1995 Gene Kozin Initial version.
26 *****************************************************************************/
28 /*****************************************************************************
31 * 1. This code is ment to be system-independent (as much as possible). To
32 * achive this, various macros are used to hide system-specific interfaces.
33 * To compile this code, one of the following constants must be defined:
40 * 2. Supported adapter types:
50 * There is no separate DPM window enable/disable control in S502A. It
51 * opens immediately after a window number it written to the HMCR
52 * register. To close the window, HMCR has to be written a value
53 * ????1111b (e.g. 0x0F or 0xFF).
55 * S502A DPM window cannot be located at offset E000 (e.g. 0xAE000).
57 * There should be a delay of ??? before reading back S502A status
62 * S502E has a h/w bug: although default IRQ line state is HIGH, enabling
63 * interrupts by setting bit 1 of the control register (BASE) to '1'
64 * causes it to go LOW! Therefore, disabling interrupts by setting that
65 * bit to '0' causes low-to-high transition on IRQ line (ghosty
66 * interrupt). The same occurs when disabling CPU by resetting bit 0 of
67 * CPU control register (BASE+3) - see the next note.
69 * S502E CPU and DPM control is limited:
71 * o CPU cannot be stopped independently. Resetting bit 0 of the CPUi
72 * control register (BASE+3) shuts the board down entirely, including
75 * o DPM access cannot be controlled dynamically. Ones CPU is started,
76 * bit 1 of the control register (BASE) is used to enable/disable IRQ,
77 * so that access to shared memory cannot be disabled while CPU is
79 ****************************************************************************/
83 #if defined(_LINUX_) /****** Linux *******************************/
85 #include <linux/kernel.h> /* printk(), and other useful stuff */
86 #include <linux/stddef.h> /* offsetof(), etc. */
87 #include <linux/errno.h> /* return codes */
88 #include <linux/string.h> /* inline memset(), etc. */
89 #include <linux/module.h> /* support for loadable modules */
90 #include <linux/sched.h> /* for jiffies, HZ, etc. */
91 #include <linux/sdladrv.h> /* API definitions */
92 #include <linux/sdlasfm.h> /* SDLA firmware module definitions */
93 #include <asm/io.h> /* for inb(), outb(), etc. */
94 #define _INB(port) (inb(port))
95 #define _OUTB(port, byte) (outb((byte),(port)))
96 #define SYSTEM_TICK jiffies
98 #elif defined(_SCO_UNIX_) /****** SCO Unix ****************************/
99 #if !defined(INKERNEL)
100 #error This code MUST be compiled in kernel mode!
102 #include <sys/sdladrv.h> /* API definitions */
103 #include <sys/sdlasfm.h> /* SDLA firmware module definitions */
104 #include <sys/inline.h> /* for inb(), outb(), etc. */
105 #define _INB(port) (inb(port))
106 #define _OUTB(port, byte) (outb((port),(byte)))
107 #define SYSTEM_TICK lbolt
110 #error Unknown system type!
113 #define MOD_VERSION 3
114 #define MOD_RELEASE 0
116 #define SDLA_IODELAY 100 /* I/O Rd/Wr delay, 10 works for 486DX2-66 */
117 #define EXEC_DELAY 20 /* shared memory access delay, mks */
118 #define EXEC_TIMEOUT (HZ*2) /* command timeout, in ticks */
120 /* I/O port address range */
121 #define S502A_IORANGE 3
122 #define S502E_IORANGE 4
123 #define S503_IORANGE 3
124 #define S507_IORANGE 4
125 #define S508_IORANGE 4
127 /* Maximum amount of memory */
128 #define S502_MAXMEM 0x10000L
129 #define S503_MAXMEM 0x10000L
130 #define S507_MAXMEM 0x40000L
131 #define S508_MAXMEM 0x40000L
133 /* Minimum amount of memory */
134 #define S502_MINMEM 0x8000L
135 #define S503_MINMEM 0x8000L
136 #define S507_MINMEM 0x20000L
137 #define S508_MINMEM 0x20000L
139 /****** Function Prototypes *************************************************/
141 /* Module entry points. These are called by the OS and must be public. */
142 int init_module (void);
143 void cleanup_module (void);
145 /* Hardware-specific functions */
146 static int sdla_detect (sdlahw_t
* hw
);
147 static int sdla_autodpm (sdlahw_t
* hw
);
148 static int sdla_setdpm (sdlahw_t
* hw
);
149 static int sdla_load (sdlahw_t
* hw
, sfm_t
* sfm
, unsigned len
);
150 static int sdla_init (sdlahw_t
* hw
);
151 static unsigned long sdla_memtest (sdlahw_t
* hw
);
152 static int sdla_bootcfg (sdlahw_t
* hw
, sfm_info_t
* sfminfo
);
153 static unsigned char make_config_byte (sdlahw_t
* hw
);
154 static int sdla_start (sdlahw_t
* hw
, unsigned addr
);
156 static int init_s502a (sdlahw_t
* hw
);
157 static int init_s502e (sdlahw_t
* hw
);
158 static int init_s503 (sdlahw_t
* hw
);
159 static int init_s507 (sdlahw_t
* hw
);
160 static int init_s508 (sdlahw_t
* hw
);
162 static int detect_s502a (int port
);
163 static int detect_s502e (int port
);
164 static int detect_s503 (int port
);
165 static int detect_s507 (int port
);
166 static int detect_s508 (int port
);
168 /* Miscellaneous functions */
169 static int calibrate_delay (int mks
);
170 static int get_option_index (unsigned* optlist
, unsigned optval
);
171 static unsigned check_memregion (void* ptr
, unsigned len
);
172 static unsigned test_memregion (void* ptr
, unsigned len
);
173 static unsigned short checksum (unsigned char* buf
, unsigned len
);
175 /****** Global Data **********************************************************
176 * Note: All data must be explicitly initialized!!!
180 static char modname
[] = "sdladrv";
181 static char fullname
[] = "SDLA Support Module";
182 static char copyright
[] = "(c) 1995-1996 Sangoma Technologies Inc.";
183 static unsigned exec_idle
;
185 /* Hardware configuration options.
186 * These are arrays of configuration options used by verification routines.
187 * The first element of each array is its size (i.e. number of options).
189 static unsigned s502_port_options
[] =
190 { 4, 0x250, 0x300, 0x350, 0x360 }
192 static unsigned s503_port_options
[] =
193 { 8, 0x250, 0x254, 0x300, 0x304, 0x350, 0x354, 0x360, 0x364 }
195 static unsigned s508_port_options
[] =
196 { 8, 0x250, 0x270, 0x280, 0x300, 0x350, 0x360, 0x380, 0x390 }
199 static unsigned s502a_irq_options
[] = { 0 };
200 static unsigned s502e_irq_options
[] = { 4, 2, 3, 5, 7 };
201 static unsigned s503_irq_options
[] = { 5, 2, 3, 4, 5, 7 };
202 static unsigned s508_irq_options
[] = { 8, 3, 4, 5, 7, 10, 11, 12, 15 };
204 static unsigned s502a_dpmbase_options
[] =
207 0xA0000, 0xA2000, 0xA4000, 0xA6000, 0xA8000, 0xAA000, 0xAC000,
208 0xC0000, 0xC2000, 0xC4000, 0xC6000, 0xC8000, 0xCA000, 0xCC000,
209 0xD0000, 0xD2000, 0xD4000, 0xD6000, 0xD8000, 0xDA000, 0xDC000,
210 0xE0000, 0xE2000, 0xE4000, 0xE6000, 0xE8000, 0xEA000, 0xEC000,
212 static unsigned s507_dpmbase_options
[] =
215 0xA0000, 0xA2000, 0xA4000, 0xA6000, 0xA8000, 0xAA000, 0xAC000, 0xAE000,
216 0xB0000, 0xB2000, 0xB4000, 0xB6000, 0xB8000, 0xBA000, 0xBC000, 0xBE000,
217 0xC0000, 0xC2000, 0xC4000, 0xC6000, 0xC8000, 0xCA000, 0xCC000, 0xCE000,
218 0xE0000, 0xE2000, 0xE4000, 0xE6000, 0xE8000, 0xEA000, 0xEC000, 0xEE000,
220 static unsigned s508_dpmbase_options
[] = /* incl. S502E and S503 */
223 0xA0000, 0xA2000, 0xA4000, 0xA6000, 0xA8000, 0xAA000, 0xAC000, 0xAE000,
224 0xC0000, 0xC2000, 0xC4000, 0xC6000, 0xC8000, 0xCA000, 0xCC000, 0xCE000,
225 0xD0000, 0xD2000, 0xD4000, 0xD6000, 0xD8000, 0xDA000, 0xDC000, 0xDE000,
226 0xE0000, 0xE2000, 0xE4000, 0xE6000, 0xE8000, 0xEA000, 0xEC000, 0xEE000,
230 static unsigned s502_dpmsize_options[] = { 2, 0x2000, 0x10000 };
231 static unsigned s507_dpmsize_options[] = { 2, 0x2000, 0x4000 };
232 static unsigned s508_dpmsize_options[] = { 1, 0x2000 };
235 static unsigned s502a_pclk_options
[] = { 2, 3600, 7200 };
236 static unsigned s502e_pclk_options
[] = { 5, 3600, 5000, 7200, 8000, 10000 };
237 static unsigned s503_pclk_options
[] = { 3, 7200, 8000, 10000 };
238 static unsigned s507_pclk_options
[] = { 1, 12288 };
239 static unsigned s508_pclk_options
[] = { 1, 16000 };
241 /* Host memory control register masks */
242 static unsigned char s502a_hmcr
[] =
244 0x10, 0x12, 0x14, 0x16, 0x18, 0x1A, 0x1C, /* A0000 - AC000 */
245 0x20, 0x22, 0x24, 0x26, 0x28, 0x2A, 0x2C, /* C0000 - CC000 */
246 0x00, 0x02, 0x04, 0x06, 0x08, 0x0A, 0x0C, /* D0000 - DC000 */
247 0x30, 0x32, 0x34, 0x36, 0x38, 0x3A, 0x3C, /* E0000 - EC000 */
249 static unsigned char s502e_hmcr
[] =
251 0x10, 0x12, 0x14, 0x16, 0x18, 0x1A, 0x1C, 0x1E, /* A0000 - AE000 */
252 0x20, 0x22, 0x24, 0x26, 0x28, 0x2A, 0x2C, 0x2E, /* C0000 - CE000 */
253 0x00, 0x02, 0x04, 0x06, 0x08, 0x0A, 0x0C, 0x0E, /* D0000 - DE000 */
254 0x30, 0x32, 0x34, 0x36, 0x38, 0x3A, 0x3C, 0x3E, /* E0000 - EE000 */
256 static unsigned char s507_hmcr
[] =
258 0x00, 0x02, 0x04, 0x06, 0x08, 0x0A, 0x0C, 0x0E, /* A0000 - AE000 */
259 0x40, 0x42, 0x44, 0x46, 0x48, 0x4A, 0x4C, 0x4E, /* B0000 - BE000 */
260 0x80, 0x82, 0x84, 0x86, 0x88, 0x8A, 0x8C, 0x8E, /* C0000 - CE000 */
261 0xC0, 0xC2, 0xC4, 0xC6, 0xC8, 0xCA, 0xCC, 0xCE, /* E0000 - EE000 */
263 static unsigned char s508_hmcr
[] =
265 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, /* A0000 - AE000 */
266 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, /* C0000 - CE000 */
267 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, /* D0000 - DE000 */
268 0x18, 0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F, /* E0000 - EE000 */
271 static unsigned char s507_irqmask
[] =
273 0x00, 0x20, 0x40, 0x60, 0x80, 0xA0, 0xC0, 0xE0
276 /******* Kernel Loadable Module Entry Points ********************************/
278 /*============================================================================
279 * Module 'insert' entry point.
280 * o print announcement
281 * o initialize static data
282 * o calibrate SDLA shared memory access delay.
290 int init_module (void)
292 printk(KERN_INFO
"%s v%u.%u %s\n",
293 fullname
, MOD_VERSION
, MOD_RELEASE
, copyright
);
294 exec_idle
= calibrate_delay(EXEC_DELAY
);
296 printk(KERN_DEBUG
"%s: exec_idle = %d\n", modname
, exec_idle
);
301 /*============================================================================
302 * Module 'remove' entry point.
303 * o release all remaining system resources
305 void cleanup_module (void)
310 /******* Kernel APIs ********************************************************/
312 /*============================================================================
314 * o detect adapter type
315 * o verify hardware configuration options
316 * o check for hardware conflicts
317 * o set up adapter shared memory
318 * o test adapter memory
324 EXPORT_SYMBOL(sdla_setup
);
326 int sdla_setup (sdlahw_t
* hw
, void* sfm
, unsigned len
)
328 unsigned* irq_opt
= NULL
; /* IRQ options */
329 unsigned* dpmbase_opt
= NULL
; /* DPM window base options */
330 unsigned* pclk_opt
= NULL
; /* CPU clock rate options */
335 printk(KERN_ERR
"%s: adapter S%04u not found at port 0x%X!\n",
336 modname
, hw
->type
, hw
->port
)
340 printk(KERN_INFO
"%s: found S%04u card at port 0x%X.\n",
341 modname
, hw
->type
, hw
->port
)
344 hw
->dpmsize
= SDLA_WINDOWSIZE
;
348 hw
->io_range
= S502A_IORANGE
;
349 irq_opt
= s502a_irq_options
;
350 dpmbase_opt
= s502a_dpmbase_options
;
351 pclk_opt
= s502a_pclk_options
;
355 hw
->io_range
= S502E_IORANGE
;
356 irq_opt
= s502e_irq_options
;
357 dpmbase_opt
= s508_dpmbase_options
;
358 pclk_opt
= s502e_pclk_options
;
362 hw
->io_range
= S503_IORANGE
;
363 irq_opt
= s503_irq_options
;
364 dpmbase_opt
= s508_dpmbase_options
;
365 pclk_opt
= s503_pclk_options
;
369 hw
->io_range
= S507_IORANGE
;
370 irq_opt
= s508_irq_options
;
371 dpmbase_opt
= s507_dpmbase_options
;
372 pclk_opt
= s507_pclk_options
;
376 hw
->io_range
= S508_IORANGE
;
377 irq_opt
= s508_irq_options
;
378 dpmbase_opt
= s508_dpmbase_options
;
379 pclk_opt
= s508_pclk_options
;
383 /* Verify IRQ configuration options */
384 if (!get_option_index(irq_opt
, hw
->irq
))
386 printk(KERN_ERR
"%s: IRQ %d is illegal!\n",
392 /* Verify CPU clock rate configuration options */
394 hw
->pclk
= pclk_opt
[1] /* use default */
396 else if (!get_option_index(pclk_opt
, hw
->pclk
))
398 printk(KERN_ERR
"%s: CPU clock %u is illegal!\n",
403 printk(KERN_INFO
"%s: assuming CPU clock rate of %u kHz.\n",
407 /* Setup adapter dual-port memory window and test memory */
408 if (hw
->dpmbase
== 0)
410 err
= sdla_autodpm(hw
);
414 "%s: can't find available memory region!\n",
420 else if (!get_option_index(dpmbase_opt
, virt_to_phys(hw
->dpmbase
)))
422 printk(KERN_ERR
"%s: memory address 0x%lX is illegal!\n",
423 modname
, virt_to_phys(hw
->dpmbase
))
427 else if (sdla_setdpm(hw
))
430 "%s: 8K memory region at 0x%lX is not available!\n",
431 modname
, virt_to_phys(hw
->dpmbase
));
434 printk(KERN_INFO
"%s: dual-port memory window is set at 0x%lX.\n",
435 modname
, virt_to_phys(hw
->dpmbase
));
437 printk(KERN_INFO
"%s: found %luK bytes of on-board memory.\n",
438 modname
, hw
->memory
/ 1024);
440 /* Load firmware. If loader fails then shut down adapter */
441 err
= sdla_load(hw
, sfm
, len
);
442 if (err
) sdla_down(hw
); /* shutdown adapter */
446 /*============================================================================
447 * Shut down SDLA: disable shared memory access and interrupts, stop CPU, etc.
450 EXPORT_SYMBOL(sdla_down
);
452 int sdla_down (sdlahw_t
* hw
)
454 unsigned port
= hw
->port
;
457 if (!port
) return -EFAULT
;
462 _OUTB(port
, 0x08); /* halt CPU */
466 _OUTB(port
+ 1, 0xFF); /* close memory window */
471 _OUTB(port
+ 3, 0); /* stop CPU */
472 _OUTB(port
, 0); /* reset board */
473 for (i
= 0; i
< S502E_IORANGE
; ++i
)
481 _OUTB(port
, 0); /* reset board logic */
491 /*============================================================================
492 * Map shared memory window into SDLA address space.
495 EXPORT_SYMBOL(sdla_mapmem
);
497 int sdla_mapmem (sdlahw_t
* hw
, unsigned long addr
)
499 unsigned port
= hw
->port
;
506 if (addr
< S502_MAXMEM
) /* verify parameter */
508 tmp
= addr
>> 13; /* convert to register mask */
509 _OUTB(port
+ 2, tmp
);
516 if (addr
< S503_MAXMEM
) /* verify parameter */
518 tmp
= (hw
->regs
[0] & 0x8F) | ((addr
>> 9) & 0x70);
526 if (addr
< S507_MAXMEM
)
528 if (!(_INB(port
) & 0x02))
531 tmp
= addr
>> 13; /* convert to register mask */
532 _OUTB(port
+ 2, tmp
);
539 if (addr
< S508_MAXMEM
)
541 tmp
= addr
>> 13; /* convert to register mask */
542 _OUTB(port
+ 2, tmp
);
551 hw
->vector
= addr
& 0xFFFFE000L
;
555 /*============================================================================
556 * Enable interrupt generation.
559 EXPORT_SYMBOL(sdla_inten
);
561 int sdla_inten (sdlahw_t
* hw
)
563 unsigned port
= hw
->port
;
569 /* Note thar interrupt control operations on S502E are allowed
570 * only if CPU is enabled (bit 0 of status register is set).
572 if (_INB(port
) & 0x01)
574 _OUTB(port
, 0x02); /* bit1 = 1, bit2 = 0 */
575 _OUTB(port
, 0x06); /* bit1 = 1, bit2 = 1 */
582 tmp
= hw
->regs
[0] | 0x04;
584 hw
->regs
[0] = tmp
; /* update mirror */
585 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
586 if (!(_INB(port
) & 0x02)) /* verify */
592 tmp
= hw
->regs
[0] | 0x10;
594 hw
->regs
[0] = tmp
; /* update mirror */
595 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
596 if (!(_INB(port
+ 1) & 0x10)) /* verify */
612 /*============================================================================
613 * Disable interrupt generation.
616 EXPORT_SYMBOL(sdla_intde
);
618 int sdla_intde (sdlahw_t
* hw
)
620 unsigned port
= hw
->port
;
627 * 1) interrupt control operations are allowed only if CPU is
628 * enabled (bit 0 of status register is set).
629 * 2) disabling interrupts using bit 1 of control register
630 * causes IRQ line go high, therefore we are going to use
631 * 0x04 instead: lower it to inhibit interrupts to PC.
633 if (_INB(port
) & 0x01)
635 _OUTB(port
, hw
->regs
[0] & ~0x04);
636 hw
->regs
[0] &= ~0x04;
642 tmp
= hw
->regs
[0] & ~0x04;
644 hw
->regs
[0] = tmp
; /* update mirror */
645 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
646 if (_INB(port
) & 0x02) /* verify */
652 tmp
= hw
->regs
[0] & ~0x10;
654 hw
->regs
[0] = tmp
; /* update mirror */
655 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
656 if (_INB(port
) & 0x10) /* verify */
671 /*============================================================================
672 * Acknowledge SDLA hardware interrupt.
675 EXPORT_SYMBOL(sdla_intack
);
677 int sdla_intack (sdlahw_t
* hw
)
679 unsigned port
= hw
->port
;
685 /* To acknoledge hardware interrupt we have to toggle bit 3 of
686 * control register: \_/
687 * Note that interrupt control operations on S502E are allowed
688 * only if CPU is enabled (bit 1 of status register is set).
690 if (_INB(port
) & 0x01)
692 tmp
= hw
->regs
[0] & ~0x04;
702 if (_INB(port
) & 0x04)
704 tmp
= hw
->regs
[0] & ~0x08;
723 /*============================================================================
724 * Generate an interrupt to adapter's CPU.
727 EXPORT_SYMBOL(sdla_intr
);
729 int sdla_intr (sdlahw_t
* hw
)
731 unsigned port
= hw
->port
;
736 if (!(_INB(port
) & 0x40))
738 _OUTB(port
, 0x10); /* issue NMI to CPU */
745 if ((_INB(port
) & 0x06) == 0x06)
753 if (_INB(port
+ 1) & 0x02)
768 /*============================================================================
769 * Execute Adapter Command.
771 * o Busy-wait until flag is reset.
772 * o Return number of loops made, or 0 if command timed out.
775 EXPORT_SYMBOL(sdla_exec
);
777 int sdla_exec (void* opflag
)
779 volatile unsigned char* flag
= opflag
;
783 if (*flag
) return 0; /* ???? */
786 tstop
= SYSTEM_TICK
+ EXEC_TIMEOUT
;
787 for (nloops
= 1; *flag
; ++nloops
)
789 unsigned delay
= exec_idle
;
790 while (--delay
); /* delay */
791 if (SYSTEM_TICK
> tstop
) return 0; /* time is up! */
796 /*============================================================================
797 * Read absolute adapter memory.
798 * Transfer data from adapter's memory to data buffer.
801 * Care should be taken when crossing dual-port memory window boundary.
802 * This function is not atomic, so caller must disable interrupt if
803 * interrupt routines are accessing adapter shared memory.
806 EXPORT_SYMBOL(sdla_peek
);
808 int sdla_peek (sdlahw_t
* hw
, unsigned long addr
, void* buf
, unsigned len
)
810 unsigned long oldvec
= hw
->vector
;
811 unsigned winsize
= hw
->dpmsize
;
812 unsigned curpos
, curlen
; /* current offset and block size */
813 unsigned long curvec
; /* current DPM window vector */
816 if (addr
+ len
> hw
->memory
) /* verify arguments */
821 curpos
= addr
% winsize
; /* current window offset */
822 curvec
= addr
- curpos
; /* current window vector */
823 curlen
= (len
> (winsize
- curpos
)) ? (winsize
- curpos
) : len
;
825 /* Relocate window and copy block of data */
826 err
= sdla_mapmem(hw
, curvec
);
827 memcpy(buf
, (void *)((u8
*)hw
->dpmbase
+ curpos
), curlen
);
829 (char*)buf
+= curlen
;
833 /* Restore DPM window position */
834 sdla_mapmem(hw
, oldvec
);
838 /*============================================================================
839 * Write Absolute Adapter Memory.
840 * Transfer data from data buffer to adapter's memory.
843 * Care should be taken when crossing dual-port memory window boundary.
844 * This function is not atomic, so caller must disable interrupt if
845 * interrupt routines are accessing adapter shared memory.
848 EXPORT_SYMBOL(sdla_poke
);
850 int sdla_poke (sdlahw_t
* hw
, unsigned long addr
, void* buf
, unsigned len
)
852 unsigned long oldvec
= hw
->vector
;
853 unsigned winsize
= hw
->dpmsize
;
854 unsigned curpos
, curlen
; /* current offset and block size */
855 unsigned long curvec
; /* current DPM window vector */
858 if (addr
+ len
> hw
->memory
) /* verify arguments */
863 curpos
= addr
% winsize
; /* current window offset */
864 curvec
= addr
- curpos
; /* current window vector */
865 curlen
= (len
> (winsize
- curpos
)) ? (winsize
- curpos
) : len
;
867 /* Relocate window and copy block of data */
868 sdla_mapmem(hw
, curvec
);
869 memcpy((void*)((u8
*)hw
->dpmbase
+ curpos
), buf
, curlen
);
871 (char*)buf
+= curlen
;
875 /* Restore DPM window position */
876 sdla_mapmem(hw
, oldvec
);
880 #ifdef DONT_COMPIPLE_THIS
881 #endif /* DONT_COMPIPLE_THIS */
883 /****** Hardware-Specific Functions *****************************************/
885 /*============================================================================
886 * Detect adapter type.
887 * o if adapter type is specified then call detection routine for that adapter
888 * type. Otherwise call detection routines for every adapter types until
889 * adapter is detected.
892 * 1) Detection tests are destructive! Adapter will be left in shutdown state
895 static int sdla_detect (sdlahw_t
* hw
)
897 unsigned port
= hw
->port
;
906 if (!detect_s502a(port
)) err
= -ENODEV
;
910 if (!detect_s502e(port
)) err
= -ENODEV
;
914 if (!detect_s503(port
)) err
= -ENODEV
;
918 if (!detect_s507(port
)) err
= -ENODEV
;
922 if (!detect_s508(port
)) err
= -ENODEV
;
926 if (detect_s502a(port
))
927 hw
->type
= SDLA_S502A
929 else if (detect_s502e(port
))
930 hw
->type
= SDLA_S502E
932 else if (detect_s503(port
))
935 else if (detect_s507(port
))
938 else if (detect_s508(port
))
946 /*============================================================================
947 * Autoselect memory region.
948 * o try all available DMP address options from the top down until success.
950 static int sdla_autodpm (sdlahw_t
* hw
)
952 int i
, err
= -EINVAL
;
958 opt
= s502a_dpmbase_options
;
964 opt
= s508_dpmbase_options
;
968 opt
= s507_dpmbase_options
;
975 for (i
= opt
[0]; i
&& err
; --i
)
977 hw
->dpmbase
= phys_to_virt(opt
[i
]);
978 err
= sdla_setdpm(hw
);
983 /*============================================================================
984 * Set up adapter dual-port memory window.
985 * o shut down adapter
986 * o make sure that no physical memory exists in this region, i.e entire
987 * region reads 0xFF and is not writable when adapter is shut down.
988 * o initialize adapter hardware
989 * o make sure that region is usable with SDLA card, i.e. we can write to it
990 * when adapter is configured.
992 static int sdla_setdpm (sdlahw_t
* hw
)
996 /* Shut down card and verify memory region */
998 if (check_memregion(hw
->dpmbase
, hw
->dpmsize
))
1002 /* Initialize adapter and test on-board memory segment by segment.
1003 * If memory size appears to be less than shared memory window size,
1004 * assume that memory region is unusable.
1006 err
= sdla_init(hw
);
1007 if (err
) return err
;
1009 if (sdla_memtest(hw
) < hw
->dpmsize
) /* less than window size */
1014 sdla_mapmem(hw
, 0L); /* set window vector at bottom */
1018 /*============================================================================
1019 * Load adapter from the memory image of the SDLA firmware module.
1020 * o verify firmware integrity and compatibility
1021 * o start adapter up
1023 static int sdla_load (sdlahw_t
* hw
, sfm_t
* sfm
, unsigned len
)
1027 /* Verify firmware signature */
1028 if (strcmp(sfm
->signature
, SFM_SIGNATURE
))
1030 printk(KERN_ERR
"%s: not SDLA firmware!\n",
1036 /* Verify firmware module format version */
1037 if (sfm
->version
!= SFM_VERSION
)
1040 "%s: firmware format %u rejected! Expecting %u.\n",
1041 modname
, sfm
->version
, SFM_VERSION
)
1046 /* Verify firmware module length and checksum */
1047 if ((len
- offsetof(sfm_t
, image
) != sfm
->info
.codesize
) ||
1048 (checksum((void*)&sfm
->info
,
1049 sizeof(sfm_info_t
) + sfm
->info
.codesize
) != sfm
->checksum
))
1051 printk(KERN_ERR
"%s: firmware corrupted!\n", modname
);
1056 printk(KERN_INFO
"%s: loading %s (ID=%u)...\n", modname
,
1057 (sfm
->descr
[0] != '\0') ? sfm
->descr
: "unknown firmware",
1061 /* Scan through the list of compatible adapters and make sure our
1062 * adapter type is listed.
1065 (i
< SFM_MAX_SDLA
) && (sfm
->info
.adapter
[i
] != hw
->type
);
1068 if (i
== SFM_MAX_SDLA
)
1070 printk(KERN_ERR
"%s: firmware is not compatible with S%u!\n",
1076 /* Make sure there is enough on-board memory */
1077 if (hw
->memory
< sfm
->info
.memsize
)
1080 "%s: firmware needs %lu bytes of on-board memory!\n",
1081 modname
, sfm
->info
.memsize
)
1086 /* Move code onto adapter */
1087 if (sdla_poke(hw
, sfm
->info
.codeoffs
, sfm
->image
, sfm
->info
.codesize
))
1089 printk(KERN_ERR
"%s: failed to load code segment!\n",
1095 /* Prepare boot-time configuration data and kick-off CPU */
1096 sdla_bootcfg(hw
, &sfm
->info
);
1097 if (sdla_start(hw
, sfm
->info
.startoffs
))
1099 printk(KERN_ERR
"%s: Damn... Adapter won't start!\n",
1105 /* position DPM window over the mailbox and enable interrupts */
1106 if (sdla_mapmem(hw
, sfm
->info
.winoffs
) || sdla_inten(hw
))
1108 printk(KERN_ERR
"%s: adapter hardware failure!\n",
1113 hw
->fwid
= sfm
->info
.codeid
; /* set firmware ID */
1117 /*============================================================================
1118 * Initialize SDLA hardware: setup memory window, IRQ, etc.
1120 static int sdla_init (sdlahw_t
* hw
)
1124 for (i
= 0; i
< SDLA_MAXIORANGE
; ++i
)
1129 case SDLA_S502A
: return init_s502a(hw
);
1130 case SDLA_S502E
: return init_s502e(hw
);
1131 case SDLA_S503
: return init_s503(hw
);
1132 case SDLA_S507
: return init_s507(hw
);
1133 case SDLA_S508
: return init_s508(hw
);
1138 /*============================================================================
1139 * Test adapter on-board memory.
1140 * o slide DPM window from the bottom up and test adapter memory segment by
1142 * Return adapter memory size.
1144 static unsigned long sdla_memtest (sdlahw_t
* hw
)
1146 unsigned long memsize
;
1149 for (memsize
= 0, winsize
= hw
->dpmsize
;
1150 !sdla_mapmem(hw
, memsize
) &&
1151 (test_memregion(hw
->dpmbase
, winsize
) == winsize
)
1155 hw
->memory
= memsize
;
1159 /*============================================================================
1160 * Prepare boot-time firmware configuration data.
1161 * o position DPM window
1162 * o initialize configuration data area
1164 static int sdla_bootcfg (sdlahw_t
* hw
, sfm_info_t
* sfminfo
)
1166 unsigned char* data
;
1168 if (!sfminfo
->datasize
) return 0; /* nothing to do */
1170 if (sdla_mapmem(hw
, sfminfo
->dataoffs
) != 0)
1173 data
= (void*)((u8
*)hw
->dpmbase
+ (sfminfo
->dataoffs
- hw
->vector
));
1174 memset(data
, 0, sfminfo
->datasize
);
1176 data
[0x00] = make_config_byte(hw
);
1177 switch (sfminfo
->codeid
)
1181 data
[0x01] = 3; /* T1 timer */
1182 data
[0x03] = 10; /* N2 */
1183 data
[0x06] = 7; /* HDLC window size */
1184 data
[0x0B] = 1; /* DTE */
1185 data
[0x0C] = 2; /* X.25 packet window size */
1186 *(short*)&data
[0x0D] = 128; /* default X.25 data size */
1187 *(short*)&data
[0x0F] = 128; /* maximum X.25 data size */
1193 /*============================================================================
1194 * Prepare configuration byte identifying adapter type and CPU clock rate.
1196 static unsigned char make_config_byte (sdlahw_t
* hw
)
1198 unsigned char byte
= 0;
1202 case 5000: byte
= 0x01; break;
1203 case 7200: byte
= 0x02; break;
1204 case 8000: byte
= 0x03; break;
1205 case 10000: byte
= 0x04; break;
1206 case 16000: byte
= 0x05; break;
1210 case SDLA_S502E
: byte
|= 0x80; break;
1211 case SDLA_S503
: byte
|= 0x40; break;
1216 /*============================================================================
1217 * Start adapter's CPU.
1218 * o calculate a pointer to adapter's cold boot entry point
1219 * o position DPM window
1220 * o place boot instruction (jp addr) at cold boot entry point
1223 static int sdla_start (sdlahw_t
* hw
, unsigned addr
)
1225 unsigned port
= hw
->port
;
1226 unsigned char *bootp
;
1229 if (!port
) return -EFAULT
;
1234 bootp
= hw
->dpmbase
;
1242 bootp
= hw
->dpmbase
;
1249 err
= sdla_mapmem(hw
, 0);
1250 if (err
) return err
;
1252 *bootp
= 0xC3; /* Z80: 'jp' opcode */
1254 *((unsigned short*)(bootp
)) = addr
;
1259 _OUTB(port
, 0x10); /* issue NMI to CPU */
1264 _OUTB(port
+ 3, 0x01); /* start CPU */
1266 for (i
= 0; i
< SDLA_IODELAY
; ++i
);
1267 if (_INB(port
) & 0x01) /* verify */
1270 * Enabling CPU changes functionality of the
1271 * control register, so we have to reset its
1274 _OUTB(port
, 0); /* disable interrupts */
1281 tmp
= hw
->regs
[0] | 0x09; /* set bits 0 and 3 */
1283 hw
->regs
[0] = tmp
; /* update mirror */
1284 for (i
= 0; i
< SDLA_IODELAY
; ++i
);
1285 if (!(_INB(port
) & 0x01)) /* verify */
1291 tmp
= hw
->regs
[0] | 0x02;
1293 hw
->regs
[0] = tmp
; /* update mirror */
1294 for (i
= 0; i
< SDLA_IODELAY
; ++i
);
1295 if (!(_INB(port
) & 0x04)) /* verify */
1301 tmp
= hw
->regs
[0] | 0x02;
1303 hw
->regs
[0] = tmp
; /* update mirror */
1304 for (i
= 0; i
< SDLA_IODELAY
; ++i
);
1305 if (!(_INB(port
+ 1) & 0x02)) /* verify */
1316 /*============================================================================
1317 * Initialize S502A adapter.
1319 static int init_s502a (sdlahw_t
* hw
)
1321 unsigned port
= hw
->port
;
1324 if (!detect_s502a(port
))
1330 /* Verify configuration options */
1331 i
= get_option_index(s502a_dpmbase_options
, virt_to_phys(hw
->dpmbase
));
1336 tmp
= s502a_hmcr
[i
- 1];
1337 switch (hw
->dpmsize
)
1350 /* Setup dual-port memory window (this also enables memory access) */
1351 _OUTB(port
+ 1, tmp
);
1357 /*============================================================================
1358 * Initialize S502E adapter.
1360 static int init_s502e (sdlahw_t
* hw
)
1362 unsigned port
= hw
->port
;
1365 if (!detect_s502e(port
))
1369 /* Verify configuration options */
1370 i
= get_option_index(s508_dpmbase_options
, virt_to_phys(hw
->dpmbase
));
1375 tmp
= s502e_hmcr
[i
- 1];
1376 switch (hw
->dpmsize
)
1389 /* Setup dual-port memory window */
1390 _OUTB(port
+ 1, tmp
);
1393 /* Enable memory access */
1396 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
1397 return (_INB(port
) & 0x02) ? 0 : -EIO
;
1400 /*============================================================================
1401 * Initialize S503 adapter.
1402 * ---------------------------------------------------------------------------
1404 static int init_s503 (sdlahw_t
* hw
)
1406 unsigned port
= hw
->port
;
1409 if (!detect_s503(port
))
1413 /* Verify configuration options */
1414 i
= get_option_index(s508_dpmbase_options
, virt_to_phys(hw
->dpmbase
));
1419 tmp
= s502e_hmcr
[i
- 1];
1420 switch (hw
->dpmsize
)
1433 /* Setup dual-port memory window */
1434 _OUTB(port
+ 1, tmp
);
1437 /* Enable memory access */
1439 hw
->regs
[0] = 0x02; /* update mirror */
1443 /*============================================================================
1444 * Initialize S507 adapter.
1446 static int init_s507 (sdlahw_t
* hw
)
1448 unsigned port
= hw
->port
;
1451 if (!detect_s507(port
))
1455 /* Verify configuration options */
1456 i
= get_option_index(s507_dpmbase_options
, virt_to_phys(hw
->dpmbase
));
1461 tmp
= s507_hmcr
[i
- 1];
1462 switch (hw
->dpmsize
)
1475 /* Enable adapter's logic */
1478 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
1479 if (!(_INB(port
) & 0x20))
1483 /* Setup dual-port memory window */
1484 _OUTB(port
+ 1, tmp
);
1487 /* Enable memory access */
1488 tmp
= hw
->regs
[0] | 0x04;
1491 i
= get_option_index(s508_irq_options
, hw
->irq
);
1492 if (i
) tmp
|= s507_irqmask
[i
- 1];
1495 hw
->regs
[0] = tmp
; /* update mirror */
1496 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
1497 return (_INB(port
) & 0x08) ? 0 : -EIO
;
1500 /*============================================================================
1501 * Initialize S508 adapter.
1503 static int init_s508 (sdlahw_t
* hw
)
1505 unsigned port
= hw
->port
;
1508 if (!detect_s508(port
))
1512 /* Verify configuration options */
1513 i
= get_option_index(s508_dpmbase_options
, virt_to_phys(hw
->dpmbase
));
1518 /* Setup memory configuration */
1519 tmp
= s508_hmcr
[i
- 1];
1520 _OUTB(port
+ 1, tmp
);
1523 /* Enable memory access */
1525 hw
->regs
[0] = 0x04; /* update mirror */
1526 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
1527 return (_INB(port
+ 1) & 0x04) ? 0 : -EIO
;
1530 /*============================================================================
1531 * Detect S502A adapter.
1532 * Following tests are used to detect S502A adapter:
1533 * 1. All registers other than status (BASE) should read 0xFF
1534 * 2. After writing 00001000b to control register, status register should
1536 * 3. After writing 0 to control register, status register should still
1538 * 4. After writing 00000100b to control register, status register should
1540 * Return 1 if detected o.k. or 0 if failed.
1541 * Note: This test is destructive! Adapter will be left in shutdown
1542 * state after the test.
1544 static int detect_s502a (int port
)
1548 if (!get_option_index(s502_port_options
, port
))
1551 for (j
= 1; j
< SDLA_MAXIORANGE
; ++j
)
1553 if (_INB(port
+ j
) != 0xFF)
1556 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
1559 _OUTB(port
, 0x08); /* halt CPU */
1562 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
1563 if (_INB(port
) != 0x40)
1567 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
1568 if (_INB(port
) != 0x40)
1572 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
1573 if (_INB(port
) != 0x44)
1581 _OUTB(port
+ 1, 0xFF);
1585 /*============================================================================
1586 * Detect S502E adapter.
1587 * Following tests are used to verify adapter presence:
1588 * 1. All registers other than status (BASE) should read 0xFF.
1589 * 2. After writing 0 to CPU control register (BASE+3), status register
1590 * (BASE) should read 11111000b.
1591 * 3. After writing 00000100b to port BASE (set bit 2), status register
1592 * (BASE) should read 11111100b.
1593 * Return 1 if detected o.k. or 0 if failed.
1594 * Note: This test is destructive! Adapter will be left in shutdown
1595 * state after the test.
1597 static int detect_s502e (int port
)
1601 if (!get_option_index(s502_port_options
, port
))
1604 for (j
= 1; j
< SDLA_MAXIORANGE
; ++j
)
1606 if (_INB(port
+ j
) != 0xFF)
1609 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
1612 _OUTB(port
+ 3, 0); /* CPU control reg. */
1613 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
1614 if (_INB(port
) != 0xF8) /* read status */
1617 _OUTB(port
, 0x04); /* set bit 2 */
1618 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
1619 if (_INB(port
) != 0xFC) /* verify */
1628 /*============================================================================
1629 * Detect s503 adapter.
1630 * Following tests are used to verify adapter presence:
1631 * 1. All registers other than status (BASE) should read 0xFF.
1632 * 2. After writing 0 to control register (BASE), status register (BASE)
1633 * should read 11110000b.
1634 * 3. After writing 00000100b (set bit 2) to control register (BASE),
1635 * status register should read 11110010b.
1636 * Return 1 if detected o.k. or 0 if failed.
1637 * Note: This test is destructive! Adapter will be left in shutdown
1638 * state after the test.
1640 static int detect_s503 (int port
)
1644 if (!get_option_index(s503_port_options
, port
))
1647 for (j
= 1; j
< SDLA_MAXIORANGE
; ++j
)
1649 if (_INB(port
+ j
) != 0xFF)
1652 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
1655 _OUTB(port
, 0); /* reset control reg.*/
1656 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
1657 if (_INB(port
) != 0xF0) /* read status */
1660 _OUTB(port
, 0x04); /* set bit 2 */
1661 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
1662 if (_INB(port
) != 0xF2) /* verify */
1671 /*============================================================================
1672 * Detect s507 adapter.
1673 * Following tests are used to detect s507 adapter:
1674 * 1. All ports should read the same value.
1675 * 2. After writing 0x00 to control register, status register should read
1677 * 3. After writing 0x01 to control register, status register should read
1679 * Return 1 if detected o.k. or 0 if failed.
1680 * Note: This test is destructive! Adapter will be left in shutdown
1681 * state after the test.
1683 static int detect_s507 (int port
)
1687 if (!get_option_index(s508_port_options
, port
))
1691 for (j
= 1; j
< S507_IORANGE
; ++j
)
1693 if (_INB(port
+ j
) != tmp
)
1696 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
1700 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
1701 if ((_INB(port
) & 0x7E) != 0x30)
1705 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
1706 if ((_INB(port
) & 0x7E) != 0x32)
1715 /*============================================================================
1716 * Detect s508 adapter.
1717 * Following tests are used to detect s508 adapter:
1718 * 1. After writing 0x00 to control register, status register should read
1720 * 2. After writing 0x10 to control register, status register should read
1722 * Return 1 if detected o.k. or 0 if failed.
1723 * Note: This test is destructive! Adapter will be left in shutdown
1724 * state after the test.
1726 static int detect_s508 (int port
)
1730 if (!get_option_index(s508_port_options
, port
))
1734 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
1735 if ((_INB(port
+ 1) & 0x3F) != 0x00)
1739 for (i
= 0; i
< SDLA_IODELAY
; ++i
); /* delay */
1740 if ((_INB(port
+ 1) & 0x3F) != 0x10)
1749 /******* Miscellaneous ******************************************************/
1751 /*============================================================================
1752 * Calibrate SDLA memory access delay.
1753 * Count number of idle loops made within 1 second and then calculate the
1754 * number of loops that should be made to achive desired delay.
1756 static int calibrate_delay (int mks
)
1761 for (delay
= 0, stop
= SYSTEM_TICK
+ HZ
; SYSTEM_TICK
< stop
; ++delay
);
1762 return (delay
/(1000000L/mks
) + 1);
1765 /*============================================================================
1766 * Get option's index into the options list.
1767 * Return option's index (1 .. N) or zero if option is invalid.
1769 static int get_option_index (unsigned* optlist
, unsigned optval
)
1773 for (i
= 1; i
<= optlist
[0]; ++i
)
1774 if ( optlist
[i
] == optval
) return i
1779 /*============================================================================
1780 * Check memory region to see if it's available.
1783 static unsigned check_memregion (void* ptr
, unsigned len
)
1785 volatile unsigned char* p
= ptr
;
1787 for (; len
&& (*p
== 0xFF); --len
, ++p
)
1789 *p
= 0; /* attempt to write 0 */
1790 if (*p
!= 0xFF) /* still has to read 0xFF */
1792 *p
= 0xFF; /* restore original value */
1793 break; /* not good */
1799 /*============================================================================
1800 * Test memory region.
1801 * Return: size of the region that passed the test.
1802 * Note: Region size must be multiple of 2 !
1804 static unsigned test_memregion (void* ptr
, unsigned len
)
1806 volatile unsigned short* w_ptr
;
1807 unsigned len_w
= len
>> 1; /* region len in words */
1810 for (i
= 0, w_ptr
= ptr
; i
< len_w
; ++i
, ++w_ptr
)
1813 for (i
= 0, w_ptr
= ptr
; i
< len_w
; ++i
, ++w_ptr
)
1814 if (*w_ptr
!= 0xAA55)
1820 for (i
= 0, w_ptr
= ptr
; i
< len_w
; ++i
, ++w_ptr
)
1823 for (i
= 0, w_ptr
= ptr
; i
< len_w
; ++i
, ++w_ptr
)
1824 if (*w_ptr
!= 0x55AA)
1830 for (i
= 0, w_ptr
= ptr
; i
< len_w
; ++i
, ++w_ptr
) *w_ptr
= 0;
1834 /*============================================================================
1835 * Calculate 16-bit CRC using CCITT polynomial.
1837 static unsigned short checksum (unsigned char* buf
, unsigned len
)
1839 unsigned short crc
= 0;
1840 unsigned mask
, flag
;
1842 for (; len
; --len
, ++buf
)
1844 for (mask
= 0x80; mask
; mask
>>= 1)
1846 flag
= (crc
& 0x8000);
1848 crc
|= ((*buf
& mask
) ? 1 : 0);
1849 if (flag
) crc
^= 0x1021;
1856 /****** End *****************************************************************/