/home/runner/work/HiCR/HiCR/include/hicr/frontends/channel/base.hpp Source File

HiCR: /home/runner/work/HiCR/HiCR/include/hicr/frontends/channel/base.hpp Source File
HiCR
base.hpp
1/*
2 * Copyright 2025 Huawei Technologies Co., Ltd.
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
24#pragma once
25
26#include <memory>
27#include <cstring>
28#include <hicr/core/definitions.hpp>
33
37enum
38{
39 _HICR_CHANNEL_COORDINATION_BUFFER_ELEMENT_COUNT = 2
40};
41
45#define _HICR_CHANNEL_COORDINATION_BUFFER_ELEMENT_TYPE size_t
46
50enum
51{
52 _HICR_CHANNEL_HEAD_ADVANCE_COUNT_IDX = 0
53};
54
58enum
59{
60 _HICR_CHANNEL_TAIL_ADVANCE_COUNT_IDX = 1
61};
62
63namespace HiCR::channel
64{
65
69class Base
70{
71 public:
72
84 [[nodiscard]] __INLINE__ size_t getTokenSize() const noexcept { return _tokenSize; }
85
92 __INLINE__ static size_t getCoordinationBufferSize() noexcept { return _HICR_CHANNEL_COORDINATION_BUFFER_ELEMENT_COUNT * sizeof(_HICR_CHANNEL_COORDINATION_BUFFER_ELEMENT_TYPE); }
93
100 __INLINE__ static void initializeCoordinationBuffer(const std::shared_ptr<LocalMemorySlot> &coordinationBuffer)
101 {
102 // Checking for correct size
103 auto requiredSize = getCoordinationBufferSize();
104 auto size = coordinationBuffer->getSize();
105 if (size < requiredSize)
106 HICR_THROW_LOGIC("Attempting to initialize coordination buffer size on a memory slot (%lu) smaller than the required size (%lu).\n", size, requiredSize);
107
108 // Getting actual buffer of the coordination buffer
109 auto bufferPtr = coordinationBuffer->getPointer();
110
111 // Resetting all its values to zero
112 memset(bufferPtr, 0, getCoordinationBufferSize());
113 }
114
123 __INLINE__ static size_t getTokenBufferSize(const size_t tokenSize, const size_t capacity) noexcept { return tokenSize * capacity; }
124
141 [[nodiscard]] __INLINE__ size_t getDepth() const noexcept { return _circularBuffer->getDepth(); }
142
151 [[nodiscard]] __INLINE__ bool isFull() const noexcept { return _circularBuffer->isFull(); }
152
161 [[nodiscard]] __INLINE__ bool isEmpty() const noexcept { return _circularBuffer->isEmpty(); }
162
167 [[nodiscard]] __INLINE__ auto getCircularBuffer() const noexcept { return _circularBuffer.get(); }
168
169 protected:
170
188 Base(CommunicationManager &communicationManager, const std::shared_ptr<LocalMemorySlot> &coordinationBuffer, const size_t tokenSize, const size_t capacity)
189 : _communicationManager(&communicationManager),
190 _coordinationBuffer(coordinationBuffer),
191 _tokenSize(tokenSize)
192 {
193 if (tokenSize == 0) HICR_THROW_LOGIC("Attempting to create a channel with token size 0.\n");
194 if (capacity == 0) HICR_THROW_LOGIC("Attempting to create a channel with zero capacity \n");
195
196 // Checking that the provided coordination buffers have the right size
197 auto requiredCoordinationBufferSize = getCoordinationBufferSize();
198 auto providedCoordinationBufferSize = _coordinationBuffer->getSize();
199 if (providedCoordinationBufferSize < requiredCoordinationBufferSize)
200 HICR_THROW_LOGIC("Attempting to create a channel with a local coordination buffer size (%lu) smaller than the required size (%lu).\n",
201 providedCoordinationBufferSize,
202 requiredCoordinationBufferSize);
203
204 // Creating internal circular buffer
205 _circularBuffer = std::make_unique<channel::CircularBuffer>(
206 capacity,
207 &static_cast<_HICR_CHANNEL_COORDINATION_BUFFER_ELEMENT_TYPE *>(coordinationBuffer->getPointer())[_HICR_CHANNEL_HEAD_ADVANCE_COUNT_IDX],
208 &static_cast<_HICR_CHANNEL_COORDINATION_BUFFER_ELEMENT_TYPE *>(coordinationBuffer->getPointer())[_HICR_CHANNEL_TAIL_ADVANCE_COUNT_IDX]);
209 }
210
211 ~Base() = default;
212
217 [[nodiscard]] __INLINE__ CommunicationManager *getCommunicationManager() const { return _communicationManager; }
218
223 [[nodiscard]] __INLINE__ auto getCoordinationBuffer() const { return _coordinationBuffer; }
224
225 private:
226
230 CommunicationManager *const _communicationManager;
231
235 const std::shared_ptr<LocalMemorySlot> _coordinationBuffer;
239 const size_t _tokenSize;
240
244 std::unique_ptr<channel::CircularBuffer> _circularBuffer;
245};
246
247} // namespace HiCR::channel
Provides generic logic for circular buffers.
Definition communicationManager.hpp:54
Definition base.hpp:70
__INLINE__ CommunicationManager * getCommunicationManager() const
Definition base.hpp:217
__INLINE__ auto getCoordinationBuffer() const
Definition base.hpp:223
__INLINE__ size_t getDepth() const noexcept
Definition base.hpp:141
__INLINE__ size_t getTokenSize() const noexcept
Definition base.hpp:84
static __INLINE__ size_t getTokenBufferSize(const size_t tokenSize, const size_t capacity) noexcept
Definition base.hpp:123
Base(CommunicationManager &communicationManager, const std::shared_ptr< LocalMemorySlot > &coordinationBuffer, const size_t tokenSize, const size_t capacity)
Definition base.hpp:188
__INLINE__ bool isFull() const noexcept
Definition base.hpp:151
__INLINE__ bool isEmpty() const noexcept
Definition base.hpp:161
static __INLINE__ void initializeCoordinationBuffer(const std::shared_ptr< LocalMemorySlot > &coordinationBuffer)
Definition base.hpp:100
static __INLINE__ size_t getCoordinationBufferSize() noexcept
Definition base.hpp:92
__INLINE__ auto getCircularBuffer() const noexcept
Definition base.hpp:167
Provides a definition for the base backend's communication manager class.
Provides a definition for a HiCR Global Memory Slot class.
Provides a failure model and corresponding exception classes.
#define HICR_THROW_LOGIC(...)
Definition exceptions.hpp:67