root/ossiedev/trunk/tools/WaveDev/wavedev/importResource.py @ 10825

Revision 10825, 13.9 KB (checked in by Snyder.Jason, 22 months ago)

modified getResource to now check for alternative implementations and read their properties from their prf files

  • Property svn:eol-style set to native
Line 
1## Copyright 2005, 2006, 2007 Virginia Polytechnic Institute and State University
2##
3## This file is part of the OSSIE Waveform Developer.
4##
5## OSSIE Waveform Developer is free software; you can redistribute it and/or modify
6## it under the terms of the GNU General Public License as published by
7## the Free Software Foundation; either version 2 of the License, or
8## (at your option) any later version.
9##
10## OSSIE Waveform Developer is distributed in the hope that it will be useful,
11## but WITHOUT ANY WARRANTY; without even the implied warranty of
12## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13## GNU General Public License for more details.
14##
15## You should have received a copy of the GNU General Public License
16## along with OSSIE Waveform Developer; if not, write to the Free Software
17## Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
18
19import os, sys
20import xml.dom.minidom
21from xml.dom.minidom import Node
22import ComponentClass as CC
23from errorMsg import *
24
25availableTypes = ["boolean", "char", "double", "float", "short", "long",
26                    "objref", "octet", "string", "ulong","ushort"]
27availableKinds = ["allocation", "configure", "test", "execparam", "factoryparam"]
28availableActions = ["eq", "ne", "gt", "lt", "ge", "le", "external"]
29availableModes = ["readonly", "readwrite", "writeonly"]
30
31def getResource(path,Rname,parent):
32    scdPath = findFile(path,Rname,".scd.xml")               
33    if scdPath == None:         
34        errorMsg(parent,"No scd file found for: " + Rname)
35        return
36   
37    spdPath = findFile(path,Rname,".spd.xml")
38    prfPath = findFile(path,Rname,".prf.xml")
39   
40    prefix = "/sdr/dom"
41    if path.startswith("/sdr/dev"):
42        prefix = "/sdr/dev"
43    #
44    # Build the main component or device from the SCD file   
45    #
46    doc_scd = xml.dom.minidom.parse(scdPath)
47    try:
48        componenttypeNode = doc_scd.getElementsByTagName("componenttype")
49        componenttype = componenttypeNode[0].childNodes[0].data
50    except:
51        errorMsg(parent,"Invalid file: " + scdPath)
52        return None
53   
54    doc_spd = xml.dom.minidom.parse(spdPath)
55
56    # get resource description
57    # note: this is not the same as the implementation description
58    softpkgNode = doc_spd.getElementsByTagName("softpkg")[0]
59    Rdescription = ''
60    for n in softpkgNode.childNodes:
61        if n.nodeName == "description":
62            resDescriptionNode = doc_spd.getElementsByTagName("description")
63            try:
64                Rdescription = resDescriptionNode[0].firstChild.data
65            except:
66                pass
67            break
68
69    #Instantiate a new component of the appropriate type
70    if componenttype == u'resource':
71        newComp = CC.Component(name=Rname,type='resource',description=Rdescription)
72    elif componenttype == u'executabledevice':
73        newComp = CC.Component(name=Rname,type='executabledevice',description=Rdescription)
74    elif componenttype == u'loadabledevice':
75        newComp = CC.Component(name=Rname,type='loadabledevice',description=Rdescription)
76    elif componenttype == u'device':
77        newComp = CC.Component(name=Rname,type='device',description=Rdescription)
78    else:
79        errorMsg(parent,"Can't identify resource type for: " + Rname)
80        return None
81       
82    # Get the Ports
83    portsNodes = doc_scd.getElementsByTagName("ports")
84    for node in portsNodes:
85        providesPortsNodes = node.getElementsByTagName("provides")
86        usesPortsNodes = node.getElementsByTagName("uses")
87
88    # Provides ports
89    for node in providesPortsNodes:
90        tmpName = node.getAttribute("providesname")
91        tmpInt = getInterface( node.getAttribute("repid"), tmpName )
92        if tmpInt == None:
93            return None
94        portTypeNodeList = node.getElementsByTagName("porttype")
95        tmpType = portTypeNodeList[0].getAttribute("type")
96        newPort = CC.Port(tmpName,tmpInt,type='Provides',portType=tmpType)
97        newComp.ports.append(newPort)
98
99    # Uses ports
100    for node in usesPortsNodes:
101        tmpName = node.getAttribute("usesname")
102        tmpInt = getInterface( node.getAttribute("repid"), tmpName )
103        if tmpInt == None:
104            return None
105        portTypeNodeList = node.getElementsByTagName("porttype")
106        tmpType = portTypeNodeList[0].getAttribute("type")
107        newPort = CC.Port(tmpName,tmpInt,type='Uses',portType=tmpType)
108        newComp.ports.append(newPort)
109
110    # Make sure that xml and code are not generated for this resource
111    newComp.generate = False       
112   
113    # Store the name of the file without the suffix (.scd.xml)
114    i = scdPath.rfind("/")
115    if i != -1:
116        newComp.xmlName = scdPath[i+1:-8]
117    else:
118        newComp.xmlName = scdPath[:-8]
119   
120    #
121    # Import the properties from the PRF file
122    #
123    # If there are no properties, just return the component as is
124    if prfPath == None:
125        return newComp
126    doc_prf = xml.dom.minidom.parse(prfPath)
127    try:
128        propertyNodeList = doc_prf.getElementsByTagName("properties")
129    except:
130        errorMsg(parent,"Invalid file: " + prfPath)
131        return None
132   
133    # get simple properties
134    simplePropertyNodeList = doc_prf.getElementsByTagName("simple")
135    props = getSimpleProperties(simplePropertyNodeList, prfPath)
136    for prop in props:
137        newComp.properties.append(prop)
138   
139
140    # get simple sequence properties
141    simpleSequencePropertyNodeList = doc_prf.getElementsByTagName("simplesequence")
142    sequenceProps = getSimpleSequenceProperties(simpleSequencePropertyNodeList, prfPath)
143    for prop in sequenceProps:
144        newComp.properties.append(prop)
145       
146   
147    # read additional implementations from the spd file if necessary
148   
149    # example implementation node from an spd file
150    #<implementation id="DCE:f559a6a6-a1b3-4acd-b926-d194be1b9930">
151    #    <description>Virtex4 FPGA Implementation, Controller Component</description>
152    #    <propertyfile type="PRF">
153    #        <localfile name="/xml/TxDemo/TxDemo_v4.prf.xml"/>
154    #    </propertyfile>
155    #    <code type="Executable">
156    #        <localfile name="/bin/TxDemo_v4"/>
157    #    </code>
158    #    <os name="Linux" version="2.6.27-rc9-xlnx"/>
159    #    <processor name="powerpc"/>
160    #    <!-- this id points to the impl ID in the XilinxFPGA SPD -->
161    #    <dependency type="Device" softpkgref="DCE:e6d7ca42-e4c9-482c-a9ed-23901f15a465"/>
162    #</implementation>   
163
164    simpleProps = []
165    simpleSequenceProps = []
166    implementationNodes = doc_spd.getElementsByTagName("implementation")
167
168    for node in implementationNodes:
169        id = node.getAttribute("id")
170        tmp = node.getElementsByTagName("description")
171        if len(tmp) > 0:
172            descriptionNode = tmp[0]
173            description = descriptionNode.firstChild.data
174        else:
175            description = ''
176        tmp = node.getElementsByTagName("propertyfile")
177        if len(tmp) > 0:
178            propertyFileNode = tmp[0]
179            propertyFile = prefix + propertyFileNode.getElementsByTagName("localfile")[0].getAttribute("name")
180            propertyDoc = xml.dom.minidom.parse(propertyFile)
181            simplePropNodes = propertyDoc.getElementsByTagName("simple")
182            simpleProps = getSimpleProperties(simplePropNodes, propertyFile)
183           
184            simpleSequencePropNodes = propertyDoc.getElementsByTagName("simplesequence")
185            simpleSequenceProps = getSimpleSequenceProperties(simpleSequencePropNodes, propertyFile)
186        else:
187            propertyFile = None
188        tmp = node.getElementsByTagName("processor")
189        if len(tmp) > 0:
190            processorNode = tmp[0]
191            processor = processorNode.getAttribute("name")
192        else:
193            processor = ''
194       
195        newImplementation = CC.Implementation(id, description, propertyFile, processor)
196        for prop in simpleProps:
197            newImplementation.properties.append(prop)
198        for prop in simpleSequenceProps:
199            newImplementation.properties.append(prop)
200       
201        newComp.implementations.append(newImplementation)
202   
203    return newComp
204
205def getInterface(repid,name):
206    try:
207        repid = repid.strip('IDL:')
208        repid = repid[:repid.rfind(':')]
209        tmpNS = repid[:repid.find('/')]
210        tmpName = repid[repid.find('/')+1:]
211        newInt = CC.Interface(tmpName,nameSpace=tmpNS)
212        return newInt
213       
214    except:
215        errorMsg(parent,"Can't read the Interface information for port: " + name)
216        return None
217   
218   
219def findFile(path,Rname,suf):
220    tmpf = None
221    if os.path.isfile(path + '/' + Rname +'Resource'+suf):
222        tmpf = path + '/' + Rname +'Resource' + suf
223    elif os.path.isfile(path + '/' + Rname + suf):
224        tmpf = path + '/' + Rname + suf     
225    else:
226        tmpFiles = os.listdir(path)
227        for f in tmpFiles:
228            if len(f)>=8 and f[-8:] == suf:
229                tmpf = path + '/' + f
230                break
231    return tmpf
232
233def stripDoctype(xmlfile):
234    """Strips out the DOCTYPE checking because the dtd files are positioned
235       in a relative location to the SCA (OSSIE) filesystem, so when Amara
236       trys to validate against them, it bails out looking for the file.
237       Returns a string representation of the xml file without the DOCTYPE line."""
238   
239    file = open(xmlfile, 'r')
240    xml = ''
241    line = file.readline()
242    while len(line) > 0:
243        if "DOCTYPE" in line:
244            break
245        xml += line
246        line = file.readline()
247    xml += file.read()
248
249    return xml
250
251def getSimpleProperties(simplePropertyNodeList, propertyFile):
252    props = []
253    for node in simplePropertyNodeList:
254        p = getSimpleProperty(node)
255        if p == None:
256            print "There was an error parsing simple properties in the PRF file " + propertyFile
257            continue
258        props.append(p)
259       
260    return props
261
262def getSimpleSequenceProperties(simpleSequencePropertyNodeList, propertyFile):
263    props = []
264    for node in simpleSequencePropertyNodeList:
265        p = getSimpleSequenceProperty(node, propertyFile)
266        if p == None:
267            print "There was an error parsing simple sequence properties in the PRF file " + propetyFile
268            continue
269        props.append(p)
270       
271    return props
272
273def getSimpleProperty(n):
274    tmpName = n.getAttribute("name")
275    tmpID   = n.getAttribute("id")
276    tmpType = n.getAttribute("type")
277    tmpMode = n.getAttribute("mode")
278    tmpDes = n.getAttribute("description")
279
280    if tmpName == "" or tmpID == "" or tmpType == "" or tmpMode == "":
281        return None
282    if tmpMode not in availableModes:
283        return None
284    if tmpType not in availableTypes:
285        return None
286   
287    newProp = CC.SimpleProperty(tmpName,tmpMode,tmpType,description=tmpDes)
288   
289    # Set ID
290    #UUID in the sad file will need to match the UUID in the prf (tmpID is from prf)
291    newProp.id = tmpID
292
293    # Get/set property value
294    valueNodeList = n.getElementsByTagName("value")
295    value = valueNodeList[0].childNodes[0].data
296    newProp.value = newProp.defaultValue = str(value)
297    del valueNodeList, value
298   
299    # Get/set property units
300    unitsNodeList = n.getElementsByTagName("units")
301    if len(unitsNodeList) > 0:
302        units = unitsNodeList[0].childNodes[0].data
303        newProp.units = str(s.units)
304    #del unitsNodeList, units
305   
306    # TODO: Get/set min/max values
307    # TODO: Get/set enum
308   
309    # Get/set kind
310    kindNodeList = n.getElementsByTagName("kind")
311    kindtype = kindNodeList[0].getAttribute("kindtype")
312    if kindtype == "":
313        return None
314    newProp.kind = str(kindtype)
315    del kindNodeList, kindtype
316   
317    # Get/set action
318    actionNodeList = n.getElementsByTagName("action")
319    if len(actionNodeList) > 0:
320        actiontype = actionNodeList[0].getAttribute("type")
321        newProp.action = str(actiontype)
322    #del actionNodeList, actiontype
323       
324    return newProp
325   
326def getSimpleSequenceProperty(n, prfPath):
327    tmpName = n.getAttribute("name")
328    tmpID   = n.getAttribute("id")
329    tmpType = n.getAttribute("type")
330    tmpMode = n.getAttribute("mode")
331    tmpDes = n.getAttribute("description")
332
333    if tmpName == "" or tmpID == "" or tmpType == "" or tmpMode == "":
334        return None
335    if tmpMode not in availableModes:
336        return None
337    if tmpType not in availableTypes:
338        return None
339   
340    newProp = CC.SimpleSequenceProperty(tmpName,tmpMode,tmpType,description=tmpDes)
341   
342    # Set ID
343    #UUID in the sad file will need to match the UUID in the prf (tmpID is from prf)
344    newProp.id = tmpID
345
346
347    # Get/set property values
348    newProp.values = []
349    newProp.defaultValues = []
350    valuesNodeList = n.getElementsByTagName("values")
351   
352    try:
353        valueNodeList = valuesNodeList[0].getElementsByTagName("value")
354    except:
355        valueNodeList = n.getElementsByTagName("value") #cbd
356        #print "\nERROR in " + prfPath
357        #print "ERROR parsing prf file.  You may be missing a values tag in a simple sequence property.\n"
358        #sys.exit()
359        print "\nWarning in " + prfPath
360        print "Warning parsing prf file.  You may be missing a values tag in a simple sequence property.\n"
361
362    for valueNode in valueNodeList:
363        tmpVal = valueNode.childNodes[0].data
364        newProp.values.append(str(tmpVal))
365        newProp.defaultValues.append(str(tmpVal))
366    del valueNodeList
367
368    # Get/set property units
369    unitsNodeList = n.getElementsByTagName("units")
370    if len(unitsNodeList) > 0:
371        units = unitsNodeList[0].childNodes[0].data
372        newProp.units = str(s.units)
373    #del unitsNodeList, units
374   
375    # TODO: Get/set min/max values
376    # TODO: Get/set enum
377   
378    # Get/set kind
379    kindNodeList = n.getElementsByTagName("kind")
380    kindtype = kindNodeList[0].getAttribute("kindtype")
381    if kindtype == "":
382        return None
383    newProp.kind = str(kindtype)
384    del kindNodeList, kindtype
385
386    # Get/set action
387    actionNodeList = n.getElementsByTagName("action")
388    if len(actionNodeList) > 0:
389        actiontype = actionNodeList[0].getAttribute("type")
390        newProp.action = str(actiontype)
391    #del actionNodeList, actiontype
392
393    return newProp
Note: See TracBrowser for help on using the browser.