4 Copyright (c) Eicon Networks, 2002.
6 This source file is supplied for the use with
7 Eicon Networks range of DIVA Server Adapters.
9 Eicon File Revision : 2.1
11 This program is free software; you can redistribute it and/or modify
12 it under the terms of the GNU General Public License as published by
13 the Free Software Foundation; either version 2, or (at your option)
16 This program is distributed in the hope that it will be useful,
17 but WITHOUT ANY WARRANTY OF ANY KIND WHATSOEVER INCLUDING ANY
18 implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
19 See the GNU General Public License for more details.
21 You should have received a copy of the GNU General Public License
22 along with this program; if not, write to the Free Software
23 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
38 /*****************************************************************************/
39 #define MAX_XLOG_SIZE (64 * 1024)
40 /* --------------------------------------------------------------------------
41 Investigate card state, recovery trace buffer
42 -------------------------------------------------------------------------- */
43 static void bri_cpu_trapped (PISDN_ADAPTER IoAdapter
) {
44 byte
*addrHi
, *addrLo
, *ioaddr
;
46 dword regs
[4], i
, size
;
49 * first read pointers and trap frame
51 if ( !(Xlog
= (word
*)diva_os_malloc (0, MAX_XLOG_SIZE
)) )
53 addrHi
= IoAdapter
->port
54 + ((IoAdapter
->Properties
.Bus
== BUS_PCI
) ? M_PCI_ADDRH
: ADDRH
) ;
55 addrLo
= IoAdapter
->port
+ ADDR
;
56 ioaddr
= IoAdapter
->port
+ DATA
;
59 for ( i
= 0 ; i
< 0x100 ; Xlog
[i
++] = inppw(ioaddr
) ) ;
61 * check for trapped MIPS 3xxx CPU, dump only exception frame
63 if ( READ_WORD(&Xlog
[0x80 / sizeof(Xlog
[0])]) == 0x99999999 )
65 dump_trap_frame (IoAdapter
, &((byte
*)Xlog
)[0x90]) ;
66 IoAdapter
->trapped
= 1 ;
68 regs
[0] = READ_DWORD(&((byte
*)Xlog
)[0x70]);
69 regs
[1] = READ_DWORD(&((byte
*)Xlog
)[0x74]);
70 regs
[2] = READ_DWORD(&((byte
*)Xlog
)[0x78]);
71 regs
[3] = READ_DWORD(&((byte
*)Xlog
)[0x7c]);
72 outpp (addrHi
, (regs
[1] >> 16) & 0x7F) ;
73 outppw (addrLo
, regs
[1] & 0xFFFF) ;
74 xlogDesc
.cnt
= inppw(ioaddr
) ;
75 outpp (addrHi
, (regs
[2] >> 16) & 0x7F) ;
76 outppw (addrLo
, regs
[2] & 0xFFFF) ;
77 xlogDesc
.out
= inppw(ioaddr
) ;
79 regs
[0] &= IoAdapter
->MemorySize
- 1 ;
80 if ( (regs
[0] < IoAdapter
->MemorySize
- 1) )
82 size
= IoAdapter
->MemorySize
- regs
[0] ;
83 if ( size
> MAX_XLOG_SIZE
)
84 size
= MAX_XLOG_SIZE
;
85 for ( i
= 0 ; i
< (size
/ sizeof(*Xlog
)) ; regs
[0] += 2 )
87 outpp (addrHi
, (regs
[0] >> 16) & 0x7F) ;
88 outppw (addrLo
, regs
[0] & 0xFFFF) ;
89 Xlog
[i
++] = inppw(ioaddr
) ;
91 dump_xlog_buffer (IoAdapter
, &xlogDesc
) ;
92 diva_os_free (0, Xlog
) ;
93 IoAdapter
->trapped
= 2 ;
95 outpp (addrHi
, (byte
)((BRI_UNCACHED_ADDR (IoAdapter
->MemoryBase
+ IoAdapter
->MemorySize
-
96 BRI_SHARED_RAM_SIZE
)) >> 16)) ;
97 outppw (addrLo
, 0x00) ;
99 /* ---------------------------------------------------------------------
101 --------------------------------------------------------------------- */
102 static void reset_bri_hardware (PISDN_ADAPTER IoAdapter
) {
103 outpp (IoAdapter
->ctlReg
, 0x00) ;
105 /* ---------------------------------------------------------------------
107 --------------------------------------------------------------------- */
108 static void stop_bri_hardware (PISDN_ADAPTER IoAdapter
) {
109 if (IoAdapter
->reset
) {
110 outpp (IoAdapter
->reset
, 0x00) ; /* disable interrupts ! */
112 outpp (IoAdapter
->ctlReg
, 0x00) ; /* clear int, halt cpu */
114 #if !defined(DIVA_USER_MODE_CARD_CONFIG) /* { */
115 /* ---------------------------------------------------------------------
116 Load protocol on the card
117 --------------------------------------------------------------------- */
118 static dword
bri_protocol_load (PISDN_ADAPTER IoAdapter
) {
120 word test
, *File
= NULL
;
121 byte
* addrHi
, *addrLo
, *ioaddr
;
122 char *FileName
= &IoAdapter
->Protocol
[0] ;
124 /* -------------------------------------------------------------------
125 Try to load protocol code. 'File' points to memory location
126 that does contain entire protocol code
127 ------------------------------------------------------------------- */
128 if ( !(File
= (word
*)xdiLoadArchive (IoAdapter
, &FileLength
, 0)) )
130 /* -------------------------------------------------------------------
131 Get protocol features and calculate load addresses
132 ------------------------------------------------------------------- */
133 IoAdapter
->features
= diva_get_protocol_file_features ((byte
*)File
,
134 OFFS_PROTOCOL_ID_STRING
,
135 IoAdapter
->ProtocolIdString
,
136 sizeof(IoAdapter
->ProtocolIdString
));
137 IoAdapter
->a
.protocol_capabilities
= IoAdapter
->features
;
138 DBG_LOG(("Loading %s", IoAdapter
->ProtocolIdString
))
139 Addr
= ((dword
)(((byte
*) File
)[OFFS_PROTOCOL_END_ADDR
]))
140 | (((dword
)(((byte
*) File
)[OFFS_PROTOCOL_END_ADDR
+ 1])) << 8)
141 | (((dword
)(((byte
*) File
)[OFFS_PROTOCOL_END_ADDR
+ 2])) << 16)
142 | (((dword
)(((byte
*) File
)[OFFS_PROTOCOL_END_ADDR
+ 3])) << 24) ;
145 IoAdapter
->DspCodeBaseAddr
= (Addr
+ 3) & (~3) ;
146 IoAdapter
->MaxDspCodeSize
= (BRI_UNCACHED_ADDR (IoAdapter
->MemoryBase
+ IoAdapter
->MemorySize
-
148 - IoAdapter
->DspCodeBaseAddr
) & (IoAdapter
->MemorySize
- 1) ;
149 Addr
= IoAdapter
->DspCodeBaseAddr
;
150 ((byte
*) File
)[OFFS_DSP_CODE_BASE_ADDR
] = (byte
) Addr
;
151 ((byte
*) File
)[OFFS_DSP_CODE_BASE_ADDR
+ 1] = (byte
)(Addr
>> 8) ;
152 ((byte
*) File
)[OFFS_DSP_CODE_BASE_ADDR
+ 2] = (byte
)(Addr
>> 16) ;
153 ((byte
*) File
)[OFFS_DSP_CODE_BASE_ADDR
+ 3] = (byte
)(Addr
>> 24) ;
154 IoAdapter
->InitialDspInfo
= 0x80 ;
158 if ( IoAdapter
->features
& PROTCAP_V90D
)
159 IoAdapter
->MaxDspCodeSize
= BRI_V90D_MAX_DSP_CODE_SIZE
;
161 IoAdapter
->MaxDspCodeSize
= BRI_ORG_MAX_DSP_CODE_SIZE
;
162 IoAdapter
->DspCodeBaseAddr
= BRI_CACHED_ADDR (IoAdapter
->MemoryBase
+ IoAdapter
->MemorySize
-
163 BRI_SHARED_RAM_SIZE
- IoAdapter
->MaxDspCodeSize
);
164 IoAdapter
->InitialDspInfo
= (IoAdapter
->MaxDspCodeSize
- BRI_ORG_MAX_DSP_CODE_SIZE
) >> 14 ;
166 DBG_LOG(("DSP code base 0x%08lx, max size 0x%08lx (%08lx,%02x)",
167 IoAdapter
->DspCodeBaseAddr
, IoAdapter
->MaxDspCodeSize
,
168 Addr
, IoAdapter
->InitialDspInfo
))
169 if ( FileLength
> ((IoAdapter
->DspCodeBaseAddr
-
170 BRI_CACHED_ADDR (IoAdapter
->MemoryBase
)) & (IoAdapter
->MemorySize
- 1)) )
173 DBG_FTL(("Protocol code '%s' too big (%ld)", FileName
, FileLength
))
176 addrHi
= IoAdapter
->port
177 + ((IoAdapter
->Properties
.Bus
== BUS_PCI
) ? M_PCI_ADDRH
: ADDRH
) ;
178 addrLo
= IoAdapter
->port
+ ADDR
;
179 ioaddr
= IoAdapter
->port
+ DATA
;
181 * set start address for download (use autoincrement mode !)
185 for ( i
= 0 ; i
< FileLength
; i
+= 2 )
187 if ( (i
& 0x0000FFFF) == 0 )
189 outpp (addrHi
, (byte
)(i
>> 16)) ;
191 outppw (ioaddr
, File
[i
/2]) ;
194 * memory test without second load of file
198 for ( i
= 0 ; i
< FileLength
; i
+= 2 )
200 if ( (i
& 0x0000FFFF) == 0 )
202 outpp (addrHi
, (byte
)(i
>> 16)) ;
204 test
= inppw (ioaddr
) ;
205 if ( test
!= File
[i
/2] )
207 DBG_FTL(("%s: Memory test failed! (%d - 0x%04X/0x%04X)",
208 IoAdapter
->Properties
.Name
, i
, test
, File
[i
/2]))
214 return (FileLength
) ;
216 /******************************************************************************/
219 PISDN_ADAPTER IoAdapter
;
224 } bri_download_info
;
225 static long bri_download_buffer (OsFileHandle
*fp
, long length
, void **addr
) {
226 int buffer_size
= 2048*sizeof(word
);
227 word
*buffer
= (word
*)diva_os_malloc (0, buffer_size
);
228 bri_download_info
*info
;
232 DBG_ERR(("A: out of memory, s_bri at %d", __LINE__
))
235 info
= (bri_download_info
*)fp
->sysLoadDesc
;
236 *addr
= (void *)info
->DownloadPos
;
237 if ( ((dword
) length
) > info
->IoAdapter
->DspCodeBaseAddr
+
238 info
->IoAdapter
->MaxDspCodeSize
- info
->DownloadPos
)
240 DBG_FTL(("%s: out of card memory during DSP download (0x%X)",
241 info
->IoAdapter
->Properties
.Name
,
242 info
->DownloadPos
+ length
))
243 diva_os_free (0, buffer
);
246 for ( len
= 0 ; length
> 0 ; length
-= len
)
248 len
= (length
> buffer_size
? buffer_size
: length
) ;
249 page
= ((long)(info
->DownloadPos
) + len
) & 0xFFFF0000 ;
250 if ( page
!= (long)(info
->DownloadPos
& 0xFFFF0000) )
252 len
= 0x00010000 - (((long)info
->DownloadPos
) & 0x0000FFFF) ;
254 if ( fp
->sysFileRead (fp
, &buffer
[0], len
) != len
) {
255 diva_os_free (0, buffer
);
258 outpp (info
->AddrHi
, (byte
)(info
->DownloadPos
>> 16)) ;
259 outppw (info
->AddrLo
, (word
)info
->DownloadPos
) ;
260 outppw_buffer (info
->Data
, &buffer
[0], (len
+ 1)) ;
262 * memory test without second load of file
264 outpp (info
->AddrHi
, (byte
)(info
->DownloadPos
>> 16)) ;
265 outppw (info
->AddrLo
, (word
)info
->DownloadPos
) ;
266 for ( i
= 0 ; i
< len
; i
+= 2 )
268 if ( (test
= inppw (info
->Data
)) != buffer
[i
/2] )
270 DBG_FTL(("%s: Memory test failed! (0x%lX - 0x%04X/0x%04X)",
271 info
->IoAdapter
->Properties
.Name
,
272 info
->DownloadPos
+ i
, test
, buffer
[i
/2]))
273 diva_os_free (0, buffer
);
277 info
->DownloadPos
+= len
;
279 info
->DownloadPos
= (info
->DownloadPos
+ 3) & (~3) ;
280 diva_os_free (0, buffer
);
283 /******************************************************************************/
284 static dword
bri_telindus_load (PISDN_ADAPTER IoAdapter
, char *DspTelindusFile
)
286 bri_download_info
*pinfo
=\
287 (bri_download_info
*)diva_os_malloc(0, sizeof(*pinfo
));
290 t_dsp_portable_desc download_table
[DSP_MAX_DOWNLOAD_COUNT
] ;
291 word download_count
;
294 DBG_ERR (("A: out of memory s_bri at %d", __LINE__
))
297 if (!(fp
= OsOpenFile (DspTelindusFile
))) {
298 diva_os_free (0, pinfo
);
301 FileLength
= fp
->sysFileSize
;
302 pinfo
->IoAdapter
= IoAdapter
;
303 pinfo
->AddrLo
= IoAdapter
->port
+ ADDR
;
304 pinfo
->AddrHi
= IoAdapter
->port
+\
305 (IoAdapter
->Properties
.Bus
== BUS_PCI
? M_PCI_ADDRH
: ADDRH
);
306 pinfo
->Data
= (word
*)(IoAdapter
->port
+ DATA
) ;
307 pinfo
->DownloadPos
= (IoAdapter
->DspCodeBaseAddr
+\
308 sizeof(dword
) + sizeof(download_table
) + 3) & (~3) ;
309 fp
->sysLoadDesc
= (void *)pinfo
;
310 fp
->sysCardLoad
= bri_download_buffer
;
311 download_count
= DSP_MAX_DOWNLOAD_COUNT
;
312 memset (&download_table
[0], '\0', sizeof(download_table
)) ;
314 * set start address for download (use autoincrement mode !)
316 error
= dsp_read_file (fp
, (word
)(IoAdapter
->cardType
),
317 &download_count
, NULL
, &download_table
[0]) ;
320 DBG_FTL(("download file error: %s", error
))
322 diva_os_free (0, pinfo
);
327 * store # of separate download files extracted from archive
329 pinfo
->DownloadPos
= IoAdapter
->DspCodeBaseAddr
;
330 outpp (pinfo
->AddrHi
, (byte
)(pinfo
->DownloadPos
>> 16)) ;
331 outppw (pinfo
->AddrLo
, (word
)pinfo
->DownloadPos
) ;
332 outppw (pinfo
->Data
, (word
)download_count
) ;
333 outppw (pinfo
->Data
, (word
)0) ;
335 * copy download table to board
337 outppw_buffer (pinfo
->Data
, &download_table
[0], sizeof(download_table
)) ;
338 diva_os_free (0, pinfo
);
339 return (FileLength
) ;
341 /******************************************************************************/
342 static int load_bri_hardware (PISDN_ADAPTER IoAdapter
) {
344 byte
* addrHi
, *addrLo
, *ioaddr
;
346 if ( IoAdapter
->Properties
.Card
!= CARD_MAE
)
350 addrHi
= IoAdapter
->port \
351 + ((IoAdapter
->Properties
.Bus
==BUS_PCI
) ? M_PCI_ADDRH
: ADDRH
);
352 addrLo
= IoAdapter
->port
+ ADDR
;
353 ioaddr
= IoAdapter
->port
+ DATA
;
354 reset_bri_hardware (IoAdapter
) ;
359 outpp (addrHi
, (byte
) 0) ;
360 outppw (addrLo
, (word
) 0) ;
361 outppw (ioaddr
, (word
) 0) ;
363 * clear shared memory
365 outpp (addrHi
, (byte
)((BRI_UNCACHED_ADDR (IoAdapter
->MemoryBase
+ \
366 IoAdapter
->MemorySize
- BRI_SHARED_RAM_SIZE
)) >> 16)) ;
368 for ( i
= 0 ; i
< 0x8000 ; outppw (ioaddr
, 0), ++i
) ;
371 * download protocol and dsp files
373 switch ( IoAdapter
->protocol_id
) {
375 if ( !xdiSetProtocol (IoAdapter
, IoAdapter
->ProtocolSuffix
) )
377 if ( !bri_protocol_load (IoAdapter
) )
379 if ( !bri_telindus_load (IoAdapter
, DSP_TELINDUS_FILE
) )
383 case PROTTYPE_CORNETN
:
384 if ( !xdiSetProtocol (IoAdapter
, IoAdapter
->ProtocolSuffix
) )
386 if (IoAdapter
->ProtocolSuffix
&& *IoAdapter
->ProtocolSuffix
) {
387 sprintf (&IoAdapter
->Protocol
[0],
388 "TE_QSIG.%s", IoAdapter
->ProtocolSuffix
) ;
390 DBG_TRC(("xdiSetProtocol: %s firmware '%s' archive '%s'",
391 IoAdapter
->Properties
.Name
,
392 &IoAdapter
->Protocol
[0], &IoAdapter
->Archive
[0]))
393 if ( !bri_protocol_load (IoAdapter
) )
395 if ( !bri_telindus_load (IoAdapter
, DSP_QSIG_TELINDUS_FILE
) )
402 outpp (addrHi
, (byte
)((BRI_UNCACHED_ADDR (IoAdapter
->MemoryBase
+ \
403 IoAdapter
->MemorySize
- BRI_SHARED_RAM_SIZE
)) >> 16)) ;
404 outppw (addrLo
, 0x1e) ;
410 diva_configure_protocol (IoAdapter
);
412 * start the protocol code
414 outpp (IoAdapter
->ctlReg
, 0x08) ;
416 * wait for signature (max. 3 seconds)
418 for ( i
= 0 ; i
< 300 ; ++i
)
421 outpp (addrHi
, (byte
)((BRI_UNCACHED_ADDR (IoAdapter
->MemoryBase
+ \
422 IoAdapter
->MemorySize
- BRI_SHARED_RAM_SIZE
)) >> 16)) ;
423 outppw (addrLo
, 0x1e) ;
424 test
= (dword
)inppw (ioaddr
) ;
425 if ( test
== 0x4447 )
427 DBG_TRC(("Protocol startup time %d.%02d seconds",
428 (i
/ 100), (i
% 100) ))
432 DBG_FTL(("%s: Adapter selftest failed (0x%04X)!",
433 IoAdapter
->Properties
.Name
, test
))
434 bri_cpu_trapped (IoAdapter
) ;
438 static int load_bri_hardware (PISDN_ADAPTER IoAdapter
) {
442 /******************************************************************************/
443 static int bri_ISR (struct _ISDN_ADAPTER
* IoAdapter
) {
444 if ( !(inpp (IoAdapter
->ctlReg
) & 0x01) )
449 outpp (IoAdapter
->ctlReg
, 0x08) ;
450 IoAdapter
->IrqCount
++ ;
451 if ( IoAdapter
->Initialized
) {
452 diva_os_schedule_soft_isr (&IoAdapter
->isr_soft_isr
);
456 /* --------------------------------------------------------------------------
457 Disable IRQ in the card hardware
458 -------------------------------------------------------------------------- */
459 static void disable_bri_interrupt (PISDN_ADAPTER IoAdapter
) {
460 if ( IoAdapter
->reset
)
462 outpp (IoAdapter
->reset
, 0x00) ; /* disable interrupts ! */
464 outpp (IoAdapter
->ctlReg
, 0x00) ; /* clear int, halt cpu */
466 /* -------------------------------------------------------------------------
467 Fill card entry points
468 ------------------------------------------------------------------------- */
469 void prepare_maestra_functions (PISDN_ADAPTER IoAdapter
) {
470 ADAPTER
*a
= &IoAdapter
->a
;
472 a
->ram_inw
= io_inw
;
473 a
->ram_in_buffer
= io_in_buffer
;
474 a
->ram_look_ahead
= io_look_ahead
;
475 a
->ram_out
= io_out
;
476 a
->ram_outw
= io_outw
;
477 a
->ram_out_buffer
= io_out_buffer
;
478 a
->ram_inc
= io_inc
;
479 IoAdapter
->MemoryBase
= BRI_MEMORY_BASE
;
480 IoAdapter
->MemorySize
= BRI_MEMORY_SIZE
;
481 IoAdapter
->out
= pr_out
;
482 IoAdapter
->dpc
= pr_dpc
;
483 IoAdapter
->tst_irq
= scom_test_int
;
484 IoAdapter
->clr_irq
= scom_clear_int
;
485 IoAdapter
->pcm
= (struct pc_maint
*)MIPS_MAINT_OFFS
;
486 IoAdapter
->load
= load_bri_hardware
;
487 IoAdapter
->disIrq
= disable_bri_interrupt
;
488 IoAdapter
->rstFnc
= reset_bri_hardware
;
489 IoAdapter
->stop
= stop_bri_hardware
;
490 IoAdapter
->trapFnc
= bri_cpu_trapped
;
491 IoAdapter
->diva_isr_handler
= bri_ISR
;
493 Prepare OS dependent functions
495 diva_os_prepare_maestra_functions (IoAdapter
);
497 /* -------------------------------------------------------------------------- */