blob: edd33c2395797aff3503b2e9414d712a55477d0d [file] [log] [blame]
/**************************************************************
*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you under the Apache License, Version 2.0 (the
* "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing,
* software distributed under the License is distributed on an
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
* KIND, either express or implied. See the License for the
* specific language governing permissions and limitations
* under the License.
*
*************************************************************/
#include <precomp.h>
#include "pe_vafu.hxx"
// NOT FULLY DEFINED SERVICES
#include <cosv/tpl/tpltools.hxx>
#include <ary/cpp/c_gate.hxx>
#include <ary/cpp/c_class.hxx>
#include <ary/cpp/c_vari.hxx>
#include <ary/cpp/c_vfflag.hxx>
#include <ary/cpp/cp_ce.hxx>
#include <ary/cpp/inpcontx.hxx>
#include "pe_type.hxx"
#include "pe_vari.hxx"
#include "pe_funct.hxx"
#include "pe_ignor.hxx"
#include <x_parse.hxx>
namespace cpp {
//*********************** PE_VarFunc ***********************//
PE_VarFunc::PE_VarFunc( Cpp_PE * i_pParent )
: Cpp_PE(i_pParent),
pStati( new PeStatusArray<PE_VarFunc> ),
// pSpType,
// pSpuType,
// pSpVariable,
// pSpuVariable,
// pSpFunction,
// pSpuFunctionStd,
// pSpuFunctionCtor,
// pSpuFunctionDtor,
// pSpuFunctionCastOperator,
// pSpuFunctionNormalOperator
// pSpIgnore,
// pSpuIgnore,
nCounter_TemplateBrackets(0),
bInDestructor(false),
// aResultIds,
nResultFrontType(0),
eResultType(result_unknown),
bVirtual(false),
bStatic(false),
bExtern(false),
bExternC(false),
bMutable(false),
bInline(false),
bRegister(false),
bExplicit(false)
{
Setup_StatusFunctions();
pSpType = new SP_Type(*this);
pSpuType = new SPU_Type(*pSpType, 0, &PE_VarFunc::SpReturn_Type);
pSpVariable = new SP_Variable(*this);
pSpuVariable = new SPU_Variable(*pSpVariable, 0, &PE_VarFunc::SpReturn_Variable);
pSpFunction = new SP_Function(*this);
pSpuFunctionStd = new SPU_Function(*pSpFunction, &PE_VarFunc::SpInit_FunctionStd, &PE_VarFunc::SpReturn_FunctionStd);
pSpuFunctionCtor = new SPU_Function(*pSpFunction, &PE_VarFunc::SpInit_FunctionCtor, &PE_VarFunc::SpReturn_FunctionStd);
pSpuFunctionDtor = new SPU_Function(*pSpFunction, &PE_VarFunc::SpInit_FunctionDtor, &PE_VarFunc::SpReturn_FunctionStd);
pSpuFunctionCastOperator
= new SPU_Function(*pSpFunction, &PE_VarFunc::SpInit_FunctionCastOperator, &PE_VarFunc::SpReturn_FunctionStd);
pSpuFunctionNormalOperator
= new SPU_Function(*pSpFunction, &PE_VarFunc::SpInit_FunctionNormalOperator, &PE_VarFunc::SpReturn_FunctionStd);
pSpIgnore = new SP_Ignore(*this);
pSpuIgnore = new SPU_Ignore(*pSpIgnore, 0, &PE_VarFunc::SpReturn_Ignore);
}
PE_VarFunc::~PE_VarFunc()
{
}
void
PE_VarFunc::Call_Handler( const cpp::Token & i_rTok )
{
pStati->Cur().Call_Handler(i_rTok.TypeId(), i_rTok.Text());
}
void
PE_VarFunc::Setup_StatusFunctions()
{
typedef CallFunction<PE_VarFunc>::F_Tok F_Tok;
static F_Tok stateF_start[] = { &PE_VarFunc::On_start_Identifier,
&PE_VarFunc::On_start_operator,
&PE_VarFunc::On_start_TypeKey,
&PE_VarFunc::On_start_TypeKey,
&PE_VarFunc::On_start_TypeKey,
&PE_VarFunc::On_start_TypeKey,
&PE_VarFunc::On_start_virtual,
&PE_VarFunc::On_start_Tilde,
&PE_VarFunc::On_start_const,
&PE_VarFunc::On_start_volatile,
&PE_VarFunc::On_start_extern,
&PE_VarFunc::On_start_static,
&PE_VarFunc::On_start_mutable,
&PE_VarFunc::On_start_register,
&PE_VarFunc::On_start_inline,
&PE_VarFunc::On_start_explicit,
&PE_VarFunc::On_start_Bracket_Right,
&PE_VarFunc::On_start_Identifier,
&PE_VarFunc::On_start_typename,
&PE_VarFunc::On_start_Identifier,
&PE_VarFunc::On_start_Identifier };
static INT16 stateT_start[] = { Tid_Identifier,
Tid_operator,
Tid_class,
Tid_struct,
Tid_union,
Tid_enum,
Tid_virtual,
Tid_Tilde,
Tid_const,
Tid_volatile,
Tid_extern,
Tid_static,
Tid_mutable,
Tid_register,
Tid_inline,
Tid_explicit,
Tid_Bracket_Right,
Tid_DoubleColon,
Tid_typename,
Tid_BuiltInType,
Tid_TypeSpecializer };
static F_Tok stateF_expectCtor[] = { &PE_VarFunc::On_expectCtor_Bracket_Left };
static INT16 stateT_expectCtor[] = { Tid_Bracket_Left };
static F_Tok stateF_afterClassDecl[] = { &PE_VarFunc::On_afterClassDecl_Semicolon };
static INT16 stateT_afterClassDecl[] = { Tid_Semicolon };
static F_Tok stateF_expectName[] = { &PE_VarFunc::On_expectName_Identifier,
&PE_VarFunc::On_expectName_operator,
&PE_VarFunc::On_expectName_Bracket_Left };
static INT16 stateT_expectName[] = { Tid_Identifier,
Tid_operator,
Tid_Bracket_Left };
static F_Tok stateF_afterName[] = { &PE_VarFunc::On_afterName_ArrayBracket_Left,
&PE_VarFunc::On_afterName_Bracket_Left,
&PE_VarFunc::On_afterName_DoubleColon,
&PE_VarFunc::On_afterName_Semicolon,
&PE_VarFunc::On_afterName_Comma,
&PE_VarFunc::On_afterName_Assign,
&PE_VarFunc::On_afterName_Less };
static INT16 stateT_afterName[] = { Tid_ArrayBracket_Left,
Tid_Bracket_Left,
Tid_DoubleColon,
Tid_Semicolon,
Tid_Comma,
Tid_Assign,
Tid_Less };
static F_Tok stateF_afterName_inErraneousTemplate[] =
{ &PE_VarFunc::On_afterName_inErraneousTemplate_Less,
&PE_VarFunc::On_afterName_inErraneousTemplate_Greater };
static INT16 stateT_afterName_inErraneousTemplate[] =
{ Tid_Less,
Tid_Greater };
static F_Tok stateF_finished[] = { &PE_VarFunc::On_finished_Semicolon,
&PE_VarFunc::On_finished_Comma };
static INT16 stateT_finished[] = { Tid_Semicolon,
Tid_Comma };
static F_Tok stateF_finishedIncludingFunctionImplementation[] =
{ &PE_VarFunc::On_finishedIncludingFunctionImplementation_Default
};
static INT16 stateT_finishedIncludingFunctionImplementation[] =
{ Tid_BuiltInType // Just to have one entry, but it is default handled, too.
};
SEMPARSE_CREATE_STATUS(PE_VarFunc, start, Hdl_UnknownToken);
SEMPARSE_CREATE_STATUS(PE_VarFunc, expectCtor, Hdl_UnknownToken);
SEMPARSE_CREATE_STATUS(PE_VarFunc, afterClassDecl, Hdl_UnknownToken);
SEMPARSE_CREATE_STATUS(PE_VarFunc, expectName, Hdl_UnknownToken);
SEMPARSE_CREATE_STATUS(PE_VarFunc, afterName, Hdl_UnknownToken);
SEMPARSE_CREATE_STATUS(PE_VarFunc, afterName_inErraneousTemplate, On_afterName_inErraneousTemplate_Default);
SEMPARSE_CREATE_STATUS(PE_VarFunc, finished, On_finished_Default);
SEMPARSE_CREATE_STATUS(PE_VarFunc, finishedIncludingFunctionImplementation, On_finishedIncludingFunctionImplementation_Default);
}
void
PE_VarFunc::InitData()
{
pStati->SetCur(start);
csv::erase_container(aResultIds);
nCounter_TemplateBrackets = 0;
bInDestructor = false;
nResultFrontType = 0;
eResultType = result_unknown;
sName.clear();
bVirtual = ary::cpp::VIRTUAL_none;
bStatic = false;
bExtern = false;
bExternC = false;
bMutable = false;
bInline = false;
bRegister = false;
bExplicit = false;
}
void
PE_VarFunc::TransferData()
{
pStati->SetCur(size_of_states);
}
void
PE_VarFunc::Hdl_UnknownToken( const char *)
{
pSpuIgnore->Push(not_done);
}
void
PE_VarFunc::SpInit_FunctionStd()
{
if ( nResultFrontType.IsValid() AND sName.length() > 0 )
{
pSpuFunctionStd->Child().Init_Std(
sName,
nResultFrontType,
bVirtual,
CreateFunctionFlags() );
}
else
{
throw X_Parser( X_Parser::x_UnexpectedToken,
"",
Env().CurFileName(),
Env().LineCount() );
}
}
void
PE_VarFunc::SpInit_FunctionCtor()
{
ary::cpp::Class * pOwnerClass = Env().Context().CurClass();
csv_assert( pOwnerClass != 0 );
pSpuFunctionStd->Child().Init_Ctor( pOwnerClass->LocalName(),
CreateFunctionFlags() );
}
void
PE_VarFunc::SpInit_FunctionDtor()
{
pSpuFunctionStd->Child().Init_Dtor( sName,
bVirtual,
CreateFunctionFlags() );
}
void
PE_VarFunc::SpInit_FunctionCastOperator()
{
pSpuFunctionStd->Child().Init_CastOperator( bVirtual,
CreateFunctionFlags() );
}
void
PE_VarFunc::SpInit_FunctionNormalOperator()
{
pSpuFunctionStd->Child().Init_NormalOperator( nResultFrontType,
bVirtual,
CreateFunctionFlags() );
}
void
PE_VarFunc::SpReturn_Type()
{
switch ( pSpuType->Child().Result_KindOf() )
{
case PE_Type::is_type:
pStati->SetCur(expectName);
nResultFrontType
= pSpuType->Child().Result_Type().Id();
break;
case PE_Type::is_constructor:
pStati->SetCur(expectCtor);
eResultType = result_function;
break;
case PE_Type::is_explicit_class_declaration:
case PE_Type::is_explicit_enum_declaration:
pStati->SetCur(afterClassDecl);
eResultType = result_ignore;
break;
case PE_Type::is_class_predeclaration:
pStati->SetCur(afterClassDecl);
eResultType = result_ignore;
break;
default:
;
}
}
void
PE_VarFunc::SpReturn_Variable()
{
typedef ary::cpp::VariableFlags VarFlags;
if ( NOT bExtern )
{
VarFlags aFlags( UINT16(
( bStatic AND Env().Context().CurClass() == 0 ? VarFlags::f_static_local : 0 )
| ( bStatic AND Env().Context().CurClass() != 0 ? VarFlags::f_static_member : 0 )
| ( bMutable ? VarFlags::f_mutable : 0 ) )
);
// ary::S_InitData aData( 0, Env().CurCeSpace().Id(), i_sName, 0 );
ary::cpp::Variable & rCurParsedVariable
= Env().AryGate().Ces().Store_Variable( Env().Context(),
sName,
nResultFrontType,
aFlags,
pSpuVariable->Child().Result_SizeExpression(),
pSpuVariable->Child().Result_InitExpression() );
Env().Event_Store_Variable(rCurParsedVariable);
aResultIds.push_back( rCurParsedVariable.CeId() );
eResultType = result_variable;
}
else if (bExtern)
{
eResultType = result_ignore;
}
pStati->SetCur(finished);
}
void
PE_VarFunc::SpReturn_FunctionStd()
{
if ( (NOT bExtern) OR bExternC )
{
aResultIds.push_back(pSpuFunctionStd->Child().Result_Id());
eResultType = result_function;
}
else
{
eResultType = result_ignore;
}
if ( NOT pSpuFunctionStd->Child().Result_WithImplementation() )
pStati->SetCur(finished);
else
pStati->SetCur(finishedIncludingFunctionImplementation);
}
void
PE_VarFunc::SpReturn_Ignore()
{
pStati->SetCur(finished);
}
void
PE_VarFunc::On_start_Identifier(const char *)
{
pSpuType->Push(not_done);
}
void
PE_VarFunc::On_start_operator(const char *)
{
pSpuFunctionCastOperator->Push(done);
}
void
PE_VarFunc::On_start_TypeKey(const char *)
{
pSpuType->Push(not_done);
}
void
PE_VarFunc::On_start_virtual(const char *)
{
SetTokenResult(done, stay);
bVirtual = true;
}
void
PE_VarFunc::On_start_Tilde(const char *)
{
SetTokenResult(done, stay);
pStati->SetCur(expectName);
bInDestructor = true;
}
void
PE_VarFunc::On_start_const(const char *)
{
pSpuType->Push(not_done);
}
void
PE_VarFunc::On_start_volatile(const char *)
{
pSpuType->Push(not_done);
}
void
PE_VarFunc::On_start_extern(const char *)
{
SetTokenResult(done, stay);
bExtern = true;
}
void
PE_VarFunc::On_start_static(const char *)
{
SetTokenResult(done, stay);
bStatic = true;
}
void
PE_VarFunc::On_start_mutable(const char *)
{
SetTokenResult(done, stay);
bMutable = true;
}
void
PE_VarFunc::On_start_register(const char *)
{
SetTokenResult(done, stay);
bRegister = true;
}
void
PE_VarFunc::On_start_inline(const char *)
{
SetTokenResult(done, stay);
bInline = true;
}
void
PE_VarFunc::On_start_explicit(const char *)
{
SetTokenResult(done, stay);
bExplicit = true;
}
void
PE_VarFunc::On_start_Bracket_Right(const char *)
{
SetTokenResult(not_done, pop_success);
}
void
PE_VarFunc::On_start_typename(const char *)
{
pSpuType->Push(not_done);
}
void
PE_VarFunc::On_expectCtor_Bracket_Left(const char *)
{
pSpuFunctionCtor->Push(not_done);
}
void
PE_VarFunc::On_afterClassDecl_Semicolon(const char *)
{
SetTokenResult(done, pop_success);
}
void
PE_VarFunc::On_expectName_Identifier(const char * i_sText)
{
SetTokenResult(done, stay);
pStati->SetCur(afterName);
sName = i_sText;
}
void
PE_VarFunc::On_expectName_operator(const char *)
{
pSpuFunctionNormalOperator->Push(done);
}
void
PE_VarFunc::On_expectName_Bracket_Left(const char *)
{
// Function pointer declaration
pSpuIgnore->Push(not_done);
// TODO
}
void
PE_VarFunc::On_afterName_ArrayBracket_Left(const char *)
{
pSpuVariable->Push(not_done);
}
void
PE_VarFunc::On_afterName_Bracket_Left(const char *)
{
if ( NOT bInDestructor)
pSpuFunctionStd->Push(not_done);
else
pSpuFunctionDtor->Push(not_done);
}
void
PE_VarFunc::On_afterName_DoubleColon(const char *)
{
pSpuIgnore->Push(done); // This seems to be only an implementation.
// This may have been a template.
// In that case, the declaration needs to be closed.
Env().Close_OpenTemplate();
}
void
PE_VarFunc::On_afterName_Semicolon(const char *)
{
pSpuVariable->Push(not_done);
}
void
PE_VarFunc::On_afterName_Comma(const char *)
{
pSpuVariable->Push(not_done);
}
void
PE_VarFunc::On_afterName_Assign(const char * )
{
pSpuVariable->Push(not_done);
}
void
PE_VarFunc::On_afterName_Less(const char * )
{
SetTokenResult(done, stay);
pStati->SetCur(afterName_inErraneousTemplate);
nCounter_TemplateBrackets = 1;
}
void
PE_VarFunc::On_afterName_inErraneousTemplate_Less(const char * )
{
SetTokenResult(done, stay);
nCounter_TemplateBrackets++;
}
void
PE_VarFunc::On_afterName_inErraneousTemplate_Greater(const char * )
{
SetTokenResult(done, stay);
nCounter_TemplateBrackets--;
if ( nCounter_TemplateBrackets == 0 )
pStati->SetCur(afterName);
}
void
PE_VarFunc::On_afterName_inErraneousTemplate_Default(const char * )
{
SetTokenResult(done, stay);
}
void
PE_VarFunc::On_finished_Semicolon(const char * ) // Should be Semicolon !!!
{
SetTokenResult(done, pop_success);
}
void
PE_VarFunc::On_finished_Comma(const char * )
{
SetTokenResult(done, stay);
pStati->SetCur(expectName);
}
void
PE_VarFunc::On_finished_Default(const char * )
{
SetTokenResult(not_done, pop_success);
}
void
PE_VarFunc::On_finishedIncludingFunctionImplementation_Default(const char * )
{
SetTokenResult(not_done, pop_success);
}
ary::cpp::FunctionFlags
PE_VarFunc::CreateFunctionFlags()
{
typedef ary::cpp::FunctionFlags FuncFlags;
return FuncFlags( UINT16(
( bStatic AND Env().Context().CurClass() == 0 ? FuncFlags::f_static_local : 0 )
| ( bStatic AND Env().Context().CurClass() != 0 ? FuncFlags::f_static_member : 0 )
| ( bExtern ? FuncFlags::f_extern : 0 )
| ( Env().IsExternC() ? FuncFlags::f_externC : 0 )
| ( bMutable ? FuncFlags::f_mutable : 0 )
| ( bInline ? FuncFlags::f_inline : 0 )
| ( bRegister ? FuncFlags::f_register : 0 )
| ( bExplicit ? FuncFlags::f_explicit : 0 ) )
);
}
} // namespace cpp