/[dynamips]/upstream/dynamips-0.2.6-RC3/dev_pa_mc8te1.c
This is repository of my old source code which isn't updated any more. Go to git.rot13.org for current projects!
ViewVC logotype

Contents of /upstream/dynamips-0.2.6-RC3/dev_pa_mc8te1.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 4 - (show annotations)
Sat Oct 6 16:06:49 2007 UTC (12 years, 1 month ago) by dpavlin
File MIME type: text/plain
File size: 8533 byte(s)
dynamips-0.2.6-RC3

1 /*
2 * Cisco C7200 (Predator) Simulation Platform.
3 * Copyright (C) 2005-2006 Christophe Fillot. All rights reserved.
4 *
5 * PA-MC-8TE1 card. Doesn't work at this time.
6 */
7
8 #include <stdio.h>
9 #include <stdlib.h>
10 #include <string.h>
11 #include <unistd.h>
12 #include <errno.h>
13 #include <pthread.h>
14 #include <assert.h>
15
16 #include "mips64.h"
17 #include "dynamips.h"
18 #include "memory.h"
19 #include "device.h"
20 #include "net.h"
21 #include "net_io.h"
22 #include "ptask.h"
23 #include "dev_c7200.h"
24 #include "dev_plx.h"
25
26 /* Debugging flags */
27 #define DEBUG_ACCESS 1
28 #define DEBUG_UNKNOWN 1
29 #define DEBUG_TRANSMIT 1
30 #define DEBUG_RECEIVE 1
31
32 /* SSRAM */
33 #define SSRAM_START 0x10000
34 #define SSRAM_END 0x30000
35
36 /* PA-MC-8TE1 Data */
37 struct pa_mc_data {
38 char *name;
39
40 /* Virtual machine */
41 vm_instance_t *vm;
42
43 /* PCI device information */
44 struct vdevice dev;
45 struct pci_device *pci_dev;
46
47 /* SSRAM device */
48 struct vdevice ssram_dev;
49 char *ssram_name;
50 m_uint8_t ssram_data[0x20000];
51
52 /* PLX9054 */
53 vm_obj_t *plx_obj;
54
55 /* NetIO descriptor */
56 netio_desc_t *nio;
57
58 /* TX ring scanner task id */
59 ptask_id_t tx_tid;
60 };
61
62 /* Log a PA-MC-8TE1 message */
63 #define PA_MC_LOG(d,msg...) vm_log((d)->vm,(d)->name,msg)
64
65 /*
66 * dev_ssram_access
67 */
68 static void *dev_ssram_access(cpu_mips_t *cpu,struct vdevice *dev,
69 m_uint32_t offset,u_int op_size,u_int op_type,
70 m_uint64_t *data)
71 {
72 struct pa_mc_data *d = dev->priv_data;
73
74 if (op_type == MTS_READ)
75 *data = 0;
76
77 if ((offset >= SSRAM_START) && (offset < SSRAM_END))
78 return(&d->ssram_data[offset-SSRAM_START]);
79
80 #if DEBUG_ACCESS
81 if (op_type == MTS_READ) {
82 cpu_log(cpu,d->name,
83 "read access to offset = 0x%x, pc = 0x%llx (size=%u)\n",
84 offset,cpu->pc,op_size);
85 } else {
86 cpu_log(cpu,d->name,"write access to vaddr = 0x%x, pc = 0x%llx, "
87 "val = 0x%llx (size=%u)\n",offset,cpu->pc,*data,op_size);
88 }
89 #endif
90
91 switch(offset) {
92 case 0xfff0c:
93 if (op_type == MTS_READ)
94 *data = 0xdeadbeef;
95 break;
96
97 case 0xfff10:
98 if (op_type == MTS_READ)
99 *data = 0xbeeffeed;
100 break;
101
102 case 0x08: /* max_dsx1 */
103 case 0x10: /* no_buf */
104 case 0x18: /* ev */
105 if (op_type == MTS_READ)
106 *data = 0x0ULL;
107 break;
108
109 case 0x00: /* tx packets */
110 if (op_type == MTS_READ)
111 *data = 0x0;
112 break;
113
114 case 0x04: /* rx packets */
115 if (op_type == MTS_READ)
116 *data = 0x0;
117 break;
118
119 case 0x0c: /* rx drops */
120 if (op_type == MTS_READ)
121 *data = 0;
122 break;
123 }
124
125 return NULL;
126 }
127
128 /* Callback when PLX9054 PCI-to-Local register is written */
129 static void plx9054_doorbell_callback(struct plx_data *plx_data,
130 struct pa_mc_data *pa_data,
131 m_uint32_t val)
132 {
133 printf("DOORBELL: 0x%x\n",val);
134
135 /* Trigger interrupt */
136 vm_set_irq(pa_data->vm,2);
137 vm_set_irq(pa_data->vm,3);
138 }
139
140 /*
141 * pa_mc8te1_access()
142 */
143 static void *pa_mc8te1_access(cpu_mips_t *cpu,struct vdevice *dev,
144 m_uint32_t offset,u_int op_size,u_int op_type,
145 m_uint64_t *data)
146 {
147 struct pa_mc_data *d = dev->priv_data;
148
149 if (op_type == MTS_READ)
150 *data = 0;
151
152 #if DEBUG_ACCESS
153 if (op_type == MTS_READ) {
154 cpu_log(cpu,d->name,"read access to offset = 0x%x, pc = 0x%llx\n",
155 offset,cpu->pc);
156 } else {
157 cpu_log(cpu,d->name,"write access to vaddr = 0x%x, pc = 0x%llx, "
158 "val = 0x%llx\n",offset,cpu->pc,*data);
159 }
160 #endif
161
162 switch(offset) {
163
164 #if DEBUG_UNKNOWN
165 default:
166 if (op_type == MTS_READ) {
167 cpu_log(cpu,d->name,
168 "read from unknown addr 0x%x, pc=0x%llx (size=%u)\n",
169 offset,cpu->pc,op_size);
170 } else {
171 cpu_log(cpu,d->name,
172 "write to unknown addr 0x%x, value=0x%llx, "
173 "pc=0x%llx (size=%u)\n",offset,*data,cpu->pc,op_size);
174 }
175 #endif
176 }
177
178 return NULL;
179 }
180
181 /*
182 * pci_pos_read()
183 */
184 static m_uint32_t pci_pos_read(cpu_mips_t *cpu,struct pci_device *dev,int reg)
185 {
186 struct pa_mc_data *d = dev->priv_data;
187
188 #if DEBUG_ACCESS
189 PA_MC_LOG(d,"read PCI register 0x%x\n",reg);
190 #endif
191
192 switch(reg) {
193 case PCI_REG_BAR0:
194 return(d->dev.phys_addr);
195 default:
196 return(0);
197 }
198 }
199
200 /*
201 * pci_pos_write()
202 */
203 static void pci_pos_write(cpu_mips_t *cpu,struct pci_device *dev,
204 int reg,m_uint32_t value)
205 {
206 struct pa_mc_data *d = dev->priv_data;
207
208 #if DEBUG_ACCESS
209 PA_MC_LOG(d,"write 0x%x to PCI register 0x%x\n",value,reg);
210 #endif
211
212 switch(reg) {
213 case PCI_REG_BAR0:
214 //vm_map_device(cpu->vm,&d->dev,(m_uint64_t)value);
215 PA_MC_LOG(d,"registers are mapped at 0x%x\n",value);
216 break;
217 }
218 }
219
220 /*
221 * dev_c7200_pa_mc8te1_init()
222 *
223 * Add a PA-MC-8TE1 port adapter into specified slot.
224 */
225 int dev_c7200_pa_mc8te1_init(c7200_t *router,char *name,u_int pa_bay)
226 {
227 struct pa_mc_data *d;
228
229 /* Allocate the private data structure for PA-MC-8TE1 chip */
230 if (!(d = malloc(sizeof(*d)))) {
231 fprintf(stderr,"%s (PA-MC-8TE1): out of memory\n",name);
232 return(-1);
233 }
234
235 memset(d,0,sizeof(*d));
236 d->name = name;
237 d->vm = router->vm;
238
239 /* Set the EEPROM */
240 c7200_pa_set_eeprom(router,pa_bay,cisco_eeprom_find_pa("PA-MC-8TE1"));
241
242 /* Create the PM7380 */
243 d->pci_dev = pci_dev_add(router->pa_bay[pa_bay].pci_map,name,
244 0x11f8, 0x7380,
245 0,0,C7200_NETIO_IRQ,d,
246 NULL,pci_pos_read,pci_pos_write);
247
248 /* Initialize SSRAM device */
249 d->ssram_name = dyn_sprintf("%s_ssram",name);
250 dev_init(&d->ssram_dev);
251 d->ssram_dev.name = d->ssram_name;
252 d->ssram_dev.priv_data = d;
253 d->ssram_dev.handler = dev_ssram_access;
254
255 /* Create the PLX9054 */
256 d->plx_obj = dev_plx9054_init(d->vm,d->name,
257 router->pa_bay[pa_bay].pci_map,1,
258 &d->ssram_dev,NULL);
259
260 /* Set callback function for PLX9054 PCI-To-Local doorbell */
261 dev_plx_set_pci2loc_doorbell_cbk(d->plx_obj->data,
262 (dev_plx_doorbell_cbk)
263 plx9054_doorbell_callback,
264 d);
265
266 /* Store device info into the router structure */
267 return(c7200_pa_set_drvinfo(router,pa_bay,d));
268 }
269
270 /* Remove a PA-POS-OC3 from the specified slot */
271 int dev_c7200_pa_mc8te1_shutdown(c7200_t *router,u_int pa_bay)
272 {
273 struct c7200_pa_bay *bay;
274 struct pa_mc_data *d;
275
276 if (!(bay = c7200_pa_get_info(router,pa_bay)))
277 return(-1);
278
279 d = bay->drv_info;
280
281 /* Remove the PA EEPROM */
282 c7200_pa_unset_eeprom(router,pa_bay);
283
284 /* Remove the PCI device */
285 pci_dev_remove(d->pci_dev);
286
287 /* Remove the PLX9054 chip */
288 vm_object_remove(d->vm,d->plx_obj);
289
290 /* Remove the device from the CPU address space */
291 //vm_unbind_device(router->vm,&d->dev);
292 vm_unbind_device(router->vm,&d->ssram_dev);
293
294 cpu_group_rebuild_mts(router->vm->cpu_group);
295
296 /* Free the device structure itself */
297 free(d);
298 return(0);
299 }
300
301 /* Bind a Network IO descriptor to a specific port */
302 int dev_c7200_pa_mc8te1_set_nio(c7200_t *router,u_int pa_bay,u_int port_id,
303 netio_desc_t *nio)
304 {
305 struct pa_mc_data *d;
306
307 if ((port_id > 0) || !(d = c7200_pa_get_drvinfo(router,pa_bay)))
308 return(-1);
309
310 if (d->nio != NULL)
311 return(-1);
312
313 d->nio = nio;
314 //d->tx_tid = ptask_add((ptask_callback)dev_pos_oc3_handle_txring,d,NULL);
315 //netio_rxl_add(nio,(netio_rx_handler_t)dev_pos_oc3_handle_rxring,d,NULL);
316 return(0);
317 }
318
319 /* Bind a Network IO descriptor to a specific port */
320 int dev_c7200_pa_mc8te1_unset_nio(c7200_t *router,u_int pa_bay,u_int port_id)
321 {
322 struct pa_mc_data *d;
323
324 if ((port_id > 0) || !(d = c7200_pa_get_drvinfo(router,pa_bay)))
325 return(-1);
326
327 if (d->nio) {
328 ptask_remove(d->tx_tid);
329 netio_rxl_remove(d->nio);
330 d->nio = NULL;
331 }
332 return(0);
333 }
334
335 /* PA-MC-8TE1 driver */
336 struct c7200_pa_driver dev_c7200_pa_mc8te1_driver = {
337 "PA-MC-8TE1", 0,
338 dev_c7200_pa_mc8te1_init,
339 dev_c7200_pa_mc8te1_shutdown,
340 dev_c7200_pa_mc8te1_set_nio,
341 dev_c7200_pa_mc8te1_unset_nio,
342 NULL,
343 };

  ViewVC Help
Powered by ViewVC 1.1.26