diff options
| author | Daniel Gavin <danielgavin5@hotmail.com> | 2022-04-15 19:56:20 +0200 |
|---|---|---|
| committer | Daniel Gavin <danielgavin5@hotmail.com> | 2022-04-15 19:56:20 +0200 |
| commit | 1ff3cccc05724f1a2485edbbace6ac540c4cb485 (patch) | |
| tree | f72ff54ba467041a0c2db247d46efc53eeb37f2c /src | |
| parent | b4720f71d63f08ec6a734fb79fb0816756484ac6 (diff) | |
Add proper multi_pointer support and fix range half range op
Diffstat (limited to 'src')
| -rw-r--r-- | src/common/ast.odin | 4 | ||||
| -rw-r--r-- | src/server/analysis.odin | 61 | ||||
| -rw-r--r-- | src/server/collector.odin | 42 | ||||
| -rw-r--r-- | src/server/definition.odin | 2 | ||||
| -rw-r--r-- | src/server/rename.odin | 3 | ||||
| -rw-r--r-- | src/server/requests.odin | 3 | ||||
| -rw-r--r-- | src/server/semantic_tokens.odin | 3 | ||||
| -rw-r--r-- | src/server/symbol.odin | 7 | ||||
| -rw-r--r-- | src/testing/testing.odin | 2 |
9 files changed, 108 insertions, 19 deletions
diff --git a/src/common/ast.odin b/src/common/ast.odin index c8398ae..841c519 100644 --- a/src/common/ast.odin +++ b/src/common/ast.odin @@ -637,6 +637,10 @@ node_equal_node :: proc(a, b: ^ast.Node) -> bool { if n, ok := a.derived.(^Dynamic_Array_Type); ok { return node_equal(n.elem, m.elem) } + case ^ast.Multi_Pointer_Type: + if n, ok := a.derived.(^Multi_Pointer_Type); ok { + return node_equal(n.elem, m.elem) + } case ^Struct_Type: if n, ok := a.derived.(^Struct_Type); ok { ret := node_equal(n.poly_params, m.poly_params) diff --git a/src/server/analysis.odin b/src/server/analysis.odin index 7ad405b..8979fe1 100644 --- a/src/server/analysis.odin +++ b/src/server/analysis.odin @@ -597,6 +597,26 @@ is_symbol_same_typed :: proc(ast_context: ^AstContext, a, b: Symbol, flags: ast. } return is_symbol_same_typed(ast_context, a_symbol, b_symbol) + case SymbolMultiPointer: + b_value := b.value.(SymbolMultiPointer) + + a_symbol: Symbol + b_symbol: Symbol + ok: bool + + a_symbol, ok = resolve_type_expression(ast_context, a_value.expr) + + if !ok { + return false + } + + b_symbol, ok = resolve_type_expression(ast_context, b_value.expr) + + if !ok { + return false + } + + return is_symbol_same_typed(ast_context, a_symbol, b_symbol) case SymbolDynamicArrayValue: b_value := b.value.(SymbolDynamicArrayValue) @@ -854,6 +874,8 @@ resolve_type_expression :: proc(ast_context: ^AstContext, node: ^ast.Expr) -> (S return make_symbol_array_from_ast(ast_context, v^, ast_context.field_name), true case ^Dynamic_Array_Type: return make_symbol_dynamic_array_from_ast(ast_context, v^, ast_context.field_name), true + case ^Multi_Pointer_Type: + return make_symbol_multi_pointer_from_ast(ast_context, v^, ast_context.field_name), true case ^Map_Type: return make_symbol_map_from_ast(ast_context, v^, ast_context.field_name), true case ^Proc_Type: @@ -923,10 +945,6 @@ resolve_type_expression :: proc(ast_context: ^AstContext, node: ^ast.Expr) -> (S symbol, ok := resolve_type_expression(ast_context, v.elem) symbol.pointers += 1 return symbol, ok - case ^Multi_Pointer_Type: - symbol, ok := resolve_type_expression(ast_context, v.elem) - symbol.pointers += 1 - return symbol, ok case ^Index_Expr: indexed, ok := resolve_type_expression(ast_context, v.expr) @@ -945,6 +963,8 @@ resolve_type_expression :: proc(ast_context: ^AstContext, node: ^ast.Expr) -> (S symbol, ok = resolve_type_expression(ast_context, v2.expr) case SymbolMapValue: symbol, ok = resolve_type_expression(ast_context, v2.value) + case SymbolMultiPointer: + symbol, ok = resolve_type_expression(ast_context, v2.expr) } symbol.type = indexed.type @@ -1469,6 +1489,9 @@ resolve_symbol_return :: proc(ast_context: ^AstContext, symbol: Symbol, ok := tr } case SymbolGenericValue: ret, ok := resolve_type_expression(ast_context, v.expr) + if symbol.type == .Variable { + ret.type = symbol.type + } return ret, ok } @@ -1702,6 +1725,21 @@ make_symbol_dynamic_array_from_ast :: proc(ast_context: ^AstContext, v: ast.Dyna return symbol } +make_symbol_multi_pointer_from_ast :: proc(ast_context: ^AstContext, v: ast.Multi_Pointer_Type, name: string) -> Symbol { + symbol := Symbol { + range = common.get_token_range(v.node, ast_context.file.src), + type = .Variable, + pkg = get_package_from_node(v.node), + name = name, + } + + symbol.value = SymbolMultiPointer { + expr = v.elem, + } + + return symbol +} + make_symbol_map_from_ast :: proc(ast_context: ^AstContext, v: ast.Map_Type, name: string) -> Symbol { symbol := Symbol { range = common.get_token_range(v.node, ast_context.file.src), @@ -2208,7 +2246,16 @@ get_locals_for_range_stmt :: proc(file: ast.File, stmt: ast.Range_Stmt, ast_cont if stmt.expr == nil { return } - + + if binary, ok := stmt.expr.derived.(^ast.Binary_Expr); ok { + if binary.op.kind == .Range_Half { + if ident, ok := stmt.vals[0].derived.(^Ident); ok { + store_local(ast_context, make_int_ast(ast_context), ident.pos.offset, ident.name, ast_context.local_id) + ast_context.variables[ident.name] = true + } + } + } + if symbol, ok := resolve_type_expression(ast_context, stmt.expr); ok { #partial switch v in symbol.value { case SymbolMapValue: @@ -2626,6 +2673,8 @@ get_signature :: proc(ast_context: ^AstContext, ident: ast.Ident, symbol: Symbol else { return "union" } + case SymbolMultiPointer: + return strings.concatenate(a = {"[^]", common.node_to_string(v.expr)}, allocator = ast_context.allocator) case SymbolDynamicArrayValue: return strings.concatenate(a = {"[dynamic]", common.node_to_string(v.expr)}, allocator = ast_context.allocator) case SymbolSliceValue: @@ -3358,6 +3407,8 @@ get_document_position_node :: proc(node: ^ast.Node, position_context: ^DocumentP get_document_position(n.elem, position_context) case ^Dynamic_Array_Type: get_document_position(n.elem, position_context) + case ^Multi_Pointer_Type: + get_document_position(n.elem, position_context) case ^Struct_Type: get_document_position(n.poly_params, position_context) get_document_position(n.align, position_context) diff --git a/src/server/collector.odin b/src/server/collector.odin index cf7e629..2de0068 100644 --- a/src/server/collector.odin +++ b/src/server/collector.odin @@ -231,6 +231,16 @@ collect_dynamic_array :: proc(collection: ^SymbolCollection, array: ast.Dynamic_ } } +collect_multi_pointer :: proc(collection: ^SymbolCollection, array: ast.Multi_Pointer_Type, package_map: map[string]string) -> SymbolMultiPointer { + elem := clone_type(array.elem, collection.allocator, &collection.unique_strings) + + replace_package_alias(elem, package_map, collection) + + return SymbolMultiPointer { + expr = elem, + } +} + collect_generic :: proc(collection: ^SymbolCollection, expr: ^ast.Expr, package_map: map[string]string, uri: string) -> SymbolGenericValue { //Bit hacky right now, but it's hopefully a temporary solution. //In the c package code it uses a documentation package(builtin). @@ -346,6 +356,10 @@ collect_symbols :: proc(collection: ^SymbolCollection, file: ast.File, uri: stri token = v^ token_type = .Variable symbol.value = collect_dynamic_array(collection, v^, package_map) + case ^ast.Multi_Pointer_Type: + token = v^ + token_type = .Variable + symbol.value = collect_multi_pointer(collection, v^, package_map) case ^ast.Basic_Lit: token = v^ symbol.value = collect_generic(collection, col_expr, package_map, uri) @@ -445,16 +459,26 @@ collect_references :: proc(collection: ^SymbolCollection, file: ast.File, uri: s parse_imports(&document, &common.config) symbols_and_nodes := resolve_entire_file(&document, common.scratch_allocator(document.allocator)) - + for k, v in symbols_and_nodes { - if pkg, ok := &collection.references[v.symbol.pkg]; ok { - if ref, ok := &pkg[v.symbol.name]; ok { - if ident, ok := v.node.derived.(^ast.Ident); ok { - //append(&ref.identifiers, cast(^ast.Ident)clone_type(ident, collection.allocator, nil)) - } else if selector, ok := v.node.derived.(^ast.Selector_Expr); ok { - //append(&ref.selectors, cast(^ast.Selector_Expr)clone_type(selector, collection.allocator, nil)) - } - } + pkg: ^map[string]Reference + + if pkg, ok = &collection.references[v.symbol.pkg]; !ok { + collection.references[get_index_unique_string(collection, v.symbol.pkg)] = make(map[string]Reference, 100, collection.allocator) + pkg = &collection.references[v.symbol.pkg] + } + + ref: ^Reference + + if ref, ok := &pkg[v.symbol.name]; !ok { + pkg[get_index_unique_string(collection, v.symbol.name)] = {} + ref = &pkg[v.symbol.name] + } + + if ident, ok := v.node.derived.(^ast.Ident); ok { + append(&ref.identifiers, cast(^ast.Ident)clone_type(ident, collection.allocator, nil)) + } else if selector, ok := v.node.derived.(^ast.Selector_Expr); ok { + append(&ref.selectors, cast(^ast.Selector_Expr)clone_type(selector, collection.allocator, nil)) } } diff --git a/src/server/definition.odin b/src/server/definition.odin index 4447bb2..3bcdcb3 100644 --- a/src/server/definition.odin +++ b/src/server/definition.odin @@ -79,7 +79,6 @@ get_definition_location :: proc(document: ^common.Document, position: common.Pos field: string if position_context.field != nil { - #partial switch v in position_context.field.derived { case ^ast.Ident: field = v.name @@ -110,7 +109,6 @@ get_definition_location :: proc(document: ^common.Document, position: common.Pos return {}, false } } else if position_context.identifier != nil { - if resolved, ok := resolve_location_identifier(&ast_context, position_context.identifier.derived.(^ast.Ident)^); ok { location.range = resolved.range uri = resolved.uri diff --git a/src/server/rename.odin b/src/server/rename.odin index 7c4629e..16becbc 100644 --- a/src/server/rename.odin +++ b/src/server/rename.odin @@ -12,6 +12,8 @@ get_rename :: proc(document: ^common.Document, new_text: string, position: commo edits := make([dynamic]TextEdit, context.temp_allocator) + + /* symbol_and_nodes := resolve_entire_file(document) ast_context := make_ast_context(document.ast, document.imports, document.package_name, document.uri.uri) @@ -63,6 +65,7 @@ get_rename :: proc(document: ^common.Document, new_text: string, position: commo append(&document_changes, document_change) workspace.documentChanges = document_changes[:] + */ return workspace, true }
\ No newline at end of file diff --git a/src/server/requests.odin b/src/server/requests.odin index fdc5d31..3aaff45 100644 --- a/src/server/requests.odin +++ b/src/server/requests.odin @@ -453,7 +453,6 @@ request_initialize :: proc (params: json.Value, id: RequestId, config: ^common.C config.collections["vendor"] = path.join(elems = {forward_path, "vendor"}, allocator = context.allocator) } - for format in initialize_params.capabilities.textDocument.hover.contentFormat { if format == "markdown" { config.hover_support_md = true @@ -502,7 +501,7 @@ request_initialize :: proc (params: json.Value, id: RequestId, config: ^common.C includeText = true, }, }, - renameProvider = false, + renameProvider = true, definitionProvider = true, completionProvider = CompletionOptions { resolveProvider = false, diff --git a/src/server/semantic_tokens.odin b/src/server/semantic_tokens.odin index acbe1a5..e373a36 100644 --- a/src/server/semantic_tokens.odin +++ b/src/server/semantic_tokens.odin @@ -306,6 +306,9 @@ visit_node :: proc(node: ^ast.Node, builder: ^SemanticTokenBuilder, ast_context: case ^Dynamic_Array_Type: write_semantic_string(builder, n.dynamic_pos, "dynamic", ast_context.file.src, .Keyword, .None) visit(n.elem, builder, ast_context) + case ^Multi_Pointer_Type: + write_semantic_string(builder, n.pos, "[^]", ast_context.file.src, .Keyword, .None) + visit(n.elem, builder, ast_context) case ^Field_Value: if ident, ok := n.field.derived.(^Ident); ok { write_semantic_node(builder, n.field, ast_context.file.src, .Property, .None) diff --git a/src/server/symbol.odin b/src/server/symbol.odin index b6a3a3c..791c609 100644 --- a/src/server/symbol.odin +++ b/src/server/symbol.odin @@ -52,6 +52,10 @@ SymbolDynamicArrayValue :: struct { expr: ^ast.Expr, } +SymbolMultiPointer :: struct { + expr: ^ast.Expr, +} + SymbolFixedArrayValue :: struct { len: ^ast.Expr, expr: ^ast.Expr, @@ -97,6 +101,7 @@ SymbolValue :: union { SymbolAggregateValue, SymbolDynamicArrayValue, SymbolFixedArrayValue, + SymbolMultiPointer, SymbolMapValue, SymbolSliceValue, SymbolBasicValue, @@ -160,6 +165,8 @@ free_symbol :: proc(symbol: Symbol, allocator: mem.Allocator) { } switch v in symbol.value { + case SymbolMultiPointer: + common.free_ast(v.expr, allocator) case SymbolProcedureValue: common.free_ast(v.return_types, allocator) common.free_ast(v.arg_types, allocator) diff --git a/src/testing/testing.odin b/src/testing/testing.odin index 356c457..a824d87 100644 --- a/src/testing/testing.odin +++ b/src/testing/testing.odin @@ -36,7 +36,7 @@ setup :: proc(src: ^Source) { src.document.allocator = new(common.Scratch_Allocator); src.document.package_name = "test"; - common.scratch_allocator_init(src.document.allocator, mem.kilobytes(200), context.temp_allocator); + common.scratch_allocator_init(src.document.allocator, mem.Kilobyte * 200, context.temp_allocator); //no unicode in tests currently current, last: u8; |