Guest User

Untitled

a guest
Jan 30th, 2014
88
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C 2.22 KB | None | 0 0
  1. #define _GNU_SOURCE
  2. #include <stdio.h>
  3. #include <stdlib.h>
  4. #include <sys/mman.h>
  5. #include <stdint.h>
  6. #include <string.h>
  7. #include <unistd.h>
  8. #include <omp.h>
  9. #include <x86intrin.h>
  10.  
  11. #define bind(f, arg) ({typeof(f(arg)) new(void) { return f(arg);} new;})
  12. #define bind2(f, arg, arg2) ({typeof(f(arg, arg2)) new(void) { return f(arg, arg2);} new;})
  13. #define bind3(f, arg, arg2, arg3) ({typeof(f(arg, arg2, arg3)) new(void) { return f(arg, arg2, arg3);} new;})
  14.  
  15. static inline void * alloc(uint64_t size, uint64_t flags) {
  16.   return mmap(NULL, size, PROT_WRITE | PROT_READ, MAP_PRIVATE | MAP_ANONYMOUS | flags, 0, 0);
  17. }
  18.  
  19. typedef void*(*vpvf_t)(void);
  20.  
  21. #define GB (1024ul*1024*1024)
  22. #define KB (1024)
  23.  
  24. void bench_memcpy(uint64_t total, uint64_t pass, vpvf_t f) {
  25.   uint64_t i = (total/pass);
  26.   double start = omp_get_wtime();
  27.   do {f();} while(--i);
  28.   double time = omp_get_wtime() - start;
  29.   fprintf(stderr, "%fGB/s\n", ((total * 2)/GB)/time);
  30. }
  31.  
  32. void * cachecp32(__m256i * to, __m256i * from, uint64_t n) {
  33.   typeof(from) from_end = ((void *)from + n), ret = to;
  34.   do {
  35.     _mm256_store_si256(to++, _mm256_load_si256(from++));
  36.   } while(from != from_end);
  37.   return ret;
  38. }
  39.  
  40. void * cachecp512(__m256i * to, __m256i * from, uint64_t n) {
  41.   typeof(from) from_end = ((void *)from + n), ret = to;
  42.   do {
  43.     *to++ = *from++;
  44.     *to++ = *from++;
  45.     *to++ = *from++;
  46.     *to++ = *from++;
  47.     *to++ = *from++;
  48.     *to++ = *from++;
  49.     *to++ = *from++;
  50.     *to++ = *from++;
  51.     *to++ = *from++;
  52.     *to++ = *from++;
  53.     *to++ = *from++;
  54.     *to++ = *from++;
  55.     *to++ = *from++;
  56.     *to++ = *from++;
  57.     *to++ = *from++;
  58.     *to++ = *from++;
  59.   } while(from != from_end);
  60.   return ret;
  61. }
  62.  
  63. int main(void) {
  64.   vpvf_t alloc1gb = bind2(alloc, GB, MAP_POPULATE);
  65.   void * from = alloc1gb(), * to = alloc1gb();
  66.   uint64_t block_size = KB, total = GB*128;
  67.   do {
  68.     fprintf(stderr, "\nBLOCK SIZE: %luKB\n", block_size/KB);
  69.     fprintf(stderr, "cachecp32:\n");
  70.     bench_memcpy(total, block_size, bind3(cachecp32, to, from, block_size));
  71.     fprintf(stderr, "cachecp512:\n");
  72.     bench_memcpy(total, block_size, bind3(cachecp512, to, from, block_size));
  73.   } while((block_size *= 2) != (sysconf(_SC_LEVEL1_DCACHE_SIZE)/2));
  74. }
Advertisement
Add Comment
Please, Sign In to add comment