1*16467b97STreehugger Robot /** \file
2*16467b97STreehugger Robot * This is the standard tree adaptor used by the C runtime unless the grammar
3*16467b97STreehugger Robot * source file says to use anything different. It embeds a BASE_TREE to which
4*16467b97STreehugger Robot * it adds its own implementation of anything that the base tree is not
5*16467b97STreehugger Robot * good for, plus a number of methods that any other adaptor type
6*16467b97STreehugger Robot * needs to implement too.
7*16467b97STreehugger Robot * \ingroup pANTLR3_COMMON_TREE_ADAPTOR
8*16467b97STreehugger Robot */
9*16467b97STreehugger Robot
10*16467b97STreehugger Robot // [The "BSD licence"]
11*16467b97STreehugger Robot // Copyright (c) 2005-2009 Jim Idle, Temporal Wave LLC
12*16467b97STreehugger Robot // http://www.temporal-wave.com
13*16467b97STreehugger Robot // http://www.linkedin.com/in/jimidle
14*16467b97STreehugger Robot //
15*16467b97STreehugger Robot // All rights reserved.
16*16467b97STreehugger Robot //
17*16467b97STreehugger Robot // Redistribution and use in source and binary forms, with or without
18*16467b97STreehugger Robot // modification, are permitted provided that the following conditions
19*16467b97STreehugger Robot // are met:
20*16467b97STreehugger Robot // 1. Redistributions of source code must retain the above copyright
21*16467b97STreehugger Robot // notice, this list of conditions and the following disclaimer.
22*16467b97STreehugger Robot // 2. Redistributions in binary form must reproduce the above copyright
23*16467b97STreehugger Robot // notice, this list of conditions and the following disclaimer in the
24*16467b97STreehugger Robot // documentation and/or other materials provided with the distribution.
25*16467b97STreehugger Robot // 3. The name of the author may not be used to endorse or promote products
26*16467b97STreehugger Robot // derived from this software without specific prior written permission.
27*16467b97STreehugger Robot //
28*16467b97STreehugger Robot // THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
29*16467b97STreehugger Robot // IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
30*16467b97STreehugger Robot // OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
31*16467b97STreehugger Robot // IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
32*16467b97STreehugger Robot // INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
33*16467b97STreehugger Robot // NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
34*16467b97STreehugger Robot // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
35*16467b97STreehugger Robot // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
36*16467b97STreehugger Robot // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
37*16467b97STreehugger Robot // THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
38*16467b97STreehugger Robot
39*16467b97STreehugger Robot #include <antlr3commontreeadaptor.h>
40*16467b97STreehugger Robot
41*16467b97STreehugger Robot #ifdef ANTLR3_WINDOWS
42*16467b97STreehugger Robot #pragma warning( disable : 4100 )
43*16467b97STreehugger Robot #endif
44*16467b97STreehugger Robot
45*16467b97STreehugger Robot /* BASE_TREE_ADAPTOR overrides... */
46*16467b97STreehugger Robot static pANTLR3_BASE_TREE dupNode (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE treeNode);
47*16467b97STreehugger Robot static pANTLR3_BASE_TREE create (pANTLR3_BASE_TREE_ADAPTOR adpator, pANTLR3_COMMON_TOKEN payload);
48*16467b97STreehugger Robot static pANTLR3_BASE_TREE dbgCreate (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_COMMON_TOKEN payload);
49*16467b97STreehugger Robot static pANTLR3_COMMON_TOKEN createToken (pANTLR3_BASE_TREE_ADAPTOR adaptor, ANTLR3_UINT32 tokenType, pANTLR3_UINT8 text);
50*16467b97STreehugger Robot static pANTLR3_COMMON_TOKEN createTokenFromToken (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_COMMON_TOKEN fromToken);
51*16467b97STreehugger Robot static pANTLR3_COMMON_TOKEN getToken (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t);
52*16467b97STreehugger Robot static pANTLR3_STRING getText (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t);
53*16467b97STreehugger Robot static ANTLR3_UINT32 getType (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t);
54*16467b97STreehugger Robot static pANTLR3_BASE_TREE getChild (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t, ANTLR3_UINT32 i);
55*16467b97STreehugger Robot static ANTLR3_UINT32 getChildCount (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t);
56*16467b97STreehugger Robot static void replaceChildren (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE parent, ANTLR3_INT32 startChildIndex, ANTLR3_INT32 stopChildIndex, pANTLR3_BASE_TREE t);
57*16467b97STreehugger Robot static void setDebugEventListener (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_DEBUG_EVENT_LISTENER debugger);
58*16467b97STreehugger Robot static void setChildIndex (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t, ANTLR3_INT32 i);
59*16467b97STreehugger Robot static ANTLR3_INT32 getChildIndex (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t);
60*16467b97STreehugger Robot static void setParent (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE child, pANTLR3_BASE_TREE parent);
61*16467b97STreehugger Robot static pANTLR3_BASE_TREE getParent (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE child);
62*16467b97STreehugger Robot static void setChild (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t, ANTLR3_UINT32 i, pANTLR3_BASE_TREE child);
63*16467b97STreehugger Robot static void deleteChild (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t, ANTLR3_UINT32 i);
64*16467b97STreehugger Robot static pANTLR3_BASE_TREE errorNode (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_TOKEN_STREAM ctnstream, pANTLR3_COMMON_TOKEN startToken, pANTLR3_COMMON_TOKEN stopToken, pANTLR3_EXCEPTION e);
65*16467b97STreehugger Robot /* Methods specific to each tree adaptor
66*16467b97STreehugger Robot */
67*16467b97STreehugger Robot static void setTokenBoundaries (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t, pANTLR3_COMMON_TOKEN startToken, pANTLR3_COMMON_TOKEN stopToken);
68*16467b97STreehugger Robot static void dbgSetTokenBoundaries (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t, pANTLR3_COMMON_TOKEN startToken, pANTLR3_COMMON_TOKEN stopToken);
69*16467b97STreehugger Robot static ANTLR3_MARKER getTokenStartIndex (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t);
70*16467b97STreehugger Robot static ANTLR3_MARKER getTokenStopIndex (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t);
71*16467b97STreehugger Robot
72*16467b97STreehugger Robot static void ctaFree (pANTLR3_BASE_TREE_ADAPTOR adaptor);
73*16467b97STreehugger Robot
74*16467b97STreehugger Robot /** Create a new tree adaptor. Note that despite the fact that this is
75*16467b97STreehugger Robot * creating a new COMMON_TREE adaptor, we return the address of the
76*16467b97STreehugger Robot * BASE_TREE interface, as should any other adaptor that wishes to be
77*16467b97STreehugger Robot * used as the tree element of a tree parse/build. It needs to be given the
78*16467b97STreehugger Robot * address of a valid string factory as we do not know what the originating
79*16467b97STreehugger Robot * input stream encoding type was. This way we can rely on just using
80*16467b97STreehugger Robot * the original input stream's string factory or one of the correct type
81*16467b97STreehugger Robot * which the user supplies us.
82*16467b97STreehugger Robot */
83*16467b97STreehugger Robot ANTLR3_API pANTLR3_BASE_TREE_ADAPTOR
ANTLR3_TREE_ADAPTORNew(pANTLR3_STRING_FACTORY strFactory)84*16467b97STreehugger Robot ANTLR3_TREE_ADAPTORNew(pANTLR3_STRING_FACTORY strFactory)
85*16467b97STreehugger Robot {
86*16467b97STreehugger Robot pANTLR3_COMMON_TREE_ADAPTOR cta;
87*16467b97STreehugger Robot
88*16467b97STreehugger Robot // First job is to create the memory we need for the tree adaptor interface.
89*16467b97STreehugger Robot //
90*16467b97STreehugger Robot cta = (pANTLR3_COMMON_TREE_ADAPTOR) ANTLR3_MALLOC((size_t)(sizeof(ANTLR3_COMMON_TREE_ADAPTOR)));
91*16467b97STreehugger Robot
92*16467b97STreehugger Robot if (cta == NULL)
93*16467b97STreehugger Robot {
94*16467b97STreehugger Robot return NULL;
95*16467b97STreehugger Robot }
96*16467b97STreehugger Robot
97*16467b97STreehugger Robot // Memory is initialized, so initialize the base tree adaptor
98*16467b97STreehugger Robot //
99*16467b97STreehugger Robot antlr3BaseTreeAdaptorInit(&(cta->baseAdaptor), NULL);
100*16467b97STreehugger Robot
101*16467b97STreehugger Robot // Install our interface overrides. Strangeness is to allow generated code to treat them
102*16467b97STreehugger Robot // as returning void *
103*16467b97STreehugger Robot //
104*16467b97STreehugger Robot cta->baseAdaptor.dupNode = (void * (*) (pANTLR3_BASE_TREE_ADAPTOR, void *))
105*16467b97STreehugger Robot dupNode;
106*16467b97STreehugger Robot cta->baseAdaptor.create = (void * (*) (pANTLR3_BASE_TREE_ADAPTOR, pANTLR3_COMMON_TOKEN))
107*16467b97STreehugger Robot create;
108*16467b97STreehugger Robot cta->baseAdaptor.createToken =
109*16467b97STreehugger Robot createToken;
110*16467b97STreehugger Robot cta->baseAdaptor.createTokenFromToken =
111*16467b97STreehugger Robot createTokenFromToken;
112*16467b97STreehugger Robot cta->baseAdaptor.setTokenBoundaries = (void (*) (pANTLR3_BASE_TREE_ADAPTOR, void *, pANTLR3_COMMON_TOKEN, pANTLR3_COMMON_TOKEN))
113*16467b97STreehugger Robot setTokenBoundaries;
114*16467b97STreehugger Robot cta->baseAdaptor.getTokenStartIndex = (ANTLR3_MARKER (*) (pANTLR3_BASE_TREE_ADAPTOR, void *))
115*16467b97STreehugger Robot getTokenStartIndex;
116*16467b97STreehugger Robot cta->baseAdaptor.getTokenStopIndex = (ANTLR3_MARKER (*) (pANTLR3_BASE_TREE_ADAPTOR, void *))
117*16467b97STreehugger Robot getTokenStopIndex;
118*16467b97STreehugger Robot cta->baseAdaptor.getText = (pANTLR3_STRING (*) (pANTLR3_BASE_TREE_ADAPTOR, void *))
119*16467b97STreehugger Robot getText;
120*16467b97STreehugger Robot cta->baseAdaptor.getType = (ANTLR3_UINT32 (*) (pANTLR3_BASE_TREE_ADAPTOR, void *))
121*16467b97STreehugger Robot getType;
122*16467b97STreehugger Robot cta->baseAdaptor.getChild = (void * (*) (pANTLR3_BASE_TREE_ADAPTOR, void *, ANTLR3_UINT32))
123*16467b97STreehugger Robot getChild;
124*16467b97STreehugger Robot cta->baseAdaptor.setChild = (void (*) (pANTLR3_BASE_TREE_ADAPTOR, void *, ANTLR3_UINT32, void *))
125*16467b97STreehugger Robot setChild;
126*16467b97STreehugger Robot cta->baseAdaptor.setParent = (void (*) (pANTLR3_BASE_TREE_ADAPTOR, void *, void *))
127*16467b97STreehugger Robot setParent;
128*16467b97STreehugger Robot cta->baseAdaptor.getParent = (void * (*) (pANTLR3_BASE_TREE_ADAPTOR, void *))
129*16467b97STreehugger Robot getParent;
130*16467b97STreehugger Robot cta->baseAdaptor.setChildIndex = (void (*) (pANTLR3_BASE_TREE_ADAPTOR, void *, ANTLR3_UINT32))
131*16467b97STreehugger Robot setChildIndex;
132*16467b97STreehugger Robot cta->baseAdaptor.deleteChild = (void (*) (pANTLR3_BASE_TREE_ADAPTOR, void *, ANTLR3_UINT32))
133*16467b97STreehugger Robot deleteChild;
134*16467b97STreehugger Robot cta->baseAdaptor.getChildCount = (ANTLR3_UINT32 (*) (pANTLR3_BASE_TREE_ADAPTOR, void *))
135*16467b97STreehugger Robot getChildCount;
136*16467b97STreehugger Robot cta->baseAdaptor.getChildIndex = (ANTLR3_INT32 (*) (pANTLR3_BASE_TREE_ADAPTOR, void *))
137*16467b97STreehugger Robot getChildIndex;
138*16467b97STreehugger Robot cta->baseAdaptor.free = (void (*) (pANTLR3_BASE_TREE_ADAPTOR))
139*16467b97STreehugger Robot ctaFree;
140*16467b97STreehugger Robot cta->baseAdaptor.setDebugEventListener =
141*16467b97STreehugger Robot setDebugEventListener;
142*16467b97STreehugger Robot cta->baseAdaptor.replaceChildren = (void (*) (pANTLR3_BASE_TREE_ADAPTOR, void *, ANTLR3_INT32, ANTLR3_INT32, void *))
143*16467b97STreehugger Robot replaceChildren;
144*16467b97STreehugger Robot cta->baseAdaptor.errorNode = (void * (*) (pANTLR3_BASE_TREE_ADAPTOR, pANTLR3_TOKEN_STREAM, pANTLR3_COMMON_TOKEN, pANTLR3_COMMON_TOKEN, pANTLR3_EXCEPTION))
145*16467b97STreehugger Robot errorNode;
146*16467b97STreehugger Robot
147*16467b97STreehugger Robot // Install the super class pointer
148*16467b97STreehugger Robot //
149*16467b97STreehugger Robot cta->baseAdaptor.super = cta;
150*16467b97STreehugger Robot
151*16467b97STreehugger Robot // Install a tree factory for creating new tree nodes
152*16467b97STreehugger Robot //
153*16467b97STreehugger Robot cta->arboretum = antlr3ArboretumNew(strFactory);
154*16467b97STreehugger Robot
155*16467b97STreehugger Robot // Install a token factory for imaginary tokens, these imaginary
156*16467b97STreehugger Robot // tokens do not require access to the input stream so we can
157*16467b97STreehugger Robot // dummy the creation of it, but they will need a string factory.
158*16467b97STreehugger Robot //
159*16467b97STreehugger Robot cta->baseAdaptor.tokenFactory = antlr3TokenFactoryNew(NULL);
160*16467b97STreehugger Robot cta->baseAdaptor.tokenFactory->unTruc.strFactory = strFactory;
161*16467b97STreehugger Robot
162*16467b97STreehugger Robot // Allow the base tree adaptor to share the tree factory's string factory.
163*16467b97STreehugger Robot //
164*16467b97STreehugger Robot cta->baseAdaptor.strFactory = strFactory;
165*16467b97STreehugger Robot
166*16467b97STreehugger Robot // Return the address of the base adaptor interface.
167*16467b97STreehugger Robot //
168*16467b97STreehugger Robot return &(cta->baseAdaptor);
169*16467b97STreehugger Robot }
170*16467b97STreehugger Robot
171*16467b97STreehugger Robot /// Debugging version of the tree adaptor (not normally called as generated code
172*16467b97STreehugger Robot /// calls setDebugEventListener instead which changes a normal token stream to
173*16467b97STreehugger Robot /// a debugging stream and means that a user's instantiation code does not need
174*16467b97STreehugger Robot /// to be changed just to debug with AW.
175*16467b97STreehugger Robot ///
176*16467b97STreehugger Robot ANTLR3_API pANTLR3_BASE_TREE_ADAPTOR
ANTLR3_TREE_ADAPTORDebugNew(pANTLR3_STRING_FACTORY strFactory,pANTLR3_DEBUG_EVENT_LISTENER debugger)177*16467b97STreehugger Robot ANTLR3_TREE_ADAPTORDebugNew(pANTLR3_STRING_FACTORY strFactory, pANTLR3_DEBUG_EVENT_LISTENER debugger)
178*16467b97STreehugger Robot {
179*16467b97STreehugger Robot pANTLR3_BASE_TREE_ADAPTOR ta;
180*16467b97STreehugger Robot
181*16467b97STreehugger Robot // Create a normal one first
182*16467b97STreehugger Robot //
183*16467b97STreehugger Robot ta = ANTLR3_TREE_ADAPTORNew(strFactory);
184*16467b97STreehugger Robot
185*16467b97STreehugger Robot if (ta != NULL)
186*16467b97STreehugger Robot {
187*16467b97STreehugger Robot // Reinitialize as a debug version
188*16467b97STreehugger Robot //
189*16467b97STreehugger Robot antlr3BaseTreeAdaptorInit(ta, debugger);
190*16467b97STreehugger Robot ta->create = (void * (*) (pANTLR3_BASE_TREE_ADAPTOR, pANTLR3_COMMON_TOKEN))
191*16467b97STreehugger Robot dbgCreate;
192*16467b97STreehugger Robot ta->setTokenBoundaries = (void (*) (pANTLR3_BASE_TREE_ADAPTOR, void *, pANTLR3_COMMON_TOKEN, pANTLR3_COMMON_TOKEN))
193*16467b97STreehugger Robot dbgSetTokenBoundaries;
194*16467b97STreehugger Robot }
195*16467b97STreehugger Robot
196*16467b97STreehugger Robot return ta;
197*16467b97STreehugger Robot }
198*16467b97STreehugger Robot
199*16467b97STreehugger Robot /// Causes an existing common tree adaptor to become a debug version
200*16467b97STreehugger Robot ///
201*16467b97STreehugger Robot static void
setDebugEventListener(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_DEBUG_EVENT_LISTENER debugger)202*16467b97STreehugger Robot setDebugEventListener (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_DEBUG_EVENT_LISTENER debugger)
203*16467b97STreehugger Robot {
204*16467b97STreehugger Robot // Reinitialize as a debug version
205*16467b97STreehugger Robot //
206*16467b97STreehugger Robot antlr3BaseTreeAdaptorInit(adaptor, debugger);
207*16467b97STreehugger Robot
208*16467b97STreehugger Robot adaptor->create = (void * (*) (pANTLR3_BASE_TREE_ADAPTOR, pANTLR3_COMMON_TOKEN))
209*16467b97STreehugger Robot dbgCreate;
210*16467b97STreehugger Robot adaptor->setTokenBoundaries = (void (*) (pANTLR3_BASE_TREE_ADAPTOR, void *, pANTLR3_COMMON_TOKEN, pANTLR3_COMMON_TOKEN))
211*16467b97STreehugger Robot dbgSetTokenBoundaries;
212*16467b97STreehugger Robot
213*16467b97STreehugger Robot }
214*16467b97STreehugger Robot
215*16467b97STreehugger Robot static void
ctaFree(pANTLR3_BASE_TREE_ADAPTOR adaptor)216*16467b97STreehugger Robot ctaFree(pANTLR3_BASE_TREE_ADAPTOR adaptor)
217*16467b97STreehugger Robot {
218*16467b97STreehugger Robot pANTLR3_COMMON_TREE_ADAPTOR cta;
219*16467b97STreehugger Robot
220*16467b97STreehugger Robot cta = (pANTLR3_COMMON_TREE_ADAPTOR)(adaptor->super);
221*16467b97STreehugger Robot
222*16467b97STreehugger Robot /* Free the tree factory we created
223*16467b97STreehugger Robot */
224*16467b97STreehugger Robot cta->arboretum->close(((pANTLR3_COMMON_TREE_ADAPTOR)(adaptor->super))->arboretum);
225*16467b97STreehugger Robot
226*16467b97STreehugger Robot /* Free the token factory we created
227*16467b97STreehugger Robot */
228*16467b97STreehugger Robot adaptor->tokenFactory->close(adaptor->tokenFactory);
229*16467b97STreehugger Robot
230*16467b97STreehugger Robot /* Free the super pointer, as it is this that was allocated
231*16467b97STreehugger Robot * and is the common tree structure.
232*16467b97STreehugger Robot */
233*16467b97STreehugger Robot ANTLR3_FREE(adaptor->super);
234*16467b97STreehugger Robot }
235*16467b97STreehugger Robot
236*16467b97STreehugger Robot /* BASE_TREE_ADAPTOR overrides */
237*16467b97STreehugger Robot
238*16467b97STreehugger Robot static pANTLR3_BASE_TREE
errorNode(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_TOKEN_STREAM ctnstream,pANTLR3_COMMON_TOKEN startToken,pANTLR3_COMMON_TOKEN stopToken,pANTLR3_EXCEPTION e)239*16467b97STreehugger Robot errorNode (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_TOKEN_STREAM ctnstream, pANTLR3_COMMON_TOKEN startToken, pANTLR3_COMMON_TOKEN stopToken, pANTLR3_EXCEPTION e)
240*16467b97STreehugger Robot {
241*16467b97STreehugger Robot // Use the supplied common tree node stream to get another tree from the factory
242*16467b97STreehugger Robot // TODO: Look at creating the erronode as in Java, but this is complicated by the
243*16467b97STreehugger Robot // need to track and free the memory allocated to it, so for now, we just
244*16467b97STreehugger Robot // want something in the tree that isn't a NULL pointer.
245*16467b97STreehugger Robot //
246*16467b97STreehugger Robot return (pANTLR3_BASE_TREE)adaptor->createTypeText(adaptor, ANTLR3_TOKEN_INVALID, (pANTLR3_UINT8)"Tree Error Node");
247*16467b97STreehugger Robot
248*16467b97STreehugger Robot }
249*16467b97STreehugger Robot
250*16467b97STreehugger Robot /** Duplicate the supplied node.
251*16467b97STreehugger Robot */
252*16467b97STreehugger Robot static pANTLR3_BASE_TREE
dupNode(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_BASE_TREE treeNode)253*16467b97STreehugger Robot dupNode (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE treeNode)
254*16467b97STreehugger Robot {
255*16467b97STreehugger Robot return treeNode == NULL ? NULL : (pANTLR3_BASE_TREE)treeNode->dupNode(treeNode);
256*16467b97STreehugger Robot }
257*16467b97STreehugger Robot
258*16467b97STreehugger Robot static pANTLR3_BASE_TREE
create(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_COMMON_TOKEN payload)259*16467b97STreehugger Robot create (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_COMMON_TOKEN payload)
260*16467b97STreehugger Robot {
261*16467b97STreehugger Robot pANTLR3_BASE_TREE ct;
262*16467b97STreehugger Robot
263*16467b97STreehugger Robot /* Create a new common tree as this is what this adaptor deals with
264*16467b97STreehugger Robot */
265*16467b97STreehugger Robot ct = ((pANTLR3_COMMON_TREE_ADAPTOR)(adaptor->super))->arboretum->newFromToken(((pANTLR3_COMMON_TREE_ADAPTOR)(adaptor->super))->arboretum, payload);
266*16467b97STreehugger Robot
267*16467b97STreehugger Robot /* But all adaptors return the pointer to the base interface.
268*16467b97STreehugger Robot */
269*16467b97STreehugger Robot return ct;
270*16467b97STreehugger Robot }
271*16467b97STreehugger Robot static pANTLR3_BASE_TREE
dbgCreate(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_COMMON_TOKEN payload)272*16467b97STreehugger Robot dbgCreate (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_COMMON_TOKEN payload)
273*16467b97STreehugger Robot {
274*16467b97STreehugger Robot pANTLR3_BASE_TREE ct;
275*16467b97STreehugger Robot
276*16467b97STreehugger Robot ct = create(adaptor, payload);
277*16467b97STreehugger Robot adaptor->debugger->createNode(adaptor->debugger, ct);
278*16467b97STreehugger Robot
279*16467b97STreehugger Robot return ct;
280*16467b97STreehugger Robot }
281*16467b97STreehugger Robot
282*16467b97STreehugger Robot /** Tell me how to create a token for use with imaginary token nodes.
283*16467b97STreehugger Robot * For example, there is probably no input symbol associated with imaginary
284*16467b97STreehugger Robot * token DECL, but you need to create it as a payload or whatever for
285*16467b97STreehugger Robot * the DECL node as in ^(DECL type ID).
286*16467b97STreehugger Robot *
287*16467b97STreehugger Robot * If you care what the token payload objects' type is, you should
288*16467b97STreehugger Robot * override this method and any other createToken variant.
289*16467b97STreehugger Robot */
290*16467b97STreehugger Robot static pANTLR3_COMMON_TOKEN
createToken(pANTLR3_BASE_TREE_ADAPTOR adaptor,ANTLR3_UINT32 tokenType,pANTLR3_UINT8 text)291*16467b97STreehugger Robot createToken (pANTLR3_BASE_TREE_ADAPTOR adaptor, ANTLR3_UINT32 tokenType, pANTLR3_UINT8 text)
292*16467b97STreehugger Robot {
293*16467b97STreehugger Robot pANTLR3_COMMON_TOKEN newToken;
294*16467b97STreehugger Robot
295*16467b97STreehugger Robot newToken = adaptor->tokenFactory->newToken(adaptor->tokenFactory);
296*16467b97STreehugger Robot
297*16467b97STreehugger Robot if (newToken != NULL)
298*16467b97STreehugger Robot {
299*16467b97STreehugger Robot newToken->textState = ANTLR3_TEXT_CHARP;
300*16467b97STreehugger Robot newToken->tokText.chars = (pANTLR3_UCHAR)text;
301*16467b97STreehugger Robot newToken->setType(newToken, tokenType);
302*16467b97STreehugger Robot newToken->input = adaptor->tokenFactory->input;
303*16467b97STreehugger Robot newToken->strFactory = adaptor->strFactory;
304*16467b97STreehugger Robot }
305*16467b97STreehugger Robot return newToken;
306*16467b97STreehugger Robot }
307*16467b97STreehugger Robot
308*16467b97STreehugger Robot /** Tell me how to create a token for use with imaginary token nodes.
309*16467b97STreehugger Robot * For example, there is probably no input symbol associated with imaginary
310*16467b97STreehugger Robot * token DECL, but you need to create it as a payload or whatever for
311*16467b97STreehugger Robot * the DECL node as in ^(DECL type ID).
312*16467b97STreehugger Robot *
313*16467b97STreehugger Robot * This is a variant of createToken where the new token is derived from
314*16467b97STreehugger Robot * an actual real input token. Typically this is for converting '{'
315*16467b97STreehugger Robot * tokens to BLOCK etc... You'll see
316*16467b97STreehugger Robot *
317*16467b97STreehugger Robot * r : lc='{' ID+ '}' -> ^(BLOCK[$lc] ID+) ;
318*16467b97STreehugger Robot *
319*16467b97STreehugger Robot * If you care what the token payload objects' type is, you should
320*16467b97STreehugger Robot * override this method and any other createToken variant.
321*16467b97STreehugger Robot *
322*16467b97STreehugger Robot * NB: this being C it is not so easy to extend the types of creaeteToken.
323*16467b97STreehugger Robot * We will have to see if anyone needs to do this and add any variants to
324*16467b97STreehugger Robot * this interface.
325*16467b97STreehugger Robot */
326*16467b97STreehugger Robot static pANTLR3_COMMON_TOKEN
createTokenFromToken(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_COMMON_TOKEN fromToken)327*16467b97STreehugger Robot createTokenFromToken (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_COMMON_TOKEN fromToken)
328*16467b97STreehugger Robot {
329*16467b97STreehugger Robot pANTLR3_COMMON_TOKEN newToken;
330*16467b97STreehugger Robot
331*16467b97STreehugger Robot newToken = adaptor->tokenFactory->newToken(adaptor->tokenFactory);
332*16467b97STreehugger Robot
333*16467b97STreehugger Robot if (newToken != NULL)
334*16467b97STreehugger Robot {
335*16467b97STreehugger Robot // Create the text using our own string factory to avoid complicating
336*16467b97STreehugger Robot // commontoken.
337*16467b97STreehugger Robot //
338*16467b97STreehugger Robot pANTLR3_STRING text;
339*16467b97STreehugger Robot
340*16467b97STreehugger Robot newToken->toString = fromToken->toString;
341*16467b97STreehugger Robot
342*16467b97STreehugger Robot if (fromToken->textState == ANTLR3_TEXT_CHARP)
343*16467b97STreehugger Robot {
344*16467b97STreehugger Robot newToken->textState = ANTLR3_TEXT_CHARP;
345*16467b97STreehugger Robot newToken->tokText.chars = fromToken->tokText.chars;
346*16467b97STreehugger Robot }
347*16467b97STreehugger Robot else
348*16467b97STreehugger Robot {
349*16467b97STreehugger Robot text = fromToken->getText(fromToken);
350*16467b97STreehugger Robot newToken->textState = ANTLR3_TEXT_STRING;
351*16467b97STreehugger Robot newToken->tokText.text = adaptor->strFactory->newPtr(adaptor->strFactory, text->chars, text->len);
352*16467b97STreehugger Robot }
353*16467b97STreehugger Robot
354*16467b97STreehugger Robot newToken->setLine (newToken, fromToken->getLine(fromToken));
355*16467b97STreehugger Robot newToken->setTokenIndex (newToken, fromToken->getTokenIndex(fromToken));
356*16467b97STreehugger Robot newToken->setCharPositionInLine (newToken, fromToken->getCharPositionInLine(fromToken));
357*16467b97STreehugger Robot newToken->setChannel (newToken, fromToken->getChannel(fromToken));
358*16467b97STreehugger Robot newToken->setType (newToken, fromToken->getType(fromToken));
359*16467b97STreehugger Robot }
360*16467b97STreehugger Robot
361*16467b97STreehugger Robot return newToken;
362*16467b97STreehugger Robot }
363*16467b97STreehugger Robot
364*16467b97STreehugger Robot /* Specific methods for a TreeAdaptor */
365*16467b97STreehugger Robot
366*16467b97STreehugger Robot /** Track start/stop token for subtree root created for a rule.
367*16467b97STreehugger Robot * Only works with CommonTree nodes. For rules that match nothing,
368*16467b97STreehugger Robot * seems like this will yield start=i and stop=i-1 in a nil node.
369*16467b97STreehugger Robot * Might be useful info so I'll not force to be i..i.
370*16467b97STreehugger Robot */
371*16467b97STreehugger Robot static void
setTokenBoundaries(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_BASE_TREE t,pANTLR3_COMMON_TOKEN startToken,pANTLR3_COMMON_TOKEN stopToken)372*16467b97STreehugger Robot setTokenBoundaries (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t, pANTLR3_COMMON_TOKEN startToken, pANTLR3_COMMON_TOKEN stopToken)
373*16467b97STreehugger Robot {
374*16467b97STreehugger Robot ANTLR3_MARKER start;
375*16467b97STreehugger Robot ANTLR3_MARKER stop;
376*16467b97STreehugger Robot
377*16467b97STreehugger Robot pANTLR3_COMMON_TREE ct;
378*16467b97STreehugger Robot
379*16467b97STreehugger Robot if (t == NULL)
380*16467b97STreehugger Robot {
381*16467b97STreehugger Robot return;
382*16467b97STreehugger Robot }
383*16467b97STreehugger Robot
384*16467b97STreehugger Robot if ( startToken != NULL)
385*16467b97STreehugger Robot {
386*16467b97STreehugger Robot start = startToken->getTokenIndex(startToken);
387*16467b97STreehugger Robot }
388*16467b97STreehugger Robot else
389*16467b97STreehugger Robot {
390*16467b97STreehugger Robot start = 0;
391*16467b97STreehugger Robot }
392*16467b97STreehugger Robot
393*16467b97STreehugger Robot if ( stopToken != NULL)
394*16467b97STreehugger Robot {
395*16467b97STreehugger Robot stop = stopToken->getTokenIndex(stopToken);
396*16467b97STreehugger Robot }
397*16467b97STreehugger Robot else
398*16467b97STreehugger Robot {
399*16467b97STreehugger Robot stop = 0;
400*16467b97STreehugger Robot }
401*16467b97STreehugger Robot
402*16467b97STreehugger Robot ct = (pANTLR3_COMMON_TREE)(t->super);
403*16467b97STreehugger Robot
404*16467b97STreehugger Robot ct->startIndex = start;
405*16467b97STreehugger Robot ct->stopIndex = stop;
406*16467b97STreehugger Robot
407*16467b97STreehugger Robot }
408*16467b97STreehugger Robot static void
dbgSetTokenBoundaries(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_BASE_TREE t,pANTLR3_COMMON_TOKEN startToken,pANTLR3_COMMON_TOKEN stopToken)409*16467b97STreehugger Robot dbgSetTokenBoundaries (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t, pANTLR3_COMMON_TOKEN startToken, pANTLR3_COMMON_TOKEN stopToken)
410*16467b97STreehugger Robot {
411*16467b97STreehugger Robot setTokenBoundaries(adaptor, t, startToken, stopToken);
412*16467b97STreehugger Robot
413*16467b97STreehugger Robot if (t != NULL && startToken != NULL && stopToken != NULL)
414*16467b97STreehugger Robot {
415*16467b97STreehugger Robot adaptor->debugger->setTokenBoundaries(adaptor->debugger, t, startToken->getTokenIndex(startToken), stopToken->getTokenIndex(stopToken));
416*16467b97STreehugger Robot }
417*16467b97STreehugger Robot }
418*16467b97STreehugger Robot
419*16467b97STreehugger Robot static ANTLR3_MARKER
getTokenStartIndex(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_BASE_TREE t)420*16467b97STreehugger Robot getTokenStartIndex (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t)
421*16467b97STreehugger Robot {
422*16467b97STreehugger Robot return ((pANTLR3_COMMON_TREE)(t->super))->startIndex;
423*16467b97STreehugger Robot }
424*16467b97STreehugger Robot
425*16467b97STreehugger Robot static ANTLR3_MARKER
getTokenStopIndex(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_BASE_TREE t)426*16467b97STreehugger Robot getTokenStopIndex (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t)
427*16467b97STreehugger Robot {
428*16467b97STreehugger Robot return ((pANTLR3_COMMON_TREE)(t->super))->stopIndex;
429*16467b97STreehugger Robot }
430*16467b97STreehugger Robot
431*16467b97STreehugger Robot static pANTLR3_STRING
getText(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_BASE_TREE t)432*16467b97STreehugger Robot getText (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t)
433*16467b97STreehugger Robot {
434*16467b97STreehugger Robot return t->getText(t);
435*16467b97STreehugger Robot }
436*16467b97STreehugger Robot
437*16467b97STreehugger Robot static ANTLR3_UINT32
getType(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_BASE_TREE t)438*16467b97STreehugger Robot getType (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t)
439*16467b97STreehugger Robot {
440*16467b97STreehugger Robot return t->getType(t);
441*16467b97STreehugger Robot }
442*16467b97STreehugger Robot
443*16467b97STreehugger Robot static void
replaceChildren(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_BASE_TREE parent,ANTLR3_INT32 startChildIndex,ANTLR3_INT32 stopChildIndex,pANTLR3_BASE_TREE t)444*16467b97STreehugger Robot replaceChildren
445*16467b97STreehugger Robot (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE parent, ANTLR3_INT32 startChildIndex, ANTLR3_INT32 stopChildIndex, pANTLR3_BASE_TREE t)
446*16467b97STreehugger Robot {
447*16467b97STreehugger Robot if (parent != NULL)
448*16467b97STreehugger Robot {
449*16467b97STreehugger Robot parent->replaceChildren(parent, startChildIndex, stopChildIndex, t);
450*16467b97STreehugger Robot }
451*16467b97STreehugger Robot }
452*16467b97STreehugger Robot
453*16467b97STreehugger Robot static pANTLR3_BASE_TREE
getChild(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_BASE_TREE t,ANTLR3_UINT32 i)454*16467b97STreehugger Robot getChild (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t, ANTLR3_UINT32 i)
455*16467b97STreehugger Robot {
456*16467b97STreehugger Robot return (pANTLR3_BASE_TREE)t->getChild(t, i);
457*16467b97STreehugger Robot }
458*16467b97STreehugger Robot static void
setChild(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_BASE_TREE t,ANTLR3_UINT32 i,pANTLR3_BASE_TREE child)459*16467b97STreehugger Robot setChild (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t, ANTLR3_UINT32 i, pANTLR3_BASE_TREE child)
460*16467b97STreehugger Robot {
461*16467b97STreehugger Robot t->setChild(t, i, child);
462*16467b97STreehugger Robot }
463*16467b97STreehugger Robot
464*16467b97STreehugger Robot static void
deleteChild(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_BASE_TREE t,ANTLR3_UINT32 i)465*16467b97STreehugger Robot deleteChild (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t, ANTLR3_UINT32 i)
466*16467b97STreehugger Robot {
467*16467b97STreehugger Robot t->deleteChild(t, i);
468*16467b97STreehugger Robot }
469*16467b97STreehugger Robot
470*16467b97STreehugger Robot static ANTLR3_UINT32
getChildCount(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_BASE_TREE t)471*16467b97STreehugger Robot getChildCount (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t)
472*16467b97STreehugger Robot {
473*16467b97STreehugger Robot return t->getChildCount(t);
474*16467b97STreehugger Robot }
475*16467b97STreehugger Robot
476*16467b97STreehugger Robot static void
setChildIndex(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_BASE_TREE t,ANTLR3_INT32 i)477*16467b97STreehugger Robot setChildIndex (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t, ANTLR3_INT32 i)
478*16467b97STreehugger Robot {
479*16467b97STreehugger Robot t->setChildIndex(t, i);
480*16467b97STreehugger Robot }
481*16467b97STreehugger Robot
482*16467b97STreehugger Robot static ANTLR3_INT32
getChildIndex(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_BASE_TREE t)483*16467b97STreehugger Robot getChildIndex (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE t)
484*16467b97STreehugger Robot {
485*16467b97STreehugger Robot return t->getChildIndex(t);
486*16467b97STreehugger Robot }
487*16467b97STreehugger Robot static void
setParent(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_BASE_TREE child,pANTLR3_BASE_TREE parent)488*16467b97STreehugger Robot setParent (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE child, pANTLR3_BASE_TREE parent)
489*16467b97STreehugger Robot {
490*16467b97STreehugger Robot child->setParent(child, parent);
491*16467b97STreehugger Robot }
492*16467b97STreehugger Robot static pANTLR3_BASE_TREE
getParent(pANTLR3_BASE_TREE_ADAPTOR adaptor,pANTLR3_BASE_TREE child)493*16467b97STreehugger Robot getParent (pANTLR3_BASE_TREE_ADAPTOR adaptor, pANTLR3_BASE_TREE child)
494*16467b97STreehugger Robot {
495*16467b97STreehugger Robot return child->getParent(child);
496*16467b97STreehugger Robot }
497