diff options
author | Evgeniy Stepanov <eugeni.stepanov@gmail.com> | 2013-11-14 12:31:18 +0000 |
---|---|---|
committer | Evgeniy Stepanov <eugeni.stepanov@gmail.com> | 2013-11-14 12:31:18 +0000 |
commit | b9ac7162892b283f05b70b6d79eb92119712ff0d (patch) | |
tree | 90da2162f020d3c30ca3f91f623803b0110d4ea0 | |
parent | 5e43cfa5e7f6d344f4b0a6a9f7a4b2811d5b8bab (diff) | |
download | compiler-rt-b9ac7162892b283f05b70b6d79eb92119712ff0d.tar.gz |
[msan] A test for r194697.
git-svn-id: https://llvm.org/svn/llvm-project/compiler-rt/trunk@194699 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r-- | lib/msan/lit_tests/wrap_indirect_calls.cc | 64 | ||||
-rw-r--r-- | lib/msan/lit_tests/wrap_indirect_calls/caller.cc | 51 | ||||
-rw-r--r-- | lib/msan/lit_tests/wrap_indirect_calls/lit.local.cfg | 3 | ||||
-rw-r--r-- | lib/msan/lit_tests/wrap_indirect_calls/one.cc | 3 | ||||
-rw-r--r-- | lib/msan/lit_tests/wrap_indirect_calls/two.cc | 11 | ||||
-rw-r--r-- | lib/msan/lit_tests/wrap_indirect_calls/wrapper.cc | 11 |
6 files changed, 143 insertions, 0 deletions
diff --git a/lib/msan/lit_tests/wrap_indirect_calls.cc b/lib/msan/lit_tests/wrap_indirect_calls.cc new file mode 100644 index 000000000..b4bac1ecb --- /dev/null +++ b/lib/msan/lit_tests/wrap_indirect_calls.cc @@ -0,0 +1,64 @@ +// Test indirect call wrapping in MemorySanitizer. + +// RUN: %clangxx_msan -O0 %p/wrap_indirect_calls/two.cc -fPIC -shared -o %t-two-so.so +// RUN: %clangxx_msan -O0 %p/wrap_indirect_calls/wrapper.cc -fPIC -shared -o %t-wrapper-so.so + +// Disable fast path. + +// RUN: %clangxx_msan -O0 %p/wrap_indirect_calls/caller.cc %p/wrap_indirect_calls/one.cc %s \ +// RUN: %t-two-so.so %t-wrapper-so.so \ +// RUN: -mllvm -msan-wrap-indirect-calls=wrapper \ +// RUN: -mllvm -msan-wrap-indirect-calls-fast=0 \ +// RUN: -DSLOW=1 \ +// RUN: -Wl,--defsym=__executable_start=0 -o %t +// RUN: %t + +// Enable fast path, call from executable, -O0. + +// RUN: %clangxx_msan -O0 %p/wrap_indirect_calls/caller.cc %p/wrap_indirect_calls/one.cc %s \ +// RUN: %t-two-so.so %t-wrapper-so.so \ +// RUN: -mllvm -msan-wrap-indirect-calls=wrapper \ +// RUN: -mllvm -msan-wrap-indirect-calls-fast=1 \ +// RUN: -DSLOW=0 \ +// RUN: -Wl,--defsym=__executable_start=0 -o %t +// RUN: %t + +// Enable fast path, call from executable, -O3. + +// RUN: %clangxx_msan -O3 %p/wrap_indirect_calls/caller.cc %p/wrap_indirect_calls/one.cc %s \ +// RUN: %t-two-so.so %t-wrapper-so.so \ +// RUN: -mllvm -msan-wrap-indirect-calls=wrapper \ +// RUN: -mllvm -msan-wrap-indirect-calls-fast=1 \ +// RUN: -DSLOW=0 \ +// RUN: -Wl,--defsym=__executable_start=0 -o %t +// RUN: %t + +// Enable fast path, call from DSO, -O0. + +// RUN: %clangxx_msan -O0 %p/wrap_indirect_calls/caller.cc %p/wrap_indirect_calls/one.cc -shared \ +// RUN: %t-two-so.so %t-wrapper-so.so \ +// RUN: -mllvm -msan-wrap-indirect-calls=wrapper \ +// RUN: -mllvm -msan-wrap-indirect-calls-fast=1 \ +// RUN: -DSLOW=0 \ +// RUN: -Wl,--defsym=__executable_start=0 -o %t-caller-so.so +// RUN: %clangxx_msan -O0 %s %t-caller-so.so %t-two-so.so %t-wrapper-so.so -o %t +// RUN: %t + +// Enable fast path, call from DSO, -O3. + +// RUN: %clangxx_msan -O3 %p/wrap_indirect_calls/caller.cc %p/wrap_indirect_calls/one.cc -shared \ +// RUN: %t-two-so.so %t-wrapper-so.so \ +// RUN: -mllvm -msan-wrap-indirect-calls=wrapper \ +// RUN: -mllvm -msan-wrap-indirect-calls-fast=1 \ +// RUN: -DSLOW=0 \ +// RUN: -Wl,--defsym=__executable_start=0 -o %t-caller-so.so +// RUN: %clangxx_msan -O3 %s %t-caller-so.so %t-two-so.so %t-wrapper-so.so -o %t +// RUN: %t + +// The actual test is in multiple files in wrap_indirect_calls/ directory. +void run_test(); + +int main() { + run_test(); + return 0; +} diff --git a/lib/msan/lit_tests/wrap_indirect_calls/caller.cc b/lib/msan/lit_tests/wrap_indirect_calls/caller.cc new file mode 100644 index 000000000..a0af8b7bb --- /dev/null +++ b/lib/msan/lit_tests/wrap_indirect_calls/caller.cc @@ -0,0 +1,51 @@ +// Indirectly call a bunch of functions. + +#include <assert.h> + +extern int cnt; + +typedef int (*F)(int, int); + +// A function in the same object. +int f_local(int x, int y) { + return x + y; +} + +// A function in another object. +int f_other_object(int x, int y); + +// A function in another DSO. +int f_dso(int x, int y); + +// A function in another DSO that is replaced by the wrapper. +int f_replaced(int x, int y); + +void run_test(void) { + int x; + int expected_cnt = 0; + volatile F f; + + if (SLOW) ++expected_cnt; + f = &f_local; + x = f(1, 2); + assert(x == 3); + assert(cnt == expected_cnt); + + if (SLOW) ++expected_cnt; + f = &f_other_object; + x = f(2, 3); + assert(x == 6); + assert(cnt == expected_cnt); + + ++expected_cnt; + f = &f_dso; + x = f(2, 3); + assert(x == 7); + assert(cnt == expected_cnt); + + ++expected_cnt; + f = &f_replaced; + x = f(2, 3); + assert(x == 11); + assert(cnt == expected_cnt); +} diff --git a/lib/msan/lit_tests/wrap_indirect_calls/lit.local.cfg b/lib/msan/lit_tests/wrap_indirect_calls/lit.local.cfg new file mode 100644 index 000000000..5e01230c0 --- /dev/null +++ b/lib/msan/lit_tests/wrap_indirect_calls/lit.local.cfg @@ -0,0 +1,3 @@ +# Sources in this directory are used by tests in parent directory. + +config.suffixes = [] diff --git a/lib/msan/lit_tests/wrap_indirect_calls/one.cc b/lib/msan/lit_tests/wrap_indirect_calls/one.cc new file mode 100644 index 000000000..ab7bf4125 --- /dev/null +++ b/lib/msan/lit_tests/wrap_indirect_calls/one.cc @@ -0,0 +1,3 @@ +int f_other_object(int x, int y) { + return x * y; +} diff --git a/lib/msan/lit_tests/wrap_indirect_calls/two.cc b/lib/msan/lit_tests/wrap_indirect_calls/two.cc new file mode 100644 index 000000000..c939a993b --- /dev/null +++ b/lib/msan/lit_tests/wrap_indirect_calls/two.cc @@ -0,0 +1,11 @@ +int f_dso(int x, int y) { + return 2 * x + y; +} + +int f_replaced(int x, int y) { + return x + y + 5; +} + +int f_replacement(int x, int y) { + return x + y + 6; +} diff --git a/lib/msan/lit_tests/wrap_indirect_calls/wrapper.cc b/lib/msan/lit_tests/wrap_indirect_calls/wrapper.cc new file mode 100644 index 000000000..8fcd0c635 --- /dev/null +++ b/lib/msan/lit_tests/wrap_indirect_calls/wrapper.cc @@ -0,0 +1,11 @@ +int f_replaced(int x, int y); +int f_replacement(int x, int y); + +int cnt; + +extern "C" void *wrapper(void *p) { + ++cnt; + if (p == (void *)f_replaced) + return (void *)f_replacement; + return p; +} |