1 | //===- DemandedBitsTest.cpp - DemandedBits tests --------------------------===// |
2 | // |
3 | // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. |
4 | // See https://llvm.org/LICENSE.txt for license information. |
5 | // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception |
6 | // |
7 | //===----------------------------------------------------------------------===// |
8 | |
9 | #include "llvm/Analysis/DemandedBits.h" |
10 | #include "../Support/KnownBitsTest.h" |
11 | #include "llvm/Support/KnownBits.h" |
12 | #include "gtest/gtest.h" |
13 | |
14 | using namespace llvm; |
15 | |
16 | namespace { |
17 | |
18 | template <typename Fn1, typename Fn2> |
19 | static void TestBinOpExhaustive(Fn1 PropagateFn, Fn2 EvalFn) { |
20 | unsigned Bits = 4; |
21 | unsigned Max = 1 << Bits; |
22 | ForeachKnownBits(Bits, [&](const KnownBits &Known1) { |
23 | ForeachKnownBits(Bits, [&](const KnownBits &Known2) { |
24 | for (unsigned AOut_ = 0; AOut_ < Max; AOut_++) { |
25 | APInt AOut(Bits, AOut_); |
26 | APInt AB1 = PropagateFn(0, AOut, Known1, Known2); |
27 | APInt AB2 = PropagateFn(1, AOut, Known1, Known2); |
28 | { |
29 | // If the propagator claims that certain known bits |
30 | // didn't matter, check it doesn't change its mind |
31 | // when they become unknown. |
32 | KnownBits Known1Redacted; |
33 | KnownBits Known2Redacted; |
34 | Known1Redacted.Zero = Known1.Zero & AB1; |
35 | Known1Redacted.One = Known1.One & AB1; |
36 | Known2Redacted.Zero = Known2.Zero & AB2; |
37 | Known2Redacted.One = Known2.One & AB2; |
38 | |
39 | APInt AB1R = PropagateFn(0, AOut, Known1Redacted, Known2Redacted); |
40 | APInt AB2R = PropagateFn(1, AOut, Known1Redacted, Known2Redacted); |
41 | EXPECT_EQ(AB1, AB1R); |
42 | EXPECT_EQ(AB2, AB2R); |
43 | } |
44 | ForeachNumInKnownBits(Known1, [&](APInt Value1) { |
45 | ForeachNumInKnownBits(Known2, [&](APInt Value2) { |
46 | APInt ReferenceResult = EvalFn((Value1 & AB1), (Value2 & AB2)); |
47 | APInt Result = EvalFn(Value1, Value2); |
48 | EXPECT_EQ(Result & AOut, ReferenceResult & AOut); |
49 | }); |
50 | }); |
51 | } |
52 | }); |
53 | }); |
54 | } |
55 | |
56 | TEST(DemandedBitsTest, Add) { |
57 | TestBinOpExhaustive(PropagateFn: DemandedBits::determineLiveOperandBitsAdd, |
58 | EvalFn: [](APInt N1, APInt N2) -> APInt { return N1 + N2; }); |
59 | } |
60 | |
61 | TEST(DemandedBitsTest, Sub) { |
62 | TestBinOpExhaustive(PropagateFn: DemandedBits::determineLiveOperandBitsSub, |
63 | EvalFn: [](APInt N1, APInt N2) -> APInt { return N1 - N2; }); |
64 | } |
65 | |
66 | } // anonymous namespace |
67 | |