#include <stdlib.h>                                                              
#include <stdio.h>                                                               
#include <time.h>                                                                
#include <math.h>                                                                
                                                                                 
#define ITER 10                                                                  
#define get_ticks(var) { \                                                       
  unsigned int __a, __d; \                                                       
  asm volatile("rdtsc" : "=a" (__a), "=d" (__d)); \                              
  var = ((unsigned long) __a) | (((unsigned long) __d) << 32); \                 
  } while(0)                                                                     
                                                                                 
                                                                                 
int main(int argc, char *argv[] )                                                
{                                                                                
  int i, j, k, n, m, THRASHING;                                                  
  double *B, *C, *D, *KICK;                                                      
                                                                                 
  double c_time, timer;                                                          
  unsigned long ticks1, ticksB4, ticksAFT;                                       
                                                                                 
                                                                                 
  if(argc < 4){                                                                  
    printf("pass me 3 arguments!\n");                                            
    return( -1 );                                                                
  }                                                                              
  else                                                                           
    {                                                                            
      m = atoi(argv[1]);                                                         
      n = atoi(argv[2]);                                                         
      THRASHING = atoi(argv[3]);                                                 
    }                                                                            
                                                                                 
  B = (double *) malloc( m*n * sizeof(double) );                                 
  C = (double *) malloc( m*n * sizeof(double) );                                 
  D = (double *) malloc( m*n * sizeof(double) );                                 
  KICK = (double *) malloc( 5000*5000 * sizeof(double) );                        
                                                                                 

  for( i=0; i<m; i++ )
    for( j=0; j<n; j++ )
      {
        B[j*m+i] =   10.0001*j+i;
        C[j*m+i] = -(10.0001*j+i);
        //printf("idx=%d \tval=%lf\n", j*m+i, 10.0001*j+i);                      
      }

  for( i=0; i<5000; i++ )
    for( j=0; j<5000; j++ )
      KICK[j*5000+i] = 10.0001;

  for( k=0; k<ITER; k++ ){
    /* part #1 */
    printf(" -- iter %d -- \n", k);
    timer = ((double) clock ())/CLOCKS_PER_SEC;
    get_ticks(ticksB4);

    for( j=0; j<n; j++ )
      for( i=0; i<m; i++ )
        {
          D[j*m+i] = B[j*m+i] + C[j*m+i];
        }

    get_ticks(ticksAFT);
    ticks1= ticksAFT - ticksB4;

    /* for( i=0; i<m; i++ ) */
    /*    for( j=0; j<n; j++ ) */
    /* printf("D[%d]=%.16lf\n", j*m+i, D[j*m+i]); */


    c_time = (((double) clock ())/CLOCKS_PER_SEC) - timer;

    //  printf(" 1) C timer= %.5lf\n", c_time);                                  
    printf(" 1) ASM timer= %.5ld\n", ticks1 );
    //printf(" 1) ratio = %.5g\n", (double) ticks1/c_time );                     

    if( THRASHING )
      for( i=0; i<5000; i++ )
        for( j=0; j<5000; j++ )
          KICK[j*5000+i] += .0001;
  }


  return 0;
}

