Now builds!
This commit is contained in:
		
							parent
							
								
									3bdb2ee444
								
							
						
					
					
						commit
						05d75781de
					
				
							
								
								
									
										184
									
								
								src/analysis.zig
									
									
									
									
									
								
							
							
						
						
									
										184
									
								
								src/analysis.zig
									
									
									
									
									
								
							| @ -376,110 +376,81 @@ pub fn resolveTypeOfNode(store: *DocumentStore, arena: *std.heap.ArenaAllocator, | |||||||
|         .Call => { |         .Call => { | ||||||
|             const call = node.cast(ast.Node.Call).?; |             const call = node.cast(ast.Node.Call).?; | ||||||
| 
 | 
 | ||||||
|             // @TODO use BoundTypeParams: ParamDecl -> NodeWithHandle or something |  | ||||||
|             const decl = (try resolveTypeOfNode(store, arena, .{ .node = call.lhs, .handle = handle })) orelse return null; |             const decl = (try resolveTypeOfNode(store, arena, .{ .node = call.lhs, .handle = handle })) orelse return null; | ||||||
|             if (decl.node.cast(ast.Node.FnProto)) |fn_decl| { |             if (decl.node.cast(ast.Node.FnProto)) |fn_decl| { | ||||||
|  |                 // @TODO use BoundTypeParams: ParamDecl -> NodeWithHandle or something | ||||||
|                 // Add type param values to the scope nodes |                 // Add type param values to the scope nodes | ||||||
|                 const param_len = std.math.min(call.params_len, fn_decl.params_len); |                 // const param_len = std.math.min(call.params_len, fn_decl.params_len); | ||||||
|                 var scope_nodes = std.ArrayList(*ast.Node).fromOwnedSlice(&analysis_ctx.arena.allocator, analysis_ctx.scope_nodes); |                 // for (fn_decl.paramsConst()) |decl_param, param_idx| { | ||||||
|                 var analysis_ctx_clone = analysis_ctx.clone() catch return null; |                 //     if (param_idx >= param_len) break; | ||||||
|                 for (fn_decl.paramsConst()) |decl_param, param_idx| { |                 //     if (decl_param.name_token == null) continue; | ||||||
|                     if (param_idx >= param_len) break; |                 //     const type_param = switch (decl_param.param_type) { | ||||||
|                     if (decl_param.name_token == null) continue; |                 //         .type_expr => |type_node| if (type_node.cast(ast.Node.Identifier)) |ident| | ||||||
| 
 |                 //             std.mem.eql(u8, analysis_ctx.tree().tokenSlice(ident.token), "type") | ||||||
|                     const type_param = switch (decl_param.param_type) { |                 //         else | ||||||
|                         .type_expr => |type_node| if (type_node.cast(ast.Node.Identifier)) |ident| |                 //             false, | ||||||
|                             std.mem.eql(u8, analysis_ctx.tree().tokenSlice(ident.token), "type") |                 //         else => false, | ||||||
|                         else |                 //     }; | ||||||
|                             false, |                 //     if (!type_param) continue; | ||||||
|                         else => false, |                 //     const call_param_type = (try resolveTypeOfNode(store, arena, .{ .node = call.paramsConst()[param_idx], .handle = handle })) orelse continue; | ||||||
|                     }; |                 // } | ||||||
|                     if (!type_param) continue; |                 return try resolveReturnType(store, arena, fn_decl, decl.handle); | ||||||
| 
 |  | ||||||
|                     // TODO Handle errors better |  | ||||||
|                     // TODO This may invalidate the analysis context so we copy it. |  | ||||||
|                     //      However, if the argument hits an import we just ignore it for now. |  | ||||||
|                     //      Once we return our own types instead of directly using nodes we can fix this. |  | ||||||
|                     const call_param_type = resolveTypeOfNode(&analysis_ctx_clone, call.paramsConst()[param_idx]) orelse continue; |  | ||||||
|                     if (analysis_ctx_clone.handle != analysis_ctx.handle) { |  | ||||||
|                         analysis_ctx_clone = analysis_ctx.clone() catch return null; |  | ||||||
|                         continue; |  | ||||||
|                     } |  | ||||||
| 
 |  | ||||||
|                     scope_nodes.append(makeVarDeclNode( |  | ||||||
|                         &analysis_ctx.arena.allocator, |  | ||||||
|                         decl_param.doc_comments, |  | ||||||
|                         decl_param.comptime_token, |  | ||||||
|                         decl_param.name_token.?, |  | ||||||
|                         null, |  | ||||||
|                         call_param_type, |  | ||||||
|                     ) catch return null) catch return null; |  | ||||||
|                     analysis_ctx.scope_nodes = scope_nodes.items; |  | ||||||
|                 } |  | ||||||
| 
 |  | ||||||
|                 return resolveReturnType(analysis_ctx, fn_decl); |  | ||||||
|             } |             } | ||||||
|             return decl; |             return decl; | ||||||
|         }, |         }, | ||||||
|         .StructInitializer => { |         .StructInitializer => { | ||||||
|             const struct_init = node.cast(ast.Node.StructInitializer).?; |             const struct_init = node.cast(ast.Node.StructInitializer).?; | ||||||
|             return resolveTypeOfNode(analysis_ctx, struct_init.lhs); |             return try resolveTypeOfNode(store, arena, .{ .node = struct_init.lhs, .handle = handle }); | ||||||
|         }, |         }, | ||||||
|         .ErrorSetDecl => { |         .ErrorSetDecl => { | ||||||
|             const set = node.cast(ast.Node.ErrorSetDecl).?; |             const set = node.cast(ast.Node.ErrorSetDecl).?; | ||||||
|             var i: usize = 0; |             var i: usize = 0; | ||||||
|             while (set.iterate(i)) |decl| : (i += 1) { |             while (set.iterate(i)) |decl| : (i += 1) { | ||||||
|                 // TODO handle errors better? |                 try store.error_completions.add(handle.tree, decl); | ||||||
|                 analysis_ctx.error_completions.add(analysis_ctx.tree(), decl) catch {}; |  | ||||||
|             } |             } | ||||||
|             return node; |             return node_handle; | ||||||
|         }, |         }, | ||||||
|         .SuffixOp => { |         .SuffixOp => { | ||||||
|             const suffix_op = node.cast(ast.Node.SuffixOp).?; |             const suffix_op = node.cast(ast.Node.SuffixOp).?; | ||||||
|             switch (suffix_op.op) { |             const left_type = (try resolveTypeOfNode(store, arena, .{ .node = suffix_op.lhs, .handle = handle })) orelse return null; | ||||||
|                 .UnwrapOptional => { |             return switch (suffix_op.op) { | ||||||
|                     const left_type = resolveTypeOfNode(analysis_ctx, suffix_op.lhs) orelse return null; |                 .UnwrapOptional => try resolveUnwrapOptionalType(store, arena, left_type), | ||||||
|                     return resolveUnwrapOptionalType(analysis_ctx, left_type); |                 .Deref => try resolveDerefType(store, arena, left_type), | ||||||
|                 }, |                 .ArrayAccess => try resolveBracketAccessType(store, arena, left_type, .Single), | ||||||
|                 .Deref => { |                 .Slice => try resolveBracketAccessType(store, arena, left_type, .Range), | ||||||
|                     const left_type = resolveTypeOfNode(analysis_ctx, suffix_op.lhs) orelse return null; |                 else => null, | ||||||
|                     return resolveDerefType(analysis_ctx, left_type); |             }; | ||||||
|                 }, |  | ||||||
|                 .ArrayAccess => { |  | ||||||
|                     const left_type = resolveTypeOfNode(analysis_ctx, suffix_op.lhs) orelse return null; |  | ||||||
|                     return resolveBracketAccessType(analysis_ctx, left_type, .Single); |  | ||||||
|                 }, |  | ||||||
|                 .Slice => { |  | ||||||
|                     const left_type = resolveTypeOfNode(analysis_ctx, suffix_op.lhs) orelse return null; |  | ||||||
|                     return resolveBracketAccessType(analysis_ctx, left_type, .Range); |  | ||||||
|                 }, |  | ||||||
|                 else => {}, |  | ||||||
|             } |  | ||||||
|         }, |         }, | ||||||
|         .InfixOp => { |         .InfixOp => { | ||||||
|             const infix_op = node.cast(ast.Node.InfixOp).?; |             const infix_op = node.cast(ast.Node.InfixOp).?; | ||||||
|             switch (infix_op.op) { |             switch (infix_op.op) { | ||||||
|                 .Period => { |                 .Period => { | ||||||
|                     // Save the child string from this tree since the tree may switch when processing |                     const rhs_str = nodeToString(handle.tree, infix_op.rhs) orelse return null; | ||||||
|                     // an import lhs. |  | ||||||
|                     var rhs_str = nodeToString(analysis_ctx.tree(), infix_op.rhs) orelse return null; |  | ||||||
|                     // Use the analysis context temporary arena to store the rhs string. |  | ||||||
|                     rhs_str = std.mem.dupe(&analysis_ctx.arena.allocator, u8, rhs_str) catch return null; |  | ||||||
| 
 |  | ||||||
|                     // If we are accessing a pointer type, remove one pointerness level :) |                     // If we are accessing a pointer type, remove one pointerness level :) | ||||||
|                     const left_type = resolveFieldAccessLhsType( |                     const left_type = try resolveFieldAccessLhsType( | ||||||
|                         analysis_ctx, |                         store, | ||||||
|                         resolveTypeOfNode(analysis_ctx, infix_op.lhs) orelse return null, |                         arena, | ||||||
|  |                         (try resolveTypeOfNode(store, arena, .{ | ||||||
|  |                             .node = infix_op.lhs, | ||||||
|  |                             .handle = handle, | ||||||
|  |                         })) orelse return null, | ||||||
|                     ); |                     ); | ||||||
| 
 | 
 | ||||||
|                     const child = getChild(analysis_ctx.tree(), left_type, rhs_str) orelse return null; |                     // @TODO Error sets | ||||||
|                     return resolveTypeOfNode(analysis_ctx, child); |                     if (left_type.node.id != .ContainerDecl and left_type.node.id != .Root) return null; | ||||||
|  | 
 | ||||||
|  |                     if (try lookupSymbolContainer(store, left_type, rhs_str, true)) |child| { | ||||||
|  |                         return try child.resolveType(store, arena); | ||||||
|  |                     } else return null; | ||||||
|                 }, |                 }, | ||||||
|                 .UnwrapOptional => { |                 .UnwrapOptional => { | ||||||
|                     const left_type = resolveTypeOfNode(analysis_ctx, infix_op.lhs) orelse return null; |                     const left_type = (try resolveTypeOfNode(store, arena, .{ | ||||||
|                     return resolveUnwrapOptionalType(analysis_ctx, left_type); |                         .node = infix_op.lhs, | ||||||
|  |                         .handle = handle, | ||||||
|  |                     })) orelse return null; | ||||||
|  |                     return try resolveUnwrapOptionalType(store, arena, left_type); | ||||||
|                 }, |                 }, | ||||||
|                 else => {}, |                 else => return null, | ||||||
|             } |             } | ||||||
|         }, |         }, | ||||||
|         .PrefixOp => { |         .PrefixOp => { | ||||||
| @ -489,13 +460,16 @@ pub fn resolveTypeOfNode(store: *DocumentStore, arena: *std.heap.ArenaAllocator, | |||||||
|                 .ArrayType, |                 .ArrayType, | ||||||
|                 .OptionalType, |                 .OptionalType, | ||||||
|                 .PtrType, |                 .PtrType, | ||||||
|                 => return node, |                 => return node_handle, | ||||||
|                 .Try => { |                 .Try => { | ||||||
|                     const rhs_type = resolveTypeOfNode(analysis_ctx, prefix_op.rhs) orelse return null; |                     const rhs_type = (try resolveTypeOfNode(store, arena, .{ .node = prefix_op.rhs, .handle = handle })) orelse return null; | ||||||
|                     switch (rhs_type.id) { |                     switch (rhs_type.node.id) { | ||||||
|                         .InfixOp => { |                         .InfixOp => { | ||||||
|                             const infix_op = rhs_type.cast(ast.Node.InfixOp).?; |                             const infix_op = rhs_type.node.cast(ast.Node.InfixOp).?; | ||||||
|                             if (infix_op.op == .ErrorUnion) return infix_op.rhs; |                             if (infix_op.op == .ErrorUnion) return NodeWithHandle{ | ||||||
|  |                                 .node = infix_op.rhs, | ||||||
|  |                                 .handle = rhs_type.handle, | ||||||
|  |                             }; | ||||||
|                         }, |                         }, | ||||||
|                         else => {}, |                         else => {}, | ||||||
|                     } |                     } | ||||||
| @ -506,10 +480,10 @@ pub fn resolveTypeOfNode(store: *DocumentStore, arena: *std.heap.ArenaAllocator, | |||||||
|         }, |         }, | ||||||
|         .BuiltinCall => { |         .BuiltinCall => { | ||||||
|             const builtin_call = node.cast(ast.Node.BuiltinCall).?; |             const builtin_call = node.cast(ast.Node.BuiltinCall).?; | ||||||
|             const call_name = analysis_ctx.tree().tokenSlice(builtin_call.builtin_token); |             const call_name = handle.tree.tokenSlice(builtin_call.builtin_token); | ||||||
|             if (std.mem.eql(u8, call_name, "@This")) { |             if (std.mem.eql(u8, call_name, "@This")) { | ||||||
|                 if (builtin_call.params_len != 0) return null; |                 if (builtin_call.params_len != 0) return null; | ||||||
|                 return analysis_ctx.in_container; |                 return innermostContainer(handle, handle.tree.token_locs[builtin_call.firstToken()].start); | ||||||
|             } |             } | ||||||
| 
 | 
 | ||||||
|             // TODO: https://github.com/ziglang/zig/issues/4335 |             // TODO: https://github.com/ziglang/zig/issues/4335 | ||||||
| @ -528,7 +502,7 @@ pub fn resolveTypeOfNode(store: *DocumentStore, arena: *std.heap.ArenaAllocator, | |||||||
|             }); |             }); | ||||||
|             if (cast_map.has(call_name)) { |             if (cast_map.has(call_name)) { | ||||||
|                 if (builtin_call.params_len < 1) return null; |                 if (builtin_call.params_len < 1) return null; | ||||||
|                 return resolveTypeOfNode(analysis_ctx, builtin_call.paramsConst()[0]); |                 return try resolveTypeOfNode(store, arena, .{ .node = builtin_call.paramsConst()[0], .handle = handle }); | ||||||
|             } |             } | ||||||
| 
 | 
 | ||||||
|             if (!std.mem.eql(u8, call_name, "@import")) return null; |             if (!std.mem.eql(u8, call_name, "@import")) return null; | ||||||
| @ -537,31 +511,30 @@ pub fn resolveTypeOfNode(store: *DocumentStore, arena: *std.heap.ArenaAllocator, | |||||||
|             const import_param = builtin_call.paramsConst()[0]; |             const import_param = builtin_call.paramsConst()[0]; | ||||||
|             if (import_param.id != .StringLiteral) return null; |             if (import_param.id != .StringLiteral) return null; | ||||||
| 
 | 
 | ||||||
|             const import_str = analysis_ctx.tree().tokenSlice(import_param.cast(ast.Node.StringLiteral).?.token); |             const import_str = handle.tree.tokenSlice(import_param.cast(ast.Node.StringLiteral).?.token); | ||||||
|             return analysis_ctx.onImport(import_str[1 .. import_str.len - 1]) catch |err| block: { |             const new_handle = (store.resolveImport(handle, import_str[1 .. import_str.len - 1]) catch |err| block: { | ||||||
|                 std.debug.warn("Error {} while processing import {}\n", .{ err, import_str }); |                 std.debug.warn("Error {} while processing import {}\n", .{ err, import_str }); | ||||||
|                 break :block null; |                 return null; | ||||||
|             }; |             }) orelse return null; | ||||||
|  | 
 | ||||||
|  |             return NodeWithHandle{ .node = &new_handle.tree.root_node.base, .handle = new_handle }; | ||||||
|         }, |         }, | ||||||
|         .ContainerDecl => { |         .ContainerDecl => { | ||||||
|             analysis_ctx.onContainer(node) catch return null; |  | ||||||
| 
 |  | ||||||
|             const container = node.cast(ast.Node.ContainerDecl).?; |             const container = node.cast(ast.Node.ContainerDecl).?; | ||||||
|             const kind = analysis_ctx.tree().token_ids[container.kind_token]; |             const kind = handle.tree.token_ids[container.kind_token]; | ||||||
| 
 | 
 | ||||||
|             if (kind == .Keyword_struct or (kind == .Keyword_union and container.init_arg_expr == .None)) { |             if (kind == .Keyword_struct or (kind == .Keyword_union and container.init_arg_expr == .None)) { | ||||||
|                 return node; |                 return node_handle; | ||||||
|             } |             } | ||||||
| 
 | 
 | ||||||
|             var i: usize = 0; |             var i: usize = 0; | ||||||
|             while (container.iterate(i)) |decl| : (i += 1) { |             while (container.iterate(i)) |decl| : (i += 1) { | ||||||
|                 if (decl.id != .ContainerField) continue; |                 if (decl.id != .ContainerField) continue; | ||||||
|                 // TODO handle errors better? |                 try store.enum_completions.add(handle.tree, decl); | ||||||
|                 analysis_ctx.enum_completions.add(analysis_ctx.tree(), decl) catch {}; |  | ||||||
|             } |             } | ||||||
|             return node; |             return node_handle; | ||||||
|         }, |         }, | ||||||
|         .MultilineStringLiteral, .StringLiteral, .FnProto => return node, |         .MultilineStringLiteral, .StringLiteral, .FnProto => return node_handle, | ||||||
|         else => std.debug.warn("Type resolution case not implemented; {}\n", .{node.id}), |         else => std.debug.warn("Type resolution case not implemented; {}\n", .{node.id}), | ||||||
|     } |     } | ||||||
|     return null; |     return null; | ||||||
| @ -640,6 +613,7 @@ pub fn getFieldAccessTypeNode( | |||||||
|                         if (after_period.loc.end == tokenizer.buffer.len) return try resolveFieldAccessLhsType(store, arena, current_node); |                         if (after_period.loc.end == tokenizer.buffer.len) return try resolveFieldAccessLhsType(store, arena, current_node); | ||||||
| 
 | 
 | ||||||
|                         current_node = try resolveFieldAccessLhsType(store, arena, current_node); |                         current_node = try resolveFieldAccessLhsType(store, arena, current_node); | ||||||
|  |                         // @TODO Error sets | ||||||
|                         if (current_node.node.id != .ContainerDecl and current_node.node.id != .Root) { |                         if (current_node.node.id != .ContainerDecl and current_node.node.id != .Root) { | ||||||
|                             // @TODO Is this ok? |                             // @TODO Is this ok? | ||||||
|                             return null; |                             return null; | ||||||
| @ -1141,6 +1115,22 @@ pub fn iterateSymbolsGlobal( | |||||||
|     } |     } | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | pub fn innermostContainer(handle: *DocumentStore.Handle, source_index: usize) NodeWithHandle { | ||||||
|  |     var current = handle.document_scope.scopes[0].data.container; | ||||||
|  |     if (handle.document_scope.scopes.len == 1) return .{ .node = current, .handle = handle }; | ||||||
|  | 
 | ||||||
|  |     for (handle.document_scope.scopes[1..]) |scope| { | ||||||
|  |         if (source_index >= scope.range.start and source_index < scope.range.end) { | ||||||
|  |             switch (scope.data) { | ||||||
|  |                 .container => |node| current = node, | ||||||
|  |                 else => {}, | ||||||
|  |             } | ||||||
|  |         } | ||||||
|  |         if (scope.range.start > source_index) break; | ||||||
|  |     } | ||||||
|  |     return .{ .node = current, .handle = handle }; | ||||||
|  | } | ||||||
|  | 
 | ||||||
| pub fn lookupSymbolGlobal(store: *DocumentStore, handle: *DocumentStore.Handle, symbol: []const u8, source_index: usize) !?DeclWithHandle { | pub fn lookupSymbolGlobal(store: *DocumentStore, handle: *DocumentStore.Handle, symbol: []const u8, source_index: usize) !?DeclWithHandle { | ||||||
|     for (handle.document_scope.scopes) |scope| { |     for (handle.document_scope.scopes) |scope| { | ||||||
|         if (source_index >= scope.range.start and source_index < scope.range.end) { |         if (source_index >= scope.range.start and source_index < scope.range.end) { | ||||||
| @ -1162,7 +1152,7 @@ pub fn lookupSymbolGlobal(store: *DocumentStore, handle: *DocumentStore.Handle, | |||||||
|             } |             } | ||||||
|         } |         } | ||||||
| 
 | 
 | ||||||
|         if (scope.range.start >= source_index) return null; |         if (scope.range.start > source_index) return null; | ||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|     return null; |     return null; | ||||||
|  | |||||||
							
								
								
									
										59
									
								
								src/main.zig
									
									
									
									
									
								
							
							
						
						
									
										59
									
								
								src/main.zig
									
									
									
									
									
								
							| @ -197,6 +197,7 @@ fn publishDiagnostics(handle: DocumentStore.Handle, config: Config) !void { | |||||||
| } | } | ||||||
| 
 | 
 | ||||||
| fn containerToCompletion( | fn containerToCompletion( | ||||||
|  |     arena: *std.heap.ArenaAllocator, | ||||||
|     list: *std.ArrayList(types.CompletionItem), |     list: *std.ArrayList(types.CompletionItem), | ||||||
|     container_handle: analysis.NodeWithHandle, |     container_handle: analysis.NodeWithHandle, | ||||||
|     orig_handle: *DocumentStore.Handle, |     orig_handle: *DocumentStore.Handle, | ||||||
| @ -211,7 +212,7 @@ fn containerToCompletion( | |||||||
|     while (container.iterate(child_idx)) |child_node| : (child_idx += 1) { |     while (container.iterate(child_idx)) |child_node| : (child_idx += 1) { | ||||||
|         // Declarations in the same file do not need to be public. |         // Declarations in the same file do not need to be public. | ||||||
|         if (orig_handle == handle or analysis.isNodePublic(handle.tree, child_node)) { |         if (orig_handle == handle or analysis.isNodePublic(handle.tree, child_node)) { | ||||||
|             try nodeToCompletion(list, .{ .node = child_node, .handle = handle }, orig_handle, config); |             try nodeToCompletion(arena, list, .{ .node = child_node, .handle = handle }, orig_handle, config); | ||||||
|         } |         } | ||||||
|     } |     } | ||||||
| } | } | ||||||
| @ -244,6 +245,7 @@ fn resolveVarDeclFnAlias(arena: *std.heap.ArenaAllocator, decl_handle: analysis. | |||||||
| } | } | ||||||
| 
 | 
 | ||||||
| fn nodeToCompletion( | fn nodeToCompletion( | ||||||
|  |     arena: *std.heap.ArenaAllocator, | ||||||
|     list: *std.ArrayList(types.CompletionItem), |     list: *std.ArrayList(types.CompletionItem), | ||||||
|     node_handle: analysis.NodeWithHandle, |     node_handle: analysis.NodeWithHandle, | ||||||
|     orig_handle: *DocumentStore.Handle, |     orig_handle: *DocumentStore.Handle, | ||||||
| @ -262,7 +264,7 @@ fn nodeToCompletion( | |||||||
| 
 | 
 | ||||||
|     switch (node.id) { |     switch (node.id) { | ||||||
|         .ErrorSetDecl, .Root, .ContainerDecl => { |         .ErrorSetDecl, .Root, .ContainerDecl => { | ||||||
|             try containerToCompletion(list, node_handle, orig_handle, config); |             try containerToCompletion(arena, list, node_handle, orig_handle, config); | ||||||
|         }, |         }, | ||||||
|         .FnProto => { |         .FnProto => { | ||||||
|             const func = node.cast(std.zig.ast.Node.FnProto).?; |             const func = node.cast(std.zig.ast.Node.FnProto).?; | ||||||
| @ -270,31 +272,32 @@ fn nodeToCompletion( | |||||||
|                 const use_snippets = config.enable_snippets and client_capabilities.supports_snippets; |                 const use_snippets = config.enable_snippets and client_capabilities.supports_snippets; | ||||||
| 
 | 
 | ||||||
|                 const insert_text = if (use_snippets) blk: { |                 const insert_text = if (use_snippets) blk: { | ||||||
|                     const skip_self_param = if (func.params_len > 0) param_check: { |                     // @TODO Rebuild this. | ||||||
|                         var child_analysis_ctx = try analysis_ctx.clone(); |                     const skip_self_param = false; | ||||||
|                         break :param_check switch (func.paramsConst()[0].param_type) { |                     // const skip_self_param = if (func.params_len > 0) param_check: { | ||||||
|                             .type_expr => |type_node| if (analysis_ctx.in_container == analysis.resolveTypeOfNode(&child_analysis_ctx, type_node)) |                     //     break :param_check switch (func.paramsConst()[0].param_type) { | ||||||
|                                 true |                     //         .type_expr => |type_node| if (analysis_ctx.in_container == analysis.resolveTypeOfNode(&child_analysis_ctx, type_node)) | ||||||
|                             else if (type_node.cast(std.zig.ast.Node.PrefixOp)) |prefix_op| |                     //             true | ||||||
|                                 prefix_op.op == .PtrType and analysis_ctx.in_container == analysis.resolveTypeOfNode(&child_analysis_ctx, prefix_op.rhs) |                     //         else if (type_node.cast(std.zig.ast.Node.PrefixOp)) |prefix_op| | ||||||
|                             else |                     //             prefix_op.op == .PtrType and analysis_ctx.in_container == analysis.resolveTypeOfNode(&child_analysis_ctx, prefix_op.rhs) | ||||||
|                                 false, |                     //         else | ||||||
|                             else => false, |                     //             false, | ||||||
|                         }; |                     //         else => false, | ||||||
|                     } else |                     //     }; | ||||||
|                         false; |                     // } else | ||||||
|  |                     //     false; | ||||||
| 
 | 
 | ||||||
|                     break :blk try analysis.getFunctionSnippet(list.allocator, analysis_ctx.tree(), func, skip_self_param); |                     break :blk try analysis.getFunctionSnippet(&arena.allocator, handle.tree, func, skip_self_param); | ||||||
|                 } else |                 } else | ||||||
|                     null; |                     null; | ||||||
| 
 | 
 | ||||||
|                 const is_type_function = analysis.isTypeFunction(analysis_ctx.tree(), func); |                 const is_type_function = analysis.isTypeFunction(handle.tree, func); | ||||||
| 
 | 
 | ||||||
|                 try list.append(.{ |                 try list.append(.{ | ||||||
|                     .label = analysis_ctx.tree().tokenSlice(name_token), |                     .label = handle.tree.tokenSlice(name_token), | ||||||
|                     .kind = if (is_type_function) .Struct else .Function, |                     .kind = if (is_type_function) .Struct else .Function, | ||||||
|                     .documentation = doc, |                     .documentation = doc, | ||||||
|                     .detail = analysis.getFunctionSignature(analysis_ctx.tree(), func), |                     .detail = analysis.getFunctionSignature(handle.tree, func), | ||||||
|                     .insertText = insert_text, |                     .insertText = insert_text, | ||||||
|                     .insertTextFormat = if (use_snippets) .Snippet else .PlainText, |                     .insertTextFormat = if (use_snippets) .Snippet else .PlainText, | ||||||
|                 }); |                 }); | ||||||
| @ -302,18 +305,18 @@ fn nodeToCompletion( | |||||||
|         }, |         }, | ||||||
|         .VarDecl => { |         .VarDecl => { | ||||||
|             const var_decl = node.cast(std.zig.ast.Node.VarDecl).?; |             const var_decl = node.cast(std.zig.ast.Node.VarDecl).?; | ||||||
|             const is_const = analysis_ctx.tree().token_ids[var_decl.mut_token] == .Keyword_const; |             const is_const = handle.tree.token_ids[var_decl.mut_token] == .Keyword_const; | ||||||
| 
 | 
 | ||||||
|             var result = try resolveVarDeclFnAlias(analysis_ctx, node); |             const result = try resolveVarDeclFnAlias(arena, node_handle); | ||||||
|             if (result.decl != node) { |             if (result.node != node) { | ||||||
|                 return try nodeToCompletion(list, &result.analysis_ctx, orig_handle, result.decl, config); |                 return try nodeToCompletion(arena, list, result, orig_handle, config); | ||||||
|             } |             } | ||||||
| 
 | 
 | ||||||
|             try list.append(.{ |             try list.append(.{ | ||||||
|                 .label = analysis_ctx.tree().tokenSlice(var_decl.name_token), |                 .label = handle.tree.tokenSlice(var_decl.name_token), | ||||||
|                 .kind = if (is_const) .Constant else .Variable, |                 .kind = if (is_const) .Constant else .Variable, | ||||||
|                 .documentation = doc, |                 .documentation = doc, | ||||||
|                 .detail = analysis.getVariableSignature(analysis_ctx.tree(), var_decl), |                 .detail = analysis.getVariableSignature(handle.tree, var_decl), | ||||||
|             }); |             }); | ||||||
|         }, |         }, | ||||||
|         .PrefixOp => { |         .PrefixOp => { | ||||||
| @ -547,7 +550,7 @@ const DeclToCompletionContext = struct { | |||||||
| fn decltoCompletion(context: DeclToCompletionContext, decl_handle: analysis.DeclWithHandle) !void { | fn decltoCompletion(context: DeclToCompletionContext, decl_handle: analysis.DeclWithHandle) !void { | ||||||
|     switch (decl_handle.decl.*) { |     switch (decl_handle.decl.*) { | ||||||
|         .ast_node => |node| { |         .ast_node => |node| { | ||||||
|             try nodeToCompletion(context.completions, .{ .node = node, .handle = decl_handle.handle }, context.orig_handle, context.config.*); |             try nodeToCompletion(context.arena, context.completions, .{ .node = node, .handle = decl_handle.handle }, context.orig_handle, context.config.*); | ||||||
|         }, |         }, | ||||||
|         else => {}, |         else => {}, | ||||||
|         // @TODO The rest |         // @TODO The rest | ||||||
| @ -590,7 +593,7 @@ fn completeFieldAccess(id: types.RequestId, handle: *DocumentStore.Handle, posit | |||||||
|     var tokenizer = std.zig.Tokenizer.init(line[range.start..range.end]); |     var tokenizer = std.zig.Tokenizer.init(line[range.start..range.end]); | ||||||
| 
 | 
 | ||||||
|     if (try analysis.getFieldAccessTypeNode(&document_store, &arena, handle, &tokenizer)) |node| { |     if (try analysis.getFieldAccessTypeNode(&document_store, &arena, handle, &tokenizer)) |node| { | ||||||
|         try nodeToCompletion(&completions, node, handle, config); |         try nodeToCompletion(&arena, &completions, node, handle, config); | ||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|     try send(types.Response{ |     try send(types.Response{ | ||||||
| @ -829,7 +832,7 @@ fn processJsonRpc(parser: *std.json.Parser, json: []const u8, config: Config) !v | |||||||
|     } |     } | ||||||
|     // Semantic highlighting |     // Semantic highlighting | ||||||
|     else if (std.mem.eql(u8, method, "textDocument/semanticTokens")) { |     else if (std.mem.eql(u8, method, "textDocument/semanticTokens")) { | ||||||
|         // @TODO Implement this (we dont get here from vscode atm even when we get the client capab.) |         // TODO Implement this (we dont get here from vscode atm even when we get the client capab.) | ||||||
|         return try respondGeneric(id, empty_array_response); |         return try respondGeneric(id, empty_array_response); | ||||||
|     } |     } | ||||||
|     // Autocomplete / Signatures |     // Autocomplete / Signatures | ||||||
|  | |||||||
		Loading…
	
		Reference in New Issue
	
	Block a user