--- /dev/null
+package org.simantics.scl.compiler.elaboration.modules;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.simantics.scl.compiler.common.names.Name;
+import org.simantics.scl.compiler.common.precedence.Precedence;
+import org.simantics.scl.compiler.constants.Constant;
+import org.simantics.scl.compiler.elaboration.contexts.SimplificationContext;
+import org.simantics.scl.compiler.elaboration.expressions.Expression;
+import org.simantics.scl.compiler.elaboration.macros.MacroRule;
+import org.simantics.scl.compiler.errors.Locations;
+import org.simantics.scl.compiler.internal.codegen.references.IVal;
+import org.simantics.scl.compiler.internal.codegen.utils.TransientClassBuilder;
+import org.simantics.scl.compiler.types.Type;
+import org.simantics.scl.compiler.types.util.Typed;
+
+/**
+ * Information about SCL values that is needed in parsing
+ * and elaboration phases.
+ * @author Hannu Niemistö
+ */
+public final class SCLValue implements Typed {
+ private static final int SIMPLIFIED = 1;
+ private static final int INLINE_IN_SIMPLIFICATION = 2;
+ private static final int FLAG_MASK = 0xffff;
+
+ private Name name;
+ private Type type;
+ private Precedence precedence = Precedence.DEFAULT;
+ private IVal value;
+ private Expression expression;
+ private MacroRule macroRule;
+ private int flags = 0;
+ private ArrayList<SCLValueProperty> properties = new ArrayList<SCLValueProperty>(2);
+ public String documentation;
+ public long definitionLocation = Locations.NO_LOCATION;
+
+ public SCLValue(Name name) {
+ this.name = name;
+ }
+
+ public SCLValue(Name name, Constant value) {
+ this(name);
+ setValue(value);
+ }
+
+ public Name getName() {
+ return name;
+ }
+
+ public Type getType() {
+ return type;
+ }
+
+ public void setType(Type type) {
+ this.type = type;
+ }
+
+ public void addProperty(SCLValueProperty property) {
+ properties.add(property);
+ }
+
+ public List<SCLValueProperty> getProperties() {
+ return properties;
+ }
+
+ public Precedence getPrecedence() {
+ return precedence;
+ }
+
+ public void setPrecedence(Precedence precedence) {
+ this.precedence = precedence;
+ }
+
+ public IVal getValue() {
+ return value;
+ }
+
+ public void setValue(IVal value) {
+ this.value = value;
+ if(type == null)
+ type = value.getType();
+ }
+
+ public Expression getExpression() {
+ return expression;
+ }
+
+ public Expression getSimplifiedExpression(SimplificationContext context) {
+ if(expression != null && (flags & SIMPLIFIED) == 0) {
+ //System.out.println("Simplify: " + name);
+ //System.out.println("BEFORE: " + expression);
+ expression = expression.simplify(context);
+ //System.out.println("AFTER: " + expression);
+ flags |= SIMPLIFIED;
+ }
+ return expression;
+ }
+
+ public void setExpression(Expression expression) {
+ this.expression = expression;
+ }
+
+ public MacroRule getMacroRule() {
+ return macroRule;
+ }
+
+ public void setMacroRule(MacroRule macroRule) {
+ this.macroRule = macroRule;
+ }
+
+ @Override
+ public String toString() {
+ return name.toString();
+ }
+
+ private void setFlag(int flagMask, boolean value) {
+ if(value)
+ flags |= flagMask;
+ else
+ flags &= FLAG_MASK - flagMask;
+ }
+
+ public void setSimplified(boolean value) {
+ setFlag(SIMPLIFIED, value);
+ }
+
+ public void setInlineInSimplification(boolean value) {
+ setFlag(INLINE_IN_SIMPLIFICATION, value);
+ }
+
+ public boolean getInlineInSimplification() {
+ return (flags & INLINE_IN_SIMPLIFICATION) != 0;
+ }
+
+ public Object realizeValue(TransientClassBuilder classLoader) {
+ return getValue().realizeValue(classLoader);
+ }
+
+ public boolean isPrivate() {
+ for(SCLValueProperty property : properties)
+ if(property == PrivateProperty.INSTANCE)
+ return true;
+ return false;
+ }
+
+ public void setDocumentation(String documentation) {
+ this.documentation = documentation;
+ }
+
+ public String getDocumentation() {
+ return documentation;
+ }
+}