Builder tool - Various, pre-constant propagation
+ Prepared flags for constant propagation + UI instructions removal in compiler + Various changes to test "demo"
This commit is contained in:
parent
c4ce6e90d7
commit
c7e4ccf67e
9 changed files with 104 additions and 52 deletions
|
@ -79,6 +79,22 @@ bool BCLResolutions_( T_SRDParserData const& data )
|
||||||
|
|
||||||
/*----------------------------------------------------------------------------*/
|
/*----------------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
F_SRDHandler BCLToggle_(
|
||||||
|
ptrdiff_t const fldOffset ) noexcept
|
||||||
|
{
|
||||||
|
return [=]( T_SRDParserData const& d ) -> bool {
|
||||||
|
auto const& in{ *d.input };
|
||||||
|
char* bCfg{ (char*) &d.currentData->value< T_BuildConfiguration >( ) };
|
||||||
|
*(bool*)( bCfg + fldOffset ) = ( in[ 1 ].stringValue( ) == "on" );
|
||||||
|
return true;
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
#define M_BCL_TOGGLE_( N ) \
|
||||||
|
BCLToggle_( offsetof( T_BuildConfiguration , N ) )
|
||||||
|
|
||||||
|
/*----------------------------------------------------------------------------*/
|
||||||
|
|
||||||
T_SRDParserConfig BCLInitDefinitions_( ) noexcept
|
T_SRDParserConfig BCLInitDefinitions_( ) noexcept
|
||||||
{
|
{
|
||||||
using namespace ebcl::SRD;
|
using namespace ebcl::SRD;
|
||||||
|
@ -116,40 +132,20 @@ T_SRDParserConfig BCLInitDefinitions_( ) noexcept
|
||||||
|
|
||||||
defs.context( "optim" )
|
defs.context( "optim" )
|
||||||
<< ( Rule( ) << "constant-folding" << "off"
|
<< ( Rule( ) << "constant-folding" << "off"
|
||||||
<< []( T_SRDParserData const& d ) -> bool {
|
<< M_BCL_TOGGLE_( constantFolding ) )
|
||||||
auto& bCfg{ d.currentData->value< T_BuildConfiguration >( ) };
|
|
||||||
bCfg.constantFolding = false;
|
|
||||||
return true;
|
|
||||||
} )
|
|
||||||
<< ( Rule( ) << "constant-folding" << "on" << EnterContext( "opt-cf" )
|
<< ( Rule( ) << "constant-folding" << "on" << EnterContext( "opt-cf" )
|
||||||
<< []( T_SRDParserData const& d ) -> bool {
|
<< M_BCL_TOGGLE_( constantFolding ) )
|
||||||
auto& bCfg{ d.currentData->value< T_BuildConfiguration >( ) };
|
<< ( Rule( ) << "constant-propagation" << Enum( "on-off" )
|
||||||
bCfg.constantFolding = true;
|
<< M_BCL_TOGGLE_( constantPropagation ) )
|
||||||
return true;
|
|
||||||
} )
|
|
||||||
<< ( Rule( ) << "dead-code-elimination" << Enum( "on-off" )
|
<< ( Rule( ) << "dead-code-elimination" << Enum( "on-off" )
|
||||||
<< []( T_SRDParserData const& d ) -> bool {
|
<< M_BCL_TOGGLE_( deadCodeElimination ) )
|
||||||
auto& bCfg{ d.currentData->value< T_BuildConfiguration >( ) };
|
|
||||||
bCfg.deadCodeElimination = true;
|
|
||||||
return true;
|
|
||||||
} )
|
|
||||||
;
|
;
|
||||||
|
|
||||||
defs.context( "opt-cf" )
|
defs.context( "opt-cf" )
|
||||||
<< ( Rule( ) << "fixed-resolution" << Enum( "on-off" )
|
<< ( Rule( ) << "fixed-resolution" << Enum( "on-off" )
|
||||||
<< []( T_SRDParserData const& d ) -> bool {
|
<< M_BCL_TOGGLE_( cfFixedSize ) )
|
||||||
auto const& in{ *d.input };
|
|
||||||
auto& bCfg{ d.currentData->value< T_BuildConfiguration >( ) };
|
|
||||||
bCfg.cfFixedSize = ( in[ 1 ].stringValue( ) == "on" );
|
|
||||||
return true;
|
|
||||||
} )
|
|
||||||
<< ( Rule( ) << "inputs" << Enum( "on-off" )
|
<< ( Rule( ) << "inputs" << Enum( "on-off" )
|
||||||
<< []( T_SRDParserData const& d ) -> bool {
|
<< M_BCL_TOGGLE_( cfInputs ) )
|
||||||
auto const& in{ *d.input };
|
|
||||||
auto& bCfg{ d.currentData->value< T_BuildConfiguration >( ) };
|
|
||||||
bCfg.cfInputs = ( in[ 1 ].stringValue( ) == "on" );
|
|
||||||
return true;
|
|
||||||
} )
|
|
||||||
;
|
;
|
||||||
|
|
||||||
return T_SRDParserConfig{ defs };
|
return T_SRDParserConfig{ defs };
|
||||||
|
|
|
@ -27,6 +27,10 @@ struct T_BuildConfiguration
|
||||||
// Get rid of (get-input) for constant or undefined curves
|
// Get rid of (get-input) for constant or undefined curves
|
||||||
bool cfInputs{ false };
|
bool cfInputs{ false };
|
||||||
|
|
||||||
|
// Constant propagation ------------------------------------------------
|
||||||
|
|
||||||
|
bool constantPropagation{ false };
|
||||||
|
|
||||||
// Dead code elimination -----------------------------------------------
|
// Dead code elimination -----------------------------------------------
|
||||||
|
|
||||||
bool deadCodeElimination{ false };
|
bool deadCodeElimination{ false };
|
||||||
|
|
25
c-opcomp.cc
25
c-opcomp.cc
|
@ -16,13 +16,17 @@ namespace {
|
||||||
|
|
||||||
struct T_CompilerImpl_
|
struct T_CompilerImpl_
|
||||||
{
|
{
|
||||||
T_CompilerImpl_( F_OPLogger* logger ) noexcept
|
T_CompilerImpl_( F_OPLogger* const logger ,
|
||||||
: logger( *logger ) {}
|
const bool noUIInstructions ) noexcept
|
||||||
|
: logger( *logger ) , noUIInstructions( noUIInstructions )
|
||||||
|
{}
|
||||||
|
|
||||||
P_OpProgram compile( T_OpsParserOutput const& input ) noexcept;
|
P_OpProgram compile( T_OpsParserOutput const& input ) noexcept;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
F_OPLogger& logger;
|
F_OPLogger& logger;
|
||||||
|
const bool noUIInstructions;
|
||||||
|
|
||||||
T_Visitor< A_Node > astVisitor{ ASTVisitorBrowser };
|
T_Visitor< A_Node > astVisitor{ ASTVisitorBrowser };
|
||||||
T_Set< uint32_t > constants{ UseTag< IndexBacked< > >( ) };
|
T_Set< uint32_t > constants{ UseTag< IndexBacked< > >( ) };
|
||||||
T_KeyValueTable< T_String , uint32_t > locations;
|
T_KeyValueTable< T_String , uint32_t > locations;
|
||||||
|
@ -650,6 +654,9 @@ bool T_CompilerImpl_::compileNode(
|
||||||
//- DEBUGGING / UI CONTROLS -----------------------------------------------------------
|
//- DEBUGGING / UI CONTROLS -----------------------------------------------------------
|
||||||
|
|
||||||
case A_Node::OP_PROFILE:
|
case A_Node::OP_PROFILE:
|
||||||
|
if ( noUIInstructions ) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
if ( exit ) {
|
if ( exit ) {
|
||||||
addInstruction( OP_UI_PEXIT , node.location( ) );
|
addInstruction( OP_UI_PEXIT , node.location( ) );
|
||||||
} else {
|
} else {
|
||||||
|
@ -663,6 +670,9 @@ bool T_CompilerImpl_::compileNode(
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case A_Node::OP_INPUT:
|
case A_Node::OP_INPUT:
|
||||||
|
if ( noUIInstructions ) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
if ( exit ) {
|
if ( exit ) {
|
||||||
auto& in( (T_InputInstrNode&) node );
|
auto& in( (T_InputInstrNode&) node );
|
||||||
T_OpValue value;
|
T_OpValue value;
|
||||||
|
@ -675,6 +685,9 @@ bool T_CompilerImpl_::compileNode(
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case A_Node::OP_ODBG:
|
case A_Node::OP_ODBG:
|
||||||
|
if ( noUIInstructions ) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
if ( exit ) {
|
if ( exit ) {
|
||||||
auto& n( (T_OutputDebugInstrNode&) node );
|
auto& n( (T_OutputDebugInstrNode&) node );
|
||||||
if ( ! output->uiStrings.contains( n.description( ) ) ) {
|
if ( ! output->uiStrings.contains( n.description( ) ) ) {
|
||||||
|
@ -689,6 +702,9 @@ bool T_CompilerImpl_::compileNode(
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case A_Node::OP_OVERRIDES:
|
case A_Node::OP_OVERRIDES:
|
||||||
|
if ( noUIInstructions ) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
if ( exit ) {
|
if ( exit ) {
|
||||||
auto& n{ (T_OverridesInstrNode&) node };
|
auto& n{ (T_OverridesInstrNode&) node };
|
||||||
const auto idx{ output->overrides.add( n.extractRoot( ) ) };
|
const auto idx{ output->overrides.add( n.extractRoot( ) ) };
|
||||||
|
@ -917,8 +933,9 @@ void T_CompilerImpl_::applyStackEffects(
|
||||||
|
|
||||||
/*= T_OpsCompiler ==============================================================*/
|
/*= T_OpsCompiler ==============================================================*/
|
||||||
|
|
||||||
T_OpsCompiler::T_OpsCompiler( ) noexcept
|
T_OpsCompiler::T_OpsCompiler(
|
||||||
: A_PrivateImplementation( new T_CompilerImpl_( &logger_ ) )
|
const bool noUIInstructions ) noexcept
|
||||||
|
: A_PrivateImplementation( new T_CompilerImpl_( &logger_ , noUIInstructions ) )
|
||||||
{ }
|
{ }
|
||||||
|
|
||||||
P_OpProgram T_OpsCompiler::compile(
|
P_OpProgram T_OpsCompiler::compile(
|
||||||
|
|
|
@ -57,7 +57,7 @@ class T_OpsCompiler : public ebcl::A_PrivateImplementation
|
||||||
F_OPLogger logger_{ []( auto , auto ) { } };
|
F_OPLogger logger_{ []( auto , auto ) { } };
|
||||||
|
|
||||||
public:
|
public:
|
||||||
T_OpsCompiler( ) noexcept;
|
T_OpsCompiler( bool noUIInstructions = false ) noexcept;
|
||||||
|
|
||||||
void setLogger( F_OPLogger logger )
|
void setLogger( F_OPLogger logger )
|
||||||
{
|
{
|
||||||
|
|
21
c-opopt.cc
21
c-opopt.cc
|
@ -392,6 +392,27 @@ bool opopt::FoldConstants(
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*= CONSTANT PROPAGATION =====================================================*/
|
||||||
|
|
||||||
|
bool opopt::PropagateConstants(
|
||||||
|
T_OpsParserOutput& program ,
|
||||||
|
T_OptData& optData ) noexcept
|
||||||
|
{
|
||||||
|
// We need to follow the general execution flow of the program. This is
|
||||||
|
// not as straightforward as it seems.
|
||||||
|
// - Handling locals is rather easy as they "die" at the end of
|
||||||
|
// the function in which they are defined.
|
||||||
|
// - Handling variables in init and functions that are called only
|
||||||
|
// from init is not too hard: once a variable is set to a constant, it
|
||||||
|
// can be substituted until the next set instruction.
|
||||||
|
// - Other variables need additional checks before propagating.
|
||||||
|
// For example, if a variable is set to a constant during init, but is
|
||||||
|
// updated at the end of the frame function, the value cannot be
|
||||||
|
// propagated.
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/*= DEAD CODE REMOVAL ========================================================*/
|
/*= DEAD CODE REMOVAL ========================================================*/
|
||||||
|
|
||||||
bool opopt::RemoveDeadCode(
|
bool opopt::RemoveDeadCode(
|
||||||
|
|
22
c-opopt.hh
22
c-opopt.hh
|
@ -39,18 +39,28 @@ struct T_OptData
|
||||||
void findInputDecls( T_OpsParserOutput& program ) noexcept;
|
void findInputDecls( T_OpsParserOutput& program ) noexcept;
|
||||||
};
|
};
|
||||||
|
|
||||||
/*----------------------------------------------------------------------------*/
|
|
||||||
|
|
||||||
// Attempts to fold constant expressions into single constants. Returns true if
|
/*= INDIVIDUAL OPTIMISATIONS =================================================*/
|
||||||
// transformations were made, false if not.
|
// All functions below return true if transformations were made, false if not.
|
||||||
|
|
||||||
|
// Attempts to fold constant expressions into single constants.
|
||||||
//
|
//
|
||||||
bool FoldConstants( T_OpsParserOutput& program ,
|
bool FoldConstants(
|
||||||
|
T_OpsParserOutput& program ,
|
||||||
|
T_OptData& optData ) noexcept;
|
||||||
|
|
||||||
|
// Attempts to propagate values from variables that contain constants to the
|
||||||
|
// locations at which they are used.
|
||||||
|
//
|
||||||
|
bool PropagateConstants(
|
||||||
|
T_OpsParserOutput& program ,
|
||||||
T_OptData& optData ) noexcept;
|
T_OptData& optData ) noexcept;
|
||||||
|
|
||||||
// Attempt to remove blocks of code that will not be executed because of
|
// Attempt to remove blocks of code that will not be executed because of
|
||||||
// constant conditions. Returns true if transformations were made, false if not.
|
// constant conditions.
|
||||||
//
|
//
|
||||||
bool RemoveDeadCode( T_OpsParserOutput& program ,
|
bool RemoveDeadCode(
|
||||||
|
T_OpsParserOutput& program ,
|
||||||
T_OptData& optData ) noexcept;
|
T_OptData& optData ) noexcept;
|
||||||
|
|
||||||
|
|
||||||
|
|
16
m-builder.cc
16
m-builder.cc
|
@ -132,7 +132,7 @@ int main( int argc , char** argv )
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 'c':
|
case 'c':
|
||||||
if ( oSrcPath ) {
|
if ( oBuildCfg ) {
|
||||||
fprintf( stderr , "Duplicate build configuration\n" );
|
fprintf( stderr , "Duplicate build configuration\n" );
|
||||||
return EXIT_FAILURE;
|
return EXIT_FAILURE;
|
||||||
}
|
}
|
||||||
|
@ -252,22 +252,18 @@ int main( int argc , char** argv )
|
||||||
bool doneStuff;
|
bool doneStuff;
|
||||||
do {
|
do {
|
||||||
doneStuff = false;
|
doneStuff = false;
|
||||||
if ( cfg.constantFolding ) {
|
if ( cfg.constantFolding && opopt::FoldConstants( *parsed , od ) ) {
|
||||||
while ( opopt::FoldConstants( *parsed , od ) ) {
|
doneStuff = true;
|
||||||
doneStuff = true;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
if ( cfg.deadCodeElimination ) {
|
if ( cfg.deadCodeElimination && opopt::RemoveDeadCode( *parsed , od ) ) {
|
||||||
while ( opopt::RemoveDeadCode( *parsed , od ) ) {
|
doneStuff = true;
|
||||||
doneStuff = true;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
} while ( doneStuff );
|
} while ( doneStuff );
|
||||||
}
|
}
|
||||||
|
|
||||||
// Compile
|
// Compile
|
||||||
M_LOGSTR( "Compiling script" , 1 );
|
M_LOGSTR( "Compiling script" , 1 );
|
||||||
T_OpsCompiler compiler;
|
T_OpsCompiler compiler( true );
|
||||||
compiler.setLogger( logger );
|
compiler.setLogger( logger );
|
||||||
compiler.compile( *parsed );
|
compiler.compile( *parsed );
|
||||||
return 0;
|
return 0;
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
(cfg "Default"
|
(cfg "Optimized"
|
||||||
(resolutions
|
(resolutions
|
||||||
(1280 720)
|
(1280 720)
|
||||||
(1920 1080)
|
(1920 1080)
|
||||||
|
@ -7,3 +7,11 @@
|
||||||
(constant-folding on)
|
(constant-folding on)
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|
||||||
|
(cfg "Basic"
|
||||||
|
(resolutions
|
||||||
|
(1280 720)
|
||||||
|
(1920 1080)
|
||||||
|
)
|
||||||
|
(optimizer off)
|
||||||
|
)
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
(duration 0.133333 450)
|
(duration 0.133333 450)
|
||||||
|
|
||||||
(camera-nearplane
|
(camera-nearplane
|
||||||
(segment linear
|
(segment smooth
|
||||||
(values 1.1547 1.1547 4.82843)
|
(values 1.1547 1.1547 4.82843)
|
||||||
(durations 225 225)
|
(durations 225 225)
|
||||||
)
|
)
|
||||||
|
@ -9,7 +9,7 @@
|
||||||
|
|
||||||
(camera-pos-x
|
(camera-pos-x
|
||||||
(segment linear
|
(segment linear
|
||||||
(values -300 -150 0)
|
(values -4000 -2000 0)
|
||||||
(durations 225 225)
|
(durations 225 225)
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
@ -51,7 +51,7 @@
|
||||||
|
|
||||||
(camera-lookat-x
|
(camera-lookat-x
|
||||||
(segment linear
|
(segment linear
|
||||||
(values -300 -150 0)
|
(values -4000 -2000 0)
|
||||||
(durations 225 225)
|
(durations 225 225)
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|
Loading…
Reference in a new issue