// File: /workspace/github_c_makefile_star2_O0/guszejnovdavid[P]MISFIT/trilinear_interpol.c
// Function: trilinear_interp(double, double, double, double const*, int, int, int, double, double, double, double, double, double, int, double)
double trilinear_interp(double X, double Y, double Z, const double *tbl, 
      const int N_X, const int N_Y, const int N_Z,
      const double X_MIN, const double X_MAX, 
      const double Y_MIN, const double Y_MAX,
      const double Z_MIN, const double Z_MAX,
      const int OUT_OF_DOMAIN, const double OUT_OF_DOMAIN_VALUE)
{

  double f111,f211,f212,f112, f121,f221,f222,f122;
  double X_A,X_B,Y_A,Y_B,Z_A,Z_B;

/* grid spacing */
  const double delta_X = (X_MAX-X_MIN)/(N_X-1);
  const double delta_Y = (Y_MAX-Y_MIN)/(N_Y-1);
  const double delta_Z = (Z_MAX-Z_MIN)/(N_Z-1);
 
  const double delta_X_inv = (N_X-1)/(X_MAX-X_MIN);
  const double delta_Y_inv = (N_Y-1)/(Y_MAX-Y_MIN);
  const double delta_Z_inv = (N_Z-1)/(Z_MAX-Z_MIN);
  int i,j,k;
  double X_unit, Y_unit, Z_unit;


  /* select upper right grid point BUG!!!!!! randomly (but very rarely) 
 sometimes select WRONG point!!!*/
  i = (int) ceil( (X-X_MIN)*delta_X_inv);
  j = (int) ceil( (Y-Y_MIN)*delta_Y_inv);
  k = (int) ceil( (Z-Z_MIN)*delta_Z_inv);

/* Return OUT_OF_DOMAIN_VALUE if X or Y or Z are under/overflown */
/* edge of the domain and out-of-range values */
   if( OUT_OF_DOMAIN==0 ) 
   {
     if( (X<X_MIN) || (Y<Y_MIN) || (Z<Z_MIN) || (X>X_MAX) || (Y>Y_MAX) || (Z>Z_MAX) ) return OUT_OF_DOMAIN_VALUE;
   };
   
/* cell corner values */ 
// f222=TBL[i][j][k] declared as double TBL[N_X+1][N_Y+1][N_Z+1]; tbl=&TBL[0][0][0]

  f111 = *(tbl+(N_Z)*(N_Y)*(i-1)+(N_Z)*(j-1)+k-1)   ; //TBL[i-1][j-1][k-1];
  f211 = *(tbl+(N_Z)*(N_Y)*i+(N_Z)*(j-1)+k-1)   ;// TBL[i][j-1][k-1];
  f212 = *(tbl+(N_Z)*(N_Y)*i+(N_Z)*(j-1)+k)   ;//TBL[i][j-1][k];
  f112 = *(tbl+(N_Z)*(N_Y)*(i-1)+(N_Z)*(j-1)+k)   ;//TBL[i-1][j-1][k];
  f121 = *(tbl+(N_Z)*(N_Y)*(i-1)+(N_Z)*j+k-1);    //TBL[i-1][j][k-1];
  f221 = *(tbl+(N_Z)*(N_Y)*i+(N_Z)*j+k-1);  //TBL[i][j][k-1];
  f222 = *(tbl+(N_Z)*(N_Y)*i+(N_Z)*j+k)   ; //TBL[i][j][k];
  f122 = *(tbl+(N_Z)*(N_Y)*(i-1)+(N_Z)*j+k); //TBL[i-1][j][k];

  X_A = X_MIN + (i-1)*delta_X;    
  X_B = X_MIN + i*delta_X;    
  
  Y_A = Y_MIN + (j-1)*delta_Y;
  Y_B = Y_MIN + j*delta_Y;

  Z_A = Z_MIN + (k-1)*delta_Z;
  Z_B = Z_MIN + k*delta_Z;


/* Rescalling to unit cube {0,1}^3 */
  X_unit = (X-X_A)/(X_B-X_A);
  Y_unit = (Y-Y_A)/(Y_B-Y_A);
  Z_unit = (Z-Z_A)/(Z_B-Z_A);

  return trilinear_interp_unit_cube(X_unit,Y_unit,Z_unit, f111,f211,f212,f112,f121,f221,f222,f122);

}

// Assembly:
subq $0x148, %rsp            # imm = 0x148
movsd 0x158(%rsp), %xmm8
movsd 0x150(%rsp), %xmm8
movsd %xmm0, 0x138(%rsp)
movsd %xmm1, 0x130(%rsp)
movsd %xmm2, 0x128(%rsp)
movq %rdi, 0x120(%rsp)
movl %esi, 0x11c(%rsp)
movl %edx, 0x118(%rsp)
movl %ecx, 0x114(%rsp)
movsd %xmm3, 0x108(%rsp)
movsd %xmm4, 0x100(%rsp)
movsd %xmm5, 0xf8(%rsp)
movsd %xmm6, 0xf0(%rsp)
movsd %xmm7, 0xe8(%rsp)
movl %r8d, 0xe4(%rsp)
movsd 0x100(%rsp), %xmm0
subsd 0x108(%rsp), %xmm0
movl 0x11c(%rsp), %eax
subl $0x1, %eax
cvtsi2sd %eax, %xmm1
divsd %xmm1, %xmm0
movsd %xmm0, 0x68(%rsp)
movsd 0xf0(%rsp), %xmm0
subsd 0xf8(%rsp), %xmm0
movl 0x118(%rsp), %eax
subl $0x1, %eax
cvtsi2sd %eax, %xmm1
divsd %xmm1, %xmm0
movsd %xmm0, 0x60(%rsp)
movsd 0x150(%rsp), %xmm0
subsd 0xe8(%rsp), %xmm0
movl 0x114(%rsp), %eax
subl $0x1, %eax
cvtsi2sd %eax, %xmm1
divsd %xmm1, %xmm0
movsd %xmm0, 0x58(%rsp)
movl 0x11c(%rsp), %eax
subl $0x1, %eax
cvtsi2sd %eax, %xmm0
movsd 0x100(%rsp), %xmm1
subsd 0x108(%rsp), %xmm1
divsd %xmm1, %xmm0
movsd %xmm0, 0x50(%rsp)
movl 0x118(%rsp), %eax
subl $0x1, %eax
cvtsi2sd %eax, %xmm0
movsd 0xf0(%rsp), %xmm1
subsd 0xf8(%rsp), %xmm1
divsd %xmm1, %xmm0
movsd %xmm0, 0x48(%rsp)
movl 0x114(%rsp), %eax
subl $0x1, %eax
cvtsi2sd %eax, %xmm0
movsd 0x150(%rsp), %xmm1
subsd 0xe8(%rsp), %xmm1
divsd %xmm1, %xmm0
movsd %xmm0, 0x40(%rsp)
movsd 0x138(%rsp), %xmm0
subsd 0x108(%rsp), %xmm0
mulsd 0x50(%rsp), %xmm0
callq 0x80f0
cvttsd2si %xmm0, %eax
movl %eax, 0x3c(%rsp)
movsd 0x130(%rsp), %xmm0
subsd 0xf8(%rsp), %xmm0
mulsd 0x48(%rsp), %xmm0
callq 0x80f0
cvttsd2si %xmm0, %eax
movl %eax, 0x38(%rsp)
movsd 0x128(%rsp), %xmm0
subsd 0xe8(%rsp), %xmm0
mulsd 0x40(%rsp), %xmm0
callq 0x80f0
cvttsd2si %xmm0, %eax
movl %eax, 0x34(%rsp)
cmpl $0x0, 0xe4(%rsp)
jne 0x1ab1e
movsd 0x138(%rsp), %xmm1
movsd 0x108(%rsp), %xmm0
ucomisd %xmm1, %xmm0
ja 0x1ab05
movsd 0x130(%rsp), %xmm1
movsd 0xf8(%rsp), %xmm0
ucomisd %xmm1, %xmm0
ja 0x1ab05
movsd 0x128(%rsp), %xmm1
movsd 0xe8(%rsp), %xmm0
ucomisd %xmm1, %xmm0
ja 0x1ab05
movsd 0x138(%rsp), %xmm0
ucomisd 0x100(%rsp), %xmm0
ja 0x1ab05
movsd 0x130(%rsp), %xmm0
ucomisd 0xf0(%rsp), %xmm0
ja 0x1ab05
movsd 0x128(%rsp), %xmm0
ucomisd 0x150(%rsp), %xmm0
jbe 0x1ab1c
movsd 0x158(%rsp), %xmm0
movsd %xmm0, 0x140(%rsp)
jmp 0x1afaf
jmp 0x1ab1e
movq 0x120(%rsp), %rax
movl 0x114(%rsp), %ecx
imull 0x118(%rsp), %ecx
movl 0x3c(%rsp), %edx
subl $0x1, %edx
imull %edx, %ecx
movslq %ecx, %rcx
shlq $0x3, %rcx
addq %rcx, %rax
movl 0x114(%rsp), %ecx
movl 0x38(%rsp), %edx
subl $0x1, %edx
imull %edx, %ecx
movslq %ecx, %rcx
shlq $0x3, %rcx
addq %rcx, %rax
movslq 0x34(%rsp), %rcx
movsd -0x8(%rax,%rcx,8), %xmm0
movsd %xmm0, 0xd8(%rsp)
movq 0x120(%rsp), %rax
movl 0x114(%rsp), %ecx
imull 0x118(%rsp), %ecx
imull 0x3c(%rsp), %ecx
movslq %ecx, %rcx
shlq $0x3, %rcx
addq %rcx, %rax
movl 0x114(%rsp), %ecx
movl 0x38(%rsp), %edx
subl $0x1, %edx
imull %edx, %ecx
movslq %ecx, %rcx
shlq $0x3, %rcx
addq %rcx, %rax
movslq 0x34(%rsp), %rcx
movsd -0x8(%rax,%rcx,8), %xmm0
movsd %xmm0, 0xd0(%rsp)
movq 0x120(%rsp), %rax
movl 0x114(%rsp), %ecx
imull 0x118(%rsp), %ecx
imull 0x3c(%rsp), %ecx
movslq %ecx, %rcx
shlq $0x3, %rcx
addq %rcx, %rax
movl 0x114(%rsp), %ecx
movl 0x38(%rsp), %edx
subl $0x1, %edx
imull %edx, %ecx
movslq %ecx, %rcx
shlq $0x3, %rcx
addq %rcx, %rax
movslq 0x34(%rsp), %rcx
movsd (%rax,%rcx,8), %xmm0
movsd %xmm0, 0xc8(%rsp)
movq 0x120(%rsp), %rax
movl 0x114(%rsp), %ecx
imull 0x118(%rsp), %ecx
movl 0x3c(%rsp), %edx
subl $0x1, %edx
imull %edx, %ecx
movslq %ecx, %rcx
shlq $0x3, %rcx
addq %rcx, %rax
movl 0x114(%rsp), %ecx
movl 0x38(%rsp), %edx
subl $0x1, %edx
imull %edx, %ecx
movslq %ecx, %rcx
shlq $0x3, %rcx
addq %rcx, %rax
movslq 0x34(%rsp), %rcx
movsd (%rax,%rcx,8), %xmm0
movsd %xmm0, 0xc0(%rsp)
movq 0x120(%rsp), %rax
movl 0x114(%rsp), %ecx
imull 0x118(%rsp), %ecx
movl 0x3c(%rsp), %edx
subl $0x1, %edx
imull %edx, %ecx
movslq %ecx, %rcx
shlq $0x3, %rcx
addq %rcx, %rax
movl 0x114(%rsp), %ecx
imull 0x38(%rsp), %ecx
movslq %ecx, %rcx
shlq $0x3, %rcx
addq %rcx, %rax
movslq 0x34(%rsp), %rcx
movsd -0x8(%rax,%rcx,8), %xmm0
movsd %xmm0, 0xb8(%rsp)
movq 0x120(%rsp), %rax
movl 0x114(%rsp), %ecx
imull 0x118(%rsp), %ecx
imull 0x3c(%rsp), %ecx
movslq %ecx, %rcx
shlq $0x3, %rcx
addq %rcx, %rax
movl 0x114(%rsp), %ecx
imull 0x38(%rsp), %ecx
movslq %ecx, %rcx
shlq $0x3, %rcx
addq %rcx, %rax
movslq 0x34(%rsp), %rcx
movsd -0x8(%rax,%rcx,8), %xmm0
movsd %xmm0, 0xb0(%rsp)
movq 0x120(%rsp), %rax
movl 0x114(%rsp), %ecx
imull 0x118(%rsp), %ecx
imull 0x3c(%rsp), %ecx
movslq %ecx, %rcx
shlq $0x3, %rcx
addq %rcx, %rax
movl 0x114(%rsp), %ecx
imull 0x38(%rsp), %ecx
movslq %ecx, %rcx
shlq $0x3, %rcx
addq %rcx, %rax
movslq 0x34(%rsp), %rcx
movsd (%rax,%rcx,8), %xmm0
movsd %xmm0, 0xa8(%rsp)
movq 0x120(%rsp), %rax
movl 0x114(%rsp), %ecx
imull 0x118(%rsp), %ecx
movl 0x3c(%rsp), %edx
subl $0x1, %edx
imull %edx, %ecx
movslq %ecx, %rcx
shlq $0x3, %rcx
addq %rcx, %rax
movl 0x114(%rsp), %ecx
imull 0x38(%rsp), %ecx
movslq %ecx, %rcx
shlq $0x3, %rcx
addq %rcx, %rax
movslq 0x34(%rsp), %rcx
movsd (%rax,%rcx,8), %xmm0
movsd %xmm0, 0xa0(%rsp)
movsd 0x108(%rsp), %xmm1
movl 0x3c(%rsp), %eax
subl $0x1, %eax
cvtsi2sd %eax, %xmm0
movsd 0x68(%rsp), %xmm2
mulsd %xmm2, %xmm0
addsd %xmm1, %xmm0
movsd %xmm0, 0x98(%rsp)
movsd 0x108(%rsp), %xmm1
cvtsi2sdl 0x3c(%rsp), %xmm0
movsd 0x68(%rsp), %xmm2
mulsd %xmm2, %xmm0
addsd %xmm1, %xmm0
movsd %xmm0, 0x90(%rsp)
movsd 0xf8(%rsp), %xmm1
movl 0x38(%rsp), %eax
subl $0x1, %eax
cvtsi2sd %eax, %xmm0
movsd 0x60(%rsp), %xmm2
mulsd %xmm2, %xmm0
addsd %xmm1, %xmm0
movsd %xmm0, 0x88(%rsp)
movsd 0xf8(%rsp), %xmm1
cvtsi2sdl 0x38(%rsp), %xmm0
movsd 0x60(%rsp), %xmm2
mulsd %xmm2, %xmm0
addsd %xmm1, %xmm0
movsd %xmm0, 0x80(%rsp)
movsd 0xe8(%rsp), %xmm1
movl 0x34(%rsp), %eax
subl $0x1, %eax
cvtsi2sd %eax, %xmm0
movsd 0x58(%rsp), %xmm2
mulsd %xmm2, %xmm0
addsd %xmm1, %xmm0
movsd %xmm0, 0x78(%rsp)
movsd 0xe8(%rsp), %xmm1
cvtsi2sdl 0x34(%rsp), %xmm0
movsd 0x58(%rsp), %xmm2
mulsd %xmm2, %xmm0
addsd %xmm1, %xmm0
movsd %xmm0, 0x70(%rsp)
movsd 0x138(%rsp), %xmm0
subsd 0x98(%rsp), %xmm0
movsd 0x90(%rsp), %xmm1
subsd 0x98(%rsp), %xmm1
divsd %xmm1, %xmm0
movsd %xmm0, 0x28(%rsp)
movsd 0x130(%rsp), %xmm0
subsd 0x88(%rsp), %xmm0
movsd 0x80(%rsp), %xmm1
subsd 0x88(%rsp), %xmm1
divsd %xmm1, %xmm0
movsd %xmm0, 0x20(%rsp)
movsd 0x128(%rsp), %xmm0
subsd 0x78(%rsp), %xmm0
movsd 0x70(%rsp), %xmm1
subsd 0x78(%rsp), %xmm1
divsd %xmm1, %xmm0
movsd %xmm0, 0x18(%rsp)
movsd 0x28(%rsp), %xmm0
movsd 0x20(%rsp), %xmm1
movsd 0x18(%rsp), %xmm2
movsd 0xd8(%rsp), %xmm3
movsd 0xd0(%rsp), %xmm4
movsd 0xc8(%rsp), %xmm5
movsd 0xc0(%rsp), %xmm6
movsd 0xb8(%rsp), %xmm7
movsd 0xb0(%rsp), %xmm10
movsd 0xa8(%rsp), %xmm9
movsd 0xa0(%rsp), %xmm8
movsd %xmm10, (%rsp)
movsd %xmm9, 0x8(%rsp)
movsd %xmm8, 0x10(%rsp)
callq 0x1afc0
movsd %xmm0, 0x140(%rsp)
movsd 0x140(%rsp), %xmm0
addq $0x148, %rsp            # imm = 0x148
retq