static_counter.hpp Source File

static_counter.hpp Source File#

Composable Kernel: static_counter.hpp Source File
static_counter.hpp
Go to the documentation of this file.
1// SPDX-License-Identifier: MIT
2// Copyright (c) 2018-2024, Advanced Micro Devices, Inc. All rights reserved.
3
4#pragma once
5
7
8namespace ck_tile {
9
10template <typename Context, index_t Start = 0, index_t Step = 1>
12{
13 public:
14 template <typename Unique>
15 static constexpr index_t next()
16 {
17 return next<Unique>(0) * Step + Start;
18 }
19
20 template <unsigned long long>
21 static constexpr index_t next()
22 {
23 struct Unique
24 {
25 };
26 return next<Unique>(0) * Step + Start;
27 }
28
29 template <typename Unique>
30 static constexpr index_t current()
31 {
32 return current<Unique>(0) * Step + Start;
33 }
34
35 template <unsigned long long>
36 static constexpr index_t current()
37 {
38 struct Unique
39 {
40 };
41 return current<Unique>(0) * Step + Start;
42 }
43
44 private:
45 template <index_t I>
46 struct slot
47 {
48 _Pragma("GCC diagnostic push");
49 _Pragma("GCC diagnostic ignored \"-Wundefined-internal\"");
50 friend constexpr bool slot_allocated(slot<I>);
51 _Pragma("GCC diagnostic pop");
52 };
53
54 template <index_t I>
55 struct allocate_slot
56 {
57 friend constexpr bool slot_allocated(slot<I>) { return true; }
58 enum
59 {
60 value = I
61 };
62 };
63
64 // If slot_allocated(slot<I>) has NOT been defined, then SFINAE will keep this function out of
65 // the overload set...
66 template <typename Unique, index_t I = 0, bool = slot_allocated(slot<I>())>
67 static constexpr index_t next(index_t)
68 {
69 return next<Unique, I + 1>(0);
70 }
71
72 // ...And this function will be used, instead, which will define slot_allocated(slot<I>) via
73 // allocate_slot<I>.
74 template <typename Unique, index_t I = 0>
75 static constexpr index_t next(double)
76 {
77 return allocate_slot<I>::value;
78 }
79
80 // If slot_allocated(slot<I>) has NOT been defined, then SFINAE will keep this function out of
81 // the overload set...
82 template <typename Unique, index_t I = Start, bool = slot_allocated(slot<I>())>
83 static constexpr index_t current(index_t)
84 {
85 return current<Unique, I + 1>(0);
86 }
87
88 // ...And this function will be used, instead, which will return the current counter, or assert
89 // in case next() hasn't been called yet.
90 template <typename Unique, index_t I = Start>
91 static constexpr index_t current(double)
92 {
93 static_assert(I != 0, "You must invoke next() first");
94
95 return I - 1;
96 }
97};
98
99namespace impl {
100template <int I>
102}
103
104#define MAKE_SC() \
105 __extension__ ck_tile::static_counter<ck_tile::impl::static_counter_uniq_<__COUNTER__>> {}
106#define MAKE_SC_WITH(start_, step_) \
107 __extension__ ck_tile:: \
108 static_counter<ck_tile::impl::static_counter_uniq_<__COUNTER__>, start_, step_> \
109 { \
110 }
111#define NEXT_SC(c_) __extension__ c_.next<__COUNTER__>()
112#define NEXT_SCI(c_, static_i_) __extension__ c_.next<__COUNTER__ + static_i_>()
113
114// Usage:
115// constexpr auto c = MAKE_SC()
116// NEXT_SC(c) // -> constexpr 0
117// NEXT_SC(c) // -> constexpr 1
118// NEXT_SC(c) // -> constexpr 2
119} // namespace ck_tile
Definition tile/core/arch/amd_buffer_addressing.hpp:110
Definition tile/core/algorithm/cluster_descriptor.hpp:13
int32_t index_t
Definition integer.hpp:9
Definition static_counter.hpp:101
Definition static_counter.hpp:12
static constexpr index_t current()
Definition static_counter.hpp:30
static constexpr index_t next()
Definition static_counter.hpp:15