diff options
author | Li Jin <dragon-fly@qq.com> | 2023-07-24 17:55:21 +0800 |
---|---|---|
committer | Li Jin <dragon-fly@qq.com> | 2023-07-24 17:55:21 +0800 |
commit | c03b88e6210818e604d7c755fe8f54fe53696ee1 (patch) | |
tree | 3d297ce64171481caeb0e86f42a206e8322abeca /src/3rdParty/LuaMinify.h | |
parent | 00c4bee811b3c92d9885959db30790b01f8cb3e2 (diff) | |
download | yuescript-c03b88e6210818e604d7c755fe8f54fe53696ee1.tar.gz yuescript-c03b88e6210818e604d7c755fe8f54fe53696ee1.tar.bz2 yuescript-c03b88e6210818e604d7c755fe8f54fe53696ee1.zip |
try fixing issue #141. fix an AST object life expired before accessing issue.
Diffstat (limited to 'src/3rdParty/LuaMinify.h')
-rw-r--r-- | src/3rdParty/LuaMinify.h | 428 |
1 files changed, 408 insertions, 20 deletions
diff --git a/src/3rdParty/LuaMinify.h b/src/3rdParty/LuaMinify.h index d01a8fe..5512f5b 100644 --- a/src/3rdParty/LuaMinify.h +++ b/src/3rdParty/LuaMinify.h | |||
@@ -319,8 +319,6 @@ R"lua_codes( | |||
319 | -- ParseLua returns an AST, internally relying on LexLua. | 319 | -- ParseLua returns an AST, internally relying on LexLua. |
320 | -- | 320 | -- |
321 | 321 | ||
322 | local WhiteChars = lookupify{' ', '\n', '\t', '\r'} | ||
323 | local EscapeLookup = {['\r'] = '\\r', ['\n'] = '\\n', ['\t'] = '\\t', ['"'] = '\\"', ["'"] = "\\'"} | ||
324 | local LowerChars = lookupify{'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', | 322 | local LowerChars = lookupify{'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', |
325 | 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', | 323 | 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', |
326 | 's', 't', 'u', 'v', 'w', 'x', 'y', 'z'} | 324 | 's', 't', 'u', 'v', 'w', 'x', 'y', 'z'} |
@@ -549,7 +547,7 @@ local function LexLua(src) | |||
549 | --get the initial char | 547 | --get the initial char |
550 | local thisLine = line | 548 | local thisLine = line |
551 | local thisChar = char | 549 | local thisChar = char |
552 | local errorAt = ":"..line..":"..char..":> " | 550 | --local errorAt = ":"..line..":"..char..":> " |
553 | local c = peek() | 551 | local c = peek() |
554 | 552 | ||
555 | --symbol to emit | 553 | --symbol to emit |
@@ -822,9 +820,9 @@ local function ParseLua(src) | |||
822 | return err | 820 | return err |
823 | end | 821 | end |
824 | -- | 822 | -- |
825 | local VarUid = 0 | 823 | -- local VarUid = 0 |
826 | -- No longer needed: handled in Scopes now local GlobalVarGetMap = {} | 824 | -- No longer needed: handled in Scopes now local GlobalVarGetMap = {} |
827 | local VarDigits = {'_', 'a', 'b', 'c', 'd'} | 825 | -- local VarDigits = {'_', 'a', 'b', 'c', 'd'} |
828 | local function CreateScope(parent) | 826 | local function CreateScope(parent) |
829 | --[[ | 827 | --[[ |
830 | local scope = {} | 828 | local scope = {} |
@@ -1736,15 +1734,6 @@ R"lua_codes( | |||
1736 | -- - All local variables are renamed | 1734 | -- - All local variables are renamed |
1737 | -- | 1735 | -- |
1738 | 1736 | ||
1739 | local LowerChars = lookupify{'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', | ||
1740 | 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', | ||
1741 | 's', 't', 'u', 'v', 'w', 'x', 'y', 'z'} | ||
1742 | local UpperChars = lookupify{'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', | ||
1743 | 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', | ||
1744 | 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z'} | ||
1745 | local Digits = lookupify{'0', '1', '2', '3', '4', '5', '6', '7', '8', '9'} | ||
1746 | local Symbols = lookupify{'+', '-', '*', '/', '^', '%', ',', '{', '}', '[', ']', '(', ')', ';', '#'} | ||
1747 | |||
1748 | local function Format_Mini(ast) | 1737 | local function Format_Mini(ast) |
1749 | local formatStatlist, formatExpr; | 1738 | local formatStatlist, formatExpr; |
1750 | --local count = 0 | 1739 | --local count = 0 |
@@ -2092,14 +2081,413 @@ local function Format_Mini(ast) | |||
2092 | ast.Scope:ObfuscateVariables() | 2081 | ast.Scope:ObfuscateVariables() |
2093 | return formatStatlist(ast) | 2082 | return formatStatlist(ast) |
2094 | end | 2083 | end |
2084 | )lua_codes" | ||
2095 | 2085 | ||
2096 | return function(src) | 2086 | R"lua_codes( |
2097 | local st, ast = ParseLua(src) | 2087 | local function FormatYue(ast, lineMap) |
2098 | if st then | 2088 | local currentLine = 1 |
2099 | return Format_Mini(ast) | 2089 | local formatStatlist, formatExpr |
2100 | else | 2090 | |
2101 | return nil, ast | 2091 | local function joinStatementsSafe(out, b, sep) |
2092 | local aa = '' | ||
2093 | for i = #out, 1, -1 do | ||
2094 | local a = out[i] | ||
2095 | aa = a:match("([^%s])%s*$") | ||
2096 | if aa then | ||
2097 | break | ||
2098 | end | ||
2099 | end | ||
2100 | sep = sep or ' ' | ||
2101 | if (out[#out] or ''):sub(-1,-1) == ' ' then | ||
2102 | sep = '' | ||
2103 | end | ||
2104 | local bb = b:match("^%s*([^%s])") | ||
2105 | if UpperChars[aa] or LowerChars[aa] or aa == '_' then | ||
2106 | if not (UpperChars[bb] or LowerChars[bb] or bb == '_' or Digits[bb]) then | ||
2107 | --bb is a symbol, can join without sep | ||
2108 | out[#out + 1] = b | ||
2109 | elseif bb == '(' then | ||
2110 | --prevent ambiguous syntax | ||
2111 | out[#out + 1] = sep | ||
2112 | out[#out + 1] = b | ||
2113 | else | ||
2114 | out[#out + 1] = sep | ||
2115 | out[#out + 1] = b | ||
2116 | end | ||
2117 | elseif Digits[aa] then | ||
2118 | if bb == '(' then | ||
2119 | --can join statements directly | ||
2120 | out[#out + 1] = b | ||
2121 | elseif Symbols[bb] then | ||
2122 | out[#out + 1] = b | ||
2123 | else | ||
2124 | out[#out + 1] = sep | ||
2125 | out[#out + 1] = b | ||
2126 | end | ||
2127 | elseif aa == '' then | ||
2128 | out[#out + 1] = b | ||
2129 | else | ||
2130 | if bb == '(' then | ||
2131 | --don't want to accidentally call last statement, can't join directly | ||
2132 | out[#out + 1] = sep | ||
2133 | out[#out + 1] = b | ||
2134 | else | ||
2135 | out[#out + 1] = b | ||
2136 | end | ||
2137 | end | ||
2102 | end | 2138 | end |
2139 | |||
2140 | formatExpr = function(expr) | ||
2141 | local out = {string.rep('(', expr.ParenCount or 0)} | ||
2142 | if expr.Tokens then | ||
2143 | local line = expr.Tokens[1].Line | ||
2144 | local targetLine = lineMap[line] | ||
2145 | if targetLine and currentLine < targetLine then | ||
2146 | out[#out + 1] = string.rep('\n', targetLine - currentLine) | ||
2147 | currentLine = targetLine | ||
2148 | end | ||
2149 | elseif expr.Value then | ||
2150 | local line = expr.Value.Line | ||
2151 | local targetLine = lineMap[line] | ||
2152 | if targetLine and currentLine < targetLine then | ||
2153 | out[#out + 1] = string.rep('\n', targetLine - currentLine) | ||
2154 | currentLine = targetLine | ||
2155 | end | ||
2156 | end | ||
2157 | if expr.AstType == 'VarExpr' then | ||
2158 | if expr.Variable then | ||
2159 | out[#out + 1] = expr.Variable.Name | ||
2160 | else | ||
2161 | out[#out + 1] = expr.Name | ||
2162 | end | ||
2163 | |||
2164 | elseif expr.AstType == 'NumberExpr' then | ||
2165 | out[#out + 1] = expr.Value.Data | ||
2166 | |||
2167 | elseif expr.AstType == 'StringExpr' then | ||
2168 | out[#out + 1] = expr.Value.Data | ||
2169 | |||
2170 | elseif expr.AstType == 'BooleanExpr' then | ||
2171 | out[#out + 1] = tostring(expr.Value) | ||
2172 | |||
2173 | elseif expr.AstType == 'NilExpr' then | ||
2174 | joinStatementsSafe(out, "nil", nil) | ||
2175 | |||
2176 | elseif expr.AstType == 'BinopExpr' then | ||
2177 | joinStatementsSafe(out, formatExpr(expr.Lhs), nil) | ||
2178 | out[#out + 1] = " " | ||
2179 | joinStatementsSafe(out, expr.Op, nil) | ||
2180 | out[#out + 1] = " " | ||
2181 | joinStatementsSafe(out, formatExpr(expr.Rhs), nil) | ||
2182 | |||
2183 | elseif expr.AstType == 'UnopExpr' then | ||
2184 | joinStatementsSafe(out, expr.Op, nil) | ||
2185 | out[#out + 1] = (#expr.Op ~= 1 and " " or "") | ||
2186 | joinStatementsSafe(out, formatExpr(expr.Rhs), nil) | ||
2187 | |||
2188 | elseif expr.AstType == 'DotsExpr' then | ||
2189 | out[#out + 1] = "..." | ||
2190 | |||
2191 | elseif expr.AstType == 'CallExpr' then | ||
2192 | out[#out + 1] = formatExpr(expr.Base) | ||
2193 | out[#out + 1] = "(" | ||
2194 | for i = 1, #expr.Arguments do | ||
2195 | out[#out + 1] = formatExpr(expr.Arguments[i]) | ||
2196 | if i ~= #expr.Arguments then | ||
2197 | out[#out + 1] = ", " | ||
2198 | end | ||
2199 | end | ||
2200 | out[#out + 1] = ")" | ||
2201 | |||
2202 | elseif expr.AstType == 'TableCallExpr' then | ||
2203 | out[#out + 1] = formatExpr(expr.Base) | ||
2204 | out[#out + 1] = " " | ||
2205 | out[#out + 1] = formatExpr(expr.Arguments[1]) | ||
2206 | |||
2207 | elseif expr.AstType == 'StringCallExpr' then | ||
2208 | out[#out + 1] = formatExpr(expr.Base) | ||
2209 | out[#out + 1] = " " | ||
2210 | out[#out + 1] = expr.Arguments[1].Data | ||
2211 | |||
2212 | elseif expr.AstType == 'IndexExpr' then | ||
2213 | out[#out + 1] = formatExpr(expr.Base) | ||
2214 | out[#out + 1] = "[" | ||
2215 | out[#out + 1] = formatExpr(expr.Index) | ||
2216 | out[#out + 1] = "]" | ||
2217 | |||
2218 | elseif expr.AstType == 'MemberExpr' then | ||
2219 | out[#out + 1] = formatExpr(expr.Base) | ||
2220 | out[#out + 1] = expr.Indexer | ||
2221 | out[#out + 1] = expr.Ident.Data | ||
2222 | |||
2223 | elseif expr.AstType == 'Function' then | ||
2224 | -- anonymous function | ||
2225 | out[#out + 1] = "function(" | ||
2226 | if #expr.Arguments > 0 then | ||
2227 | for i = 1, #expr.Arguments do | ||
2228 | out[#out + 1] = expr.Arguments[i].Name | ||
2229 | if i ~= #expr.Arguments then | ||
2230 | out[#out + 1] = ", " | ||
2231 | elseif expr.VarArg then | ||
2232 | out[#out + 1] = ", ..." | ||
2233 | end | ||
2234 | end | ||
2235 | elseif expr.VarArg then | ||
2236 | out[#out + 1] = "..." | ||
2237 | end | ||
2238 | out[#out + 1] = ")" | ||
2239 | joinStatementsSafe(out, formatStatlist(expr.Body), nil) | ||
2240 | joinStatementsSafe(out, "end", nil) | ||
2241 | elseif expr.AstType == 'ConstructorExpr' then | ||
2242 | out[#out + 1] = "{ " | ||
2243 | for i = 1, #expr.EntryList do | ||
2244 | local entry = expr.EntryList[i] | ||
2245 | if entry.Type == 'Key' then | ||
2246 | out[#out + 1] = "[" | ||
2247 | out[#out + 1] = formatExpr(entry.Key) | ||
2248 | out[#out + 1] = "] = " | ||
2249 | out[#out + 1] = formatExpr(entry.Value) | ||
2250 | elseif entry.Type == 'Value' then | ||
2251 | out[#out + 1] = formatExpr(entry.Value) | ||
2252 | elseif entry.Type == 'KeyString' then | ||
2253 | out[#out + 1] = entry.Key | ||
2254 | out[#out + 1] = " = " | ||
2255 | out[#out + 1] = formatExpr(entry.Value) | ||
2256 | end | ||
2257 | if i ~= #expr.EntryList then | ||
2258 | out[#out + 1] = ", " | ||
2259 | end | ||
2260 | end | ||
2261 | out[#out + 1] = " }" | ||
2262 | |||
2263 | elseif expr.AstType == 'Parentheses' then | ||
2264 | out[#out + 1] = "(" | ||
2265 | out[#out + 1] = formatExpr(expr.Inner) | ||
2266 | out[#out + 1] = ")" | ||
2267 | |||
2268 | end | ||
2269 | out[#out + 1] = string.rep(')', expr.ParenCount or 0) | ||
2270 | return table.concat(out) | ||
2271 | end | ||
2272 | |||
2273 | local formatStatement = function(statement) | ||
2274 | local out = {""} | ||
2275 | if statement.Tokens and statement.Tokens[1] then | ||
2276 | local line = statement.Tokens[1].Line | ||
2277 | local targetLine = lineMap[line] | ||
2278 | if targetLine and currentLine < targetLine then | ||
2279 | out[#out + 1] = string.rep('\n', targetLine - currentLine) | ||
2280 | currentLine = targetLine | ||
2281 | end | ||
2282 | end | ||
2283 | if statement.AstType == 'AssignmentStatement' then | ||
2284 | for i = 1, #statement.Lhs do | ||
2285 | out[#out + 1] = formatExpr(statement.Lhs[i]) | ||
2286 | if i ~= #statement.Lhs then | ||
2287 | out[#out + 1] = ", " | ||
2288 | end | ||
2289 | end | ||
2290 | if #statement.Rhs > 0 then | ||
2291 | out[#out + 1] = " = " | ||
2292 | for i = 1, #statement.Rhs do | ||
2293 | out[#out + 1] = formatExpr(statement.Rhs[i]) | ||
2294 | if i ~= #statement.Rhs then | ||
2295 | out[#out + 1] = ", " | ||
2296 | end | ||
2297 | end | ||
2298 | end | ||
2299 | elseif statement.AstType == 'CallStatement' then | ||
2300 | out[#out + 1] = formatExpr(statement.Expression) | ||
2301 | elseif statement.AstType == 'LocalStatement' then | ||
2302 | out[#out + 1] = "local " | ||
2303 | for i = 1, #statement.LocalList do | ||
2304 | out[#out + 1] = statement.LocalList[i].Name | ||
2305 | if statement.AttrList[i] then | ||
2306 | out[#out + 1] = " <" | ||
2307 | out[#out + 1] = statement.AttrList[i] | ||
2308 | out[#out + 1] = ">" | ||
2309 | end | ||
2310 | if i ~= #statement.LocalList then | ||
2311 | out[#out + 1] = "," | ||
2312 | end | ||
2313 | end | ||
2314 | if #statement.InitList > 0 then | ||
2315 | out[#out + 1] = " = " | ||
2316 | for i = 1, #statement.InitList do | ||
2317 | out[#out + 1] = formatExpr(statement.InitList[i]) | ||
2318 | if i ~= #statement.InitList then | ||
2319 | out[#out + 1] = ", " | ||
2320 | end | ||
2321 | end | ||
2322 | end | ||
2323 | elseif statement.AstType == 'IfStatement' then | ||
2324 | out[#out + 1] = "if " | ||
2325 | joinStatementsSafe(out, formatExpr(statement.Clauses[1].Condition), nil) | ||
2326 | joinStatementsSafe(out, " then", nil) | ||
2327 | joinStatementsSafe(out, formatStatlist(statement.Clauses[1].Body), nil) | ||
2328 | for i = 2, #statement.Clauses do | ||
2329 | local st = statement.Clauses[i] | ||
2330 | if st.Condition then | ||
2331 | joinStatementsSafe(out, "elseif ", nil) | ||
2332 | joinStatementsSafe(out, formatExpr(st.Condition), nil) | ||
2333 | joinStatementsSafe(out, " then", nil) | ||
2334 | else | ||
2335 | joinStatementsSafe(out, "else", nil) | ||
2336 | end | ||
2337 | joinStatementsSafe(out, formatStatlist(st.Body), nil) | ||
2338 | end | ||
2339 | joinStatementsSafe(out, "end", nil) | ||
2340 | elseif statement.AstType == 'WhileStatement' then | ||
2341 | out[#out + 1] = "while " | ||
2342 | joinStatementsSafe(out, formatExpr(statement.Condition), nil) | ||
2343 | joinStatementsSafe(out, " do", nil) | ||
2344 | joinStatementsSafe(out, formatStatlist(statement.Body), nil) | ||
2345 | joinStatementsSafe(out, "end", nil) | ||
2346 | elseif statement.AstType == 'DoStatement' then | ||
2347 | joinStatementsSafe(out, "do", nil) | ||
2348 | joinStatementsSafe(out, formatStatlist(statement.Body), nil) | ||
2349 | joinStatementsSafe(out, "end", nil) | ||
2350 | elseif statement.AstType == 'ReturnStatement' then | ||
2351 | out[#out + 1] = "return " | ||
2352 | for i = 1, #statement.Arguments do | ||
2353 | joinStatementsSafe(out, formatExpr(statement.Arguments[i]), nil) | ||
2354 | if i ~= #statement.Arguments then | ||
2355 | out[#out + 1] = ", " | ||
2356 | end | ||
2357 | end | ||
2358 | elseif statement.AstType == 'BreakStatement' then | ||
2359 | out[#out + 1] = "break" | ||
2360 | elseif statement.AstType == 'RepeatStatement' then | ||
2361 | out[#out + 1] = "repeat" | ||
2362 | joinStatementsSafe(out, formatStatlist(statement.Body), nil) | ||
2363 | joinStatementsSafe(out, "until ", nil) | ||
2364 | joinStatementsSafe(out, formatExpr(statement.Condition), nil) | ||
2365 | elseif statement.AstType == 'Function' then | ||
2366 | if statement.IsLocal then | ||
2367 | out[#out + 1] = "local " | ||
2368 | end | ||
2369 | joinStatementsSafe(out, "function ", nil) | ||
2370 | if statement.IsLocal then | ||
2371 | out[#out + 1] = statement.Name.Name | ||
2372 | else | ||
2373 | out[#out + 1] = formatExpr(statement.Name) | ||
2374 | end | ||
2375 | out[#out + 1] = "(" | ||
2376 | if #statement.Arguments > 0 then | ||
2377 | for i = 1, #statement.Arguments do | ||
2378 | out[#out + 1] = statement.Arguments[i].Name | ||
2379 | if i ~= #statement.Arguments then | ||
2380 | out[#out + 1] = ", " | ||
2381 | elseif statement.VarArg then | ||
2382 | out[#out + 1] = ",..." | ||
2383 | end | ||
2384 | end | ||
2385 | elseif statement.VarArg then | ||
2386 | out[#out + 1] = "..." | ||
2387 | end | ||
2388 | out[#out + 1] = ")" | ||
2389 | joinStatementsSafe(out, formatStatlist(statement.Body), nil) | ||
2390 | joinStatementsSafe(out, "end", nil) | ||
2391 | elseif statement.AstType == 'GenericForStatement' then | ||
2392 | out[#out + 1] = "for " | ||
2393 | for i = 1, #statement.VariableList do | ||
2394 | out[#out + 1] = statement.VariableList[i].Name | ||
2395 | if i ~= #statement.VariableList then | ||
2396 | out[#out + 1] = ", " | ||
2397 | end | ||
2398 | end | ||
2399 | out[#out + 1] = " in " | ||
2400 | for i = 1, #statement.Generators do | ||
2401 | joinStatementsSafe(out, formatExpr(statement.Generators[i]), nil) | ||
2402 | if i ~= #statement.Generators then | ||
2403 | joinStatementsSafe(out, ', ', nil) | ||
2404 | end | ||
2405 | end | ||
2406 | joinStatementsSafe(out, " do", nil) | ||
2407 | joinStatementsSafe(out, formatStatlist(statement.Body), nil) | ||
2408 | joinStatementsSafe(out, "end", nil) | ||
2409 | elseif statement.AstType == 'NumericForStatement' then | ||
2410 | out[#out + 1] = "for " | ||
2411 | out[#out + 1] = statement.Variable.Name | ||
2412 | out[#out + 1] = " = " | ||
2413 | out[#out + 1] = formatExpr(statement.Start) | ||
2414 | out[#out + 1] = ", " | ||
2415 | out[#out + 1] = formatExpr(statement.End) | ||
2416 | if statement.Step then | ||
2417 | out[#out + 1] = ", " | ||
2418 | out[#out + 1] = formatExpr(statement.Step) | ||
2419 | end | ||
2420 | joinStatementsSafe(out, " do", nil) | ||
2421 | joinStatementsSafe(out, formatStatlist(statement.Body), nil) | ||
2422 | joinStatementsSafe(out, "end", nil) | ||
2423 | elseif statement.AstType == 'LabelStatement' then | ||
2424 | out[#out + 1] = "::" | ||
2425 | out[#out + 1] = statement.Label | ||
2426 | out[#out + 1] = "::" | ||
2427 | elseif statement.AstType == 'GotoStatement' then | ||
2428 | out[#out + 1] = "goto " | ||
2429 | out[#out + 1] = statement.Label | ||
2430 | elseif statement.AstType == 'Comment' then | ||
2431 | -- Ignore | ||
2432 | elseif statement.AstType == 'Eof' then | ||
2433 | -- Ignore | ||
2434 | else | ||
2435 | print("Unknown AST Type: ", statement.AstType) | ||
2436 | end | ||
2437 | return table.concat(out) | ||
2438 | end | ||
2439 | |||
2440 | formatStatlist = function(statList) | ||
2441 | local out = {""} | ||
2442 | for _, stat in pairs(statList.Body) do | ||
2443 | joinStatementsSafe(out, formatStatement(stat), ';') | ||
2444 | end | ||
2445 | return table.concat(out) | ||
2446 | end | ||
2447 | |||
2448 | return formatStatlist(ast) | ||
2449 | end | ||
2450 | |||
2451 | local function GetYueLineMap(luaCodes) | ||
2452 | local current = 1 | ||
2453 | local lastLine = 1 | ||
2454 | local lineMap = { } | ||
2455 | for lineCode in luaCodes:gmatch("[^\n\r]*") do | ||
2456 | local num = lineCode:match("--%s*(%d+)%s*$") | ||
2457 | if num then | ||
2458 | local line = tonumber(num) | ||
2459 | if line > lastLine then | ||
2460 | lastLine = line | ||
2461 | end | ||
2462 | end | ||
2463 | lineMap[current] = lastLine | ||
2464 | current = current + 1 | ||
2465 | end | ||
2466 | return lineMap | ||
2103 | end | 2467 | end |
2468 | |||
2469 | return { | ||
2470 | FormatMini = function(src) | ||
2471 | local st, ast = ParseLua(src) | ||
2472 | if st then | ||
2473 | return Format_Mini(ast) | ||
2474 | else | ||
2475 | return nil, ast | ||
2476 | end | ||
2477 | end, | ||
2478 | |||
2479 | FormatYue = function(src) | ||
2480 | local st, ast = ParseLua(src) | ||
2481 | if st then | ||
2482 | local lineMap = GetYueLineMap(src) | ||
2483 | if #lineMap == 0 then | ||
2484 | return src | ||
2485 | end | ||
2486 | return FormatYue(ast, lineMap) | ||
2487 | else | ||
2488 | return nil, ast | ||
2489 | end | ||
2490 | end | ||
2491 | } | ||
2104 | )lua_codes"; | 2492 | )lua_codes"; |
2105 | 2493 | ||