100% coverage
This commit is contained in:
parent
49ed7c5df5
commit
efe42f0bf8
@ -138,6 +138,7 @@ $ sh boot.sh
|
|||||||
- 函数只支持最多八个参数。函数声明中支持可变参数,仅用于兼容 C 语言库。
|
- 函数只支持最多八个参数。函数声明中支持可变参数,仅用于兼容 C 语言库。
|
||||||
- 类型检查有遗漏,若 C 编译器报错,而本语言编译通过,就可以认为是 UB。
|
- 类型检查有遗漏,若 C 编译器报错,而本语言编译通过,就可以认为是 UB。
|
||||||
- 例如函数调用的参数和 `return` 语句不会检查类型。
|
- 例如函数调用的参数和 `return` 语句不会检查类型。
|
||||||
|
- 赋值和比较时没有类型检查,这是为了方便 `0` 成为空指针常量。
|
||||||
|
|
||||||
|
|
||||||
## 限制
|
## 限制
|
||||||
|
13
boot.c
13
boot.c
@ -1095,10 +1095,6 @@ int asm_add(int lhs, int rhs) {
|
|||||||
idx = lhs;
|
idx = lhs;
|
||||||
}
|
}
|
||||||
int ptr_type = reg_type[ptr];
|
int ptr_type = reg_type[ptr];
|
||||||
if (ptr_type == TYPE_VOID_PTR) {
|
|
||||||
fprintf(stderr, "void pointer cannot be arithmetically operated\n");
|
|
||||||
exit(1);
|
|
||||||
}
|
|
||||||
int offset = next_reg(TYPE_INT);
|
int offset = next_reg(TYPE_INT);
|
||||||
_asm_ri("slli", offset, idx, log_step_of(ptr_type));
|
_asm_ri("slli", offset, idx, log_step_of(ptr_type));
|
||||||
return asm_rr(ptr_type, "add", ptr, offset);
|
return asm_rr(ptr_type, "add", ptr, offset);
|
||||||
@ -1120,10 +1116,6 @@ int asm_sub(int lhs, int rhs) {
|
|||||||
fprintf(stderr, "pointer type mismatch\n");
|
fprintf(stderr, "pointer type mismatch\n");
|
||||||
exit(1);
|
exit(1);
|
||||||
}
|
}
|
||||||
if (lhs_type == TYPE_VOID_PTR) {
|
|
||||||
fprintf(stderr, "void pointer cannot be arithmetically operated\n");
|
|
||||||
exit(1);
|
|
||||||
}
|
|
||||||
int diff = asm_rr(TYPE_INT, "sub", lhs, rhs);
|
int diff = asm_rr(TYPE_INT, "sub", lhs, rhs);
|
||||||
_asm_ri("srai", diff, diff, log_step_of(lhs_type));
|
_asm_ri("srai", diff, diff, log_step_of(lhs_type));
|
||||||
return diff;
|
return diff;
|
||||||
@ -1151,6 +1143,7 @@ int addressof(int reg) {
|
|||||||
indirection[reg] = 0;
|
indirection[reg] = 0;
|
||||||
} else {
|
} else {
|
||||||
printf("cannot take address of this expression");
|
printf("cannot take address of this expression");
|
||||||
|
exit(1);
|
||||||
}
|
}
|
||||||
return reg;
|
return reg;
|
||||||
}
|
}
|
||||||
@ -1651,10 +1644,6 @@ void parse_local_variable(int type) {
|
|||||||
unget_token();
|
unget_token();
|
||||||
expect_token(TOKEN_ASSIGN);
|
expect_token(TOKEN_ASSIGN);
|
||||||
int reg = parse_expr();
|
int reg = parse_expr();
|
||||||
if (type != reg_type[reg]) {
|
|
||||||
fprintf(stderr, "type mismatch in assignment\n");
|
|
||||||
exit(1);
|
|
||||||
}
|
|
||||||
store_into_local(reg, slot);
|
store_into_local(reg, slot);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2,8 +2,8 @@ mkdir -p cov && cd cov &&
|
|||||||
rm *
|
rm *
|
||||||
gcc --coverage -g -O0 ../boot.c -o boot.elf
|
gcc --coverage -g -O0 ../boot.c -o boot.elf
|
||||||
for i in ../test/**/*.c; do
|
for i in ../test/**/*.c; do
|
||||||
echo "Running coverage for test '$(basename $i .c)'"
|
echo "Running coverage for test '$i'"
|
||||||
./boot.elf < $i > /dev/null
|
./boot.elf < $i > /dev/null 2>/dev/null
|
||||||
gcov boot.elf-boot.c
|
gcov boot.elf-boot.c
|
||||||
done
|
done
|
||||||
|
|
||||||
|
2
run.sh
2
run.sh
@ -3,4 +3,4 @@ gcc boot.c -o boot.elf &&
|
|||||||
riscv64-linux-gnu-gcc-12 -static $1.s -o $1.elf &&
|
riscv64-linux-gnu-gcc-12 -static $1.s -o $1.elf &&
|
||||||
qemu-riscv64 $1.elf
|
qemu-riscv64 $1.elf
|
||||||
echo $?
|
echo $?
|
||||||
rm $1.s $1.elf boot.elf
|
rm $1.s $1.elf boot.elf 2> /dev/null
|
||||||
|
3
test/error/addressof_rvalue.c
Normal file
3
test/error/addressof_rvalue.c
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
int main() {
|
||||||
|
&0;
|
||||||
|
}
|
4
test/error/deref_non_ptr.c
Normal file
4
test/error/deref_non_ptr.c
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
int main() {
|
||||||
|
int a;
|
||||||
|
*a;
|
||||||
|
}
|
4
test/error/deref_void_ptr.c
Normal file
4
test/error/deref_void_ptr.c
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
int main() {
|
||||||
|
void* p;
|
||||||
|
*p;
|
||||||
|
}
|
3
test/error/endless_char.c
Normal file
3
test/error/endless_char.c
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
int main() {
|
||||||
|
'
|
||||||
|
}
|
1
test/error/endless_comment.c
Normal file
1
test/error/endless_comment.c
Normal file
@ -0,0 +1 @@
|
|||||||
|
/*
|
3
test/error/endless_string.c
Normal file
3
test/error/endless_string.c
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
int main() {
|
||||||
|
"
|
||||||
|
}
|
3
test/error/invalid_break.c
Normal file
3
test/error/invalid_break.c
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
int main() {
|
||||||
|
break;
|
||||||
|
}
|
3
test/error/invalid_continue.c
Normal file
3
test/error/invalid_continue.c
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
int main() {
|
||||||
|
continue;
|
||||||
|
}
|
1
test/error/invalid_dots.c
Normal file
1
test/error/invalid_dots.c
Normal file
@ -0,0 +1 @@
|
|||||||
|
.
|
3
test/error/invalid_escape.c
Normal file
3
test/error/invalid_escape.c
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
int main() {
|
||||||
|
return '\i';
|
||||||
|
}
|
1
test/error/negative_array_size.c
Normal file
1
test/error/negative_array_size.c
Normal file
@ -0,0 +1 @@
|
|||||||
|
int a[-1];
|
1
test/error/unexpected_char.c
Normal file
1
test/error/unexpected_char.c
Normal file
@ -0,0 +1 @@
|
|||||||
|
`
|
1
test/error/unexpected_global.c
Normal file
1
test/error/unexpected_global.c
Normal file
@ -0,0 +1 @@
|
|||||||
|
0
|
3
test/error/unexpected_token.c
Normal file
3
test/error/unexpected_token.c
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
int main() {
|
||||||
|
if 1
|
||||||
|
}
|
2
test/error/variable_array_size.c
Normal file
2
test/error/variable_array_size.c
Normal file
@ -0,0 +1,2 @@
|
|||||||
|
int size = 10;
|
||||||
|
int a[size];
|
1
test/error/void_arg.c
Normal file
1
test/error/void_arg.c
Normal file
@ -0,0 +1 @@
|
|||||||
|
void f(void a) {}
|
1
test/error/void_global.c
Normal file
1
test/error/void_global.c
Normal file
@ -0,0 +1 @@
|
|||||||
|
void a;
|
3
test/error/void_local.c
Normal file
3
test/error/void_local.c
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
void f() {
|
||||||
|
void a;
|
||||||
|
}
|
28
test/operator/assign.c
Normal file
28
test/operator/assign.c
Normal file
@ -0,0 +1,28 @@
|
|||||||
|
int printf(char* format, ...);
|
||||||
|
|
||||||
|
int main() {
|
||||||
|
int a = 5;
|
||||||
|
int b = 4;
|
||||||
|
a += b;
|
||||||
|
printf("%d\n", a);
|
||||||
|
a -= b;
|
||||||
|
printf("%d\n", a);
|
||||||
|
a *= b;
|
||||||
|
printf("%d\n", a);
|
||||||
|
a /= b;
|
||||||
|
printf("%d\n", a);
|
||||||
|
a %= b;
|
||||||
|
printf("%d\n", a);
|
||||||
|
a &= b;
|
||||||
|
printf("%d\n", a);
|
||||||
|
a |= b;
|
||||||
|
printf("%d\n", a);
|
||||||
|
a ^= b;
|
||||||
|
printf("%d\n", a);
|
||||||
|
a = b;
|
||||||
|
printf("%d\n", a);
|
||||||
|
a <<= b;
|
||||||
|
printf("%d\n", a);
|
||||||
|
a >>= b;
|
||||||
|
printf("%d\n", a);
|
||||||
|
}
|
4
test/unsupported/address_of_pointer.c
Normal file
4
test/unsupported/address_of_pointer.c
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
int main() {
|
||||||
|
int* p;
|
||||||
|
&p;
|
||||||
|
}
|
1
test/unsupported/array_of_pointer_arg.c
Normal file
1
test/unsupported/array_of_pointer_arg.c
Normal file
@ -0,0 +1 @@
|
|||||||
|
void f(int* a[]) {}
|
1
test/unsupported/array_of_pointer_global.c
Normal file
1
test/unsupported/array_of_pointer_global.c
Normal file
@ -0,0 +1 @@
|
|||||||
|
int* a[10];
|
@ -1,3 +1,3 @@
|
|||||||
int main() {
|
void f() {
|
||||||
int* a[10];
|
int* a[10];
|
||||||
}
|
}
|
Loading…
Reference in New Issue
Block a user