Coverage for /Syzygy/block_graph/transforms/chained_basic_block_transforms_unittest.cc

CoverageLines executed / instrumented / missingexe / inst / missLanguageGroup
100.0%65650.C++test

Line-by-line coverage:

   1    :  // Copyright 2013 Google Inc. All Rights Reserved.
   2    :  //
   3    :  // Licensed under the Apache License, Version 2.0 (the "License");
   4    :  // you may not use this file except in compliance with the License.
   5    :  // You may obtain a copy of the License at
   6    :  //
   7    :  //     http://www.apache.org/licenses/LICENSE-2.0
   8    :  //
   9    :  // Unless required by applicable law or agreed to in writing, software
  10    :  // distributed under the License is distributed on an "AS IS" BASIS,
  11    :  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  12    :  // See the License for the specific language governing permissions and
  13    :  // limitations under the License.
  14    :  //
  15    :  // Unittests for ChainedBasicBlockTransforms.
  16    :  
  17    :  #include "syzygy/block_graph/transforms/chained_basic_block_transforms.h"
  18    :  
  19    :  #include "gtest/gtest.h"
  20    :  #include "syzygy/block_graph/basic_block.h"
  21    :  #include "syzygy/block_graph/basic_block_assembler.h"
  22    :  #include "syzygy/block_graph/basic_block_decomposer.h"
  23    :  #include "syzygy/block_graph/basic_block_subgraph.h"
  24    :  #include "syzygy/block_graph/block_graph.h"
  25    :  #include "syzygy/block_graph/transform.h"
  26    :  #include "syzygy/block_graph/unittest_util.h"
  27    :  
  28    :  #include "mnemonics.h"  // NOLINT
  29    :  
  30    :  namespace block_graph {
  31    :  namespace transforms {
  32    :  namespace {
  33    :  
  34    :  class TestChainedBasicBlockTransforms : public ChainedBasicBlockTransforms {
  35    :   public:
  36    :    using ChainedBasicBlockTransforms::transforms_;
  37    :  };
  38    :  
  39    :  const uint8 kData1Data[] =
  40    :      { 1,  2,  3,  4,  5,  6,  7,  8,  9, 10, 11, 12, 13, 14, 15, 16 };
  41    :  
  42    :  // kNop9 + kRet
  43    :  const uint8 kCode1Data[] =
  44    :      { 0x66, 0x0F, 0x1F, 0x84, 0x00, 0x00, 0x00, 0x00, 0x00, 0xC3 };
  45    :  // kRet
  46    :  const uint8 kCode2Data[] = { 0xC3 };
  47    :  
  48    :  class ChainedBasicBlockTransformsTest : public testing::Test {
  49    :   public:
  50  E :    virtual void SetUp() {
  51    :      BlockGraph::Block* d1 =
  52  E :          block_graph_.AddBlock(BlockGraph::DATA_BLOCK, sizeof(kData1Data), "d1");
  53  E :      ASSERT_NE(reinterpret_cast<BlockGraph::Block*>(NULL), d1);
  54  E :      d1->SetData(kData1Data, sizeof(kData1Data));
  55    :  
  56    :      BlockGraph::Block* c1 =
  57  E :          block_graph_.AddBlock(BlockGraph::CODE_BLOCK, sizeof(kCode1Data), "c1");
  58  E :      ASSERT_NE(reinterpret_cast<BlockGraph::Block*>(NULL), c1);
  59  E :      c1->SetData(kCode1Data, sizeof(kCode1Data));
  60    :  
  61    :      BlockGraph::Block* c2 =
  62  E :          block_graph_.AddBlock(BlockGraph::CODE_BLOCK, sizeof(kCode2Data), "c2");
  63  E :      ASSERT_NE(reinterpret_cast<BlockGraph::Block*>(NULL), c2);
  64  E :      c2->SetData(kCode2Data, sizeof(kCode2Data));
  65    :  
  66  E :      header_ = d1;
  67  E :    }
  68    :  
  69  E :    bool Relink(TestChainedBasicBlockTransforms* transform) {
  70  E :      DCHECK_NE(reinterpret_cast<TestChainedBasicBlockTransforms*>(NULL),
  71    :                transform);
  72    :      return ApplyBlockGraphTransform(transform,
  73    :                                      &policy_,
  74    :                                      &block_graph_,
  75  E :                                      header_);
  76  E :    }
  77    :  
  78    :   protected:
  79    :    testing::DummyTransformPolicy policy_;
  80    :    BlockGraph block_graph_;
  81    :    BlockGraph::Block* header_;
  82    :  };
  83    :  
  84    :  class InsertOrRemoveBasicBlockTransform
  85    :      : public block_graph::transforms::NamedBasicBlockSubGraphTransformImpl<
  86    :                   InsertOrRemoveBasicBlockTransform> {
  87    :   public:
  88  E :    InsertOrRemoveBasicBlockTransform(std::set<std::string>* blocks,
  89    :                                      bool insert)
  90    :        : blocks_(blocks), insert_(insert) {
  91  E :    }
  92    :  
  93    :    bool TransformBasicBlockSubGraph(
  94    :        const TransformPolicyInterface* policy,
  95    :        BlockGraph* block_graph,
  96    :        BasicBlockSubGraph* basic_block_subgraph) override;
  97    :  
  98    :    static const char InsertOrRemoveBasicBlockTransform::kTransformName[];
  99    :  
 100    :    bool insert_;
 101    :    std::set<std::string>* blocks_;
 102    :  };
 103    :  
 104    :  bool InsertOrRemoveBasicBlockTransform::TransformBasicBlockSubGraph(
 105    :      const TransformPolicyInterface* policy,
 106    :      BlockGraph* block_graph,
 107  E :      BasicBlockSubGraph* subgraph) {
 108  E :    DCHECK_NE(reinterpret_cast<TransformPolicyInterface*>(NULL), policy);
 109  E :    DCHECK_NE(reinterpret_cast<BlockGraph*>(NULL), block_graph);
 110  E :    DCHECK_NE(reinterpret_cast<BasicBlockSubGraph*>(NULL), subgraph);
 111    :  
 112  E :    if (insert_) {
 113  E :      blocks_->insert(subgraph->original_block()->name());
 114  E :    } else {
 115  E :      blocks_->erase(subgraph->original_block()->name());
 116    :    }
 117    :  
 118  E :    return true;
 119  E :  }
 120    :  
 121    :  const char InsertOrRemoveBasicBlockTransform::kTransformName[] =
 122    :      "InsertOrRemoveBasicBlockTransform";
 123    :  
 124    :  }  // namespace
 125    :  
 126  E :  TEST_F(ChainedBasicBlockTransformsTest, NoTransforms) {
 127  E :    TestChainedBasicBlockTransforms chains;
 128  E :    EXPECT_EQ(std::string("ChainedBasicBlockTransforms"), chains.name());
 129  E :    EXPECT_TRUE(chains.transforms_.empty());
 130  E :  }
 131    :  
 132  E :  TEST_F(ChainedBasicBlockTransformsTest, AppendTransforms) {
 133  E :    std::set<std::string> blocks;
 134  E :    InsertOrRemoveBasicBlockTransform insert(&blocks, true);
 135  E :    InsertOrRemoveBasicBlockTransform remove(&blocks, false);
 136    :  
 137    :    // Validate AppendTransform.
 138  E :    TestChainedBasicBlockTransforms chains;
 139  E :    EXPECT_TRUE(chains.transforms_.empty());
 140  E :    chains.AppendTransform(&insert);
 141  E :    EXPECT_EQ(1U, chains.transforms_.size());
 142  E :    chains.AppendTransform(&remove);
 143  E :    EXPECT_EQ(2U, chains.transforms_.size());
 144  E :  }
 145    :  
 146  E :  TEST_F(ChainedBasicBlockTransformsTest, SingleTransforms) {
 147  E :    std::set<std::string> blocks;
 148  E :    InsertOrRemoveBasicBlockTransform insert(&blocks, true);
 149    :  
 150  E :    TestChainedBasicBlockTransforms chains;
 151  E :    chains.AppendTransform(&insert);
 152  E :    EXPECT_TRUE(Relink(&chains));
 153    :  
 154    :    // Validate that the data block are ignored.
 155  E :    EXPECT_TRUE(blocks.find("d1") == blocks.end());
 156    :  
 157    :    // Validate that code block are present.
 158  E :    EXPECT_TRUE(blocks.find("c1") != blocks.end());
 159  E :    EXPECT_TRUE(blocks.find("c2") != blocks.end());
 160    :  
 161    :    // Validate that insert pass was executed.
 162  E :    EXPECT_EQ(2U, blocks.size());
 163  E :  }
 164    :  
 165  E :  TEST_F(ChainedBasicBlockTransformsTest, FullTransforms) {
 166  E :    std::set<std::string> blocks;
 167  E :    InsertOrRemoveBasicBlockTransform insert(&blocks, true);
 168  E :    InsertOrRemoveBasicBlockTransform remove(&blocks, false);
 169    :  
 170  E :    TestChainedBasicBlockTransforms chains;
 171  E :    chains.AppendTransform(&insert);
 172  E :    chains.AppendTransform(&remove);
 173  E :    EXPECT_TRUE(Relink(&chains));
 174    :  
 175    :    // Validate that both passes were executed.
 176  E :    EXPECT_TRUE(blocks.empty());
 177  E :  }
 178    :  
 179    :  }  // namespace transforms
 180    :  }  // namespace block_graph

Coverage information generated Thu Jan 14 17:40:38 2016.