Browse code

bytecode: refactored cleanup on error exit paths, cid #10509 & #10510

David Raynor authored on 2013/08/16 05:23:44
Showing 1 changed files
... ...
@@ -1232,6 +1232,7 @@ public:
1232 1232
 	for (unsigned j=0;j<bc->num_func;j++) {
1233 1233
 	    PrettyStackTraceString CrashInfo("Generate LLVM IR");
1234 1234
 	    const struct cli_bc_func *func = &bc->funcs[j];
1235
+	    bool broken = false;
1235 1236
 
1236 1237
 	    // Create all BasicBlocks
1237 1238
 	    Function *F = Functions[j];
... ...
@@ -1308,12 +1309,12 @@ public:
1308 1308
 	    }
1309 1309
 
1310 1310
 	    // Generate LLVM IR for each BB
1311
-	    for (unsigned i=0;i<func->numBB;i++) {
1311
+	    for (unsigned i=0;i<func->numBB && !broken;i++) {
1312 1312
 		bool unreachable = false;
1313 1313
 		const struct cli_bc_bb *bb = &func->BB[i];
1314 1314
 		Builder.SetInsertPoint(BB[i]);
1315 1315
 		unsigned c = 0;
1316
-		for (unsigned j=0;j<bb->numInsts;j++) {
1316
+		for (unsigned j=0;j<bb->numInsts && !broken;j++) {
1317 1317
 		    const struct cli_bc_inst *inst = &bb->insts[j];
1318 1318
 		    Value *Op0=0, *Op1=0, *Op2=0;
1319 1319
 		    // libclamav has already validated this.
... ...
@@ -1453,8 +1454,8 @@ public:
1453 1453
 			    BasicBlock *False = BB[inst->u.branch.br_false];
1454 1454
 			    if (Cond->getType() != Type::getInt1Ty(Context)) {
1455 1455
 				cli_warnmsg("[Bytecode JIT]: type mismatch in condition");
1456
-				apiMap.irgenTimer.stopTimer();
1457
-				return 0;
1456
+				broken = true;
1457
+				break;
1458 1458
 			    }
1459 1459
 			    Builder.CreateCondBr(Cond, True, False);
1460 1460
 			    break;
... ...
@@ -1558,8 +1559,8 @@ public:
1558 1558
 			    Value *Op = convertOperand(func, I32Ty, inst->u.three[2]);
1559 1559
 			    Op = GEPOperand(Op);
1560 1560
 			    if (!createGEP(inst->dest, V, ARRAYREF(Value*, &Op, &Op+1))) {
1561
-				apiMap.irgenTimer.stopTimer();
1562
-				return 0;
1561
+				cli_warnmsg("[Bytecode JIT]: OP_BC_GEP1 createGEP failed\n");
1562
+				broken = true;
1563 1563
 			    }
1564 1564
 			    break;
1565 1565
 			}
... ...
@@ -1572,8 +1573,8 @@ public:
1572 1572
 			    Ops[1] = convertOperand(func, I32Ty, inst->u.three[2]);
1573 1573
 			    Ops[1] = GEPOperand(Ops[1]);
1574 1574
 			    if (!createGEP(inst->dest, V, ARRAYREF(Value*, Ops, Ops+2))) {
1575
-				apiMap.irgenTimer.stopTimer();
1576
-				return 0;
1575
+				cli_warnmsg("[Bytecode JIT]: OP_BC_GEPZ createGEP failed\n");
1576
+				broken = true;
1577 1577
 			    }
1578 1578
 			    break;
1579 1579
 			}
... ...
@@ -1589,8 +1590,8 @@ public:
1589 1589
 				Idxs.push_back(Op);
1590 1590
 			    }
1591 1591
 			    if (!createGEP(inst->dest, V, ARRAYREFVECTOR(Value*, Idxs))) {
1592
-				apiMap.irgenTimer.stopTimer();
1593
-				return 0;
1592
+				cli_warnmsg("[Bytecode JIT]: OP_BC_GEPN createGEP failed\n");
1593
+				broken = true;
1594 1594
 			    }
1595 1595
 			    break;
1596 1596
 			}
... ...
@@ -1745,22 +1746,31 @@ public:
1745 1745
 			default:
1746 1746
 			    cli_warnmsg("[Bytecode JIT]: JIT doesn't implement opcode %d yet!\n",
1747 1747
 					inst->opcode);
1748
-			    apiMap.irgenTimer.stopTimer();
1749
-			    return 0;
1748
+			    broken = true;
1749
+			    break;
1750 1750
 		    }
1751 1751
 		}
1752 1752
 	    }
1753 1753
 
1754
-	    if (verifyFunction(*F, PrintMessageAction)) {
1755
-		// verification failed
1756
-		cli_warnmsg("[Bytecode JIT]: Verification failed\n");
1757
-		if (cli_debug_flag) {
1758
-		    std::string str;
1759
-		    raw_string_ostream ostr(str);
1760
-		    F->print(ostr);
1761
-		    cli_dbgmsg_internal("[Bytecode JIT]: %s\n", ostr.str().c_str());
1754
+	    // If successful so far, run verifyFunction
1755
+	    if (!broken) {
1756
+		if (verifyFunction(*F, PrintMessageAction)) {
1757
+		    // verification failed
1758
+		    broken = true;
1759
+		    cli_warnmsg("[Bytecode JIT]: Verification failed\n");
1760
+		    if (cli_debug_flag) {
1761
+			std::string str;
1762
+			raw_string_ostream ostr(str);
1763
+			F->print(ostr);
1764
+			cli_dbgmsg_internal("[Bytecode JIT]: %s\n", ostr.str().c_str());
1765
+		    }
1762 1766
 		}
1763
-		delete [] Values;
1767
+	    }
1768
+
1769
+	    delete [] Values;
1770
+
1771
+	    // Cleanup after failure and return 0
1772
+	    if (broken) {
1764 1773
 		for (unsigned z=0; z < func->numBB ; z++) {
1765 1774
 		    delete BB[z];
1766 1775
 		}
... ...
@@ -1773,7 +1783,7 @@ public:
1773 1773
 		delete [] Functions;
1774 1774
 		return 0;
1775 1775
 	    }
1776
-	    delete [] Values;
1776
+
1777 1777
 	    delete [] BB;
1778 1778
 	    apiMap.irgenTimer.stopTimer();
1779 1779
 	    apiMap.pmTimer.startTimer();