source: soft/giet_vm/giet_python/mapping.py@ 508

Last change on this file since 508 was 497, checked in by alain, 12 years ago

Cosmetic

  • Property svn:executable set to *
File size: 110.0 KB
RevLine 
[425]1#!/usr/bin/env python
[305]2
[319]3import sys
4
5##########################################################################################
[305]6# file : giet_mapping.py
7# date : april 2014
8# author : Alain Greiner
[319]9##########################################################################################
10# This file contains the classes required to define a mapping for the GIET_VM.
11# - A 'Mapping' contains a set of 'Cluster' (hardware architecture)
12# a set of 'Vseg' (kernel virtual segments mapping)
13# a set of 'Vspace' (several user applications).
14# - A 'Cluster' contains a set of 'Pseg' (all physical segments in cluster)
15# a set of 'Proc' (processors in cluster)
16# a set of 'Periph' (peripherals in cluster)
17# a set of 'Coproc' (coprocessors in cluster)
18# - A 'Vspace' contains a set of 'Vseg' (user virtual segments mapping)
19# a set of 'Task' (user tasks mapping)
20# - A 'Vseg' contains a set of 'Vobj'
[441]21# - A 'Periph' contains a set of 'Irq' (only for XCU and PIC types )
[319]22# - A 'Coproc' contains a set of 'Cpports' (one port per MWMR channel)
23##########################################################################################
24# Implementation Note
[411]25# The various objects used to describe a mapping are distributed in the PYTHON structure:
[319]26# For example the psegs set is split in several subsets (one subset per cluster),
27# or the tasks set is split in several subsets (one subset per vspace), etc...
28# In the C binary data structure used by the giet_vm, all objects of same type
[406]29# are stored in a linear array (one single array for all psegs for example).
30# For all objects, we compute and store in the PYTHON object itsel a "global index"
31# corresponding to the index in this global array, and this index can be used as
[319]32# a pseudo-pointer to identify a specific object of a given type.
33##########################################################################################
[305]34
[411]35##########################################################################################
36# Various constants
37##########################################################################################
38
39PADDR_WIDTH = 40 # number of bits for physical address
40X_WIDTH = 4 # number of bits encoding x coordinate
41Y_WIDTH = 4 # number of bits encoding y coordinate
42P_WIDTH = 4 # number of bits encoding local proc_id
43VPN_ANTI_MASK = 0x00000FFF # mask virtual address to get offset in a small page
44BPN_MASK = 0xFFE00000 # mask virtual address to get the BPN (big page)
45PERI_INCREMENT = 0x10000 # virtual address increment for replicated global vsegs
46RESET_ADDRESS = 0xBFC00000 # Processor wired boot_address
47MAPPING_SIGNATURE = 0xDACE2014 # Magic number indicating a valid C binary struture
48
49##########################################################################################
50# These global lists must be consistent with enums in mapping_info.h or irq_handler.
51##########################################################################################
[319]52PERIPHTYPES = [
53 'CMA',
54 'DMA',
55 'FBF',
56 'IOB',
57 'IOC',
58 'MMC',
59 'MWR',
60 'NIC',
61 'ROM',
62 'SIM',
63 'TIM',
64 'TTY',
65 'XCU',
66 'PIC',
[491]67 'DROM',
[319]68 ]
69
70PERIPHSUBTYPES = [
71 'BDV',
72 'HBA',
73 'SPI',
74 'NONE',
75 ]
76
77IRQTYPES = [
78 'HWI',
79 'WTI',
80 'PTI',
81 ]
82
83ISRTYPES = [
84 'ISR_DEFAULT',
85 'ISR_TICK',
86 'ISR_TTY_RX',
87 'ISR_TTY_TX',
88 'ISR_BDV',
89 'ISR_TIMER',
90 'ISR_WAKUP',
91 'ISR_NIC_RX',
92 'ISR_NIC_TX',
93 'ISR_CMA',
94 'ISR_MMC',
95 'ISR_DMA',
96 'ISR_SPI',
97 ]
98
99VOBJTYPES = [
100 'ELF',
101 'BLOB',
102 'PTAB',
103 'PERI',
104 'MWMR',
105 'LOCK',
106 'BUFFER',
107 'BARRIER',
108 'CONST',
109 'MEMSPACE',
110 'SCHED',
[471]111 'HEAP',
[319]112 ]
113
114VSEGMODES = [
115 '____',
116 '___U',
117 '__W_',
118 '__WU',
119 '_X__',
120 '_X_U',
121 '_XW_',
122 '_XWU',
123 'C___',
124 'C__U',
125 'C_W_',
126 'C_WU',
127 'CX__',
128 'CX_U',
129 'CXW_',
130 'CXWU',
131 ]
132
133PSEGTYPES = [
134 'RAM',
135 'ROM', # deprecated => use PERI
136 'PERI',
137 ]
138
139CP_PORT_DIRS = [
140 'TO_COPROC',
141 'FROM_COPROC',
142 ]
143
144##########################################################################################
[305]145class Mapping( object ):
[319]146##########################################################################################
[305]147 def __init__( self,
[411]148 name, # mapping name
149 x_size, # number of clusters in a row
150 y_size, # number of clusters in a column
[421]151 nprocs, # max number of processors per cluster
[411]152 x_width = X_WIDTH, # number of bits encoding x coordinate
153 y_width = Y_WIDTH, # number of bits encoding y coordinate
154 p_width = P_WIDTH, # number of bits encoding local proc_id
155 paddr_width = PADDR_WIDTH, # number of bits for physical address
156 coherence = 1, # hardware cache coherence when non-zero
157 irq_per_proc = 1, # number or IRQs from XCU to processor
158 use_ramdisk = False, # use ramdisk when true
159 x_io = 0, # cluster_io x coordinate
160 y_io = 0, # cluster_io y coordinate
161 peri_increment = PERI_INCREMENT, # address increment for globals
162 reset_address = RESET_ADDRESS, # Processor wired boot_address
163 ram_base = 0, # RAM physical base in cluster[0,0]
164 ram_size = 0 ): # RAM size in each cluster (bytes)
[305]165
[411]166 assert ( x_size <= (1<<X_WIDTH) )
167 assert ( y_size <= (1<<Y_WIDTH) )
168 assert ( nprocs <= (1<<P_WIDTH) )
[406]169
[411]170 self.signature = MAPPING_SIGNATURE
[319]171 self.name = name
[497]172 self.name = name
[406]173 self.paddr_width = paddr_width
[319]174 self.coherence = coherence
175 self.x_size = x_size
176 self.y_size = y_size
[441]177 self.nprocs = nprocs
[319]178 self.x_width = x_width
179 self.y_width = y_width
[406]180 self.p_width = p_width
[319]181 self.irq_per_proc = irq_per_proc
182 self.use_ramdisk = use_ramdisk
183 self.x_io = x_io
184 self.y_io = y_io
[328]185 self.peri_increment = peri_increment
[319]186 self.reset_address = reset_address
[356]187 self.ram_base = ram_base
188 self.ram_size = ram_size
[305]189
[319]190 self.total_vspaces = 0
191 self.total_globals = 0
192 self.total_psegs = 0
193 self.total_vsegs = 0
194 self.total_vobjs = 0
195 self.total_tasks = 0
196 self.total_procs = 0
197 self.total_irqs = 0
198 self.total_coprocs = 0
199 self.total_cpports = 0
200 self.total_periphs = 0
[305]201
[319]202 self.clusters = []
203 self.globs = []
204 self.vspaces = []
[305]205
[319]206 for x in xrange( self.x_size ):
207 for y in xrange( self.y_size ):
208 cluster = Cluster( x , y )
[406]209 cluster.index = (x * self.y_size) + y
[319]210 self.clusters.append( cluster )
[305]211
212 return
213
[319]214 ########################## add a ram pseg in a cluster
[406]215 def addRam( self,
[319]216 name, # pseg name
217 base, # pseg base address
218 size ): # pseg length (bytes)
[406]219
[497]220 # computes cluster index and coordinates from the base address
[356]221 paddr_lsb_width = self.paddr_width - self.x_width - self.y_width
222 cluster_xy = base >> paddr_lsb_width
[497]223 x = cluster_xy >> (self.y_width);
224 y = cluster_xy & ((1 << self.y_width) - 1)
225 cluster_id = (x * self.y_size) + y
[305]226
[411]227 assert (base & VPN_ANTI_MASK) == 0
[319]228
229 assert (x < self.x_size) and (y < self.y_size)
[406]230
[356]231 assert ( (base & ((1<<paddr_lsb_width)-1)) == self.ram_base )
232
233 assert ( size == self.ram_size )
234
[319]235 # add one pseg in the mapping
236 pseg = Pseg( name, base, size, x, y, 'RAM' )
237 self.clusters[cluster_id].psegs.append( pseg )
238 pseg.index = self.total_psegs
239 self.total_psegs += 1
240
241 return pseg
242
243 ############################## add a peripheral and the associated pseg in a cluster
[406]244 def addPeriph( self,
[319]245 name, # associated pseg name
246 base, # associated pseg base address
247 size, # associated pseg length (bytes)
[406]248 ptype, # peripheral type
[319]249 subtype = 'NONE', # peripheral subtype
250 channels = 1, # number of channels
251 arg = 0 ): # optional argument (semantic depends on ptype)
252
[497]253 # computes cluster index and coordinates from the base address
[319]254 cluster_xy = base >> (self.paddr_width - self.x_width - self.y_width)
[497]255 x = cluster_xy >> (self.y_width);
256 y = cluster_xy & ((1 << self.y_width) - 1)
257 cluster_id = (x * self.y_size) + y
[305]258
[319]259 assert (x < self.x_size) and (y < self.y_size)
260
[411]261 assert (base & VPN_ANTI_MASK) == 0
[319]262
263 assert ptype in PERIPHTYPES
264
265 assert subtype in PERIPHSUBTYPES
266
267 # add one pseg into mapping
268 pseg = Pseg( name, base, size, x, y, 'PERI' )
269 self.clusters[cluster_id].psegs.append( pseg )
270 pseg.index = self.total_psegs
271 self.total_psegs += 1
272
273 # add one periph into mapping
[406]274 periph = Periph( pseg, ptype, subtype, channels, arg )
[319]275 self.clusters[cluster_id].periphs.append( periph )
276 periph.index = self.total_periphs
277 self.total_periphs += 1
278
279 return periph
280
281 ################################ add an IRQ in a peripheral
282 def addIrq( self,
283 periph, # peripheral containing IRQ (PIC or XCU)
284 index, # peripheral input port index
285 isrtype, # ISR type
286 channel = 0 ): # channel for multi-channels ISR
287
288 assert isrtype in ISRTYPES
289
290 assert index < 32
291
[406]292 # add one irq into mapping
[319]293 irq = Irq( 'HWI', index , isrtype, channel )
294 periph.irqs.append( irq )
295 irq.index = self.total_irqs
296 self.total_irqs += 1
297
298 return irq
299
300 ########################## add a processor in a cluster
[406]301 def addProc( self,
[319]302 x, # cluster x coordinate
303 y, # cluster y coordinate
304 p ): # processor local index
305
306 assert (x < self.x_size) and (y < self.y_size)
307
308 cluster_id = (x * self.y_size) + y
309
[406]310 # add one proc into mapping
[319]311 proc = Processor( x, y, p )
312 self.clusters[cluster_id].procs.append( proc )
313 proc.index = self.total_procs
[305]314 self.total_procs += 1
315
[319]316 return proc
317
318 ############################## add a coprocessor in a cluster
[406]319 def addCoproc( self,
[319]320 name, # associated pseg name
321 base, # associated pseg base address
322 size ): # associated pseg length
[406]323
[319]324 # check cluster coordinates (obtained from the base address)
325 cluster_xy = base >> (self.paddr_width - self.x_width - self.y_width)
326 x = cluster_xy >> (self.y_width);
[406]327 y = cluster_xy & ((1 << self.y_width) - 1)
[319]328
329 assert (x < self.x_size) and (y < self.y_size)
330
331 cluster_id = (x * self.y_size) + y
332
333 # add one pseg into mapping
334 pseg = Pseg( name, base, size, x, y, 'PERI' )
335 self.clusters[cluster_id].psegs.append( pseg )
336 pseg.index = self.total_psegs
337 self.total_psegs += 1
338
339 # add one coproc into mapping
[406]340 periph = Coproc( pseg )
[319]341 self.clusters[cluster_id].coprocs.append( coproc )
342 periph.index = self.total_coprocs
343 self.total_coprocs += 1
344
345 return coproc
346
[406]347 ################################## add a port in a coprocessor
348 def addPort( self,
[319]349 coproc, # coprocessor containing the port
350 direction, # direction (TO_COPROC / FROM_COPROC)
351 vspacename, # name of vspace using the coproc
352 mwmrname ): # name of the vobj defining the MWMR channel
353
354 assert direction in CP_PORT_DIRS
355
356 # add one cpport into mapping
357 port = Cpport( direction, vspacename, mwmrname )
358 coproc.ports.append( port )
359 port.index = self.total_cpports
360 self.total_cpports += 1
361
362 return port
363
[411]364 ############################ add one global vseg into mapping
365 def addGlobal( self,
366 name, # vseg name
367 vbase, # virtual base address
368 size, # vobj length (bytes)
369 mode, # CXWU flags
370 vtype, # vobj type
371 x, # destination x coordinate
372 y, # destination y coordinate
373 pseg, # destination pseg name
374 identity = False, # identity mapping required if true
375 binpath = '', # pathname for binary code if required
376 align = 0, # alignment required
377 local = False, # only mapped in local PTAB if true
378 big = False ): # to be mapped in a big physical page
[319]379
380 assert mode in VSEGMODES
381
382 assert vtype in VOBJTYPES
383
384 assert (x < self.x_size) and (y < self.y_size)
385
[411]386 # two global vsegs must not overlap if they have different names
387 for prev in self.globs:
388 prev_vbase = prev.vbase
389 prev_size = prev.vobjs[0].length
390
391 if ( ((prev_vbase + prev_size) > vbase ) and
392 ((vbase + size) > prev_vbase) and
393 (prev.name != name) ):
394 print '[genmap error] in addGlobal() : %s overlap %s' % (name, prev.name)
395 print ' %s : base = %x / size = %x' %( name, vbase, size )
396 print ' %s : base = %x / size = %x' %( prev.name, prev_vbase, prev_size )
397 sys.exit(1)
398
[328]399 # add one vseg into mapping
[406]400 vseg = Vseg( name, vbase, mode, x, y, pseg,
[411]401 identity = identity, local = local, big = big )
[348]402
[328]403 self.globs.append( vseg )
404 self.total_globals += 1
[406]405 vseg.index = self.total_vsegs
[328]406 self.total_vsegs += 1
[406]407
[328]408 # add one vobj into mapping
409 vobj = Vobj( name, size, vtype, binpath, 0, 0 )
410 vseg.vobjs.append( vobj )
411 vobj.index = self.total_vobjs
412 self.total_vobjs += 1
[319]413
[305]414 return
415
[319]416 ################################ add a vspace into mapping
[406]417 def addVspace( self,
[319]418 name, # vspace name
419 startname ): # name of vobj containing start_vector
420
421 # add one vspace into mapping
422 vspace = Vspace( name, startname )
[305]423 self.vspaces.append( vspace )
[319]424 vspace.index = self.total_vspaces
425 self.total_vspaces += 1
426
427 return vspace
[406]428
[319]429 ################################# add a private vseg and a vobj in a vspace
430 def addVseg( self,
[406]431 vspace, # vspace containing the vseg
[319]432 name, # vseg name
433 vbase, # virtual base address
434 size, # vobj length (bytes)
435 mode, # CXWU flags
436 vtype, # vobj type
437 x, # destination x coordinate
438 y, # destination y coordinate
439 pseg, # destination pseg name
[348]440 binpath = '', # pathname for binary code
441 align = 0, # alignment required
442 init = 0, # initial value
[411]443 local = False, # only mapped in local PTAB if true
444 big = False ): # to be mapped in a big physical page
[319]445
446 assert mode in VSEGMODES
447
448 assert vtype in VOBJTYPES
449
450 assert (x < self.x_size) and (y < self.y_size)
451
452 # add one vseg into mapping
[411]453 vseg = Vseg( name, vbase, mode, x, y, pseg, local = local, big = big )
[319]454 vspace.vsegs.append( vseg )
455 vseg.index = self.total_vsegs
456 self.total_vsegs += 1
457
458 # add one vobj into mapping
459 vobj = Vobj( name, size, vtype, binpath, align, init )
460 vseg.vobjs.append( vobj )
461 vobj.index = self.total_vobjs
462 self.total_vobjs += 1
463
464 return vseg
465
466 ################################ add a vobj in a private vseg
[406]467 def addVobj( self,
[319]468 vseg, # vseg containing vobj
469 name, # vobj name
470 size, # vobj length (bytes)
471 vtype, # vobj type
472 binpath = '', # pathname to binary
473 align = 0, # alignment constraint
474 init = 0 ): # initial value
475
476 assert vtype in VOBJTYPES
477
478 # add one vobj into mapping
479 vobj = Vobj( name, size, vtype, binpath, align, init )
480 vseg.vobjs.append( vobj )
481 vobj.index = self.total_vobjs
482 self.total_vobjs += 1
483
484 return vobj
485
[406]486 ################################ add a task in a vspace
487 def addTask( self,
[319]488 vspace, # vspace containing task
489 name, # task name
490 trdid, # task index in vspace
491 x, # destination x coordinate
492 y, # destination y coordinate
493 lpid, # destination processor local index
494 stackname, # name of vobj containing stack
495 heapname, # name of vobj containing heap
[441]496 startid ): # index in start_vector
[406]497
[319]498 assert (x < self.x_size) and (y < self.y_size)
[411]499 assert lpid < self.nprocs
[319]500
[406]501 # add one task into mapping
[441]502 task = Task( name, trdid, x, y, lpid, stackname, heapname, startid )
[319]503 vspace.tasks.append( task )
504 task.index = self.total_tasks
505 self.total_tasks += 1
506
507 return task
508
509 #################################
510 def str2bytes( self, nbytes, s ): # string => nbytes_packed byte array
511
512 byte_stream = bytearray()
513 length = len( s )
514 if length < (nbytes - 1):
515 for b in s:
516 byte_stream.append( b )
517 for x in xrange(nbytes-length):
518 byte_stream.append( '\0' )
519 else:
[348]520 print '[genmap error] in str2bytes() : string %s too long' % s
[319]521 sys.exit(1)
522
523 return byte_stream
524
525 ###################################
[406]526 def int2bytes( self, nbytes, val ): # integer => nbytes litle endian byte array
[319]527
528 byte_stream = bytearray()
529 for n in xrange( nbytes ):
530 byte_stream.append( (val >> (n<<3)) & 0xFF )
531
532 return byte_stream
533
[411]534 ####################################################################################
535 def xml( self ): # compute string for map.xml file generation
[319]536
[305]537 s = '<?xml version="1.0"?>\n\n'
[319]538 s += '<mapping_info signature = "0x%x"\n' % (self.signature)
[305]539 s += ' name = "%s"\n' % (self.name)
540 s += ' x_size = "%d"\n' % (self.x_size)
541 s += ' y_size = "%d"\n' % (self.y_size)
542 s += ' x_width = "%d"\n' % (self.x_width)
543 s += ' y_width = "%d"\n' % (self.y_width)
544 s += ' irq_per_proc = "%d"\n' % (self.irq_per_proc)
[319]545 s += ' use_ramdisk = "%d"\n' % (self.use_ramdisk)
[305]546 s += ' x_io = "%d"\n' % (self.x_io)
547 s += ' y_io = "%d" >\n' % (self.y_io)
[319]548 s += '\n'
549
[305]550 s += ' <clusterset>\n'
551 for x in xrange ( self.x_size ):
552 for y in xrange ( self.y_size ):
[406]553 cluster_id = (x * self.y_size) + y
[319]554 s += self.clusters[cluster_id].xml()
[305]555 s += ' </clusterset>\n'
[319]556 s += '\n'
557
[305]558 s += ' <globalset>\n'
[319]559 for vseg in self.globs: s += vseg.xml()
[305]560 s += ' </globalset>\n'
[319]561 s += '\n'
562
[305]563 s += ' <vspaceset>\n'
[319]564 for vspace in self.vspaces: s += vspace.xml()
[305]565 s += ' </vspaceset>\n'
[319]566
[305]567 s += '</mapping_info>\n'
568 return s
[319]569
[411]570 #####################################################################################
571 def cbin( self, verbose ): # C binary structure for map.bin file generation
[319]572
573 byte_stream = bytearray()
574
575 # header
576 byte_stream += self.int2bytes(4, self.signature)
[406]577 byte_stream += self.int2bytes(4, self.x_size)
578 byte_stream += self.int2bytes(4, self.y_size)
579 byte_stream += self.int2bytes(4, self.x_width)
580 byte_stream += self.int2bytes(4, self.y_width)
581 byte_stream += self.int2bytes(4, self.x_io)
582 byte_stream += self.int2bytes(4, self.y_io)
583 byte_stream += self.int2bytes(4, self.irq_per_proc)
584 byte_stream += self.int2bytes(4, self.use_ramdisk)
585 byte_stream += self.int2bytes(4, self.total_globals)
586 byte_stream += self.int2bytes(4, self.total_vspaces)
587 byte_stream += self.int2bytes(4, self.total_psegs)
588 byte_stream += self.int2bytes(4, self.total_vsegs)
589 byte_stream += self.int2bytes(4, self.total_vobjs)
590 byte_stream += self.int2bytes(4, self.total_tasks)
591 byte_stream += self.int2bytes(4, self.total_procs)
592 byte_stream += self.int2bytes(4, self.total_irqs)
593 byte_stream += self.int2bytes(4, self.total_coprocs)
594 byte_stream += self.int2bytes(4, self.total_cpports)
595 byte_stream += self.int2bytes(4, self.total_periphs)
[319]596 byte_stream += self.str2bytes(32, self.name)
597
598 if ( verbose ):
[406]599 print '\n'
[319]600 print 'name = %s' % self.name
601 print 'signature = %x' % self.signature
602 print 'x_size = %d' % self.x_size
603 print 'y_size = %d' % self.y_size
604 print 'x_width = %d' % self.x_width
605 print 'y_width = %d' % self.y_width
[406]606 print 'x_io = %d' % self.x_io
607 print 'y_io = %d' % self.y_io
[319]608 print 'irq_per_proc = %d' % self.irq_per_proc
609 print 'use_ramdisk = %d' % self.use_ramdisk
610 print 'total_globals = %d' % self.total_globals
[406]611 print 'total_psegs = %d' % self.total_psegs
612 print 'total_vsegs = %d' % self.total_vsegs
613 print 'total_vobjs = %d' % self.total_vobjs
614 print 'total_tasks = %d' % self.total_tasks
615 print 'total_procs = %d' % self.total_procs
616 print 'total_irqs = %d' % self.total_irqs
[319]617 print 'total_coprocs = %d' % self.total_coprocs
618 print 'total_cpports = %d' % self.total_cpports
619 print 'total_periphs = %d' % self.total_periphs
[406]620 print '\n'
[319]621
622 # clusters array
623 index = 0
624 for cluster in self.clusters:
625 byte_stream += cluster.cbin( self, verbose, index )
626 index += 1
627
628 if ( verbose ): print '\n'
629
630 # psegs array
631 index = 0
632 for cluster in self.clusters:
[406]633 for pseg in cluster.psegs:
[319]634 byte_stream += pseg.cbin( self, verbose, index, cluster )
635 index += 1
636
637 if ( verbose ): print '\n'
638
639 # vspaces array
640 index = 0
[406]641 for vspace in self.vspaces:
642 byte_stream += vspace.cbin( self, verbose, index )
[319]643 index += 1
644
645 if ( verbose ): print '\n'
646
647 # vsegs array
648 index = 0
649 for vseg in self.globs:
650 byte_stream += vseg.cbin( self, verbose, index )
651 index += 1
652 for vspace in self.vspaces:
[406]653 for vseg in vspace.vsegs:
[319]654 byte_stream += vseg.cbin( self, verbose, index )
655 index += 1
656
657 if ( verbose ): print '\n'
658
659 # vobjs array
660 index = 0
661 for vseg in self.globs:
662 for vobj in vseg.vobjs:
663 byte_stream += vobj.cbin( self, verbose, index )
664 index += 1
665 for vspace in self.vspaces:
[406]666 for vseg in vspace.vsegs:
[319]667 for vobj in vseg.vobjs:
[406]668 byte_stream += vobj.cbin( self, verbose, index )
[319]669 index += 1
670
671 if ( verbose ): print '\n'
672
673 # tasks array
674 index = 0
675 for vspace in self.vspaces:
[406]676 for task in vspace.tasks:
[319]677 byte_stream += task.cbin( self, verbose, index, vspace )
678 index += 1
679
680 if ( verbose ): print '\n'
681
682 # procs array
683 index = 0
684 for cluster in self.clusters:
[406]685 for proc in cluster.procs:
[319]686 byte_stream += proc.cbin( self, verbose, index )
687 index += 1
[406]688
[319]689 if ( verbose ): print '\n'
690
691 # irqs array
[406]692 index = 0
[319]693 for cluster in self.clusters:
694 for periph in cluster.periphs:
695 for irq in periph.irqs:
696 byte_stream += irq.cbin( self, verbose, index )
697 index += 1
698
699 if ( verbose ): print '\n'
700
701 # coprocs array
702 index = 0
703 for cluster in self.clusters:
[406]704 for coproc in cluster.coprocs:
705 byte_stream += coproc.cbin( self, verbose, index )
[319]706 index += 1
707
708 if ( verbose ): print '\n'
709
710 # cpports array
711 index = 0
712 for cluster in self.clusters:
[406]713 for coproc in cluster.coprocs:
[319]714 for port in coproc.ports:
715 byte_stream += port.cbin( self, verbose, index )
716 index += 1
717
718 if ( verbose ): print '\n'
719
720 # periphs array
721 index = 0
722 for cluster in self.clusters:
[406]723 for periph in cluster.periphs:
[319]724 byte_stream += periph.cbin( self, verbose, index )
725 index += 1
726
727 return byte_stream
728 # end of cbin()
[406]729
[411]730 ##################################################################################
731 def giet_vsegs( self ): # compute string for giet_vsegs.ld file generation
[319]732 # required by giet_vm compilation
733
[406]734 # search the vsegs required for the giet_vsegs.ld
[319]735 boot_code_found = False
736 boot_data_found = False
737 kernel_uncdata_found = False
738 kernel_data_found = False
739 kernel_code_found = False
740 kernel_init_found = False
741 for vseg in self.globs:
[348]742
[319]743 if ( vseg.name == 'seg_boot_code' ):
[406]744 boot_code_vbase = vseg.vbase
[319]745 boot_code_size = vseg.vobjs[0].length
746 boot_code_found = True
747
[406]748 if ( vseg.name == 'seg_boot_data' ):
749 boot_data_vbase = vseg.vbase
[319]750 boot_data_size = vseg.vobjs[0].length
751 boot_data_found = True
752
753 if ( vseg.name == 'seg_kernel_uncdata' ):
[406]754 kernel_uncdata_vbase = vseg.vbase
[319]755 kernel_uncdata_size = vseg.vobjs[0].length
756 kernel_uncdata_found = True
757
758 if ( vseg.name == 'seg_kernel_data' ):
[406]759 kernel_data_vbase = vseg.vbase
[319]760 kernel_data_size = vseg.vobjs[0].length
761 kernel_data_found = True
762
763 if ( vseg.name == 'seg_kernel_code' ):
[406]764 kernel_code_vbase = vseg.vbase
[319]765 kernel_code_size = vseg.vobjs[0].length
766 kernel_code_found = True
767
768 if ( vseg.name == 'seg_kernel_init' ):
[406]769 kernel_init_vbase = vseg.vbase
[319]770 kernel_init_size = vseg.vobjs[0].length
771 kernel_init_found = True
772
773 # check if all required vsegs have been found
[406]774 if ( boot_code_found == False ):
[348]775 print '[genmap error] in giet_vsegs() : seg_boot_code vseg missing'
[319]776 sys.exit()
777
[406]778 if ( boot_data_found == False ):
[348]779 print '[genmap error] in giet_vsegs() : seg_boot_data vseg missing'
[319]780 sys.exit()
781
[406]782 if ( kernel_data_found == False ):
[348]783 print '[genmap error] in giet_vsegs() : seg_kernel_data vseg missing'
[319]784 sys.exit()
785
786 if ( kernel_uncdata_found == False ):
[348]787 print '[genmap error] in giet_vsegs() : seg_kernel_uncdata vseg missing'
[319]788 sys.exit()
789
790 if ( kernel_code_found == False ):
[348]791 print '[genmap error] in giet_vsegs() : seg_kernel_code vseg missing'
[319]792 sys.exit()
793
794 if ( kernel_init_found == False ):
[348]795 print '[genmap error] in giet_vsegs() : seg_kernel_init vseg missing'
[319]796 sys.exit()
797
798 # build string
[406]799 s = '/* Generated by genmap for %s */\n' % self.name
[319]800 s += '\n'
801
[406]802 s += 'boot_code_vbase = 0x%x;\n' % boot_code_vbase
803 s += 'boot_code_size = 0x%x;\n' % boot_code_size
[319]804 s += '\n'
[406]805 s += 'boot_data_vbase = 0x%x;\n' % boot_data_vbase
806 s += 'boot_data_size = 0x%x;\n' % boot_data_size
[319]807 s += '\n'
[406]808 s += 'kernel_code_vbase = 0x%x;\n' % kernel_code_vbase
809 s += 'kernel_code_size = 0x%x;\n' % kernel_code_size
[319]810 s += '\n'
[406]811 s += 'kernel_data_vbase = 0x%x;\n' % kernel_data_vbase
812 s += 'kernel_data_size = 0x%x;\n' % kernel_data_size
[319]813 s += '\n'
[406]814 s += 'kernel_uncdata_vbase = 0x%x;\n' % kernel_uncdata_vbase
815 s += 'kernel_uncdata_size = 0x%x;\n' % kernel_uncdata_size
[319]816 s += '\n'
[406]817 s += 'kernel_init_vbase = 0x%x;\n' % kernel_init_vbase
818 s += 'kernel_init_size = 0x%x;\n' % kernel_init_size
[319]819 s += '\n'
820
821 return s
[406]822
[411]823 ###################################################################################
824 def hard_config( self ): # compute string for hard_config.h file generation,
825 # required by
[319]826 # - top.cpp compilation
827 # - giet_vm compilation
828 # - tsar_preloader compilation
829
830 nb_total_procs = 0
831
832 # for each peripheral type, define default values
[406]833 # for pbase address, size, number of components, and channels
[319]834 nb_cma = 0
835 cma_channels = 0
836 seg_cma_base = 0xFFFFFFFF
837 seg_cma_size = 0
838
839 nb_dma = 0
840 dma_channels = 0
841 seg_dma_base = 0xFFFFFFFF
842 seg_dma_size = 0
843
844 nb_fbf = 0
845 fbf_channels = 0
[328]846 fbf_arg = 0
[319]847 seg_fbf_base = 0xFFFFFFFF
848 seg_fbf_size = 0
849
850 nb_iob = 0
851 iob_channels = 0
852 seg_iob_base = 0xFFFFFFFF
853 seg_iob_size = 0
854
855 nb_ioc = 0
856 ioc_channels = 0
857 seg_ioc_base = 0xFFFFFFFF
858 seg_ioc_size = 0
859
860 nb_mmc = 0
861 mmc_channels = 0
862 seg_mmc_base = 0xFFFFFFFF
863 seg_mmc_size = 0
864
865 nb_mwr = 0
866 mwr_channels = 0
867 seg_mwr_base = 0xFFFFFFFF
868 seg_mwr_size = 0
869
870 nb_nic = 0
871 nic_channels = 0
872 seg_nic_base = 0xFFFFFFFF
873 seg_nic_size = 0
874
875 nb_pic = 0
876 pic_channels = 0
877 seg_pic_base = 0xFFFFFFFF
878 seg_pic_size = 0
879
880 nb_rom = 0
881 rom_channels = 0
882 seg_rom_base = 0xFFFFFFFF
883 seg_rom_size = 0
884
885 nb_sim = 0
886 sim_channels = 0
887 seg_sim_base = 0xFFFFFFFF
888 seg_sim_size = 0
889
890 nb_tim = 0
891 tim_channels = 0
892 seg_tim_base = 0xFFFFFFFF
893 seg_tim_size = 0
894
895 nb_tty = 0
896 tty_channels = 0
897 seg_tty_base = 0xFFFFFFFF
898 seg_tty_size = 0
899
900 nb_xcu = 0
901 xcu_channels = 0
[328]902 xcu_arg = 0
[319]903 seg_xcu_base = 0xFFFFFFFF
904 seg_xcu_size = 0
905
[491]906 nb_drom = 0
907 drom_channels = 0
908 seg_drom_base = 0xFFFFFFFF
909 seg_drom_size = 0
910
[319]911 use_bdv = False
912 use_spi = False
913 use_hba = False
914
915 # get peripherals attributes
916 for cluster in self.clusters:
917 for periph in cluster.periphs:
[406]918 if ( periph.ptype == 'CMA' ):
[319]919 seg_cma_base = periph.pseg.base & 0xFFFFFFFF
920 seg_cma_size = periph.pseg.size
921 cma_channels = periph.channels
922 nb_cma +=1
923
[406]924 elif ( periph.ptype == 'DMA' ):
925 seg_dma_base = periph.pseg.base & 0xFFFFFFFF
[319]926 seg_dma_size = periph.pseg.size
927 dma_channels = periph.channels
928 nb_dma +=1
929
[406]930 elif ( periph.ptype == 'FBF' ):
[319]931 seg_fbf_base = periph.pseg.base & 0xFFFFFFFF
932 seg_fbf_size = periph.pseg.size
933 fbf_channels = periph.channels
[328]934 fbf_arg = periph.arg
[319]935 nb_fbf +=1
936
937 elif ( periph.ptype == 'IOB' ):
938 seg_iob_base = periph.pseg.base & 0xFFFFFFFF
939 seg_iob_size = periph.pseg.size
940 iob_channels = periph.channels
941 nb_iob +=1
942
[406]943 elif ( periph.ptype == 'IOC' ):
[319]944 seg_ioc_base = periph.pseg.base & 0xFFFFFFFF
945 seg_ioc_size = periph.pseg.size
946 ioc_channels = periph.channels
947 nb_ioc += 1
[404]948
949 if self.use_ramdisk: continue
950
[319]951 if ( periph.subtype == 'BDV' ): use_bdv = True
952 elif ( periph.subtype == 'HBA' ): use_hba = True
953 elif ( periph.subtype == 'SPI' ): use_spi = True
954
955 elif ( periph.ptype == 'MMC' ):
956 seg_mmc_base = periph.pseg.base & 0xFFFFFFFF
957 seg_mmc_size = periph.pseg.size
958 mmc_channels = periph.channels
959 nb_mmc +=1
960
961 elif ( periph.ptype == 'MWR' ):
962 seg_mwr_base = periph.pseg.base & 0xFFFFFFFF
963 seg_wmr_size = periph.pseg.size
964 mwr_channels = periph.channels
965 nb_mwr +=1
966
967 elif ( periph.ptype == 'ROM' ):
968 seg_rom_base = periph.pseg.base & 0xFFFFFFFF
969 seg_rom_size = periph.pseg.size
970 rom_channels = periph.channels
971 nb_rom +=1
972
[491]973 elif ( periph.ptype == 'DROM' ):
974 seg_drom_base = periph.pseg.base & 0xFFFFFFFF
975 seg_drom_size = periph.pseg.size
976 drom_channels = periph.channels
977 nb_drom +=1
978
[319]979 elif ( periph.ptype == 'SIM' ):
980 seg_sim_base = periph.pseg.base & 0xFFFFFFFF
981 seg_sim_size = periph.pseg.size
982 sim_channels = periph.channels
983 nb_sim +=1
984
[406]985 elif ( periph.ptype == 'NIC' ):
[319]986 seg_nic_base = periph.pseg.base & 0xFFFFFFFF
987 seg_nic_size = periph.pseg.size
988 nic_channels = periph.channels
989 nb_nic +=1
990
[406]991 elif ( periph.ptype == 'PIC' ):
[319]992 seg_pic_base = periph.pseg.base & 0xFFFFFFFF
993 seg_pic_size = periph.pseg.size
994 pic_channels = periph.channels
995 nb_pic +=1
[406]996
997 elif ( periph.ptype == 'TIM' ):
[319]998 seg_tim_base = periph.pseg.base & 0xFFFFFFFF
999 seg_tim_size = periph.pseg.size
1000 tim_channels = periph.channels
1001 nb_tim +=1
[406]1002
[319]1003 elif ( periph.ptype == 'TTY' ):
1004 seg_tty_base = periph.pseg.base & 0xFFFFFFFF
1005 seg_tty_size = periph.pseg.size
1006 tty_channels = periph.channels
1007 nb_tty +=1
[406]1008
1009 elif ( periph.ptype == 'XCU' ):
[319]1010 seg_xcu_base = periph.pseg.base & 0xFFFFFFFF
1011 seg_xcu_size = periph.pseg.size
1012 xcu_channels = periph.channels
[328]1013 xcu_arg = periph.arg
[319]1014 nb_xcu +=1
[406]1015
[319]1016 # no more than two access to external peripherals
[406]1017 assert ( nb_fbf <= 2 )
1018 assert ( nb_cma <= 2 )
1019 assert ( nb_ioc <= 2 )
1020 assert ( nb_nic <= 2 )
1021 assert ( nb_tim <= 2 )
1022 assert ( nb_tty <= 2 )
[319]1023 assert ( nb_pic <= 2 )
1024
1025 # one and only one type of IOC controller
[403]1026 nb_iocs = 0
1027 if use_hba : nb_iocs += 1
1028 if use_bdv : nb_iocs += 1
1029 if use_spi : nb_iocs += 1
1030 if self.use_ramdisk: nb_iocs += 1
1031 assert ( nb_iocs == 1 )
[404]1032
[319]1033 # Compute total number of processors
1034 for cluster in self.clusters:
1035 nb_total_procs += len( cluster.procs )
1036
1037 # Compute physical addresses for BOOT vsegs
1038 boot_mapping_found = False
1039 boot_code_found = False
1040 boot_data_found = False
1041 boot_stack_found = False
1042
1043 for vseg in self.globs:
1044 if ( vseg.name == 'seg_boot_mapping' ):
[406]1045 boot_mapping_base = vseg.vbase
[319]1046 boot_mapping_size = vseg.vobjs[0].length
[348]1047 boot_mapping_identity = vseg.identity
[319]1048 boot_mapping_found = True
1049
1050 if ( vseg.name == 'seg_boot_code' ):
[406]1051 boot_code_base = vseg.vbase
[319]1052 boot_code_size = vseg.vobjs[0].length
[348]1053 boot_code_identity = vseg.identity
[319]1054 boot_code_found = True
1055
[406]1056 if ( vseg.name == 'seg_boot_data' ):
1057 boot_data_base = vseg.vbase
[319]1058 boot_data_size = vseg.vobjs[0].length
[348]1059 boot_data_identity = vseg.identity
[319]1060 boot_data_found = True
1061
1062 if ( vseg.name == 'seg_boot_stack' ):
[406]1063 boot_stack_base = vseg.vbase
[319]1064 boot_stack_size = vseg.vobjs[0].length
[348]1065 boot_stack_identity = vseg.identity
[319]1066 boot_stack_found = True
1067
[328]1068 # check that BOOT vsegs are found and identity mapping
[348]1069 if ( (boot_mapping_found == False) or (boot_mapping_identity == False) ):
1070 print '[genmap error] in hard_config() : seg_boot_mapping missing or not ident'
[319]1071 sys.exit()
1072
[406]1073 if ( (boot_code_found == False) or (boot_code_identity == False) ):
[348]1074 print '[genmap error] in hard_config() : seg_boot_code missing or not ident'
[319]1075 sys.exit()
1076
[406]1077 if ( (boot_data_found == False) or (boot_data_identity == False) ):
[348]1078 print '[genmap error] in hard_config() : seg_boot_data missing or not ident'
[319]1079 sys.exit()
1080
[348]1081 if ( (boot_stack_found == False) or (boot_stack_identity == False) ):
1082 print '[genmap error] in giet_vsegs() : seg_boot_stack missing or not ident'
[319]1083 sys.exit()
1084
1085 # Search RAMDISK global vseg if required
1086 seg_rdk_base = 0xFFFFFFFF
1087 seg_rdk_size = 0
1088 seg_rdk_found = False
1089
1090 if self.use_ramdisk:
1091 for vseg in self.globs:
[497]1092 if ( vseg.name == 'seg_ramdisk' ):
[319]1093 seg_rdk_base = vseg.vbase
1094 seg_rdk_size = vseg.vobjs[0].length
1095 seg_rdk_found = True
1096
1097 if ( seg_rdk_found == False ):
1098 print 'Error in hard_config() "seg_ramdisk" not found'
1099 sys.exit(1)
1100
1101 # build string
[406]1102 s = '/* Generated by genmap for %s */\n' % self.name
[319]1103 s += '\n'
1104 s += '#ifndef HARD_CONFIG_H\n'
1105 s += '#define HARD_CONFIG_H\n'
1106 s += '\n'
1107
[406]1108 s += '/* General platform parameters */\n'
[319]1109 s += '\n'
1110 s += '#define X_SIZE %d\n' % self.x_size
1111 s += '#define Y_SIZE %d\n' % self.y_size
1112 s += '#define X_WIDTH %d\n' % self.x_width
1113 s += '#define Y_WIDTH %d\n' % self.y_width
[406]1114 s += '#define P_WIDTH %d\n' % self.p_width
[319]1115 s += '#define X_IO %d\n' % self.x_io
[406]1116 s += '#define Y_IO %d\n' % self.y_io
[411]1117 s += '#define NB_PROCS_MAX %d\n' % self.nprocs
[319]1118 s += '#define IRQ_PER_PROCESSOR %d\n' % self.irq_per_proc
1119 s += '#define RESET_ADDRESS 0x%x\n' % self.reset_address
1120 s += '#define NB_TOTAL_PROCS %d\n' % nb_total_procs
1121 s += '\n'
1122
[406]1123 s += '/* Peripherals */\n'
[319]1124 s += '\n'
1125 s += '#define NB_TTY_CHANNELS %d\n' % tty_channels
1126 s += '#define NB_IOC_CHANNELS %d\n' % ioc_channels
1127 s += '#define NB_NIC_CHANNELS %d\n' % nic_channels
1128 s += '#define NB_CMA_CHANNELS %d\n' % cma_channels
1129 s += '#define NB_TIM_CHANNELS %d\n' % tim_channels
1130 s += '#define NB_DMA_CHANNELS %d\n' % dma_channels
1131 s += '\n'
1132 s += '#define USE_XCU %d\n' % ( nb_xcu != 0 )
1133 s += '#define USE_IOB %d\n' % ( nb_iob != 0 )
1134 s += '#define USE_PIC %d\n' % ( nb_pic != 0 )
1135 s += '#define USE_FBF %d\n' % ( nb_fbf != 0 )
1136 s += '\n'
1137 s += '#define USE_IOC_BDV %d\n' % use_bdv
1138 s += '#define USE_IOC_SPI %d\n' % use_spi
1139 s += '#define USE_IOC_HBA %d\n' % use_hba
[403]1140 s += '#define USE_IOC_RDK %d\n' % self.use_ramdisk
[319]1141 s += '\n'
[328]1142 s += '#define FBUF_X_SIZE %d\n' % fbf_arg
1143 s += '#define FBUF_Y_SIZE %d\n' % fbf_arg
1144 s += '\n'
1145 s += '#define XCU_NB_INPUTS %d\n' % xcu_arg
1146 s += '\n'
[319]1147
[356]1148 s += '/* base addresses and sizes for physical segments */\n'
[319]1149 s += '\n'
[406]1150 s += '#define SEG_RAM_BASE 0x%x\n' % self.ram_base
1151 s += '#define SEG_RAM_SIZE 0x%x\n' % self.ram_size
[356]1152 s += '\n'
[406]1153 s += '#define SEG_CMA_BASE 0x%x\n' % seg_cma_base
1154 s += '#define SEG_CMA_SIZE 0x%x\n' % seg_cma_size
[319]1155 s += '\n'
[406]1156 s += '#define SEG_DMA_BASE 0x%x\n' % seg_dma_base
1157 s += '#define SEG_DMA_SIZE 0x%x\n' % seg_dma_size
[319]1158 s += '\n'
[406]1159 s += '#define SEG_FBF_BASE 0x%x\n' % seg_fbf_base
1160 s += '#define SEG_FBF_SIZE 0x%x\n' % seg_fbf_size
[319]1161 s += '\n'
[406]1162 s += '#define SEG_IOB_BASE 0x%x\n' % seg_iob_base
1163 s += '#define SEG_IOB_SIZE 0x%x\n' % seg_iob_size
[319]1164 s += '\n'
[406]1165 s += '#define SEG_IOC_BASE 0x%x\n' % seg_ioc_base
1166 s += '#define SEG_IOC_SIZE 0x%x\n' % seg_ioc_size
[319]1167 s += '\n'
[406]1168 s += '#define SEG_MMC_BASE 0x%x\n' % seg_mmc_base
1169 s += '#define SEG_MMC_SIZE 0x%x\n' % seg_mmc_size
[319]1170 s += '\n'
[406]1171 s += '#define SEG_MWR_BASE 0x%x\n' % seg_mwr_base
1172 s += '#define SEG_MWR_SIZE 0x%x\n' % seg_mwr_size
[319]1173 s += '\n'
[406]1174 s += '#define SEG_ROM_BASE 0x%x\n' % seg_rom_base
1175 s += '#define SEG_ROM_SIZE 0x%x\n' % seg_rom_size
[319]1176 s += '\n'
[406]1177 s += '#define SEG_SIM_BASE 0x%x\n' % seg_sim_base
1178 s += '#define SEG_SIM_SIZE 0x%x\n' % seg_sim_size
[319]1179 s += '\n'
[406]1180 s += '#define SEG_NIC_BASE 0x%x\n' % seg_nic_base
1181 s += '#define SEG_NIC_SIZE 0x%x\n' % seg_nic_size
[319]1182 s += '\n'
[406]1183 s += '#define SEG_PIC_BASE 0x%x\n' % seg_pic_base
1184 s += '#define SEG_PIC_SIZE 0x%x\n' % seg_pic_size
[319]1185 s += '\n'
[406]1186 s += '#define SEG_TIM_BASE 0x%x\n' % seg_tim_base
1187 s += '#define SEG_TIM_SIZE 0x%x\n' % seg_tim_size
[319]1188 s += '\n'
[406]1189 s += '#define SEG_TTY_BASE 0x%x\n' % seg_tty_base
1190 s += '#define SEG_TTY_SIZE 0x%x\n' % seg_tty_size
[319]1191 s += '\n'
[406]1192 s += '#define SEG_XCU_BASE 0x%x\n' % seg_xcu_base
1193 s += '#define SEG_XCU_SIZE 0x%x\n' % seg_xcu_size
[319]1194 s += '\n'
1195 s += '#define SEG_RDK_BASE 0x%x\n' % seg_rdk_base
1196 s += '#define SEG_RDK_SIZE 0x%x\n' % seg_rdk_size
1197 s += '\n'
[491]1198 s += '#define SEG_DROM_BASE 0x%x\n' % seg_drom_base
1199 s += '#define SEG_DROM_SIZE 0x%x\n' % seg_drom_size
1200 s += '\n'
[328]1201 s += '#define PERI_CLUSTER_INCREMENT 0x%x\n' % self.peri_increment
[319]1202 s += '\n'
1203
[326]1204 s += '/* physical base addresses for identity mapped vsegs */\n'
1205 s += '/* used by the GietVM OS */\n'
[319]1206 s += '\n'
1207 s += '#define SEG_BOOT_MAPPING_BASE 0x%x\n' % boot_mapping_base
1208 s += '#define SEG_BOOT_MAPPING_SIZE 0x%x\n' % boot_mapping_size
1209 s += '\n'
1210 s += '#define SEG_BOOT_CODE_BASE 0x%x\n' % boot_code_base
1211 s += '#define SEG_BOOT_CODE_SIZE 0x%x\n' % boot_code_size
1212 s += '\n'
1213 s += '#define SEG_BOOT_DATA_BASE 0x%x\n' % boot_data_base
1214 s += '#define SEG_BOOT_DATA_SIZE 0x%x\n' % boot_data_size
1215 s += '\n'
1216 s += '#define SEG_BOOT_STACK_BASE 0x%x\n' % boot_stack_base
1217 s += '#define SEG_BOOT_STACK_SIZE 0x%x\n' % boot_stack_size
1218 s += '#endif\n'
[406]1219
[319]1220 return s
1221
1222 # end of hard_config()
1223
[411]1224 ################################################################################
1225 def linux_dts( self ): # compute string for linux.dts file generation
[424]1226 # used for linux configuration
[411]1227 # header
1228 s = '/dts-v1/;\n'
1229 s += '\n'
1230 s += '/{\n'
[421]1231 s += ' compatible = "tsar,%s";\n' % self.name
[411]1232 s += ' #address-cells = <2>;\n' # physical address on 64 bits
1233 s += ' #size-cells = <1>;\n' # segment size on 32 bits
1234 s += ' model = "%s";\n' % self.name
1235 s += '\n'
1236
1237 # linux globals arguments
1238 s += ' chosen {\n'
1239 s += ' linux,stdout-path = &tty;\n'
1240 s += ' bootargs = "console=tty0 console=ttyVTTY0 earlyprintk";\n'
[424]1241 s += ' };\n\n'
[411]1242
1243 # cpus (for each cluster)
1244 s += ' cpus {\n'
1245 s += ' #address-cells = <1>;\n'
1246 s += ' #size-cells = <0>;\n'
1247
1248 for cluster in self.clusters:
1249 for proc in cluster.procs:
1250 x = cluster.x
1251 y = cluster.y
1252 l = proc.lpid
[421]1253 proc_id = (((x << self.y_width) + y) << self.p_width) + l
[411]1254 s += ' cpu@%d_%d_%d {\n' %(x,y,l)
1255 s += ' device_type = "cpu";\n'
1256 s += ' compatible = "soclib,mips32el";\n'
1257 s += ' reg = <0x%x>;\n' % proc_id
1258 s += ' };\n'
1259 s += '\n'
1260
1261 s += ' };\n\n'
1262
1263 # devices (ram or peripheral) are grouped per cluster
[424]1264 # the "compatible" attribute links a peripheral device
[411]1265 # to one or several drivers identified by ("major","minor")
1266
1267 for cluster in self.clusters:
1268 x = cluster.x
1269 y = cluster.y
1270 found_xcu = False
1271 found_pic = False
1272
1273 s += ' /*** cluster[%d,%d] ***/\n\n' % (x,y)
1274
1275 # scan all psegs to find RAM in current cluster
1276 for pseg in cluster.psegs:
1277 if ( pseg.segtype == 'RAM' ):
1278 msb = pseg.base >> 32
1279 lsb = pseg.base & 0xFFFFFFFF
1280 size = pseg.size
1281
[424]1282 s += ' ram_%d_%d: ram@0x%x {\n' % (x, y, pseg.base)
[411]1283 s += ' device_type = "memory";\n'
1284 s += ' reg = <0x%x 0x%x 0x%x>;\n' % (msb, lsb, size)
1285 s += ' };\n\n'
1286
1287 # scan all periphs to find XCU or PIC in current cluster
1288 for periph in cluster.periphs:
1289 msb = periph.pseg.base >> 32
1290 lsb = periph.pseg.base & 0xFFFFFFFF
1291 size = periph.pseg.size
1292
1293 # search XCU (can be replicated)
[424]1294 if ( (periph.ptype == 'XCU') ):
[411]1295 found_xcu = True
1296 xcu = periph
[424]1297 irq_ctrl_name = 'xcu_%d_%d' % (x, y)
[411]1298
[424]1299 s += ' %s: xcu@0x%x {\n' % (irq_ctrl_name, periph.pseg.base)
[421]1300 s += ' compatible = "soclib,vci_xicu","soclib,vci_xicu_timer";\n'
[411]1301 s += ' interrupt-controller;\n'
1302 s += ' #interrupt-cells = <1>;\n'
1303 s += ' clocks = <&freq>;\n' # the XCU component contains a timer
[424]1304 s += ' reg = <0x%x 0x%x 0x%x>;\n' % (msb, lsb, size)
[411]1305 s += ' };\n\n'
1306
1307 # search PIC (non replicated)
[424]1308 if ( periph.ptype == 'PIC' ):
[411]1309 found_pic = True
1310 pic = periph
1311 irq_ctrl_name = 'pic'
1312
[424]1313 s += ' %s: pic@0x%x {\n' % (irq_ctrl_name, periph.pseg.base)
[421]1314 s += ' compatible = "soclib,vci_iopic";\n'
[411]1315 s += ' interrupt-controller;\n'
1316 s += ' #interrupt-cells = <1>;\n'
1317 s += ' reg = <0x%x 0x%x 0x%x>;\n' % (msb, lsb, size)
1318 s += ' };\n\n'
1319
1320 # we need one interrupt controler in any cluster containing peripherals
1321 if ( (found_xcu == False) and (found_pic == False) and (len(cluster.periphs) > 0) ):
1322 print '[genmap error] in linux_dts() : No XCU/PIC in cluster(%d,%d)' % (x,y)
[424]1323 sys.exit(1)
[411]1324
1325 if ( found_pic == True ): irq_ctrl = pic
1326 else: irq_ctrl = xcu
[424]1327
[411]1328 # scan all periphs to find TTY and IOC in current cluster
1329 for periph in cluster.periphs:
1330 msb = periph.pseg.base >> 32
1331 lsb = periph.pseg.base & 0xFFFFFFFF
1332 size = periph.pseg.size
1333
1334 # search TTY (non replicated)
[424]1335 if ( periph.ptype == 'TTY' ):
[411]1336
1337 # get HWI index to XCU or PIC (only TTY channel 0 is used by Linux)
1338 hwi_id = 0xFFFFFFFF
1339 for irq in irq_ctrl.irqs:
1340 if ( (irq.isrtype == 'ISR_TTY_RX') and (irq.channel == 0) ): hwi_id = irq.srcid
1341 if ( hwi_id == 0xFFFFFFFF ):
1342 print '[genmap error] in linux.dts() IRQ_TTY_RX not found'
1343 sys.exit(1)
1344
1345 s += ' tty: tty {\n'
[421]1346 s += ' compatible = "soclib,vci_multi_tty";\n'
[411]1347 s += ' interrupt-parent = <&%s>;\n' % (irq_ctrl_name)
[424]1348 s += ' interrupts = <%d>;\n' % hwi_id
[411]1349 s += ' reg = <0x%x 0x%x 0x%x>;\n' % (msb, lsb, size)
1350 s += ' };\n\n'
1351
1352 # search IOC (non replicated)
[424]1353 elif ( periph.ptype == 'IOC' ):
[411]1354
1355 if ( periph.subtype == 'BDV' ):
1356
1357 # get irq line index associated to bdv
1358 hwi_id = 0xFFFFFFFF
1359 for irq in irq_ctrl.irqs:
1360 if ( irq.isrtype == 'ISR_BDV' ): hwi_id = irq.srcid
1361 if ( hwi_id == 0xFFFFFFFF ):
1362 print '[genmap error] in linux.dts() ISR_BDV not found'
1363 sys.exit(1)
1364
1365 s += ' bdv: bdv {\n'
[421]1366 s += ' compatible = "soclib,vci_blockdevice";\n'
[411]1367 s += ' interrupt-parent = <&%s>;\n' % (irq_ctrl_name)
[424]1368 s += ' interrupts = <%d>;\n' % hwi_id
[411]1369 s += ' reg = <0x%x 0x%x 0x%x>;\n' % (msb, lsb, size)
1370 s += ' };\n\n'
1371
1372 elif ( periph.subtype == 'HBA' ):
1373
1374 print '[genmap error] in linux_dts() : HBA peripheral not supported by LINUX'
1375 sys.exit(1)
1376
1377 elif ( periph.subtype == 'SPI' ):
1378
1379 print '[genmap error] in linux_dts() : SPI peripheral not supported by LINUX'
1380 sys.exit(1)
1381
[465]1382 # XCU or PIC have been already parsed
1383 elif ( periph.ptype == 'XCU' ) or ( periph.ptype == 'PIC' ):
1384 pass
1385
[411]1386 # other peripherals
[424]1387 else:
[411]1388 type = periph.ptype
1389 print '[genmap warning] in linux_dts() : %s peripheral not supported by LINUX' % (type)
[424]1390
1391 # clocks
[411]1392 s += ' /*** clocks ***/\n\n'
1393 s += ' clocks {\n'
[424]1394 s += ' freq: freq@50MHZ {\n'
[411]1395 s += ' #clock-cells = <0>;\n'
1396 s += ' compatible = "fixed-clock";\n'
1397 s += ' clock-frequency = <50000000>;\n'
1398 s += ' };\n'
1399 s += ' };\n\n'
1400 s += ' cpuclk {\n'
[421]1401 s += ' compatible = "soclib,mips32_clksrc";\n'
[424]1402 s += ' clocks = <&freq>;\n'
[411]1403 s += ' };\n'
1404 s += '};\n'
1405
1406 return s
1407 # end linux_dts()
1408
1409
1410 #############################################################################
[319]1411 def netbsd_dts( self ): # compute string for netbsd.dts file generation,
[406]1412 # used for netbsd configuration
[319]1413 # header
1414 s = '/dts-v1/;\n'
1415 s += '\n'
1416 s += '/{\n'
[406]1417 s += ' #address-cells = <2>;\n'
1418 s += ' #size-cells = <1>;\n'
[319]1419
1420 # cpus (for each cluster)
1421 s += ' cpus {\n'
1422 s += ' #address-cells = <1>;\n'
1423 s += ' #size-cells = <0>;\n'
1424
1425 for cluster in self.clusters:
1426 for proc in cluster.procs:
[406]1427 proc_id = (((cluster.x << self.y_width) + cluster.y) << self.p_width) + proc.lpid
[319]1428
1429 s += ' Mips,32@0x%x {\n' % proc_id
1430 s += ' device_type = "cpu";\n'
1431 s += ' icudev_type = "cpu:mips";\n'
1432 s += ' name = "Mips,32";\n'
1433 s += ' reg = <0x%x>;\n' % proc_id
1434 s += ' };\n'
1435 s += '\n'
1436
1437 s += ' };\n'
1438
[411]1439 # physical memory banks (for each cluster)
[319]1440 for cluster in self.clusters:
1441 for pseg in cluster.psegs:
1442
1443 if ( pseg.segtype == 'RAM' ):
1444 msb = pseg.base >> 32
1445 lsb = pseg.base & 0xFFFFFFFF
1446 size = pseg.size
1447
1448 s += ' %s@0x%x {\n' % (pseg.name, pseg.base)
1449 s += ' cached = <1>;\n'
1450 s += ' device_type = "memory";\n'
1451 s += ' reg = <0x%x 0x%x 0x%x>;\n' % (msb, lsb, size)
1452 s += ' };\n'
1453
1454 # peripherals (for each cluster)
1455 for cluster in self.clusters:
[411]1456 x = cluster.x
1457 y = cluster.y
[319]1458
[406]1459 # research XCU component
[319]1460 found_xcu = False
1461 for periph in cluster.periphs:
[406]1462 if ( (periph.ptype == 'XCU') ):
[319]1463 found_xcu = True
1464 xcu = periph
1465 msb = periph.pseg.base >> 32
1466 lsb = periph.pseg.base & 0xFFFFFFFF
1467 size = periph.pseg.size
1468
1469 s += ' %s@0x%x {\n' % (periph.pseg.name, periph.pseg.base)
1470 s += ' device_type = "soclib:xicu:root";\n'
1471 s += ' reg = <0x%x 0x%x 0x%x>;\n' % (msb, lsb, size)
[400]1472 s += ' input_lines = <%d>;\n' % periph.arg
1473 s += ' ipis = <%d>;\n' % periph.arg
1474 s += ' timers = <%d>;\n' % periph.arg
[319]1475
1476 output_id = 0 # output index from XCU
1477 for lpid in xrange ( len(cluster.procs) ): # destination processor index
1478 for itid in xrange ( self.irq_per_proc ): # input irq index on processor
[406]1479 cluster_xy = (cluster.x << self.y_width) + cluster.y
1480 proc_id = (cluster_xy << self.p_width) + lpid
[319]1481 s += ' out@%d {\n' % output_id
1482 s += ' device_type = "soclib:xicu:filter";\n'
[411]1483 s += ' irq = <&{/cpus/Mips,32@0x%x} %d>;\n' % (proc_id, itid)
[406]1484 s += ' output_line = <%d>;\n' % output_id
[411]1485 s += ' parent = <&{/%s@0x%x}>;\n' % (periph.pseg.name, periph.pseg.base)
[319]1486 s += ' };\n'
1487
1488 output_id += 1
1489
1490 s += ' };\n'
1491
1492 # research PIC component
1493 found_pic = False
1494 for periph in cluster.periphs:
[406]1495 if ( periph.ptype == 'PIC' ):
[319]1496 found_pic = True
1497 pic = periph
1498 msb = periph.pseg.base >> 32
1499 lsb = periph.pseg.base & 0xFFFFFFFF
1500 size = periph.pseg.size
1501
1502 s += ' %s@0x%x {\n' % (periph.pseg.name, periph.pseg.base)
1503 s += ' device_type = "soclib:pic:root";\n'
1504 s += ' reg = <0x%x 0x%x 0x%x>;\n' % (msb, lsb, size)
[406]1505 s += ' input_lines = <%d>;\n' % periph.channels
[319]1506 s += ' };\n'
1507
[411]1508 # at least one interrupt controller
[319]1509 if ( (found_xcu == False) and (found_pic == False) and (len(cluster.periphs) > 0) ):
[411]1510 print '[genmap error] in netbsd_dts() : No XCU/PIC in cluster(%d,%d)' % (x,y)
[406]1511 sys.exit(1)
1512
[319]1513 if ( found_pic == True ): irq_tgt = pic
1514 else: irq_tgt = xcu
[406]1515
[319]1516 # get all others peripherals in cluster
1517 for periph in cluster.periphs:
1518 msb = periph.pseg.base >> 32
1519 lsb = periph.pseg.base & 0xFFFFFFFF
1520 size = periph.pseg.size
1521
1522 # research DMA component
1523 if ( periph.ptype == 'DMA' ):
1524
1525 s += ' %s@0x%x {\n' % (periph.pseg.name, periph.pseg.base)
[411]1526 s += ' device_type = "soclib:dma";\n'
1527 s += ' reg = <0x%x 0x%x 0x%x>;\n' % (msb, lsb, size)
[319]1528 s += ' channel_count = <%d>;\n' % periph.channels
1529
1530 # multi-channels : get HWI index (to XCU) for each channel
1531 for channel in xrange( periph.channels ):
1532 hwi_id = 0xFFFFFFFF
1533 for irq in xcu.irqs:
[406]1534 if ( (irq.isrtype == 'ISR_DMA') and (irq.channel == channel) ):
[319]1535 hwi_id = irq.srcid
1536 if ( hwi_id == 0xFFFFFFFF ):
[348]1537 print '[genmap error] in netbsd.dts() ISR_DMA channel %d not found' % channel
[319]1538 sys.exit(1)
1539
1540 name = '%s@0x%x' % (xcu.pseg.name, xcu.pseg.base)
1541 s += ' irq@%d{\n' % channel
1542 s += ' device_type = "soclib:periph:irq";\n'
1543 s += ' output_line = <%d>;\n' % channel
[411]1544 s += ' irq = <&{/%s} %d>;\n' % (name, hwi_id)
1545 s += ' parent = <&{/%s@0x%x}>;\n' % (periph.pseg.name, periph.pseg.base)
[319]1546 s += ' };\n'
1547
[406]1548 s += ' };\n'
[319]1549
1550 # research MMC component
1551 elif ( periph.ptype == 'MMC' ):
1552
1553 # get irq line index associated to MMC in XCU
1554 irq_in = 0xFFFFFFFF
1555 for irq in xcu.irqs:
1556 if ( irq.isrtype == 'ISR_MMC' ): irq_in = irq.srcid
1557 if ( irq_in == 0xFFFFFFFF ):
[348]1558 print '[genmap error] in netbsd.dts() ISR_MMC not found'
[319]1559 sys.exit(1)
1560
1561 s += ' %s@0x%x {\n' % (periph.pseg.name, periph.pseg.base)
1562 s += ' device_type = "soclib:mmc";\n'
[411]1563 s += ' irq = <&{/%s@0x%x} %d>;\n' % (irq_tgt.pseg.name, irq_tgt.pseg.base, irq_in)
1564 s += ' reg = <0x%x 0x%x 0x%x>;\n' % (msb, lsb, size)
[406]1565 s += ' };\n'
[319]1566
1567 # research FBF component
[406]1568 elif ( periph.ptype == 'FBF' ):
[319]1569
[411]1570 s += ' %s@0x%x {\n' % (periph.pseg.name, periph.pseg.base)
[319]1571 s += ' device_type = "soclib:framebuffer";\n'
1572 s += ' mode = <32>;\n' # bits par pixel
[400]1573 s += ' width = <%d>;\n' % periph.arg
1574 s += ' height = <%d>;\n' % periph.arg
[319]1575 s += ' reg = <0x%x 0x%x 0x%x>;\n' % (msb, lsb, size)
1576 s += ' };\n'
1577
1578 # research IOC component
[406]1579 elif ( periph.ptype == 'IOC' ):
[319]1580
1581 if ( periph.subtype == 'BDV' ):
1582
1583 # get irq line index associated to bdv
1584 irq_in = 0xFFFFFFFF
1585 for irq in irq_tgt.irqs:
1586 if ( irq.isrtype == 'ISR_BDV' ): irq_in = irq.srcid
1587 if ( irq_in == 0xFFFFFFFF ):
[348]1588 print '[genmap error] in netbsd.dts() ISR_BDV not found'
[319]1589 sys.exit(1)
1590
[411]1591 s += ' %s@0x%x {\n' % (periph.pseg.name, periph.pseg.base)
[319]1592 s += ' device_type = "soclib:blockdevice";\n'
[411]1593 s += ' irq = <&{/%s@0x%x} %d>;\n' % (irq_tgt.pseg.name,irq_tgt.pseg.base,irq_in)
1594 s += ' reg = <0x%x 0x%x 0x%x>;\n' % (msb, lsb, size)
[319]1595 s += ' };\n'
1596
1597 elif ( periph.subtype == 'HBA' ):
[348]1598 print '[genmap error] in netbsd_dts() : HBA peripheral not supported by NetBSD'
[319]1599 sys.exit(1)
1600
1601 elif ( periph.subtype == 'SPI' ):
1602
1603 # get irq line index associated to spi
1604 irq_in = 0xFFFFFFFF
1605 for irq in irq_tgt.irqs:
1606 if ( irq.isrtype == 'ISR_SPI' ): irq_in = irq.srcid
1607 if ( irq_in == 0xFFFFFFFF ):
[348]1608 print '[genmap error] in netbsd.dts() ISR_SPI not found'
[319]1609 sys.exit(1)
1610
1611 s += ' %s@0x%x {\n' % (periph.pseg.name, periph.pseg.base)
1612 s += ' device_type = "soclib:spi";\n'
[411]1613 s += ' irq = <&{/%s@0x%x} %d>;\n' % (irq_tgt.pseg.name,irq_tgt.pseg.base,irq_in)
1614 s += ' reg = <0x%x 0x%x 0x%x>;\n' % (msb, lsb, size)
[319]1615 s += ' };\n'
1616
1617 # research ROM component
1618 elif ( periph.ptype == 'ROM' ):
1619
[411]1620 s += ' %s@0x%x {\n' % (periph.pseg.name, periph.pseg.base)
[319]1621 s += ' device_type = "rom";\n'
[411]1622 s += ' cached = <1>;\n'
1623 s += ' reg = <0x%x 0x%x 0x%x>;\n' % (msb, lsb, size)
[319]1624 s += ' };\n'
1625
1626 # research SIM component
1627 elif ( periph.ptype == 'SIM' ):
1628
1629 s += ' %s@0x%x {\n' % (periph.pseg.name, periph.pseg.base)
1630 s += ' device_type = "soclib:simhelper";\n'
1631 s += ' reg = <0x%x 0x%x 0x%x>;\n' % (msb, lsb, size)
1632 s += ' };\n'
1633
1634 # research TTY component
1635 elif ( periph.ptype == 'TTY' ):
1636
[411]1637 s += ' %s@0x%x {\n' % (periph.pseg.name, periph.pseg.base)
1638 s += ' device_type = "soclib:tty";\n'
[406]1639 s += ' channel_count = < %d >;\n' % periph.channels
[411]1640 s += ' reg = <0x%x 0x%x 0x%x>;\n' % (msb, lsb, size)
[319]1641
1642 # multi-channels : get HWI index (to XCU or PIC) for each channel
1643 for channel in xrange( periph.channels ):
1644 hwi_id = 0xFFFFFFFF
1645 for irq in irq_tgt.irqs:
[406]1646 if ( (irq.isrtype == 'ISR_TTY_RX') and (irq.channel == channel) ):
[319]1647 hwi_id = irq.srcid
1648 if ( hwi_id == 0xFFFFFFFF ):
[348]1649 print '[genmap error] in netbsd.dts() ISR_TTY_RX channel %d not found' % channel
[319]1650 sys.exit(1)
1651
1652 name = '%s@0x%x' % (irq_tgt.pseg.name, irq_tgt.pseg.base)
1653 s += ' irq@%d{\n' % channel
1654 s += ' device_type = "soclib:periph:irq";\n'
1655 s += ' output_line = <%d>;\n' % channel
[411]1656 s += ' irq = <&{/%s} %d>;\n' % (name, hwi_id)
1657 s += ' parent = <&{/%s@0x%x}>;\n' % (periph.pseg.name, periph.pseg.base)
[319]1658 s += ' };\n'
1659
1660 s += ' };\n'
[406]1661
[319]1662 # research IOB component
1663 elif ( periph.ptype == 'IOB' ):
1664
1665 s += ' %s@0x%x {\n' % (periph.pseg.name, periph.pseg.base)
1666 s += ' device_type = "soclib:iob";\n'
1667 s += ' reg = <0x%x 0x%x 0x%x>;\n' % (msb, lsb, size)
1668 s += ' };\n'
1669
1670 # research NIC component
[406]1671 elif ( periph.ptype == 'NIC' ):
[319]1672
1673 s += ' %s@0x%x {\n' % (periph.pseg.name, periph.pseg.base)
1674 s += ' device_type = "soclib:nic";\n'
1675 s += ' reg = <0x%x 0x%x 0x%x>;\n' % (msb, lsb, size)
1676 s += ' channel_count = < %d >;\n' % periph.channels
1677
1678 # multi-channels : get HWI index (to XCU or PIC) for RX & TX IRQs
1679 # RX IRQ : (2*channel) / TX IRQs : (2*channel + 1)
1680 for channel in xrange( periph.channels ):
1681 hwi_id = 0xFFFFFFFF
1682 for irq in irq_tgt.irqs:
[406]1683 if ( (irq.isrtype == 'ISR_NIC_RX') and (irq.channel == channel) ):
[319]1684 hwi_id = irq.srcid
1685 if ( hwi_id == 0xFFFFFFFF ):
[348]1686 print '[genmap error] in netbsd.dts() ISR_NIC_RX channel %d not found' % channel
[319]1687 sys.exit(1)
1688
1689 name = '%s@0x%x' % (irq_tgt.pseg.name, irq_tgt.pseg.base)
1690 s += ' irq_rx@%d{\n' % channel
1691 s += ' device_type = "soclib:periph:irq";\n'
1692 s += ' output_line = <%d>;\n' % (2*channel)
1693 s += ' irq = <&{/%s} %d>;\n' % (name, hwi_id)
1694 s += ' parent = <&{/%s@0x%x}>;\n' % (periph.pseg.name, periph.pseg.base)
1695 s += ' };\n'
1696
1697 hwi_id = 0xFFFFFFFF
1698 for irq in irq_tgt.irqs:
[406]1699 if ( (irq.isrtype == 'ISR_NIC_TX') and (irq.channel == channel) ):
[319]1700 hwi_id = irq.srcid
1701 if ( hwi_id == 0xFFFFFFFF ):
[348]1702 print '[genmap error] in netbsd.dts() ISR_NIC_TX channel %d not found' % channel
[319]1703 sys.exit(1)
1704
1705 name = '%s@0x%x' % (irq_tgt.pseg.name, irq_tgt.pseg.base)
1706 s += ' irq_tx@%d{\n' % channel
1707 s += ' device_type = "soclib:periph:irq";\n'
1708 s += ' output_line = <%d>;\n' % (2*channel + 1)
1709 s += ' irq = <&{/%s} %d>;\n' % (name, hwi_id)
1710 s += ' parent = <&{/%s@0x%x}>;\n' % (periph.pseg.name, periph.pseg.base)
1711 s += ' };\n'
[406]1712
[319]1713 s += ' };\n'
1714
1715 # research CMA component
[406]1716 elif ( periph.ptype == 'CMA' ):
[319]1717
1718 s += ' %s@0x%x {\n' % (periph.pseg.name, periph.pseg.base)
1719 s += ' device_type = "soclib:cma";\n'
1720 s += ' reg = <0x%x 0x%x 0x%x>;\n' % (msb, lsb, size)
1721 s += ' channel_count = < %d >;\n' % periph.channels
1722
1723 # multi-channels : get HWI index (to XCU or PIC) for each channel
1724 for channel in xrange( periph.channels ):
1725 hwi_id = 0xFFFFFFFF
1726 for irq in irq_tgt.irqs:
[406]1727 if ( (irq.isrtype == 'ISR_CMA') and (irq.channel == channel) ):
[319]1728 hwi_id = irq.srcid
1729 if ( hwi_id == 0xFFFFFFFF ):
[348]1730 print '[genmap error] in netbsd.dts() ISR_CMA channel %d not found' % channel
[319]1731 sys.exit(1)
1732
1733 name = '%s@0x%x' % (irq_tgt.pseg.name, irq_tgt.pseg.base)
1734 s += ' irq@%d{\n' % channel
1735 s += ' device_type = "soclib:periph:irq";\n'
1736 s += ' output_line = <%d>;\n' % channel
[411]1737 s += ' irq = <&{/%s} %d>;\n' % (name, hwi_id)
1738 s += ' parent = <&{/%s@0x%x}>;\n' % (periph.pseg.name, periph.pseg.base)
[319]1739 s += ' };\n'
1740
1741 s += ' };\n'
1742
1743 # research TIM component
[406]1744 elif ( periph.ptype == 'TIM' ):
[319]1745
[348]1746 print '[genmap error] in netbsd_dts() : TIM peripheral not supported by NetBSD'
[319]1747 sys.exit(1)
1748
1749 # research MWR component
1750 elif ( periph.ptype == 'MWR' ):
1751
[348]1752 print '[genmap error] in netbsd_dts() : MWR peripheral not supported by NetBSD'
[319]1753 sys.exit(1)
1754
1755 # topology
1756 s += '\n'
1757 s += ' topology {\n'
1758 s += ' #address-cells = <2>;\n'
1759 s += ' #size-cells = <0>;\n'
1760 for cluster in self.clusters:
[406]1761 s += ' cluster@%d,%d {\n' % (cluster.x, cluster.y)
[319]1762 s += ' reg = <%d %d>;\n' % (cluster.x, cluster.y)
1763 s += ' devices = <\n'
1764
[406]1765 offset = ((cluster.x << self.y_width) + cluster.y) << self.p_width
[319]1766 for proc in cluster.procs:
1767 s += ' &{/cpus/Mips,32@0x%x}\n' % (offset + proc.lpid)
1768 for periph in cluster.periphs:
1769 s += ' &{/%s@0x%x}\n' % (periph.pseg.name, periph.pseg.base)
[492]1770 for pseg in cluster.psegs:
1771 if ( pseg.segtype == 'RAM' ):
1772 s += ' &{/%s@0x%x}\n' % (pseg.name, pseg.base)
[319]1773
1774 s += ' >;\n'
1775 s += ' };\n'
1776 s += ' };\n'
1777 s += '};\n'
1778
1779 return s
[411]1780 # end netbsd_dts()
[319]1781
1782 ###########################
1783 def almos_archinfo( self ): # compute string for arch.info file generation,
[406]1784 # used for almos configuration
[319]1785 # header
[327]1786 s = '# arch.info file generated by genmap for %s\n' % self.name
[319]1787 s += '\n'
1788 s += '[HEADER]\n'
1789 s += ' REVISION=1\n'
1790 s += ' ARCH=%s\n' % self.name
1791 s += ' XMAX=%d\n' % self.x_size
1792 s += ' YMAX=%d\n' % self.y_size
[411]1793 s += ' CPU_NR=%d\n' % self.nprocs
[319]1794 s += '\n'
1795
1796 # clusters
1797 cluster_id = 0
1798 for cluster in self.clusters:
1799
1800 ram = None
1801 nb_cpus = len( cluster.procs )
1802 nb_devs = len( cluster.periphs )
1803 if ( len( cluster.coprocs ) != 0 ):
1804 print 'Error in almos_archinfo() coprocessors not supported yet'
1805 sys.exit(1)
1806
1807 # search a RAM
1808 for pseg in cluster.psegs:
[406]1809 if ( pseg.segtype == 'RAM' ):
[319]1810 ram = pseg
1811 nb_devs += 1
1812
1813 # search XCU to get IRQs indexes if cluster contains peripherals
1814 if ( len( cluster.periphs ) != 0 ):
1815 tty_irq_id = None
1816 bdv_irq_id = None
1817 dma_irq_id = None
1818
1819 for periph in cluster.periphs:
[406]1820 if ( periph.ptype == 'XCU' ):
[319]1821 # scan irqs
1822 for irq in periph.irqs:
1823 if ( irq.isrtype == 'ISR_TTY_RX' ) : tty_irq_id = irq.srcid
1824 if ( irq.isrtype == 'ISR_BDV' ) : bdv_irq_id = irq.srcid
1825 if ( irq.isrtype == 'ISR_DMA' ) : dma_irq_id = irq.srcid
1826
1827 # Build the cluster description
1828 s += '[CLUSTER]\n'
[406]1829 s += ' CID=%d\n' % cluster_id
1830 s += ' ARCH_CID=0x%x\n' % ((cluster.x << self.y_width) + cluster.y)
[319]1831 s += ' CPU_NR=%d\n' % nb_cpus
1832 s += ' DEV_NR=%d\n' % nb_devs
1833
[406]1834
[319]1835 # Handling RAM when cluster contain a RAM
1836 if (ram != None ):
1837 base = ram.base
1838 size = ram.size
1839 irqid = -1
[406]1840 s += ' DEVID=RAM'
[319]1841 s += ' BASE=0x%x SIZE=0x%x IRQ=-1\n' % ( base, size )
1842
1843 # Handling peripherals
1844 for periph in cluster.periphs:
1845 base = periph.pseg.base
1846 size = periph.pseg.size
1847
[406]1848 if ( periph.ptype == 'XCU' ):
[319]1849
[406]1850 s += ' DEVID=XICU'
[319]1851 s += ' BASE=0x%x SIZE=0x%x IRQ=-1\n' % ( base, size )
1852
[406]1853 elif ( (periph.ptype == 'TTY')
[319]1854 and (tty_irq_id != None) ):
1855
[406]1856 s += ' DEVID=TTY'
[319]1857 s += ' BASE=0x%x SIZE=0x%x IRQ=%d\n' % ( base, size, tty_irq_id )
1858
[406]1859 elif ( (periph.ptype == 'DMA')
[319]1860 and (dma_irq_id != None) ):
1861
1862 s += ' DEVID=DMA'
1863 s += ' BASE=0x%x SIZE=0x%x IRQ=%d\n' % ( base, size, dma_irq_id )
1864
1865 elif ( periph.ptype == 'FBF' ):
1866
1867 s += ' DEVID=FB'
1868 s += ' BASE=0x%x SIZE=0x%x IRQ=-1\n' % ( base, size )
1869
1870 elif ( (periph.ptype == 'IOC') and (periph.subtype == 'BDV')
1871 and (bdv_irq_id != None) ):
1872
[406]1873 s += ' DEVID=BLKDEV'
[319]1874 s += ' BASE=0x%x SIZE=0x%x IRQ=%d\n' % ( base, size, bdv_irq_id )
1875
1876 elif ( periph.ptype == 'PIC' ):
1877
[406]1878 s += ' DEVID=IOPIC'
[319]1879 s += ' BASE=0x%x SIZE=0x%x IRQ=-1\n' % ( base, size )
1880
1881 else:
1882 print '# Warning from almos_archinfo() in cluster[%d,%d]' \
1883 % (cluster.x, cluster.y)
1884 print '# peripheral type %s/%s not supported yet\n' \
1885 % ( periph.ptype, periph.subtype )
[406]1886
[319]1887 cluster_id += 1
1888
1889 return s
1890
1891 # end of almos_archinfo()
1892
1893
1894
1895
1896
1897
1898
1899
1900###########################################################################################
1901class Cluster ( object ):
1902###########################################################################################
1903 def __init__( self,
[406]1904 x,
[319]1905 y ):
[406]1906
[319]1907 self.index = 0 # global index (set by Mapping constructor)
1908 self.x = x # x coordinate
1909 self.y = y # y coordinate
1910 self.psegs = [] # filled by addRam() or addPeriph()
1911 self.procs = [] # filled by addProc()
1912 self.coprocs = [] # filled by addCoproc()
1913 self.periphs = [] # filled by addPeriph()
1914
1915 return
1916
1917 ################
1918 def xml( self ): # xml for a cluster
1919
1920 s = ' <cluster x="%d" y="%d" >\n' % (self.x, self.y)
[406]1921 for pseg in self.psegs: s += pseg.xml()
[319]1922 for proc in self.procs: s += proc.xml()
[406]1923 for copr in self.coprocs: s += copr.xml()
1924 for peri in self.periphs: s += peri.xml()
[319]1925 s += ' </cluster>\n'
1926
1927 return s
1928
1929 #############################################
1930 def cbin( self, mapping, verbose, expected ): # C binary structure for Cluster
1931
1932 if ( verbose ):
1933 print '*** cbin for cluster [%d,%d]' % (self.x, self.y)
1934
1935 # check index
1936 if (self.index != expected):
[348]1937 print '[genmap error] in Cluster.cbin() : cluster global index = %d / expected = %d' \
[319]1938 % (self.index, expected )
1939 sys.exit(1)
1940
[406]1941 # compute global index for first pseg
[319]1942 if ( len(self.psegs) > 0 ):
1943 pseg_id = self.psegs[0].index
1944 else:
1945 pseg_id = 0
1946
[406]1947 # compute global index for first proc
[319]1948 if ( len(self.procs) > 0 ):
1949 proc_id = self.procs[0].index
1950 else:
1951 proc_id = 0
1952
[406]1953 # compute global index for first coproc
[319]1954 if ( len(self.coprocs) > 0 ):
1955 coproc_id = self.coprocs[0].index
1956 else:
1957 coproc_id = 0
1958
[406]1959 # compute global index for first periph
[319]1960 if ( len(self.periphs) > 0 ):
1961 periph_id = self.periphs[0].index
1962 else:
1963 periph_id = 0
1964
1965 byte_stream = bytearray()
1966 byte_stream += mapping.int2bytes( 4 , self.x ) # x coordinate
1967 byte_stream += mapping.int2bytes( 4 , self.y ) # x coordinate
1968 byte_stream += mapping.int2bytes( 4 , len( self.psegs ) ) # number of psegs in cluster
1969 byte_stream += mapping.int2bytes( 4 , pseg_id ) # first pseg global index
1970 byte_stream += mapping.int2bytes( 4 , len( self.procs ) ) # number of procs in cluster
1971 byte_stream += mapping.int2bytes( 4 , proc_id ) # first proc global index
1972 byte_stream += mapping.int2bytes( 4 , len( self.coprocs ) ) # number of coprocs in cluster
1973 byte_stream += mapping.int2bytes( 4 , coproc_id ) # first coproc global index
1974 byte_stream += mapping.int2bytes( 4 , len( self.periphs ) ) # number of periphs in cluster
1975 byte_stream += mapping.int2bytes( 4 , periph_id ) # first periph global index
[406]1976
[319]1977 if ( verbose ):
1978 print 'nb_psegs = %d' % len( self.psegs )
1979 print 'pseg_id = %d' % pseg_id
1980 print 'nb_procs = %d' % len( self.procs )
1981 print 'proc_id = %d' % proc_id
1982 print 'nb_coprocs = %d' % len( self.coprocs )
1983 print 'coproc_id = %d' % coproc_id
1984 print 'nb_periphs = %d' % len( self.periphs )
1985 print 'periph_id = %d' % periph_id
1986
1987 return byte_stream
1988
1989###########################################################################################
[305]1990class Vspace( object ):
[319]1991###########################################################################################
[406]1992 def __init__( self,
1993 name,
[319]1994 startname ):
1995
1996 self.index = 0 # global index ( set by addVspace() )
1997 self.name = name # vspace name
[305]1998 self.startname = startname # name of vobj containing the start_vector
[406]1999 self.vsegs = []
[305]2000 self.tasks = []
2001
2002 return
2003
[319]2004 ################
2005 def xml( self ): # xml for one vspace
2006
[305]2007 s = ' <vspace name="%s" startname="%s" >\n' % ( self.name, self.startname )
[319]2008 for vseg in self.vsegs: s += vseg.xml()
[406]2009 for task in self.tasks: s += task.xml()
[305]2010 s += ' </vspace>\n'
[319]2011
[305]2012 return s
2013
[319]2014 #############################################
2015 def cbin( self, mapping, verbose, expected ): # C binary structure for Vspace
2016
2017 if ( verbose ):
2018 print '*** cbin for vspace %s' % (self.name)
2019
2020 # check index
2021 if (self.index != expected):
[348]2022 print '[genmap error] in Vspace.cbin() : vspace global index = %d / expected = %d' \
[319]2023 % (self.index, expected )
2024 sys.exit(1)
2025
2026 # compute global index for vobj containing start_vector
2027 vobj_start_id = 0xFFFFFFFF
2028 for vseg in self.vsegs:
2029 if ( vseg.vobjs[0].name == self.startname ):
2030 vobj_start_id = vseg.vobjs[0].index
2031 if ( vobj_start_id == 0xFFFFFFFF ):
[348]2032 print '[genmap error] in Vspace.cbin() : startname %s not found for vspace %s' \
[319]2033 % ( self.startname, self.name )
2034 sys.exit(1)
[406]2035
[319]2036 # compute first vseg, vobj, task global index
2037 first_vseg_id = self.vsegs[0].index
2038 first_vobj_id = self.vsegs[0].vobjs[0].index
2039 first_task_id = self.tasks[0].index
[406]2040
[319]2041 # compute number of vobjs, tasks, vsegs
2042 nb_vsegs = len( self.vsegs )
2043 nb_tasks = len( self.tasks )
2044 nb_vobjs = 0
2045 for vseg in self.vsegs:
2046 nb_vobjs += len( vseg.vobjs )
2047
2048 byte_stream = bytearray()
2049 byte_stream += mapping.str2bytes( 32, self.name ) # vspace name
[406]2050 byte_stream += mapping.int2bytes( 4, vobj_start_id ) # vobj start_vector
[319]2051 byte_stream += mapping.int2bytes( 4, nb_vsegs ) # number of vsegs
2052 byte_stream += mapping.int2bytes( 4, nb_vobjs ) # number of vobjs
2053 byte_stream += mapping.int2bytes( 4, nb_tasks ) # number of tasks
2054 byte_stream += mapping.int2bytes( 4, first_vseg_id ) # first vseg global index
2055 byte_stream += mapping.int2bytes( 4, first_vobj_id ) # first vobj global index
2056 byte_stream += mapping.int2bytes( 4, first_task_id ) # first task global index
2057
2058 if ( verbose ):
2059 print 'start_id = %d' % vobj_start_id
2060 print 'nb_vsegs = %d' % nb_vsegs
2061 print 'nb_vobjs = %d' % nb_vobjs
2062 print 'nb_tasks = %d' % nb_tasks
2063 print 'vseg_id = %d' % first_vseg_id
2064 print 'vobj_id = %d' % first_vobj_id
2065 print 'task_id = %d' % first_task_id
2066
2067 return byte_stream
2068
2069###########################################################################################
[305]2070class Task( object ):
[319]2071###########################################################################################
[406]2072 def __init__( self,
2073 name,
2074 trdid,
2075 x,
[319]2076 y,
[406]2077 p,
2078 stackname,
2079 heapname,
[441]2080 startid ):
[319]2081
2082 self.index = 0 # global index value set by addTask()
2083 self.name = name # tsk name
2084 self.trdid = trdid # task index (unique in vspace)
[406]2085 self.x = x # cluster x coordinate
2086 self.y = y # cluster y coordinate
2087 self.p = p # processor local index
[319]2088 self.stackname = stackname # name of vobj containing the stack
2089 self.heapname = heapname # name of vobj containing the heap
2090 self.startid = startid # index in start_vector
[305]2091 return
2092
[319]2093 ################
2094 def xml( self ): # xml for one task
2095
2096 s = ' <task name="%s"' % self.name
2097 s += ' trdid="%d"' % self.trdid
2098 s += ' x="%d"' % self.x
2099 s += ' y="%d"' % self.y
2100 s += ' p="%d"' % self.p
2101 s += ' stackname="%s"' % self.stackname
2102 s += ' heapname="%s"' % self.heapname
2103 s += ' startid="%d"' % self.startid
[406]2104 s += ' />\n'
[319]2105
[305]2106 return s
2107
[319]2108 #####################################################
[406]2109 def cbin( self, mapping, verbose, expected, vspace ): # C binary data structure for Task
[319]2110
2111 if ( verbose ):
2112 print '*** cbin for task %s in vspace %s' % (self.name, vspace.name)
2113
2114 # check index
2115 if (self.index != expected):
[348]2116 print '[genmap error] in Task.cbin() : task global index = %d / expected = %d' \
[319]2117 % (self.index, expected )
2118 sys.exit(1)
2119
2120 # compute cluster global index
2121 cluster_id = (self.x * mapping.y_size) + self.y
2122
2123 # compute vobj local index for stack
2124 vobj_stack_id = 0xFFFFFFFF
2125 for vseg in vspace.vsegs:
2126 if ( vseg.vobjs[0].name == self.stackname ):
[406]2127 vobj_stack_id = vseg.vobjs[0].index
[319]2128 if ( vobj_stack_id == 0xFFFFFFFF ):
[348]2129 print '[genmap error] in Task.cbin() : stackname %s not found for task %s in vspace %s' \
[319]2130 % ( self.stackname, self.name, vspace.name )
2131 sys.exit(1)
2132
2133 # compute vobj local index for heap
[453]2134 if ( self.heapname == '' ):
2135 vobj_heap_id = 0
2136 else:
2137 vobj_heap_id = 0xFFFFFFFF
2138 for vseg in vspace.vsegs:
2139 if ( vseg.vobjs[0].name == self.heapname ):
2140 vobj_heap_id = vseg.vobjs[0].index
2141 if ( vobj_heap_id == 0xFFFFFFFF ):
2142 print '[genmap error] in Task.cbin() : heapname %s not found for task %s in vspace %s' \
2143 % ( self.heapname, self.name, vspace.name )
2144 sys.exit(1)
[319]2145
2146 byte_stream = bytearray()
2147 byte_stream += mapping.str2bytes( 32, self.name ) # task name in vspace
2148 byte_stream += mapping.int2bytes( 4, cluster_id ) # cluster global index
2149 byte_stream += mapping.int2bytes( 4, self.p ) # processor local index in cluster
2150 byte_stream += mapping.int2bytes( 4, self.trdid ) # thread local index in vspace
2151 byte_stream += mapping.int2bytes( 4, vobj_stack_id ) # stack vobj local index
2152 byte_stream += mapping.int2bytes( 4, vobj_heap_id ) # heap vobj local index
[406]2153 byte_stream += mapping.int2bytes( 4, self.startid ) # index in start vector
[319]2154
2155 if ( verbose ):
2156 print 'clusterid = %d' % cluster_id
2157 print 'lpid = %d' % self.p
[406]2158 print 'trdid = %d' % self.trdid
2159 print 'stackid = %d' % vobj_stack_id
2160 print 'heapid = %d' % vobj_heap_id
2161 print 'startid = %d' % self.startid
2162
[319]2163 return byte_stream
2164
2165###########################################################################################
[305]2166class Vseg( object ):
[319]2167###########################################################################################
[406]2168 def __init__( self,
2169 name,
2170 vbase,
2171 mode,
2172 x,
2173 y,
2174 psegname,
[348]2175 identity = False,
[411]2176 local = False,
2177 big = False ):
[305]2178
[319]2179 assert mode in VSEGMODES
2180
[348]2181 self.index = 0 # global index ( set by addVseg() )
2182 self.name = name # vseg name
[406]2183 self.vbase = vbase & 0xFFFFFFFF # virtual base address in vspace
[348]2184 self.mode = mode # CXWU access rights
[406]2185 self.x = x # x coordinate of destination cluster
[348]2186 self.y = y # y coordinate of destination cluster
2187 self.psegname = psegname # name of pseg in destination cluster
2188 self.identity = identity # identity mapping required
[411]2189 self.local = local # only mapped in local PTAB when true
2190 self.big = big # to be mapped in a big physical page
[348]2191 self.vobjs = []
[305]2192 return
2193
[319]2194 ################
[406]2195 def xml( self ): # xml for one vseg
[319]2196
2197 s = ' <vseg name="%s" vbase="0x%x" mode="%s" x="%d" y="%d" psegname="%s"' \
2198 % ( self.name, self.vbase, self.mode, self.x, self.y, self.psegname )
[348]2199 if ( self.identity ): s += ' ident="1"'
2200 if ( self.local ): s += ' local="1"'
[411]2201 if ( self.big ): s += ' big="1"'
[348]2202 s += ' >\n'
2203 for vobj in self.vobjs: s += vobj.xml()
[319]2204 s += ' </vseg>\n'
2205
[305]2206 return s
2207
[319]2208 #############################################
2209 def cbin( self, mapping, verbose, expected ): # C binary structure for Vseg
2210
2211 if ( verbose ):
2212 print '*** cbin for vseg[%d] %s' % (self.index, self.name)
2213
2214 # check index
2215 if (self.index != expected):
[348]2216 print '[genmap error] in Vseg.cbin() : vseg global index = %d / expected = %d' \
[319]2217 % (self.index, expected )
2218 sys.exit(1)
2219
2220 # compute pseg_id
2221 pseg_id = 0xFFFFFFFF
2222 cluster_id = (self.x * mapping.y_size) + self.y
2223 cluster = mapping.clusters[cluster_id]
2224 for pseg in cluster.psegs:
2225 if (self.psegname == pseg.name):
2226 pseg_id = pseg.index
2227 if (pseg_id == 0xFFFFFFFF):
[348]2228 print '[genmap error] in Vseg.cbin() : psegname %s not found for vseg %s in cluster %d' \
[319]2229 % ( self.psegname, self.name, cluster_id )
2230 sys.exit(1)
2231
2232 # compute numerical value for mode
2233 mode_id = 0xFFFFFFFF
[406]2234 for x in xrange( len(VSEGMODES) ):
2235 if ( self.mode == VSEGMODES[x] ):
[319]2236 mode_id = x
2237 if ( mode_id == 0xFFFFFFFF ):
[348]2238 print '[genmap error] in Vseg.cbin() : undefined vseg mode %s' % self.mode
[319]2239 sys.exit(1)
2240
2241 # compute vobj_id
[406]2242 vobj_id = self.vobjs[0].index
[319]2243
2244 byte_stream = bytearray()
[406]2245 byte_stream += mapping.str2bytes( 32, self.name ) # vseg name
[319]2246 byte_stream += mapping.int2bytes( 4, self.vbase ) # virtual base address
2247 byte_stream += mapping.int2bytes( 8, 0 ) # physical base address
2248 byte_stream += mapping.int2bytes( 4, 0 ) # vseg size (bytes)
2249 byte_stream += mapping.int2bytes( 4, pseg_id ) # physical segment global index
2250 byte_stream += mapping.int2bytes( 4, mode_id ) # CXWU flags
2251 byte_stream += mapping.int2bytes( 4, len(self.vobjs) ) # number of vobjs in vseg
[406]2252 byte_stream += mapping.int2bytes( 4, vobj_id ) # first vobj global index
[411]2253 byte_stream += mapping.int2bytes( 4, 0 ) # linked list of vsegs on pseg
[319]2254 byte_stream += mapping.int2bytes( 1, 0 ) # mapped when non zero
[411]2255 byte_stream += mapping.int2bytes( 1, self.identity ) # identity mapping if non zero
2256 byte_stream += mapping.int2bytes( 1, self.local ) # only mapped in local PTAB
2257 byte_stream += mapping.int2bytes( 1, self.big ) # to be mapped in big physical page
[319]2258
2259 if ( verbose ):
2260 print 'vbase = %x' % self.vbase
2261 print 'pseg_id = %d' % pseg_id
2262 print 'mode = %s' % self.mode
2263 print 'nb_vobjs = %d' % len(self.vobjs)
[406]2264 print 'vobj_id = %d' % vobj_id
2265
[319]2266 return byte_stream
2267
2268###########################################################################################
[305]2269class Vobj( object ):
[319]2270###########################################################################################
2271 def __init__( self,
[406]2272 name,
2273 length,
2274 vtype,
2275 binpath = '',
2276 align = 0,
[319]2277 init = 0 ):
2278
[305]2279 assert vtype in ['ELF','BLOB','PTAB','PERI','MWMR','LOCK', \
[471]2280 'BUFFER','BARRIER','CONST','MEMSPACE','SCHED','HEAP']
[319]2281
2282 assert (vtype != 'ELF') or (binpath != '')
2283
2284 self.index = 0 # global index ( set by addVobj() )
2285 self.name = name # vobj name (unique in vspace)
2286 self.vtype = vtype # vobj type (defined in mapping_info.h)
2287 self.length = length # vobj size (bytes)
2288 self.binpath = binpath # pathname for (ELF type)
2289 self.align = align # required alignment (logarithm of 2)
2290 self.init = init # initialisation value (for BARRIER or MWMR types)
2291
[305]2292 return
2293
[319]2294 ################
2295 def xml( self ): # xml for a vobj
2296
[305]2297 s = ' <vobj name="%s" type="%s" length="0x%x"' \
2298 % ( self.name, self.vtype, self.length )
[319]2299 if (self.binpath != ''): s += ' binpath="%s"' % (self.binpath)
2300 if (self.align != 0 ): s += ' align="%d"' % (self.align)
2301 if (self.init != 0 ): s += ' init="%d"' % (self.init)
[305]2302 s += ' />\n'
[319]2303
[305]2304 return s
2305
[319]2306 #############################################
2307 def cbin( self, mapping, verbose, expected ): # C binary structure for Vobj
[305]2308
[319]2309 # check index
2310 if (self.index != expected):
[348]2311 print '[genmap error] in Vobj.cbin() : vobj global index = %d / expected = %d' \
[319]2312 % (self.index, expected )
2313 sys.exit(1)
2314 elif ( verbose ):
2315 print '*** cbin for vobj[%d] %s' % (self.index, self.name)
[305]2316
[319]2317 # compute numerical value for vtype
2318 vtype_int = 0xFFFFFFFF
[406]2319 for x in xrange( len(VOBJTYPES) ):
2320 if ( self.vtype == VOBJTYPES[x] ):
[319]2321 vtype_int = x
2322 if ( vtype_int == 0xFFFFFFFF ):
[348]2323 print '[genmap error] in Vobj.cbin() : undefined vobj type %s' % self.vtype
[319]2324 sys.exit(1)
2325
2326 byte_stream = bytearray()
[406]2327 byte_stream += mapping.str2bytes( 32, self.name ) # vobj name
[319]2328 byte_stream += mapping.str2bytes( 64, self.binpath ) # pathname for .elf file
2329 byte_stream += mapping.int2bytes( 4 , vtype_int ) # vobj type
2330 byte_stream += mapping.int2bytes( 4 , self.length ) # vobj size
2331 byte_stream += mapping.int2bytes( 4 , self.align ) # required alignment
2332 byte_stream += mapping.int2bytes( 4 , 0 ) # virtual base address
2333 byte_stream += mapping.int2bytes( 4 , self.init ) # init value
[406]2334
[319]2335 if ( verbose ):
2336 print 'binpath = %s' % self.binpath
2337 print 'type = %s' % self.vtype
2338 print 'length = %x' % self.length
[406]2339
[319]2340 return byte_stream
2341
2342###########################################################################################
[305]2343class Processor ( object ):
[319]2344###########################################################################################
2345 def __init__( self,
[406]2346 x,
2347 y,
[319]2348 lpid ):
2349
2350 self.index = 0 # global index ( set by addProc() )
2351 self.x = x # x cluster coordinate
2352 self.y = y # y cluster coordinate
2353 self.lpid = lpid # processor local index
2354
[305]2355 return
2356
[319]2357 ################
[406]2358 def xml( self ): # xml for a processor
[305]2359 return ' <proc index="%d" />\n' % (self.lpid)
2360
[319]2361 #############################################
2362 def cbin( self, mapping, verbose, expected ): # C binary structure for Proc
2363
2364 if ( verbose ):
2365 print '*** cbin for proc %d in cluster (%d,%d)' % (self.lpid, self.x, self.y)
2366
2367 # check index
2368 if (self.index != expected):
[348]2369 print '[genmap error] in Proc.cbin() : proc global index = %d / expected = %d' \
[319]2370 % (self.index, expected )
2371 sys.exit(1)
2372
2373 byte_stream = bytearray()
2374 byte_stream += mapping.int2bytes( 4 , self.lpid ) # local index
[406]2375
[319]2376 return byte_stream
2377
2378###########################################################################################
[305]2379class Pseg ( object ):
[319]2380###########################################################################################
[406]2381 def __init__( self,
2382 name,
2383 base,
2384 size,
[319]2385 x,
2386 y,
2387 segtype ):
2388
2389 assert( segtype in PSEGTYPES )
2390
2391 self.index = 0 # global index ( set by addPseg() )
2392 self.name = name # pseg name (unique in cluster)
2393 self.base = base # physical base address
2394 self.size = size # segment size (bytes)
[406]2395 self.x = x # cluster x coordinate
2396 self.y = y # cluster y coordinate
[319]2397 self.segtype = segtype # RAM / PERI (defined in mapping_info.h)
2398
[305]2399 return
[406]2400
[319]2401 ################
2402 def xml( self ): # xml for a pseg
2403
[305]2404 return ' <pseg name="%s" type="%s" base="0x%x" length="0x%x" />\n' \
2405 % (self.name, self.segtype, self.base, self.size)
2406
[319]2407 ######################################################
2408 def cbin( self, mapping, verbose, expected, cluster ): # C binary structure for Pseg
2409
2410 if ( verbose ):
2411 print '*** cbin for pseg[%d] %s in cluster[%d,%d]' \
2412 % (self.index, self.name, cluster.x, cluster.y)
2413
2414 # check index
2415 if (self.index != expected):
[348]2416 print '[genmap error] in Pseg.cbin() : pseg global index = %d / expected = %d' \
[319]2417 % (self.index, expected )
2418 sys.exit(1)
[406]2419
[319]2420 # compute numerical value for segtype
2421 segtype_int = 0xFFFFFFFF
[406]2422 for x in xrange( len(PSEGTYPES) ):
2423 if ( self.segtype == PSEGTYPES[x] ):
[319]2424 segtype_int = x
2425 if ( segtype_int == 0xFFFFFFFF ):
[348]2426 print '[genmap error] in Pseg.cbin() : undefined segment type %s' % self.segtype
[319]2427 sys.exit(1)
2428
2429 byte_stream = bytearray()
[406]2430 byte_stream += mapping.str2bytes( 32, self.name ) # pseg name
[319]2431 byte_stream += mapping.int2bytes( 8 , self.base ) # physical base address
2432 byte_stream += mapping.int2bytes( 8 , self.size ) # segment length
2433 byte_stream += mapping.int2bytes( 4 , segtype_int ) # segment type
2434 byte_stream += mapping.int2bytes( 4 , cluster.index ) # cluster global index
[406]2435 byte_stream += mapping.int2bytes( 4 , 0 ) # linked list of vsegs
[319]2436
2437 if ( verbose ):
2438 print 'pbase = %x' % self.base
2439 print 'size = %x' % self.size
2440 print 'type = %s' % self.segtype
[406]2441
[319]2442 return byte_stream
2443
2444###########################################################################################
2445class Periph ( object ):
2446###########################################################################################
[406]2447 def __init__( self,
[319]2448 pseg, # associated pseg
2449 ptype, # peripheral type
2450 subtype = 'NONE', # peripheral subtype
2451 channels = 1, # for multi-channels peripherals
2452 arg = 0 ): # optional argument (semantic depends on ptype)
2453
2454 assert ptype in PERIPHTYPES
2455
2456 assert subtype in PERIPHSUBTYPES
2457
2458 self.index = 0 # global index ( set by addPeriph() )
[406]2459 self.channels = channels
2460 self.ptype = ptype
2461 self.subtype = subtype
[319]2462 self.arg = arg
2463 self.pseg = pseg
2464 self.irqs = []
[305]2465 return
2466
[319]2467 ################
2468 def xml( self ): # xml for a periph
2469
2470 s = ' <periph type="%s"' % self.ptype
2471 s += ' subtype="%s"' % self.subtype
2472 s += ' psegname="%s"' % self.pseg.name
2473 s += ' channels="%d"' % self.channels
2474 s += ' arg="%d" >\n' % self.arg
[441]2475 if ( (self.ptype == 'PIC') or (self.ptype == 'XCU') ):
[319]2476 for irq in self.irqs: s += irq.xml()
[305]2477 s += ' </periph>\n'
[319]2478
[305]2479 return s
2480
[319]2481 #############################################
2482 def cbin( self, mapping, verbose, expected ): # C binary structure for Periph
[305]2483
[319]2484 if ( verbose ):
2485 print '*** cbin for periph %s in cluster [%d,%d]' \
2486 % (self.ptype, self.pseg.x, self.pseg.y)
[305]2487
[319]2488 # check index
2489 if (self.index != expected):
[348]2490 print '[genmap error] in Periph.cbin() : periph global index = %d / expected = %d' \
[319]2491 % (self.index, expected )
2492 sys.exit(1)
[305]2493
[319]2494 # compute pseg global index
2495 pseg_id = self.pseg.index
[305]2496
[319]2497 # compute first irq global index
2498 if ( len(self.irqs) > 0 ):
2499 irq_id = self.irqs[0].index
2500 else:
2501 irq_id = 0
[305]2502
[319]2503 # compute numerical value for ptype
2504 ptype_id = 0xFFFFFFFF
[406]2505 for x in xrange( len(PERIPHTYPES) ):
[319]2506 if ( self.ptype == PERIPHTYPES[x] ): ptype_id = x
2507 if ( ptype_id == 0xFFFFFFFF ):
[348]2508 print '[genmap error] in Periph.cbin() : undefined peripheral type %s' % self.ptype
[319]2509 sys.exit(1)
[305]2510
[319]2511 # compute numerical value for subtype
2512 subtype_id = 0xFFFFFFFF
[406]2513 for x in xrange( len(PERIPHSUBTYPES) ):
[319]2514 if ( self.subtype == PERIPHSUBTYPES[x] ): subtype_id = x
[305]2515
[319]2516 # compute
2517 byte_stream = bytearray()
[406]2518 byte_stream += mapping.int2bytes( 4 , ptype_id ) # peripheral type
[319]2519 byte_stream += mapping.int2bytes( 4 , subtype_id ) # peripheral subtype
[406]2520 byte_stream += mapping.int2bytes( 4 , pseg_id ) # pseg global index
[319]2521 byte_stream += mapping.int2bytes( 4 , self.channels ) # number of channels
2522 byte_stream += mapping.int2bytes( 4 , self.arg ) # optionnal argument
[406]2523 byte_stream += mapping.int2bytes( 4 , len( self.irqs ) ) # number of input irqs
2524 byte_stream += mapping.int2bytes( 4 , irq_id ) # first irq global index
[305]2525
[319]2526 if ( verbose ):
2527 print 'ptype = %d' % ptype_id
2528 print 'pseg_id = %d' % pseg_id
2529 print 'nb_irqs = %d' % len( self.irqs )
[406]2530 print 'irq_id = %d' % irq_id
[319]2531 return byte_stream
[305]2532
[319]2533###########################################################################################
2534class Irq ( object ):
2535###########################################################################################
[406]2536 def __init__( self,
[319]2537 irqtype, # input IRQ type : HWI / WTI / PTI (for XCU only)
2538 srcid, # input IRQ index (for XCU or PIC)
2539 isrtype, # Type of ISR to be executed
2540 channel = 0 ): # channel index for multi-channel ISR
[305]2541
[319]2542 assert irqtype in IRQTYPES
2543 assert isrtype in ISRTYPES
2544 assert srcid < 32
[305]2545
[319]2546 self.index = 0 # global index ( set by addIrq() )
[406]2547 self.irqtype = irqtype # IRQ type
[319]2548 self.srcid = srcid # source IRQ index
[406]2549 self.isrtype = isrtype # ISR type
[319]2550 self.channel = channel # channel index (for multi-channels ISR)
[305]2551 return
2552
[319]2553 ################
2554 def xml( self ): # xml for Irq
[305]2555
[319]2556 return ' <irq srctype="%s" srcid="%d" isr="%s" channel="%d" />\n' \
2557 % ( self.irqtype, self.srcid, self.isrtype, self.channel )
[305]2558
[319]2559 #############################################
2560 def cbin( self, mapping, verbose, expected ): # C binary structure for Irq
[305]2561
[319]2562 if ( verbose ):
[406]2563 print '*** cbin for irq[%d]' % (self.index)
[305]2564
[319]2565 # check index
2566 if (self.index != expected):
[348]2567 print '[genmap error] in Irq.cbin() : irq global index = %d / expected = %d' \
[319]2568 % (self.index, expected )
2569 sys.exit(1)
[305]2570
[319]2571 # compute numerical value for irqtype
2572 irqtype_id = 0xFFFFFFFF
2573 for x in xrange( len(IRQTYPES) ):
[406]2574 if ( self.irqtype == IRQTYPES[x] ):
[319]2575 irqtype_id = x
2576 if ( irqtype_id == 0xFFFFFFFF ):
[348]2577 print '[genmap error] in Irq.cbin() : undefined irqtype %s' % self.irqtype
[319]2578 sys.exit(1)
[305]2579
[319]2580 # compute numerical value for isrtype
2581 isrtype_id = 0xFFFFFFFF
[406]2582 for x in xrange( len(ISRTYPES) ):
2583 if ( self.isrtype == ISRTYPES[x] ):
[319]2584 isrtype_id = x
2585 if ( isrtype_id == 0xFFFFFFFF ):
[348]2586 print '[genmap error] in Irq.cbin() : undefined isrtype %s' % self.isrtype
[319]2587 sys.exit(1)
2588
2589 byte_stream = bytearray()
2590 byte_stream += mapping.int2bytes( 4, irqtype_id )
2591 byte_stream += mapping.int2bytes( 4, self.srcid )
2592 byte_stream += mapping.int2bytes( 4, isrtype_id )
2593 byte_stream += mapping.int2bytes( 4, self.channel )
2594 byte_stream += mapping.int2bytes( 4, 0 )
2595 byte_stream += mapping.int2bytes( 4, 0 )
2596
2597 if ( verbose ):
2598 print 'irqtype = %s' % self.irqtype
2599 print 'srcid = %d' % self.srcid
2600 print 'isrtype = %s' % self.isrtype
2601 print 'channel = %d' % self.channel
2602
2603 return byte_stream
2604
2605###########################################################################################
2606class Coproc ( object ):
2607###########################################################################################
[406]2608 def __init__( self,
2609 pseg ): # associated pseg
[319]2610
2611 self.index = 0 # global index value set by addCoproc()
2612 self.pseg = pseg
2613 self.ports = []
2614
[305]2615 return
2616
[319]2617 ################
[406]2618 def xml( self ): # xml for Coproc
[305]2619
[348]2620 print '[genmap error] in Coproc.xml() : not defined yet'
[319]2621 sys.exit(1)
2622
[406]2623 return
[319]2624
2625 #############################################
2626 def cbin( self, mapping, verbose, expected ): # C binary structure for Coproc
2627
2628 if ( verbose ):
2629 print '*** cbin for coproc in cluster (%d,%d)' % (self.pseg.x, self.pseg.y)
2630
2631 # check index
2632 if (self.index != expected):
[348]2633 print '[genmap error] in Coproc.cbin() : coproc global index = %d / expected = %d' \
[319]2634 % (self.index, expected )
2635 sys.exit(1)
2636
2637 # compute pseg global index
2638 pseg_id = self.pseg.index
2639
2640 # compute first port global index
2641 port_id = self.ports[0].index
2642
2643 byte_stream = bytearray()
2644 byte_stream += mapping.str2bytes( 32, self.pseg.name ) # probablement inutile (AG)
[406]2645 byte_stream += mapping.int2bytes( 4 , pseg_id ) # pseg global index
2646 byte_stream += mapping.int2bytes( 4 , len( self.ports ) ) # number of input irqs
2647 byte_stream += mapping.int2bytes( 4 , port_id ) # first port global index
2648
[319]2649 if ( verbose ):
2650 print 'irqtype = %s' % self.irqtype
2651 print 'pseg_id = %d' % pseg_id
2652 print 'nb_ports = %d' % len( self.ports )
2653 print 'port_id %d' % port_id
[406]2654
[319]2655 return byte_stream
2656
2657###########################################################################################
2658class Cpport ( object ):
2659###########################################################################################
[406]2660 def __init__( self,
2661 direction,
2662 vspacename,
[319]2663 mwmrname ):
2664
2665 self.index = 0 # global index ( set by addCpport() )
2666 self.direction = direction # TO_COPROC / FROM_COPROC
2667 self.vspacename = vspacename # name of vspace containing mwmr channel
2668 self.mwmrname = mwmrname # name of vobj defining mwmr channel
2669
[305]2670 return
2671
[319]2672 ################
2673 def xml( self ): # xml for Cpport
[305]2674
[348]2675 print '[genmap error] in Cpport.xml() : not defined yet'
[319]2676 sys.exit(1)
[305]2677
[406]2678 return
[319]2679
2680 #############################################
2681 def cbin( self, mapping, verbose, expected ): # C binary structure for Cpport
2682
2683 if ( verbose ):
2684 print '*** cbin for cpport[%d]' % (self.index)
2685
2686 # check index
2687 if ( self.index != expected ):
[348]2688 print '[genmap error] in Cpport.cbin() : port global index = %d / expected = %d' \
[319]2689 % ( self.index, expected )
2690 sys.exit(1)
2691
2692 # compute numerical value for direction
2693 if ( self.direction == 'TO_COPROC' ):
2694 dir_int = 0
2695 else:
2696 dir_int = 1
2697
2698 # compute vspace global index
2699 vspace_id = 0xFFFFFFFF
2700 for vspace in mapping.vspaces:
[406]2701 if ( self.vspacename == vspace.name ):
[319]2702 vspace_id = vspace.index
2703 if (vspace_id == 0xFFFFFFFF):
[348]2704 print '[genmap error] in Cpport.cbin() : vspace name %s not found' \
[319]2705 % ( self.vspacename )
2706 sys.exit(1)
2707
2708 # compute mwmr global index
2709 mwmr_id = 0xFFFFFFFF
2710 for vseg in mapping.vspace[vspace_id].vsegs:
2711 for vobj in vseg.vobjs:
[406]2712 if (self.mwmrname == vobj.name):
[319]2713 mwmr_id = vobj.index
2714 if (mwmr_id == 0xFFFFFFFF):
[348]2715 print '[genmap error] in Cpport.cbin() : mwmr vobj name %s not found in vspace %s' \
[319]2716 % ( self.mwmrname, self.vspacename )
2717 sys.exit(1)
2718
2719 byte_stream = bytearray()
[406]2720 byte_stream += mapping.int2bytes( 4 , dir_int ) # pseg global index
2721 byte_stream += mapping.int2bytes( 4 , vspace_id ) # vspace global index
2722 byte_stream += mapping.int2bytes( 4 , mwmr_id ) # mwmr vobj global index
2723
[319]2724 if ( verbose ):
2725 print 'direction = %s' % self.direction
2726 print 'vspace_id = %d' % vspace_id
2727 print 'mwmr_id = %d' % mwmr_id
2728
2729 return byte_stream
2730
2731
[305]2732# Local Variables:
2733# tab-width: 4;
2734# c-basic-offset: 4;
2735# c-file-offsets:((innamespace . 0)(inline-open . 0));
2736# indent-tabs-mode: nil;
2737# End:
2738#
2739# vim: filetype=python:expandtab:shiftwidth=4:tabstop=4:softtabstop=4
2740
Note: See TracBrowser for help on using the repository browser.