all: make __global behave consistent with const (#9711)
							parent
							
								
									49330af715
								
							
						
					
					
						commit
						70c651ff17
					
				| 
						 | 
				
			
			@ -4,8 +4,8 @@
 | 
			
		|||
module builtin
 | 
			
		||||
 | 
			
		||||
__global (
 | 
			
		||||
	g_m2_buf &byte 
 | 
			
		||||
	g_m2_ptr &byte 
 | 
			
		||||
	g_m2_buf &byte
 | 
			
		||||
	g_m2_ptr &byte
 | 
			
		||||
)
 | 
			
		||||
 | 
			
		||||
// isnil returns true if an object is nil (only for C objects).
 | 
			
		||||
| 
						 | 
				
			
			@ -48,7 +48,7 @@ __global (
 | 
			
		|||
	total_m              = i64(0)
 | 
			
		||||
	nr_mallocs           = int(0)
 | 
			
		||||
	// will be filled in cgen
 | 
			
		||||
	as_cast_type_indexes   []VCastTypeIndexName 
 | 
			
		||||
	as_cast_type_indexes []VCastTypeIndexName
 | 
			
		||||
)
 | 
			
		||||
 | 
			
		||||
fn __as_cast(obj voidptr, obj_type int, expected_type int) voidptr {
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -66,7 +66,9 @@ const (
 | 
			
		|||
)
 | 
			
		||||
 | 
			
		||||
// g_original_codepage - used to restore the original windows console code page when exiting
 | 
			
		||||
__global ( g_original_codepage = u32(0))
 | 
			
		||||
__global (
 | 
			
		||||
	g_original_codepage = u32(0)
 | 
			
		||||
)
 | 
			
		||||
 | 
			
		||||
// utf8 to stdout needs C.SetConsoleOutputCP(C.CP_UTF8)
 | 
			
		||||
fn C.GetConsoleOutputCP() u32
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1285,7 +1285,9 @@ pub fn (s string) ustring() ustring {
 | 
			
		|||
// A hack that allows to create ustring without allocations.
 | 
			
		||||
// It's called from functions like draw_text() where we know that the string is going to be freed
 | 
			
		||||
// right away. Uses global buffer for storing runes []int array.
 | 
			
		||||
__global ( g_ustring_runes []int )
 | 
			
		||||
__global (
 | 
			
		||||
	g_ustring_runes []int
 | 
			
		||||
)
 | 
			
		||||
 | 
			
		||||
pub fn (s string) ustring_tmp() ustring {
 | 
			
		||||
	if g_ustring_runes.len == 0 {
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -526,7 +526,8 @@ pub mut:
 | 
			
		|||
 | 
			
		||||
pub struct GlobalDecl {
 | 
			
		||||
pub:
 | 
			
		||||
	pos token.Position
 | 
			
		||||
	pos      token.Position
 | 
			
		||||
	is_block bool // __global() block
 | 
			
		||||
pub mut:
 | 
			
		||||
	fields       []GlobalField
 | 
			
		||||
	end_comments []Comment
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,3 +1,3 @@
 | 
			
		|||
vlib/v/checker/tests/globals/assign_no_type.vv:1:21: error: global assign must have a type and value, use `__global ( name = type(value) )` or `__global ( name type )`
 | 
			
		||||
vlib/v/checker/tests/globals/assign_no_type.vv:1:21: error: global assign must have a type and value, use `name = type(value)` or `name type`
 | 
			
		||||
    1 | __global ( test = 0 )
 | 
			
		||||
      |                     ^
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,3 +1,3 @@
 | 
			
		|||
vlib/v/checker/tests/globals/assign_no_value.vv:1:23: error: global assign must have a type and value, use `__global ( name = type(value) )` or `__global ( name type )`
 | 
			
		||||
vlib/v/checker/tests/globals/assign_no_value.vv:1:23: error: global assign must have a type and value, use `name = type(value)` or `name type`
 | 
			
		||||
    1 | __global ( test = int )
 | 
			
		||||
      |                       ^
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -0,0 +1,3 @@
 | 
			
		|||
vlib/v/checker/tests/globals/unexpected_eof.vv:3:1: error: unexpected eof, expecting ´)´
 | 
			
		||||
    1 | __global (
 | 
			
		||||
    2 |     x string
 | 
			
		||||
| 
						 | 
				
			
			@ -0,0 +1,2 @@
 | 
			
		|||
__global (
 | 
			
		||||
	x string
 | 
			
		||||
| 
						 | 
				
			
			@ -1083,21 +1083,23 @@ pub fn (mut f Fmt) for_stmt(node ast.ForStmt) {
 | 
			
		|||
}
 | 
			
		||||
 | 
			
		||||
pub fn (mut f Fmt) global_decl(node ast.GlobalDecl) {
 | 
			
		||||
	single := node.fields.len == 1
 | 
			
		||||
	if single {
 | 
			
		||||
		f.write('__global ( ')
 | 
			
		||||
	} else {
 | 
			
		||||
		f.writeln('__global (')
 | 
			
		||||
		f.indent++
 | 
			
		||||
	if node.fields.len == 0 && node.pos.line_nr == node.pos.last_line {
 | 
			
		||||
		f.writeln('__global ()')
 | 
			
		||||
		return
 | 
			
		||||
	}
 | 
			
		||||
	f.write('__global ')
 | 
			
		||||
	mut max := 0
 | 
			
		||||
	mut has_assign := false
 | 
			
		||||
	for field in node.fields {
 | 
			
		||||
		if field.name.len > max {
 | 
			
		||||
			max = field.name.len
 | 
			
		||||
		}
 | 
			
		||||
		if field.has_expr {
 | 
			
		||||
			has_assign = true
 | 
			
		||||
	if node.is_block {
 | 
			
		||||
		f.writeln('(')
 | 
			
		||||
		f.indent++
 | 
			
		||||
		for field in node.fields {
 | 
			
		||||
			if field.name.len > max {
 | 
			
		||||
				max = field.name.len
 | 
			
		||||
			}
 | 
			
		||||
			if field.has_expr {
 | 
			
		||||
				has_assign = true
 | 
			
		||||
			}
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	for field in node.fields {
 | 
			
		||||
| 
						 | 
				
			
			@ -1111,20 +1113,19 @@ pub fn (mut f Fmt) global_decl(node ast.GlobalDecl) {
 | 
			
		|||
			f.expr(field.expr)
 | 
			
		||||
			f.write(')')
 | 
			
		||||
		} else {
 | 
			
		||||
			if !single && has_assign {
 | 
			
		||||
				f.write('  ')
 | 
			
		||||
			}
 | 
			
		||||
			f.write('${f.table.type_to_str_using_aliases(field.typ, f.mod2alias)} ')
 | 
			
		||||
			f.write('${f.table.type_to_str_using_aliases(field.typ, f.mod2alias)}')
 | 
			
		||||
		}
 | 
			
		||||
		if !single {
 | 
			
		||||
		if node.is_block {
 | 
			
		||||
			f.writeln('')
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	if !single {
 | 
			
		||||
		f.indent--
 | 
			
		||||
	}
 | 
			
		||||
	f.comments_after_last_field(node.end_comments)
 | 
			
		||||
	f.writeln(')\n')
 | 
			
		||||
	if node.is_block {
 | 
			
		||||
		f.indent--
 | 
			
		||||
		f.writeln(')')
 | 
			
		||||
	} else {
 | 
			
		||||
		f.writeln('')
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
pub fn (mut f Fmt) go_expr(node ast.GoExpr) {
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -0,0 +1,10 @@
 | 
			
		|||
__global x = bool(true)
 | 
			
		||||
__global y f32
 | 
			
		||||
__global ()
 | 
			
		||||
__global (
 | 
			
		||||
	spam string
 | 
			
		||||
	foo  = int(5)
 | 
			
		||||
)
 | 
			
		||||
__global (
 | 
			
		||||
	a int
 | 
			
		||||
)
 | 
			
		||||
| 
						 | 
				
			
			@ -2818,17 +2818,19 @@ fn (mut p Parser) global_decl() ast.GlobalDecl {
 | 
			
		|||
		return ast.GlobalDecl{}
 | 
			
		||||
	}
 | 
			
		||||
	start_pos := p.tok.position()
 | 
			
		||||
	end_pos := p.tok.position()
 | 
			
		||||
	p.check(.key_global)
 | 
			
		||||
	if p.tok.kind != .lpar {
 | 
			
		||||
		p.error('globals must be grouped, e.g. `__global ( a = int(1) )`')
 | 
			
		||||
		return ast.GlobalDecl{}
 | 
			
		||||
	is_block := p.tok.kind == .lpar
 | 
			
		||||
	if is_block {
 | 
			
		||||
		p.next() // (
 | 
			
		||||
	}
 | 
			
		||||
	p.next() // (
 | 
			
		||||
	mut fields := []ast.GlobalField{}
 | 
			
		||||
	mut comments := []ast.Comment{}
 | 
			
		||||
	for {
 | 
			
		||||
		comments = p.eat_comments({})
 | 
			
		||||
		if is_block && p.tok.kind == .eof {
 | 
			
		||||
			p.error('unexpected eof, expecting ´)´')
 | 
			
		||||
			return ast.GlobalDecl{}
 | 
			
		||||
		}
 | 
			
		||||
		if p.tok.kind == .rpar {
 | 
			
		||||
			break
 | 
			
		||||
		}
 | 
			
		||||
| 
						 | 
				
			
			@ -2840,13 +2842,13 @@ fn (mut p Parser) global_decl() ast.GlobalDecl {
 | 
			
		|||
		}
 | 
			
		||||
		typ := p.parse_type()
 | 
			
		||||
		if p.tok.kind == .assign {
 | 
			
		||||
			p.error('global assign must have the type around the value, use `__global ( name = type(value) )`')
 | 
			
		||||
			p.error('global assign must have the type around the value, use `name = type(value)`')
 | 
			
		||||
			return ast.GlobalDecl{}
 | 
			
		||||
		}
 | 
			
		||||
		mut expr := ast.empty_expr()
 | 
			
		||||
		if has_expr {
 | 
			
		||||
			if p.tok.kind != .lpar {
 | 
			
		||||
				p.error('global assign must have a type and value, use `__global ( name = type(value) )` or `__global ( name type )`')
 | 
			
		||||
				p.error('global assign must have a type and value, use `name = type(value)` or `name type`')
 | 
			
		||||
				return ast.GlobalDecl{}
 | 
			
		||||
			}
 | 
			
		||||
			p.next() // (
 | 
			
		||||
| 
						 | 
				
			
			@ -2864,12 +2866,18 @@ fn (mut p Parser) global_decl() ast.GlobalDecl {
 | 
			
		|||
		fields << field
 | 
			
		||||
		p.global_scope.register(field)
 | 
			
		||||
		comments = []
 | 
			
		||||
		if !is_block {
 | 
			
		||||
			break
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	if is_block {
 | 
			
		||||
		p.check(.rpar)
 | 
			
		||||
	}
 | 
			
		||||
	p.check(.rpar)
 | 
			
		||||
	return ast.GlobalDecl{
 | 
			
		||||
		pos: start_pos.extend(end_pos)
 | 
			
		||||
		pos: start_pos.extend(p.prev_tok.position())
 | 
			
		||||
		fields: fields
 | 
			
		||||
		end_comments: comments
 | 
			
		||||
		is_block: is_block
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
		Loading…
	
		Reference in New Issue