Skip to content
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
Original file line number Diff line number Diff line change
Expand Up @@ -7,18 +7,14 @@
* @file cudnn.h
* @brief Stub C-API header for the hipDNN cuDNN-compatibility shim (v9-only).
*
* This is a hand-curated, **v9-only** replacement for NVIDIA's `<cudnn.h>`
* (RFC 0012 §4.7). It declares only the small set of C-API types that the
* cuDNN frontend v9 graph API refers to in its own method signatures, plus the
* handful of C entry points needed for handle init, stream binding, error
* handling, and version checks (and to build the mirrored samples, §8.3).
*
* Everything here forwards to an existing hipDNN equivalent; the full cuDNN C
* library (convolution-descriptor APIs, etc.) is intentionally out of scope.
* Hand-curated, v9-only replacement for NVIDIA's `<cudnn.h>`: declares the few
* C-API types the cuDNN frontend v9 graph API names in its signatures, plus the
* C entry points for handle init, stream binding, error handling, and version
* checks. Everything forwards to an existing hipDNN equivalent.
*
* @note Forwarding goes through `hipdnn_frontend::detail::hipdnnBackend()` — the
* same mockable indirection `hipdnn_frontend/Handle.hpp` uses — so these
* entry points are unit-testable with the in-tree mock backend.
* same mockable indirection `Handle.hpp` uses — so these entry points are
* unit-testable with the in-tree mock backend.
*/

#pragma once
Expand All @@ -35,39 +31,29 @@
#include <hipdnn_frontend/detail/BackendWrapper.hpp>

// ===========================================================================
// C-API types (RFC 0012 §4.7)
// C-API types
// ===========================================================================

/// @brief cuDNN handle, aliased directly to the hipDNN handle type.
///
/// `hipdnnHandle_t` is the global C typedef from `<hipdnn_backend.h>`
/// (`typedef struct hipdnnHandle* hipdnnHandle_t;`), not a member of namespace
/// `hipdnn_frontend`.
/// `hipdnnHandle_t` is the global C typedef from `<hipdnn_backend.h>`, not a
/// member of namespace `hipdnn_frontend`.
using cudnnHandle_t = ::hipdnnHandle_t;

static_assert(std::is_same_v<cudnnHandle_t, ::hipdnnHandle_t>,
"cudnnHandle_t must alias the hipDNN handle type (RFC 0012 §4.7)");

// `cudnnStatus_t` is declared in `cudnn_status.h` (included above) so the
// status enum is available without the C entry points — this lets
// `detail/status_translation.h` be self-contained.

// NOTE: This stub intentionally declares only the C-API types the *implemented*
// entry points use — `cudnnHandle_t` and `cudnnStatus_t`. The remaining v9
// C-API enums named in RFC 0012 §4.7 (`cudnnDataType_t`, `cudnnTensorFormat_t`,
// `cudnnConvolutionMode_t`, `cudnnReduceTensorOp_t`, `cudnnNormFwdPhase_t`,
// `cudnnBackendHeurMode_t`, `cudnnBackendNumericalNote_t`,
// `cudnnBackendBehaviorNote_t`, `cudnnBackendDescriptorType_t`) land with the
// type-mapping work, where their values/aliasing are verified against upstream
// rather than stubbed here.

// Status translation between the cuDNN and hipDNN enum families. Included after
// the C-API types above (it needs cudnnStatus_t) and before the entry points
// below (which use it). Lives under detail/ and is shim-internal.
"cudnnHandle_t must alias the hipDNN handle type");

// Only the C-API types the v9 graph API actually references are declared here
// (cudnnHandle_t, plus cudnnStatus_t from cudnn_status.h). Other cuDNN C-API
// enums are intentionally omitted: the v9 graph surface uses the FE-namespace
// enums (DataType_t, …) aliased in cudnn_frontend_utils.h, not the C-API ones.

// Status translation. Included after cudnnStatus_t above and before the entry
// points below, which use it.
#include <hipdnn_compatibility/cudnn/detail/status_translation.h>

// ===========================================================================
// C entry points (RFC 0012 §4.7) — forward to the hipDNN backend
// C entry points — forward to the hipDNN backend
// ===========================================================================

extern "C" {
Expand Down Expand Up @@ -118,10 +104,8 @@ inline size_t cudnnGetVersion(void)
// ===========================================================================
// create_cudnn_handle() convenience helper
// ===========================================================================
// Mirrors the helper NVIDIA ships in its sample utilities
// (samples/cpp/utils/helpers.h), so mirrored sample code that calls
// `create_cudnn_handle()` works unchanged (RFC 0012 §4.7, §8.3). Unlike the
// upstream helper, this version does not depend on a test framework.
// Mirrors the helper in NVIDIA's sample utilities so mirrored sample code
// compiles unchanged, minus the upstream test-framework dependency.

/// @brief RAII deleter that destroys a heap-allocated cuDNN handle.
struct CudnnHandleDeleter
Expand All @@ -130,8 +114,8 @@ struct CudnnHandleDeleter
{
if(handle != nullptr)
{
// A failed destroy at teardown is not recoverable, so we log and
// ignore it (the heap allocation is still freed below).
// A failed destroy at teardown is not recoverable; log and ignore
// (the heap allocation is still freed below).
const cudnnStatus_t status = cudnnDestroy(*handle);
if(status != CUDNN_STATUS_SUCCESS)
{
Expand All @@ -145,11 +129,8 @@ struct CudnnHandleDeleter

/// @brief Create a managed cuDNN handle (mirrors NVIDIA's sample helper).
///
/// The snake_case name intentionally mirrors NVIDIA's helper so mirrored sample
/// code compiles unchanged; the naming check is suppressed accordingly.
///
/// On a backend create failure the error is logged and an empty pointer is
/// returned, so callers can detect the failure via a null result.
/// snake_case name mirrors NVIDIA's so sample code compiles unchanged. On a
/// backend create failure, logs and returns an empty (null) pointer.
inline std::unique_ptr<cudnnHandle_t, CudnnHandleDeleter>
create_cudnn_handle() // NOLINT(readability-identifier-naming)
{
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,33 +5,23 @@
* @file cudnn_frontend.h
* @brief Umbrella header for the hipDNN cuDNN-compatibility shim (v9-only).
*
* This is the entry point for the cuDNN frontend compatibility shim described in
* RFC 0012 ("cuDNN shim for hipDNN"). It mirrors the filename of NVIDIA's
* upstream `cudnn_frontend.h` so that consumer source can be hipified by
* swapping the include path and (optionally) aliasing the namespace:
* Entry point for the shim. Mirrors the filename of NVIDIA's `cudnn_frontend.h`
* so consumer source can be ported by swapping the include and aliasing the
* namespace:
*
* @code{.cpp}
* // Textual hipification (RFC §4.2 workflow 1):
* #include <hipdnn_compatibility/cudnn/cudnn_frontend.h>
* namespace cudnn_frontend = hipdnn_frontend::compatibility::cudnn_frontend;
* @endcode
*
* @note Scope: this shim targets the cuDNN frontend **v9 graph API only**
* (RFC §1, §4.7). It does not reconstruct the v0.x / v8 builder surface.
*
* @note This header must remain includable standalone with no extra `#define`s
* or CMake variables (RFC §4.2). It is installed by the `Development`
* CMake component and is gated, build-side, behind the
* `HIPDNN_ENABLE_CUDNN_COMPATIBILITY` option.
*
* @par Status
* The stub C-API layer — `cudnn.h` (v9-required C-API types,
* handle/stream/error/version entry points, `create_cudnn_handle()`) and the
* version macros — is wired in below. The type/status round-trip mapping, error
* aliasing, and the graph/attribute wrappers land in subsequent tickets.
* Scope: the cuDNN frontend v9 graph API only; the v0.x / v8 builder surface is
* not reconstructed. Must remain includable standalone with no extra defines.
*/

#pragma once

#include <hipdnn_compatibility/cudnn/cudnn.h>
#include <hipdnn_compatibility/cudnn/cudnn_frontend/graph_helpers.h>
#include <hipdnn_compatibility/cudnn/cudnn_frontend/graph_properties.h>
#include <hipdnn_compatibility/cudnn/cudnn_frontend_utils.h>
#include <hipdnn_compatibility/cudnn/cudnn_frontend_version.h>
Original file line number Diff line number Diff line change
@@ -0,0 +1,92 @@
// Copyright © Advanced Micro Devices, Inc., or its affiliates.
// SPDX-License-Identifier: MIT
//
// Portions derived from NVIDIA cuDNN frontend (include/cudnn_frontend/graph_helpers.h
// and include/cudnn_frontend_Logging.h), used under the MIT license.

/**
* @file graph_helpers.h
* @brief Error-type aliases and error/log macros for the hipDNN cuDNN shim.
*
* Contains aliases for cuDNN-compatible types from hipDNN, and
* re-exports the cuDNN frontend error/log macros.
*
* @note Internal-to-shim; pulled in by the umbrella `cudnn_frontend.h`.
*/

#pragma once

#include <hipdnn_frontend/Error.hpp>
#include <hipdnn_frontend/Logging.hpp>

namespace hipdnn_frontend::compatibility::cudnn_frontend
{

using hipdnn_frontend::error_code_t;
using hipdnn_frontend::error_object;
using hipdnn_frontend::error_t;

} // namespace hipdnn_frontend::compatibility::cudnn_frontend

// The log macros forward their `<<`-streamed argument straight into hipDNN's
// frontend INFO logger. HIPDNN_FE_LOG_INFO gates on HIPDNN_LOG_LEVEL (off by
// default) and accepts a stream expression, so chained `<<` arguments work.
#ifndef CUDNN_FE_LOG
#define CUDNN_FE_LOG(X) HIPDNN_FE_LOG_INFO(X)
#endif

// The X argument is a stream expression: it must stay un-parenthesized so it
// chains off the leftmost LogStream operand (parenthesizing it would force a
// `const char* << ...` evaluation and break compilation). Same NOLINT pattern
// the SDK uses for its own streaming log macros.
#ifndef CUDNN_FE_LOG_LABEL
#define CUDNN_FE_LOG_LABEL(X) \
HIPDNN_FE_LOG_INFO("[cudnn_frontend] " << X) // NOLINT(bugprone-macro-parentheses)
#endif

#ifndef CUDNN_FE_LOG_LABEL_ENDL
#define CUDNN_FE_LOG_LABEL_ENDL(X) \
HIPDNN_FE_LOG_INFO("[cudnn_frontend] " << X) // NOLINT(bugprone-macro-parentheses)
#endif

#ifndef CUDNN_FE_LOG_BANNER
#define CUDNN_FE_LOG_BANNER(X) \
HIPDNN_FE_LOG_INFO("[cudnn_frontend] === " << X << " ===") // NOLINT(bugprone-macro-parentheses)
#endif

/// @brief Evaluate an expression returning `error_t`; on `is_bad()`, log and
/// propagate it. Mirrors cuDNN FE's `CHECK_CUDNN_FRONTEND_ERROR`.
#ifndef CHECK_CUDNN_FRONTEND_ERROR
#define CHECK_CUDNN_FRONTEND_ERROR(x) \
do \
{ \
if(auto retval = (x); retval.is_bad()) \
{ \
CUDNN_FE_LOG_LABEL_ENDL("ERROR: " << #x << " at " << __FILE__ << ":" << __LINE__); \
return retval; \
} \
} while(0)
#endif

/// @brief If `cond`, log and `return {retval, message}`. Mirrors cuDNN FE's
/// `RETURN_CUDNN_FRONTEND_ERROR_IF`.
#ifndef RETURN_CUDNN_FRONTEND_ERROR_IF
#define RETURN_CUDNN_FRONTEND_ERROR_IF(cond, retval, message) \
do \
{ \
if(cond) \
{ \
if((retval) == error_code_t::OK) \
{ \
CUDNN_FE_LOG_LABEL("INFO: "); \
} \
else \
{ \
CUDNN_FE_LOG_LABEL("ERROR: "); \
} \
CUDNN_FE_LOG((message) << ". because (" << #cond ") at " << __FILE__ << ":" \
<< __LINE__ << "\n"); \
return {retval, message}; \
} \
} while(0)
#endif
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
// Copyright © Advanced Micro Devices, Inc., or its affiliates.
// SPDX-License-Identifier: MIT
//
// Portions derived from NVIDIA cuDNN frontend
// (include/cudnn_frontend/graph_properties.h), used under the MIT license.

/**
* @file graph_properties.h
* @brief Graph attribute-type aliases for the hipDNN cuDNN-compatibility shim.
*
* Brings hipDNN's v9 graph attribute types into `<shim_ns>::graph` by aliasing
* them with `using` declarations — zero overhead, no shim-side state. A tensor
* configured through the shim therefore *is* a hipDNN `TensorAttributes` and
* flows into a wrapped hipDNN graph with no conversion (UID handling stays on
* the hipDNN side).
*
* @note Internal-to-shim; pulled in by the umbrella `cudnn_frontend.h`.
*/

#pragma once

#include <hipdnn_frontend/attributes/TensorAttributes.hpp>

namespace hipdnn_frontend::compatibility::cudnn_frontend::graph
{

// hipDNN publishes cuDNN's `Tensor_attributes` spelling as a typedef; aliasing
// it lets consumer code using that name resolve through the shim.
using hipdnn_frontend::graph::Tensor_attributes;

} // namespace hipdnn_frontend::compatibility::cudnn_frontend::graph
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
// Copyright © Advanced Micro Devices, Inc., or its affiliates.
// SPDX-License-Identifier: MIT
//
// Portions derived from NVIDIA cuDNN frontend (include/cudnn_frontend_utils.h),
// used under the MIT license.

/**
* @file cudnn_frontend_utils.h
* @brief FE-namespace enum aliases for the hipDNN cuDNN-compatibility shim.
*
* The v9 graph API signatures use cuDNN's FE-namespace enums (`DataType_t`,
* `PointwiseMode_t`, …), not the C-API ones from `<cudnn.h>`. hipDNN already
* publishes these as cuDNN-named `_t` typedefs (see `Types.hpp`), so this header
* just aliases them into `<shim_ns>` with `using` declarations — zero overhead,
* no numeric cast between enum families.
*
* @note Internal-to-shim; pulled in by the umbrella `cudnn_frontend.h`.
*/

#pragma once

#include <hipdnn_frontend/Types.hpp>

namespace hipdnn_frontend::compatibility::cudnn_frontend
{

// FE-namespace enums hipDNN publishes 1:1, aliased so e.g.
// `cudnn_frontend::DataType_t` *is* `hipdnn_frontend::DataType_t`.
using hipdnn_frontend::AttentionImplementation_t;
using hipdnn_frontend::BehaviorNote_t;
using hipdnn_frontend::BuildPlanPolicy_t;
using hipdnn_frontend::ConvolutionMode_t;
using hipdnn_frontend::DataType_t;
using hipdnn_frontend::DiagonalAlignment_t;
using hipdnn_frontend::HeurMode_t;
using hipdnn_frontend::NormFwdPhase_t;
using hipdnn_frontend::PaddingMode_t;
using hipdnn_frontend::PointwiseMode_t;
using hipdnn_frontend::ReductionMode_t;
using hipdnn_frontend::ResampleMode_t;

// Other cuDNN FE-namespace enums (NumericalNote_t, NormMode_t, RngDistribution_t,
// DescriptorType_t, MoeGroupedMatmulMode_t, TensorReordering_t, ReshapeMode_t)
// are not aliased yet: hipDNN does not publish them and their nodes are out of
// scope. They are aliased when their node lands.

} // namespace hipdnn_frontend::compatibility::cudnn_frontend

// The `graph` sub-namespace is populated by the `cudnn_frontend/*` headers the
// umbrella pulls in; declared empty here so this header is self-contained when
// included on its own.
namespace hipdnn_frontend::compatibility::cudnn_frontend::graph
{
} // namespace hipdnn_frontend::compatibility::cudnn_frontend::graph
Original file line number Diff line number Diff line change
Expand Up @@ -6,25 +6,18 @@

/**
* @file cudnn_frontend_version.h
* @brief Version macros for the hipDNN cuDNN-compatibility shim.
* @brief cuDNN frontend (FE) version the shim claims source compatibility with.
*
* These mirror NVIDIA's `cudnn_frontend_version.h` and declare which cuDNN
* frontend (FE) release this shim claims *source* compatibility with
* (RFC 0012 §4.8). This is the cuDNN **frontend** library version (an
* NVIDIA/cudnn-frontend tag), independent of both hipDNN's own version and the
* cuDNN **runtime** version returned by `cudnnGetVersion()` (see `cudnn.h`).
*
* Consumers such as PyTorch's `MHA.cpp` gate on `CUDNN_FRONTEND_VERSION`
* (e.g. `#if CUDNN_FRONTEND_VERSION <= 11200`), so matching upstream matters.
*
* Pinned to cuDNN FE v1.24.0 (RFC 0012 §2).
* The cuDNN *frontend* library version (a cudnn-frontend tag), distinct from
* hipDNN's version and from the cuDNN *runtime* version in
* `cudnn_runtime_version.h`. Consumers gate on `CUDNN_FRONTEND_VERSION` (e.g.
* PyTorch's `MHA.cpp`), so it must match upstream. Pinned to cuDNN FE v1.24.0.
Comment thread
mousdahl-amd marked this conversation as resolved.
*/

#pragma once

// These must remain preprocessor macros (not an enum): consumers such as
// PyTorch's MHA.cpp gate on them in `#if CUDNN_FRONTEND_VERSION <= 11200`
// directives, which an enum cannot satisfy. Suppress modernize-macro-to-enum.
// Must remain preprocessor macros, not an enum: consumers gate on these in `#if`
// directives (e.g. `CUDNN_FRONTEND_VERSION <= 11200`), which an enum cannot do.
// NOLINTBEGIN(modernize-macro-to-enum,cppcoreguidelines-macro-to-enum)
#define CUDNN_FRONTEND_MAJOR_VERSION 1
#define CUDNN_FRONTEND_MINOR_VERSION 24
Expand Down
Loading
Loading