#ifndef GPU_INTEL_MATMUL_SPARSE_REF_HPP
#define GPU_INTEL_MATMUL_SPARSE_REF_HPP
#include <assert.h>
#include "common/c_types_map.hpp"
#include "common/primitive.hpp"
#include "common/utils.hpp"
#include "gpu/intel/matmul/config.hpp"
#include "gpu/intel/primitive.hpp"
#include "gpu/intel/primitive_conf.hpp"
namespace dnnl {
namespace impl {
namespace gpu {
namespace intel {
namespace matmul {
struct ref_sparse_t : public primitive_t {
using primitive_t::primitive_t;
struct pd_t : public matmul::pd_t {
using matmul::pd_t::pd_t;
DECLARE_COMMON_PD_T("ocl:ref:any", ref_sparse_t);
status_t init(impl::engine_t *engine) {
using namespace data_type;
src_dt_ = src_md()->data_type;
dst_dt_ = dst_md()->data_type;
wei_dt_ = weights_md(0)->data_type;
memory_desc_wrapper src_d(src_md());
memory_desc_wrapper wei_d(weights_md(0));
bool is_f16_dt = utils::everyone_is(f16, src_dt_, wei_dt_, dst_dt_);
bool is_f32_dt = utils::everyone_is(f32, src_dt_, wei_dt_, dst_dt_);
VDISPATCH_MATMUL(
is_f32_dt || is_f16_dt, VERBOSE_UNSUPPORTED_DT_CFG);
bool is_src_coo_sparse = src_d.is_sparse_desc()
&& (src_d.encoding() == sparse_encoding::coo);
VDISPATCH_MATMUL(is_src_coo_sparse, VERBOSE_UNSUPPORTED_SPARSE_CFG);
bool is_meta_data_valid = src_d.metadata_type(0) == s32;
VDISPATCH_MATMUL(
is_meta_data_valid, VERBOSE_UNSUPPORTED_SPARSE_CFG);
VDISPATCH_MATMUL(set_default_formats(), VERBOSE_UNSUPPORTED_TAG);
bool wei_tag_check
= wei_d.matches_one_of_tag(format_tag::ab, format_tag::ba);
VDISPATCH_MATMUL(wei_tag_check, VERBOSE_UNSUPPORTED_TAG);
VDISPATCH_MATMUL(
attr()->has_default_values(), VERBOSE_UNSUPPORTED_ATTR);
VDISPATCH_MATMUL(!with_bias(), VERBOSE_UNSUPPORTED_BIAS_CFG);
return status::success;
}
data_type_t src_dt_ = data_type::undef;
data_type_t dst_dt_ = data_type::undef;
data_type_t wei_dt_ = data_type::undef;
};
status_t init(impl::engine_t *engine) override {
compute::kernel_ctx_t kernel_ctx;
int ndims = pd()->dst_md()->ndims;
kernel_ctx.set_data_type(pd()->dst_dt_);
kernel_ctx.require_stateless_addressing(pd()->has_large_buffers());
const memory_desc_wrapper src_d(pd()->src_md(0));
const memory_desc_wrapper wei_d(pd()->weights_md(0));
const memory_desc_wrapper dst_d(pd()->dst_md(0));
offsets_t off;
set_offsets(src_d, off.src_off);
set_offsets(wei_d, off.wei_off);
set_offsets(dst_d, off.dst_off);
def_offsets(off.src_off, kernel_ctx, "SRC", ndims);
def_offsets(off.wei_off, kernel_ctx, "WEI", ndims);
def_offsets(off.dst_off, kernel_ctx, "DST", ndims);
kernel_ctx.define_int("NDIMS", ndims);
def_data_type(kernel_ctx, pd()->src_dt_, "SRC");
def_data_type(kernel_ctx, pd()->wei_dt_, "WEI");
def_data_type(kernel_ctx, pd()->dst_dt_, "DST");
def_data_type(kernel_ctx, pd()->desc()->accum_data_type, "ACC");
CHECK(create_kernel(engine, &kernel_, "ref_sparse_matmul", kernel_ctx));
if (!kernel_) return status::runtime_error;
return status::success;
}
status_t execute(const exec_ctx_t &ctx) const override {
return execute_ref(ctx);
}
private:
const pd_t *pd() const { return (const pd_t *)primitive_t::pd().get(); }
status_t execute_ref(const exec_ctx_t &ctx) const;
compute::kernel_t kernel_;
};
} } } } }
#endif