OLD | NEW |
1 //===- NaClBitcodeReader.cpp ----------------------------------------------===// | 1 //===- NaClBitcodeReader.cpp ----------------------------------------------===// |
2 // Internal NaClBitcodeReader implementation | 2 // Internal NaClBitcodeReader implementation |
3 // | 3 // |
4 // The LLVM Compiler Infrastructure | 4 // The LLVM Compiler Infrastructure |
5 // | 5 // |
6 // This file is distributed under the University of Illinois Open Source | 6 // This file is distributed under the University of Illinois Open Source |
7 // License. See LICENSE.TXT for details. | 7 // License. See LICENSE.TXT for details. |
8 // | 8 // |
9 //===----------------------------------------------------------------------===// | 9 //===----------------------------------------------------------------------===// |
10 | 10 |
(...skipping 1472 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1483 | 1483 |
1484 | 1484 |
1485 bool NaClBitcodeReader::isMaterializable(const GlobalValue *GV) const { | 1485 bool NaClBitcodeReader::isMaterializable(const GlobalValue *GV) const { |
1486 if (const Function *F = dyn_cast<Function>(GV)) { | 1486 if (const Function *F = dyn_cast<Function>(GV)) { |
1487 return F->isDeclaration() && | 1487 return F->isDeclaration() && |
1488 DeferredFunctionInfo.count(const_cast<Function*>(F)); | 1488 DeferredFunctionInfo.count(const_cast<Function*>(F)); |
1489 } | 1489 } |
1490 return false; | 1490 return false; |
1491 } | 1491 } |
1492 | 1492 |
1493 bool NaClBitcodeReader::Materialize(GlobalValue *GV, std::string *ErrInfo) { | 1493 error_code NaClBitcodeReader::Materialize(GlobalValue *GV) { |
1494 Function *F = dyn_cast<Function>(GV); | 1494 Function *F = dyn_cast<Function>(GV); |
1495 // If it's not a function or is already material, ignore the request. | 1495 // If it's not a function or is already material, ignore the request. |
1496 if (!F || !F->isMaterializable()) return false; | 1496 if (!F || !F->isMaterializable()) |
| 1497 return error_code::success(); |
1497 | 1498 |
1498 DenseMap<Function*, uint64_t>::iterator DFII = DeferredFunctionInfo.find(F); | 1499 DenseMap<Function*, uint64_t>::iterator DFII = DeferredFunctionInfo.find(F); |
1499 assert(DFII != DeferredFunctionInfo.end() && "Deferred function not found!"); | 1500 assert(DFII != DeferredFunctionInfo.end() && "Deferred function not found!"); |
1500 // If its position is recorded as 0, its body is somewhere in the stream | 1501 // If its position is recorded as 0, its body is somewhere in the stream |
1501 // but we haven't seen it yet. | 1502 // but we haven't seen it yet. |
1502 if (DFII->second == 0) | 1503 if (DFII->second == 0) { |
1503 if (LazyStreamer && FindFunctionInStream(F, DFII)) return true; | 1504 if (FindFunctionInStream(F, DFII)) { |
| 1505 // Refactoring upstream in LLVM 3.4 means we can no longer |
| 1506 // return an error string here, so return a catch-all error |
| 1507 // code. |
| 1508 // TODO(mseaborn): Clean up the reader to return a more |
| 1509 // meaningful error_code here. |
| 1510 return make_error_code(errc::invalid_argument); |
| 1511 } |
| 1512 } |
1504 | 1513 |
1505 // Move the bit stream to the saved position of the deferred function body. | 1514 // Move the bit stream to the saved position of the deferred function body. |
1506 Stream.JumpToBit(DFII->second); | 1515 Stream.JumpToBit(DFII->second); |
1507 | 1516 |
1508 if (ParseFunctionBody(F)) { | 1517 if (ParseFunctionBody(F)) { |
1509 if (ErrInfo) *ErrInfo = ErrorString; | 1518 // TODO(mseaborn): Clean up the reader to return a more meaningful |
1510 return true; | 1519 // error_code instead of a catch-all. |
| 1520 return make_error_code(errc::invalid_argument); |
1511 } | 1521 } |
1512 | 1522 |
1513 // Upgrade any old intrinsic calls in the function. | 1523 // Upgrade any old intrinsic calls in the function. |
1514 for (UpgradedIntrinsicMap::iterator I = UpgradedIntrinsics.begin(), | 1524 for (UpgradedIntrinsicMap::iterator I = UpgradedIntrinsics.begin(), |
1515 E = UpgradedIntrinsics.end(); I != E; ++I) { | 1525 E = UpgradedIntrinsics.end(); I != E; ++I) { |
1516 if (I->first != I->second) { | 1526 if (I->first != I->second) { |
1517 for (Value::use_iterator UI = I->first->use_begin(), | 1527 for (Value::use_iterator UI = I->first->use_begin(), |
1518 UE = I->first->use_end(); UI != UE; ) { | 1528 UE = I->first->use_end(); UI != UE; ) { |
1519 if (CallInst* CI = dyn_cast<CallInst>(*UI++)) | 1529 if (CallInst* CI = dyn_cast<CallInst>(*UI++)) |
1520 UpgradeIntrinsicCall(CI, I->second); | 1530 UpgradeIntrinsicCall(CI, I->second); |
1521 } | 1531 } |
1522 } | 1532 } |
1523 } | 1533 } |
1524 | 1534 |
1525 return false; | 1535 return error_code::success(); |
1526 } | 1536 } |
1527 | 1537 |
1528 bool NaClBitcodeReader::isDematerializable(const GlobalValue *GV) const { | 1538 bool NaClBitcodeReader::isDematerializable(const GlobalValue *GV) const { |
1529 const Function *F = dyn_cast<Function>(GV); | 1539 const Function *F = dyn_cast<Function>(GV); |
1530 if (!F || F->isDeclaration()) | 1540 if (!F || F->isDeclaration()) |
1531 return false; | 1541 return false; |
1532 return DeferredFunctionInfo.count(const_cast<Function*>(F)); | 1542 return DeferredFunctionInfo.count(const_cast<Function*>(F)); |
1533 } | 1543 } |
1534 | 1544 |
1535 void NaClBitcodeReader::Dematerialize(GlobalValue *GV) { | 1545 void NaClBitcodeReader::Dematerialize(GlobalValue *GV) { |
1536 Function *F = dyn_cast<Function>(GV); | 1546 Function *F = dyn_cast<Function>(GV); |
1537 // If this function isn't dematerializable, this is a noop. | 1547 // If this function isn't dematerializable, this is a noop. |
1538 if (!F || !isDematerializable(F)) | 1548 if (!F || !isDematerializable(F)) |
1539 return; | 1549 return; |
1540 | 1550 |
1541 assert(DeferredFunctionInfo.count(F) && "No info to read function later?"); | 1551 assert(DeferredFunctionInfo.count(F) && "No info to read function later?"); |
1542 | 1552 |
1543 // Just forget the function body, we can remat it later. | 1553 // Just forget the function body, we can remat it later. |
1544 F->deleteBody(); | 1554 F->deleteBody(); |
1545 } | 1555 } |
1546 | 1556 |
1547 | 1557 |
1548 bool NaClBitcodeReader::MaterializeModule(Module *M, std::string *ErrInfo) { | 1558 error_code NaClBitcodeReader::MaterializeModule(Module *M) { |
1549 assert(M == TheModule && | 1559 assert(M == TheModule && |
1550 "Can only Materialize the Module this NaClBitcodeReader is attached to.
"); | 1560 "Can only Materialize the Module this NaClBitcodeReader is attached to.
"); |
1551 // Iterate over the module, deserializing any functions that are still on | 1561 // Iterate over the module, deserializing any functions that are still on |
1552 // disk. | 1562 // disk. |
1553 for (Module::iterator F = TheModule->begin(), E = TheModule->end(); | 1563 for (Module::iterator F = TheModule->begin(), E = TheModule->end(); |
1554 F != E; ++F) | 1564 F != E; ++F) { |
1555 if (F->isMaterializable() && | 1565 if (F->isMaterializable()) { |
1556 Materialize(F, ErrInfo)) | 1566 if (error_code EC = Materialize(F)) |
1557 return true; | 1567 return EC; |
| 1568 } |
| 1569 } |
1558 | 1570 |
1559 // At this point, if there are any function bodies, the current bit is | 1571 // At this point, if there are any function bodies, the current bit is |
1560 // pointing to the END_BLOCK record after them. Now make sure the rest | 1572 // pointing to the END_BLOCK record after them. Now make sure the rest |
1561 // of the bits in the module have been read. | 1573 // of the bits in the module have been read. |
1562 if (NextUnreadBit) | 1574 if (NextUnreadBit) |
1563 ParseModule(true); | 1575 ParseModule(true); |
1564 | 1576 |
1565 // Upgrade any intrinsic calls that slipped through (should not happen!) and | 1577 // Upgrade any intrinsic calls that slipped through (should not happen!) and |
1566 // delete the old functions to clean up. We can't do this unless the entire | 1578 // delete the old functions to clean up. We can't do this unless the entire |
1567 // module is materialized because there could always be another function body | 1579 // module is materialized because there could always be another function body |
1568 // with calls to the old function. | 1580 // with calls to the old function. |
1569 for (std::vector<std::pair<Function*, Function*> >::iterator I = | 1581 for (std::vector<std::pair<Function*, Function*> >::iterator I = |
1570 UpgradedIntrinsics.begin(), E = UpgradedIntrinsics.end(); I != E; ++I) { | 1582 UpgradedIntrinsics.begin(), E = UpgradedIntrinsics.end(); I != E; ++I) { |
1571 if (I->first != I->second) { | 1583 if (I->first != I->second) { |
1572 for (Value::use_iterator UI = I->first->use_begin(), | 1584 for (Value::use_iterator UI = I->first->use_begin(), |
1573 UE = I->first->use_end(); UI != UE; ) { | 1585 UE = I->first->use_end(); UI != UE; ) { |
1574 if (CallInst* CI = dyn_cast<CallInst>(*UI++)) | 1586 if (CallInst* CI = dyn_cast<CallInst>(*UI++)) |
1575 UpgradeIntrinsicCall(CI, I->second); | 1587 UpgradeIntrinsicCall(CI, I->second); |
1576 } | 1588 } |
1577 if (!I->first->use_empty()) | 1589 if (!I->first->use_empty()) |
1578 I->first->replaceAllUsesWith(I->second); | 1590 I->first->replaceAllUsesWith(I->second); |
1579 I->first->eraseFromParent(); | 1591 I->first->eraseFromParent(); |
1580 } | 1592 } |
1581 } | 1593 } |
1582 std::vector<std::pair<Function*, Function*> >().swap(UpgradedIntrinsics); | 1594 std::vector<std::pair<Function*, Function*> >().swap(UpgradedIntrinsics); |
1583 | 1595 |
1584 return false; | 1596 return error_code::success(); |
1585 } | 1597 } |
1586 | 1598 |
1587 bool NaClBitcodeReader::InitStream() { | 1599 bool NaClBitcodeReader::InitStream() { |
1588 if (LazyStreamer) return InitLazyStream(); | 1600 if (LazyStreamer) return InitLazyStream(); |
1589 return InitStreamFromBuffer(); | 1601 return InitStreamFromBuffer(); |
1590 } | 1602 } |
1591 | 1603 |
1592 bool NaClBitcodeReader::InitStreamFromBuffer() { | 1604 bool NaClBitcodeReader::InitStreamFromBuffer() { |
1593 const unsigned char *BufPtr = (const unsigned char*)Buffer->getBufferStart(); | 1605 const unsigned char *BufPtr = (const unsigned char*)Buffer->getBufferStart(); |
1594 const unsigned char *BufEnd = BufPtr+Buffer->getBufferSize(); | 1606 const unsigned char *BufEnd = BufPtr+Buffer->getBufferSize(); |
(...skipping 88 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1683 if (M->MaterializeAllPermanently(ErrMsg)) { | 1695 if (M->MaterializeAllPermanently(ErrMsg)) { |
1684 delete M; | 1696 delete M; |
1685 return 0; | 1697 return 0; |
1686 } | 1698 } |
1687 | 1699 |
1688 // TODO: Restore the use-lists to the in-memory state when the bitcode was | 1700 // TODO: Restore the use-lists to the in-memory state when the bitcode was |
1689 // written. We must defer until the Module has been fully materialized. | 1701 // written. We must defer until the Module has been fully materialized. |
1690 | 1702 |
1691 return M; | 1703 return M; |
1692 } | 1704 } |
OLD | NEW |