Statistics
| Branch: | Tag: | Revision:

root / firmware / fx2 / lib / isr.c @ 70eae1d2

History | View | Annotate | Download (3.9 kB)

1
/* -*- c++ -*- */
2
/*
3
 * Copyright 2003 Free Software Foundation, Inc.
4
 * 
5
 * This file is part of GNU Radio
6
 * 
7
 * GNU Radio is free software; you can redistribute it and/or modify
8
 * it under the terms of the GNU General Public License as published by
9
 * the Free Software Foundation; either version 3, or (at your option)
10
 * any later version.
11
 * 
12
 * GNU Radio is distributed in the hope that it will be useful,
13
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15
 * GNU General Public License for more details.
16
 * 
17
 * You should have received a copy of the GNU General Public License
18
 * along with GNU Radio; see the file COPYING.  If not, write to
19
 * the Free Software Foundation, Inc., 51 Franklin Street,
20
 * Boston, MA 02110-1301, USA.
21
 */
22

    
23
#include "isr.h"
24
#include "fx2regs.h"
25
#include "syncdelay.h"
26

    
27
extern xdata unsigned char _standard_interrupt_vector[];
28
extern xdata unsigned char _usb_autovector[];
29
extern xdata unsigned char _fifo_gpif_autovector[];
30

    
31
#define LJMP_OPCODE        0x02
32

    
33
/*
34
 * Hook standard interrupt vector.
35
 *
36
 * vector_number is from the SV_<foo> list.
37
 * addr is the address of the interrupt service routine.
38
 */
39
void 
40
hook_sv (unsigned char vector_number, unsigned short addr)
41
{
42
  bit        t;
43
  
44
  // sanity checks
45

    
46
  if (vector_number < SV_MIN || vector_number > SV_MAX)
47
    return;
48

    
49
  if ((vector_number & 0x0f) != 0x03 && (vector_number & 0x0f) != 0x0b)
50
    return;
51

    
52
  t = EA;
53
  EA = 0;
54
  _standard_interrupt_vector[vector_number] = LJMP_OPCODE;
55
  _standard_interrupt_vector[vector_number + 1] = addr >> 8;
56
  _standard_interrupt_vector[vector_number + 2] = addr & 0xff;
57
  EA = t;
58
}
59

    
60
/*
61
 * Hook usb interrupt vector.
62
 *
63
 * vector_number is from the UV_<foo> list.
64
 * addr is the address of the interrupt service routine.
65
 */
66
void 
67
hook_uv (unsigned char vector_number, unsigned short addr)
68
{
69
  bit        t;
70
  
71
  // sanity checks
72

    
73
  if (vector_number < UV_MIN || vector_number > UV_MAX)
74
    return;
75

    
76
  if ((vector_number & 0x3) != 0)
77
    return;
78

    
79
  t = EA;
80
  EA = 0;
81
  _usb_autovector[vector_number] = LJMP_OPCODE;
82
  _usb_autovector[vector_number + 1] = addr >> 8;
83
  _usb_autovector[vector_number + 2] = addr & 0xff;
84
  EA = t;
85
}
86

    
87
/*
88
 * Hook fifo/gpif interrupt vector.
89
 *
90
 * vector_number is from the FGV_<foo> list.
91
 * addr is the address of the interrupt service routine.
92
 */
93
void 
94
hook_fgv (unsigned char vector_number, unsigned short addr)
95
{
96
  bit        t;
97
  
98
  // sanity checks
99

    
100
  if (vector_number < FGV_MIN || vector_number > FGV_MAX)
101
    return;
102

    
103
  if ((vector_number & 0x3) != 0)
104
    return;
105

    
106
  t = EA;
107
  EA = 0;
108
  _fifo_gpif_autovector[vector_number] = LJMP_OPCODE;
109
  _fifo_gpif_autovector[vector_number + 1] = addr >> 8;
110
  _fifo_gpif_autovector[vector_number + 2] = addr & 0xff;
111
  EA = t;
112
}
113

    
114
/*
115
 * One time call to enable autovectoring for both USB and FIFO/GPIF.
116
 *
117
 * This disables all USB and FIFO/GPIF interrupts and clears
118
 * any pending interrupts too.  It leaves the master USB and FIFO/GPIF
119
 * interrupts enabled.
120
 */
121
void
122
setup_autovectors (void)
123
{
124
  // disable master usb and fifo/gpif interrupt enables
125
  EIUSB = 0;
126
  EIEX4 = 0;
127

    
128
  hook_sv (SV_INT_2, (unsigned short) _usb_autovector);
129
  hook_sv (SV_INT_4, (unsigned short) _fifo_gpif_autovector);
130

    
131
  // disable all fifo interrupt enables
132
  SYNCDELAY;
133
  EP2FIFOIE = 0;        SYNCDELAY;
134
  EP4FIFOIE = 0;        SYNCDELAY;
135
  EP6FIFOIE = 0;        SYNCDELAY;
136
  EP8FIFOIE = 0;        SYNCDELAY;
137

    
138
  // clear all pending fifo irqs        
139
  EP2FIFOIRQ = 0xff;        SYNCDELAY;
140
  EP4FIFOIRQ = 0xff;        SYNCDELAY;
141
  EP6FIFOIRQ = 0xff;        SYNCDELAY;
142
  EP8FIFOIRQ = 0xff;        SYNCDELAY;
143

    
144
  IBNIE  = 0;
145
  IBNIRQ = 0xff;
146
  NAKIE  = 0;
147
  NAKIRQ = 0xff;
148
  USBIE  = 0;
149
  USBIRQ = 0xff;
150
  EPIE   = 0;
151
  EPIRQ  = 0xff;
152
  SYNCDELAY;        GPIFIE = 0;                
153
  SYNCDELAY;        GPIFIRQ = 0xff;
154
  USBERRIE = 0;
155
  USBERRIRQ = 0xff;
156
  CLRERRCNT = 0;
157
  
158
  INTSETUP = bmAV2EN | bmAV4EN | bmINT4IN;
159

    
160
  // clear master irq's for usb and fifo/gpif
161
  EXIF &= ~bmEXIF_USBINT;
162
  EXIF &= ~bmEXIF_IE4;
163
  
164
  // enable master usb and fifo/gpif interrrupts
165
  EIUSB = 1;
166
  EIEX4 = 1;
167
}