5 # File : wireshark_be.py
7 # Author : Frank Singleton (frank.singleton@ericsson.com)
9 # Copyright (C) 2001 Frank Singleton, Ericsson Inc.
11 # This file is a backend to "omniidl", used to generate "Wireshark"
12 # dissectors from IDL descriptions. The output language generated
13 # is "C". It will generate code to use the GIOP/IIOP get_CDR_XXX API.
15 # Please see packet-giop.h in Wireshark distro for API description.
16 # Wireshark is available at http://www.wireshark.org/
18 # Omniidl is part of the OmniOrb distribution, and is available at
19 # http://omniorb.sourceforge.net
21 # This program is free software; you can redistribute it and/or modify it
22 # under the terms of the GNU General Public License as published by
23 # the Free Software Foundation; either version 2 of the License, or
24 # (at your option) any later version.
26 # This program is distributed in the hope that it will be useful,
27 # but WITHOUT ANY WARRANTY; without even the implied warranty of
28 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
29 # General Public License for more details.
31 # You should have received a copy of the GNU General Public License
32 # along with this program; if not, write to the Free Software
33 # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
37 # Omniidl Back-end which parses an IDL data structure provided by the frontend
38 # and generates packet-idl-xxx.[ch] for compiling as a dissector in
39 # Wireshark IP protocol anlayser.
46 # Crawl all the way down all branches until I hit "Operation", "Enum", "Attribute",
47 # "Struct" and "Union" nodes. Then store these nodes in lists.
49 # Pass these lists (via an object ref) to the src code
50 # generator (wireshark_gen) class and let it do the hard work !
53 # Dont forget structs can contain embedded structs etc .. so dont forget
54 # to peek inside and check :-)
59 """Wireshark IDL compiler back-end."""
61 from omniidl
import idlast
, idltype
, idlvisitor
, idlutil
, output
64 from wireshark_gen
import wireshark_gen_C
67 # This class finds the "Operation" nodes ,Enum Nodes, "Attribute" nodes, Struct Nodes
68 # and Union Nodes. Then it hands them off to an instance of the source code generator
69 # class "wireshark_gen"
72 class WiresharkVisitor
:
74 DEBUG
= 0 # debug flag
76 def __init__(self
, st
):
78 self
.oplist
= [] # list of operation nodes
79 self
.enlist
= [] # list of enum nodes
80 self
.atlist
= [] # list of attribute nodes
81 self
.stlist
= [] # list of struct nodes
82 self
.unlist
= [] # list of union nodes
85 def visitAST(self
, node
):
87 print "XXX visitAST() node = ", node
89 for n
in node
.declarations():
90 if isinstance(n
, idlast
.Module
):
92 if isinstance(n
, idlast
.Interface
):
93 self
.visitInterface(n
)
94 if isinstance(n
, idlast
.Operation
):
95 self
.visitOperation(n
)
96 if isinstance(n
, idlast
.Attribute
):
97 self
.visitAttribute(n
)
98 if isinstance(n
, idlast
.Enum
):
100 if isinstance(n
, idlast
.Struct
):
102 if isinstance(n
, idlast
.Union
):
105 # Check for Typedef structs and unions
107 if isinstance(n
, idlast
.Typedef
):
108 self
.visitTypedef(n
) # who are you ?
111 def visitModule(self
, node
):
113 print "XXX visitModule() node = ", node
115 for n
in node
.definitions():
116 if isinstance(n
, idlast
.Module
):
118 if isinstance(n
, idlast
.Interface
):
119 self
.visitInterface(n
)
120 if isinstance(n
, idlast
.Operation
):
121 self
.visitOperation(n
)
122 if isinstance(n
, idlast
.Attribute
):
123 self
.visitAttribute(n
)
124 if isinstance(n
, idlast
.Enum
):
126 if isinstance(n
, idlast
.Struct
):
128 if isinstance(n
, idlast
.Union
):
131 # Check for Typedef structs and unions
133 if isinstance(n
, idlast
.Typedef
):
134 self
.visitTypedef(n
) # who are you ?
137 def visitInterface(self
, node
):
139 print "XXX visitInterface() node = ", node
141 for c
in node
.callables():
142 if isinstance(c
, idlast
.Operation
):
143 self
.visitOperation(c
)
144 if isinstance(c
, idlast
.Attribute
):
145 self
.visitAttribute(c
)
147 for d
in node
.contents():
148 if isinstance(d
, idlast
.Enum
):
151 if isinstance(d
, idlast
.Struct
):
154 if isinstance(d
, idlast
.Union
):
157 # Check for Typedef structs and unions
159 if isinstance(d
, idlast
.Typedef
):
160 self
.visitTypedef(d
) # who are you ?
168 # populates the operations node list "oplist"
172 def visitOperation(self
,opnode
):
173 if not opnode
in self
.oplist
:
174 self
.oplist
.append(opnode
) # store operation node
179 # populates the attribute node list "atlist"
183 def visitAttribute(self
,atnode
):
184 if not atnode
in self
.atlist
:
185 self
.atlist
.append(atnode
) # store attribute node
191 # populates the Enum node list "enlist"
195 def visitEnum(self
,enode
):
196 if not enode
in self
.enlist
:
197 self
.enlist
.append(enode
) # store enum node if unique
202 # Search to see if its a typedef'd struct, union, or enum
204 # eg: typdef enum colors {red, green, blue } mycolors;
207 def visitTypedef(self
,td
):
208 d
= td
.aliasType() # get Type, possibly Declared
209 if isinstance(d
,idltype
.Declared
):
210 self
.visitDeclared(d
)
216 # Search to see if its a struct, union, or enum
220 def visitDeclared(self
,d
):
221 if isinstance(d
,idltype
.Declared
):
222 sue
= d
.decl() # grab the struct or union or enum
224 if isinstance(sue
, idlast
.Struct
):
225 self
.visitStruct(sue
)
226 if isinstance(sue
, idlast
.Union
):
228 if isinstance(sue
, idlast
.Enum
):
237 # populates the struct node list "stlist"
238 # and checks its members also
242 def visitStruct(self
,stnode
):
243 if not stnode
in self
.stlist
:
244 self
.stlist
.append(stnode
) # store struct node if unique and avoid recursive loops
245 # if we come across recursive structs
247 for m
in stnode
.members(): # find embedded struct definitions within this
249 if isinstance(mt
,idltype
.Declared
):
250 self
.visitDeclared(mt
) # if declared, then check it out
257 # populates the struct node list "unlist"
258 # and checks its members also
262 def visitUnion(self
,unnode
):
263 if not unnode
in self
.unlist
:
264 self
.unlist
.append(unnode
) # store union node if unique
266 if unnode
.constrType(): # enum defined within switch type
267 if isinstance(unnode
.switchType(),idltype
.Declared
):
268 self
.visitDeclared(unnode
.switchType())
270 for c
in unnode
.cases():
272 if isinstance(ct
,idltype
.Declared
):
273 self
.visitDeclared(ct
) # if declared, then check it out
280 st
= output
.Stream(sys
.stdout
, 4) # set indent for stream
281 ev
= WiresharkVisitor(st
) # create visitor object
283 ev
.visitAST(tree
) # go find some operations
286 # Grab name of main IDL file being compiled.
288 # Assumption: Name is of the form abcdefg.xyz (eg: CosNaming.idl)
291 fname
= path
.basename(tree
.file()) # grab basename only, dont care about path
292 nl
= string
.split(fname
,".")[0] # split name of main IDL file using "." as separator
293 # and grab first field (eg: CosNaming)
297 print "XXX - Operation node ", i
, " repoId() = ", i
.repoId()
299 print "XXX - Attribute node ", i
, " identifiers() = ", i
.identifiers()
301 print "XXX - Enum node ", i
, " repoId() = ", i
.repoId()
303 print "XXX - Struct node ", i
, " repoId() = ", i
.repoId()
305 print "XXX - Union node ", i
, " repoId() = ", i
.repoId()
308 # create a C generator object
309 # and generate some C code
314 eg
= wireshark_gen_C(ev
.st
, string
.upper(nl
), string
.lower(nl
), string
.capitalize(nl
) + " Dissector Using GIOP API")
315 eg
.genCode(ev
.oplist
, ev
.atlist
, ev
.enlist
, ev
.stlist
, ev
.unlist
) # pass them onto the C generator