1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
|
local vm = require 'vm.vm'
local files = require 'files'
local ws = require 'workspace'
local guide = require 'parser.guide'
local await = require 'await'
local library = require 'library'
local m = {}
function m.searchFileReturn(results, ast, index)
local returns = ast.returns
if not returns then
return
end
for _, ret in ipairs(returns) do
local exp = ret[index]
if exp then
vm.mergeResults(results, { exp })
end
end
end
function m.require(args, index)
local reqName = args[1] and args[1][1]
if not reqName then
return nil
end
local results = {}
local myUri = guide.getRoot(args[1]).uri
local uris = ws.findUrisByRequirePath(reqName, true)
for _, uri in ipairs(uris) do
if not files.eq(myUri, uri) then
local ast = files.getAst(uri)
if ast then
m.searchFileReturn(results, ast.ast, index)
end
end
end
local lib = library.library[reqName]
results[#results+1] = lib
return results
end
function m.dofile(args, index)
local reqName = args[1] and args[1][1]
if not reqName then
return
end
local results = {}
local myUri = guide.getRoot(args[1]).uri
local uris = ws.findUrisByFilePath(reqName, true)
for _, uri in ipairs(uris) do
if not files.eq(myUri, uri) then
local ast = files.getAst(uri)
if ast then
m.searchFileReturn(results, ast.ast, index)
end
end
end
return results
end
vm.interface = {}
-- 向前寻找引用的层数限制,一般情况下都为0
-- 在自动完成/漂浮提示等情况时设置为5(需要清空缓存)
-- 在查找引用时设置为10(需要清空缓存)
vm.interface.searchLevel = 0
function vm.interface.call(func, args, index)
if func.special == 'require' and index == 1 then
await.delay()
return m.require(args, index)
end
if func.special == 'dofile' then
await.delay()
return m.dofile(args, index)
end
end
function vm.interface.global(name)
await.delay()
return vm.getGlobals(name)
end
function vm.interface.link(uri)
await.delay()
return vm.getLinksTo(uri)
end
function vm.interface.index(obj)
if obj.library then
return obj.fields
end
local tp = obj.type
if tp == 'getglobal' and obj.node.special == '_G' then
obj = library.global[obj[1]]
if not obj then
return nil
end
tp = obj.type
end
local lib = library.object[tp]
if lib then
return lib.fields
end
return nil
end
function vm.interface.cache(source, mode)
await.delay()
local cache = vm.getCache('cache')
if not cache[mode] then
cache[mode] = {}
end
local sourceCache = cache[mode][source]
if sourceCache then
return sourceCache
end
sourceCache = {}
cache[mode][source] = sourceCache
return nil, function (results)
for i = 1, #results do
sourceCache[i] = results[i]
end
end
end
function vm.setSearchLevel(n)
-- 只有在搜索等级由低变高时,才需要清空缓存
if n > vm.interface.searchLevel then
--vm.flushCache()
end
vm.interface.searchLevel = n
end
|