Project
Loading...
Searching...
No Matches
utils.h
Go to the documentation of this file.
1// Copyright 2019-2023 CERN and copyright holders of ALICE O2.
2// See https://alice-o2.web.cern.ch/copyright for details of the copyright holders.
3// All rights not expressly granted are reserved.
4//
5// This software is distributed under the terms of the GNU General Public
6// License v3 (GPL Version 3), copied verbatim in the file "COPYING".
7//
8// In applying this license CERN does not waive the privileges and immunities
9// granted to it by virtue of its status as an Intergovernmental Organization
10// or submit itself to any jurisdiction.
11
15
16#ifndef RANS_INTERNAL_PACK_UTILS_H_
17#define RANS_INTERNAL_PACK_UTILS_H_
18
19#include <cstdint>
20#include <cstring>
21#include <array>
22#include <type_traits>
23
24#ifdef __BMI__
25#include <immintrin.h>
26#endif
27
29
30namespace o2::rans::internal
31{
32
33using packing_type = uint64_t;
34
35inline constexpr std::array<packing_type, (utils::toBits<packing_type>() + 1)> All1BackTill = []() constexpr
36{
37 constexpr size_t packingBufferBits = utils::toBits<packing_type>();
38 std::array<packing_type, (packingBufferBits + 1)> ret{};
39 for (size_t i = 0; i < packingBufferBits; ++i) {
40 ret[i] = (1ull << i) - 1;
41 }
42 ret[packingBufferBits] = ~0;
43 return ret;
44}
45();
46
47inline constexpr std::array<packing_type, (utils::toBits<packing_type>() + 1)> All1FrontTill = []() constexpr
48{
49 constexpr size_t size = utils::toBits<packing_type>() + 1;
50 std::array<packing_type, size> ret{};
51 for (size_t i = 0; i < size; ++i) {
52 ret[i] = ~0ull ^ All1BackTill[i];
53 }
54 return ret;
55}
56();
57
58[[nodiscard]] inline uint64_t bitExtract(uint64_t data, uint32_t start, uint32_t length) noexcept
59{
60#ifdef __BMI__
61 return _bextr_u64(data, start, length);
62#else
63 const uint64_t mask = All1BackTill[start + length] ^ All1BackTill[start];
64 return (data & mask) >> start;
65#endif
66};
67
68template <typename source_T, size_t width_V>
69inline constexpr packing_type packMultiple(const source_T* __restrict data, source_T offset)
70{
72
73 constexpr size_t PackingWidth = width_V;
74 constexpr size_t NIterations = utils::toBits<packing_type>() / PackingWidth;
75
76 for (size_t i = 0; i < NIterations; ++i) {
77 const int64_t adjustedValue = static_cast<int64_t>(data[i]) - offset;
78 result |= static_cast<packing_type>(adjustedValue) << (PackingWidth * i);
79 }
80
81 return result;
82};
83
84} // namespace o2::rans::internal
85
86#endif /* RANS_INTERNAL_PACK_UTILS_H_ */
int32_t i
common helper classes and functions
GLuint64EXT * result
Definition glcorearb.h:5662
GLsizeiptr size
Definition glcorearb.h:659
GLboolean * data
Definition glcorearb.h:298
GLintptr offset
Definition glcorearb.h:660
GLuint GLsizei GLsizei * length
Definition glcorearb.h:790
GLuint start
Definition glcorearb.h:469
GLint GLuint mask
Definition glcorearb.h:291
constexpr std::array< packing_type,(utils::toBits< packing_type >()+1)> All1BackTill
Definition utils.h:35
uint64_t packing_type
Definition utils.h:33
constexpr std::array< packing_type,(utils::toBits< packing_type >()+1)> All1FrontTill
Definition utils.h:47
uint64_t bitExtract(uint64_t data, uint32_t start, uint32_t length) noexcept
Definition utils.h:58
constexpr packing_type packMultiple(const source_T *__restrict data, source_T offset)
Definition utils.h:69
class DenseHistogram< source_T, std::enable_if_t< sizeof(source_T)<=2 > > :public internal::VectorContainer< source_T, uint32_t >, internal::HistogramConcept< source_T, typename internal::VectorContainer< source_T, uint32_t >::value_type, typename internal::VectorContainer< source_T, uint32_t >::difference_type, DenseHistogram< source_T > >{ using containerBase_type=internal::VectorContainer< source_T, uint32_t >;using HistogramConcept_type=internal::HistogramConcept< source_T, typename internal::VectorContainer< source_T, uint32_t >::value_type, typename internal::VectorContainer< source_T, uint32_t >::difference_type, DenseHistogram< source_T > >;friend containerBase_type;friend HistogramConcept_type;public:using source_type=source_T;using value_type=typename containerBase_type::value_type;using container_type=typename containerBase_type::container_type;using size_type=typename containerBase_type::size_type;using difference_type=typename containerBase_type::difference_type;using reference=typename containerBase_type::reference;using const_reference=typename containerBase_type::const_reference;using pointer=typename containerBase_type::pointer;using const_pointer=typename containerBase_type::const_pointer;using const_iterator=typename containerBase_type::const_iterator;DenseHistogram() :containerBase_type{MaxSize, std::numeric_limits< source_type >::min()} {};template< typename freq_IT > DenseHistogram(freq_IT begin, freq_IT end, difference_type offset) :containerBase_type{MaxSize, std::numeric_limits< source_type >::min()}, HistogramConcept_type{begin, end, offset} {};using HistogramConcept_type::addSamples;template< typename source_IT > inline DenseHistogram &addSamples(source_IT begin, source_IT end, source_type min, source_type max) { return addSamplesImpl(begin, end);};template< typename source_IT > DenseHistogram &addSamples(gsl::span< const source_type > span, source_type min, source_type max) { return addSamplesImpl(span);};using HistogramConcept_type::addFrequencies;protected:template< typename source_IT > DenseHistogram &addSamplesImpl(source_IT begin, source_IT end);DenseHistogram &addSamplesImpl(gsl::span< const source_type > samples);template< typename freq_IT > DenseHistogram &addFrequenciesImpl(freq_IT begin, freq_IT end, difference_type offset);private:inline static constexpr size_t MaxSize=utils::pow2(utils::toBits< source_type >());};template< typename source_T >template< typename source_IT >auto DenseHistogram< source_T, std::enable_if_t< sizeof(source_T)<=2 > >::addSamplesImpl(source_IT begin, source_IT end) -> DenseHistogram &{ if constexpr(std::is_pointer_v< source_IT >) { return addSamplesImpl({begin, end});} else { std::for_each(begin, end,[this](const source_type &symbol) {++this->mNSamples;++this->mContainer[symbol];});} return *this;}template< typename source_T >auto DenseHistogram< source_T, std::enable_if_t< sizeof(source_T)<=2 > >::addSamplesImpl(gsl::span< const source_type > samples) -> DenseHistogram &{ using namespace internal;using namespace utils;if(samples.empty()) { return *this;} const auto begin=samples.data();const auto end=begin+samples.size();constexpr size_t ElemsPerQWord=sizeof(uint64_t)/sizeof(source_type);constexpr size_t nUnroll=2 *ElemsPerQWord;auto iter=begin;if constexpr(sizeof(source_type)==1) { std::array< ShiftableVector< source_type, value_type >, 3 > histograms{ {{this-> mContainer size()