#pragma once

#define MAX_PARLIB_MP_DIMS	6		// maximum number of dims for manual packing

#define MIN_MEMCPY_BLOCK	256		// minimum block (in bytes) for memcpy copy (magic number)

#define MAX_PL_BUFS		4096		// maximum number of parLIB internal buffers

// _RESTRICT definition 
// ------------------------------------------------------------------- //
#if defined(__INTEL_COMPILER)
#define _RESTRICT restrict
#elif defined(__GNUC__) && !defined(_WIN32) && !defined(_CYGWIN32__)
#define _RESTRICT __restrict__
#elif defined(_MSC_VER)
#define _RESTRICT __restrict
#else
#define _RESTRICT
#endif
// ------------------------------------------------------------------- //


// parLIB buffers [declaration]
// -------------------------------------------------------------------------- //
extern void *plbuf[MAX_PL_BUFS];
extern int plbuf_size[MAX_PL_BUFS];
extern int plbuf_status[MAX_PL_BUFS];

extern int plbuf_ptr;
// -------------------------------------------------------------------------- //


void init_plbuf();
void deinit_plbuf();

void* get_plbuf(int msize, int* id);
void free_plbuf(void* ptr, int id);
// -------------------------------------------------------------------------- //

void copy_to_buffer(char* _RESTRICT buf, const char* _RESTRICT const a,
	const int ndims,
	const int* _RESTRICT const msgdim,
	const int* _RESTRICT const stride,
	const int fsize);

void copy_from_buffer(char* _RESTRICT a, const char* _RESTRICT const buf,
	const int ndims,
	const int* _RESTRICT const msgdim,
	const int* _RESTRICT const stride,
	const int fsize);
// -------------------------------------------------------------------------- //