blob: a674fec92f1998a3102237e075672f1c7b7af210 [file] [log] [blame]
/*******************************************************************************
* Copyright (c) 2016 CEA LIST.
*
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
* Arnault Lapitre (CEA LIST) arnault.lapitre@cea.fr
* - Initial API and implementation
******************************************************************************/
#include "ExecutableForm.h"
#include <collection/List.h>
#include <fml/common/SpecifierElement.h>
#include <fml/executable/ExecutableSystem.h>
#include <fml/expression/StatementTypeChecker.h>
#include <fml/infrastructure/BehavioralPart.h>
#include <fml/infrastructure/Transition.h>
namespace sep
{
/**
* SETTER
* updateFullyQualifiedNameID()
*/
void ExecutableForm::updateFullyQualifiedNameID(
const std::string & aFullyQualifiedNameID)
{
std::string::size_type pos =
aFullyQualifiedNameID.find(FQN_ID_ROOT_SEPARATOR);
if( pos != std::string::npos )
{
setFullyQualifiedNameID( "exec" + aFullyQualifiedNameID.substr(pos) );
}
else
{
setFullyQualifiedNameID( "exec::" + aFullyQualifiedNameID );
AVM_OS_FATAL_ERROR_EXIT
<< "Unexpected UFI without LOCATOR for executable:> "
<< aFullyQualifiedNameID << " !!!"
<< SEND_EXIT;
}
setNameID( NamedElement::extractNameID( aFullyQualifiedNameID ) );
}
/**
* GETTER
* any SYMBOL filtering by an optional type specifier family
*/
#define IF_MUST_BE_MACHINE_SYMBOL \
if( (typeFamily == TYPE_MACHINE_SPECIFIER) || \
(typeFamily == TYPE_UNIVERSAL_SPECIFIER) || \
(typeFamily == TYPE_UNDEFINED_SPECIFIER) )
#define IF_MUST_BE_GENERIC_PORT_SYMBOL \
if( (typeFamily == TYPE_PORT_SPECIFIER) || \
(typeFamily == TYPE_SIGNAL_SPECIFIER) || \
(typeFamily == TYPE_MESSAGE_SPECIFIER) || \
(typeFamily == TYPE_UNIVERSAL_SPECIFIER) || \
(typeFamily == TYPE_UNDEFINED_SPECIFIER) )
#define IF_MUST_BE_CHANNEL_SYMBOL \
if( (typeFamily == TYPE_CHANNEL_SPECIFIER) || \
(typeFamily == TYPE_UNIVERSAL_SPECIFIER) || \
(typeFamily == TYPE_UNDEFINED_SPECIFIER) )
#define IF_MUST_BE_BUFFER_SYMBOL \
if( (typeFamily == TYPE_BUFFER_SPECIFIER) || \
(typeFamily == TYPE_UNIVERSAL_SPECIFIER) || \
(typeFamily == TYPE_UNDEFINED_SPECIFIER) )
#define IF_MUST_BE_CONNECTOR_SYMBOL \
if( (typeFamily == TYPE_CONNECTOR_SPECIFIER) || \
(typeFamily == TYPE_UNIVERSAL_SPECIFIER) || \
(typeFamily == TYPE_UNDEFINED_SPECIFIER) )
#define ANYTHING_ELSE_CONDITION ( \
( typeFamily != TYPE_MACHINE_SPECIFIER ) && \
( typeFamily != TYPE_PORT_SPECIFIER ) && \
( typeFamily != TYPE_SIGNAL_SPECIFIER ) && \
( typeFamily != TYPE_MESSAGE_SPECIFIER ) && \
( typeFamily != TYPE_CHANNEL_SPECIFIER ) && \
( typeFamily != TYPE_BUFFER_SPECIFIER ) && \
( typeFamily != TYPE_CONNECTOR_SPECIFIER ) )
#define IF_COULD_BE_TYPE_SPECIFIER_SYMBOL \
if( ANYTHING_ELSE_CONDITION )
#define IF_COULD_BE_TRANSITION_SYMBOL \
if( ANYTHING_ELSE_CONDITION )
#define IF_COULD_BE_GENERIC_PROGRAM_SYMBOL \
if( ANYTHING_ELSE_CONDITION )
const BF & ExecutableForm::getSymbol(
const std::string & aFullyQualifiedNameID,
avm_type_specifier_kind_t typeFamily) const
{
IF_MUST_BE_GENERIC_PORT_SYMBOL
{
const Symbol & foundSymbol =
mTableOfPort.getByFQNameID( aFullyQualifiedNameID );
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_MUST_BE_MACHINE_SYMBOL
{
const Symbol & foundSymbol =
mTableOfInstanceStatic.getByFQNameID( aFullyQualifiedNameID );
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
// IF_MUST_BE_MACHINE_SYMBOL
// {
// const Symbol & foundSymbol =
mTableOfInstanceModel.getByFQNameID( aFullyQualifiedNameID );
// if( foundSymbol.valid() )
// {
// return( foundSymbol );
// }
// }
IF_MUST_BE_BUFFER_SYMBOL
{
const Symbol & foundSymbol =
mTableOfBuffer.getByFQNameID( aFullyQualifiedNameID );
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_MUST_BE_CONNECTOR_SYMBOL
{
const Symbol & foundSymbol =
mTableOfChannel.getByFQNameID( aFullyQualifiedNameID );
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_MUST_BE_CONNECTOR_SYMBOL
{
const Symbol & foundSymbol =
mTableOfConnect.getByFQNameID( aFullyQualifiedNameID );
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
// UNCONDITIONAL
{
const BF & foundSymbol =
AvmProgram::getSymbol(aFullyQualifiedNameID, typeFamily);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_COULD_BE_TYPE_SPECIFIER_SYMBOL
{
const BF & foundSymbol =
getTypeSpecifier().getByFQNameID( aFullyQualifiedNameID );
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_COULD_BE_TRANSITION_SYMBOL
{
const BF & foundSymbol =
getTransition().getByFQNameID( aFullyQualifiedNameID );
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_COULD_BE_GENERIC_PROGRAM_SYMBOL
{
const BF & foundSymbol =
getProgram().getByFQNameID( aFullyQualifiedNameID );
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
// UNCONDITIONAL
{
const Symbol & foundSymbol =
getAlias().getByFQNameID( aFullyQualifiedNameID );
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
return( BF::REF_NULL );
}
const BF & ExecutableForm::getSymbolByQualifiedNameID(
const std::string & aQualifiedNameID,
avm_type_specifier_kind_t typeFamily) const
{
IF_MUST_BE_GENERIC_PORT_SYMBOL
{
const Symbol & foundSymbol =
mTableOfPort.getByQualifiedNameID( aQualifiedNameID );
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_MUST_BE_MACHINE_SYMBOL
{
const Symbol & foundSymbol = mTableOfInstanceStatic.
getByQualifiedNameID( aQualifiedNameID );
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_MUST_BE_MACHINE_SYMBOL
{
const Symbol & foundSymbol = mTableOfInstanceDynamic.
getByQualifiedNameID( aQualifiedNameID );
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
// IF_MUST_BE_MACHINE_SYMBOL
// {
// const Symbol & foundSymbol =
// mTableOfInstanceModel.getByQualifiedNameID(aQualifiedNameID);
// if( foundSymbol.valid() )
// {
// return( foundSymbol );
// }
// }
IF_MUST_BE_BUFFER_SYMBOL
{
const Symbol & foundSymbol =
mTableOfBuffer.getByQualifiedNameID(aQualifiedNameID);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_MUST_BE_CONNECTOR_SYMBOL
{
const Symbol & foundSymbol =
mTableOfConnect.getByQualifiedNameID(aQualifiedNameID);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
// UNCONDITIONAL
{
const BF & foundSymbol =
AvmProgram::getSymbolByQualifiedNameID(
aQualifiedNameID, typeFamily);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_COULD_BE_TYPE_SPECIFIER_SYMBOL
{
const BF & foundSymbol = mTableOfTypeSpecifier.
getByQualifiedNameID( aQualifiedNameID );
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_COULD_BE_TRANSITION_SYMBOL
{
const BF & foundSymbol = mTableOfTransition.
getByQualifiedNameID( aQualifiedNameID );
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_COULD_BE_GENERIC_PROGRAM_SYMBOL
{
const BF & foundSymbol = mTableOfProgram.
getByQualifiedNameID( aQualifiedNameID );
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
// // UNCONDITIONAL
// {
// const Symbol & foundSymbol =
// mTableOfAlias.getByQualifiedNameID( aQualifiedNameID );
// if( foundSymbol.valid() )
// {
// return( foundSymbol );
// }
// }
return( BF::REF_NULL );
}
const BF & ExecutableForm::getSymbolByNameID(const std::string & aNameID,
avm_type_specifier_kind_t typeFamily) const
{
IF_MUST_BE_GENERIC_PORT_SYMBOL
{
const Symbol & foundSymbol = mTableOfPort.getByNameID(aNameID);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_MUST_BE_MACHINE_SYMBOL
{
const Symbol & foundSymbol =
mTableOfInstanceStatic.getByNameID(aNameID);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
// IF_MUST_BE_MACHINE_SYMBOL
// {
// const Symbol & foundSymbol =
// mTableOfInstanceModel.getByNameID(aNameID);
// if( foundSymbol.valid() )
// {
// return( foundSymbol );
// }
// }
IF_MUST_BE_BUFFER_SYMBOL
{
const Symbol & foundSymbol = mTableOfBuffer.getByNameID(aNameID);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_MUST_BE_CONNECTOR_SYMBOL
{
const Symbol & foundSymbol = mTableOfConnect.getByNameID(aNameID);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
// UNCONDITIONAL
{
const BF & foundSymbol =
AvmProgram::getSymbolByNameID(aNameID, typeFamily);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_COULD_BE_TYPE_SPECIFIER_SYMBOL
{
const BF & foundSymbol = mTableOfTypeSpecifier.getByNameID(aNameID);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_COULD_BE_TRANSITION_SYMBOL
{
const BF & foundSymbol = mTableOfTransition.getByNameID(aNameID);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_COULD_BE_GENERIC_PROGRAM_SYMBOL
{
const BF & foundSymbol = mTableOfProgram.getByNameID(aNameID);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
// // UNCONDITIONAL
// {
// const Symbol & foundSymbol = mTableOfAlias.getByNameID(id);
// if( foundSymbol.valid() )
// {
// return( foundSymbol );
// }
// }
return( BF::REF_NULL );
}
const BF & ExecutableForm::getSymbolByAstElement(
const ObjectElement * astElement,
avm_type_specifier_kind_t typeFamily) const
{
IF_MUST_BE_GENERIC_PORT_SYMBOL
{
const Symbol & foundSymbol = mTableOfPort.getByAstElement(astElement);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_MUST_BE_MACHINE_SYMBOL
{
const Symbol & foundSymbol = getByAstInstanceStatic(astElement);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_MUST_BE_BUFFER_SYMBOL
{
const Symbol & foundSymbol = mTableOfBuffer.getByAstElement(astElement);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_MUST_BE_CHANNEL_SYMBOL
{
const Symbol & foundSymbol = mTableOfChannel.getByAstElement(astElement);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_MUST_BE_CONNECTOR_SYMBOL
{
const Symbol & foundSymbol = mTableOfConnect.getByAstElement(astElement);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
// UNCONDITIONAL
{
const BF & foundSymbol =
AvmProgram::getSymbolByAstElement(astElement, typeFamily);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_COULD_BE_TYPE_SPECIFIER_SYMBOL
{
const BF & foundSymbol = getTypeSpecifier().getByAstElement(astElement);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_COULD_BE_TRANSITION_SYMBOL
{
const BF & foundSymbol = getTransition().getByAstElement(astElement);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
IF_COULD_BE_GENERIC_PROGRAM_SYMBOL
{
const BF & foundSymbol = getProgram().getByAstElement(astElement);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
// UNCONDITIONAL
{
const Symbol & foundSymbol = getAlias().getByAstElement(astElement);
if( foundSymbol.valid() )
{
return( foundSymbol );
}
}
return( BF::REF_NULL );
}
/**
* GETTER - SETTER
* Machine Count
*/
avm_size_t ExecutableForm::getrecMachineCount() const
{
avm_size_t count = 0;
if( hasInstanceStatic() )
{
TableOfSymbol::const_iterator itMachine = instance_static_begin();
TableOfSymbol::const_iterator endIt = instance_static_end();
for( ; itMachine != endIt ; ++itMachine )
{
count += 1;
if( (*itMachine).hasExecutable() )
{
count += (*itMachine).getExecutable()->getrecMachineCount();
}
}
}
return( count );
}
/**
* ExecutableForm::LCA
*
*/
const ExecutableForm * ExecutableForm::LCA(
const ExecutableForm * anExecutable) const
{
List< const ExecutableForm * > containerListOfThis;
containerListOfThis.push_back(this);
ExecutableForm * containerOfThis = this->getExecutableContainer();
for ( ; containerOfThis != NULL ;
containerOfThis = containerOfThis->getExecutableContainer() )
{
containerListOfThis.push_back(containerOfThis);
}
List< const ExecutableForm * > containerListOfOtherExecutable;
containerListOfOtherExecutable.push_back(anExecutable);
ExecutableForm * containerOfOtherForm = anExecutable->getExecutableContainer();
for ( ; containerOfOtherForm != NULL ;
containerOfOtherForm = containerOfOtherForm->getExecutableContainer() )
{
containerListOfOtherExecutable.push_back(containerOfOtherForm);
}
List< const ExecutableForm * >::const_iterator otherIt;
List< const ExecutableForm * >::
const_iterator oneIt = containerListOfThis.begin();
for ( ; oneIt != containerListOfThis.end() ; oneIt++ )
{
otherIt = containerListOfOtherExecutable.begin();
for ( ; otherIt != containerListOfOtherExecutable.end() ; ++otherIt )
{
if( (*oneIt) == (*otherIt) )
{
// AVM_OS_LOG << "LCA ( "
// << oneExecutable->getFullyQualifiedNameID()
// << " , " << otherExecutable->getFullyQualifiedNameID()
// << " ) = " << (*oneIt)->getFullyQualifiedNameID();
return( *oneIt );
}
}
}
return( NULL );
}
/*
* GETTER - SETTER
* Single or Multiple
* Instanciation Information
* for Data Access optimisation
*/
void ExecutableForm::incrPossibleStaticInstanciationCount(avm_offset_t offset)
{
mPossibleStaticInstanciationCount += offset;
if( mPossibleStaticInstanciationCount > 1 )
{
TableOfSymbol::const_iterator itInstabce = instance_static_begin();
TableOfSymbol::const_iterator endInstabce = instance_static_end();
for( ; itInstabce != endInstabce ; ++itInstabce )
{
(*itInstabce).getExecutable()->
incrPossibleStaticInstanciationCount(offset);
}
}
}
void ExecutableForm::incrPossibleDynamicInstanciationCount(avm_size_t offset)
{
mPossibleDynamicInstanciationCount += offset;
if( mPossibleDynamicInstanciationCount > 1 )
{
TableOfSymbol::const_iterator itInstabce = instance_static_begin();
TableOfSymbol::const_iterator endInstabce = instance_static_end();
for( ; itInstabce != endInstabce ; ++itInstabce )
{
(*itInstabce).getExecutable()->
incrPossibleDynamicInstanciationCount(offset);
}
}
}
bool ExecutableForm::hasSingleRuntimeInstance()
{
// AVM_OS_COUT << strModifier() << "executable< mok:"
// << getSpecifier().str()
// << " , id:" << getOffset()
// << " , pic:(static:" << mPossibleStaticInstanciationCount
// << " , dynamic:" << mPossibleDynamicInstanciationCount << ")"
// << " , instance:(init:" << mInitialInstanceCount
// << " , max:" << ( (mMaximalInstanceCount == AVM_NUMERIC_MAX_SIZE_T) ?
// -1 : static_cast< avm_int64_t >(mMaximalInstanceCount) )
// << ") > " << getFullyQualifiedNameID() << std::endl;
if( (mPossibleStaticInstanciationCount > 1) ||
(mPossibleDynamicInstanciationCount > 0) )
{
return( false );
}
else
{
ExecutableForm * containerExec = getExecutableContainer();
if( (containerExec != NULL) &&
(not containerExec->hasSingleRuntimeInstance()) )
{
mPossibleDynamicInstanciationCount = 1;
return( false );
}
return( true );
}
}
/**
* GETTER - SETTER
* mMutableScheduleFlag
* MOC Attribute for mutable Schedule
*/
bool ExecutableForm::isInlinableSchedule() const
{
// if( not hasSingleRuntimeInstance() )
// {
// return( false );
// }
TableOfSymbol::const_iterator itModel = instance_model_begin();
TableOfSymbol::const_iterator endModel = instance_model_end();
for( ; itModel != endModel ; ++itModel )
{
if( not (*itModel).getExecutable()->hasSingleRuntimeInstance() )
{
return( false );
}
}
return( (not mMutableScheduleFlag) );
}
/**
* GETTER
* on activity by opcode
*/
AvmProgram & ExecutableForm::getOnActivityRoutine(AVM_OPCODE opCode)
{
switch( opCode )
{
case AVM_OPCODE_INIT:
{
return( getOnInitRoutine() );
}
case AVM_OPCODE_FINAL:
case AVM_OPCODE_DESTROY:
{
return( getOnFinalRoutine() );
}
case AVM_OPCODE_RETURN:
{
return( getOnReturnRoutine() );
}
case AVM_OPCODE_START:
case AVM_OPCODE_RESTART:
{
return( getOnStartRoutine() );
}
case AVM_OPCODE_STOP:
{
return( getOnStopRoutine() );
}
// case AVM_OPCODE_WAIT:
// case AVM_OPCODE_SUSPEND:
// case AVM_OPCODE_RESUME:
case AVM_OPCODE_IENABLE_INVOKE:
{
return( getOnIEnableRoutine() );
}
case AVM_OPCODE_ENABLE_INVOKE:
{
return( getOnEnableRoutine() );
}
// case AVM_OPCODE_ENABLE_SET:
case AVM_OPCODE_IDISABLE_INVOKE:
{
return( getOnIDisableRoutine() );
}
case AVM_OPCODE_DISABLE_INVOKE:
{
return( getOnDisableRoutine() );
}
// case AVM_OPCODE_DISABLE_SET:
// case AVM_OPCODE_DISABLE_CHILD:
// case AVM_OPCODE_DISABLE_SELF:
// case AVM_OPCODE_DISABLE_SELVES:
case AVM_OPCODE_IABORT_INVOKE:
{
return( getOnIAbortRoutine() );
}
case AVM_OPCODE_ABORT_INVOKE:
{
return( getOnAbortRoutine() );
}
// case AVM_OPCODE_ABORT_SET:
// case AVM_OPCODE_ABORT_CHILD:
// case AVM_OPCODE_ABORT_SELF:
// case AVM_OPCODE_ABORT_SELVES:
case AVM_OPCODE_IRUN:
{
return( getOnIRunRoutine() );
}
case AVM_OPCODE_RUN:
{
return( getOnRunRoutine() );
}
case AVM_OPCODE_RTC:
{
return( getOnRtcRoutine() );
}
case AVM_OPCODE_SCHEDULE_INVOKE:
{
return( getOnScheduleRoutine() );
}
// case AVM_OPCODE_DEFER_INVOKE:
default:
{
AVM_OS_FATAL_ERROR_EXIT
<< "ExecutableForm::getOnActivityRoutine:> "
"Unexpected AVM_OPCODE !!!"
<< SEND_EXIT;
return( getOnScheduleRoutine() );
}
}
}
const BFCode & ExecutableForm::getOnActivity(AVM_OPCODE opCode) const
{
switch( opCode )
{
case AVM_OPCODE_INIT:
{
return( getOnInit() );
}
case AVM_OPCODE_FINAL:
case AVM_OPCODE_DESTROY:
{
return( getOnFinal() );
}
case AVM_OPCODE_RETURN:
{
return( getOnReturn() );
}
case AVM_OPCODE_START:
case AVM_OPCODE_RESTART:
{
return( getOnStart() );
}
case AVM_OPCODE_STOP:
{
return( getOnStop() );
}
// case AVM_OPCODE_WAIT:
// case AVM_OPCODE_SUSPEND:
// case AVM_OPCODE_RESUME:
case AVM_OPCODE_IENABLE_INVOKE:
{
return( getOnIEnable() );
}
case AVM_OPCODE_ENABLE_INVOKE:
{
return( getOnEnable() );
}
// case AVM_OPCODE_ENABLE_SET:
case AVM_OPCODE_IDISABLE_INVOKE:
{
return( getOnIDisable() );
}
case AVM_OPCODE_DISABLE_INVOKE:
{
return( getOnDisable() );
}
// case AVM_OPCODE_DISABLE_SET:
// case AVM_OPCODE_DISABLE_CHILD:
// case AVM_OPCODE_DISABLE_SELF:
// case AVM_OPCODE_DISABLE_SELVES:
case AVM_OPCODE_IABORT_INVOKE:
{
return( getOnIAbort() );
}
case AVM_OPCODE_ABORT_INVOKE:
{
return( getOnAbort() );
}
// case AVM_OPCODE_ABORT_SET:
// case AVM_OPCODE_ABORT_CHILD:
// case AVM_OPCODE_ABORT_SELF:
// case AVM_OPCODE_ABORT_SELVES:
case AVM_OPCODE_IRUN:
{
return( getOnIRun() );
}
case AVM_OPCODE_RUN:
{
return( getOnRun() );
}
case AVM_OPCODE_RTC:
{
return( getOnRtc() );
}
case AVM_OPCODE_SCHEDULE_INVOKE:
{
return( getOnSchedule() );
}
// case AVM_OPCODE_DEFER_INVOKE:
default:
{
return( BFCode::REF_NULL );
}
}
}
/**
* Serialization
*/
void ExecutableForm::header(OutStream & os) const
{
os << getModifier().toString()
<< getSpecifier().toString( Specifier::ENABLE_FEATURE_DESIGN_FIELD )
<< "executable< moc: "
<< getSpecifier().str( Specifier::DISABLE_FEATURE_DESIGN_FIELD )
<< " , id:" << getOffset();
InstanceSpecifierPart::strMultiplicity(
os, mPossibleStaticInstanciationCount,
mPossibleDynamicInstanciationCount,
mMaximalInstanceCount, ", instanciation: [ ", " ]");
//AVM_IF_DEBUG_ENABLED_AND(
// getSpecifier().isFamilyComponentComposite()
// && ( (mPossibleStaticInstanciationCount != 1)
// || (mPossibleDynamicInstanciationCount > 0) ) )
// os << " , pic:(static:" << mPossibleStaticInstanciationCount
// << " , dynamic:" << mPossibleDynamicInstanciationCount << ")";
//AVM_ENDIF_DEBUG_ENABLED
//
//AVM_IF_DEBUG_ENABLED_AND(
// getSpecifier().isFamilyComponentComposite()
// && ( (mInitialInstanceCount != 1)
// || (mMaximalInstanceCount != AVM_NUMERIC_MAX_SIZE_T) ) )
// os << " , instance:(init:" << mInitialInstanceCount << " , max:"
// << ( (mMaximalInstanceCount == AVM_NUMERIC_MAX_SIZE_T) ?
// -1 : static_cast< avm_int64_t >(mMaximalInstanceCount) )
// << " )";
//AVM_ENDIF_DEBUG_ENABLED
os << " > ";
};
void ExecutableForm::strHeader(OutStream & os) const
{
header( os );
AVM_IF_DEBUG_FLAG_AND( COMPILING , hasAstElement() )
os << "&" << getAstFullyQualifiedNameID() << " ";
AVM_ENDIF_DEBUG_FLAG_AND( COMPILING )
os << getFullyQualifiedNameID();
}
void ExecutableForm::toStream(OutStream & os,
const TableOfRouter & aTableOfRouter, const std::string & sectionName)
{
if( aTableOfRouter.nonempty() )
{
os << TAB << sectionName << EOL_INCR_INDENT;
TableOfRouter::const_iterator itRouter = aTableOfRouter.begin();
TableOfRouter::const_iterator endRouter = aTableOfRouter.end();
for( ; itRouter != endRouter ; ++itRouter )
{
if( (*itRouter).valid() )
{
(*itRouter).toStream(os);
}
else
{
os << TAB << "routeur<null>";
}
os << EOL_FLUSH;
}
if( aTableOfRouter.last().invalid() )
{
os << EOL;
}
os << DECR_INDENT;
}
}
void ExecutableForm::toStream(OutStream & os) const
{
if( os.preferablyFQN() )
{
os << TAB << getFullyQualifiedNameID();
AVM_DEBUG_REF_COUNTER(os);
return;
}
header( os << TAB );
AVM_IF_DEBUG_FLAG_AND( COMPILING , hasAstElement() )
os << "&" << getAstFullyQualifiedNameID() << " ";
AVM_ENDIF_DEBUG_FLAG_AND( COMPILING )
os << getFullyQualifiedNameID() << " {" << EOL;
//AVM_IF_DEBUG_ENABLED_AND(
// getSpecifier().isFamilyComponentComposite()
// && ( (mPossibleStaticInstanciationCount != 1)
// || (mPossibleDynamicInstanciationCount > 0) ) )
// os << TAB2 << "//possible_instanciation_count = (static:"
// << mPossibleStaticInstanciationCount << " , dynamic:"
// << mPossibleDynamicInstanciationCount << ");" << EOL;
//AVM_ENDIF_DEBUG_ENABLED
AVM_IF_DEBUG_FLAG( COMPILING )
if( hasContainer() )
{
os << TAB2 << "//container = "
<< str_header( getContainer()->as< ExecutableForm >() )
<< ";" << EOL;
}
if( hasPrototypeInstance() )
{
os << TAB2 << "//prototype = "
<< str_header( getPrototypeInstance() )
<< ";" << EOL;
}
AVM_ENDIF_DEBUG_FLAG( COMPILING )
// MOC Attribute
if( isInputEnabledCommunication() )
{
os << TAB2 << "input_enabled = true;" << EOL << std::flush;
}
// Any program data
toStreamData(os);
if( hasAlias() )
{
( hasDataAlias() ? os : os << TAB << "alias:" ) << EOL_INCR_INDENT;
getAlias().toStream(os);
os << DECR_INDENT;
}
if( hasPort() )
{
if( (mMessageSignalCount == 0) ||
(mMessageSignalCount == getPort().size()) )
{
os << TAB << "port:" << EOL;
}
else
{
os << TAB << "port< ms: " << mMessageSignalCount << " >:" << EOL;
}
os << incr_stream( getPort() );
}
if( hasBuffer() )
{
os << TAB << "buffer:" << EOL_INCR_INDENT;
getBuffer().toStream(os);
os << DECR_INDENT;
}
if( hasChannel() )
{
os << TAB << "channel:" << EOL_INCR_INDENT;
getChannel().toStream(os);
os << DECR_INDENT;
}
if( hasConnect() )
{
os << TAB << "connection:" << "/* < " << getFullyQualifiedNameID() << " > */"
<< EOL_INCR_INDENT;
getConnect().toStream(os);
os << DECR_INDENT;
}
if( hasRdvCommunication() )
{
os << EOL_TAB2 << "rdv_communication = true;" << EOL << EOL;
}
// Table of Router for Instance
toStream(os, mTableOfRouter4Instance, "router:");
// Table of Router for Model
toStream(os, mTableOfRouter4Model, "router#model:");
if( hasExecutable() )
{
os << TAB << "procedure:" << EOL_INCR_INDENT;
getExecutables().toStream(os);
os << DECR_INDENT;
}
if( hasInstanceModel() )
{
os << TAB << "model:" << EOL_INCR_INDENT;
getInstanceModel().toStream(os);
os << DECR_INDENT;
}
if( hasInstanceStatic() )
{
os << TAB << "instance:" << EOL_INCR_INDENT;
getInstanceStatic().toStream(os);
os << DECR_INDENT;
}
if( hasInstanceDynamic() )
{
os << TAB << "instance#dynamic:" << EOL_INCR_INDENT;
getInstanceDynamic().toStream(os);
os << DECR_INDENT;
}
if( hasTransition() )
{
os << TAB << "transition:" << EOL_INCR_INDENT;
getTransition().toStream(os);
os << DECR_INDENT;
}
if( hasProgram() )
{
os << TAB << "program:" << EOL_INCR_INDENT;
getProgram().toStream(os);
os << DECR_INDENT;
}
if( mTableOfAnonymousInnerRoutine.nonempty() )
{
os << TAB << "routine< anonymous#inner >:" << EOL_INCR_INDENT;
mTableOfAnonymousInnerRoutine.fqnStream(os);
os << DECR_INDENT;
}
////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////
// STATIC ANALYSIS ATTRIBUTE
////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////
AVM_IF_DEBUG_FLAG2( COMPILING , DATA )
if( hasTransition() || hasProgram() )
{
TableOfInstanceOfData::const_raw_iterator itData;
TableOfInstanceOfData::const_raw_iterator endData;
if( getRequiredData().nonempty() )
{
os << TAB << "data#required:" << EOL;
itData = getRequiredData().begin();
endData = getRequiredData().end();
for( ; itData != endData ; ++itData )
{
os << TAB2 << itData->getFullyQualifiedNameID() << ";" << EOL;
}
}
if( getUselessData().nonempty() )
{
os << TAB << "data#useless:" << EOL;
itData = getUselessData().begin();
endData = getUselessData().end();
for( ; itData != endData ; ++itData )
{
os << TAB2 << itData->getFullyQualifiedNameID() << ";" << EOL;
}
}
}
AVM_ENDIF_DEBUG_FLAG2( COMPILING , DATA )
if( hasVariableDependency() )
{
os << TAB << "dependency#variable = "
<< STATIC_ANALYSIS::to_string( getVariableDependent() ) << EOL;
}
if( (not isReachableStateFlag)
&& (not getSpecifier().isPseudostateInitialOrStateStart()) )
{
os << TAB2 << "reachable#machine = false;" << EOL;
}
if( hasBackwardReachableMachine() )
{
os << TAB << "reachable#backward#machine:" << EOL;
ListOfInstanceOfMachine::const_iterator itMachine =
getBackwardReachableMachine().begin();
ListOfInstanceOfMachine::const_iterator endMachine =
getBackwardReachableMachine().end();
for( ; itMachine != endMachine ; ++itMachine )
{
os << TAB2 << str_header( *itMachine ) << ";" << EOL;
}
}
if( hasBackwardReachableTransition() )
{
os << TAB << "reachable#backward#transition:" << EOL;
OutStream osHierarchy( os );
osHierarchy.INDENT.CHAR = " ";
ListOfAvmTransition::const_iterator itProg =
getBackwardReachableTransition().begin();
ListOfAvmTransition::const_iterator endProg =
getBackwardReachableTransition().end();
for( ; itProg != endProg ; ++itProg )
{
os << TAB2 << str_header( *itProg ) << ";" << EOL;
}
}
if( hasForwardReachableMachine() )
{
os << TAB << "reachable#forward#machine:" << EOL;
OutStream osHierarchy( os );
osHierarchy.INDENT.CHAR = " ";
ListOfInstanceOfMachine::const_iterator itMachine =
getForwardReachableMachine().begin();
ListOfInstanceOfMachine::const_iterator endMachine =
getForwardReachableMachine().end();
for( ; itMachine != endMachine ; ++itMachine )
{
os << TAB2 << str_header( *itMachine ) << ";" << EOL;
}
}
if( hasForwardReachableTransition() )
{
os << TAB << "reachable#forward#transition:" << EOL;
OutStream osHierarchy( os );
osHierarchy.INDENT.CHAR = " ";
ListOfAvmTransition::const_iterator itProg =
getForwardReachableTransition().begin();
ListOfAvmTransition::const_iterator endProg =
getForwardReachableTransition().end();
for( ; itProg != endProg ; ++itProg )
{
os << TAB2 << str_header( *itProg ) << ";" << EOL;
}
}
os << TAB << "moe:" << EOL;
if( hasOnCreate() )
{
os << TAB2 << "@create{" << INCR2_INDENT;
getOnCreate()->toStreamRoutine( os );
os << DECR2_INDENT_TAB2 << "}" << EOL;
}
if( hasOnInit() )
{
os << TAB2 << "@init{" << INCR2_INDENT;
getOnInit()->toStreamRoutine( os );
os << DECR2_INDENT_TAB2 << "}" << EOL;
}
if( hasOnReturn() )
{
os << TAB2 << "@return{" << INCR2_INDENT;
getOnReturn()->toStreamRoutine( os );
os << DECR2_INDENT_TAB2 << "}" << EOL;
}
if( hasOnFinal() )
{
os << TAB2 << "@final{" << INCR2_INDENT;
getOnFinal()->toStreamRoutine( os );
os << DECR2_INDENT_TAB2 << "}" << EOL;
}
if( hasOnStart() )
{
os << TAB2 << "@start{" << INCR2_INDENT;
getOnStart()->toStreamRoutine( os );
os << DECR2_INDENT_TAB2 << "}" << EOL;
}
if( hasOnStop() )
{
os << TAB2 << "@stop{" << INCR2_INDENT;
getOnStop()->toStreamRoutine( os );
os << DECR2_INDENT_TAB2 << "}" << EOL;
}
if( hasOnIEnable() )
{
os << TAB2 << "@ienable{" << INCR2_INDENT;
getOnIEnable()->toStreamRoutine( os );
os << DECR2_INDENT_TAB2 << "}" << EOL;
}
if( hasOnEnable() )
{
os << TAB2 << "@enable{" << INCR2_INDENT;
getOnEnable()->toStreamRoutine( os );
os << DECR2_INDENT_TAB2 << "}" << EOL;
}
if( hasOnIDisable() )
{
os << TAB2 << "@idisable{" << INCR2_INDENT;
getOnIDisable()->toStreamRoutine( os );
os << DECR2_INDENT_TAB2 << "}" << EOL;
}
if( hasOnDisable() )
{
os << TAB2 << "@disable{" << INCR2_INDENT;
getOnDisable()->toStreamRoutine( os );
os << DECR2_INDENT_TAB2 << "}" << EOL;
}
if( hasOnIAbort() )
{
os << TAB2 << "@iabort{" << INCR2_INDENT;
getOnIAbort()->toStreamRoutine( os );
os << DECR2_INDENT_TAB2 << "}" << EOL;
}
if( hasOnAbort() )
{
os << TAB2 << "@abort{" << INCR2_INDENT;
getOnAbort()->toStreamRoutine( os );
os << DECR2_INDENT_TAB2 << "}" << EOL;
}
if( hasOnIRun() )
{
os << TAB2 << "@irun{" << INCR2_INDENT;
getOnIRun()->toStreamRoutine( os );
os << DECR2_INDENT_TAB2 << "}" << EOL;
}
if( hasOnRun() )
{
os << TAB2 << "@run{" << INCR2_INDENT;
getOnRun()->toStreamRoutine( os );
os << DECR2_INDENT_TAB2 << "}" << EOL;
}
if( hasOnRtc() )
{
os << TAB2 << "@rtc{" << INCR2_INDENT;
getOnRtc()->toStreamRoutine( os );
os << DECR2_INDENT_TAB2 << "}" << EOL;
}
if( hasOnSchedule() )
{
os << TAB2 << "@schedule" << (isMutableSchedule() ? "" : "<final>")
<< "{" << INCR2_INDENT;
getOnSchedule()->toStreamRoutine( os );
os << DECR2_INDENT_TAB2 << "}" << EOL;
}
else if( isMutableSchedule() )
{
os << TAB2 << "@schedule#mutable{ }" << EOL;
}
if( hasOnConcurrency() )
{
os << TAB2 << "@concurrency{";
if( getOnConcurrency()->empty() )
{
os << " " << getOnConcurrencyOperator()->strOp() << " ";
}
else
{
getOnConcurrency()->toStreamRoutine( os << INCR2_INDENT )
<< DECR2_INDENT_TAB2;
}
os << "}" << EOL;
}
if( hasOnSynchronize() )
{
os << TAB2 << "@synchronize{" << INCR2_INDENT;
getOnSynchronize()->toStreamRoutine( os );
os << DECR2_INDENT_TAB2 << "}" << EOL;
}
// static class of Port/Message/Signal in communicated transition
os << INCR_INDENT;
toStreamStaticCom(os);
os << DECR_INDENT;
os << TAB << "}" << EOL << std::flush;
}
}