//===-- APIDefs.td - Base definitions for Offload tablegen -*- tablegen -*-===//
//
// 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
//
//===----------------------------------------------------------------------===//
//
// This file contains the class definitions used to implement the Offload API,
// as well as helper functions used to help populate relevant records.
// See offload/API/README.md for more detailed documentation.
//
//===----------------------------------------------------------------------===//

// Prefix for API naming. This could be hard-coded in the future when a value
// is agreed upon.
defvar PREFIX = "OL";
defvar prefix = !tolower(PREFIX);

// Parameter flags
defvar PARAM_IN = 0x1;
defvar PARAM_OUT = 0x2;
defvar PARAM_OPTIONAL = 0x4;
defvar PARAM_IN_OPTIONAL = !or(PARAM_IN, PARAM_OPTIONAL);
defvar PARAM_OUT_OPTIONAL = !or(PARAM_OUT, PARAM_OPTIONAL);

// Does the type end with '_handle_t'?
class IsHandleType<string Type> {
  // size("_handle_t") == 9
  bit ret = !if(!lt(!size(Type), 9), 0,
                !ne(!find(Type, "_handle_t", !sub(!size(Type), 9)), -1));
}

// Does the type end with '_cb_t'?
class IsCallbackType<string Type> {
  // size("_cb_t") == 5
  bit ret = !if(!lt(!size(Type), 5), 0,
                !ne(!find(Type, "_cb_t", !sub(!size(Type), 5)), -1));
}

// Does the type end with '*'?
class IsPointerType<string Type> {
  bit ret = !ne(!find(Type, "*", !sub(!size(Type), 1)), -1);
}

// Describes the valid range of a pointer parameter that represents an array
class Range<string Begin, string End> {
  string begin = Begin;
  string end = End;
}

// Names the parameters that indicate the type and size of the data pointed to
// by an opaque pointer parameter
class TypeInfo<string TypeEnum, string TypeSize> {
  string enum = TypeEnum;
  string size = TypeSize;
}

class Param<string Type, string Name, string Desc, bits<3> Flags = 0> {
  string type = Type;
  string name = Name;
  string desc = Desc;
  bits<3> flags = Flags;
  Range range = Range<"", "">;
  TypeInfo type_info = TypeInfo<"", "">;
  bit IsHandle = IsHandleType<type>.ret;
  bit IsPointer = IsPointerType<type>.ret;
  bit IsCallback = IsCallbackType<type>.ret;
}

// A parameter whose range is described by other parameters in the function.
class RangedParam<string Type, string Name, string Desc, bits<3> Flags, Range ParamRange> : Param<Type, Name, Desc, Flags> {
  let range = ParamRange;
}

// A parameter (normally of type void*) which has its pointee type and size
// described by other parameters in the function.
class TypeTaggedParam<string Type, string Name, string Desc, bits<3> Flags, TypeInfo ParamTypeInfo> : Param<Type, Name, Desc, Flags> {
  let type_info = ParamTypeInfo;
}

class Return<string Value, list<string> Conditions = []> {
  string value = Value;
  list<string> conditions = Conditions;
}

class ShouldCheckHandle<Param P> {
  bit ret = !and(P.IsHandle, !eq(!and(PARAM_OPTIONAL, P.flags), 0));
}

class ShouldCheckPointer<Param P> {
  bit ret = !and(!or(P.IsPointer, P.IsCallback), !eq(!and(PARAM_OPTIONAL, P.flags), 0));
}

// For a list of returns that contains a specific return code, find and append
// new conditions to that return
class AppendConditionsToReturn<list<Return> Returns, string ReturnValue,
                               list<string> Conditions> {
  list<Return> ret =
      !foreach(Ret, Returns,
               !if(!eq(Ret.value, ReturnValue),
                   Return<Ret.value, Ret.conditions#Conditions>, Ret));
}

// Add null handle checks to a function's return value descriptions
class AddHandleChecksToReturns<list<Param> Params, list<Return> Returns> {
  list<string> handle_params =
      !foreach(P, Params, !if(ShouldCheckHandle<P>.ret, P.name, ""));
  list<string> handle_params_filt =
      !filter(param, handle_params, !ne(param, ""));
  list<string> handle_param_conds =
      !foreach(handle, handle_params_filt, "`NULL == "#handle#"`");

  // Does the list of returns already contain ERROR_INVALID_NULL_HANDLE?
  bit returns_has_inv_handle = !foldl(
      0, Returns, HasErr, Ret,
      !or(HasErr, !eq(Ret.value, PREFIX#"_ERRC_INVALID_NULL_HANDLE")));

  list<Return> returns_out = !if(returns_has_inv_handle,
        AppendConditionsToReturn<Returns, PREFIX # "_ERRC_INVALID_NULL_HANDLE", handle_param_conds>.ret,
        !listconcat(Returns, [Return<PREFIX # "_ERRC_INVALID_NULL_HANDLE", handle_param_conds>])
    );
}

// Add null pointer checks to a function's return value descriptions
class AddPointerChecksToReturns<list<Param> Params, list<Return> Returns> {
  list<string> ptr_params =
      !foreach(P, Params, !if(ShouldCheckPointer<P>.ret, P.name, ""));
  list<string> ptr_params_filt = !filter(param, ptr_params, !ne(param, ""));
  list<string> ptr_param_conds =
      !foreach(ptr, ptr_params_filt, "`NULL == "#ptr#"`");

  // Does the list of returns already contain ERROR_INVALID_NULL_POINTER?
  bit returns_has_inv_ptr = !foldl(
      0, Returns, HasErr, Ret,
      !or(HasErr, !eq(Ret.value, PREFIX#"_ERRC_INVALID_NULL_POINTER")));
  list<Return> returns_out = !if(returns_has_inv_ptr,
        AppendConditionsToReturn<Returns, PREFIX # "_ERRC_INVALID_NULL_POINTER", ptr_param_conds>.ret,
        !listconcat(Returns, [Return<PREFIX # "_ERRC_INVALID_NULL_POINTER", ptr_param_conds>])
    );
}

defvar DefaultReturns = [Return<PREFIX#"_RESULT_SUCCESS">,
                         Return<PREFIX#"_ERRC_UNINITIALIZED">,
                         Return<PREFIX#"_ERRC_DEVICE_LOST">];

class APIObject {
  string desc;
}

class Function : APIObject {
  list<Param> params;
  list<Return> returns;
  list<string> details = [];
  list<string> analogues = [];

  list<Return> returns_with_def = !listconcat(DefaultReturns, returns);
  list<Return> all_returns = AddPointerChecksToReturns<params,
        AddHandleChecksToReturns<params, returns_with_def>.returns_out>.returns_out;
}

class Etor<string Name, string Desc> {
  string name = Name;
  string desc = Desc;
  string tagged_type;
}

class TaggedEtor<string Name, string Type, string Desc> : Etor<Name, Desc> {
  let tagged_type = Type;
}

class Enum : APIObject {
  // This refers to whether the enumerator descriptions specify a return
  // type for functions where this enum may be used as an output type. If set,
  // all Etor values must be TaggedEtor records
  bit is_typed = 0;

  // This refers to whether the enumerator is used to name bits of a bit field,
  // where consecutive values are bit-shifted rather than incremented.
  bit is_bit_field = 0;

  list<Etor> etors = [];
}

class StructMember<string Type, string Name, string Desc> {
  string type = Type;
  string name = Name;
  string desc = Desc;
}

defvar DefaultPropStructMembers =
    [StructMember<prefix#"_structure_type_t", "stype",
                  "type of this structure">,
     StructMember<"void*", "pNext", "pointer to extension-specific structure">];

class StructHasInheritedMembers<string BaseClass> {
  bit ret = !or(!eq(BaseClass, prefix#"_base_properties_t"),
                !eq(BaseClass, prefix#"_base_desc_t"));
}

class Struct : APIObject {
  string base_class = "";
  list<StructMember> members;
  list<StructMember> all_members =
      !if(StructHasInheritedMembers<base_class>.ret,
          DefaultPropStructMembers, [])#members;
}

class Typedef : APIObject { string value; }

class FptrTypedef : APIObject {
  list<Param> params;
  string return;
}

class Macro : APIObject {
  string value;

  string condition;
  string alt_value;
}

class Handle : APIObject;
