// File: /workspace/github_c_makefile_star2_O2/ugobas[P]tnm/nma.c
// Function: Convert_cart2torsion1
int Convert_cart2torsion1(float *Tors_dev,
			  float *Masswtd_Tors_dev,
			  float *Cart_dev,
			  struct Reference Ref,
			  struct Jacobian *J)
{
  // Formula: (LL^t)Delta_theta = JM Delta_r  with:
  // L=T_sqrt (lower diagonal matrix if obtained from Cholevsky decomposition)
  // T=JMJ^t = LL^t
  // J is the jacobian matrix dr_int_i/d_theta_a
  // M_i is the diagonal mass matrix.
  // ==> L^t Delta_theta = L^{-1} J M Delta_r = Jtilde M Delta_r
  // To solve the equation:
  // Compute x=Jtilde MDelta_r =Masswtd_Tors
  // solve x=L^t Delta_theta (by backward substitution if T_sqrt lower diagonal)
  // Return the torsional fraction,
  // sum_i m_i (J d_theta)^2/sum_i m_i Dr_i^2

  if(J->Jtilde_ar==NULL)Compute_Jtilde(J);

  double sum=0; int i, j, a;

  // Compute Masswtd_Tors_dev = Jtilde M Delta_r
  for(a=0; a<J->N_axes; a++){
    float *Jt=J->Jtilde_ar[a]; sum=0;
    float *r=Cart_dev, *m=Ref.mass_coord;
    for(j=0; j<J->N_Cart; j++)sum+=m[j]*r[j]*Jt[j];
    Masswtd_Tors_dev[a]=sum;
  }
  if(J->T_sqrt_inv){
    // T_sqrt is not lower diagonal!
    for(a=0; a<J->N_axes; a++){
      sum=0;
      for(i=0; i<J->N_axes; i++)sum+=J->T_sqrt_inv[i][a]*Masswtd_Tors_dev[i];
      Tors_dev[a]=sum;
    }
  }else{
    // Exploit that T_sqrt is lower diagonal
    // Backward_substitution
    // theta_i =(x_i - sum_j>i L_ji x_j)/L_ii
    for(i=J->N_axes-1; i>=0; i--){
      Tors_dev[i]=Masswtd_Tors_dev[i];
      for(j=i+1; j<J->N_axes; j++)Tors_dev[i]-=Tors_dev[j]*J->T_sqrt[j][i];
      Tors_dev[i]/=J->T_sqrt[i][i];
    }
  }
  return(0);
}

// Assembly:
pushq %r15
pushq %r14
pushq %r13
pushq %r12
pushq %rbx
movq %rcx, %r15
movq %rdx, %r12
movq %rsi, %rbx
movq %rdi, %r14
leaq 0x30(%rsp), %r13
cmpq $0x0, 0x18(%rcx)
jne 0x23a26
movq %r15, %rdi
callq 0x209d5
movl (%r15), %eax
movq 0x18(%r13), %rdx
xorl %esi, %esi
testl %eax, %eax
movl $0x0, %ecx
cmovgl %eax, %ecx
xorl %edi, %edi
cmpq %rcx, %rdi
je 0x23a8c
movq 0x18(%r15), %r8
movq (%r8,%rdi,8), %r8
movl 0x4(%r15), %r9d
testl %r9d, %r9d
cmovlel %esi, %r9d
xorpd %xmm0, %xmm0
xorl %r10d, %r10d
cmpq %r10, %r9
je 0x23a7e
movss (%rdx,%r10,4), %xmm1
mulss (%r12,%r10,4), %xmm1
mulss (%r8,%r10,4), %xmm1
cvtss2sd %xmm1, %xmm1
addsd %xmm1, %xmm0
incq %r10
jmp 0x23a5a
cvtsd2ss %xmm0, %xmm0
movss %xmm0, (%rbx,%rdi,4)
incq %rdi
jmp 0x23a3b
movq 0x30(%r15), %rdx
testq %rdx, %rdx
je 0x23ad5
xorl %esi, %esi
cmpq %rcx, %rsi
je 0x23b35
xorps %xmm0, %xmm0
xorl %edi, %edi
cmpq %rdi, %rax
je 0x23ac6
movq (%rdx,%rdi,8), %r8
movss (%r8,%rsi,4), %xmm1
mulss (%rbx,%rdi,4), %xmm1
cvtss2sd %xmm1, %xmm1
addsd %xmm1, %xmm0
incq %rdi
jmp 0x23aa5
cvtsd2ss %xmm0, %xmm0
movss %xmm0, (%r14,%rsi,4)
incq %rsi
jmp 0x23a97
movq %rax, %rcx
testl %ecx, %ecx
jle 0x23b35
leaq -0x1(%rcx), %rdx
movss (%rbx,%rdx,4), %xmm0
movss %xmm0, (%r14,%rdx,4)
cvtss2sd %xmm0, %xmm0
cmpl %ecx, %eax
jle 0x23b19
cvtss2sd (%r14,%rcx,4), %xmm1
movq 0x28(%r15), %rsi
movq (%rsi,%rcx,8), %rsi
mulsd (%rsi,%rdx,8), %xmm1
subsd %xmm1, %xmm0
cvtsd2ss %xmm0, %xmm0
movss %xmm0, (%r14,%rdx,4)
incq %rcx
jmp 0x23aeb
movq 0x28(%r15), %rcx
movq (%rcx,%rdx,8), %rcx
divsd (%rcx,%rdx,8), %xmm0
cvtsd2ss %xmm0, %xmm0
movss %xmm0, (%r14,%rdx,4)
movq %rdx, %rcx
jmp 0x23ad8
xorl %eax, %eax
popq %rbx
popq %r12
popq %r13
popq %r14
popq %r15
retq