@@ -9,6 +9,48 @@ using namespace libscratchcpp;
99static const std::unordered_set<LLVMInstruction::Type>
1010 BEGIN_LOOP_INSTRUCTIONS = { LLVMInstruction::Type::BeginRepeatLoop, LLVMInstruction::Type::BeginWhileLoop, LLVMInstruction::Type::BeginRepeatUntilLoop };
1111
12+ Compiler::StaticType LLVMTypeAnalyzer::variableType (LLVMVariablePtr *varPtr, LLVMInstruction *pos, Compiler::StaticType previousType) const
13+ {
14+ if (!varPtr || !pos)
15+ return Compiler::StaticType::Unknown;
16+
17+ // Check the last write operation before the instruction
18+ LLVMInstruction *ins = pos;
19+ LLVMInstruction *write = nullptr ;
20+ LLVMInstruction *loopStart = nullptr ;
21+ int level = 0 ;
22+
23+ while (ins) {
24+ if (isLoopEnd (ins))
25+ level++;
26+ else if (isLoopStart (ins)) {
27+ level--;
28+
29+ if (!loopStart)
30+ loopStart = ins;
31+ } else if (ins->type == LLVMInstruction::Type::WriteVariable && ins->workVariable == varPtr->var ) {
32+ if (level <= 0 ) { // ignore nested loops (they're handled later)
33+ write = ins;
34+ break ;
35+ }
36+ }
37+
38+ ins = ins->previous ;
39+ }
40+
41+ if (loopStart) {
42+ // Analyze the first loop that was found
43+ if (variableTypeChangesInLoop (varPtr, loopStart, previousType))
44+ return write ? writeValueType (write) : Compiler::StaticType::Unknown;
45+ } else if (write) {
46+ // There wasn't any loop found, so we can just check the last write operation
47+ return writeValueType (write);
48+ }
49+
50+ // No write operation found
51+ return previousType;
52+ }
53+
1254bool LLVMTypeAnalyzer::variableTypeChangesInLoop (LLVMVariablePtr *varPtr, LLVMInstruction *loopBody, Compiler::StaticType preLoopType) const
1355{
1456 if (!varPtr || !loopBody)
0 commit comments