2016-03-01 15:47:10 +00:00
# ifndef THINGDEF_EXP_H
# define THINGDEF_EXP_H
/*
* * thingdef_exp . h
* *
* * Expression evaluation
* *
* * - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
* * Copyright 2008 Christoph Oelckers
* * All rights reserved .
* *
* * Redistribution and use in source and binary forms , with or without
* * modification , are permitted provided that the following conditions
* * are met :
* *
* * 1. Redistributions of source code must retain the above copyright
* * notice , this list of conditions and the following disclaimer .
* * 2. Redistributions in binary form must reproduce the above copyright
* * notice , this list of conditions and the following disclaimer in the
* * documentation and / or other materials provided with the distribution .
* * 3. The name of the author may not be used to endorse or promote products
* * derived from this software without specific prior written permission .
* * 4. When not used as part of ZDoom or a ZDoom derivative , this code will be
* * covered by the terms of the GNU General Public License as published by
* * the Free Software Foundation ; either version 2 of the License , or ( at
* * your option ) any later version .
* *
* * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ` ` AS IS ' ' AND ANY EXPRESS OR
* * IMPLIED WARRANTIES , INCLUDING , BUT NOT LIMITED TO , THE IMPLIED WARRANTIES
* * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED .
* * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT , INDIRECT ,
* * INCIDENTAL , SPECIAL , EXEMPLARY , OR CONSEQUENTIAL DAMAGES ( INCLUDING , BUT
* * NOT LIMITED TO , PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES ; LOSS OF USE ,
* * DATA , OR PROFITS ; OR BUSINESS INTERRUPTION ) HOWEVER CAUSED AND ON ANY
* * THEORY OF LIABILITY , WHETHER IN CONTRACT , STRICT LIABILITY , OR TORT
* * ( INCLUDING NEGLIGENCE OR OTHERWISE ) ARISING IN ANY WAY OUT OF THE USE OF
* * THIS SOFTWARE , EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE .
* * - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
* *
*/
# include "m_random.h"
2016-10-12 22:53:59 +00:00
# include "sc_man.h"
# include "s_sound.h"
# include "actor.h"
2016-11-17 15:44:41 +00:00
# include "vmbuilder.h"
2016-03-01 15:47:10 +00:00
# define CHECKRESOLVED() if (isresolved) return this; isresolved=true;
# define SAFE_DELETE(p) if (p!=NULL) { delete p; p=NULL; }
# define RESOLVE(p,c) if (p!=NULL) p = p->Resolve(c)
# define ABORT(p) if (!(p)) { delete this; return NULL; }
# define SAFE_RESOLVE(p,c) RESOLVE(p,c); ABORT(p)
2016-07-25 04:38:02 +00:00
# define SAFE_RESOLVE_OPT(p,c) if (p!=NULL) { SAFE_RESOLVE(p,c) }
2016-03-01 15:47:10 +00:00
class VMFunctionBuilder ;
2016-07-26 21:57:26 +00:00
class FxJumpStatement ;
2016-03-01 15:47:10 +00:00
2016-11-10 14:13:31 +00:00
extern FMemArena FxAlloc ;
2016-03-01 15:47:10 +00:00
//==========================================================================
//
//
//
//==========================================================================
2016-10-12 22:53:59 +00:00
struct FScriptPosition ;
2016-10-19 12:36:54 +00:00
class FxLoopStatement ;
2016-10-19 17:05:48 +00:00
class FxCompoundStatement ;
2016-10-20 14:55:12 +00:00
class FxLocalVariableDeclaration ;
2016-11-19 23:25:38 +00:00
typedef TDeletingArray < FxExpression * > FArgumentList ;
2016-03-01 15:47:10 +00:00
2017-02-17 15:58:16 +00:00
// [ZZ] this is kind of related to compile context as well
2017-02-17 16:24:01 +00:00
struct FScopeBarrier
2017-02-17 15:58:16 +00:00
{
bool callable ;
bool readable ;
bool writable ;
// this is the error message
FString callerror ;
FString readerror ;
FString writeerror ;
// this is used to make the error message.
enum Side
{
Side_PlainData = 0 ,
Side_UI ,
Side_Play
} ;
int sidefrom ;
int sidelast ;
// Note: the same object can't be both UI and Play. This is checked explicitly in the field construction and will cause esoteric errors here if found.
2017-02-17 20:41:04 +00:00
static int SideFromFlags ( int flags )
2017-02-17 15:58:16 +00:00
{
if ( flags & VARF_UI )
return Side_UI ;
if ( flags & VARF_Play )
return Side_Play ;
return Side_PlainData ;
}
2017-02-17 20:41:04 +00:00
//
static int FlagsFromSide ( int side )
{
switch ( side )
{
case Side_Play :
return VARF_Play ;
case Side_UI :
return VARF_UI ;
default :
return 0 ;
}
}
2017-02-17 15:58:16 +00:00
// used for errors
2017-02-17 20:41:04 +00:00
static const char * StringFromSide ( int side )
2017-02-17 15:58:16 +00:00
{
switch ( side )
{
case Side_PlainData :
return " data " ;
case Side_UI :
return " ui " ;
case Side_Play :
return " play " ;
default :
return " unknown " ;
}
}
2017-02-17 16:24:01 +00:00
FScopeBarrier ( )
2017-02-17 15:58:16 +00:00
{
sidefrom = - 1 ;
sidelast = - 1 ;
callable = true ;
readable = true ;
writable = true ;
}
2017-02-17 16:24:01 +00:00
FScopeBarrier ( int flags1 , int flags2 , const char * name )
2017-02-17 15:58:16 +00:00
{
sidefrom = - 1 ;
sidelast = - 1 ;
callable = true ;
readable = true ;
writable = true ;
AddFlags ( flags1 , flags2 , name ) ;
}
// AddFlags modifies ALLOWED actions by flags1->flags2.
// This is used for comparing a.b.c.d access - if non-allowed field is seen anywhere in the chain, anything after it is non-allowed.
// This struct is used so that the logic is in a single place.
void AddFlags ( int flags1 , int flags2 , const char * name )
{
// note: if it's already non-readable, don't even try advancing
if ( ! readable )
return ;
// we aren't interested in any other flags
flags1 & = VARF_UI | VARF_Play ;
flags2 & = VARF_UI | VARF_Play | VARF_ReadOnly ;
if ( sidefrom < 0 ) sidefrom = SideFromFlags ( flags1 ) ;
if ( sidelast < 0 ) sidelast = sidefrom ;
// flags1 = what's trying to access
// flags2 = what's being accessed
int sideto = SideFromFlags ( flags2 ) ;
// plain data inherits whatever scope modifiers that context or field container has.
// i.e. play String bla; is play, and all non-specified methods/fields inside it are play as well.
if ( sideto ! = Side_PlainData )
sidelast = sideto ;
else sideto = sidelast ;
if ( ( sideto = = Side_UI ) ! = ( sidefrom = = Side_UI ) ) // only ui -> ui is readable
{
readable = false ;
readerror . Format ( " Can't read %s field %s from %s context " , StringFromSide ( sideto ) , StringFromSide ( sidefrom ) ) ;
}
if ( ! readable )
{
writable = false ;
callable = false ;
writeerror . Format ( " Can't write %s field %s from %s context (not readable) " , StringFromSide ( sideto ) , name , StringFromSide ( sidefrom ) ) ;
callerror . Format ( " Can't call %s function %s from %s context (not readable) " , StringFromSide ( sideto ) , name , StringFromSide ( sidefrom ) ) ;
return ;
}
if ( writable & & ( sidefrom ! = sideto ) ) // only matching types are writable (plain data implicitly takes context type by default, unless overridden)
{
writable = false ;
writeerror . Format ( " Can't write %s field %s from %s context " , StringFromSide ( sideto ) , name , StringFromSide ( sidefrom ) ) ;
}
if ( callable & & ( sidefrom ! = sideto ) & & ! ( flags2 & VARF_ReadOnly ) ) // readonly on methods is used for plain data stuff that can be called from ui/play context.
{
callable = false ;
callerror . Format ( " Can't call %s field %s from %s context " , StringFromSide ( sideto ) , name , StringFromSide ( sidefrom ) ) ;
}
}
} ;
2016-03-01 15:47:10 +00:00
struct FCompileContext
{
2016-11-26 23:18:07 +00:00
FxExpression * ControlStmt = nullptr ;
2016-10-19 17:05:48 +00:00
FxLoopStatement * Loop = nullptr ;
FxCompoundStatement * Block = nullptr ;
2016-08-02 16:50:34 +00:00
PPrototype * ReturnProto ;
2016-10-15 15:40:27 +00:00
PFunction * Function ; // The function that is currently being compiled (or nullptr for constant evaluation.)
2016-11-19 11:12:29 +00:00
PStruct * Class ; // The type of the owning class.
2016-11-06 12:14:46 +00:00
bool FromDecorate ; // DECORATE must silence some warnings and demote some errors.
int StateIndex ; // index in actor's state table for anonymous functions, otherwise -1 (not used by DECORATE which pre-resolves state indices)
int StateCount ; // amount of states an anoymous function is being used on (must be 1 for state indices to be allowed.)
2016-11-08 10:12:56 +00:00
int Lump ;
2016-11-13 11:02:41 +00:00
bool Unsafe = false ;
2016-10-20 14:55:12 +00:00
TDeletingArray < FxLocalVariableDeclaration * > FunctionArgs ;
2017-01-23 18:09:36 +00:00
PNamespace * CurGlobals ;
2016-03-01 15:47:10 +00:00
2017-01-23 18:09:36 +00:00
FCompileContext ( PNamespace * spc , PFunction * func , PPrototype * ret , bool fromdecorate , int stateindex , int statecount , int lump ) ;
FCompileContext ( PNamespace * spc , PStruct * cls , bool fromdecorate ) ; // only to be used to resolve constants!
2016-03-01 15:47:10 +00:00
2016-10-15 15:40:27 +00:00
PSymbol * FindInClass ( FName identifier , PSymbolTable * & symt ) ;
PSymbol * FindInSelfClass ( FName identifier , PSymbolTable * & symt ) ;
2016-07-26 21:57:26 +00:00
PSymbol * FindGlobal ( FName identifier ) ;
void HandleJumps ( int token , FxExpression * handler ) ;
2016-08-02 16:50:34 +00:00
void CheckReturn ( PPrototype * proto , FScriptPosition & pos ) ;
2017-02-17 17:25:29 +00:00
bool CheckWritable ( int flags ) ;
2016-10-20 23:12:54 +00:00
FxLocalVariableDeclaration * FindLocalVariable ( FName name ) ;
2016-03-01 15:47:10 +00:00
} ;
//==========================================================================
//
//
//
//==========================================================================
struct ExpVal
{
PType * Type ;
union
{
int Int ;
double Float ;
void * pointer ;
} ;
ExpVal ( )
{
Type = TypeSInt32 ;
Int = 0 ;
}
~ ExpVal ( )
{
if ( Type = = TypeString )
{
( ( FString * ) & pointer ) - > ~ FString ( ) ;
}
}
ExpVal ( const FString & str )
{
Type = TypeString ;
: : new ( & pointer ) FString ( str ) ;
}
ExpVal ( const ExpVal & o )
{
Type = o . Type ;
if ( o . Type = = TypeString )
{
: : new ( & pointer ) FString ( * ( FString * ) & o . pointer ) ;
}
else
{
memcpy ( & Float , & o . Float , 8 ) ;
}
}
ExpVal & operator = ( const ExpVal & o )
{
if ( Type = = TypeString )
{
( ( FString * ) & pointer ) - > ~ FString ( ) ;
}
Type = o . Type ;
if ( o . Type = = TypeString )
{
: : new ( & pointer ) FString ( * ( FString * ) & o . pointer ) ;
}
else
{
memcpy ( & Float , & o . Float , 8 ) ;
}
return * this ;
}
int GetInt ( ) const
{
int regtype = Type - > GetRegType ( ) ;
return regtype = = REGT_INT ? Int : regtype = = REGT_FLOAT ? int ( Float ) : 0 ;
}
2016-11-18 11:23:58 +00:00
unsigned GetUInt ( ) const
{
int regtype = Type - > GetRegType ( ) ;
return regtype = = REGT_INT ? unsigned ( Int ) : regtype = = REGT_FLOAT ? unsigned ( Float ) : 0 ;
}
2016-03-01 15:47:10 +00:00
double GetFloat ( ) const
{
int regtype = Type - > GetRegType ( ) ;
2016-11-18 11:23:58 +00:00
return regtype = = REGT_INT ? ( Type = = TypeUInt32 ? double ( unsigned ( Int ) ) : double ( Int ) ) : regtype = = REGT_FLOAT ? Float : 0 ;
2016-03-01 15:47:10 +00:00
}
2016-10-19 17:05:48 +00:00
void * GetPointer ( ) const
{
int regtype = Type - > GetRegType ( ) ;
return regtype = = REGT_POINTER ? pointer : nullptr ;
}
2016-03-01 15:47:10 +00:00
const FString GetString ( ) const
{
return Type = = TypeString ? * ( FString * ) & pointer : Type = = TypeName ? FString ( FName ( ENamedName ( Int ) ) . GetChars ( ) ) : " " ;
}
bool GetBool ( ) const
{
int regtype = Type - > GetRegType ( ) ;
return regtype = = REGT_INT ? ! ! Int : regtype = = REGT_FLOAT ? Float ! = 0. : false ;
}
FName GetName ( ) const
{
2016-11-12 09:06:26 +00:00
if ( Type = = TypeString )
{
if ( ( ( FString * ) & pointer ) - > Len ( ) = = 0 ) return NAME_None ;
return FName ( * ( FString * ) & pointer ) ;
}
2016-03-01 15:47:10 +00:00
return Type = = TypeName ? ENamedName ( Int ) : NAME_None ;
}
} ;
2016-10-22 23:14:49 +00:00
enum EFxType
{
EFX_Expression ,
EFX_Identifier ,
EFX_MemberIdentifier ,
EFX_ClassDefaults ,
EFX_Constant ,
EFX_BoolCast ,
EFX_IntCast ,
EFX_FloatCast ,
EFX_NameCast ,
EFX_StringCast ,
EFX_ColorCast ,
EFX_SoundCast ,
EFX_TypeCast ,
EFX_PlusSign ,
EFX_MinusSign ,
EFX_UnaryNotBitwise ,
EFX_UnaryNotBoolean ,
EFX_SizeAlign ,
EFX_PreIncrDecr ,
EFX_PostIncrDecr ,
EFX_Assign ,
EFX_AssignSelf ,
EFX_Binary , // one token fits all, the operator is enough to distinguish them.
EFX_BinaryLogical ,
2016-10-29 08:16:00 +00:00
EFX_DotCross ,
2016-10-22 23:14:49 +00:00
EFX_Conditional ,
EFX_Abs ,
EFX_ATan2 ,
2017-02-03 21:56:03 +00:00
EFX_New ,
2016-10-22 23:14:49 +00:00
EFX_MinMax ,
EFX_Random ,
EFX_RandomPick ,
EFX_FRandom ,
EFX_Random2 ,
EFX_ClassMember ,
2016-10-24 11:18:13 +00:00
EFX_StructMember ,
2016-10-22 23:14:49 +00:00
EFX_LocalVariable ,
EFX_Self ,
EFX_ArrayElement ,
EFX_FunctionCall ,
EFX_MemberFunctionCall ,
EFX_ActionSpecialCall ,
EFX_FlopFunctionCall ,
EFX_VMFunctionCall ,
EFX_Sequence ,
EFX_CompoundStatement ,
EFX_IfStatement ,
EFX_LoopStatement ,
EFX_WhileLoop ,
EFX_DoWhileLoop ,
EFX_ForLoop ,
EFX_JumpStatement ,
EFX_ReturnStatement ,
EFX_ClassTypeCast ,
2016-11-17 19:31:53 +00:00
EFX_ClassPtrCast ,
2016-10-22 23:14:49 +00:00
EFX_StateByIndex ,
EFX_RuntimeStateIndex ,
EFX_MultiNameState ,
EFX_DamageValue ,
EFX_Nop ,
EFX_LocalVariableDeclaration ,
2016-10-23 10:00:25 +00:00
EFX_SwitchStatement ,
EFX_CaseStatement ,
2016-10-30 03:35:01 +00:00
EFX_VectorValue ,
2016-10-29 08:43:22 +00:00
EFX_VectorBuiltin ,
2016-10-29 23:05:56 +00:00
EFX_TypeCheck ,
2016-10-31 16:02:47 +00:00
EFX_DynamicCast ,
2016-11-03 12:38:40 +00:00
EFX_GlobalVariable ,
2016-11-11 20:52:08 +00:00
EFX_Super ,
2016-11-17 15:44:41 +00:00
EFX_StackVariable ,
2016-11-19 23:25:38 +00:00
EFX_MultiAssign ,
2016-11-20 17:00:37 +00:00
EFX_StaticArray ,
EFX_StaticArrayVariable ,
2016-11-20 19:24:39 +00:00
EFX_CVar ,
2016-11-21 00:32:01 +00:00
EFX_NamedNode ,
2016-11-24 19:02:44 +00:00
EFX_GetClass ,
2017-01-15 00:02:38 +00:00
EFX_GetParentClass ,
EFX_StrLen ,
2016-11-26 12:18:48 +00:00
EFX_ColorLiteral ,
2016-11-27 14:50:58 +00:00
EFX_GetDefaultByType ,
2017-02-05 12:14:22 +00:00
EFX_FontCast ,
2016-10-22 23:14:49 +00:00
EFX_COUNT
} ;
2016-03-01 15:47:10 +00:00
//==========================================================================
//
//
//
//==========================================================================
class FxExpression
{
protected :
2016-10-22 23:14:49 +00:00
FxExpression ( EFxType type , const FScriptPosition & pos )
: ScriptPosition ( pos ) , ExprType ( type )
2016-03-01 15:47:10 +00:00
{
}
2016-10-15 22:12:33 +00:00
public :
FxExpression * CheckIntForName ( ) ;
2016-03-01 15:47:10 +00:00
virtual ~ FxExpression ( ) { }
virtual FxExpression * Resolve ( FCompileContext & ctx ) ;
virtual bool isConstant ( ) const ;
2016-11-08 10:12:56 +00:00
virtual bool RequestAddress ( FCompileContext & ctx , bool * writable ) ;
2016-08-02 16:50:34 +00:00
virtual PPrototype * ReturnProto ( ) ;
2016-03-01 15:47:10 +00:00
virtual VMFunction * GetDirectFunction ( ) ;
2016-11-05 17:05:57 +00:00
virtual bool CheckReturn ( ) { return false ; }
2016-11-30 12:36:13 +00:00
virtual int GetBitValue ( ) { return - 1 ; }
2016-11-14 13:12:27 +00:00
bool IsNumeric ( ) const { return ValueType - > isNumeric ( ) ; }
2016-10-29 16:57:56 +00:00
bool IsFloat ( ) const { return ValueType - > GetRegType ( ) = = REGT_FLOAT & & ValueType - > GetRegCount ( ) = = 1 ; }
2016-11-14 13:12:27 +00:00
bool IsInteger ( ) const { return ValueType - > isNumeric ( ) & & ( ValueType - > GetRegType ( ) = = REGT_INT ) ; }
2016-03-01 15:47:10 +00:00
bool IsPointer ( ) const { return ValueType - > GetRegType ( ) = = REGT_POINTER ; }
2016-10-28 23:39:25 +00:00
bool IsVector ( ) const { return ValueType = = TypeVector2 | | ValueType = = TypeVector3 ; } ;
2016-10-29 16:57:56 +00:00
bool IsBoolCompat ( ) const { return ValueType - > GetRegCount ( ) = = 1 & & ( ValueType - > GetRegType ( ) = = REGT_INT | | ValueType - > GetRegType ( ) = = REGT_FLOAT | | ValueType - > GetRegType ( ) = = REGT_POINTER ) ; }
2016-11-24 19:02:44 +00:00
bool IsObject ( ) const { return ValueType - > IsKindOf ( RUNTIME_CLASS ( PPointer ) ) & & ! ValueType - > IsKindOf ( RUNTIME_CLASS ( PClassPointer ) ) & & ValueType ! = TypeNullPtr & & static_cast < PPointer * > ( ValueType ) - > PointedType - > IsKindOf ( RUNTIME_CLASS ( PClass ) ) ; }
2017-01-02 20:40:52 +00:00
bool IsArray ( ) const { return ValueType - > IsKindOf ( RUNTIME_CLASS ( PArray ) ) | | ( ValueType - > IsKindOf ( RUNTIME_CLASS ( PPointer ) ) & & static_cast < PPointer * > ( ValueType ) - > PointedType - > IsKindOf ( RUNTIME_CLASS ( PArray ) ) ) ; }
bool IsResizableArray ( ) const { return ( ValueType - > IsKindOf ( RUNTIME_CLASS ( PPointer ) ) & & static_cast < PPointer * > ( ValueType ) - > PointedType - > IsKindOf ( RUNTIME_CLASS ( PResizableArray ) ) ) ; } // can only exist in pointer form.
2017-02-06 20:39:21 +00:00
bool IsDynamicArray ( ) const { return ( ValueType - > IsKindOf ( RUNTIME_CLASS ( PDynArray ) ) ) ; }
2016-03-01 15:47:10 +00:00
virtual ExpEmit Emit ( VMFunctionBuilder * build ) ;
2016-12-02 16:36:29 +00:00
void EmitStatement ( VMFunctionBuilder * build ) ;
2016-12-01 23:51:29 +00:00
virtual void EmitCompare ( VMFunctionBuilder * build , bool invert , TArray < size_t > & patchspots_yes , TArray < size_t > & patchspots_no ) ;
2016-03-01 15:47:10 +00:00
FScriptPosition ScriptPosition ;
2016-10-15 08:34:26 +00:00
PType * ValueType = nullptr ;
2016-03-01 15:47:10 +00:00
2016-10-15 08:34:26 +00:00
bool isresolved = false ;
2016-10-26 09:30:30 +00:00
bool NeedResult = true ; // should be set to false if not needed and properly handled by all nodes for their subnodes to eliminate redundant code
2016-10-22 23:14:49 +00:00
EFxType ExprType ;
2016-11-10 14:13:31 +00:00
void * operator new ( size_t size )
{
return FxAlloc . Alloc ( size ) ;
}
void operator delete ( void * block ) { }
void operator delete [ ] ( void * block ) { }
2016-03-01 15:47:10 +00:00
} ;
//==========================================================================
//
// FxIdentifier
//
//==========================================================================
class FxIdentifier : public FxExpression
{
2016-10-31 16:02:47 +00:00
public :
2016-03-01 15:47:10 +00:00
FName Identifier ;
2016-11-19 23:25:38 +00:00
bool noglobal = false ;
2016-03-01 15:47:10 +00:00
FxIdentifier ( FName i , const FScriptPosition & p ) ;
FxExpression * Resolve ( FCompileContext & ) ;
2016-11-19 11:12:29 +00:00
FxExpression * ResolveMember ( FCompileContext & , PStruct * , FxExpression * & , PStruct * ) ;
2016-03-01 15:47:10 +00:00
} ;
2016-10-21 15:41:39 +00:00
//==========================================================================
//
2016-11-13 08:34:05 +00:00
// FxMemberIdentifier
2016-10-21 15:41:39 +00:00
//
//==========================================================================
class FxMemberIdentifier : public FxIdentifier
{
FxExpression * Object ;
public :
FxMemberIdentifier ( FxExpression * obj , FName i , const FScriptPosition & p ) ;
2016-11-10 14:13:31 +00:00
~ FxMemberIdentifier ( ) ;
2016-10-21 15:41:39 +00:00
FxExpression * Resolve ( FCompileContext & ) ;
} ;
2016-03-01 15:47:10 +00:00
//==========================================================================
//
// FxClassDefaults
//
//==========================================================================
class FxClassDefaults : public FxExpression
{
FxExpression * obj ;
2016-11-05 16:14:16 +00:00
bool EmitTail ;
2016-03-01 15:47:10 +00:00
public :
2016-11-05 16:14:16 +00:00
FxClassDefaults ( FxExpression * , const FScriptPosition & ) ;
2016-03-01 15:47:10 +00:00
~ FxClassDefaults ( ) ;
2016-11-05 16:14:16 +00:00
PPrototype * ReturnProto ( ) ;
2016-03-01 15:47:10 +00:00
FxExpression * Resolve ( FCompileContext & ) ;
2016-11-05 16:14:16 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
2016-03-01 15:47:10 +00:00
} ;
//==========================================================================
//
// FxConstant
//
//==========================================================================
class FxConstant : public FxExpression
{
ExpVal value ;
public :
2016-10-22 23:14:49 +00:00
FxConstant ( bool val , const FScriptPosition & pos ) : FxExpression ( EFX_Constant , pos )
2016-07-04 00:19:52 +00:00
{
ValueType = value . Type = TypeBool ;
value . Int = val ;
isresolved = true ;
}
2016-10-22 23:14:49 +00:00
FxConstant ( int val , const FScriptPosition & pos ) : FxExpression ( EFX_Constant , pos )
2016-03-01 15:47:10 +00:00
{
ValueType = value . Type = TypeSInt32 ;
value . Int = val ;
isresolved = true ;
}
2017-01-02 20:40:52 +00:00
FxConstant ( unsigned int val , const FScriptPosition & pos ) : FxExpression ( EFX_Constant , pos )
{
ValueType = value . Type = TypeUInt32 ;
value . Int = val ;
isresolved = true ;
}
2016-10-22 23:14:49 +00:00
FxConstant ( double val , const FScriptPosition & pos ) : FxExpression ( EFX_Constant , pos )
2016-03-01 15:47:10 +00:00
{
ValueType = value . Type = TypeFloat64 ;
value . Float = val ;
isresolved = true ;
}
2016-10-22 23:14:49 +00:00
FxConstant ( FSoundID val , const FScriptPosition & pos ) : FxExpression ( EFX_Constant , pos )
2016-03-01 15:47:10 +00:00
{
ValueType = value . Type = TypeSound ;
value . Int = val ;
isresolved = true ;
}
2016-10-22 23:14:49 +00:00
FxConstant ( FName val , const FScriptPosition & pos ) : FxExpression ( EFX_Constant , pos )
2016-03-01 15:47:10 +00:00
{
ValueType = value . Type = TypeName ;
value . Int = val ;
isresolved = true ;
}
2016-10-22 23:14:49 +00:00
FxConstant ( const FString & str , const FScriptPosition & pos ) : FxExpression ( EFX_Constant , pos )
2016-03-01 15:47:10 +00:00
{
ValueType = TypeString ;
value = ExpVal ( str ) ;
isresolved = true ;
}
2016-10-22 23:14:49 +00:00
FxConstant ( ExpVal cv , const FScriptPosition & pos ) : FxExpression ( EFX_Constant , pos )
2016-03-01 15:47:10 +00:00
{
value = cv ;
ValueType = cv . Type ;
isresolved = true ;
}
2016-10-22 23:14:49 +00:00
FxConstant ( PClass * val , PClassPointer * valtype , const FScriptPosition & pos ) : FxExpression ( EFX_Constant , pos )
2016-03-01 15:47:10 +00:00
{
value . pointer = ( void * ) val ;
2016-10-22 17:51:24 +00:00
value . Type = ValueType = valtype ;
2016-03-01 15:47:10 +00:00
isresolved = true ;
}
2016-10-22 23:14:49 +00:00
FxConstant ( FState * state , const FScriptPosition & pos ) : FxExpression ( EFX_Constant , pos )
2016-03-01 15:47:10 +00:00
{
value . pointer = state ;
ValueType = value . Type = TypeState ;
isresolved = true ;
}
2016-10-21 17:18:39 +00:00
2017-02-05 12:14:22 +00:00
FxConstant ( FFont * state , const FScriptPosition & pos ) : FxExpression ( EFX_Constant , pos )
{
value . pointer = state ;
ValueType = value . Type = TypeFont ;
isresolved = true ;
}
2016-10-22 23:14:49 +00:00
FxConstant ( const FScriptPosition & pos ) : FxExpression ( EFX_Constant , pos )
2016-10-21 17:18:39 +00:00
{
value . pointer = nullptr ;
ValueType = value . Type = TypeNullPtr ;
isresolved = true ;
}
2016-11-21 00:32:01 +00:00
FxConstant ( PType * type , VMValue & vmval , const FScriptPosition & pos ) : FxExpression ( EFX_Constant , pos )
{
ValueType = value . Type = type ;
isresolved = true ;
switch ( vmval . Type )
{
default :
case REGT_INT :
value . Int = vmval . i ;
break ;
case REGT_FLOAT :
value . Float = vmval . f ;
break ;
case REGT_STRING :
value = ExpVal ( vmval . s ( ) ) ;
break ;
case REGT_POINTER :
value . pointer = vmval . a ;
break ;
}
}
2016-03-01 15:47:10 +00:00
static FxExpression * MakeConstant ( PSymbol * sym , const FScriptPosition & pos ) ;
bool isConstant ( ) const
{
return true ;
}
ExpVal GetValue ( ) const
{
return value ;
}
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-10-28 13:15:30 +00:00
//==========================================================================
//
//
//
//==========================================================================
2016-10-30 03:35:01 +00:00
class FxVectorValue : public FxExpression
2016-10-28 13:15:30 +00:00
{
FxExpression * xyz [ 3 ] ;
2016-10-30 08:05:42 +00:00
bool isConst ; // gets set to true if all element are const (used by function defaults parser)
2016-10-28 13:15:30 +00:00
public :
2016-10-30 08:05:42 +00:00
friend class ZCCCompiler ;
2016-10-30 03:35:01 +00:00
FxVectorValue ( FxExpression * x , FxExpression * y , FxExpression * z , const FScriptPosition & sc ) ;
~ FxVectorValue ( ) ;
2016-10-28 13:15:30 +00:00
FxExpression * Resolve ( FCompileContext & ) ;
2016-10-30 08:05:42 +00:00
bool isConstVector ( int dim )
{
if ( ! isConst ) return false ;
return dim = = 2 ? xyz [ 2 ] = = nullptr : xyz [ 2 ] ! = nullptr ;
}
2016-10-28 13:15:30 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-03-01 15:47:10 +00:00
//==========================================================================
//
//
//
//==========================================================================
2016-07-04 00:19:52 +00:00
class FxBoolCast : public FxExpression
2016-03-01 15:47:10 +00:00
{
FxExpression * basex ;
2016-10-23 13:30:58 +00:00
bool NeedValue ;
2016-03-01 15:47:10 +00:00
public :
2016-10-23 13:30:58 +00:00
FxBoolCast ( FxExpression * x , bool needvalue = true ) ;
2016-07-04 00:19:52 +00:00
~ FxBoolCast ( ) ;
2016-03-01 15:47:10 +00:00
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
2016-12-01 23:51:29 +00:00
void EmitCompare ( VMFunctionBuilder * build , bool invert , TArray < size_t > & patchspots_yes , TArray < size_t > & patchspots_no ) ;
2016-03-01 15:47:10 +00:00
} ;
2016-07-04 00:19:52 +00:00
class FxIntCast : public FxExpression
2016-03-01 15:47:10 +00:00
{
FxExpression * basex ;
2016-10-15 19:35:31 +00:00
bool NoWarn ;
2016-10-27 13:53:53 +00:00
bool Explicit ;
2016-03-01 15:47:10 +00:00
public :
2016-10-27 13:53:53 +00:00
FxIntCast ( FxExpression * x , bool nowarn , bool explicitly = false ) ;
2016-07-04 00:19:52 +00:00
~ FxIntCast ( ) ;
2016-03-01 15:47:10 +00:00
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-07-04 00:19:52 +00:00
class FxFloatCast : public FxExpression
2016-03-01 15:47:10 +00:00
{
FxExpression * basex ;
public :
2016-07-04 00:19:52 +00:00
FxFloatCast ( FxExpression * x ) ;
~ FxFloatCast ( ) ;
2016-03-01 15:47:10 +00:00
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-10-16 17:42:22 +00:00
class FxNameCast : public FxExpression
{
FxExpression * basex ;
2017-01-14 01:05:52 +00:00
bool mExplicit ;
2016-10-16 17:42:22 +00:00
public :
2017-01-14 01:05:52 +00:00
FxNameCast ( FxExpression * x , bool explicitly = false ) ;
2016-10-16 17:42:22 +00:00
~ FxNameCast ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
class FxStringCast : public FxExpression
{
FxExpression * basex ;
public :
FxStringCast ( FxExpression * x ) ;
~ FxStringCast ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
class FxColorCast : public FxExpression
{
FxExpression * basex ;
public :
FxColorCast ( FxExpression * x ) ;
~ FxColorCast ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
class FxSoundCast : public FxExpression
{
FxExpression * basex ;
public :
FxSoundCast ( FxExpression * x ) ;
~ FxSoundCast ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2017-02-05 12:14:22 +00:00
class FxFontCast : public FxExpression
{
FxExpression * basex ;
public :
FxFontCast ( FxExpression * x ) ;
~ FxFontCast ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
} ;
2016-10-16 17:42:22 +00:00
//==========================================================================
//
// FxTypeCast
//
//==========================================================================
class FxTypeCast : public FxExpression
{
FxExpression * basex ;
bool NoWarn ;
2016-10-27 13:53:53 +00:00
bool Explicit ;
2016-10-16 17:42:22 +00:00
public :
2016-10-27 13:53:53 +00:00
FxTypeCast ( FxExpression * x , PType * type , bool nowarn , bool explicitly = false ) ;
2016-10-16 17:42:22 +00:00
~ FxTypeCast ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-03-01 15:47:10 +00:00
//==========================================================================
//
// FxSign
//
//==========================================================================
class FxPlusSign : public FxExpression
{
FxExpression * Operand ;
public :
FxPlusSign ( FxExpression * ) ;
~ FxPlusSign ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
//==========================================================================
//
// FxSign
//
//==========================================================================
class FxMinusSign : public FxExpression
{
FxExpression * Operand ;
public :
FxMinusSign ( FxExpression * ) ;
~ FxMinusSign ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
//==========================================================================
//
// FxUnaryNot
//
//==========================================================================
class FxUnaryNotBitwise : public FxExpression
{
FxExpression * Operand ;
public :
FxUnaryNotBitwise ( FxExpression * ) ;
~ FxUnaryNotBitwise ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
//==========================================================================
//
// FxUnaryNot
//
//==========================================================================
class FxUnaryNotBoolean : public FxExpression
{
FxExpression * Operand ;
public :
FxUnaryNotBoolean ( FxExpression * ) ;
~ FxUnaryNotBoolean ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
2016-12-01 23:51:29 +00:00
void EmitCompare ( VMFunctionBuilder * build , bool invert , TArray < size_t > & patchspots_yes , TArray < size_t > & patchspots_no ) ;
2016-03-01 15:47:10 +00:00
} ;
2016-10-17 18:33:35 +00:00
//==========================================================================
//
// FxSign
//
//==========================================================================
class FxSizeAlign : public FxExpression
{
FxExpression * Operand ;
int Which ;
public :
FxSizeAlign ( FxExpression * , int which ) ;
~ FxSizeAlign ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-08-05 15:33:29 +00:00
//==========================================================================
//
// FxPreIncrDecr
//
//==========================================================================
class FxPreIncrDecr : public FxExpression
{
int Token ;
FxExpression * Base ;
bool AddressRequested ;
bool AddressWritable ;
public :
FxPreIncrDecr ( FxExpression * base , int token ) ;
~ FxPreIncrDecr ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
2016-11-08 10:12:56 +00:00
bool RequestAddress ( FCompileContext & ctx , bool * writable ) ;
2016-08-05 15:33:29 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
//==========================================================================
//
// FxPostIncrDecr
//
//==========================================================================
class FxPostIncrDecr : public FxExpression
{
int Token ;
FxExpression * Base ;
public :
FxPostIncrDecr ( FxExpression * base , int token ) ;
~ FxPostIncrDecr ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-03-01 15:47:10 +00:00
//==========================================================================
2016-07-31 22:32:02 +00:00
//
// FxAssign
//
//==========================================================================
class FxAssign : public FxExpression
{
FxExpression * Base ;
FxExpression * Right ;
2016-10-24 15:18:20 +00:00
int IsBitWrite ;
2016-07-31 22:32:02 +00:00
bool AddressRequested ;
bool AddressWritable ;
2016-10-24 15:18:20 +00:00
bool IsModifyAssign ;
friend class FxAssignSelf ;
2016-07-31 22:32:02 +00:00
public :
2016-10-24 15:18:20 +00:00
FxAssign ( FxExpression * base , FxExpression * right , bool ismodify = false ) ;
2016-07-31 22:32:02 +00:00
~ FxAssign ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
2016-11-08 10:12:56 +00:00
//bool RequestAddress(FCompileContext &ctx, bool *writable);
2016-07-31 22:32:02 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
2016-08-01 01:32:02 +00:00
ExpEmit Address ;
} ;
2016-11-19 23:25:38 +00:00
//==========================================================================
//
// FxAssign
//
//==========================================================================
class FxCompoundStatement ;
class FxMultiAssign : public FxExpression
{
FxCompoundStatement * LocalVarContainer ; // for handling the temporary variables of the results, which may need type casts.
FArgumentList Base ;
FxExpression * Right ;
bool AddressRequested = false ;
bool AddressWritable = false ;
public :
FxMultiAssign ( FArgumentList & base , FxExpression * right , const FScriptPosition & pos ) ;
~ FxMultiAssign ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-08-01 01:32:02 +00:00
//==========================================================================
//
// FxAssignSelf
//
//==========================================================================
class FxAssignSelf : public FxExpression
{
public :
FxAssign * Assignment ;
FxAssignSelf ( const FScriptPosition & pos ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
2016-07-31 22:32:02 +00:00
} ;
//==========================================================================
2016-03-01 15:47:10 +00:00
//
// FxBinary
//
//==========================================================================
class FxBinary : public FxExpression
{
public :
int Operator ;
FxExpression * left ;
FxExpression * right ;
FxBinary ( int , FxExpression * , FxExpression * ) ;
~ FxBinary ( ) ;
2016-11-18 13:19:55 +00:00
bool Promote ( FCompileContext & ctx , bool forceint = false ) ;
2016-03-01 15:47:10 +00:00
} ;
//==========================================================================
//
// FxBinary
//
//==========================================================================
class FxAddSub : public FxBinary
{
public :
FxAddSub ( int , FxExpression * , FxExpression * ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
//==========================================================================
//
// FxBinary
//
//==========================================================================
class FxMulDiv : public FxBinary
{
public :
FxMulDiv ( int , FxExpression * , FxExpression * ) ;
2016-10-17 13:17:48 +00:00
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
//==========================================================================
//
// FxBinary
//
//==========================================================================
class FxPow : public FxBinary
{
public :
FxPow ( FxExpression * , FxExpression * ) ;
2016-03-01 15:47:10 +00:00
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
//==========================================================================
//
// FxBinary
//
//==========================================================================
class FxCompareRel : public FxBinary
{
2016-11-18 11:23:58 +00:00
PType * CompareType ;
2016-03-01 15:47:10 +00:00
public :
FxCompareRel ( int , FxExpression * , FxExpression * ) ;
FxExpression * Resolve ( FCompileContext & ) ;
2016-12-01 23:51:29 +00:00
ExpEmit EmitCommon ( VMFunctionBuilder * build , bool forcompare , bool invert ) ;
2016-03-01 15:47:10 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
2016-12-01 23:51:29 +00:00
void EmitCompare ( VMFunctionBuilder * build , bool invert , TArray < size_t > & patchspots_yes , TArray < size_t > & patchspots_no ) ;
2016-03-01 15:47:10 +00:00
} ;
//==========================================================================
//
// FxBinary
//
//==========================================================================
class FxCompareEq : public FxBinary
{
public :
FxCompareEq ( int , FxExpression * , FxExpression * ) ;
FxExpression * Resolve ( FCompileContext & ) ;
2016-12-01 23:51:29 +00:00
ExpEmit EmitCommon ( VMFunctionBuilder * build , bool forcompare , bool invert ) ;
2016-03-01 15:47:10 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
2016-12-01 23:51:29 +00:00
void EmitCompare ( VMFunctionBuilder * build , bool invert , TArray < size_t > & patchspots_yes , TArray < size_t > & patchspots_no ) ;
2016-03-01 15:47:10 +00:00
} ;
//==========================================================================
//
// FxBinary
//
//==========================================================================
2016-11-18 13:19:55 +00:00
class FxBitOp : public FxBinary
2016-03-01 15:47:10 +00:00
{
public :
2016-11-18 13:19:55 +00:00
FxBitOp ( int , FxExpression * , FxExpression * ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
//==========================================================================
//
// FxBinary
//
//==========================================================================
class FxShift : public FxBinary
{
public :
FxShift ( int , FxExpression * , FxExpression * ) ;
2016-03-01 15:47:10 +00:00
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-10-21 14:35:07 +00:00
//==========================================================================
//
//
//
//==========================================================================
class FxLtGtEq : public FxBinary
{
public :
FxLtGtEq ( FxExpression * , FxExpression * ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-11-18 16:44:25 +00:00
//==========================================================================
//
//
//
//==========================================================================
class FxConcat : public FxBinary
{
public :
FxConcat ( FxExpression * , FxExpression * ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-03-01 15:47:10 +00:00
//==========================================================================
//
// FxBinaryLogical
//
//==========================================================================
class FxBinaryLogical : public FxExpression
{
public :
int Operator ;
FxExpression * left ;
FxExpression * right ;
2016-11-02 14:46:15 +00:00
TDeletingArray < FxExpression * > list ;
2016-03-01 15:47:10 +00:00
FxBinaryLogical ( int , FxExpression * , FxExpression * ) ;
~ FxBinaryLogical ( ) ;
2016-11-02 14:46:15 +00:00
void Flatten ( ) ;
2016-03-01 15:47:10 +00:00
FxExpression * Resolve ( FCompileContext & ) ;
2016-10-29 08:16:00 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
//==========================================================================
//
// FxBinaryLogical
//
//==========================================================================
class FxDotCross : public FxExpression
{
public :
int Operator ;
FxExpression * left ;
FxExpression * right ;
FxDotCross ( int , FxExpression * , FxExpression * ) ;
~ FxDotCross ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
2016-03-01 15:47:10 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-10-29 23:05:56 +00:00
//==========================================================================
//
2016-10-31 16:02:47 +00:00
//
2016-10-29 23:05:56 +00:00
//
//==========================================================================
class FxTypeCheck : public FxExpression
{
public :
FxExpression * left ;
FxExpression * right ;
2017-01-17 16:31:54 +00:00
bool ClassCheck ;
2016-10-29 23:05:56 +00:00
FxTypeCheck ( FxExpression * , FxExpression * ) ;
~ FxTypeCheck ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
2016-12-05 13:52:34 +00:00
ExpEmit EmitCommon ( VMFunctionBuilder * build ) ;
2016-10-29 23:05:56 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
2016-12-05 13:52:34 +00:00
void EmitCompare ( VMFunctionBuilder * build , bool invert , TArray < size_t > & patchspots_yes , TArray < size_t > & patchspots_no ) ;
2016-10-29 23:05:56 +00:00
} ;
2016-10-31 16:02:47 +00:00
//==========================================================================
//
//
//
//==========================================================================
class FxDynamicCast : public FxExpression
{
PClass * CastType ;
public :
FxExpression * expr ;
FxDynamicCast ( PClass * , FxExpression * ) ;
~ FxDynamicCast ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-03-01 15:47:10 +00:00
//==========================================================================
//
// FxConditional
//
//==========================================================================
class FxConditional : public FxExpression
{
public :
FxExpression * condition ;
FxExpression * truex ;
FxExpression * falsex ;
FxConditional ( FxExpression * , FxExpression * , FxExpression * ) ;
~ FxConditional ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
//==========================================================================
//
//
//
//==========================================================================
class FxAbs : public FxExpression
{
FxExpression * val ;
public :
FxAbs ( FxExpression * v ) ;
~ FxAbs ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
//==========================================================================
//
//
//
//==========================================================================
2016-04-19 04:06:17 +00:00
class FxATan2 : public FxExpression
{
FxExpression * yval , * xval ;
public :
FxATan2 ( FxExpression * y , FxExpression * x , const FScriptPosition & pos ) ;
~ FxATan2 ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
private :
ExpEmit ToReg ( VMFunctionBuilder * build , FxExpression * val ) ;
} ;
2017-02-03 21:56:03 +00:00
//==========================================================================
//
//
//
//==========================================================================
class FxNew : public FxExpression
{
FxExpression * val ;
2017-02-16 02:14:21 +00:00
PFunction * CallingFunction ;
2017-02-03 21:56:03 +00:00
public :
FxNew ( FxExpression * v ) ;
~ FxNew ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-04-19 04:06:17 +00:00
//==========================================================================
//
//
//
//==========================================================================
2016-03-01 15:47:10 +00:00
class FxMinMax : public FxExpression
{
TDeletingArray < FxExpression * > choices ;
FName Type ;
public :
FxMinMax ( TArray < FxExpression * > & expr , FName type , const FScriptPosition & pos ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
//==========================================================================
//
//
//
//==========================================================================
class FxRandom : public FxExpression
{
protected :
2016-08-02 16:50:34 +00:00
bool EmitTail ;
2016-03-01 15:47:10 +00:00
FRandom * rng ;
FxExpression * min , * max ;
public :
2016-10-15 19:35:31 +00:00
FxRandom ( FRandom * , FxExpression * mi , FxExpression * ma , const FScriptPosition & pos , bool nowarn ) ;
2016-03-01 15:47:10 +00:00
~ FxRandom ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
2016-08-02 16:50:34 +00:00
PPrototype * ReturnProto ( ) ;
2016-03-01 15:47:10 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
//==========================================================================
//
//
//
//==========================================================================
class FxRandomPick : public FxExpression
{
protected :
FRandom * rng ;
TDeletingArray < FxExpression * > choices ;
public :
2016-10-15 19:35:31 +00:00
FxRandomPick ( FRandom * , TArray < FxExpression * > & expr , bool floaty , const FScriptPosition & pos , bool nowarn ) ;
2016-03-01 15:47:10 +00:00
~ FxRandomPick ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
//==========================================================================
//
//
//
//==========================================================================
class FxFRandom : public FxRandom
{
public :
FxFRandom ( FRandom * , FxExpression * mi , FxExpression * ma , const FScriptPosition & pos ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
//==========================================================================
//
//
//
//==========================================================================
class FxRandom2 : public FxExpression
{
2016-08-02 16:50:34 +00:00
bool EmitTail ;
2016-03-01 15:47:10 +00:00
FRandom * rng ;
FxExpression * mask ;
public :
2016-10-15 19:35:31 +00:00
FxRandom2 ( FRandom * , FxExpression * m , const FScriptPosition & pos , bool nowarn ) ;
2016-03-01 15:47:10 +00:00
~ FxRandom2 ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
2016-08-02 16:50:34 +00:00
PPrototype * ReturnProto ( ) ;
2016-03-01 15:47:10 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-11-03 12:38:40 +00:00
//==========================================================================
//
2017-02-06 21:57:42 +00:00
// FxMemberBase
2016-11-03 12:38:40 +00:00
//
//==========================================================================
2017-02-06 21:57:42 +00:00
class FxMemberBase : public FxExpression
2016-11-03 12:38:40 +00:00
{
public :
PField * membervar ;
2017-02-06 21:57:42 +00:00
bool AddressRequested = false ;
bool AddressWritable = true ;
2017-02-17 20:41:04 +00:00
int BarrierSide = - 1 ; // [ZZ] some magic
2017-02-06 21:57:42 +00:00
FxMemberBase ( EFxType type , PField * f , const FScriptPosition & p ) ;
} ;
//==========================================================================
//
// FxGlobalVariab<61> e
//
//==========================================================================
2016-11-03 12:38:40 +00:00
2017-02-06 21:57:42 +00:00
class FxGlobalVariable : public FxMemberBase
{
public :
2016-11-03 12:38:40 +00:00
FxGlobalVariable ( PField * , const FScriptPosition & ) ;
FxExpression * Resolve ( FCompileContext & ) ;
2016-11-08 10:12:56 +00:00
bool RequestAddress ( FCompileContext & ctx , bool * writable ) ;
2016-11-03 12:38:40 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
2016-11-30 12:36:13 +00:00
virtual int GetBitValue ( ) { return membervar - > BitValue ; }
2016-11-03 12:38:40 +00:00
} ;
2016-11-20 19:24:39 +00:00
class FxCVar : public FxExpression
{
FBaseCVar * CVar ;
public :
FxCVar ( FBaseCVar * , const FScriptPosition & ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2017-02-06 21:57:42 +00:00
2016-03-01 15:47:10 +00:00
//==========================================================================
//
// FxClassMember
//
//==========================================================================
2017-02-06 21:57:42 +00:00
class FxStructMember : public FxMemberBase
2016-03-01 15:47:10 +00:00
{
public :
FxExpression * classx ;
2016-10-24 11:18:13 +00:00
FxStructMember ( FxExpression * , PField * , const FScriptPosition & ) ;
~ FxStructMember ( ) ;
2016-03-01 15:47:10 +00:00
FxExpression * Resolve ( FCompileContext & ) ;
2016-11-08 10:12:56 +00:00
bool RequestAddress ( FCompileContext & ctx , bool * writable ) ;
2016-03-01 15:47:10 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
2016-11-30 12:36:13 +00:00
virtual int GetBitValue ( ) { return membervar - > BitValue ; }
2016-03-01 15:47:10 +00:00
} ;
2016-10-24 11:18:13 +00:00
//==========================================================================
//
// FxClassMember
//
//==========================================================================
class FxClassMember : public FxStructMember
{
public :
FxClassMember ( FxExpression * , PField * , const FScriptPosition & ) ;
} ;
2016-10-20 23:12:54 +00:00
//==========================================================================
//
// FxLocalVariable
//
//==========================================================================
class FxLocalVariable : public FxExpression
{
public :
FxLocalVariableDeclaration * Variable ;
bool AddressRequested ;
2016-10-28 23:39:25 +00:00
int RegOffset ;
2016-10-20 23:12:54 +00:00
FxLocalVariable ( FxLocalVariableDeclaration * , const FScriptPosition & ) ;
FxExpression * Resolve ( FCompileContext & ) ;
2016-11-08 10:12:56 +00:00
bool RequestAddress ( FCompileContext & ctx , bool * writable ) ;
2016-10-20 23:12:54 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-11-17 15:44:41 +00:00
//==========================================================================
//
// FxLocalVariable
//
//==========================================================================
2017-02-06 21:57:42 +00:00
class FxStackVariable : public FxMemberBase
2016-11-17 15:44:41 +00:00
{
public :
FxStackVariable ( PType * type , int offset , const FScriptPosition & ) ;
~ FxStackVariable ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
bool RequestAddress ( FCompileContext & ctx , bool * writable ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
2016-11-30 12:36:13 +00:00
virtual int GetBitValue ( ) { return membervar - > BitValue ; }
2016-11-17 15:44:41 +00:00
} ;
2016-11-20 17:00:37 +00:00
//==========================================================================
//
// FxLocalVariable
//
//==========================================================================
class FxStaticArray ;
class FxStaticArrayVariable : public FxExpression
{
public :
FxStaticArray * Variable ;
bool AddressRequested ;
FxStaticArrayVariable ( FxLocalVariableDeclaration * , const FScriptPosition & ) ;
FxExpression * Resolve ( FCompileContext & ) ;
bool RequestAddress ( FCompileContext & ctx , bool * writable ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-03-01 15:47:10 +00:00
//==========================================================================
//
// FxSelf
//
//==========================================================================
class FxSelf : public FxExpression
{
2016-11-13 08:34:05 +00:00
bool check ;
2016-03-01 15:47:10 +00:00
public :
2016-11-13 08:34:05 +00:00
FxSelf ( const FScriptPosition & , bool deccheck = false ) ;
2016-03-01 15:47:10 +00:00
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-11-11 20:52:08 +00:00
//==========================================================================
//
// FxSuper
//
//==========================================================================
class FxSuper : public FxSelf
{
public :
FxSuper ( const FScriptPosition & pos )
: FxSelf ( pos )
{
ExprType = EFX_Super ;
}
FxExpression * Resolve ( FCompileContext & ) ;
} ;
2016-03-01 15:47:10 +00:00
//==========================================================================
//
// FxArrayElement
//
//==========================================================================
class FxArrayElement : public FxExpression
{
public :
FxExpression * Array ;
FxExpression * index ;
2017-01-14 17:04:49 +00:00
size_t SizeAddr ;
2016-08-05 15:33:29 +00:00
bool AddressRequested ;
bool AddressWritable ;
2016-11-27 17:52:24 +00:00
bool arrayispointer = false ;
2016-03-01 15:47:10 +00:00
FxArrayElement ( FxExpression * , FxExpression * ) ;
~ FxArrayElement ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
2016-11-08 10:12:56 +00:00
bool RequestAddress ( FCompileContext & ctx , bool * writable ) ;
2016-03-01 15:47:10 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
//==========================================================================
//
// FxFunctionCall
//
//==========================================================================
class FxFunctionCall : public FxExpression
{
FName MethodName ;
2016-10-15 23:08:02 +00:00
FRandom * RNG ;
2016-11-10 14:13:31 +00:00
FArgumentList ArgList ;
2016-03-01 15:47:10 +00:00
public :
2016-11-10 14:13:31 +00:00
FxFunctionCall ( FName methodname , FName rngname , FArgumentList & args , const FScriptPosition & pos ) ;
2016-03-01 15:47:10 +00:00
~ FxFunctionCall ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
} ;
2016-10-22 10:10:19 +00:00
//==========================================================================
//
// FxFunctionCall
//
//==========================================================================
class FxMemberFunctionCall : public FxExpression
{
FxExpression * Self ;
FName MethodName ;
2016-11-10 14:13:31 +00:00
FArgumentList ArgList ;
2016-10-22 10:10:19 +00:00
public :
2016-11-10 14:13:31 +00:00
FxMemberFunctionCall ( FxExpression * self , FName methodname , FArgumentList & args , const FScriptPosition & pos ) ;
2016-10-22 10:10:19 +00:00
~ FxMemberFunctionCall ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
} ;
2016-03-01 15:47:10 +00:00
//==========================================================================
//
// FxActionSpecialCall
//
//==========================================================================
class FxActionSpecialCall : public FxExpression
{
int Special ;
2016-08-02 16:50:34 +00:00
bool EmitTail ;
FxExpression * Self ;
2016-11-10 14:13:31 +00:00
FArgumentList ArgList ;
2016-03-01 15:47:10 +00:00
public :
2016-11-10 14:13:31 +00:00
FxActionSpecialCall ( FxExpression * self , int special , FArgumentList & args , const FScriptPosition & pos ) ;
2016-03-01 15:47:10 +00:00
~ FxActionSpecialCall ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
2016-08-02 16:50:34 +00:00
PPrototype * ReturnProto ( ) ;
2016-03-01 15:47:10 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
//==========================================================================
//
// FxFlopFunctionCall
//
//==========================================================================
class FxFlopFunctionCall : public FxExpression
{
int Index ;
2016-11-10 14:13:31 +00:00
FArgumentList ArgList ;
2016-03-01 15:47:10 +00:00
public :
2016-11-10 14:13:31 +00:00
FxFlopFunctionCall ( size_t index , FArgumentList & args , const FScriptPosition & pos ) ;
2016-03-01 15:47:10 +00:00
~ FxFlopFunctionCall ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2017-01-13 19:44:34 +00:00
//==========================================================================
//
// FxVectorBuiltin
2016-10-29 08:43:22 +00:00
//
//==========================================================================
class FxVectorBuiltin : public FxExpression
{
FName Function ;
FxExpression * Self ;
public :
FxVectorBuiltin ( FxExpression * self , FName name ) ;
~ FxVectorBuiltin ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2017-01-15 00:02:38 +00:00
//==========================================================================
//
// FxVectorBuiltin
//
//==========================================================================
class FxStrLen : public FxExpression
{
FxExpression * Self ;
public :
FxStrLen ( FxExpression * self ) ;
~ FxStrLen ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-11-24 19:02:44 +00:00
//==========================================================================
//
2017-01-13 19:44:34 +00:00
// FxGetClass
2016-11-24 19:02:44 +00:00
//
//==========================================================================
class FxGetClass : public FxExpression
{
FxExpression * Self ;
public :
FxGetClass ( FxExpression * self ) ;
~ FxGetClass ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-11-27 14:50:58 +00:00
//==========================================================================
2017-01-14 22:34:47 +00:00
//
// FxGetClass
//
//==========================================================================
class FxGetParentClass : public FxExpression
{
FxExpression * Self ;
public :
FxGetParentClass ( FxExpression * self ) ;
~ FxGetParentClass ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
//==========================================================================
2016-11-27 14:50:58 +00:00
//
2017-01-13 19:44:34 +00:00
// FxGetDefaultByType
2016-11-27 14:50:58 +00:00
//
//==========================================================================
class FxGetDefaultByType : public FxExpression
{
FxExpression * Self ;
public :
FxGetDefaultByType ( FxExpression * self ) ;
~ FxGetDefaultByType ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-11-26 12:18:48 +00:00
//==========================================================================
//
// FxColorLiteral
//
//==========================================================================
class FxColorLiteral : public FxExpression
{
FArgumentList ArgList ;
int constval = 0 ;
public :
FxColorLiteral ( FArgumentList & args , FScriptPosition & sc ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-03-01 15:47:10 +00:00
//==========================================================================
//
// FxVMFunctionCall
//
//==========================================================================
class FxVMFunctionCall : public FxExpression
{
2016-11-19 23:25:38 +00:00
friend class FxMultiAssign ;
2016-08-02 16:50:34 +00:00
bool EmitTail ;
2016-10-22 10:10:19 +00:00
bool NoVirtual ;
FxExpression * Self ;
2016-03-01 15:47:10 +00:00
PFunction * Function ;
2016-11-10 14:13:31 +00:00
FArgumentList ArgList ;
2016-11-19 23:25:38 +00:00
// for multi assignment
int AssignCount = 0 ;
TArray < ExpEmit > ReturnRegs ;
2016-03-01 15:47:10 +00:00
public :
2016-11-10 14:13:31 +00:00
FxVMFunctionCall ( FxExpression * self , PFunction * func , FArgumentList & args , const FScriptPosition & pos , bool novirtual ) ;
2016-03-01 15:47:10 +00:00
~ FxVMFunctionCall ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
2016-08-02 16:50:34 +00:00
PPrototype * ReturnProto ( ) ;
VMFunction * GetDirectFunction ( ) ;
2016-03-01 15:47:10 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
bool CheckEmitCast ( VMFunctionBuilder * build , bool returnit , ExpEmit & reg ) ;
2016-11-19 23:25:38 +00:00
TArray < PType * > & GetReturnTypes ( ) const
{
return Function - > Variants [ 0 ] . Proto - > ReturnTypes ;
}
2016-03-01 15:47:10 +00:00
} ;
//==========================================================================
//
2016-10-19 23:09:35 +00:00
// FxSequence (a list of statements with no semantics attached - used to return multiple nodes as one)
2016-03-01 15:47:10 +00:00
//
//==========================================================================
2016-10-19 17:05:48 +00:00
class FxLocalVariableDeclaration ;
2016-03-01 15:47:10 +00:00
2016-10-19 23:09:35 +00:00
class FxSequence : public FxExpression
2016-03-01 15:47:10 +00:00
{
TDeletingArray < FxExpression * > Expressions ;
2016-10-19 23:09:35 +00:00
public :
2016-10-22 23:14:49 +00:00
FxSequence ( const FScriptPosition & pos ) : FxExpression ( EFX_Sequence , pos ) { }
2016-10-19 23:09:35 +00:00
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
2016-10-26 09:30:30 +00:00
void Add ( FxExpression * expr ) { if ( expr ! = NULL ) Expressions . Push ( expr ) ; expr - > NeedResult = false ; }
2016-10-19 23:09:35 +00:00
VMFunction * GetDirectFunction ( ) ;
2016-11-05 17:05:57 +00:00
bool CheckReturn ( ) ;
2016-10-19 23:09:35 +00:00
} ;
//==========================================================================
//
// FxCompoundStatement (like a list but implements maintenance of local variables)
//
//==========================================================================
class FxLocalVariableDeclaration ;
class FxCompoundStatement : public FxSequence
{
TArray < FxLocalVariableDeclaration * > LocalVars ;
2016-10-19 17:05:48 +00:00
FxCompoundStatement * Outer = nullptr ;
friend class FxLocalVariableDeclaration ;
2016-11-20 17:00:37 +00:00
friend class FxStaticArray ;
2016-11-19 23:25:38 +00:00
friend class FxMultiAssign ;
2016-03-01 15:47:10 +00:00
public :
2016-10-19 23:09:35 +00:00
FxCompoundStatement ( const FScriptPosition & pos ) : FxSequence ( pos ) { }
2016-03-01 15:47:10 +00:00
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
2016-10-20 14:55:12 +00:00
FxLocalVariableDeclaration * FindLocalVariable ( FName name , FCompileContext & ctx ) ;
2016-10-19 17:05:48 +00:00
bool CheckLocalVariable ( FName name ) ;
2016-03-01 15:47:10 +00:00
} ;
2016-10-23 10:00:25 +00:00
//==========================================================================
//
// FxSwitchStatement
//
//==========================================================================
class FxSwitchStatement : public FxExpression
{
FxExpression * Condition ;
2016-11-10 14:13:31 +00:00
FArgumentList Content ;
2016-10-23 10:00:25 +00:00
struct CaseAddr
{
int casevalue ;
size_t jumpaddress ;
} ;
TArray < CaseAddr > CaseAddresses ;
public :
2016-11-26 23:18:07 +00:00
TArray < FxJumpStatement * > Breaks ;
2016-11-10 14:13:31 +00:00
FxSwitchStatement ( FxExpression * cond , FArgumentList & content , const FScriptPosition & pos ) ;
2016-10-23 10:00:25 +00:00
~ FxSwitchStatement ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
2016-11-05 17:05:57 +00:00
bool CheckReturn ( ) ;
2016-10-23 10:00:25 +00:00
} ;
//==========================================================================
//
// FxSwitchStatement
//
//==========================================================================
class FxCaseStatement : public FxExpression
{
FxExpression * Condition ;
int CaseValue ; // copy the value to here for easier access.
friend class FxSwitchStatement ;
public :
FxCaseStatement ( FxExpression * cond , const FScriptPosition & pos ) ;
~ FxCaseStatement ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
} ;
2016-03-01 15:47:10 +00:00
//==========================================================================
//
// FxIfStatement
//
//==========================================================================
class FxIfStatement : public FxExpression
{
FxExpression * Condition ;
FxExpression * WhenTrue ;
FxExpression * WhenFalse ;
public :
FxIfStatement ( FxExpression * cond , FxExpression * true_part , FxExpression * false_part , const FScriptPosition & pos ) ;
~ FxIfStatement ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
2016-11-05 17:05:57 +00:00
bool CheckReturn ( ) ;
2016-03-01 15:47:10 +00:00
} ;
2016-10-15 08:34:26 +00:00
//==========================================================================
//
// Base class for loops
//
//==========================================================================
class FxLoopStatement : public FxExpression
{
protected :
2016-10-22 23:14:49 +00:00
FxLoopStatement ( EFxType etype , const FScriptPosition & pos )
: FxExpression ( etype , pos )
2016-10-15 08:34:26 +00:00
{
}
2016-10-19 12:36:54 +00:00
void Backpatch ( VMFunctionBuilder * build , size_t loopstart , size_t loopend ) ;
FxExpression * Resolve ( FCompileContext & ) final ;
virtual FxExpression * DoResolve ( FCompileContext & ) = 0 ;
2016-10-15 08:34:26 +00:00
2016-10-19 12:36:54 +00:00
public :
TArray < FxJumpStatement * > Jumps ;
2016-10-15 08:34:26 +00:00
} ;
2016-07-25 04:38:02 +00:00
//==========================================================================
//
// FxWhileLoop
//
//==========================================================================
2016-10-15 08:34:26 +00:00
class FxWhileLoop : public FxLoopStatement
2016-07-25 04:38:02 +00:00
{
FxExpression * Condition ;
FxExpression * Code ;
public :
FxWhileLoop ( FxExpression * condition , FxExpression * code , const FScriptPosition & pos ) ;
~ FxWhileLoop ( ) ;
2016-10-19 12:36:54 +00:00
FxExpression * DoResolve ( FCompileContext & ) ;
2016-07-25 04:38:02 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-07-27 15:14:54 +00:00
//==========================================================================
//
// FxDoWhileLoop
//
//==========================================================================
2016-10-15 08:34:26 +00:00
class FxDoWhileLoop : public FxLoopStatement
2016-07-27 15:14:54 +00:00
{
FxExpression * Condition ;
FxExpression * Code ;
public :
FxDoWhileLoop ( FxExpression * condition , FxExpression * code , const FScriptPosition & pos ) ;
~ FxDoWhileLoop ( ) ;
2016-10-19 12:36:54 +00:00
FxExpression * DoResolve ( FCompileContext & ) ;
2016-07-27 15:14:54 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-07-28 15:36:05 +00:00
//==========================================================================
//
// FxForLoop
//
//==========================================================================
2016-10-15 08:34:26 +00:00
class FxForLoop : public FxLoopStatement
2016-07-28 15:36:05 +00:00
{
FxExpression * Init ;
FxExpression * Condition ;
FxExpression * Iteration ;
FxExpression * Code ;
public :
FxForLoop ( FxExpression * init , FxExpression * condition , FxExpression * iteration , FxExpression * code , const FScriptPosition & pos ) ;
~ FxForLoop ( ) ;
2016-10-19 12:36:54 +00:00
FxExpression * DoResolve ( FCompileContext & ) ;
2016-07-28 15:36:05 +00:00
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-07-26 21:57:26 +00:00
//==========================================================================
//
// FxJumpStatement
//
//==========================================================================
class FxJumpStatement : public FxExpression
{
public :
FxJumpStatement ( int token , const FScriptPosition & pos ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
int Token ;
size_t Address ;
} ;
2016-03-01 15:47:10 +00:00
//==========================================================================
//
// FxReturnStatement
//
//==========================================================================
class FxReturnStatement : public FxExpression
{
2017-01-18 00:27:50 +00:00
FArgumentList Args ;
2016-03-01 15:47:10 +00:00
public :
2016-08-02 16:50:34 +00:00
FxReturnStatement ( FxExpression * value , const FScriptPosition & pos ) ;
2017-01-18 00:27:50 +00:00
FxReturnStatement ( FArgumentList & args , const FScriptPosition & pos ) ;
2016-03-01 15:47:10 +00:00
~ FxReturnStatement ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
VMFunction * GetDirectFunction ( ) ;
2016-11-05 17:05:57 +00:00
bool CheckReturn ( ) { return true ; }
2016-03-01 15:47:10 +00:00
} ;
//==========================================================================
//
//
//
//==========================================================================
class FxClassTypeCast : public FxExpression
{
PClass * desttype ;
FxExpression * basex ;
2017-01-24 09:04:46 +00:00
bool Explicit ;
2016-03-01 15:47:10 +00:00
public :
2017-01-24 09:04:46 +00:00
FxClassTypeCast ( PClassPointer * dtype , FxExpression * x , bool explicitly ) ;
2016-03-01 15:47:10 +00:00
~ FxClassTypeCast ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-11-17 19:31:53 +00:00
//==========================================================================
//
//
//
//==========================================================================
class FxClassPtrCast : public FxExpression
{
PClass * desttype ;
FxExpression * basex ;
public :
FxClassPtrCast ( PClass * dtype , FxExpression * x ) ;
~ FxClassPtrCast ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-03-01 15:47:10 +00:00
//==========================================================================
//
// Only used to resolve the old jump by index feature of DECORATE
//
//==========================================================================
class FxStateByIndex : public FxExpression
{
int index ;
public :
2016-10-22 23:14:49 +00:00
FxStateByIndex ( int i , const FScriptPosition & pos ) : FxExpression ( EFX_StateByIndex , pos )
2016-03-01 15:47:10 +00:00
{
index = i ;
}
FxExpression * Resolve ( FCompileContext & ) ;
} ;
2016-08-05 15:26:33 +00:00
//==========================================================================
//
// Same as above except for expressions which means it will have to be
// evaluated at runtime
//
//==========================================================================
class FxRuntimeStateIndex : public FxExpression
{
FxExpression * Index ;
2016-11-14 13:12:27 +00:00
int symlabel ;
2016-08-05 15:26:33 +00:00
public :
FxRuntimeStateIndex ( FxExpression * index ) ;
~ FxRuntimeStateIndex ( ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-03-01 15:47:10 +00:00
//==========================================================================
//
//
//
//==========================================================================
class FxMultiNameState : public FxExpression
{
PClassActor * scope ;
TArray < FName > names ;
public :
FxMultiNameState ( const char * statestring , const FScriptPosition & pos ) ;
FxExpression * Resolve ( FCompileContext & ) ;
} ;
2016-04-07 18:31:12 +00:00
//==========================================================================
//
//
//
//==========================================================================
class FxNop : public FxExpression
{
public :
FxNop ( const FScriptPosition & p )
2016-10-22 23:14:49 +00:00
: FxExpression ( EFX_Nop , p )
2016-04-07 18:31:12 +00:00
{
isresolved = true ;
}
ExpEmit Emit ( VMFunctionBuilder * build )
{
return ExpEmit ( ) ;
}
} ;
2016-03-01 15:47:10 +00:00
2016-10-19 17:05:48 +00:00
//==========================================================================
//
//
//
//==========================================================================
2016-03-01 15:47:10 +00:00
2016-10-19 17:05:48 +00:00
class FxLocalVariableDeclaration : public FxExpression
{
friend class FxCompoundStatement ;
2016-10-20 23:12:54 +00:00
friend class FxLocalVariable ;
2016-11-20 17:00:37 +00:00
friend class FxStaticArrayVariable ;
2016-10-19 17:05:48 +00:00
FName Name ;
FxExpression * Init ;
2016-10-20 23:12:54 +00:00
int VarFlags ;
2016-10-28 13:15:30 +00:00
int RegCount ;
2016-10-20 14:55:12 +00:00
public :
2016-11-17 15:44:41 +00:00
int StackOffset = - 1 ;
2016-10-19 17:05:48 +00:00
int RegNum = - 1 ;
2017-01-11 22:46:03 +00:00
bool constructed = false ;
2016-10-19 17:05:48 +00:00
2016-10-20 23:12:54 +00:00
FxLocalVariableDeclaration ( PType * type , FName name , FxExpression * initval , int varflags , const FScriptPosition & p ) ;
2016-11-10 14:13:31 +00:00
~ FxLocalVariableDeclaration ( ) ;
2016-10-19 17:05:48 +00:00
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
void Release ( VMFunctionBuilder * build ) ;
2016-11-19 23:25:38 +00:00
void SetReg ( ExpEmit reginfo ) ;
2016-10-19 17:05:48 +00:00
} ;
2016-03-01 15:47:10 +00:00
2016-11-20 17:00:37 +00:00
//==========================================================================
//
//
//
//==========================================================================
class FxStaticArray : public FxLocalVariableDeclaration
{
friend class FxStaticArrayVariable ;
PType * ElementType ;
FArgumentList values ;
public :
FxStaticArray ( PType * type , FName name , FArgumentList & args , const FScriptPosition & pos ) ;
FxExpression * Resolve ( FCompileContext & ) ;
ExpEmit Emit ( VMFunctionBuilder * build ) ;
} ;
2016-11-21 00:32:01 +00:00
class FxNamedNode : public FxExpression
{
public :
FName name ;
FxExpression * value ;
FxNamedNode ( FName n , FxExpression * x , const FScriptPosition & pos )
: FxExpression ( EFX_NamedNode , pos ) , name ( n ) , value ( x )
{
}
FxExpression * Resolve ( FCompileContext & )
{
// This should never reach the backend in a supported context,
// it's just needed to extend argument lists with the skipped parameters and needs to be resolved by the parent node.
ScriptPosition . Message ( MSG_ERROR , " Named arguments not supported here " ) ;
delete this ;
return nullptr ;
}
} ;
2016-11-20 17:00:37 +00:00
2016-03-01 15:47:10 +00:00
# endif