cgen: put `shared` arrays and maps always on heap (#8496)
parent
4d268d1436
commit
17746561f2
|
@ -2522,11 +2522,13 @@ pub fn (mut c Checker) assign_stmt(mut assign_stmt ast.AssignStmt) {
|
|||
}
|
||||
mut ident_var_info := left.info as ast.IdentVar
|
||||
if ident_var_info.share == .shared_t {
|
||||
if left_type.nr_muls() > 1 {
|
||||
c.error('shared cannot be multi level reference', left.pos)
|
||||
}
|
||||
left_type = left_type.set_flag(.shared_f)
|
||||
left_type = left_type.set_nr_muls(1)
|
||||
if is_decl {
|
||||
if left_type.nr_muls() > 1 {
|
||||
c.error('shared cannot be multi level reference', left.pos)
|
||||
}
|
||||
left_type = left_type.set_nr_muls(1)
|
||||
}
|
||||
}
|
||||
if ident_var_info.share == .atomic_t {
|
||||
left_type = left_type.set_flag(.atomic_f)
|
||||
|
|
|
@ -14,17 +14,13 @@ fn (mut g Gen) array_init(node ast.ArrayInit) {
|
|||
g.is_amp = false
|
||||
if is_amp {
|
||||
g.out.go_back(1) // delete the `&` already generated in `prefix_expr()
|
||||
if g.is_shared {
|
||||
mut shared_typ := node.typ.set_flag(.shared_f)
|
||||
shared_styp = g.typ(shared_typ)
|
||||
g.writeln('($shared_styp*)__dup_shared_array(&($shared_styp){.val = ')
|
||||
} else {
|
||||
g.write('($styp*)memdup(ADDR($styp, ')
|
||||
}
|
||||
} else {
|
||||
if g.is_shared {
|
||||
g.writeln('{.val = ($styp*)')
|
||||
}
|
||||
}
|
||||
if g.is_shared {
|
||||
mut shared_typ := node.typ.set_flag(.shared_f)
|
||||
shared_styp = g.typ(shared_typ)
|
||||
g.writeln('($shared_styp*)__dup_shared_array(&($shared_styp){.val = ')
|
||||
} else if is_amp {
|
||||
g.write('($styp*)memdup(ADDR($styp, ')
|
||||
}
|
||||
if type_sym.kind == .array_fixed {
|
||||
g.write('{')
|
||||
|
@ -93,12 +89,10 @@ fn (mut g Gen) array_init(node ast.ArrayInit) {
|
|||
} else {
|
||||
g.write('0)')
|
||||
}
|
||||
if is_amp {
|
||||
if g.is_shared {
|
||||
g.write('}, sizeof($shared_styp))')
|
||||
} else {
|
||||
g.write('), sizeof($styp))')
|
||||
}
|
||||
if g.is_shared {
|
||||
g.write('}, sizeof($shared_styp))')
|
||||
} else if is_amp {
|
||||
g.write('), sizeof($styp))')
|
||||
}
|
||||
return
|
||||
}
|
||||
|
@ -121,12 +115,9 @@ fn (mut g Gen) array_init(node ast.ArrayInit) {
|
|||
}
|
||||
g.write('}))')
|
||||
if g.is_shared {
|
||||
g.write(', .mtx = sync__new_rwmutex()}')
|
||||
if is_amp {
|
||||
g.write(', sizeof($shared_styp))')
|
||||
}
|
||||
g.write('}, sizeof($shared_styp))')
|
||||
} else if is_amp {
|
||||
g.write(', sizeof($styp))')
|
||||
g.write('), sizeof($styp))')
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -2692,19 +2692,14 @@ fn (mut g Gen) expr(node ast.Expr) {
|
|||
g.is_amp = false
|
||||
if is_amp {
|
||||
g.out.go_back(1) // delete the `&` already generated in `prefix_expr()
|
||||
if g.is_shared {
|
||||
mut shared_typ := node.typ.set_flag(.shared_f)
|
||||
shared_styp = g.typ(shared_typ)
|
||||
g.writeln('($shared_styp*)__dup_shared_map(&($shared_styp){.val = ')
|
||||
} else {
|
||||
styp = g.typ(node.typ)
|
||||
g.write('($styp*)memdup(ADDR($styp, ')
|
||||
}
|
||||
} else {
|
||||
if g.is_shared {
|
||||
// TODO: shared objects on stack should be forbidden or auto-converted to heap
|
||||
g.writeln('{.val = ($styp*)')
|
||||
}
|
||||
}
|
||||
if g.is_shared {
|
||||
mut shared_typ := node.typ.set_flag(.shared_f)
|
||||
shared_styp = g.typ(shared_typ)
|
||||
g.writeln('($shared_styp*)__dup_shared_map(&($shared_styp){.val = ')
|
||||
} else if is_amp {
|
||||
styp = g.typ(node.typ)
|
||||
g.write('($styp*)memdup(ADDR($styp, ')
|
||||
}
|
||||
if size > 0 {
|
||||
if value_typ.kind == .function {
|
||||
|
@ -2730,10 +2725,7 @@ fn (mut g Gen) expr(node ast.Expr) {
|
|||
g.write('new_map_2(sizeof($key_typ_str), sizeof($value_typ_str), $hash_fn, $key_eq_fn, $clone_fn, $free_fn)')
|
||||
}
|
||||
if g.is_shared {
|
||||
g.write('}')
|
||||
if is_amp {
|
||||
g.write(', sizeof($shared_styp))')
|
||||
}
|
||||
g.write('}, sizeof($shared_styp))')
|
||||
} else if is_amp {
|
||||
g.write('), sizeof($styp))')
|
||||
}
|
||||
|
|
|
@ -40,3 +40,26 @@ fn test_shared_array() {
|
|||
assert f1 == 350020
|
||||
}
|
||||
}
|
||||
|
||||
fn test_shared_init_syntax() {
|
||||
shared foo := &[3, 5, 6, -12]
|
||||
shared bar := [-12.5, 23.125, 6.0625, 12.5]
|
||||
shared baz := &[]int{len: 5, cap: 12}
|
||||
shared qux := []f64{len: 7}
|
||||
lock foo {
|
||||
foo[2] = 20
|
||||
}
|
||||
lock bar {
|
||||
bar[3] = 12.5
|
||||
}
|
||||
lock baz, qux {
|
||||
baz[3] = 12
|
||||
qux[6] = -17.0625
|
||||
}
|
||||
rlock foo, bar, baz, qux {
|
||||
assert foo[2] == 20
|
||||
assert bar[3] == 12.5
|
||||
assert baz[3] == 12
|
||||
assert qux[6] == -17.0625
|
||||
}
|
||||
}
|
||||
|
|
|
@ -10,7 +10,7 @@ fn incr(shared foo map[string]int, key string, mut sem sync.Semaphore) {
|
|||
}
|
||||
|
||||
fn test_shared_array() {
|
||||
shared foo := &{'p': 10, 'q': 0}
|
||||
shared foo := {'p': 10, 'q': 0}
|
||||
lock foo {
|
||||
foo['q'] = 20
|
||||
}
|
||||
|
@ -35,3 +35,26 @@ fn test_shared_array() {
|
|||
assert fq == 350020
|
||||
}
|
||||
}
|
||||
|
||||
fn test_shared_init_syntax() {
|
||||
shared foo := &{'p': 17, 'q': -3, 'qwertz': 10}
|
||||
shared bar := {'wer': 13.75, 'cvbn': -7.25, 'asd': -0.0625}
|
||||
shared baz := &map[string]int{}
|
||||
shared qux := map[string]f64{}
|
||||
lock foo {
|
||||
foo['q'] = 20
|
||||
}
|
||||
lock bar {
|
||||
bar['asd'] = 12.5
|
||||
}
|
||||
lock baz, qux {
|
||||
baz['wer'] = 12
|
||||
qux['abc'] = -17.0625
|
||||
}
|
||||
rlock foo, bar, baz, qux {
|
||||
assert foo['q'] == 20
|
||||
assert bar['asd'] == 12.5
|
||||
assert baz['wer'] == 12
|
||||
assert qux['abc'] == -17.0625
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue