brintos

brintos / llvm-project-archived public Read only

0
0
Text · 6.0 KiB · e782438 Raw
247 lines · cpp
1//===----------------------------------------------------------------------===//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-exception6//7//===----------------------------------------------------------------------===//8 9// Test libc++'s implementation of align_val_t, and the relevant new/delete10// overloads in all dialects when -faligned-allocation is present.11 12// Libc++ when built for z/OS doesn't contain the aligned allocation functions,13// nor does the dynamic library shipped with z/OS.14// XFAIL: target={{.+}}-zos{{.*}}15 16// XFAIL: sanitizer-new-delete && !hwasan17 18// TODO: Investigate this failure19// UNSUPPORTED: ubsan20 21// GCC doesn't support the aligned-allocation flags.22// XFAIL: gcc23 24// RUN: %{build} -faligned-allocation -fsized-deallocation25// RUN: %{run}26// RUN: %{build} -faligned-allocation -fno-sized-deallocation -DNO_SIZE27// RUN: %{run}28// RUN: %{build} -fno-aligned-allocation -fsized-deallocation -DNO_ALIGN29// RUN: %{run}30// RUN: %{build} -fno-aligned-allocation -fno-sized-deallocation -DNO_ALIGN -DNO_SIZE31// RUN: %{run}32 33#include <cassert>34#include <cstdlib>35#include <new>36 37#include "test_macros.h"38 39TEST_DIAGNOSTIC_PUSH40TEST_CLANG_DIAGNOSTIC_IGNORED("-Wprivate-header")41#include <__cxx03/__memory/aligned_alloc.h>42TEST_DIAGNOSTIC_POP43 44struct alloc_stats {45  alloc_stats() { reset(); }46 47  int aligned_sized_called;48  int aligned_called;49  int sized_called;50  int plain_called;51  int last_size;52  int last_align;53 54  void reset() {55    aligned_sized_called = aligned_called = sized_called = plain_called = 0;56    last_align = last_size = -1;57  }58 59  bool expect_plain() const {60    assert(aligned_sized_called == 0);61    assert(aligned_called == 0);62    assert(sized_called == 0);63    assert(last_size == -1);64    assert(last_align == -1);65    return plain_called == 1;66  }67 68  bool expect_size(int n) const {69    assert(plain_called == 0);70    assert(aligned_sized_called == 0);71    assert(aligned_called == 0);72    assert(last_size == n);73    assert(last_align == -1);74    return sized_called == 1;75  }76 77  bool expect_align(int a) const {78    assert(plain_called == 0);79    assert(aligned_sized_called == 0);80    assert(sized_called == 0);81    assert(last_size == -1);82    assert(last_align == a);83    return aligned_called == 1;84  }85 86  bool expect_size_align(int n, int a) const {87    assert(plain_called == 0);88    assert(sized_called == 0);89    assert(aligned_called == 0);90    assert(last_size == n);91    assert(last_align == a);92    return aligned_sized_called == 1;93  }94};95alloc_stats stats;96 97void operator delete(void* p) TEST_NOEXCEPT {98  ::free(p);99  stats.plain_called++;100  stats.last_size = stats.last_align = -1;101}102 103#ifndef NO_SIZE104void operator delete(void* p, std::size_t n) TEST_NOEXCEPT {105  ::free(p);106  stats.sized_called++;107  stats.last_size  = n;108  stats.last_align = -1;109}110#endif111 112#ifndef NO_ALIGN113void operator delete(void* p, std::align_val_t a) TEST_NOEXCEPT {114  std::__libcpp_aligned_free(p);115  stats.aligned_called++;116  stats.last_align = static_cast<int>(a);117  stats.last_size  = -1;118}119 120void operator delete(void* p, std::size_t n, std::align_val_t a) TEST_NOEXCEPT {121  std::__libcpp_aligned_free(p);122  stats.aligned_sized_called++;123  stats.last_align = static_cast<int>(a);124  stats.last_size  = n;125}126#endif127 128void test_libcpp_dealloc() {129  void* p = nullptr;130#ifdef __STDCPP_DEFAULT_NEW_ALIGNMENT__131  std::size_t over_align_val = __STDCPP_DEFAULT_NEW_ALIGNMENT__ * 2;132#else133  std::size_t over_align_val = TEST_ALIGNOF(std::max_align_t) * 2;134#endif135  std::size_t under_align_val = TEST_ALIGNOF(int);136  std::size_t with_size_val   = 2;137 138  {139    std::__libcpp_deallocate_unsized(p, under_align_val);140    assert(stats.expect_plain());141  }142  stats.reset();143 144#if defined(NO_SIZE) && defined(NO_ALIGN)145  {146    std::__libcpp_deallocate(p, with_size_val, over_align_val);147    assert(stats.expect_plain());148  }149  stats.reset();150#elif defined(NO_SIZE)151  {152    std::__libcpp_deallocate(p, with_size_val, over_align_val);153    assert(stats.expect_align(over_align_val));154  }155  stats.reset();156#elif defined(NO_ALIGN)157  {158    std::__libcpp_deallocate(p, with_size_val, over_align_val);159    assert(stats.expect_size(with_size_val));160  }161  stats.reset();162#else163  {164    std::__libcpp_deallocate(p, with_size_val, over_align_val);165    assert(stats.expect_size_align(with_size_val, over_align_val));166  }167  stats.reset();168  {169    std::__libcpp_deallocate_unsized(p, over_align_val);170    assert(stats.expect_align(over_align_val));171  }172  stats.reset();173  {174    std::__libcpp_deallocate(p, with_size_val, under_align_val);175    assert(stats.expect_size(with_size_val));176  }177  stats.reset();178#endif179}180 181struct TEST_ALIGNAS(128) AlignedType {182  AlignedType() : elem(0) {}183  TEST_ALIGNAS(128) char elem;184};185 186void test_allocator_and_new_match() {187  stats.reset();188#if defined(NO_SIZE) && defined(NO_ALIGN)189  {190    int* x = DoNotOptimize(new int(42));191    delete x;192    assert(stats.expect_plain());193  }194  stats.reset();195  {196    AlignedType* a = DoNotOptimize(new AlignedType());197    delete a;198    assert(stats.expect_plain());199  }200  stats.reset();201#elif defined(NO_SIZE)202  stats.reset();203  stats.reset();204  {205    AlignedType* a = DoNotOptimize(new AlignedType());206    delete a;207    assert(stats.expect_align(TEST_ALIGNOF(AlignedType)));208  }209  stats.reset();210#elif defined(NO_ALIGN)211  stats.reset();212  {213    int* x = DoNotOptimize(new int(42));214    delete x;215    assert(stats.expect_size(sizeof(int)));216  }217  stats.reset();218  {219    AlignedType* a = DoNotOptimize(new AlignedType());220    delete a;221    assert(stats.expect_size(sizeof(AlignedType)));222  }223  stats.reset();224#else225  stats.reset();226  {227    int* x = DoNotOptimize(new int(42));228    delete x;229    assert(stats.expect_size(sizeof(int)));230  }231  stats.reset();232  {233    AlignedType* a = DoNotOptimize(new AlignedType());234    delete a;235    assert(stats.expect_size_align(sizeof(AlignedType), TEST_ALIGNOF(AlignedType)));236  }237  stats.reset();238#endif239}240 241int main(int, char**) {242  test_libcpp_dealloc();243  test_allocator_and_new_match();244 245  return 0;246}247