Skip to content

[SYCL][ESIMD] Add basic headers for ESIMD runtime library. #1853

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 19 additions & 0 deletions sycl/include/CL/sycl/intel/esimd.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
//==------------ esimd.hpp - DPC++ Explicit SIMD API -----------------------==//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//
// The main header of the Explicit SIMD API.
//===----------------------------------------------------------------------===//

#pragma once

#ifdef __SYCL_DEVICE_ONLY__
#define SYCL_ESIMD_KERNEL __attribute__((sycl_explicit_simd))
#define SYCL_ESIMD_FUNCTION __attribute__((sycl_explicit_simd))
#else
#define SYCL_ESIMD_KERNEL
#define SYCL_ESIMD_FUNCTION
#endif
119 changes: 119 additions & 0 deletions sycl/include/CL/sycl/intel/esimd/detail/esimd_region.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,119 @@
//==-------------- esimd_region.hpp - DPC++ Explicit SIMD API --------------==//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//
// Region type to implement the Explicit SIMD APIs.
//===----------------------------------------------------------------------===//

#pragma once

#include <CL/sycl/detail/defines.hpp>
#include <cstdint>
#include <type_traits>
#include <utility>

__SYCL_INLINE_NAMESPACE(cl) {
namespace sycl {
namespace intel {
namespace gpu {

// The common base type of region types.
template <bool Is2D, typename T, int SizeY, int StrideY, int SizeX, int StrideX>
struct region_base {
using element_type = T;
static constexpr int length = SizeX * SizeY;
static constexpr int Is_2D = Is2D;
static constexpr int Size_x = SizeX;
static constexpr int Stride_x = StrideX;
static constexpr int Size_y = SizeY;
static constexpr int Stride_y = StrideY;
static constexpr int Size_in_bytes = sizeof(T) * length;

static_assert(Size_x > 0 && Stride_x >= 0, "illegal region in x-dimension");
static_assert(Size_y > 0 && Stride_y >= 0, "illegal region in y-dimension");

uint16_t M_offset_y;
uint16_t M_offset_x;

explicit region_base() : M_offset_y(0), M_offset_x(0) {}

explicit region_base(uint16_t OffsetX) : M_offset_y(0), M_offset_x(OffsetX) {}

explicit region_base(uint16_t OffsetY, uint16_t OffsetX)
: M_offset_y(OffsetY), M_offset_x(OffsetX) {}
};

// A basic 1D region type.
template <typename T, int Size, int Stride>
using region1d_t = region_base<false, T, 1, 0, Size, Stride>;

// A basic 2D region type.
template <typename T, int SizeY, int StrideY, int SizeX, int StrideX>
using region2d_t = region_base<true, T, SizeY, StrideY, SizeX, StrideX>;

// simd_view forward declaration.
template <typename BaseTy, typename RegionTy> class simd_view;

// Compute the region type of a simd_view type.
//
// A region type could be either
// - region1d_t
// - region2d_t
// - a pair (top_region_type, base_region_type)
//
// This is a recursive definition to capture the following rvalue region stack:
//
// simd<int 16> v;
// v.format<int, 4, 4>().select<1, 0, 4, 1>(0, 0).format<short>() = 0;
//
// The LHS will be represented as a rvalue
//
// simd_view({v, { region1d_t<short, 8, 1>(0, 0),
// { region2d_t<int, 1, 1, 4, 1>(0, 0),
// region2d_t<int, 4, 1, 4, 1>(0, 0)
// }}})
//
template <typename Ty> struct shape_type {
using element_type = Ty;
using type = void;
};

template <typename Ty, int Size, int Stride>
struct shape_type<region1d_t<Ty, Size, Stride>> {
using element_type = Ty;
using type = region1d_t<Ty, Size, Stride>;
};

template <typename Ty, int SizeY, int StrideY, int SizeX, int StrideX>
struct shape_type<region2d_t<Ty, SizeY, StrideY, SizeX, StrideX>> {
using element_type = Ty;
using type = region2d_t<Ty, SizeY, StrideY, SizeX, StrideX>;
};

// Forward the shape computation on the top region type.
template <typename TopRegionTy, typename BaseRegionTy>
struct shape_type<std::pair<TopRegionTy, BaseRegionTy>>
: public shape_type<TopRegionTy> {};

// Forward the shape computation on the region type.
template <typename BaseTy, typename RegionTy>
struct shape_type<simd_view<BaseTy, RegionTy>> : public shape_type<RegionTy> {};

// Utility functions to access region components.
template <typename T> T getTopRegion(T Reg) { return Reg; }
template <typename T, typename U> T getTopRegion(std::pair<T, U> Reg) {
return Reg.first;
}

template <typename T> T getBaseRegion(T Reg) { return Reg; }
template <typename T, typename U> T getBaseRegion(std::pair<T, U> Reg) {
return Reg.second;
}

} // namespace gpu
} // namespace intel
} // namespace sycl
} // __SYCL_INLINE_NAMESPACE(cl)
Loading