Skip to content

Commit

Permalink
v0.9.1+luau625
Browse files Browse the repository at this point in the history
  • Loading branch information
khvzak committed May 12, 2024
1 parent 6b8c97e commit a5b5504
Show file tree
Hide file tree
Showing 14 changed files with 202 additions and 65 deletions.
2 changes: 1 addition & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
[package]
name = "luau0-src"
version = "0.9.0+luau624"
version = "0.9.1+luau625"
authors = ["Aleksandr Orlenko <[email protected]>"]
edition = "2021"
repository = "https://github.com/khvzak/luau-src-rs"
Expand Down
26 changes: 11 additions & 15 deletions luau/Ast/src/Parser.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,6 @@ LUAU_FASTINTVARIABLE(LuauParseErrorLimit, 100)
// flag so that we don't break production games by reverting syntax changes.
// See docs/SyntaxChanges.md for an explanation.
LUAU_FASTFLAG(LuauCheckedFunctionSyntax)
LUAU_FASTFLAGVARIABLE(LuauReadWritePropertySyntax, false)
LUAU_FASTFLAGVARIABLE(DebugLuauDeferredConstraintResolution, false)

namespace Luau
Expand Down Expand Up @@ -1340,22 +1339,19 @@ AstType* Parser::parseTableType(bool inDeclarationContext)
AstTableAccess access = AstTableAccess::ReadWrite;
std::optional<Location> accessLocation;

if (FFlag::LuauReadWritePropertySyntax || FFlag::DebugLuauDeferredConstraintResolution)
if (lexer.current().type == Lexeme::Name && lexer.lookahead().type != ':')
{
if (lexer.current().type == Lexeme::Name && lexer.lookahead().type != ':')
if (AstName(lexer.current().name) == "read")
{
if (AstName(lexer.current().name) == "read")
{
accessLocation = lexer.current().location;
access = AstTableAccess::Read;
lexer.next();
}
else if (AstName(lexer.current().name) == "write")
{
accessLocation = lexer.current().location;
access = AstTableAccess::Write;
lexer.next();
}
accessLocation = lexer.current().location;
access = AstTableAccess::Read;
lexer.next();
}
else if (AstName(lexer.current().name) == "write")
{
accessLocation = lexer.current().location;
access = AstTableAccess::Write;
lexer.next();
}
}

Expand Down
3 changes: 2 additions & 1 deletion luau/CodeGen/include/Luau/BytecodeAnalysis.h
Original file line number Diff line number Diff line change
Expand Up @@ -13,10 +13,11 @@ namespace CodeGen
{

struct IrFunction;
struct HostIrHooks;

void loadBytecodeTypeInfo(IrFunction& function);
void buildBytecodeBlocks(IrFunction& function, const std::vector<uint8_t>& jumpTargets);
void analyzeBytecodeTypes(IrFunction& function);
void analyzeBytecodeTypes(IrFunction& function, const HostIrHooks& hostHooks);

} // namespace CodeGen
} // namespace Luau
42 changes: 39 additions & 3 deletions luau/CodeGen/include/Luau/CodeGen.h
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,39 @@ struct CompilationResult
}
};

struct IrBuilder;

using HostVectorOperationBytecodeType = uint8_t (*)(const char* member, size_t memberLength);
using HostVectorAccessHandler = bool (*)(IrBuilder& builder, const char* member, size_t memberLength, int resultReg, int sourceReg, int pcpos);
using HostVectorNamecallHandler = bool (*)(
IrBuilder& builder, const char* member, size_t memberLength, int argResReg, int sourceReg, int params, int results, int pcpos);

struct HostIrHooks
{
// Suggest result type of a vector field access
HostVectorOperationBytecodeType vectorAccessBytecodeType = nullptr;

// Suggest result type of a vector function namecall
HostVectorOperationBytecodeType vectorNamecallBytecodeType = nullptr;

// Handle vector value field access
// 'sourceReg' is guaranteed to be a vector
// Guards should take a VM exit to 'pcpos'
HostVectorAccessHandler vectorAccess = nullptr;

// Handle namecalled performed on a vector value
// 'sourceReg' (self argument) is guaranteed to be a vector
// All other arguments can be of any type
// Guards should take a VM exit to 'pcpos'
HostVectorNamecallHandler vectorNamecall = nullptr;
};

struct CompilationOptions
{
unsigned int flags = 0;
HostIrHooks hooks;
};

struct CompilationStats
{
size_t bytecodeSizeBytes = 0;
Expand Down Expand Up @@ -118,8 +151,11 @@ void setNativeExecutionEnabled(lua_State* L, bool enabled);
using ModuleId = std::array<uint8_t, 16>;

// Builds target function and all inner functions
CompilationResult compile(lua_State* L, int idx, unsigned int flags = 0, CompilationStats* stats = nullptr);
CompilationResult compile(const ModuleId& moduleId, lua_State* L, int idx, unsigned int flags = 0, CompilationStats* stats = nullptr);
CompilationResult compile(lua_State* L, int idx, unsigned int flags, CompilationStats* stats = nullptr);
CompilationResult compile(const ModuleId& moduleId, lua_State* L, int idx, unsigned int flags, CompilationStats* stats = nullptr);

CompilationResult compile(lua_State* L, int idx, const CompilationOptions& options, CompilationStats* stats = nullptr);
CompilationResult compile(const ModuleId& moduleId, lua_State* L, int idx, const CompilationOptions& options, CompilationStats* stats = nullptr);

using AnnotatorFn = void (*)(void* context, std::string& result, int fid, int instpos);

Expand Down Expand Up @@ -164,7 +200,7 @@ struct AssemblyOptions

Target target = Host;

unsigned int flags = 0;
CompilationOptions compilationOptions;

bool outputBinary = false;

Expand Down
10 changes: 7 additions & 3 deletions luau/CodeGen/include/Luau/IrBuilder.h
Original file line number Diff line number Diff line change
Expand Up @@ -16,11 +16,11 @@ namespace Luau
namespace CodeGen
{

struct AssemblyOptions;
struct HostIrHooks;

struct IrBuilder
{
IrBuilder();
IrBuilder(const HostIrHooks& hostHooks);

void buildFunctionIr(Proto* proto);

Expand Down Expand Up @@ -64,13 +64,17 @@ struct IrBuilder

IrOp vmExit(uint32_t pcpos);

const HostIrHooks& hostHooks;

bool inTerminatedBlock = false;

bool interruptRequested = false;

bool activeFastcallFallback = false;
IrOp fastcallFallbackReturn;
int fastcallSkipTarget = -1;

// Force builder to skip source commands
int cmdSkipTarget = -1;

IrFunction function;

Expand Down
49 changes: 46 additions & 3 deletions luau/CodeGen/src/BytecodeAnalysis.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
#include "Luau/BytecodeAnalysis.h"

#include "Luau/BytecodeUtils.h"
#include "Luau/CodeGen.h"
#include "Luau/IrData.h"
#include "Luau/IrUtils.h"

Expand All @@ -17,6 +18,8 @@ LUAU_FASTFLAG(LuauLoadTypeInfo) // Because new VM typeinfo loa
LUAU_FASTFLAGVARIABLE(LuauCodegenTypeInfo, false) // New analysis is flagged separately
LUAU_FASTFLAG(LuauTypeInfoLookupImprovement)
LUAU_FASTFLAGVARIABLE(LuauCodegenVectorMispredictFix, false)
LUAU_FASTFLAGVARIABLE(LuauCodegenAnalyzeHostVectorOps, false)
LUAU_FASTFLAGVARIABLE(LuauCodegenLoadTypeUpvalCheck, false)

namespace Luau
{
Expand Down Expand Up @@ -95,7 +98,10 @@ void loadBytecodeTypeInfo(IrFunction& function)
uint32_t upvalCount = readVarInt(data, offset);
uint32_t localCount = readVarInt(data, offset);

CODEGEN_ASSERT(upvalCount == unsigned(proto->nups));
if (!FFlag::LuauCodegenLoadTypeUpvalCheck)
{
CODEGEN_ASSERT(upvalCount == unsigned(proto->nups));
}

if (typeSize != 0)
{
Expand All @@ -114,6 +120,11 @@ void loadBytecodeTypeInfo(IrFunction& function)

if (upvalCount != 0)
{
if (FFlag::LuauCodegenLoadTypeUpvalCheck)
{
CODEGEN_ASSERT(upvalCount == unsigned(proto->nups));
}

typeInfo.upvalueTypes.resize(upvalCount);

uint8_t* types = (uint8_t*)data + offset;
Expand Down Expand Up @@ -611,7 +622,7 @@ void buildBytecodeBlocks(IrFunction& function, const std::vector<uint8_t>& jumpT
}
}

void analyzeBytecodeTypes(IrFunction& function)
void analyzeBytecodeTypes(IrFunction& function, const HostIrHooks& hostHooks)
{
Proto* proto = function.proto;
CODEGEN_ASSERT(proto);
Expand Down Expand Up @@ -662,6 +673,8 @@ void analyzeBytecodeTypes(IrFunction& function)
for (int i = proto->numparams; i < proto->maxstacksize; ++i)
regTags[i] = LBC_TYPE_ANY;

LuauBytecodeType knownNextCallResult = LBC_TYPE_ANY;

for (int i = block.startpc; i <= block.finishpc;)
{
const Instruction* pc = &proto->code[i];
Expand Down Expand Up @@ -790,6 +803,9 @@ void analyzeBytecodeTypes(IrFunction& function)
if (ch == 'x' || ch == 'y' || ch == 'z')
regTags[ra] = LBC_TYPE_NUMBER;
}

if (FFlag::LuauCodegenAnalyzeHostVectorOps && regTags[ra] == LBC_TYPE_ANY && hostHooks.vectorAccessBytecodeType)
regTags[ra] = hostHooks.vectorAccessBytecodeType(field, str->len);
}
}
else
Expand Down Expand Up @@ -1161,6 +1177,34 @@ void analyzeBytecodeTypes(IrFunction& function)
regTags[ra + 1] = bcType.a;

bcType.result = LBC_TYPE_FUNCTION;

if (FFlag::LuauCodegenAnalyzeHostVectorOps && bcType.a == LBC_TYPE_VECTOR && hostHooks.vectorNamecallBytecodeType)
{
TString* str = gco2ts(function.proto->k[kc].value.gc);
const char* field = getstr(str);

knownNextCallResult = LuauBytecodeType(hostHooks.vectorNamecallBytecodeType(field, str->len));
}
}
break;
}
case LOP_CALL:
{
if (FFlag::LuauCodegenAnalyzeHostVectorOps)
{
int ra = LUAU_INSN_A(*pc);

if (knownNextCallResult != LBC_TYPE_ANY)
{
bcType.result = knownNextCallResult;

knownNextCallResult = LBC_TYPE_ANY;

regTags[ra] = bcType.result;
}

if (FFlag::LuauCodegenTypeInfo)
refineRegType(bcTypeInfo, ra, i, bcType.result);
}
break;
}
Expand Down Expand Up @@ -1199,7 +1243,6 @@ void analyzeBytecodeTypes(IrFunction& function)
}
case LOP_GETGLOBAL:
case LOP_SETGLOBAL:
case LOP_CALL:
case LOP_RETURN:
case LOP_JUMP:
case LOP_JUMPBACK:
Expand Down
42 changes: 32 additions & 10 deletions luau/CodeGen/src/CodeGen.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -201,12 +201,12 @@ static void logPerfFunction(Proto* p, uintptr_t addr, unsigned size)
}

template<typename AssemblyBuilder>
static std::optional<OldNativeProto> createNativeFunction(
AssemblyBuilder& build, ModuleHelpers& helpers, Proto* proto, uint32_t& totalIrInstCount, CodeGenCompilationResult& result)
static std::optional<OldNativeProto> createNativeFunction(AssemblyBuilder& build, ModuleHelpers& helpers, Proto* proto, uint32_t& totalIrInstCount,
const HostIrHooks& hooks, CodeGenCompilationResult& result)
{
CODEGEN_ASSERT(!FFlag::LuauCodegenContext);

IrBuilder ir;
IrBuilder ir(hooks);
ir.buildFunctionIr(proto);

unsigned instCount = unsigned(ir.function.instructions.size());
Expand Down Expand Up @@ -476,7 +476,7 @@ void setNativeExecutionEnabled(lua_State* L, bool enabled)
}
}

static CompilationResult compile_OLD(lua_State* L, int idx, unsigned int flags, CompilationStats* stats)
static CompilationResult compile_OLD(lua_State* L, int idx, const CompilationOptions& options, CompilationStats* stats)
{
CompilationResult compilationResult;

Expand All @@ -485,7 +485,7 @@ static CompilationResult compile_OLD(lua_State* L, int idx, unsigned int flags,

Proto* root = clvalue(func)->l.p;

if ((flags & CodeGen_OnlyNativeModules) != 0 && (root->flags & LPF_NATIVE_MODULE) == 0)
if ((options.flags & CodeGen_OnlyNativeModules) != 0 && (root->flags & LPF_NATIVE_MODULE) == 0)
{
compilationResult.result = CodeGenCompilationResult::NotNativeModule;
return compilationResult;
Expand All @@ -500,7 +500,7 @@ static CompilationResult compile_OLD(lua_State* L, int idx, unsigned int flags,
}

std::vector<Proto*> protos;
gatherFunctions(protos, root, flags);
gatherFunctions(protos, root, options.flags);

// Skip protos that have been compiled during previous invocations of CodeGen::compile
protos.erase(std::remove_if(protos.begin(), protos.end(),
Expand Down Expand Up @@ -541,7 +541,7 @@ static CompilationResult compile_OLD(lua_State* L, int idx, unsigned int flags,
{
CodeGenCompilationResult protoResult = CodeGenCompilationResult::Success;

if (std::optional<OldNativeProto> np = createNativeFunction(build, helpers, p, totalIrInstCount, protoResult))
if (std::optional<OldNativeProto> np = createNativeFunction(build, helpers, p, totalIrInstCount, options.hooks, protoResult))
results.push_back(*np);
else
compilationResult.protoFailures.push_back({protoResult, p->debugname ? getstr(p->debugname) : "", p->linedefined});
Expand Down Expand Up @@ -618,21 +618,43 @@ static CompilationResult compile_OLD(lua_State* L, int idx, unsigned int flags,

CompilationResult compile(lua_State* L, int idx, unsigned int flags, CompilationStats* stats)
{
Luau::CodeGen::CompilationOptions options{flags};

if (FFlag::LuauCodegenContext)
{
return compile_NEW(L, idx, flags, stats);
return compile_NEW(L, idx, options, stats);
}
else
{
return compile_OLD(L, idx, flags, stats);
return compile_OLD(L, idx, options, stats);
}
}

CompilationResult compile(const ModuleId& moduleId, lua_State* L, int idx, unsigned int flags, CompilationStats* stats)
{
CODEGEN_ASSERT(FFlag::LuauCodegenContext);

return compile_NEW(moduleId, L, idx, flags, stats);
Luau::CodeGen::CompilationOptions options{flags};
return compile_NEW(moduleId, L, idx, options, stats);
}

CompilationResult compile(lua_State* L, int idx, const CompilationOptions& options, CompilationStats* stats)
{
if (FFlag::LuauCodegenContext)
{
return compile_NEW(L, idx, options, stats);
}
else
{
return compile_OLD(L, idx, options, stats);
}
}

CompilationResult compile(const ModuleId& moduleId, lua_State* L, int idx, const CompilationOptions& options, CompilationStats* stats)
{
CODEGEN_ASSERT(FFlag::LuauCodegenContext);

return compile_NEW(moduleId, L, idx, options, stats);
}

void setPerfLog(void* context, PerfLogFn logFn)
Expand Down
6 changes: 3 additions & 3 deletions luau/CodeGen/src/CodeGenAssembly.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -183,11 +183,11 @@ static std::string getAssemblyImpl(AssemblyBuilder& build, const TValue* func, A
{
Proto* root = clvalue(func)->l.p;

if ((options.flags & CodeGen_OnlyNativeModules) != 0 && (root->flags & LPF_NATIVE_MODULE) == 0)
if ((options.compilationOptions.flags & CodeGen_OnlyNativeModules) != 0 && (root->flags & LPF_NATIVE_MODULE) == 0)
return std::string();

std::vector<Proto*> protos;
gatherFunctions(protos, root, options.flags);
gatherFunctions(protos, root, options.compilationOptions.flags);

protos.erase(std::remove_if(protos.begin(), protos.end(),
[](Proto* p) {
Expand Down Expand Up @@ -215,7 +215,7 @@ static std::string getAssemblyImpl(AssemblyBuilder& build, const TValue* func, A

for (Proto* p : protos)
{
IrBuilder ir;
IrBuilder ir(options.compilationOptions.hooks);
ir.buildFunctionIr(p);
unsigned asmSize = build.getCodeSize();
unsigned asmCount = build.getInstructionCount();
Expand Down
Loading

0 comments on commit a5b5504

Please sign in to comment.