1 /**************************************************************
2  *
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  *   http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  *
20  *************************************************************/
21 
22 #include <precomp.h>
23 #include "pe_class.hxx"
24 
25 
26 // NOT FULLY DECLARED SERVICES
27 #include <cosv/tpl/tpltools.hxx>
28 #include <ary/cpp/c_gate.hxx>
29 #include <ary/cpp/c_class.hxx>
30 #include <ary/cpp/c_namesp.hxx>
31 #include <ary/cpp/cp_ce.hxx>
32 #include <all_toks.hxx>
33 #include "pe_base.hxx"
34 #include "pe_defs.hxx"
35 #include "pe_enum.hxx"
36 #include "pe_tydef.hxx"
37 #include "pe_vafu.hxx"
38 #include "pe_ignor.hxx"
39 
40 
41 namespace cpp {
42 
43 // using ary::Cid;
44 
PE_Class(Cpp_PE * i_pParent)45 PE_Class::PE_Class(Cpp_PE * i_pParent )
46 	:   Cpp_PE(i_pParent),
47 		pStati( new PeStatusArray<PE_Class> ),
48 		// pSpBase,
49 		// pSpTypedef,
50 		// pSpVarFunc,
51 		// pSpIgnore,
52 		// pSpuBase,
53 		// pSpuTypedef,
54 		// pSpuVarFunc,
55 		// pSpuUsing,
56         // pSpuIgnoreFailure,
57 		// sLocalName,
58 		eClassKey(ary::cpp::CK_class),
59 		pCurObject(0),
60         // aBases,
61 		eResult_KindOf(is_declaration)
62 {
63 	Setup_StatusFunctions();
64 
65 	pSpBase     = new SP_Base(*this);
66 	pSpTypedef  = new SP_Typedef(*this);
67 	pSpVarFunc  = new SP_VarFunc(*this);
68 	pSpIgnore   = new SP_Ignore(*this);
69 	pSpDefs     = new SP_Defines(*this);
70 
71 	pSpuBase	= new SPU_Base(*pSpBase, 0, &PE_Class::SpReturn_Base);
72 	pSpuTypedef	= new SPU_Typedef(*pSpTypedef, 0, 0);
73 	pSpuVarFunc = new SPU_VarFunc(*pSpVarFunc, 0, 0);
74 
75 	pSpuTemplate= new SPU_Ignore(*pSpIgnore, 0, 0);
76 	pSpuUsing   = new SPU_Ignore(*pSpIgnore, 0, 0);
77     pSpuIgnoreFailure
78                 = new SPU_Ignore(*pSpIgnore, 0, 0);
79 	pSpuDefs	= new SPU_Defines(*pSpDefs, 0, 0);
80 }
81 
82 
~PE_Class()83 PE_Class::~PE_Class()
84 {
85 }
86 
87 void
Call_Handler(const cpp::Token & i_rTok)88 PE_Class::Call_Handler( const cpp::Token &	i_rTok )
89 {
90 	pStati->Cur().Call_Handler(i_rTok.TypeId(), i_rTok.Text());
91 }
92 
93 Cpp_PE *
Handle_ChildFailure()94 PE_Class::Handle_ChildFailure()
95 {
96     SetCurSPU(pSpuIgnoreFailure.Ptr());
97     return &pSpuIgnoreFailure->Child();
98 }
99 
100 void
Setup_StatusFunctions()101 PE_Class::Setup_StatusFunctions()
102 {
103 	typedef CallFunction<PE_Class>::F_Tok	F_Tok;
104 
105 	static F_Tok stateF_start[] =			{ &PE_Class::On_start_class,
106 											  &PE_Class::On_start_struct,
107 											  &PE_Class::On_start_union };
108 	static INT16 stateT_start[] =       	{ Tid_class,
109 											  Tid_struct,
110 											  Tid_union };
111 
112 	static F_Tok stateF_expectName[] = 		{ &PE_Class::On_expectName_Identifier,
113 											  &PE_Class::On_expectName_SwBracket_Left,
114 											  &PE_Class::On_expectName_Colon
115 											};
116 	static INT16 stateT_expectName[] = 		{ Tid_Identifier,
117 											  Tid_SwBracket_Left,
118 											  Tid_Colon
119 											};
120 
121 	static F_Tok stateF_gotName[] =			{ &PE_Class::On_gotName_SwBracket_Left,
122 											  &PE_Class::On_gotName_Semicolon,
123 											  &PE_Class::On_gotName_Colon };
124 	static INT16 stateT_gotName[] =       	{ Tid_SwBracket_Left,
125 											  Tid_Semicolon,
126 											  Tid_Colon };
127 
128 	static F_Tok stateF_bodyStd[] =			{ &PE_Class::On_bodyStd_VarFunc,
129 											  &PE_Class::On_bodyStd_VarFunc,
130 											  &PE_Class::On_bodyStd_ClassKey,
131 											  &PE_Class::On_bodyStd_ClassKey,
132 											  &PE_Class::On_bodyStd_ClassKey,
133 
134 											  &PE_Class::On_bodyStd_enum,
135 											  &PE_Class::On_bodyStd_typedef,
136 											  &PE_Class::On_bodyStd_public,
137 											  &PE_Class::On_bodyStd_protected,
138 											  &PE_Class::On_bodyStd_private,
139 
140 											  &PE_Class::On_bodyStd_template,
141 											  &PE_Class::On_bodyStd_VarFunc,
142 											  &PE_Class::On_bodyStd_friend,
143 											  &PE_Class::On_bodyStd_VarFunc,
144 											  &PE_Class::On_bodyStd_VarFunc,
145 
146 											  &PE_Class::On_bodyStd_VarFunc,
147 											  &PE_Class::On_bodyStd_VarFunc,
148 											  &PE_Class::On_bodyStd_VarFunc,
149 											  &PE_Class::On_bodyStd_VarFunc,
150 											  &PE_Class::On_bodyStd_VarFunc,
151 
152 											  &PE_Class::On_bodyStd_using,
153 											  &PE_Class::On_bodyStd_SwBracket_Right,
154 											  &PE_Class::On_bodyStd_VarFunc,
155                                               &PE_Class::On_bodyStd_DefineName,
156                                               &PE_Class::On_bodyStd_MacroName,
157 
158 											  &PE_Class::On_bodyStd_VarFunc,
159 											  &PE_Class::On_bodyStd_VarFunc,
160                                               &PE_Class::On_bodyStd_VarFunc, };
161 
162 	static INT16 stateT_bodyStd[] =       	{ Tid_Identifier,
163 											  Tid_operator,
164 											  Tid_class,
165 											  Tid_struct,
166 											  Tid_union,
167 
168 											  Tid_enum,
169 											  Tid_typedef,
170 											  Tid_public,
171 											  Tid_protected,
172 											  Tid_private,
173 
174 											  Tid_template,
175 											  Tid_virtual,
176 											  Tid_friend,
177 											  Tid_Tilde,
178 											  Tid_const,
179 
180 											  Tid_volatile,
181 											  Tid_static,
182 											  Tid_mutable,
183 					  						  Tid_inline,
184 											  Tid_explicit,
185 
186 											  Tid_using,
187 											  Tid_SwBracket_Right,
188 											  Tid_DoubleColon,
189                                               Tid_typename,
190                                               Tid_DefineName,
191 
192                                               Tid_MacroName,
193 											  Tid_BuiltInType,
194 											  Tid_TypeSpecializer };
195 
196 											  static F_Tok stateF_inProtection[] = 	{ &PE_Class::On_inProtection_Colon };
197 	static INT16 stateT_inProtection[] =   	{ Tid_Colon };
198 
199 	static F_Tok stateF_afterDecl[] = 	    { &PE_Class::On_afterDecl_Semicolon };
200 	static INT16 stateT_afterDecl[] =   	{ Tid_Semicolon };
201 
202 	SEMPARSE_CREATE_STATUS(PE_Class, start, Hdl_SyntaxError);
203 	SEMPARSE_CREATE_STATUS(PE_Class, expectName, Hdl_SyntaxError);
204 	SEMPARSE_CREATE_STATUS(PE_Class, gotName, On_gotName_Return2Type);
205 	SEMPARSE_CREATE_STATUS(PE_Class, bodyStd, Hdl_SyntaxError);
206 	SEMPARSE_CREATE_STATUS(PE_Class, inProtection, Hdl_SyntaxError);
207 	SEMPARSE_CREATE_STATUS(PE_Class, afterDecl, On_afterDecl_Return2Type);
208 
209 #if 0
210 	static F_Tok stateF_inFriend[] =	 	{ On_inFriend_class,
211 											  On_inFriend_struct,
212 											  On_inFriend_union };
213 											  // Default: On_inFriend_Function
214 	static INT16 stateT_inFriend[] =     	{ Tid_class,
215 											  Tid_struct,
216 											  Tid_union };
217 #endif // 0
218 }
219 
220 void
InitData()221 PE_Class::InitData()
222 {
223 	pStati->SetCur(start);
224 	sLocalName.clear();
225 	eClassKey = ary::cpp::CK_class;
226 	pCurObject = 0;
227     csv::erase_container(aBases);
228     eResult_KindOf = is_declaration;
229 }
230 
231 void
TransferData()232 PE_Class::TransferData()
233 {
234 	pStati->SetCur(size_of_states);
235 }
236 
237 void
Hdl_SyntaxError(const char * i_sText)238 PE_Class::Hdl_SyntaxError( const char * i_sText)
239 {
240     if ( *i_sText == ';' )
241     {
242      	Cerr() << Env().CurFileName() << ", line "
243                   << Env().LineCount()
244                   << ": Sourcecode warning: ';' as a toplevel declaration is deprecated."
245                   << Endl();
246     	SetTokenResult(done,stay);
247         return;
248     }
249 
250 	StdHandlingOfSyntaxError(i_sText);
251 }
252 
253 void
Init_CurObject()254 PE_Class::Init_CurObject()
255 {
256     // KORR_FUTURE
257     //   This will have to be done before parsing base classes, because of
258     //   possible inline documentation for base classes.
259 	pCurObject = & Env().AryGate().Ces().Store_Class( Env().Context(), sLocalName, eClassKey );
260 
261   	for ( PE_Base::BaseList::const_iterator it = aBases.begin();
262 		  it !=  aBases.end();
263 		  ++it )
264 	{
265 		pCurObject->Add_BaseClass( *it );
266 	}  // end for
267 
268     Dyn< StringVector >
269             pTplParams( Env().Get_CurTemplateParameters() );
270     if ( pTplParams )
271     {
272       	for ( StringVector::const_iterator it = pTplParams->begin();
273 	    	  it !=  pTplParams->end();
274 		      ++it )
275     	{
276 	    	pCurObject->Add_TemplateParameterType( *it, ary::cpp::Type_id(0) );
277     	}  // end for
278     }
279 }
280 
281 void
SpReturn_Base()282 PE_Class::SpReturn_Base()
283 {
284 	aBases = pSpuBase->Child().Result_BaseIds();
285 	pStati->SetCur(gotName);
286 }
287 
288 void
On_start_class(const char *)289 PE_Class::On_start_class( const char * )
290 {
291 	SetTokenResult(done, stay);
292 	pStati->SetCur(expectName);
293 	eClassKey = ary::cpp::CK_class;
294 }
295 
296 void
On_start_struct(const char *)297 PE_Class::On_start_struct( const char * )
298 {
299 	SetTokenResult(done, stay);
300 	pStati->SetCur(expectName);
301 	eClassKey = ary::cpp::CK_struct;
302 }
303 
304 void
On_start_union(const char *)305 PE_Class::On_start_union( const char * )
306 {
307 	SetTokenResult(done, stay);
308 	pStati->SetCur(expectName);
309 	eClassKey = ary::cpp::CK_union;
310 }
311 
312 void
On_expectName_Identifier(const char * i_sText)313 PE_Class::On_expectName_Identifier( const char * i_sText )
314 {
315 	SetTokenResult(done, stay);
316 	pStati->SetCur(gotName);
317     sLocalName = i_sText;
318 }
319 
320 void
On_expectName_SwBracket_Left(const char *)321 PE_Class::On_expectName_SwBracket_Left( const char * )
322 {
323 	SetTokenResult(done, stay);
324 	pStati->SetCur(bodyStd);
325 
326     sLocalName = "";
327 	Init_CurObject();
328     sLocalName = pCurObject->LocalName();
329 
330     Env().OpenClass(*pCurObject);
331 }
332 
333 void
On_expectName_Colon(const char *)334 PE_Class::On_expectName_Colon( const char * )
335 {
336 	pStati->SetCur(gotName);
337     sLocalName = "";
338 
339 	pSpuBase->Push(done);
340 }
341 
342 void
On_gotName_SwBracket_Left(const char *)343 PE_Class::On_gotName_SwBracket_Left( const char * )
344 {
345 	SetTokenResult(done, stay);
346 	pStati->SetCur(bodyStd);
347 
348 	Init_CurObject();
349     if ( sLocalName.empty() )
350         sLocalName = pCurObject->LocalName();
351 
352     Env().OpenClass(*pCurObject);
353 }
354 
355 void
On_gotName_Semicolon(const char *)356 PE_Class::On_gotName_Semicolon( const char * )
357 {
358 	SetTokenResult(not_done, pop_success);
359 
360 	eResult_KindOf = is_predeclaration;
361 }
362 
363 void
On_gotName_Colon(const char *)364 PE_Class::On_gotName_Colon( const char * )
365 {
366 	pSpuBase->Push(done);
367 }
368 
369 void
On_gotName_Return2Type(const char *)370 PE_Class::On_gotName_Return2Type( const char * )
371 {
372 	SetTokenResult(not_done, pop_success);
373 
374 	eResult_KindOf = is_qualified_typename;
375 }
376 
377 void
On_bodyStd_VarFunc(const char *)378 PE_Class::On_bodyStd_VarFunc( const char * )
379 {
380     pSpuVarFunc->Push(not_done);
381 }
382 
383 void
On_bodyStd_ClassKey(const char *)384 PE_Class::On_bodyStd_ClassKey( const char * )
385 {
386 	pSpuVarFunc->Push(not_done);		// This is correct,
387                                         //   classes are parsed via PE_Type.
388 }
389 
390 void
On_bodyStd_enum(const char *)391 PE_Class::On_bodyStd_enum( const char * )
392 {
393 	pSpuVarFunc->Push(not_done);		// This is correct,
394                                         //   enums are parsed via PE_Type.
395 }
396 
397 void
On_bodyStd_typedef(const char *)398 PE_Class::On_bodyStd_typedef( const char * )
399 {
400     pSpuTypedef->Push(not_done);
401 }
402 
403 void
On_bodyStd_public(const char *)404 PE_Class::On_bodyStd_public( const char * )
405 {
406     SetTokenResult(done, stay);
407     pStati->SetCur(inProtection);
408 
409     Env().SetCurProtection(ary::cpp::PROTECT_public);
410 }
411 
412 void
On_bodyStd_protected(const char *)413 PE_Class::On_bodyStd_protected( const char * )
414 {
415     SetTokenResult(done, stay);
416     pStati->SetCur(inProtection);
417 
418     Env().SetCurProtection(ary::cpp::PROTECT_protected);
419 }
420 
421 void
On_bodyStd_private(const char *)422 PE_Class::On_bodyStd_private( const char * )
423 {
424     SetTokenResult(done, stay);
425     pStati->SetCur(inProtection);
426 
427     Env().SetCurProtection(ary::cpp::PROTECT_private);
428 }
429 
430 void
On_bodyStd_template(const char *)431 PE_Class::On_bodyStd_template( const char * )
432 {
433     pSpuTemplate->Push(done);
434 }
435 
436 void
On_bodyStd_friend(const char *)437 PE_Class::On_bodyStd_friend( const char * )
438 {
439     // KORR_FUTURE
440     pSpuUsing->Push(done);
441 }
442 
443 void
On_bodyStd_using(const char *)444 PE_Class::On_bodyStd_using( const char * )
445 {
446     pSpuUsing->Push(done);
447 }
448 
449 void
On_bodyStd_SwBracket_Right(const char *)450 PE_Class::On_bodyStd_SwBracket_Right( const char * )
451 {
452     SetTokenResult(done, stay);
453     pStati->SetCur(afterDecl);
454 
455     Env().CloseClass();
456 }
457 
458 void
On_bodyStd_DefineName(const char *)459 PE_Class::On_bodyStd_DefineName(const char * )
460 {
461 	pSpuDefs->Push(not_done);
462 }
463 
464 void
On_bodyStd_MacroName(const char *)465 PE_Class::On_bodyStd_MacroName(const char * )
466 {
467 	pSpuDefs->Push(not_done);
468 }
469 
470 
471 void
On_inProtection_Colon(const char *)472 PE_Class::On_inProtection_Colon( const char * )
473 {
474     SetTokenResult(done, stay);
475     pStati->SetCur(bodyStd);
476 }
477 
478 void
On_afterDecl_Semicolon(const char *)479 PE_Class::On_afterDecl_Semicolon( const char * )
480 {
481 	SetTokenResult(not_done, pop_success);
482 	eResult_KindOf = is_declaration;
483 }
484 
485 void
On_afterDecl_Return2Type(const char *)486 PE_Class::On_afterDecl_Return2Type( const char * )
487 {
488 	SetTokenResult(not_done, pop_success);
489 	eResult_KindOf = is_implicit_declaration;
490 }
491 
492 
493 }   // namespace cpp
494 
495 
496 
497 
498