diff --git a/Engine/source/console/astNodes.cpp b/Engine/source/console/astNodes.cpp index c85c32ebe..1ee165272 100644 --- a/Engine/source/console/astNodes.cpp +++ b/Engine/source/console/astNodes.cpp @@ -1594,10 +1594,12 @@ U32 FunctionDeclStmtNode::compileStmt(CodeStream& codeStream, U32 ip) setCurrentFloatTable(&getGlobalFloatTable()); // map local variables to registers for this function. + // Note we have to map these in order because the table itself is ordered by the register id. CompilerLocalVariableToRegisterMappingTable* tbl = &getFunctionVariableMappingTable(); - for (const auto& pair : gFuncVars->variableNameMap) + for (size_t i = 0; i < gFuncVars->variableNameMap.size(); ++i) { - tbl->add(fnName, nameSpace, pair.second, pair.first); + StringTableEntry varName = gFuncVars->variableNameMap[i]; + tbl->add(fnName, nameSpace, varName); } gFuncVars = NULL; diff --git a/Engine/source/console/codeBlock.cpp b/Engine/source/console/codeBlock.cpp index 8d0cde4d5..14c447ba0 100644 --- a/Engine/source/console/codeBlock.cpp +++ b/Engine/source/console/codeBlock.cpp @@ -405,6 +405,30 @@ bool CodeBlock::read(StringTableEntry fileName, Stream &st) for (i = 0; i < size; i++) st.read(&functionFloats[i]); } + + // Variable register mapping table + st.read(&size); + if (size) + { + for (i = 0; i < size; i++) + { + char functionNameBuffer[256]; + st.readString(functionNameBuffer); + StringTableEntry fnName = StringTable->insert(functionNameBuffer); + + U32 count; + st.read(&count); + for (U32 j = 0; j < count; j++) + { + char varNameBuffer[256]; + st.readString(varNameBuffer); + StringTableEntry varName = StringTable->insert(varNameBuffer); + + variableRegisterTable.localVarToRegister[fnName].varList.push_back(varName); + } + } + } + U32 codeLength; st.read(&codeLength); st.read(&lineBreakPairCount); @@ -533,6 +557,9 @@ bool CodeBlock::compile(const char *codeFileName, StringTableEntry fileName, con getGlobalFloatTable().write(st); getFunctionFloatTable().write(st); + // write variable mapping table + getFunctionVariableMappingTable().write(st); + if (lastIp != codeSize) Con::errorf(ConsoleLogEntry::General, "CodeBlock::compile - precompile size mismatch, a precompile/compile function pair is probably mismatched."); @@ -645,9 +672,6 @@ ConsoleValue CodeBlock::compileExec(StringTableEntry fileName, const char *inStr codeStream.emit(OP_RETURN_VOID); codeStream.emitCodeStream(&codeSize, &code, &lineBreakPairs); - //if (Con::getBoolVariable("dump")) - //dumpInstructions(0, false); - consoleAllocReset(); if (lineBreakPairCount && fileName) @@ -679,10 +703,14 @@ String CodeBlock::getFunctionArgs(U32 ip) { StringBuilder str; + StringTableEntry fnName = CodeToSTE(code, ip); + StringTableEntry fnNamespace = CodeToSTE(code, ip + 2); + StringTableEntry fnNsName = StringTable->insert(avar("%s::%s", fnNamespace, fnName)); + U32 fnArgc = code[ip + 8]; for (U32 i = 0; i < fnArgc; ++i) { - StringTableEntry var = CodeToSTE(code, ip + (i * 2) + 9); + StringTableEntry var = variableRegisterTable.localVarToRegister[fnNsName].varList[i]; if (i != 0) str.append(", "); diff --git a/Engine/source/console/codeBlock.h b/Engine/source/console/codeBlock.h index be9de012f..a3c1015e9 100644 --- a/Engine/source/console/codeBlock.h +++ b/Engine/source/console/codeBlock.h @@ -27,18 +27,18 @@ struct CompilerLocalVariableToRegisterMappingTable { - // First key: function name struct RemappingTable { - std::unordered_map table; + std::vector varList; }; std::unordered_map localVarToRegister; - void add(StringTableEntry functionName, StringTableEntry namespaceName, StringTableEntry varName, S32 reg); + void add(StringTableEntry functionName, StringTableEntry namespaceName, StringTableEntry varName); S32 lookup(StringTableEntry namespaceName, StringTableEntry functionName, StringTableEntry varName); CompilerLocalVariableToRegisterMappingTable copy(); void reset(); + void write(Stream& stream); }; #include "console/compiler.h" diff --git a/Engine/source/console/compiler.cpp b/Engine/source/console/compiler.cpp index 7a091c202..9af61bef2 100644 --- a/Engine/source/console/compiler.cpp +++ b/Engine/source/console/compiler.cpp @@ -212,11 +212,11 @@ void CompilerStringTable::write(Stream &st) //------------------------------------------------------------ -void CompilerLocalVariableToRegisterMappingTable::add(StringTableEntry functionName, StringTableEntry namespaceName, StringTableEntry varName, S32 reg) +void CompilerLocalVariableToRegisterMappingTable::add(StringTableEntry functionName, StringTableEntry namespaceName, StringTableEntry varName) { StringTableEntry funcLookupTableName = StringTable->insert(avar("%s::%s", namespaceName, functionName)); - localVarToRegister[funcLookupTableName].table[varName] = reg; + localVarToRegister[funcLookupTableName].varList.push_back(varName);; } S32 CompilerLocalVariableToRegisterMappingTable::lookup(StringTableEntry namespaceName, StringTableEntry functionName, StringTableEntry varName) @@ -226,11 +226,11 @@ S32 CompilerLocalVariableToRegisterMappingTable::lookup(StringTableEntry namespa auto functionPosition = localVarToRegister.find(funcLookupTableName); if (functionPosition != localVarToRegister.end()) { - const auto& table = localVarToRegister[funcLookupTableName].table; - auto varPosition = table.find(varName); + const auto& table = localVarToRegister[funcLookupTableName].varList; + auto varPosition = std::find(table.begin(), table.end(), varName); if (varPosition != table.end()) { - return varPosition->second; + return std::distance(table.begin(), varPosition); } } @@ -243,7 +243,7 @@ CompilerLocalVariableToRegisterMappingTable CompilerLocalVariableToRegisterMappi // Trivilly copyable as its all plain old data and using STL containers... (We want a deep copy though!) CompilerLocalVariableToRegisterMappingTable table; table.localVarToRegister = localVarToRegister; - return std::move(table); + return table; } void CompilerLocalVariableToRegisterMappingTable::reset() @@ -251,6 +251,21 @@ void CompilerLocalVariableToRegisterMappingTable::reset() localVarToRegister.clear(); } +void CompilerLocalVariableToRegisterMappingTable::write(Stream& stream) +{ + stream.write(localVarToRegister.size()); + for (const auto& pair : localVarToRegister) + { + StringTableEntry functionName = pair.first; + stream.writeString(functionName); + + const auto& localVariableTableForFunction = localVarToRegister[functionName].varList; + stream.write(localVariableTableForFunction.size()); + for (const StringTableEntry& varName : localVariableTableForFunction) + stream.writeString(varName); + } +} + //------------------------------------------------------------ U32 CompilerFloatTable::add(F64 value)