26 #ifndef __COMMON_HPP__
27 #define __COMMON_HPP__
31 #include <glog/logging.h>
35 using std::unique_ptr;
44 template<
typename T,
typename... Args>
46 return std::unique_ptr<T>(
new T(std::forward<Args>(args)...));
53 #include <sys/mta_task.h>
54 #include <machine/runtime.h>
55 #elif defined(__MACH__)
56 #include <mach/mach_time.h>
62 #define KILO (1024ULL * ONE)
63 #define MEGA (1024ULL * KILO)
64 #define GIGA (1024ULL * MEGA)
65 #define TERA (1024ULL * GIGA)
66 #define PETA (1024ULL * TERA)
67 #define CACHE_LINE_SIZE (64ULL)
68 #define SIZE_OF_CACHE (MEGA * 64ULL)
69 #define THOUSAND (1000ULL * ONE)
70 #define MILLION (1000ULL * THOUSAND)
71 #define BILLION (1000ULL * MILLION)
74 # define MAX(a,b) ((a) < (b) ? (b) : (a))
77 # define MIN(a,b) ((a) > (b) ? (b) : (a))
81 #define ALIGN_UP(x, y) \
82 ((((u_int64_t)(x) & (((u_int64_t)(y))-1)) != 0) ? \
83 ((void *)(((u_int64_t)(x) & (~(u_int64_t)((y)-1)))+(y))) \
87 #define GRAPPA_DEPRECATED __attribute__((deprecated))
101 return((
double)mta_get_clock(0) / mta_clock_freq());
102 #elif defined(__MACH__)
103 static mach_timebase_info_data_t info;
104 mach_timebase_info(&info);
105 uint64_t now = mach_absolute_time();
108 return 1.0e-9 * (double)now;
111 #if defined(CLOCK_PROCESS_CPUTIME_ID)
112 #define CLKID CLOCK_PROCESS_CPUTIME_ID
113 #elif defined(CLOCK_REALTIME_ID)
114 #define CLKID CLOCK_REALTIME_ID
116 clock_gettime(CLOCK_MONOTONIC, &tp);
117 return (
double)tp.tv_sec + (double)tp.tv_nsec /
BILLION;
123 #define GRAPPA_TIME(var, block) \
125 double _tmptime = Grappa::walltime(); \
127 var = Grappa::walltime()-_tmptime; \
130 #define GRAPPA_TIMER(var) \
131 for (double _tmpstart = Grappa::walltime(), _tmptime = -1; \
133 var = _tmptime = Grappa::walltime() - _tmpstart)
135 #define GRAPPA_TIME_LOG(name) \
136 for (double _tmpstart = Grappa::walltime(), _tmptime = -1; _tmptime < 0; \
137 LOG(INFO) << name << ": " << (Grappa::walltime()-_tmpstart), _tmptime = 1)
139 #define GRAPPA_TIME_VLOG(level, name, indent) \
140 VLOG(level) << indent << name << "..."; \
141 for (double _tmpstart = Grappa::walltime(), _tmptime = -1; _tmptime < 0; \
142 VLOG(level) << indent << " (" << (Grappa::walltime()-_tmpstart) << " s)", _tmptime = 1)
144 #define GRAPPA_TIME_REGION(var) \
145 for (double _tmpstart = Grappa::walltime(), _tmptime = -1; _tmptime < 0; \
146 var += (Grappa::walltime()-_tmpstart), _tmptime = 1)
149 template<
typename T,
typename U >
150 static inline double nanless_double_ratio( T x, U y ) {
151 return y == 0 ? 0.0 :
static_cast<double>(x) / static_cast<double>(y);
157 #define DISALLOW_COPY_AND_ASSIGN( Name ) \
158 Name( const Name & ); \
159 void operator=( const Name & )
161 namespace bittwiddle {
164 template <
typename T,
unsigned B>
173 inline unsigned int log2(
unsigned int v ) {
177 r = (v > 0xFFFF) << 4; v >>= r;
178 shift = (v > 0xFF ) << 3; v >>= shift; r |= shift;
179 shift = (v > 0xF ) << 2; v >>= shift; r |= shift;
180 shift = (v > 0x3 ) << 1; v >>= shift; r |= shift;
188 #define rdtscll(val) do { \
189 unsigned int __a,__d; \
190 asm volatile("rdtsc" : "=a" (__a), "=d" (__d)); \
191 (val) = ((unsigned long)__a) | (((unsigned long)__d)<<32); \
195 static inline unsigned long long rdtsc() {
196 unsigned long long val;
203 template<
typename T >
209 template<
typename Container,
typename Comparator >
210 auto min_element(
const Container& c, Comparator cmp) -> decltype(*c.begin()) {
215 template<
typename Container,
typename Comparator >
216 auto min_element(
const Container& c0,
const Container& c1, Comparator cmp) -> decltype(*c0.begin()) {
219 return cmp(m0,m1) ? m0 : m1;
224 template<
typename T >
228 template<
typename T,
typename Comparator >
231 for (T e = r.
start; e < r.
end; e++) {
244 o <<
"<" << r.
start <<
"," << r.
end <<
">";
249 int64_t numElems = end-start;
250 int64_t each = numElems / numBlocks;
251 int64_t remain = numElems % numBlocks;
252 int64_t mynum = (rank < remain) ? each+1 : each;
253 int64_t mystart = start + ((rank < remain) ? (each+1)*rank : (each+1)*remain + (rank-remain)*each);
254 range_t r = { mystart, mystart+mynum };
262 int64_t each = numElements / numBlocks,
263 remain = numElements % numBlocks;
264 if (index < (each+1)*remain) {
265 result = { index / (each+1), index % (each+1) };
267 index -= (each+1)*remain;
268 result = { remain + index/each, index % each };
274 #define GET_TYPE(member) BOOST_PP_TUPLE_ELEM(2,0,member)
276 #define GET_NAME(member) BOOST_PP_TUPLE_ELEM(2,1,member)
278 #define CAT_EACH(r, data, elem) BOOST_PP_CAT(elem, data)
280 #define AUTO_CONSTRUCTOR_DETAIL_PARAM(r, data, member) \
281 GET_TYPE(member) GET_NAME(member)
283 #define DECL_W_TYPE(r, data, member) \
284 GET_TYPE(member) GET_NAME(member);
286 #define AUTO_CONSTRUCTOR_DETAIL_INIT(r, data, member) \
287 GET_NAME(member) ( GET_NAME(member) )
289 #define AUTO_CONSTRUCTOR_DETAIL(className, members) \
290 className(BOOST_PP_SEQ_ENUM(BOOST_PP_SEQ_TRANSFORM( \
291 AUTO_CONSTRUCTOR_DETAIL_PARAM, BOOST_PP_EMPTY, members))) : \
292 BOOST_PP_SEQ_ENUM(BOOST_PP_SEQ_TRANSFORM( \
293 AUTO_CONSTRUCTOR_DETAIL_INIT, BOOST_PP_EMPTY, members)) \
296 #define AUTO_CONSTRUCTOR(className, members) \
297 AUTO_CONSTRUCTOR_DETAIL(className, members)
299 #define AUTO_DECLS(members) \
300 BOOST_PP_SEQ_FOR_EACH(CAT_EACH, ,BOOST_PP_SEQ_TRANSFORM(DECL_W_TYPE, BOOST_PP_EMPTY, members))
306 #define FUNCTOR(name, members) \
307 struct name : public Functor { \
308 AUTO_DECLS(members) \
309 AUTO_CONSTRUCTOR( name, members ) \
311 inline void operator()() const; \
313 inline void name::operator()() const
318 static unsigned int g_seed;
323 g_seed = (214013*g_seed+2531011);
324 return (g_seed>>16)&0x7FFF;
335 template<
typename T >
338 static const int size =
sizeof(__PRETTY_FUNCTION__);
341 static char fn_name[
size ] = {
'\0' };
344 static const char * strcpy_retval = strncpy( fn_name, __PRETTY_FUNCTION__, size );
347 static const char with[] =
"[with T = ";
348 static const char * name = strstr( fn_name, with ) +
sizeof( with ) - 1;
351 static const char erase_bracket = fn_name[size-2] =
'\0';
358 template<
typename T >
360 return typename_of<T>();
365 template <
typename T>
366 inline T* CheckNull(
const char *file,
int line,
const char *names, T* t) {
368 google::LogMessageFatal(file, line,
new std::string(names));
374 #define CHECK_NULL(val) \
375 Grappa::impl::CheckNull(__FILE__, __LINE__, "'" #val "' Must be non NULL", (val))
378 #define DCHECK_NULL(val) \
379 Grappa::impl::CheckNull(__FILE__, __LINE__, "'" #val "' Must be non NULL", (val))
381 #define DCHECK_NULL(val) \
386 #define MPI_CHECK( mpi_call ) \
389 if( (retval = (mpi_call)) != 0 ) { \
390 char error_string[MPI_MAX_ERROR_STRING]; \
392 MPI_Error_string( retval, error_string, &length); \
393 LOG(FATAL) << "MPI call failed: " #mpi_call ": " \
409 static inline void prefetcht0(
const void *p) {
410 __builtin_prefetch(p, 0, 3);
413 static inline void prefetchnta(
const void *p) {
414 __builtin_prefetch(p, 0, 0);
417 static inline void prefetcht2(
const void *p) {
418 __builtin_prefetch(p, 0, 1);
double walltime(void)
"Universal" wallclock time (works at least for Mac, MTA, and most Linux)
range_t blockDist(int64_t start, int64_t end, int64_t rank, int64_t numBlocks)
block_offset_t indexToBlock(int64_t index, int64_t numElements, int64_t numBlocks)
auto min_element(const Container &c, Comparator cmp) -> decltype(*c.begin())
Helper for invoking 'std::min_element' on containers.
T signextend(const T x)
Sign extension.
std::unique_ptr< T > make_unique(Args &&...args)
Construct unique_ptr more easily.
SyncMode
Specify whether an operation blocks until complete, or returns "immediately".
TaskMode
Specify whether tasks are bound to the core they're spawned on, or if they can be load-balanced (via ...
void fast_srand(int seed)
Range type that represents the values [start,end).
#define rdtscll(val)
Read 64-bit timestamp counter.
virtual const size_t size() const
Unserialized message size.
const char * typename_of()
Get string containing name of type.
T * Grappa_magic_identity_function(T *t)
OMGWTFBBQ Grappa magic identity function Use this to get a pointer to a template function inside a te...
unsigned int log2(unsigned int v)
Base 2 log of 32-bit number.
std::ostream & operator<<(std::ostream &o, const range_t &r)