// Copyright (c) 1995 David Engberg All rights reserved // $Id: VariableDeclaration.C,v 1.6 1997/08/21 16:30:12 geppetto Exp $ #include "VariableDeclaration.h" #include "Expression.h" #include "CompileError.h" #include "JavaMethodInfo.h" #include "JavaClassFile.h" #include "Compiler.h" #include "BinaryExpression.h" #include "CompileContext.h" // // Method name : CVariableDeclaration // Description : Default constructor. // CVariableDeclaration::CVariableDeclaration() : fInitializer(0), fFinal(false) { } // // Method name : CVariableDeclaration // Description : Constructs a variable declaration out of its name, type, and // optional initializer. // CVariableDeclaration::CVariableDeclaration(const CJavaTypeSignature& type, const unicode_string& name, CExpression* adoptInitializer, bool final) : fSignature(type, name), fInitializer(adoptInitializer), fFinal(final) { } // // Method name : CVariableDeclaration // Description : Copy constructor. // CVariableDeclaration::CVariableDeclaration(const CVariableDeclaration& source) : fSignature(source.fSignature), fInitializer(0), fFinal(source.fFinal) { if (source.fInitializer != 0) { fInitializer = source.fInitializer->Clone(); } } // // Method name : ~CVariableDeclaration // Description : Destructor // CVariableDeclaration::~CVariableDeclaration() { delete fInitializer; } // // Method name : GetType // Description : Returns the type of this variable. // CJavaTypeSignature CVariableDeclaration::GetType() const { return fSignature.GetType(); } // // Method name : SetType // Description : Sets the type of this variable. // void CVariableDeclaration::SetType(const CJavaTypeSignature& type) { fSignature = CJavaFieldSignature(type, fSignature.GetFieldName()); } // // Method name : GenerateCode // Description : Appends the generated bytecode for this statement onto the // code parameter, using the other parameters to help get the // needed information. In addition, the 'stackUsed' parameter is set to // the maximum expression stack depth incurred by this statement. // If this operation is successful, 0 is returned, otherwise a compile // error structure is created and returned to the caller to explain what // went wrong. // CCompileError* CVariableDeclaration::GenerateCode(CCodeSequence& code, CCompileContext& context, const CJavaAccessFlags& modifiers, unsigned short& stackUsed) { CCompileError* error = 0; CJavaTypeSignature type; stackUsed = 0; if (fInitializer != 0) { error = CExpression::EvaluateType(fInitializer, context, type); if (error == 0) { bool skipFinalConstant = false; if (context.GetCompiler().InClassInitializers() && modifiers.fFinal != 0) { CExpression* constantExpression = 0; error = GetConstantValue(constantExpression, context); if (constantExpression != 0) { delete constantExpression; skipFinalConstant = true; } } if (!skipFinalConstant && error == 0) { error = fInitializer->GenerateCode(code, context, stackUsed, true); } } } return error; } // // Method name : GetConstantValue // Description : This method is used to try to extract a constant literal // value associated with this variable declaration's initializer. If // no initializer exists, or if the initializer can't be resolved to // a constant value, then the intoPointer is set to 0, otherwise it is // filled with the appropriate constant value. // If a problem occurs during assesment, an error is created and returned // to the caller, otherwise 0 is returned. // CCompileError* CVariableDeclaration::GetConstantValue(CExpression*& intoPointer, CCompileContext& context) { CCompileError* error = 0; intoPointer = 0; if (fInitializer != 0) { CJavaTypeSignature type; error = CExpression::EvaluateType(fInitializer, context, type, false); CBinaryExpression* initializer = DYNAMIC_CAST(CBinaryExpression, fInitializer); if (initializer != 0 && error == 0) { const CExpression* initializerValue = initializer->GetRightArgument(); assert(initializerValue != 0); error = initializerValue->CreateConstantExpression(intoPointer, context); } } return error; } // // Method name : SetFinal // Description : Specifies whether this variable is final or not. // void CVariableDeclaration::SetFinal(bool final) { fFinal = final; } // // Method name : GetName // Description : Spits out the name of this declared field. // unicode_string CVariableDeclaration::GetName() const { return fSignature.GetFieldName(); }