Commit Diff


commit - b472dc4b0fb08c37c9b539cad4c0eaa2cf05b01b
commit + cc17802d9c1b8d811f2045b6e047326d85dc3444
blob - a53351c28db4a20b91144e436234f89f1169f586
blob + e7327b6620de46d6741a80b92a4b7b576d5ce2b6
--- Makefile
+++ Makefile
@@ -13,7 +13,7 @@ CFLAGS	= ${CFLAGS_OS} ${COPT} -std=c2x
 LDFLAGS	= ${LDFLAGS_OS} -lpthread
 
 OBJ	= src/linurv.o src/ecall.o src/cpu.o src/exec.o
-T	= asm
+T	= test
 PROGS	= examples/test.elf	\
 	  examples/echo.elf	\
 	  examples/cat.elf	\
blob - b39eecdefe0f9e9d959459ada0c867b5b9d81afd
blob + 59f126f89644bd5a2f80bb454eb876f488386d09
--- examples/cat.c
+++ examples/cat.c
@@ -33,8 +33,8 @@ int main (int argc, char* argv[]) {
 
 		cat (file);
 
-		//if (file != stdin)
-		//	fclose (file);
+		if (file != stdin)
+			fclose (file);
 	}
 	return ec;
 }
blob - 55a7a59cd36faa349357bfd385c3c37bd7116c37
blob + 38e805d47cdc9eeb4bfd6a7c9acbf6074b47bbb7
--- examples/test.c
+++ examples/test.c
@@ -22,15 +22,11 @@ inline static void *sys_brk (void *ptr)
 }
 
 int main (int argc, char *argv[]) {
-	volatile int *ptr, *p2;
+	int *ptr;
 
-	ptr = sys_brk (NULL);
-	p2 = sys_brk ((void *)((size_t)ptr + 4096));
-	printf ("XXX ptr = %p, p2 = %p\n", ptr, p2);
+	ptr = malloc (4);
+	*ptr = 1;
+	free (ptr);
 
-	*ptr = 42;
-
-	printf ("XXX *ptr = %d\n", *ptr);
-
 	return 0;
 }
blob - 6aab3a3a59ada2565b3f6779c303333bfcb266b6
blob + 1e8765501eefc02cf51b9f751f1b7208f15ce810
--- src/cpu.c
+++ src/cpu.c
@@ -59,8 +59,9 @@ void cpu_exec (u32 instr)
 		cpu_set (rd, imm_u);
 		break;
 	case 0b0010111: // auipc rd, uimm
-		log ("auipc x%u, %"PRIu64, (uint)rd, imm_u);
-		cpu_set (rd, pc + imm_u - 4);
+		a = pc + imm_u - 4;
+		log ("auipc x%u, %"PRIu64 " ; %"PRIu64, (uint)rd, imm_u, a);
+		cpu_set (rd, a);
 		break;
 	case 0b1101111: // jal rd, jimm
 		log ("jal x%u, %"PRId64, (uint)rd, imm_j);
@@ -78,157 +79,162 @@ void cpu_exec (u32 instr)
 			goto ud;
 		}
 		break;
+#define br(name) log (name " x%u, x%u, %d ; %s", (uint)rs1, (uint)rs2, (int)imm_b, c ? "true" : "false")
 	case 0b1100011: // bcc rs1, rs2, bimm
 		a = cpu_get (rs1);
 		b = cpu_get (rs2);
 		switch (funct3) {
 		case 0b000:
-			name = "beq";
 			c = a == b;
+			br ("beq");
 			break;
 		case 0b001:
-			name = "bne";
 			c = a != b;
+			br ("bne");
 			break;
 		case 0b100:
-			name = "blt";
 			c = (i64)a < (i64)b;
+			br ("blt");
 			break;
 		case 0b101:
-			name = "bge";
 			c = (i64)a >= (i64)b;
+			br ("bge");
 			break;
 		case 0b110:
-			name = "bltu";
 			c = a < b;
+			br ("bltu");
 			break;
 		case 0b111:
-			name = "bgeu";
 			c = a >= b;
+			br ("bgeu");
 			break;
 		default:
 			goto ud;
 		}
-		log ("%s x%u, x%u, %d", name, (uint)rs1, (uint)rs2, (int)imm_b);
 		if (c)
 			pc += imm_b - 4;
 		break;
+#undef br
+#define lx(name) log (name " x%u, %d(x%u) ; *%p", (uint)rs2, (int)imm_i, (uint)rs1, (void *)a)
 	case 0b0000011: // lx rd, iimm(rs1)
 		a = cpu_get (rs1) + imm_i;
 		switch (funct3) {
 		case 0b000: // lb
-			name = "lb";
+			lx ("lb");
 			b = (i64)read_i8 (a);
 			break;
 		case 0b001: // lh
-			name = "lh";
+			lx ("lh");
 			b = (i64)read_i16 (a);
 			break;
 		case 0b010: // lw
-			name = "lw";
+			lx ("lw");
 			b = (i64)read_i32 (a);
 			break;
 		case 0b011: // ld
-			name = "ld";
+			lx ("ld");
 			b = read_u64 (a);
 			break;
 		case 0b100: // lbu
-			name = "lbu";
+			lx ("lbu");
 			b = read_u8 (a);
 			break;
 		case 0b101: // lhu
-			name = "lhu";
+			lx ("lhu");
 			b = read_u16 (a);
 			break;
 		case 0b110: // lwu
-			name = "lwu";
+			lx ("lwu");
 			b = read_u32 (a);
 			break;
 		default:
 			goto ud;
 		}
-		log ("%s x%u, %d(x%u)", name, (uint)rd, (int)imm_i, (uint)rs1);
 		cpu_set (rd, b);
 		break;
+#undef lx
+#define sx(name) log (name " x%u, %d(x%u) ; *%p = %u", (uint)rs2, (int)imm_s, (uint)rs1, (void *)b, (uint)a)
 	case 0b0100011: // sx rs2, simm(rs1)
 		a = cpu_get (rs2);
 		b = cpu_get (rs1) + imm_s;
 		switch (funct3) {
 		case 0b000: // sb
-			name = "sb";
+			sx ("sb");
 			write_u8 (b, a);
 			break;
 		case 0b001: // sh
-			name = "sh";
+			sx ("sh");
 			write_u16 (b, a);
 			break;
 		case 0b010: // sw
-			name = "sw";
+			sx ("sw");
 			write_u32 (b, a);
 			break;
 		case 0b011: // sd
-			 name = "sd";
+			sx ("sd");
 			 write_u64 (b, a);
 			 break;
 		default:
 			goto ud;
 		}
-		log ("%s x%u, %d(x%u)", name, (uint)rs2, (int)imm_s, (uint)rs1);
 		break;
+#undef sx
+#define alui(name) log (name " x%u, x%u, %"PRId64" ; "name"(%"PRId64", %"PRId64") = %"PRId64, \
+	(uint)rd, (uint)rs1, b, a, b, c)
 	case 0b0010011: // alui rd, rs1, iimm
 		a = cpu_get (rs1);
 		b = imm_i;
 		switch (funct3) {
 		case 0b000: // addi
-			name = "addi";
 			c = a + b;
+			alui ("addi");
 			break;
 		case 0b001: // slli
 			if (funct6 != 0)
 				goto ud;
-			name = "slli";
 			c = a << shamt;
+			alui ("slli");
 			break;
 		case 0b010: // slti
-			name = "slti";
 			c = (i64)a < (i64)b;
+			alui ("slti");
 			break;
 		case 0b011: // sltiu
-			name = "sltiu";
 			c = a < b;
+			alui ("sltiu");
 			break;
 		case 0b100: // xori
-			name = "xori";
 			c = a ^ b;
+			alui ("xori");
 			break;
 		case 0b101: // srli/srai
 			switch (funct6) {
 			case 0b000000:
-				name = "srli";
 				c = a >> shamt;
+				alui ("srli");
 				break;
 			case 0b010000:
-				name = "srai";
 				c = (i64)a >> shamt;
+				alui ("srai");
 				break;
 			default:
 				goto ud;
 			}
 			break;
 		case 0b110: // ori
-			name = "ori";
 			c = a | b;
+			alui ("ori");
 			break;
 		case 0b111: // andi
-			name = "andi";
 			c = a & b;
+			alui ("andi");
 			break;
 		default:
 			goto ud;
 		}
-		log ("%s x%u, x%u, %"PRId64, name, (uint)rd, (uint)rs1, (i64)imm_i);
 		cpu_set (rd, c);
 		break;
+#undef alui
 	case 0b0011011: // aluiw rd, rs1, iimm
 		a = cpu_get (rs1);
 		b = imm_i;
@@ -268,72 +274,72 @@ void cpu_exec (u32 instr)
 		log ("%s x%u, x%u, %"PRId64, name, (uint)rd, (uint)rs1, (i64)imm_i);
 		cpu_set (rd, c);
 		break;
+#define alu(name) log (name " x%u, x%u, x%u ; "name"(%"PRId64", %"PRId64") = %"PRId64, (uint)rd, (uint)rs1, (uint)rs2, a, b, c)
 	case 0b0110011: // alu rd, rs1, rs2
 		a = cpu_get (rs1);
 		b = cpu_get (rs2);
 		switch (funct10) {
-		case 0b0000000'000:
-			name = "add";
+		case 0b0000000'000: // add
 			c = a + b;
+			alu ("add");
 			break;
-		case 0b0000001'000:
-			name = "mul";
+		case 0b0000001'000: // mul
 			c = a * b;
+			alu ("mul");
 			break;
-		case 0b0100000'000:
-			name = "sub";
+		case 0b0100000'000: // sub
 			c = a - b;
+			alu ("sub");
 			break;
-		case 0b0000000'001:
-			name = "sll";
+		case 0b0000000'001: // sll
 			c = a << b;
+			alu ("sll");
 			break;
-		case 0b0000000'010:
-			name = "slt";
+		case 0b0000000'010: // slt
 			c = (i64)a < (i64)b;
+			alu ("slt");
 			break;
-		case 0b0000000'011:
-			name = "sltu";
+		case 0b0000000'011: // sltu
 			c = a < b;
+			alu ("sltu");
 			break;
-		case 0b0000000'100:
-			name = "xor";
+		case 0b0000000'100: // xor
 			c = a ^ b;
+			alu ("xor");
 			break;
-		case 0b0000001'100:
-			name = "div";
+		case 0b0000001'100: // div
 			c = b != 0 ? (i64)a / (i64)b : -1;
+			alu ("div");
 			break;
-		case 0b0000000'101:
-			name = "srl";
+		case 0b0000000'101: // srl
 			c = a >> (b & 0x3f);
+			alu ("srl");
 			break;
-		case 0b0000001'101:
-			name = "divu";
+		case 0b0000001'101: // divu
 			c = b != 0 ? a / b : -1;
+			alu ("divu");
 			break;
-		case 0b0100000'101:
-			name = "sra";
+		case 0b0100000'101: // sra
 			c = (i64)a >> (b & 0x3f);
+			alu ("sra");
 			break;
-		case 0b0000000'110:
-			name = "or";
+		case 0b0000000'110: // or
 			c = a | b;
+			alu ("or");
 			break;
-		case 0b0000001'110:
-			name = "rem";
+		case 0b0000001'110: // rem
 			c = b != 0 ? (i64)a % (i64)b : -1;
+			alu ("rem");
 			break;
-		case 0b0000000'111:
-			name = "and";
+		case 0b0000000'111: // and
 			c = a & b;
+			alu ("and");
 			break;
-		case 0b0000001'111:
-			name = "remu";
+		case 0b0000001'111: // remu
 			c = b != 0 ? a % b : -1;
+			alu ("remu");
 			break;
 		}
-		log ("%s x%u, x%u, x%u", name, (uint)rd, (uint)rs1, (uint)rs2);
 		cpu_set (rd, c);
 		break;
 	case 0b0111011: // aluw
@@ -341,31 +347,31 @@ void cpu_exec (u32 instr)
 		b = cpu_get (rs2);
 		switch (funct10) {
 		case 0b0000000'000: // addw
-			name = "addw";
-			c = a + b;
+			c = extend (a + b);
+			alu ("addw");
 			break;
 		case 0b0100000'000: // subw
-			name = "addw";
-			c = a - b;
+			c = extend (a - b);
+			alu ("subw");
 			break;
 		case 0b0000000'001: // sllw
-			name = "sllw";
-			c = a << (b & 0x1f);
+			c = extend (a << (b & 0x1f));
+			alu ("sllw");
 			break;
 		case 0b0000000'101: // srlw
-			name = "srlw";
-			c = a >> (b & 0x1f);
+			c = extend (a >> (b & 0x1f));
+			alu ("srlw");
 			break;
 		case 0b0100000'101: // sraw
-			name = "sraw";
-			c = (i64)a >> (b & 0x1f);
+			c = extend ((i64)a >> (b & 0x1f));
+			alu ("sraw");
 			break;
 		default:
 			goto ud;
 		}
-		log ("%s x%u, x%u, x%u", name, (uint)rd, (uint)rs1, (uint)rs2);
-		cpu_set (rd, extend ((i32)a));
+		cpu_set (rd, c);
 		break;
+#undef alu
 	case 0b0001111: // fence/fence.tso/pause
 		eprintf ("%08"PRIx64": efence\n", pc - 4);
 		break;
blob - 24edc75616e9d0e8c904863d33c37c7de7d42af7
blob + 2bda756a811c891b361ee1d635509cffe283eb18
--- src/ecall.c
+++ src/ecall.c
@@ -215,7 +215,7 @@ void ecall (void)
 
 
 	eprintf (
-			"ecall a7=%"PRIu64", a0=%"PRIu64", a1=%"PRIu64", a2=%"PRIu64", a3=%"PRIu64", a4=%"PRIu64", a5=%"PRIu64,
+			"ecall a7=%"PRIu64", a0=%"PRIu64", a1=%"PRIu64", a2=%"PRIu64", a3=%"PRIu64", a4=%"PRIu64", a5=%"PRIu64 "\n",
 			a7, a0, a1, a2, a3, a4, a5
 	);