Boehm-GC: fix global `const` handling (#9477)

* define global `__v_inside_init`

* unset `__v_inside_init` after `_vinit()`

* define `C.GC_MALLOC_UNCOLLECTABLE()`

* allocate uncollectable memory during `_vinit()`

* ci: run test cases with V copiler that uses GC-Boehm itself

* wrap `__v_inside_init` access into `#ifdef _VGCBOEHM`
pull/9483/head
Uwe Krüger 2021-03-26 15:44:45 +01:00 committed by GitHub
parent a38fc89150
commit 3220ab7053
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 33 additions and 15 deletions

View File

@ -129,7 +129,9 @@ jobs:
thirdparty/tcc/tcc.exe -version thirdparty/tcc/tcc.exe -version
./v -cg -o v cmd/v # Make sure vtcc can build itself twice ./v -cg -o v cmd/v # Make sure vtcc can build itself twice
- name: v self compilation with -gc boehm - name: v self compilation with -gc boehm
run: ./v -gc boehm -o v2 cmd/v && ./v2 -gc boehm -o v3 cmd/v && ./v3 -gc boehm -o v4 cmd/v run: |
./v -gc boehm -o v2 cmd/v && ./v2 -gc boehm -o v3 cmd/v && ./v3 -gc boehm -o v4 cmd/v
mv v4 v
- name: v doctor - name: v doctor
run: | run: |
./v doctor ./v doctor
@ -137,8 +139,7 @@ jobs:
run: | run: |
./v -gc boehm cmd/tools/test_if_v_test_system_works.v ./v -gc boehm cmd/tools/test_if_v_test_system_works.v
./cmd/tools/test_if_v_test_system_works ./cmd/tools/test_if_v_test_system_works
- name: Self tests with `-gc boehm` - name: Self tests with `-gc boehm` with V compiler using Boehm-GC itself
## The test cases are run with non-gc `v` for now
run: ./v -gc boehm -silent test-self run: ./v -gc boehm -silent test-self
- name: Test leak detector - name: Test leak detector
run: | run: |

View File

@ -189,7 +189,13 @@ pub fn malloc(n int) byteptr {
nr_mallocs++ nr_mallocs++
} $else { } $else {
$if gcboehm ? { $if gcboehm ? {
res = unsafe { C.GC_MALLOC(n) } unsafe {
if C.__v_inside_init == 0 {
res = C.GC_MALLOC(n)
} else {
res = C.GC_MALLOC_UNCOLLECTABLE(n)
}
}
} $else { } $else {
res = unsafe { C.malloc(n) } res = unsafe { C.malloc(n) }
} }
@ -282,16 +288,6 @@ pub fn realloc_data(old_data byteptr, old_size int, new_size int) byteptr {
return nptr return nptr
} }
// v_calloc dynamically allocates a zeroed `n` bytes block of memory on the heap.
// v_calloc returns a `byteptr` pointing to the memory address of the allocated space.
pub fn v_calloc(n int) byteptr {
$if gcboehm ? {
return C.GC_MALLOC(n)
} $else {
return C.calloc(1, n)
}
}
// vcalloc dynamically allocates a zeroed `n` bytes block of memory on the heap. // vcalloc dynamically allocates a zeroed `n` bytes block of memory on the heap.
// vcalloc returns a `byteptr` pointing to the memory address of the allocated space. // vcalloc returns a `byteptr` pointing to the memory address of the allocated space.
// Unlike `v_calloc` vcalloc checks for negative values given in `n`. // Unlike `v_calloc` vcalloc checks for negative values given in `n`.
@ -302,7 +298,11 @@ pub fn vcalloc(n int) byteptr {
return byteptr(0) return byteptr(0)
} }
$if gcboehm ? { $if gcboehm ? {
return C.GC_MALLOC(n) return if C.__v_inside_init == 0 {
byteptr(C.GC_MALLOC(n))
} else {
byteptr(C.GC_MALLOC_UNCOLLECTABLE(n))
}
} $else { } $else {
return C.calloc(1, n) return C.calloc(1, n)
} }

View File

@ -22,6 +22,8 @@ $if gcboehm_leak ? {
// compiled with `-gc boehm` or `-gc boehm_leak`. // compiled with `-gc boehm` or `-gc boehm_leak`.
fn C.GC_MALLOC(n size_t) voidptr fn C.GC_MALLOC(n size_t) voidptr
fn C.GC_MALLOC_UNCOLLECTABLE(n size_t) voidptr
fn C.GC_REALLOC(ptr voidptr, n size_t) voidptr fn C.GC_REALLOC(ptr voidptr, n size_t) voidptr
fn C.GC_FREE(ptr voidptr) fn C.GC_FREE(ptr voidptr)

View File

@ -6,6 +6,8 @@ module builtin
fn C.GC_MALLOC(n size_t) voidptr fn C.GC_MALLOC(n size_t) voidptr
fn C.GC_MALLOC_UNCOLLECTABLE(n size_t) voidptr
fn C.GC_REALLOC(ptr voidptr, n size_t) voidptr fn C.GC_REALLOC(ptr voidptr, n size_t) voidptr
fn C.GC_FREE(ptr voidptr) fn C.GC_FREE(ptr voidptr)

View File

@ -335,6 +335,9 @@ static inline bool _us64_lt(uint64_t a, int64_t b) { return a < INT64_MAX && (in
#endif #endif
//================================== GLOBALS =================================*/ //================================== GLOBALS =================================*/
#if defined(_VGCBOEHM)
int __v_inside_init = 1;
#endif
//byte g_str_buf[1024]; //byte g_str_buf[1024];
byte* g_str_buf; byte* g_str_buf;
int load_so(byteptr); int load_so(byteptr);

View File

@ -76,6 +76,11 @@ fn (mut g Gen) gen_c_main_header() {
g.writeln('#endif') g.writeln('#endif')
} }
g.writeln('\t_vinit(___argc, (voidptr)___argv);') g.writeln('\t_vinit(___argc, (voidptr)___argv);')
if g.pref.gc_mode in [.boehm, .boehm_leak] {
g.writeln('#if defined(_VGCBOEHM)')
g.writeln('\t__v_inside_init = 0;')
g.writeln('#endif')
}
if g.pref.is_prof { if g.pref.is_prof {
g.writeln('') g.writeln('')
g.writeln('\tatexit(vprint_profile_stats);') g.writeln('\tatexit(vprint_profile_stats);')
@ -167,6 +172,11 @@ pub fn (mut g Gen) gen_c_main_for_tests() {
g.writeln('#endif') g.writeln('#endif')
} }
g.writeln('\t_vinit(___argc, (voidptr)___argv);') g.writeln('\t_vinit(___argc, (voidptr)___argv);')
if g.pref.gc_mode in [.boehm, .boehm_leak] {
g.writeln('#if defined(_VGCBOEHM)')
g.writeln('\t__v_inside_init = 0;')
g.writeln('#endif')
}
all_tfuncs := g.get_all_test_function_names() all_tfuncs := g.get_all_test_function_names()
if g.pref.is_stats { if g.pref.is_stats {
g.writeln('\tmain__BenchedTests bt = main__start_testing($all_tfuncs.len, _SLIT("$g.pref.path"));') g.writeln('\tmain__BenchedTests bt = main__start_testing($all_tfuncs.len, _SLIT("$g.pref.path"));')