001: package kawa.standard;
002:
003: import kawa.lang.*;
004: import gnu.lists.*;
005: import gnu.expr.*;
006: import gnu.mapping.Symbol;
007:
008: public class define_class extends Syntax {
009: public static final define_class define_class = new define_class(
010: "define-class", false);
011: public static final define_class define_simple_class = new define_class(
012: "define-simple-class", true);
013:
014: boolean isSimple;
015: object objectSyntax;
016:
017: define_class(object objectSyntax, boolean isSimple) {
018: this .objectSyntax = objectSyntax;
019: this .isSimple = isSimple;
020: }
021:
022: define_class(String name, boolean isSimple) {
023: super (name);
024: this .objectSyntax = object.objectSyntax;
025: this .isSimple = isSimple;
026: }
027:
028: public boolean scanForDefinitions(Pair st, java.util.Vector forms,
029: ScopeExp defs, Translator tr) {
030: Object st_cdr = st.cdr;
031: SyntaxForm nameSyntax = null;
032: while (st_cdr instanceof SyntaxForm) {
033: nameSyntax = (SyntaxForm) st_cdr;
034: st_cdr = nameSyntax.form;
035: }
036: if (!(st_cdr instanceof Pair))
037: return super .scanForDefinitions(st, forms, defs, tr);
038: Pair p = (Pair) st_cdr;
039: Object name = p.car;
040: while (name instanceof SyntaxForm) {
041: nameSyntax = (SyntaxForm) name;
042: name = nameSyntax.form;
043: }
044: if (!(name instanceof String || name instanceof Symbol))
045: return super .scanForDefinitions(st, forms, defs, tr);
046: Declaration decl = tr.define(name, nameSyntax, defs);
047: if (p instanceof PairWithPosition)
048: decl.setLocation((PairWithPosition) p);
049: ClassExp oexp = new ClassExp(isSimple);
050: decl.noteValue(oexp);
051: decl.setFlag(Declaration.IS_CONSTANT);
052: decl.setType(Compilation.typeClassType);
053: tr.mustCompileHere();
054:
055: String cname = name instanceof Symbol ? ((Symbol) name)
056: .getName() : name.toString();
057: int nlen = cname.length();
058: if (nlen > 2 && cname.charAt(0) == '<'
059: && cname.charAt(nlen - 1) == '>')
060: cname = cname.substring(1, nlen - 1);
061: oexp.setName(cname);
062:
063: Object members = p.cdr;
064: while (members instanceof SyntaxForm) {
065: nameSyntax = (SyntaxForm) members;
066: members = nameSyntax.form;
067: }
068: if (!(members instanceof Pair)) {
069: tr.error('e', "missing class members");
070: return false;
071: }
072: p = (Pair) members;
073: ScopeExp save_scope = tr.currentScope();
074: if (nameSyntax != null)
075: tr.setCurrentScope(nameSyntax.scope);
076: Object[] saved = objectSyntax.scanClassDef(p, oexp, tr);
077: if (nameSyntax != null)
078: tr.setCurrentScope(save_scope);
079: if (saved == null)
080: return false;
081: st = Translator.makePair(st, this , Translator.makePair(p, decl,
082: saved));
083: forms.addElement(st);
084: return true;
085: }
086:
087: public Expression rewriteForm(Pair form, Translator tr) {
088: //FIXME needs work
089: Declaration decl = null;
090: if (form.cdr instanceof Pair) {
091: form = (Pair) form.cdr;
092: if (!(form.car instanceof Declaration))
093: return tr.syntaxError(this .getName()
094: + " can only be used in <body>");
095: decl = (Declaration) form.car;
096: }
097: ClassExp oexp = (ClassExp) decl.getValue();
098: objectSyntax.rewriteClassDef((Object[]) form.cdr, tr);
099: SetExp sexp = new SetExp(decl, oexp);
100: sexp.setDefining(true);
101: return sexp;
102: }
103: }
|