/* Copyright 2017-2020, NVIDIA CORPORATION. All rights reserved. */

#define __PGI_CPLUS_PREINCLUDE__ 1

/* Define all the builtins that are behind the implementation of variadic
   functions. */

struct __va_list_tag {
  unsigned int gp_offset;
  unsigned int fp_offset;
  char *overflow_arg_area;
  char *reg_save_area;
};

#if defined(__NVCC_HOST__) && defined(__PREPROCESS_ONLY__) && \
    __CUDACC_VER_MAJOR__ < 11

/* If pgc++ is preprocessing code that will later be parsed by the nvcc C++
   front end, __builtin_va_list must be a pointer to __pgi_tag.  __pgi_tag will
   be defined automatically by the the nvcc front end, so it can't be defined
   here.  If the preprocessed code is later passed back to pgc++ to be
   compiled, _cplus_nvcc.h will change things back to how pgc++ likes them,
   with __builtin_va_list being a pointer to __va_list_tag. */
typedef __pgi_tag __pgi_va_list[1];

#else

typedef struct __va_list_tag __pgi_va_list[1];

#endif

#if defined(__NVCC_HOST__) && defined(__PREPROCESS_ONLY__) && \
    (__CUDACC_VER_MAJOR__ < 11 || \
     (__CUDACC_VER_MAJOR__ == 11 && __CUDACC_VER_MINOR__ < 5))
/* nvcc pre-11.5 doesn't recognize __builtin_pgi_va_start and
   __builtin_pgi_va_arg as built-in functions.  Explicit declarations are
   necessary. */
extern "C" void __builtin_pgi_va_start(...);
extern "C" void* __builtin_pgi_va_arg(...);
#endif

#define __builtin_va_list              __pgi_va_list
#define __builtin_va_start(ap, param) (__builtin_pgi_va_start(ap, param))
#define __builtin_c23_va_start(ap, param) (__builtin_pgi_va_start(ap, param))
#define __builtin_va_arg(ap, type) (*(type*)__builtin_pgi_va_arg(ap, (type*)0))
#define __builtin_va_copy(dst, src)   ((dst)[0] = (src)[0])
#define __builtin_va_end(ap)          ((void)0)

#ifdef _WIN64
#define __builtin_expect(a,b) (a)
#endif

