mirror of https://github.com/aamine/cbc
* net/loveruby/cflat/asm/Assembler.java: objectify instructions, directives, comments and labels.
* net/loveruby/cflat/asm/Label.java: inherits Assembly instead of AsmEntity. * net/loveruby/cflat/asm/Address.java: new method #isAddress. * net/loveruby/cflat/asm/ImmediateValue.java: accept Literals. * net/loveruby/cflat/asm/AbsoluteAddress.java: new file. * net/loveruby/cflat/asm/AsmComment.java: new file. * net/loveruby/cflat/asm/Assembly.java: new file. * net/loveruby/cflat/asm/Directive.java: new file. * net/loveruby/cflat/asm/Reference.java -> DirectAddress.java: new file. * net/loveruby/cflat/asm/SimpleAddress.java, CompositeAddress.java -> IndirectAddress.java * net/loveruby/cflat/asm/Instruction.java: new file. * net/loveruby/cflat/asm/IntegerLiteral.java: new file. * net/loveruby/cflat/asm/Literal.java: new file. * net/loveruby/cflat/asm/Symbol.java: new file. * net/loveruby/cflat/compiler/CodeGenerator.java: follow asm changes. * net/loveruby/cflat/ast/UndefinedVariable.java: * net/loveruby/cflat/ast/Function.java git-svn-id: file:///Users/aamine/c/gitwork/public/cbc/trunk@4022 1b9489fe-b721-0410-924e-b54b9192deb8
This commit is contained in:
parent
ae0f46cee4
commit
7314d4bf6f
41
ChangeLog
41
ChangeLog
|
|
@ -1,3 +1,44 @@
|
|||
Tue Sep 16 00:21:10 2008 Minero Aoki <aamine@loveruby.net>
|
||||
|
||||
* net/loveruby/cflat/asm/Assembler.java: objectify instructions,
|
||||
directives, comments and labels.
|
||||
|
||||
* net/loveruby/cflat/asm/Label.java: inherits Assembly instead of
|
||||
AsmEntity.
|
||||
|
||||
* net/loveruby/cflat/asm/Address.java: new method #isAddress.
|
||||
|
||||
* net/loveruby/cflat/asm/ImmediateValue.java: accept Literals.
|
||||
|
||||
* net/loveruby/cflat/asm/AbsoluteAddress.java: new file.
|
||||
|
||||
* net/loveruby/cflat/asm/AsmComment.java: new file.
|
||||
|
||||
* net/loveruby/cflat/asm/Assembly.java: new file.
|
||||
|
||||
* net/loveruby/cflat/asm/Directive.java: new file.
|
||||
|
||||
* net/loveruby/cflat/asm/Reference.java -> DirectAddress.java: new
|
||||
file.
|
||||
|
||||
* net/loveruby/cflat/asm/SimpleAddress.java, CompositeAddress.java
|
||||
-> IndirectAddress.java
|
||||
|
||||
* net/loveruby/cflat/asm/Instruction.java: new file.
|
||||
|
||||
* net/loveruby/cflat/asm/IntegerLiteral.java: new file.
|
||||
|
||||
* net/loveruby/cflat/asm/Literal.java: new file.
|
||||
|
||||
* net/loveruby/cflat/asm/Symbol.java: new file.
|
||||
|
||||
* net/loveruby/cflat/compiler/CodeGenerator.java: follow asm
|
||||
changes.
|
||||
|
||||
* net/loveruby/cflat/ast/UndefinedVariable.java:
|
||||
|
||||
* net/loveruby/cflat/ast/Function.java
|
||||
|
||||
Mon Sep 15 21:19:05 2008 Minero Aoki <aamine@loveruby.net>
|
||||
|
||||
* net/loveruby/cflat/compiler/Compiler.java: link libcbc on making
|
||||
|
|
|
|||
2
ToDo
2
ToDo
|
|
@ -14,6 +14,7 @@
|
|||
* imull $1, %eax => NONE
|
||||
* label renaming
|
||||
* remove useless jump
|
||||
* generate prologue/epilogue after function body.
|
||||
* -fPIC (PIC generation)
|
||||
* -shared
|
||||
* remove all FIXME
|
||||
|
|
@ -234,3 +235,4 @@
|
|||
- -Wa, -Xassembler
|
||||
- write install.sh
|
||||
- va_list
|
||||
- objectify instruction
|
||||
|
|
|
|||
|
|
@ -0,0 +1,17 @@
|
|||
package net.loveruby.cflat.asm;
|
||||
|
||||
public class AbsoluteAddress extends Address {
|
||||
protected Register register;
|
||||
|
||||
public AbsoluteAddress(Register reg) {
|
||||
this.register = reg;
|
||||
}
|
||||
|
||||
public AsmEntity register() {
|
||||
return this.register;
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
return "*" + register.toString();
|
||||
}
|
||||
}
|
||||
|
|
@ -1,4 +1,7 @@
|
|||
package net.loveruby.cflat.asm;
|
||||
|
||||
abstract public class Address extends AsmEntity {
|
||||
public boolean isAddress() {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,13 @@
|
|||
package net.loveruby.cflat.asm;
|
||||
|
||||
public class AsmComment extends Assembly {
|
||||
protected String string;
|
||||
|
||||
public AsmComment(String string) {
|
||||
this.string = string;
|
||||
}
|
||||
|
||||
public String toSource() {
|
||||
return "\t# " + string;
|
||||
}
|
||||
}
|
||||
|
|
@ -2,4 +2,8 @@ package net.loveruby.cflat.asm;
|
|||
|
||||
abstract public class AsmEntity {
|
||||
abstract public String toString();
|
||||
|
||||
public boolean isAddress() {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -4,7 +4,7 @@ import net.loveruby.cflat.utils.*;
|
|||
import java.util.*;
|
||||
|
||||
public class Assembler {
|
||||
protected List list;
|
||||
protected List list; // List<Assembly>
|
||||
protected Type naturalType;
|
||||
|
||||
static public long align(long n, long alignment) {
|
||||
|
|
@ -20,154 +20,55 @@ public class Assembler {
|
|||
StringBuffer buf = new StringBuffer();
|
||||
Iterator i = list.iterator();
|
||||
while (i.hasNext()) {
|
||||
buf.append((String)i.next());
|
||||
Assembly asm = (Assembly)i.next();
|
||||
buf.append(asm.toSource());
|
||||
buf.append("\n");
|
||||
}
|
||||
return buf.toString();
|
||||
}
|
||||
|
||||
protected void op(String op) {
|
||||
list.add("\t" + op);
|
||||
}
|
||||
|
||||
protected void op(String op, AsmEntity ent) {
|
||||
list.add("\t" + op + "\t" + ent.toString());
|
||||
}
|
||||
|
||||
protected void op(String op, AsmEntity ent1, AsmEntity ent2) {
|
||||
list.add("\t" + op + "\t" + ent1.toString() + ", " + ent2.toString());
|
||||
}
|
||||
|
||||
protected void op(String op, String arg) {
|
||||
list.add("\t" + op + "\t" + arg);
|
||||
}
|
||||
|
||||
protected void op(String op, String arg1, String arg2) {
|
||||
list.add("\t" + op + "\t" + arg1 + ", " + arg2);
|
||||
}
|
||||
|
||||
protected void op(String op, String arg1, String arg2, String arg3) {
|
||||
list.add("\t" + op + "\t" + arg1 + ", " + arg2 + ", " + arg3);
|
||||
}
|
||||
|
||||
public void comment(String str) {
|
||||
list.add("\t# " + str);
|
||||
list.add(new AsmComment(str));
|
||||
}
|
||||
|
||||
public void line(String str) {
|
||||
list.add(str);
|
||||
}
|
||||
|
||||
public void _file(String name) {
|
||||
line("\t.file\t" + TextUtils.dumpString(name));
|
||||
}
|
||||
|
||||
public void _text() {
|
||||
line("\t.text");
|
||||
}
|
||||
|
||||
public void _data() {
|
||||
line("\t.data");
|
||||
}
|
||||
|
||||
public void _section(String name) {
|
||||
line("\t.section\t" + name);
|
||||
}
|
||||
|
||||
public void _globl(String sym) {
|
||||
line(".globl " + sym);
|
||||
}
|
||||
|
||||
public void _local(String sym) {
|
||||
line(".local " + sym);
|
||||
}
|
||||
|
||||
public void _comm(String sym, long size, long alignment) {
|
||||
line("\t.comm\t" + sym + "," + size + "," + alignment);
|
||||
}
|
||||
|
||||
public void _align(long n) {
|
||||
line("\t.align\t" + n);
|
||||
}
|
||||
|
||||
public void _type(String sym, String type) {
|
||||
line("\t.type\t" + sym + ", " + type);
|
||||
}
|
||||
|
||||
public void _size(String sym, long size) {
|
||||
_size(sym, new Long(size).toString());
|
||||
}
|
||||
|
||||
public void _size(String sym, String size) {
|
||||
line("\t.size\t" + sym + ", " + size);
|
||||
}
|
||||
|
||||
public void _byte(long n) {
|
||||
line(".byte\t" + n);
|
||||
}
|
||||
|
||||
public void _value(long n) {
|
||||
line(".value\t" + n);
|
||||
}
|
||||
|
||||
public void _long(long n) {
|
||||
line(".long\t" + n);
|
||||
}
|
||||
|
||||
public void _long(Label label) {
|
||||
line(".long\t" + label);
|
||||
}
|
||||
|
||||
public void _quad(long n) {
|
||||
line(".quad\t" + n);
|
||||
}
|
||||
|
||||
public void _quad(Label label) {
|
||||
line(".quad\t" + label);
|
||||
}
|
||||
|
||||
public void _string(String str) {
|
||||
line("\t.string\t" + TextUtils.dumpString(str));
|
||||
}
|
||||
|
||||
public void label(String label) {
|
||||
line(label + ":");
|
||||
public void label(String sym) {
|
||||
list.add(new Label(sym));
|
||||
}
|
||||
|
||||
public void label(Label label) {
|
||||
line(label.toString() + ":");
|
||||
list.add(label);
|
||||
}
|
||||
|
||||
public void jmp(Label label) {
|
||||
op("jmp", label);
|
||||
protected void directive(String direc) {
|
||||
list.add(new Directive(direc));
|
||||
}
|
||||
|
||||
public void jz(Label label) {
|
||||
op("jz", label);
|
||||
protected void insn(String op) {
|
||||
list.add(new Instruction(op));
|
||||
}
|
||||
|
||||
public void jnz(Label label) {
|
||||
op("jnz", label);
|
||||
protected void insn(String op, AsmEntity a) {
|
||||
list.add(new Instruction(op, "", a));
|
||||
}
|
||||
|
||||
public void je(Label label) {
|
||||
op("je", label);
|
||||
protected void insn(String op, String suffix, AsmEntity a) {
|
||||
list.add(new Instruction(op, suffix, a));
|
||||
}
|
||||
|
||||
public void jne(Label label) {
|
||||
op("jne", label);
|
||||
protected void insn(Type t, String op, AsmEntity a) {
|
||||
list.add(new Instruction(op, typeSuffix(t), a));
|
||||
}
|
||||
|
||||
protected void typedOp(Type t, String op, AsmEntity a) {
|
||||
op(addSuffix(op, t), a);
|
||||
protected void insn(String op, String suffix, AsmEntity a, AsmEntity b) {
|
||||
list.add(new Instruction(op, suffix, a, b));
|
||||
}
|
||||
|
||||
protected void typedOp(Type t, String op, AsmEntity a, AsmEntity b) {
|
||||
op(addSuffix(op, t), a, b);
|
||||
protected void insn(Type t, String op, AsmEntity a, AsmEntity b) {
|
||||
list.add(new Instruction(op, typeSuffix(t), a, b));
|
||||
}
|
||||
|
||||
protected String addSuffix(String op, Type t) {
|
||||
return op + typeSuffix(t);
|
||||
protected String typeSuffix(Type t1, Type t2) {
|
||||
return typeSuffix(t1) + typeSuffix(t2);
|
||||
}
|
||||
|
||||
protected String typeSuffix(Type t) {
|
||||
|
|
@ -180,82 +81,174 @@ public class Assembler {
|
|||
}
|
||||
}
|
||||
|
||||
//
|
||||
// directives
|
||||
//
|
||||
|
||||
public void _file(String name) {
|
||||
directive(".file\t" + TextUtils.dumpString(name));
|
||||
}
|
||||
|
||||
public void _text() {
|
||||
directive("\t.text");
|
||||
}
|
||||
|
||||
public void _data() {
|
||||
directive("\t.data");
|
||||
}
|
||||
|
||||
public void _section(String name) {
|
||||
directive("\t.section\t" + name);
|
||||
}
|
||||
|
||||
public void _globl(String sym) {
|
||||
directive(".globl " + sym);
|
||||
}
|
||||
|
||||
public void _local(String sym) {
|
||||
directive(".local " + sym);
|
||||
}
|
||||
|
||||
public void _comm(String sym, long size, long alignment) {
|
||||
directive("\t.comm\t" + sym + "," + size + "," + alignment);
|
||||
}
|
||||
|
||||
public void _align(long n) {
|
||||
directive("\t.align\t" + n);
|
||||
}
|
||||
|
||||
public void _type(String sym, String type) {
|
||||
directive("\t.type\t" + sym + "," + type);
|
||||
}
|
||||
|
||||
public void _size(String sym, long size) {
|
||||
_size(sym, new Long(size).toString());
|
||||
}
|
||||
|
||||
public void _size(String sym, String size) {
|
||||
directive("\t.size\t" + sym + "," + size);
|
||||
}
|
||||
|
||||
public void _byte(long n) {
|
||||
directive(".byte\t" + n);
|
||||
}
|
||||
|
||||
public void _value(long n) {
|
||||
directive(".value\t" + n);
|
||||
}
|
||||
|
||||
public void _long(long n) {
|
||||
directive(".long\t" + n);
|
||||
}
|
||||
|
||||
public void _long(Label sym) {
|
||||
directive(".long\t" + sym.toString());
|
||||
}
|
||||
|
||||
public void _quad(long n) {
|
||||
directive(".quad\t" + n);
|
||||
}
|
||||
|
||||
public void _quad(Label sym) {
|
||||
directive(".quad\t" + sym.toString());
|
||||
}
|
||||
|
||||
public void _string(String str) {
|
||||
directive("\t.string\t" + TextUtils.dumpString(str));
|
||||
}
|
||||
|
||||
//
|
||||
// Instructions
|
||||
//
|
||||
|
||||
public void jmp(Label label) {
|
||||
insn("jmp", new Symbol(label));
|
||||
}
|
||||
|
||||
public void jz(Label label) {
|
||||
insn("jz", new Symbol(label));
|
||||
}
|
||||
|
||||
public void jnz(Label label) {
|
||||
insn("jnz", new Symbol(label));
|
||||
}
|
||||
|
||||
public void je(Label label) {
|
||||
insn("je", new Symbol(label));
|
||||
}
|
||||
|
||||
public void jne(Label label) {
|
||||
insn("jne", new Symbol(label));
|
||||
}
|
||||
|
||||
public void cmp(Type t, Register a, Register b) {
|
||||
typedOp(t, "cmp", a, b);
|
||||
insn(t, "cmp", a, b);
|
||||
}
|
||||
|
||||
public void sete(Register reg) {
|
||||
op("sete", reg);
|
||||
insn("sete", reg);
|
||||
}
|
||||
|
||||
public void setne(Register reg) {
|
||||
op("setne", reg);
|
||||
insn("setne", reg);
|
||||
}
|
||||
|
||||
public void seta(Register reg) {
|
||||
op("seta", reg);
|
||||
insn("seta", reg);
|
||||
}
|
||||
|
||||
public void setae(Register reg) {
|
||||
op("setae", reg);
|
||||
insn("setae", reg);
|
||||
}
|
||||
|
||||
public void setb(Register reg) {
|
||||
op("setb", reg);
|
||||
insn("setb", reg);
|
||||
}
|
||||
|
||||
public void setbe(Register reg) {
|
||||
op("setbe", reg);
|
||||
insn("setbe", reg);
|
||||
}
|
||||
|
||||
public void setg(Register reg) {
|
||||
op("setg", reg);
|
||||
insn("setg", reg);
|
||||
}
|
||||
|
||||
public void setge(Register reg) {
|
||||
op("setge", reg);
|
||||
insn("setge", reg);
|
||||
}
|
||||
|
||||
public void setl(Register reg) {
|
||||
op("setl", reg);
|
||||
insn("setl", reg);
|
||||
}
|
||||
|
||||
public void setle(Register reg) {
|
||||
op("setle", reg);
|
||||
insn("setle", reg);
|
||||
}
|
||||
|
||||
public void test(Type type, Register a, Register b) {
|
||||
typedOp(type, "test", a, b);
|
||||
insn(type, "test", a, b);
|
||||
}
|
||||
|
||||
public void push(Register reg) {
|
||||
push(naturalType, reg);
|
||||
}
|
||||
|
||||
public void push(Type t, Register reg) {
|
||||
typedOp(t, "push", reg);
|
||||
insn("push", typeSuffix(naturalType), reg);
|
||||
}
|
||||
|
||||
public void pop(Register reg) {
|
||||
pop(naturalType, reg);
|
||||
}
|
||||
|
||||
public void pop(Type t, Register reg) {
|
||||
op("popl", reg);
|
||||
insn("pop", typeSuffix(naturalType), reg);
|
||||
}
|
||||
|
||||
// call function by relative address
|
||||
public void call(String sym) {
|
||||
op("call", sym);
|
||||
insn("call", new Symbol(new Label(sym)));
|
||||
}
|
||||
|
||||
// call function by absolute address
|
||||
public void callAbsolute(Register reg) {
|
||||
op("call", "*" + reg.toString());
|
||||
insn("call", new AbsoluteAddress(reg));
|
||||
}
|
||||
|
||||
public void ret() {
|
||||
op("ret");
|
||||
insn("ret");
|
||||
}
|
||||
|
||||
public void mov(AsmEntity src, AsmEntity dest) {
|
||||
|
|
@ -263,35 +256,35 @@ public class Assembler {
|
|||
}
|
||||
|
||||
public void mov(Type type, AsmEntity src, AsmEntity dest) {
|
||||
typedOp(type, "mov", src, dest);
|
||||
insn(type, "mov", src, dest);
|
||||
}
|
||||
|
||||
public void movsx(Type from, Type to, AsmEntity src, AsmEntity dest) {
|
||||
op("movs" + typeSuffix(from) + typeSuffix(to), src, dest);
|
||||
public void movsx(Type t1, Type t2, AsmEntity src, AsmEntity dest) {
|
||||
insn("movs", typeSuffix(t1, t2), src, dest);
|
||||
}
|
||||
|
||||
public void movsbl(AsmEntity src, AsmEntity dest) {
|
||||
op("movsbl", src, dest);
|
||||
insn("movs", "bl", src, dest);
|
||||
}
|
||||
|
||||
public void movswl(AsmEntity src, AsmEntity dest) {
|
||||
op("movswl", src, dest);
|
||||
insn("movs", "wl", src, dest);
|
||||
}
|
||||
|
||||
public void movzx(Type from, Type to, AsmEntity src, AsmEntity dest) {
|
||||
op("movz" + typeSuffix(from) + typeSuffix(to), src, dest);
|
||||
public void movzx(Type t1, Type t2, AsmEntity src, AsmEntity dest) {
|
||||
insn("movz", typeSuffix(t1, t2), src, dest);
|
||||
}
|
||||
|
||||
public void movzb(Type type, AsmEntity src, AsmEntity dest) {
|
||||
typedOp(type, "movzb", src, dest);
|
||||
public void movzb(Type t, AsmEntity src, AsmEntity dest) {
|
||||
insn("movz", "b" + typeSuffix(t), src, dest);
|
||||
}
|
||||
|
||||
public void movzbl(AsmEntity src, AsmEntity dest) {
|
||||
op("movzbl", src, dest);
|
||||
insn("movz", "bl", src, dest);
|
||||
}
|
||||
|
||||
public void movzwl(AsmEntity src, AsmEntity dest) {
|
||||
op("movzwl", src, dest);
|
||||
insn("movz", "wl", src, dest);
|
||||
}
|
||||
|
||||
public void lea(AsmEntity src, AsmEntity dest) {
|
||||
|
|
@ -299,19 +292,19 @@ public class Assembler {
|
|||
}
|
||||
|
||||
public void lea(Type type, AsmEntity src, AsmEntity dest) {
|
||||
typedOp(type, "lea", src, dest);
|
||||
insn(type, "lea", src, dest);
|
||||
}
|
||||
|
||||
public void neg(Type type, Register reg) {
|
||||
typedOp(type, "neg", reg);
|
||||
insn(type, "neg", reg);
|
||||
}
|
||||
|
||||
public void inc(Type type, AsmEntity reg) {
|
||||
typedOp(type, "inc", reg);
|
||||
insn(type, "inc", reg);
|
||||
}
|
||||
|
||||
public void dec(Type type, AsmEntity reg) {
|
||||
typedOp(type, "dec", reg);
|
||||
insn(type, "dec", reg);
|
||||
}
|
||||
|
||||
public void add(AsmEntity diff, AsmEntity base) {
|
||||
|
|
@ -319,7 +312,7 @@ public class Assembler {
|
|||
}
|
||||
|
||||
public void add(Type type, AsmEntity diff, AsmEntity base) {
|
||||
typedOp(type, "add", diff, base);
|
||||
insn(type, "add", diff, base);
|
||||
}
|
||||
|
||||
public void sub(AsmEntity diff, AsmEntity base) {
|
||||
|
|
@ -327,7 +320,7 @@ public class Assembler {
|
|||
}
|
||||
|
||||
public void sub(Type type, AsmEntity diff, AsmEntity base) {
|
||||
typedOp(type, "sub", diff, base);
|
||||
insn(type, "sub", diff, base);
|
||||
}
|
||||
|
||||
public void imul(AsmEntity m, Register base) {
|
||||
|
|
@ -335,46 +328,46 @@ public class Assembler {
|
|||
}
|
||||
|
||||
public void imul(Type type, AsmEntity m, Register base) {
|
||||
typedOp(type, "imul", m, base);
|
||||
insn(type, "imul", m, base);
|
||||
}
|
||||
|
||||
public void cltd() {
|
||||
op("cltd");
|
||||
insn("cltd");
|
||||
}
|
||||
|
||||
public void div(Type type, Register base) {
|
||||
typedOp(type, "div", base);
|
||||
insn(type, "div", base);
|
||||
}
|
||||
|
||||
public void idiv(Type type, Register base) {
|
||||
typedOp(type, "idiv", base);
|
||||
insn(type, "idiv", base);
|
||||
}
|
||||
|
||||
public void not(Type type, Register reg) {
|
||||
typedOp(type, "not", reg);
|
||||
insn(type, "not", reg);
|
||||
}
|
||||
|
||||
public void and(Type type, Register bits, Register base) {
|
||||
typedOp(type, "and", bits, base);
|
||||
insn(type, "and", bits, base);
|
||||
}
|
||||
|
||||
public void or(Type type, Register bits, Register base) {
|
||||
typedOp(type, "or", bits, base);
|
||||
insn(type, "or", bits, base);
|
||||
}
|
||||
|
||||
public void xor(Type type, Register bits, Register base) {
|
||||
typedOp(type, "xor", bits, base);
|
||||
insn(type, "xor", bits, base);
|
||||
}
|
||||
|
||||
public void sar(Type type, Register bits, Register base) {
|
||||
typedOp(type, "sar", bits, base);
|
||||
insn(type, "sar", bits, base);
|
||||
}
|
||||
|
||||
public void sal(Type type, Register bits, Register base) {
|
||||
typedOp(type, "sal", bits, base);
|
||||
insn(type, "sal", bits, base);
|
||||
}
|
||||
|
||||
public void shr(Type type, Register bits, Register base) {
|
||||
typedOp(type, "shr", bits, base);
|
||||
insn(type, "shr", bits, base);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,13 @@
|
|||
package net.loveruby.cflat.asm;
|
||||
|
||||
abstract public class Assembly {
|
||||
abstract public String toSource();
|
||||
|
||||
public boolean isInstruction() {
|
||||
return false;
|
||||
}
|
||||
|
||||
public boolean isLabel() {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
|
@ -1,23 +0,0 @@
|
|||
package net.loveruby.cflat.asm;
|
||||
|
||||
public class CompositeAddress extends Address {
|
||||
long offset;
|
||||
Register base;
|
||||
|
||||
public CompositeAddress(long off, Register reg) {
|
||||
offset = off;
|
||||
base = reg;
|
||||
}
|
||||
|
||||
public long offset() {
|
||||
return offset;
|
||||
}
|
||||
|
||||
public Register base() {
|
||||
return base;
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
return "" + offset + "(" + base.toString() + ")";
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,21 @@
|
|||
package net.loveruby.cflat.asm;
|
||||
|
||||
public class DirectAddress extends Address {
|
||||
protected Literal value;
|
||||
|
||||
public DirectAddress(Label label) {
|
||||
this.value = new Symbol(label);
|
||||
}
|
||||
|
||||
public DirectAddress(IntegerLiteral n) {
|
||||
this.value = n;
|
||||
}
|
||||
|
||||
public Literal value() {
|
||||
return this.value;
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
return this.value.toString();
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,13 @@
|
|||
package net.loveruby.cflat.asm;
|
||||
|
||||
public class Directive extends Assembly {
|
||||
protected String content;
|
||||
|
||||
public Directive(String content) {
|
||||
this.content = content;
|
||||
}
|
||||
|
||||
public String toSource() {
|
||||
return this.content;
|
||||
}
|
||||
}
|
||||
|
|
@ -1,17 +1,25 @@
|
|||
package net.loveruby.cflat.asm;
|
||||
|
||||
public class ImmediateValue extends AsmEntity {
|
||||
long value;
|
||||
protected AsmEntity entity;
|
||||
|
||||
public ImmediateValue(long n) {
|
||||
value = n;
|
||||
this(new IntegerLiteral(n));
|
||||
}
|
||||
|
||||
public long value() {
|
||||
return value;
|
||||
public ImmediateValue(Label label) {
|
||||
this(new Symbol(label));
|
||||
}
|
||||
|
||||
public ImmediateValue(AsmEntity entity) {
|
||||
this.entity = entity;
|
||||
}
|
||||
|
||||
public AsmEntity entity() {
|
||||
return this.entity;
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
return "$" + value;
|
||||
return "$" + entity.toString();
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,27 @@
|
|||
package net.loveruby.cflat.asm;
|
||||
|
||||
public class IndirectAddress extends Address {
|
||||
protected long offset;
|
||||
protected Register base;
|
||||
|
||||
public IndirectAddress(Register base) {
|
||||
this(0, base);
|
||||
}
|
||||
|
||||
public IndirectAddress(long offset, Register base) {
|
||||
this.offset = offset;
|
||||
this.base = base;
|
||||
}
|
||||
|
||||
public long offset() {
|
||||
return offset;
|
||||
}
|
||||
|
||||
public Register base() {
|
||||
return base;
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
return (offset == 0 ? "" : "" + offset) + "(" + base.toString() + ")";
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,62 @@
|
|||
package net.loveruby.cflat.asm;
|
||||
import net.loveruby.cflat.type.Type;
|
||||
|
||||
public class Instruction extends Assembly {
|
||||
protected String mnemonic;
|
||||
protected String suffix;
|
||||
protected AsmEntity[] operands;
|
||||
|
||||
public Instruction(String mnemonic) {
|
||||
this(mnemonic, "", new AsmEntity[0]);
|
||||
}
|
||||
|
||||
public Instruction(String mnemonic, String suffix, AsmEntity a1) {
|
||||
this(mnemonic, suffix, new AsmEntity[] { a1 });
|
||||
}
|
||||
|
||||
public Instruction(String mnemonic, String suffix,
|
||||
AsmEntity a1, AsmEntity a2) {
|
||||
this(mnemonic, suffix, new AsmEntity[] { a1, a2 });
|
||||
}
|
||||
|
||||
public Instruction(String mnemonic, String suffix, AsmEntity[] operands) {
|
||||
this.mnemonic = mnemonic;
|
||||
this.suffix = suffix;
|
||||
this.operands = operands;
|
||||
}
|
||||
|
||||
public boolean isInstruction() {
|
||||
return true;
|
||||
}
|
||||
|
||||
public String mnemonic() {
|
||||
return this.mnemonic;
|
||||
}
|
||||
|
||||
public int numOperands() {
|
||||
return this.operands.length;
|
||||
}
|
||||
|
||||
public AsmEntity operand1() {
|
||||
return this.operands[0];
|
||||
}
|
||||
|
||||
public AsmEntity operand2() {
|
||||
return this.operands[1];
|
||||
}
|
||||
|
||||
public String toSource() {
|
||||
StringBuffer buf = new StringBuffer();
|
||||
buf.append(mnemonic + suffix);
|
||||
String sep = "\t";
|
||||
for (int i = 0; i < operands.length; i++) {
|
||||
buf.append(sep); sep = ", ";
|
||||
buf.append(operands[i]);
|
||||
}
|
||||
return buf.toString();
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
return "#<Insn " + mnemonic + ">";
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
package net.loveruby.cflat.asm;
|
||||
|
||||
public class IntegerLiteral extends Literal {
|
||||
protected long value;
|
||||
|
||||
public IntegerLiteral(long n) {
|
||||
this.value = n;
|
||||
}
|
||||
|
||||
public long value() {
|
||||
return this.value;
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
return new Long(value).toString();
|
||||
}
|
||||
}
|
||||
|
|
@ -1,8 +1,8 @@
|
|||
package net.loveruby.cflat.asm;
|
||||
|
||||
public class Label extends AsmEntity {
|
||||
long seq;
|
||||
String name;
|
||||
public class Label extends Assembly {
|
||||
protected long seq;
|
||||
protected String name;
|
||||
|
||||
public Label(String n) {
|
||||
seq = -1;
|
||||
|
|
@ -22,6 +22,10 @@ public class Label extends AsmEntity {
|
|||
return name;
|
||||
}
|
||||
|
||||
public String toSource() {
|
||||
return name + ":";
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
return name;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,4 @@
|
|||
package net.loveruby.cflat.asm;
|
||||
|
||||
abstract public class Literal extends AsmEntity {
|
||||
}
|
||||
|
|
@ -1,17 +0,0 @@
|
|||
package net.loveruby.cflat.asm;
|
||||
|
||||
public class Reference extends Address {
|
||||
protected Label label;
|
||||
|
||||
public Reference(String sym) {
|
||||
this(new Label(sym));
|
||||
}
|
||||
|
||||
public Reference(Label label) {
|
||||
this.label = label;
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
return "$" + label.toString();
|
||||
}
|
||||
}
|
||||
|
|
@ -1,17 +0,0 @@
|
|||
package net.loveruby.cflat.asm;
|
||||
|
||||
public class SimpleAddress extends Address {
|
||||
Register base;
|
||||
|
||||
public SimpleAddress(Register reg) {
|
||||
base = reg;
|
||||
}
|
||||
|
||||
public Register base() {
|
||||
return base;
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
return "(" + base.toString() + ")";
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
package net.loveruby.cflat.asm;
|
||||
|
||||
public class Symbol extends Literal {
|
||||
protected Label label;
|
||||
|
||||
public Symbol(Label label) {
|
||||
this.label = label;
|
||||
}
|
||||
|
||||
public String symbol() {
|
||||
return label.name();
|
||||
}
|
||||
|
||||
public String toString() {
|
||||
return symbol();
|
||||
}
|
||||
}
|
||||
|
|
@ -26,6 +26,6 @@ abstract public class Function extends Entity {
|
|||
}
|
||||
|
||||
public AsmEntity address() {
|
||||
return new Reference(name());
|
||||
return new DirectAddress(new Label(name()));
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -20,7 +20,7 @@ public class UndefinedVariable extends Variable {
|
|||
}
|
||||
|
||||
public AsmEntity address() {
|
||||
return new Label(symbol());
|
||||
return new DirectAddress(new Label(symbol()));
|
||||
}
|
||||
|
||||
protected void _dump(Dumper d) {
|
||||
|
|
|
|||
|
|
@ -82,13 +82,13 @@ public class CodeGenerator extends Visitor implements ASTLHSVisitor {
|
|||
/** Linux/IA-32 dependent */
|
||||
// FIXME: PIC
|
||||
protected AsmEntity globalVariableAddress(String sym) {
|
||||
return new Label(csymbol(sym));
|
||||
return new Symbol(new Label(csymbol(sym)));
|
||||
}
|
||||
|
||||
/** Linux/IA-32 dependent */
|
||||
// FIXME: PIC
|
||||
protected AsmEntity commonSymbolAddress(String sym) {
|
||||
return new Label(csymbol(sym));
|
||||
return new Symbol(new Label(csymbol(sym)));
|
||||
}
|
||||
|
||||
/** Generates static variable entries */
|
||||
|
|
@ -866,20 +866,20 @@ public class CodeGenerator extends Visitor implements ASTLHSVisitor {
|
|||
return new Register(name);
|
||||
}
|
||||
|
||||
protected SimpleAddress mem(Register reg) {
|
||||
return new SimpleAddress(reg);
|
||||
protected IndirectAddress mem(Register reg) {
|
||||
return new IndirectAddress(reg);
|
||||
}
|
||||
|
||||
protected CompositeAddress mem(long offset, Register reg) {
|
||||
return new CompositeAddress(offset, reg);
|
||||
protected IndirectAddress mem(long offset, Register reg) {
|
||||
return new IndirectAddress(offset, reg);
|
||||
}
|
||||
|
||||
protected ImmediateValue imm(long n) {
|
||||
return new ImmediateValue(n);
|
||||
}
|
||||
|
||||
protected Reference imm(Label label) {
|
||||
return new Reference(label);
|
||||
protected ImmediateValue imm(Label label) {
|
||||
return new ImmediateValue(label);
|
||||
}
|
||||
|
||||
protected void load(Type type, AsmEntity addr, Register reg) {
|
||||
|
|
@ -909,7 +909,6 @@ public class CodeGenerator extends Visitor implements ASTLHSVisitor {
|
|||
}
|
||||
|
||||
public void comment(String str) { as.comment(str); }
|
||||
public void line(String str) { as.line(str); }
|
||||
public void _file(String name) { as._file(name); }
|
||||
public void _text() { as._text(); }
|
||||
public void _data() { as._data(); }
|
||||
|
|
|
|||
Loading…
Reference in New Issue