brintos

brintos / llvm-project-archived public Read only

0
0
Text · 2.5 KiB · 35032f9 Raw
96 lines · cpp
1// ParamTLS has limited size. Everything that does not fit is considered fully2// initialized.3 4// RUN: %clangxx_msan -fno-sanitize-memory-param-retval -O0 %s -o %t && %run %t5// RUN: %clangxx_msan -fno-sanitize-memory-param-retval -fsanitize-memory-track-origins -O0 %s -o %t && %run %t6// RUN: %clangxx_msan -fno-sanitize-memory-param-retval -fsanitize-memory-track-origins=2 -O0 %s -o %t && %run %t7//8// AArch64 and LoongArch64 fail with:9// void f801(S<801>): Assertion `__msan_test_shadow(&s, sizeof(s)) == -1' failed10// XFAIL: target={{(aarch64|loongarch64).*}}11// When passing huge structs by value, SystemZ uses pointers, therefore this12// test in its present form is unfortunately not applicable.13// ABI says: "A struct or union of any other size <snip>. Replace such an14// argument by a pointer to the object, or to a copy where necessary to enforce15// call-by-value semantics."16// XFAIL: target=s390x{{.*}}17 18#include <sanitizer/msan_interface.h>19#include <assert.h>20 21// This test assumes that ParamTLS size is 800 bytes.22 23// This test passes poisoned values through function argument list.24// In case of overflow, argument is unpoisoned.25#define OVERFLOW(x) assert(__msan_test_shadow(&x, sizeof(x)) == -1)26// In case of no overflow, it is still poisoned.27#define NO_OVERFLOW(x) assert(__msan_test_shadow(&x, sizeof(x)) == 0)28 29#if defined(__x86_64__)30// In x86_64, if argument is partially outside tls, it is considered completely31// unpoisoned32#define PARTIAL_OVERFLOW(x) OVERFLOW(x)33#else34// In other archs, bigger arguments are splitted in multiple IR arguments, so35// they are considered poisoned till tls limit. Checking last byte of such arg:36#define PARTIAL_OVERFLOW(x) assert(__msan_test_shadow((char *)(&(x) + 1) - 1, 1) == -1)37#endif38 39 40template<int N>41struct S {42  char x[N];43};44 45void f100(S<100> s) {46  NO_OVERFLOW(s);47}48 49void f800(S<800> s) {50  NO_OVERFLOW(s);51}52 53void f801(S<801> s) {54  PARTIAL_OVERFLOW(s);55}56 57void f1000(S<1000> s) {58  PARTIAL_OVERFLOW(s);59}60 61void f_many(int a, double b, S<800> s, int c, double d) {62  NO_OVERFLOW(a);63  NO_OVERFLOW(b);64  PARTIAL_OVERFLOW(s);65  OVERFLOW(c);66  OVERFLOW(d);67}68 69// -8 bytes for "int a", aligned by 870// -2 to make "int c" a partial fit71void f_many2(int a, S<800 - 8 - 2> s, int c, double d) {72  NO_OVERFLOW(a);73  NO_OVERFLOW(s);74  PARTIAL_OVERFLOW(c);75  OVERFLOW(d);76}77 78int main(void) {79  S<100> s100;80  S<800> s800;81  S<801> s801;82  S<1000> s1000;83  f100(s100);84  f800(s800);85  f801(s801);86  f1000(s1000);87 88  int i;89  double d;90  f_many(i, d, s800, i, d);91 92  S<800 - 8 - 2> s788;93  f_many2(i, s788, i, d);94  return 0;95}96