001: package gnu.expr;
002:
003: import gnu.bytecode.*;
004:
005: /** A Literal contains compile-time information about a constant. */
006:
007: public class Literal {
008: Literal next;
009:
010: public Field field;
011:
012: Object value;
013:
014: /* If field is non-null, it is the number of the Field.
015: * I.e. if the index is 10, the value of the Literal is the value of
016: * the static Field named Lit10. */
017: int index;
018:
019: public Type type;
020:
021: public int flags;
022:
023: /** Set at the beginning of the call to writeObject. */
024: static final int WRITING = 1;
025:
026: /** Set at the end of the call to writeObject. */
027: static final int WRITTEN = 2;
028:
029: static final int CYCLIC = 4;
030:
031: /** In pass 2, object has been at least allocated. */
032: static final int EMITTED = 8;
033:
034: /** Values produced by calling writeObject on value. */
035: Object[] argValues;
036: /** Types produced by calling writeObject on value. */
037: Type[] argTypes;
038:
039: public static final Literal nullLiteral = new Literal(null,
040: Type.nullType);
041:
042: public final Object getValue() {
043: return value;
044: }
045:
046: void assign(LitTable litTable) {
047: assign((String) null, litTable);
048: }
049:
050: /** Assign a static Field to hold the value of this Literal.
051: * This supports the same value being used multiple times or cyclically. */
052: void assign(String name, LitTable litTable) {
053: int flags = litTable.comp.immediate ? Access.STATIC
054: | Access.PUBLIC : Access.STATIC | Access.FINAL;
055: if (name == null) {
056: index = litTable.literalsCount++;
057: name = "Lit" + index;
058: } else
059: flags |= Access.PUBLIC;
060: assign(litTable.mainClass.addField(name, type, flags), litTable);
061: }
062:
063: void assign(Field field, LitTable litTable) {
064: next = litTable.literalsChain;
065: litTable.literalsChain = this ;
066: this .field = field;
067: }
068:
069: /** Create a new Literal, where comp must be in immediate mode. */
070: public Literal(Object value, LitTable litTable) {
071: this (value, (String) null, litTable);
072: }
073:
074: public Literal(Object value, String name, LitTable litTable) {
075: this .value = value;
076: litTable.literalTable.put(value, this );
077: this .type = Type.make(value.getClass());
078: assign(name, litTable);
079: }
080:
081: /** Create a new Literal, for a value available from a static field.
082: * The field must be static and already exist. */
083: public Literal(Object value, Field field, LitTable litTable) {
084: this .value = value;
085: litTable.literalTable.put(value, this );
086: this .field = field;
087: this .type = field.getType();
088: flags = WRITTEN | EMITTED;
089: }
090:
091: public Literal(Object value, Type type, LitTable litTable) {
092: this .value = value;
093: litTable.literalTable.put(value, this );
094: this .type = type;
095: }
096:
097: Literal(Object value, Type type) {
098: this.value = value;
099: this.type = type;
100: }
101: }
|