7aca3b5a34abc3722234721a048cb97e25860b95
[alexxy/gromacs.git] / src / gromacs / gmxlib / nonbonded / nb_kernel_avx_256_double / nb_kernel_ElecRF_VdwLJ_GeomW4W4_avx_256_double.c
1 /*
2  * This file is part of the GROMACS molecular simulation package.
3  *
4  * Copyright (c) 2012,2013,2014, by the GROMACS development team, led by
5  * Mark Abraham, David van der Spoel, Berk Hess, and Erik Lindahl,
6  * and including many others, as listed in the AUTHORS file in the
7  * top-level source directory and at http://www.gromacs.org.
8  *
9  * GROMACS is free software; you can redistribute it and/or
10  * modify it under the terms of the GNU Lesser General Public License
11  * as published by the Free Software Foundation; either version 2.1
12  * of the License, or (at your option) any later version.
13  *
14  * GROMACS is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
17  * Lesser General Public License for more details.
18  *
19  * You should have received a copy of the GNU Lesser General Public
20  * License along with GROMACS; if not, see
21  * http://www.gnu.org/licenses, or write to the Free Software Foundation,
22  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA.
23  *
24  * If you want to redistribute modifications to GROMACS, please
25  * consider that scientific software is very special. Version
26  * control is crucial - bugs must be traceable. We will be happy to
27  * consider code for inclusion in the official distribution, but
28  * derived work must not be called official GROMACS. Details are found
29  * in the README & COPYING files - if they are missing, get the
30  * official version at http://www.gromacs.org.
31  *
32  * To help us fund GROMACS development, we humbly ask that you cite
33  * the research papers on the package. Check out http://www.gromacs.org.
34  */
35 /*
36  * Note: this file was generated by the GROMACS avx_256_double kernel generator.
37  */
38 #include "config.h"
39
40 #include <math.h>
41
42 #include "../nb_kernel.h"
43 #include "types/simple.h"
44 #include "gromacs/math/vec.h"
45 #include "nrnb.h"
46
47 #include "gromacs/simd/math_x86_avx_256_double.h"
48 #include "kernelutil_x86_avx_256_double.h"
49
50 /*
51  * Gromacs nonbonded kernel:   nb_kernel_ElecRF_VdwLJ_GeomW4W4_VF_avx_256_double
52  * Electrostatics interaction: ReactionField
53  * VdW interaction:            LennardJones
54  * Geometry:                   Water4-Water4
55  * Calculate force/pot:        PotentialAndForce
56  */
57 void
58 nb_kernel_ElecRF_VdwLJ_GeomW4W4_VF_avx_256_double
59                     (t_nblist                    * gmx_restrict       nlist,
60                      rvec                        * gmx_restrict          xx,
61                      rvec                        * gmx_restrict          ff,
62                      t_forcerec                  * gmx_restrict          fr,
63                      t_mdatoms                   * gmx_restrict     mdatoms,
64                      nb_kernel_data_t gmx_unused * gmx_restrict kernel_data,
65                      t_nrnb                      * gmx_restrict        nrnb)
66 {
67     /* Suffixes 0,1,2,3 refer to particle indices for waters in the inner or outer loop, or 
68      * just 0 for non-waters.
69      * Suffixes A,B,C,D refer to j loop unrolling done with AVX, e.g. for the four different
70      * jnr indices corresponding to data put in the four positions in the SIMD register.
71      */
72     int              i_shift_offset,i_coord_offset,outeriter,inneriter;
73     int              j_index_start,j_index_end,jidx,nri,inr,ggid,iidx;
74     int              jnrA,jnrB,jnrC,jnrD;
75     int              jnrlistA,jnrlistB,jnrlistC,jnrlistD;
76     int              jnrlistE,jnrlistF,jnrlistG,jnrlistH;
77     int              j_coord_offsetA,j_coord_offsetB,j_coord_offsetC,j_coord_offsetD;
78     int              *iinr,*jindex,*jjnr,*shiftidx,*gid;
79     real             rcutoff_scalar;
80     real             *shiftvec,*fshift,*x,*f;
81     real             *fjptrA,*fjptrB,*fjptrC,*fjptrD;
82     real             scratch[4*DIM];
83     __m256d          tx,ty,tz,fscal,rcutoff,rcutoff2,jidxall;
84     real *           vdwioffsetptr0;
85     __m256d          ix0,iy0,iz0,fix0,fiy0,fiz0,iq0,isai0;
86     real *           vdwioffsetptr1;
87     __m256d          ix1,iy1,iz1,fix1,fiy1,fiz1,iq1,isai1;
88     real *           vdwioffsetptr2;
89     __m256d          ix2,iy2,iz2,fix2,fiy2,fiz2,iq2,isai2;
90     real *           vdwioffsetptr3;
91     __m256d          ix3,iy3,iz3,fix3,fiy3,fiz3,iq3,isai3;
92     int              vdwjidx0A,vdwjidx0B,vdwjidx0C,vdwjidx0D;
93     __m256d          jx0,jy0,jz0,fjx0,fjy0,fjz0,jq0,isaj0;
94     int              vdwjidx1A,vdwjidx1B,vdwjidx1C,vdwjidx1D;
95     __m256d          jx1,jy1,jz1,fjx1,fjy1,fjz1,jq1,isaj1;
96     int              vdwjidx2A,vdwjidx2B,vdwjidx2C,vdwjidx2D;
97     __m256d          jx2,jy2,jz2,fjx2,fjy2,fjz2,jq2,isaj2;
98     int              vdwjidx3A,vdwjidx3B,vdwjidx3C,vdwjidx3D;
99     __m256d          jx3,jy3,jz3,fjx3,fjy3,fjz3,jq3,isaj3;
100     __m256d          dx00,dy00,dz00,rsq00,rinv00,rinvsq00,r00,qq00,c6_00,c12_00;
101     __m256d          dx11,dy11,dz11,rsq11,rinv11,rinvsq11,r11,qq11,c6_11,c12_11;
102     __m256d          dx12,dy12,dz12,rsq12,rinv12,rinvsq12,r12,qq12,c6_12,c12_12;
103     __m256d          dx13,dy13,dz13,rsq13,rinv13,rinvsq13,r13,qq13,c6_13,c12_13;
104     __m256d          dx21,dy21,dz21,rsq21,rinv21,rinvsq21,r21,qq21,c6_21,c12_21;
105     __m256d          dx22,dy22,dz22,rsq22,rinv22,rinvsq22,r22,qq22,c6_22,c12_22;
106     __m256d          dx23,dy23,dz23,rsq23,rinv23,rinvsq23,r23,qq23,c6_23,c12_23;
107     __m256d          dx31,dy31,dz31,rsq31,rinv31,rinvsq31,r31,qq31,c6_31,c12_31;
108     __m256d          dx32,dy32,dz32,rsq32,rinv32,rinvsq32,r32,qq32,c6_32,c12_32;
109     __m256d          dx33,dy33,dz33,rsq33,rinv33,rinvsq33,r33,qq33,c6_33,c12_33;
110     __m256d          velec,felec,velecsum,facel,crf,krf,krf2;
111     real             *charge;
112     int              nvdwtype;
113     __m256d          rinvsix,rvdw,vvdw,vvdw6,vvdw12,fvdw,fvdw6,fvdw12,vvdwsum,sh_vdw_invrcut6;
114     int              *vdwtype;
115     real             *vdwparam;
116     __m256d          one_sixth   = _mm256_set1_pd(1.0/6.0);
117     __m256d          one_twelfth = _mm256_set1_pd(1.0/12.0);
118     __m256d          dummy_mask,cutoff_mask;
119     __m128           tmpmask0,tmpmask1;
120     __m256d          signbit = _mm256_castsi256_pd( _mm256_set1_epi32(0x80000000) );
121     __m256d          one     = _mm256_set1_pd(1.0);
122     __m256d          two     = _mm256_set1_pd(2.0);
123     x                = xx[0];
124     f                = ff[0];
125
126     nri              = nlist->nri;
127     iinr             = nlist->iinr;
128     jindex           = nlist->jindex;
129     jjnr             = nlist->jjnr;
130     shiftidx         = nlist->shift;
131     gid              = nlist->gid;
132     shiftvec         = fr->shift_vec[0];
133     fshift           = fr->fshift[0];
134     facel            = _mm256_set1_pd(fr->epsfac);
135     charge           = mdatoms->chargeA;
136     krf              = _mm256_set1_pd(fr->ic->k_rf);
137     krf2             = _mm256_set1_pd(fr->ic->k_rf*2.0);
138     crf              = _mm256_set1_pd(fr->ic->c_rf);
139     nvdwtype         = fr->ntype;
140     vdwparam         = fr->nbfp;
141     vdwtype          = mdatoms->typeA;
142
143     /* Setup water-specific parameters */
144     inr              = nlist->iinr[0];
145     iq1              = _mm256_mul_pd(facel,_mm256_set1_pd(charge[inr+1]));
146     iq2              = _mm256_mul_pd(facel,_mm256_set1_pd(charge[inr+2]));
147     iq3              = _mm256_mul_pd(facel,_mm256_set1_pd(charge[inr+3]));
148     vdwioffsetptr0   = vdwparam+2*nvdwtype*vdwtype[inr+0];
149
150     jq1              = _mm256_set1_pd(charge[inr+1]);
151     jq2              = _mm256_set1_pd(charge[inr+2]);
152     jq3              = _mm256_set1_pd(charge[inr+3]);
153     vdwjidx0A        = 2*vdwtype[inr+0];
154     c6_00            = _mm256_set1_pd(vdwioffsetptr0[vdwjidx0A]);
155     c12_00           = _mm256_set1_pd(vdwioffsetptr0[vdwjidx0A+1]);
156     qq11             = _mm256_mul_pd(iq1,jq1);
157     qq12             = _mm256_mul_pd(iq1,jq2);
158     qq13             = _mm256_mul_pd(iq1,jq3);
159     qq21             = _mm256_mul_pd(iq2,jq1);
160     qq22             = _mm256_mul_pd(iq2,jq2);
161     qq23             = _mm256_mul_pd(iq2,jq3);
162     qq31             = _mm256_mul_pd(iq3,jq1);
163     qq32             = _mm256_mul_pd(iq3,jq2);
164     qq33             = _mm256_mul_pd(iq3,jq3);
165
166     /* Avoid stupid compiler warnings */
167     jnrA = jnrB = jnrC = jnrD = 0;
168     j_coord_offsetA = 0;
169     j_coord_offsetB = 0;
170     j_coord_offsetC = 0;
171     j_coord_offsetD = 0;
172
173     outeriter        = 0;
174     inneriter        = 0;
175
176     for(iidx=0;iidx<4*DIM;iidx++)
177     {
178         scratch[iidx] = 0.0;
179     }
180
181     /* Start outer loop over neighborlists */
182     for(iidx=0; iidx<nri; iidx++)
183     {
184         /* Load shift vector for this list */
185         i_shift_offset   = DIM*shiftidx[iidx];
186
187         /* Load limits for loop over neighbors */
188         j_index_start    = jindex[iidx];
189         j_index_end      = jindex[iidx+1];
190
191         /* Get outer coordinate index */
192         inr              = iinr[iidx];
193         i_coord_offset   = DIM*inr;
194
195         /* Load i particle coords and add shift vector */
196         gmx_mm256_load_shift_and_4rvec_broadcast_pd(shiftvec+i_shift_offset,x+i_coord_offset,
197                                                     &ix0,&iy0,&iz0,&ix1,&iy1,&iz1,&ix2,&iy2,&iz2,&ix3,&iy3,&iz3);
198
199         fix0             = _mm256_setzero_pd();
200         fiy0             = _mm256_setzero_pd();
201         fiz0             = _mm256_setzero_pd();
202         fix1             = _mm256_setzero_pd();
203         fiy1             = _mm256_setzero_pd();
204         fiz1             = _mm256_setzero_pd();
205         fix2             = _mm256_setzero_pd();
206         fiy2             = _mm256_setzero_pd();
207         fiz2             = _mm256_setzero_pd();
208         fix3             = _mm256_setzero_pd();
209         fiy3             = _mm256_setzero_pd();
210         fiz3             = _mm256_setzero_pd();
211
212         /* Reset potential sums */
213         velecsum         = _mm256_setzero_pd();
214         vvdwsum          = _mm256_setzero_pd();
215
216         /* Start inner kernel loop */
217         for(jidx=j_index_start; jidx<j_index_end && jjnr[jidx+3]>=0; jidx+=4)
218         {
219
220             /* Get j neighbor index, and coordinate index */
221             jnrA             = jjnr[jidx];
222             jnrB             = jjnr[jidx+1];
223             jnrC             = jjnr[jidx+2];
224             jnrD             = jjnr[jidx+3];
225             j_coord_offsetA  = DIM*jnrA;
226             j_coord_offsetB  = DIM*jnrB;
227             j_coord_offsetC  = DIM*jnrC;
228             j_coord_offsetD  = DIM*jnrD;
229
230             /* load j atom coordinates */
231             gmx_mm256_load_4rvec_4ptr_swizzle_pd(x+j_coord_offsetA,x+j_coord_offsetB,
232                                                  x+j_coord_offsetC,x+j_coord_offsetD,
233                                                  &jx0,&jy0,&jz0,&jx1,&jy1,&jz1,&jx2,
234                                                  &jy2,&jz2,&jx3,&jy3,&jz3);
235
236             /* Calculate displacement vector */
237             dx00             = _mm256_sub_pd(ix0,jx0);
238             dy00             = _mm256_sub_pd(iy0,jy0);
239             dz00             = _mm256_sub_pd(iz0,jz0);
240             dx11             = _mm256_sub_pd(ix1,jx1);
241             dy11             = _mm256_sub_pd(iy1,jy1);
242             dz11             = _mm256_sub_pd(iz1,jz1);
243             dx12             = _mm256_sub_pd(ix1,jx2);
244             dy12             = _mm256_sub_pd(iy1,jy2);
245             dz12             = _mm256_sub_pd(iz1,jz2);
246             dx13             = _mm256_sub_pd(ix1,jx3);
247             dy13             = _mm256_sub_pd(iy1,jy3);
248             dz13             = _mm256_sub_pd(iz1,jz3);
249             dx21             = _mm256_sub_pd(ix2,jx1);
250             dy21             = _mm256_sub_pd(iy2,jy1);
251             dz21             = _mm256_sub_pd(iz2,jz1);
252             dx22             = _mm256_sub_pd(ix2,jx2);
253             dy22             = _mm256_sub_pd(iy2,jy2);
254             dz22             = _mm256_sub_pd(iz2,jz2);
255             dx23             = _mm256_sub_pd(ix2,jx3);
256             dy23             = _mm256_sub_pd(iy2,jy3);
257             dz23             = _mm256_sub_pd(iz2,jz3);
258             dx31             = _mm256_sub_pd(ix3,jx1);
259             dy31             = _mm256_sub_pd(iy3,jy1);
260             dz31             = _mm256_sub_pd(iz3,jz1);
261             dx32             = _mm256_sub_pd(ix3,jx2);
262             dy32             = _mm256_sub_pd(iy3,jy2);
263             dz32             = _mm256_sub_pd(iz3,jz2);
264             dx33             = _mm256_sub_pd(ix3,jx3);
265             dy33             = _mm256_sub_pd(iy3,jy3);
266             dz33             = _mm256_sub_pd(iz3,jz3);
267
268             /* Calculate squared distance and things based on it */
269             rsq00            = gmx_mm256_calc_rsq_pd(dx00,dy00,dz00);
270             rsq11            = gmx_mm256_calc_rsq_pd(dx11,dy11,dz11);
271             rsq12            = gmx_mm256_calc_rsq_pd(dx12,dy12,dz12);
272             rsq13            = gmx_mm256_calc_rsq_pd(dx13,dy13,dz13);
273             rsq21            = gmx_mm256_calc_rsq_pd(dx21,dy21,dz21);
274             rsq22            = gmx_mm256_calc_rsq_pd(dx22,dy22,dz22);
275             rsq23            = gmx_mm256_calc_rsq_pd(dx23,dy23,dz23);
276             rsq31            = gmx_mm256_calc_rsq_pd(dx31,dy31,dz31);
277             rsq32            = gmx_mm256_calc_rsq_pd(dx32,dy32,dz32);
278             rsq33            = gmx_mm256_calc_rsq_pd(dx33,dy33,dz33);
279
280             rinv11           = gmx_mm256_invsqrt_pd(rsq11);
281             rinv12           = gmx_mm256_invsqrt_pd(rsq12);
282             rinv13           = gmx_mm256_invsqrt_pd(rsq13);
283             rinv21           = gmx_mm256_invsqrt_pd(rsq21);
284             rinv22           = gmx_mm256_invsqrt_pd(rsq22);
285             rinv23           = gmx_mm256_invsqrt_pd(rsq23);
286             rinv31           = gmx_mm256_invsqrt_pd(rsq31);
287             rinv32           = gmx_mm256_invsqrt_pd(rsq32);
288             rinv33           = gmx_mm256_invsqrt_pd(rsq33);
289
290             rinvsq00         = gmx_mm256_inv_pd(rsq00);
291             rinvsq11         = _mm256_mul_pd(rinv11,rinv11);
292             rinvsq12         = _mm256_mul_pd(rinv12,rinv12);
293             rinvsq13         = _mm256_mul_pd(rinv13,rinv13);
294             rinvsq21         = _mm256_mul_pd(rinv21,rinv21);
295             rinvsq22         = _mm256_mul_pd(rinv22,rinv22);
296             rinvsq23         = _mm256_mul_pd(rinv23,rinv23);
297             rinvsq31         = _mm256_mul_pd(rinv31,rinv31);
298             rinvsq32         = _mm256_mul_pd(rinv32,rinv32);
299             rinvsq33         = _mm256_mul_pd(rinv33,rinv33);
300
301             fjx0             = _mm256_setzero_pd();
302             fjy0             = _mm256_setzero_pd();
303             fjz0             = _mm256_setzero_pd();
304             fjx1             = _mm256_setzero_pd();
305             fjy1             = _mm256_setzero_pd();
306             fjz1             = _mm256_setzero_pd();
307             fjx2             = _mm256_setzero_pd();
308             fjy2             = _mm256_setzero_pd();
309             fjz2             = _mm256_setzero_pd();
310             fjx3             = _mm256_setzero_pd();
311             fjy3             = _mm256_setzero_pd();
312             fjz3             = _mm256_setzero_pd();
313
314             /**************************
315              * CALCULATE INTERACTIONS *
316              **************************/
317
318             /* LENNARD-JONES DISPERSION/REPULSION */
319
320             rinvsix          = _mm256_mul_pd(_mm256_mul_pd(rinvsq00,rinvsq00),rinvsq00);
321             vvdw6            = _mm256_mul_pd(c6_00,rinvsix);
322             vvdw12           = _mm256_mul_pd(c12_00,_mm256_mul_pd(rinvsix,rinvsix));
323             vvdw             = _mm256_sub_pd( _mm256_mul_pd(vvdw12,one_twelfth) , _mm256_mul_pd(vvdw6,one_sixth) );
324             fvdw             = _mm256_mul_pd(_mm256_sub_pd(vvdw12,vvdw6),rinvsq00);
325
326             /* Update potential sum for this i atom from the interaction with this j atom. */
327             vvdwsum          = _mm256_add_pd(vvdwsum,vvdw);
328
329             fscal            = fvdw;
330
331             /* Calculate temporary vectorial force */
332             tx               = _mm256_mul_pd(fscal,dx00);
333             ty               = _mm256_mul_pd(fscal,dy00);
334             tz               = _mm256_mul_pd(fscal,dz00);
335
336             /* Update vectorial force */
337             fix0             = _mm256_add_pd(fix0,tx);
338             fiy0             = _mm256_add_pd(fiy0,ty);
339             fiz0             = _mm256_add_pd(fiz0,tz);
340
341             fjx0             = _mm256_add_pd(fjx0,tx);
342             fjy0             = _mm256_add_pd(fjy0,ty);
343             fjz0             = _mm256_add_pd(fjz0,tz);
344
345             /**************************
346              * CALCULATE INTERACTIONS *
347              **************************/
348
349             /* REACTION-FIELD ELECTROSTATICS */
350             velec            = _mm256_mul_pd(qq11,_mm256_sub_pd(_mm256_add_pd(rinv11,_mm256_mul_pd(krf,rsq11)),crf));
351             felec            = _mm256_mul_pd(qq11,_mm256_sub_pd(_mm256_mul_pd(rinv11,rinvsq11),krf2));
352
353             /* Update potential sum for this i atom from the interaction with this j atom. */
354             velecsum         = _mm256_add_pd(velecsum,velec);
355
356             fscal            = felec;
357
358             /* Calculate temporary vectorial force */
359             tx               = _mm256_mul_pd(fscal,dx11);
360             ty               = _mm256_mul_pd(fscal,dy11);
361             tz               = _mm256_mul_pd(fscal,dz11);
362
363             /* Update vectorial force */
364             fix1             = _mm256_add_pd(fix1,tx);
365             fiy1             = _mm256_add_pd(fiy1,ty);
366             fiz1             = _mm256_add_pd(fiz1,tz);
367
368             fjx1             = _mm256_add_pd(fjx1,tx);
369             fjy1             = _mm256_add_pd(fjy1,ty);
370             fjz1             = _mm256_add_pd(fjz1,tz);
371
372             /**************************
373              * CALCULATE INTERACTIONS *
374              **************************/
375
376             /* REACTION-FIELD ELECTROSTATICS */
377             velec            = _mm256_mul_pd(qq12,_mm256_sub_pd(_mm256_add_pd(rinv12,_mm256_mul_pd(krf,rsq12)),crf));
378             felec            = _mm256_mul_pd(qq12,_mm256_sub_pd(_mm256_mul_pd(rinv12,rinvsq12),krf2));
379
380             /* Update potential sum for this i atom from the interaction with this j atom. */
381             velecsum         = _mm256_add_pd(velecsum,velec);
382
383             fscal            = felec;
384
385             /* Calculate temporary vectorial force */
386             tx               = _mm256_mul_pd(fscal,dx12);
387             ty               = _mm256_mul_pd(fscal,dy12);
388             tz               = _mm256_mul_pd(fscal,dz12);
389
390             /* Update vectorial force */
391             fix1             = _mm256_add_pd(fix1,tx);
392             fiy1             = _mm256_add_pd(fiy1,ty);
393             fiz1             = _mm256_add_pd(fiz1,tz);
394
395             fjx2             = _mm256_add_pd(fjx2,tx);
396             fjy2             = _mm256_add_pd(fjy2,ty);
397             fjz2             = _mm256_add_pd(fjz2,tz);
398
399             /**************************
400              * CALCULATE INTERACTIONS *
401              **************************/
402
403             /* REACTION-FIELD ELECTROSTATICS */
404             velec            = _mm256_mul_pd(qq13,_mm256_sub_pd(_mm256_add_pd(rinv13,_mm256_mul_pd(krf,rsq13)),crf));
405             felec            = _mm256_mul_pd(qq13,_mm256_sub_pd(_mm256_mul_pd(rinv13,rinvsq13),krf2));
406
407             /* Update potential sum for this i atom from the interaction with this j atom. */
408             velecsum         = _mm256_add_pd(velecsum,velec);
409
410             fscal            = felec;
411
412             /* Calculate temporary vectorial force */
413             tx               = _mm256_mul_pd(fscal,dx13);
414             ty               = _mm256_mul_pd(fscal,dy13);
415             tz               = _mm256_mul_pd(fscal,dz13);
416
417             /* Update vectorial force */
418             fix1             = _mm256_add_pd(fix1,tx);
419             fiy1             = _mm256_add_pd(fiy1,ty);
420             fiz1             = _mm256_add_pd(fiz1,tz);
421
422             fjx3             = _mm256_add_pd(fjx3,tx);
423             fjy3             = _mm256_add_pd(fjy3,ty);
424             fjz3             = _mm256_add_pd(fjz3,tz);
425
426             /**************************
427              * CALCULATE INTERACTIONS *
428              **************************/
429
430             /* REACTION-FIELD ELECTROSTATICS */
431             velec            = _mm256_mul_pd(qq21,_mm256_sub_pd(_mm256_add_pd(rinv21,_mm256_mul_pd(krf,rsq21)),crf));
432             felec            = _mm256_mul_pd(qq21,_mm256_sub_pd(_mm256_mul_pd(rinv21,rinvsq21),krf2));
433
434             /* Update potential sum for this i atom from the interaction with this j atom. */
435             velecsum         = _mm256_add_pd(velecsum,velec);
436
437             fscal            = felec;
438
439             /* Calculate temporary vectorial force */
440             tx               = _mm256_mul_pd(fscal,dx21);
441             ty               = _mm256_mul_pd(fscal,dy21);
442             tz               = _mm256_mul_pd(fscal,dz21);
443
444             /* Update vectorial force */
445             fix2             = _mm256_add_pd(fix2,tx);
446             fiy2             = _mm256_add_pd(fiy2,ty);
447             fiz2             = _mm256_add_pd(fiz2,tz);
448
449             fjx1             = _mm256_add_pd(fjx1,tx);
450             fjy1             = _mm256_add_pd(fjy1,ty);
451             fjz1             = _mm256_add_pd(fjz1,tz);
452
453             /**************************
454              * CALCULATE INTERACTIONS *
455              **************************/
456
457             /* REACTION-FIELD ELECTROSTATICS */
458             velec            = _mm256_mul_pd(qq22,_mm256_sub_pd(_mm256_add_pd(rinv22,_mm256_mul_pd(krf,rsq22)),crf));
459             felec            = _mm256_mul_pd(qq22,_mm256_sub_pd(_mm256_mul_pd(rinv22,rinvsq22),krf2));
460
461             /* Update potential sum for this i atom from the interaction with this j atom. */
462             velecsum         = _mm256_add_pd(velecsum,velec);
463
464             fscal            = felec;
465
466             /* Calculate temporary vectorial force */
467             tx               = _mm256_mul_pd(fscal,dx22);
468             ty               = _mm256_mul_pd(fscal,dy22);
469             tz               = _mm256_mul_pd(fscal,dz22);
470
471             /* Update vectorial force */
472             fix2             = _mm256_add_pd(fix2,tx);
473             fiy2             = _mm256_add_pd(fiy2,ty);
474             fiz2             = _mm256_add_pd(fiz2,tz);
475
476             fjx2             = _mm256_add_pd(fjx2,tx);
477             fjy2             = _mm256_add_pd(fjy2,ty);
478             fjz2             = _mm256_add_pd(fjz2,tz);
479
480             /**************************
481              * CALCULATE INTERACTIONS *
482              **************************/
483
484             /* REACTION-FIELD ELECTROSTATICS */
485             velec            = _mm256_mul_pd(qq23,_mm256_sub_pd(_mm256_add_pd(rinv23,_mm256_mul_pd(krf,rsq23)),crf));
486             felec            = _mm256_mul_pd(qq23,_mm256_sub_pd(_mm256_mul_pd(rinv23,rinvsq23),krf2));
487
488             /* Update potential sum for this i atom from the interaction with this j atom. */
489             velecsum         = _mm256_add_pd(velecsum,velec);
490
491             fscal            = felec;
492
493             /* Calculate temporary vectorial force */
494             tx               = _mm256_mul_pd(fscal,dx23);
495             ty               = _mm256_mul_pd(fscal,dy23);
496             tz               = _mm256_mul_pd(fscal,dz23);
497
498             /* Update vectorial force */
499             fix2             = _mm256_add_pd(fix2,tx);
500             fiy2             = _mm256_add_pd(fiy2,ty);
501             fiz2             = _mm256_add_pd(fiz2,tz);
502
503             fjx3             = _mm256_add_pd(fjx3,tx);
504             fjy3             = _mm256_add_pd(fjy3,ty);
505             fjz3             = _mm256_add_pd(fjz3,tz);
506
507             /**************************
508              * CALCULATE INTERACTIONS *
509              **************************/
510
511             /* REACTION-FIELD ELECTROSTATICS */
512             velec            = _mm256_mul_pd(qq31,_mm256_sub_pd(_mm256_add_pd(rinv31,_mm256_mul_pd(krf,rsq31)),crf));
513             felec            = _mm256_mul_pd(qq31,_mm256_sub_pd(_mm256_mul_pd(rinv31,rinvsq31),krf2));
514
515             /* Update potential sum for this i atom from the interaction with this j atom. */
516             velecsum         = _mm256_add_pd(velecsum,velec);
517
518             fscal            = felec;
519
520             /* Calculate temporary vectorial force */
521             tx               = _mm256_mul_pd(fscal,dx31);
522             ty               = _mm256_mul_pd(fscal,dy31);
523             tz               = _mm256_mul_pd(fscal,dz31);
524
525             /* Update vectorial force */
526             fix3             = _mm256_add_pd(fix3,tx);
527             fiy3             = _mm256_add_pd(fiy3,ty);
528             fiz3             = _mm256_add_pd(fiz3,tz);
529
530             fjx1             = _mm256_add_pd(fjx1,tx);
531             fjy1             = _mm256_add_pd(fjy1,ty);
532             fjz1             = _mm256_add_pd(fjz1,tz);
533
534             /**************************
535              * CALCULATE INTERACTIONS *
536              **************************/
537
538             /* REACTION-FIELD ELECTROSTATICS */
539             velec            = _mm256_mul_pd(qq32,_mm256_sub_pd(_mm256_add_pd(rinv32,_mm256_mul_pd(krf,rsq32)),crf));
540             felec            = _mm256_mul_pd(qq32,_mm256_sub_pd(_mm256_mul_pd(rinv32,rinvsq32),krf2));
541
542             /* Update potential sum for this i atom from the interaction with this j atom. */
543             velecsum         = _mm256_add_pd(velecsum,velec);
544
545             fscal            = felec;
546
547             /* Calculate temporary vectorial force */
548             tx               = _mm256_mul_pd(fscal,dx32);
549             ty               = _mm256_mul_pd(fscal,dy32);
550             tz               = _mm256_mul_pd(fscal,dz32);
551
552             /* Update vectorial force */
553             fix3             = _mm256_add_pd(fix3,tx);
554             fiy3             = _mm256_add_pd(fiy3,ty);
555             fiz3             = _mm256_add_pd(fiz3,tz);
556
557             fjx2             = _mm256_add_pd(fjx2,tx);
558             fjy2             = _mm256_add_pd(fjy2,ty);
559             fjz2             = _mm256_add_pd(fjz2,tz);
560
561             /**************************
562              * CALCULATE INTERACTIONS *
563              **************************/
564
565             /* REACTION-FIELD ELECTROSTATICS */
566             velec            = _mm256_mul_pd(qq33,_mm256_sub_pd(_mm256_add_pd(rinv33,_mm256_mul_pd(krf,rsq33)),crf));
567             felec            = _mm256_mul_pd(qq33,_mm256_sub_pd(_mm256_mul_pd(rinv33,rinvsq33),krf2));
568
569             /* Update potential sum for this i atom from the interaction with this j atom. */
570             velecsum         = _mm256_add_pd(velecsum,velec);
571
572             fscal            = felec;
573
574             /* Calculate temporary vectorial force */
575             tx               = _mm256_mul_pd(fscal,dx33);
576             ty               = _mm256_mul_pd(fscal,dy33);
577             tz               = _mm256_mul_pd(fscal,dz33);
578
579             /* Update vectorial force */
580             fix3             = _mm256_add_pd(fix3,tx);
581             fiy3             = _mm256_add_pd(fiy3,ty);
582             fiz3             = _mm256_add_pd(fiz3,tz);
583
584             fjx3             = _mm256_add_pd(fjx3,tx);
585             fjy3             = _mm256_add_pd(fjy3,ty);
586             fjz3             = _mm256_add_pd(fjz3,tz);
587
588             fjptrA             = f+j_coord_offsetA;
589             fjptrB             = f+j_coord_offsetB;
590             fjptrC             = f+j_coord_offsetC;
591             fjptrD             = f+j_coord_offsetD;
592
593             gmx_mm256_decrement_4rvec_4ptr_swizzle_pd(fjptrA,fjptrB,fjptrC,fjptrD,
594                                                       fjx0,fjy0,fjz0,fjx1,fjy1,fjz1,
595                                                       fjx2,fjy2,fjz2,fjx3,fjy3,fjz3);
596
597             /* Inner loop uses 323 flops */
598         }
599
600         if(jidx<j_index_end)
601         {
602
603             /* Get j neighbor index, and coordinate index */
604             jnrlistA         = jjnr[jidx];
605             jnrlistB         = jjnr[jidx+1];
606             jnrlistC         = jjnr[jidx+2];
607             jnrlistD         = jjnr[jidx+3];
608             /* Sign of each element will be negative for non-real atoms.
609              * This mask will be 0xFFFFFFFF for dummy entries and 0x0 for real ones,
610              * so use it as val = _mm_andnot_pd(mask,val) to clear dummy entries.
611              */
612             tmpmask0 = gmx_mm_castsi128_ps(_mm_cmplt_epi32(_mm_loadu_si128((const __m128i *)(jjnr+jidx)),_mm_setzero_si128()));
613
614             tmpmask1 = _mm_permute_ps(tmpmask0,_GMX_MM_PERMUTE(3,3,2,2));
615             tmpmask0 = _mm_permute_ps(tmpmask0,_GMX_MM_PERMUTE(1,1,0,0));
616             dummy_mask = _mm256_castps_pd(gmx_mm256_set_m128(tmpmask1,tmpmask0));
617
618             jnrA       = (jnrlistA>=0) ? jnrlistA : 0;
619             jnrB       = (jnrlistB>=0) ? jnrlistB : 0;
620             jnrC       = (jnrlistC>=0) ? jnrlistC : 0;
621             jnrD       = (jnrlistD>=0) ? jnrlistD : 0;
622             j_coord_offsetA  = DIM*jnrA;
623             j_coord_offsetB  = DIM*jnrB;
624             j_coord_offsetC  = DIM*jnrC;
625             j_coord_offsetD  = DIM*jnrD;
626
627             /* load j atom coordinates */
628             gmx_mm256_load_4rvec_4ptr_swizzle_pd(x+j_coord_offsetA,x+j_coord_offsetB,
629                                                  x+j_coord_offsetC,x+j_coord_offsetD,
630                                                  &jx0,&jy0,&jz0,&jx1,&jy1,&jz1,&jx2,
631                                                  &jy2,&jz2,&jx3,&jy3,&jz3);
632
633             /* Calculate displacement vector */
634             dx00             = _mm256_sub_pd(ix0,jx0);
635             dy00             = _mm256_sub_pd(iy0,jy0);
636             dz00             = _mm256_sub_pd(iz0,jz0);
637             dx11             = _mm256_sub_pd(ix1,jx1);
638             dy11             = _mm256_sub_pd(iy1,jy1);
639             dz11             = _mm256_sub_pd(iz1,jz1);
640             dx12             = _mm256_sub_pd(ix1,jx2);
641             dy12             = _mm256_sub_pd(iy1,jy2);
642             dz12             = _mm256_sub_pd(iz1,jz2);
643             dx13             = _mm256_sub_pd(ix1,jx3);
644             dy13             = _mm256_sub_pd(iy1,jy3);
645             dz13             = _mm256_sub_pd(iz1,jz3);
646             dx21             = _mm256_sub_pd(ix2,jx1);
647             dy21             = _mm256_sub_pd(iy2,jy1);
648             dz21             = _mm256_sub_pd(iz2,jz1);
649             dx22             = _mm256_sub_pd(ix2,jx2);
650             dy22             = _mm256_sub_pd(iy2,jy2);
651             dz22             = _mm256_sub_pd(iz2,jz2);
652             dx23             = _mm256_sub_pd(ix2,jx3);
653             dy23             = _mm256_sub_pd(iy2,jy3);
654             dz23             = _mm256_sub_pd(iz2,jz3);
655             dx31             = _mm256_sub_pd(ix3,jx1);
656             dy31             = _mm256_sub_pd(iy3,jy1);
657             dz31             = _mm256_sub_pd(iz3,jz1);
658             dx32             = _mm256_sub_pd(ix3,jx2);
659             dy32             = _mm256_sub_pd(iy3,jy2);
660             dz32             = _mm256_sub_pd(iz3,jz2);
661             dx33             = _mm256_sub_pd(ix3,jx3);
662             dy33             = _mm256_sub_pd(iy3,jy3);
663             dz33             = _mm256_sub_pd(iz3,jz3);
664
665             /* Calculate squared distance and things based on it */
666             rsq00            = gmx_mm256_calc_rsq_pd(dx00,dy00,dz00);
667             rsq11            = gmx_mm256_calc_rsq_pd(dx11,dy11,dz11);
668             rsq12            = gmx_mm256_calc_rsq_pd(dx12,dy12,dz12);
669             rsq13            = gmx_mm256_calc_rsq_pd(dx13,dy13,dz13);
670             rsq21            = gmx_mm256_calc_rsq_pd(dx21,dy21,dz21);
671             rsq22            = gmx_mm256_calc_rsq_pd(dx22,dy22,dz22);
672             rsq23            = gmx_mm256_calc_rsq_pd(dx23,dy23,dz23);
673             rsq31            = gmx_mm256_calc_rsq_pd(dx31,dy31,dz31);
674             rsq32            = gmx_mm256_calc_rsq_pd(dx32,dy32,dz32);
675             rsq33            = gmx_mm256_calc_rsq_pd(dx33,dy33,dz33);
676
677             rinv11           = gmx_mm256_invsqrt_pd(rsq11);
678             rinv12           = gmx_mm256_invsqrt_pd(rsq12);
679             rinv13           = gmx_mm256_invsqrt_pd(rsq13);
680             rinv21           = gmx_mm256_invsqrt_pd(rsq21);
681             rinv22           = gmx_mm256_invsqrt_pd(rsq22);
682             rinv23           = gmx_mm256_invsqrt_pd(rsq23);
683             rinv31           = gmx_mm256_invsqrt_pd(rsq31);
684             rinv32           = gmx_mm256_invsqrt_pd(rsq32);
685             rinv33           = gmx_mm256_invsqrt_pd(rsq33);
686
687             rinvsq00         = gmx_mm256_inv_pd(rsq00);
688             rinvsq11         = _mm256_mul_pd(rinv11,rinv11);
689             rinvsq12         = _mm256_mul_pd(rinv12,rinv12);
690             rinvsq13         = _mm256_mul_pd(rinv13,rinv13);
691             rinvsq21         = _mm256_mul_pd(rinv21,rinv21);
692             rinvsq22         = _mm256_mul_pd(rinv22,rinv22);
693             rinvsq23         = _mm256_mul_pd(rinv23,rinv23);
694             rinvsq31         = _mm256_mul_pd(rinv31,rinv31);
695             rinvsq32         = _mm256_mul_pd(rinv32,rinv32);
696             rinvsq33         = _mm256_mul_pd(rinv33,rinv33);
697
698             fjx0             = _mm256_setzero_pd();
699             fjy0             = _mm256_setzero_pd();
700             fjz0             = _mm256_setzero_pd();
701             fjx1             = _mm256_setzero_pd();
702             fjy1             = _mm256_setzero_pd();
703             fjz1             = _mm256_setzero_pd();
704             fjx2             = _mm256_setzero_pd();
705             fjy2             = _mm256_setzero_pd();
706             fjz2             = _mm256_setzero_pd();
707             fjx3             = _mm256_setzero_pd();
708             fjy3             = _mm256_setzero_pd();
709             fjz3             = _mm256_setzero_pd();
710
711             /**************************
712              * CALCULATE INTERACTIONS *
713              **************************/
714
715             /* LENNARD-JONES DISPERSION/REPULSION */
716
717             rinvsix          = _mm256_mul_pd(_mm256_mul_pd(rinvsq00,rinvsq00),rinvsq00);
718             vvdw6            = _mm256_mul_pd(c6_00,rinvsix);
719             vvdw12           = _mm256_mul_pd(c12_00,_mm256_mul_pd(rinvsix,rinvsix));
720             vvdw             = _mm256_sub_pd( _mm256_mul_pd(vvdw12,one_twelfth) , _mm256_mul_pd(vvdw6,one_sixth) );
721             fvdw             = _mm256_mul_pd(_mm256_sub_pd(vvdw12,vvdw6),rinvsq00);
722
723             /* Update potential sum for this i atom from the interaction with this j atom. */
724             vvdw             = _mm256_andnot_pd(dummy_mask,vvdw);
725             vvdwsum          = _mm256_add_pd(vvdwsum,vvdw);
726
727             fscal            = fvdw;
728
729             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
730
731             /* Calculate temporary vectorial force */
732             tx               = _mm256_mul_pd(fscal,dx00);
733             ty               = _mm256_mul_pd(fscal,dy00);
734             tz               = _mm256_mul_pd(fscal,dz00);
735
736             /* Update vectorial force */
737             fix0             = _mm256_add_pd(fix0,tx);
738             fiy0             = _mm256_add_pd(fiy0,ty);
739             fiz0             = _mm256_add_pd(fiz0,tz);
740
741             fjx0             = _mm256_add_pd(fjx0,tx);
742             fjy0             = _mm256_add_pd(fjy0,ty);
743             fjz0             = _mm256_add_pd(fjz0,tz);
744
745             /**************************
746              * CALCULATE INTERACTIONS *
747              **************************/
748
749             /* REACTION-FIELD ELECTROSTATICS */
750             velec            = _mm256_mul_pd(qq11,_mm256_sub_pd(_mm256_add_pd(rinv11,_mm256_mul_pd(krf,rsq11)),crf));
751             felec            = _mm256_mul_pd(qq11,_mm256_sub_pd(_mm256_mul_pd(rinv11,rinvsq11),krf2));
752
753             /* Update potential sum for this i atom from the interaction with this j atom. */
754             velec            = _mm256_andnot_pd(dummy_mask,velec);
755             velecsum         = _mm256_add_pd(velecsum,velec);
756
757             fscal            = felec;
758
759             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
760
761             /* Calculate temporary vectorial force */
762             tx               = _mm256_mul_pd(fscal,dx11);
763             ty               = _mm256_mul_pd(fscal,dy11);
764             tz               = _mm256_mul_pd(fscal,dz11);
765
766             /* Update vectorial force */
767             fix1             = _mm256_add_pd(fix1,tx);
768             fiy1             = _mm256_add_pd(fiy1,ty);
769             fiz1             = _mm256_add_pd(fiz1,tz);
770
771             fjx1             = _mm256_add_pd(fjx1,tx);
772             fjy1             = _mm256_add_pd(fjy1,ty);
773             fjz1             = _mm256_add_pd(fjz1,tz);
774
775             /**************************
776              * CALCULATE INTERACTIONS *
777              **************************/
778
779             /* REACTION-FIELD ELECTROSTATICS */
780             velec            = _mm256_mul_pd(qq12,_mm256_sub_pd(_mm256_add_pd(rinv12,_mm256_mul_pd(krf,rsq12)),crf));
781             felec            = _mm256_mul_pd(qq12,_mm256_sub_pd(_mm256_mul_pd(rinv12,rinvsq12),krf2));
782
783             /* Update potential sum for this i atom from the interaction with this j atom. */
784             velec            = _mm256_andnot_pd(dummy_mask,velec);
785             velecsum         = _mm256_add_pd(velecsum,velec);
786
787             fscal            = felec;
788
789             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
790
791             /* Calculate temporary vectorial force */
792             tx               = _mm256_mul_pd(fscal,dx12);
793             ty               = _mm256_mul_pd(fscal,dy12);
794             tz               = _mm256_mul_pd(fscal,dz12);
795
796             /* Update vectorial force */
797             fix1             = _mm256_add_pd(fix1,tx);
798             fiy1             = _mm256_add_pd(fiy1,ty);
799             fiz1             = _mm256_add_pd(fiz1,tz);
800
801             fjx2             = _mm256_add_pd(fjx2,tx);
802             fjy2             = _mm256_add_pd(fjy2,ty);
803             fjz2             = _mm256_add_pd(fjz2,tz);
804
805             /**************************
806              * CALCULATE INTERACTIONS *
807              **************************/
808
809             /* REACTION-FIELD ELECTROSTATICS */
810             velec            = _mm256_mul_pd(qq13,_mm256_sub_pd(_mm256_add_pd(rinv13,_mm256_mul_pd(krf,rsq13)),crf));
811             felec            = _mm256_mul_pd(qq13,_mm256_sub_pd(_mm256_mul_pd(rinv13,rinvsq13),krf2));
812
813             /* Update potential sum for this i atom from the interaction with this j atom. */
814             velec            = _mm256_andnot_pd(dummy_mask,velec);
815             velecsum         = _mm256_add_pd(velecsum,velec);
816
817             fscal            = felec;
818
819             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
820
821             /* Calculate temporary vectorial force */
822             tx               = _mm256_mul_pd(fscal,dx13);
823             ty               = _mm256_mul_pd(fscal,dy13);
824             tz               = _mm256_mul_pd(fscal,dz13);
825
826             /* Update vectorial force */
827             fix1             = _mm256_add_pd(fix1,tx);
828             fiy1             = _mm256_add_pd(fiy1,ty);
829             fiz1             = _mm256_add_pd(fiz1,tz);
830
831             fjx3             = _mm256_add_pd(fjx3,tx);
832             fjy3             = _mm256_add_pd(fjy3,ty);
833             fjz3             = _mm256_add_pd(fjz3,tz);
834
835             /**************************
836              * CALCULATE INTERACTIONS *
837              **************************/
838
839             /* REACTION-FIELD ELECTROSTATICS */
840             velec            = _mm256_mul_pd(qq21,_mm256_sub_pd(_mm256_add_pd(rinv21,_mm256_mul_pd(krf,rsq21)),crf));
841             felec            = _mm256_mul_pd(qq21,_mm256_sub_pd(_mm256_mul_pd(rinv21,rinvsq21),krf2));
842
843             /* Update potential sum for this i atom from the interaction with this j atom. */
844             velec            = _mm256_andnot_pd(dummy_mask,velec);
845             velecsum         = _mm256_add_pd(velecsum,velec);
846
847             fscal            = felec;
848
849             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
850
851             /* Calculate temporary vectorial force */
852             tx               = _mm256_mul_pd(fscal,dx21);
853             ty               = _mm256_mul_pd(fscal,dy21);
854             tz               = _mm256_mul_pd(fscal,dz21);
855
856             /* Update vectorial force */
857             fix2             = _mm256_add_pd(fix2,tx);
858             fiy2             = _mm256_add_pd(fiy2,ty);
859             fiz2             = _mm256_add_pd(fiz2,tz);
860
861             fjx1             = _mm256_add_pd(fjx1,tx);
862             fjy1             = _mm256_add_pd(fjy1,ty);
863             fjz1             = _mm256_add_pd(fjz1,tz);
864
865             /**************************
866              * CALCULATE INTERACTIONS *
867              **************************/
868
869             /* REACTION-FIELD ELECTROSTATICS */
870             velec            = _mm256_mul_pd(qq22,_mm256_sub_pd(_mm256_add_pd(rinv22,_mm256_mul_pd(krf,rsq22)),crf));
871             felec            = _mm256_mul_pd(qq22,_mm256_sub_pd(_mm256_mul_pd(rinv22,rinvsq22),krf2));
872
873             /* Update potential sum for this i atom from the interaction with this j atom. */
874             velec            = _mm256_andnot_pd(dummy_mask,velec);
875             velecsum         = _mm256_add_pd(velecsum,velec);
876
877             fscal            = felec;
878
879             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
880
881             /* Calculate temporary vectorial force */
882             tx               = _mm256_mul_pd(fscal,dx22);
883             ty               = _mm256_mul_pd(fscal,dy22);
884             tz               = _mm256_mul_pd(fscal,dz22);
885
886             /* Update vectorial force */
887             fix2             = _mm256_add_pd(fix2,tx);
888             fiy2             = _mm256_add_pd(fiy2,ty);
889             fiz2             = _mm256_add_pd(fiz2,tz);
890
891             fjx2             = _mm256_add_pd(fjx2,tx);
892             fjy2             = _mm256_add_pd(fjy2,ty);
893             fjz2             = _mm256_add_pd(fjz2,tz);
894
895             /**************************
896              * CALCULATE INTERACTIONS *
897              **************************/
898
899             /* REACTION-FIELD ELECTROSTATICS */
900             velec            = _mm256_mul_pd(qq23,_mm256_sub_pd(_mm256_add_pd(rinv23,_mm256_mul_pd(krf,rsq23)),crf));
901             felec            = _mm256_mul_pd(qq23,_mm256_sub_pd(_mm256_mul_pd(rinv23,rinvsq23),krf2));
902
903             /* Update potential sum for this i atom from the interaction with this j atom. */
904             velec            = _mm256_andnot_pd(dummy_mask,velec);
905             velecsum         = _mm256_add_pd(velecsum,velec);
906
907             fscal            = felec;
908
909             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
910
911             /* Calculate temporary vectorial force */
912             tx               = _mm256_mul_pd(fscal,dx23);
913             ty               = _mm256_mul_pd(fscal,dy23);
914             tz               = _mm256_mul_pd(fscal,dz23);
915
916             /* Update vectorial force */
917             fix2             = _mm256_add_pd(fix2,tx);
918             fiy2             = _mm256_add_pd(fiy2,ty);
919             fiz2             = _mm256_add_pd(fiz2,tz);
920
921             fjx3             = _mm256_add_pd(fjx3,tx);
922             fjy3             = _mm256_add_pd(fjy3,ty);
923             fjz3             = _mm256_add_pd(fjz3,tz);
924
925             /**************************
926              * CALCULATE INTERACTIONS *
927              **************************/
928
929             /* REACTION-FIELD ELECTROSTATICS */
930             velec            = _mm256_mul_pd(qq31,_mm256_sub_pd(_mm256_add_pd(rinv31,_mm256_mul_pd(krf,rsq31)),crf));
931             felec            = _mm256_mul_pd(qq31,_mm256_sub_pd(_mm256_mul_pd(rinv31,rinvsq31),krf2));
932
933             /* Update potential sum for this i atom from the interaction with this j atom. */
934             velec            = _mm256_andnot_pd(dummy_mask,velec);
935             velecsum         = _mm256_add_pd(velecsum,velec);
936
937             fscal            = felec;
938
939             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
940
941             /* Calculate temporary vectorial force */
942             tx               = _mm256_mul_pd(fscal,dx31);
943             ty               = _mm256_mul_pd(fscal,dy31);
944             tz               = _mm256_mul_pd(fscal,dz31);
945
946             /* Update vectorial force */
947             fix3             = _mm256_add_pd(fix3,tx);
948             fiy3             = _mm256_add_pd(fiy3,ty);
949             fiz3             = _mm256_add_pd(fiz3,tz);
950
951             fjx1             = _mm256_add_pd(fjx1,tx);
952             fjy1             = _mm256_add_pd(fjy1,ty);
953             fjz1             = _mm256_add_pd(fjz1,tz);
954
955             /**************************
956              * CALCULATE INTERACTIONS *
957              **************************/
958
959             /* REACTION-FIELD ELECTROSTATICS */
960             velec            = _mm256_mul_pd(qq32,_mm256_sub_pd(_mm256_add_pd(rinv32,_mm256_mul_pd(krf,rsq32)),crf));
961             felec            = _mm256_mul_pd(qq32,_mm256_sub_pd(_mm256_mul_pd(rinv32,rinvsq32),krf2));
962
963             /* Update potential sum for this i atom from the interaction with this j atom. */
964             velec            = _mm256_andnot_pd(dummy_mask,velec);
965             velecsum         = _mm256_add_pd(velecsum,velec);
966
967             fscal            = felec;
968
969             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
970
971             /* Calculate temporary vectorial force */
972             tx               = _mm256_mul_pd(fscal,dx32);
973             ty               = _mm256_mul_pd(fscal,dy32);
974             tz               = _mm256_mul_pd(fscal,dz32);
975
976             /* Update vectorial force */
977             fix3             = _mm256_add_pd(fix3,tx);
978             fiy3             = _mm256_add_pd(fiy3,ty);
979             fiz3             = _mm256_add_pd(fiz3,tz);
980
981             fjx2             = _mm256_add_pd(fjx2,tx);
982             fjy2             = _mm256_add_pd(fjy2,ty);
983             fjz2             = _mm256_add_pd(fjz2,tz);
984
985             /**************************
986              * CALCULATE INTERACTIONS *
987              **************************/
988
989             /* REACTION-FIELD ELECTROSTATICS */
990             velec            = _mm256_mul_pd(qq33,_mm256_sub_pd(_mm256_add_pd(rinv33,_mm256_mul_pd(krf,rsq33)),crf));
991             felec            = _mm256_mul_pd(qq33,_mm256_sub_pd(_mm256_mul_pd(rinv33,rinvsq33),krf2));
992
993             /* Update potential sum for this i atom from the interaction with this j atom. */
994             velec            = _mm256_andnot_pd(dummy_mask,velec);
995             velecsum         = _mm256_add_pd(velecsum,velec);
996
997             fscal            = felec;
998
999             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
1000
1001             /* Calculate temporary vectorial force */
1002             tx               = _mm256_mul_pd(fscal,dx33);
1003             ty               = _mm256_mul_pd(fscal,dy33);
1004             tz               = _mm256_mul_pd(fscal,dz33);
1005
1006             /* Update vectorial force */
1007             fix3             = _mm256_add_pd(fix3,tx);
1008             fiy3             = _mm256_add_pd(fiy3,ty);
1009             fiz3             = _mm256_add_pd(fiz3,tz);
1010
1011             fjx3             = _mm256_add_pd(fjx3,tx);
1012             fjy3             = _mm256_add_pd(fjy3,ty);
1013             fjz3             = _mm256_add_pd(fjz3,tz);
1014
1015             fjptrA             = (jnrlistA>=0) ? f+j_coord_offsetA : scratch;
1016             fjptrB             = (jnrlistB>=0) ? f+j_coord_offsetB : scratch;
1017             fjptrC             = (jnrlistC>=0) ? f+j_coord_offsetC : scratch;
1018             fjptrD             = (jnrlistD>=0) ? f+j_coord_offsetD : scratch;
1019
1020             gmx_mm256_decrement_4rvec_4ptr_swizzle_pd(fjptrA,fjptrB,fjptrC,fjptrD,
1021                                                       fjx0,fjy0,fjz0,fjx1,fjy1,fjz1,
1022                                                       fjx2,fjy2,fjz2,fjx3,fjy3,fjz3);
1023
1024             /* Inner loop uses 323 flops */
1025         }
1026
1027         /* End of innermost loop */
1028
1029         gmx_mm256_update_iforce_4atom_swizzle_pd(fix0,fiy0,fiz0,fix1,fiy1,fiz1,fix2,fiy2,fiz2,fix3,fiy3,fiz3,
1030                                                  f+i_coord_offset,fshift+i_shift_offset);
1031
1032         ggid                        = gid[iidx];
1033         /* Update potential energies */
1034         gmx_mm256_update_1pot_pd(velecsum,kernel_data->energygrp_elec+ggid);
1035         gmx_mm256_update_1pot_pd(vvdwsum,kernel_data->energygrp_vdw+ggid);
1036
1037         /* Increment number of inner iterations */
1038         inneriter                  += j_index_end - j_index_start;
1039
1040         /* Outer loop uses 26 flops */
1041     }
1042
1043     /* Increment number of outer iterations */
1044     outeriter        += nri;
1045
1046     /* Update outer/inner flops */
1047
1048     inc_nrnb(nrnb,eNR_NBKERNEL_ELEC_VDW_W4W4_VF,outeriter*26 + inneriter*323);
1049 }
1050 /*
1051  * Gromacs nonbonded kernel:   nb_kernel_ElecRF_VdwLJ_GeomW4W4_F_avx_256_double
1052  * Electrostatics interaction: ReactionField
1053  * VdW interaction:            LennardJones
1054  * Geometry:                   Water4-Water4
1055  * Calculate force/pot:        Force
1056  */
1057 void
1058 nb_kernel_ElecRF_VdwLJ_GeomW4W4_F_avx_256_double
1059                     (t_nblist                    * gmx_restrict       nlist,
1060                      rvec                        * gmx_restrict          xx,
1061                      rvec                        * gmx_restrict          ff,
1062                      t_forcerec                  * gmx_restrict          fr,
1063                      t_mdatoms                   * gmx_restrict     mdatoms,
1064                      nb_kernel_data_t gmx_unused * gmx_restrict kernel_data,
1065                      t_nrnb                      * gmx_restrict        nrnb)
1066 {
1067     /* Suffixes 0,1,2,3 refer to particle indices for waters in the inner or outer loop, or 
1068      * just 0 for non-waters.
1069      * Suffixes A,B,C,D refer to j loop unrolling done with AVX, e.g. for the four different
1070      * jnr indices corresponding to data put in the four positions in the SIMD register.
1071      */
1072     int              i_shift_offset,i_coord_offset,outeriter,inneriter;
1073     int              j_index_start,j_index_end,jidx,nri,inr,ggid,iidx;
1074     int              jnrA,jnrB,jnrC,jnrD;
1075     int              jnrlistA,jnrlistB,jnrlistC,jnrlistD;
1076     int              jnrlistE,jnrlistF,jnrlistG,jnrlistH;
1077     int              j_coord_offsetA,j_coord_offsetB,j_coord_offsetC,j_coord_offsetD;
1078     int              *iinr,*jindex,*jjnr,*shiftidx,*gid;
1079     real             rcutoff_scalar;
1080     real             *shiftvec,*fshift,*x,*f;
1081     real             *fjptrA,*fjptrB,*fjptrC,*fjptrD;
1082     real             scratch[4*DIM];
1083     __m256d          tx,ty,tz,fscal,rcutoff,rcutoff2,jidxall;
1084     real *           vdwioffsetptr0;
1085     __m256d          ix0,iy0,iz0,fix0,fiy0,fiz0,iq0,isai0;
1086     real *           vdwioffsetptr1;
1087     __m256d          ix1,iy1,iz1,fix1,fiy1,fiz1,iq1,isai1;
1088     real *           vdwioffsetptr2;
1089     __m256d          ix2,iy2,iz2,fix2,fiy2,fiz2,iq2,isai2;
1090     real *           vdwioffsetptr3;
1091     __m256d          ix3,iy3,iz3,fix3,fiy3,fiz3,iq3,isai3;
1092     int              vdwjidx0A,vdwjidx0B,vdwjidx0C,vdwjidx0D;
1093     __m256d          jx0,jy0,jz0,fjx0,fjy0,fjz0,jq0,isaj0;
1094     int              vdwjidx1A,vdwjidx1B,vdwjidx1C,vdwjidx1D;
1095     __m256d          jx1,jy1,jz1,fjx1,fjy1,fjz1,jq1,isaj1;
1096     int              vdwjidx2A,vdwjidx2B,vdwjidx2C,vdwjidx2D;
1097     __m256d          jx2,jy2,jz2,fjx2,fjy2,fjz2,jq2,isaj2;
1098     int              vdwjidx3A,vdwjidx3B,vdwjidx3C,vdwjidx3D;
1099     __m256d          jx3,jy3,jz3,fjx3,fjy3,fjz3,jq3,isaj3;
1100     __m256d          dx00,dy00,dz00,rsq00,rinv00,rinvsq00,r00,qq00,c6_00,c12_00;
1101     __m256d          dx11,dy11,dz11,rsq11,rinv11,rinvsq11,r11,qq11,c6_11,c12_11;
1102     __m256d          dx12,dy12,dz12,rsq12,rinv12,rinvsq12,r12,qq12,c6_12,c12_12;
1103     __m256d          dx13,dy13,dz13,rsq13,rinv13,rinvsq13,r13,qq13,c6_13,c12_13;
1104     __m256d          dx21,dy21,dz21,rsq21,rinv21,rinvsq21,r21,qq21,c6_21,c12_21;
1105     __m256d          dx22,dy22,dz22,rsq22,rinv22,rinvsq22,r22,qq22,c6_22,c12_22;
1106     __m256d          dx23,dy23,dz23,rsq23,rinv23,rinvsq23,r23,qq23,c6_23,c12_23;
1107     __m256d          dx31,dy31,dz31,rsq31,rinv31,rinvsq31,r31,qq31,c6_31,c12_31;
1108     __m256d          dx32,dy32,dz32,rsq32,rinv32,rinvsq32,r32,qq32,c6_32,c12_32;
1109     __m256d          dx33,dy33,dz33,rsq33,rinv33,rinvsq33,r33,qq33,c6_33,c12_33;
1110     __m256d          velec,felec,velecsum,facel,crf,krf,krf2;
1111     real             *charge;
1112     int              nvdwtype;
1113     __m256d          rinvsix,rvdw,vvdw,vvdw6,vvdw12,fvdw,fvdw6,fvdw12,vvdwsum,sh_vdw_invrcut6;
1114     int              *vdwtype;
1115     real             *vdwparam;
1116     __m256d          one_sixth   = _mm256_set1_pd(1.0/6.0);
1117     __m256d          one_twelfth = _mm256_set1_pd(1.0/12.0);
1118     __m256d          dummy_mask,cutoff_mask;
1119     __m128           tmpmask0,tmpmask1;
1120     __m256d          signbit = _mm256_castsi256_pd( _mm256_set1_epi32(0x80000000) );
1121     __m256d          one     = _mm256_set1_pd(1.0);
1122     __m256d          two     = _mm256_set1_pd(2.0);
1123     x                = xx[0];
1124     f                = ff[0];
1125
1126     nri              = nlist->nri;
1127     iinr             = nlist->iinr;
1128     jindex           = nlist->jindex;
1129     jjnr             = nlist->jjnr;
1130     shiftidx         = nlist->shift;
1131     gid              = nlist->gid;
1132     shiftvec         = fr->shift_vec[0];
1133     fshift           = fr->fshift[0];
1134     facel            = _mm256_set1_pd(fr->epsfac);
1135     charge           = mdatoms->chargeA;
1136     krf              = _mm256_set1_pd(fr->ic->k_rf);
1137     krf2             = _mm256_set1_pd(fr->ic->k_rf*2.0);
1138     crf              = _mm256_set1_pd(fr->ic->c_rf);
1139     nvdwtype         = fr->ntype;
1140     vdwparam         = fr->nbfp;
1141     vdwtype          = mdatoms->typeA;
1142
1143     /* Setup water-specific parameters */
1144     inr              = nlist->iinr[0];
1145     iq1              = _mm256_mul_pd(facel,_mm256_set1_pd(charge[inr+1]));
1146     iq2              = _mm256_mul_pd(facel,_mm256_set1_pd(charge[inr+2]));
1147     iq3              = _mm256_mul_pd(facel,_mm256_set1_pd(charge[inr+3]));
1148     vdwioffsetptr0   = vdwparam+2*nvdwtype*vdwtype[inr+0];
1149
1150     jq1              = _mm256_set1_pd(charge[inr+1]);
1151     jq2              = _mm256_set1_pd(charge[inr+2]);
1152     jq3              = _mm256_set1_pd(charge[inr+3]);
1153     vdwjidx0A        = 2*vdwtype[inr+0];
1154     c6_00            = _mm256_set1_pd(vdwioffsetptr0[vdwjidx0A]);
1155     c12_00           = _mm256_set1_pd(vdwioffsetptr0[vdwjidx0A+1]);
1156     qq11             = _mm256_mul_pd(iq1,jq1);
1157     qq12             = _mm256_mul_pd(iq1,jq2);
1158     qq13             = _mm256_mul_pd(iq1,jq3);
1159     qq21             = _mm256_mul_pd(iq2,jq1);
1160     qq22             = _mm256_mul_pd(iq2,jq2);
1161     qq23             = _mm256_mul_pd(iq2,jq3);
1162     qq31             = _mm256_mul_pd(iq3,jq1);
1163     qq32             = _mm256_mul_pd(iq3,jq2);
1164     qq33             = _mm256_mul_pd(iq3,jq3);
1165
1166     /* Avoid stupid compiler warnings */
1167     jnrA = jnrB = jnrC = jnrD = 0;
1168     j_coord_offsetA = 0;
1169     j_coord_offsetB = 0;
1170     j_coord_offsetC = 0;
1171     j_coord_offsetD = 0;
1172
1173     outeriter        = 0;
1174     inneriter        = 0;
1175
1176     for(iidx=0;iidx<4*DIM;iidx++)
1177     {
1178         scratch[iidx] = 0.0;
1179     }
1180
1181     /* Start outer loop over neighborlists */
1182     for(iidx=0; iidx<nri; iidx++)
1183     {
1184         /* Load shift vector for this list */
1185         i_shift_offset   = DIM*shiftidx[iidx];
1186
1187         /* Load limits for loop over neighbors */
1188         j_index_start    = jindex[iidx];
1189         j_index_end      = jindex[iidx+1];
1190
1191         /* Get outer coordinate index */
1192         inr              = iinr[iidx];
1193         i_coord_offset   = DIM*inr;
1194
1195         /* Load i particle coords and add shift vector */
1196         gmx_mm256_load_shift_and_4rvec_broadcast_pd(shiftvec+i_shift_offset,x+i_coord_offset,
1197                                                     &ix0,&iy0,&iz0,&ix1,&iy1,&iz1,&ix2,&iy2,&iz2,&ix3,&iy3,&iz3);
1198
1199         fix0             = _mm256_setzero_pd();
1200         fiy0             = _mm256_setzero_pd();
1201         fiz0             = _mm256_setzero_pd();
1202         fix1             = _mm256_setzero_pd();
1203         fiy1             = _mm256_setzero_pd();
1204         fiz1             = _mm256_setzero_pd();
1205         fix2             = _mm256_setzero_pd();
1206         fiy2             = _mm256_setzero_pd();
1207         fiz2             = _mm256_setzero_pd();
1208         fix3             = _mm256_setzero_pd();
1209         fiy3             = _mm256_setzero_pd();
1210         fiz3             = _mm256_setzero_pd();
1211
1212         /* Start inner kernel loop */
1213         for(jidx=j_index_start; jidx<j_index_end && jjnr[jidx+3]>=0; jidx+=4)
1214         {
1215
1216             /* Get j neighbor index, and coordinate index */
1217             jnrA             = jjnr[jidx];
1218             jnrB             = jjnr[jidx+1];
1219             jnrC             = jjnr[jidx+2];
1220             jnrD             = jjnr[jidx+3];
1221             j_coord_offsetA  = DIM*jnrA;
1222             j_coord_offsetB  = DIM*jnrB;
1223             j_coord_offsetC  = DIM*jnrC;
1224             j_coord_offsetD  = DIM*jnrD;
1225
1226             /* load j atom coordinates */
1227             gmx_mm256_load_4rvec_4ptr_swizzle_pd(x+j_coord_offsetA,x+j_coord_offsetB,
1228                                                  x+j_coord_offsetC,x+j_coord_offsetD,
1229                                                  &jx0,&jy0,&jz0,&jx1,&jy1,&jz1,&jx2,
1230                                                  &jy2,&jz2,&jx3,&jy3,&jz3);
1231
1232             /* Calculate displacement vector */
1233             dx00             = _mm256_sub_pd(ix0,jx0);
1234             dy00             = _mm256_sub_pd(iy0,jy0);
1235             dz00             = _mm256_sub_pd(iz0,jz0);
1236             dx11             = _mm256_sub_pd(ix1,jx1);
1237             dy11             = _mm256_sub_pd(iy1,jy1);
1238             dz11             = _mm256_sub_pd(iz1,jz1);
1239             dx12             = _mm256_sub_pd(ix1,jx2);
1240             dy12             = _mm256_sub_pd(iy1,jy2);
1241             dz12             = _mm256_sub_pd(iz1,jz2);
1242             dx13             = _mm256_sub_pd(ix1,jx3);
1243             dy13             = _mm256_sub_pd(iy1,jy3);
1244             dz13             = _mm256_sub_pd(iz1,jz3);
1245             dx21             = _mm256_sub_pd(ix2,jx1);
1246             dy21             = _mm256_sub_pd(iy2,jy1);
1247             dz21             = _mm256_sub_pd(iz2,jz1);
1248             dx22             = _mm256_sub_pd(ix2,jx2);
1249             dy22             = _mm256_sub_pd(iy2,jy2);
1250             dz22             = _mm256_sub_pd(iz2,jz2);
1251             dx23             = _mm256_sub_pd(ix2,jx3);
1252             dy23             = _mm256_sub_pd(iy2,jy3);
1253             dz23             = _mm256_sub_pd(iz2,jz3);
1254             dx31             = _mm256_sub_pd(ix3,jx1);
1255             dy31             = _mm256_sub_pd(iy3,jy1);
1256             dz31             = _mm256_sub_pd(iz3,jz1);
1257             dx32             = _mm256_sub_pd(ix3,jx2);
1258             dy32             = _mm256_sub_pd(iy3,jy2);
1259             dz32             = _mm256_sub_pd(iz3,jz2);
1260             dx33             = _mm256_sub_pd(ix3,jx3);
1261             dy33             = _mm256_sub_pd(iy3,jy3);
1262             dz33             = _mm256_sub_pd(iz3,jz3);
1263
1264             /* Calculate squared distance and things based on it */
1265             rsq00            = gmx_mm256_calc_rsq_pd(dx00,dy00,dz00);
1266             rsq11            = gmx_mm256_calc_rsq_pd(dx11,dy11,dz11);
1267             rsq12            = gmx_mm256_calc_rsq_pd(dx12,dy12,dz12);
1268             rsq13            = gmx_mm256_calc_rsq_pd(dx13,dy13,dz13);
1269             rsq21            = gmx_mm256_calc_rsq_pd(dx21,dy21,dz21);
1270             rsq22            = gmx_mm256_calc_rsq_pd(dx22,dy22,dz22);
1271             rsq23            = gmx_mm256_calc_rsq_pd(dx23,dy23,dz23);
1272             rsq31            = gmx_mm256_calc_rsq_pd(dx31,dy31,dz31);
1273             rsq32            = gmx_mm256_calc_rsq_pd(dx32,dy32,dz32);
1274             rsq33            = gmx_mm256_calc_rsq_pd(dx33,dy33,dz33);
1275
1276             rinv11           = gmx_mm256_invsqrt_pd(rsq11);
1277             rinv12           = gmx_mm256_invsqrt_pd(rsq12);
1278             rinv13           = gmx_mm256_invsqrt_pd(rsq13);
1279             rinv21           = gmx_mm256_invsqrt_pd(rsq21);
1280             rinv22           = gmx_mm256_invsqrt_pd(rsq22);
1281             rinv23           = gmx_mm256_invsqrt_pd(rsq23);
1282             rinv31           = gmx_mm256_invsqrt_pd(rsq31);
1283             rinv32           = gmx_mm256_invsqrt_pd(rsq32);
1284             rinv33           = gmx_mm256_invsqrt_pd(rsq33);
1285
1286             rinvsq00         = gmx_mm256_inv_pd(rsq00);
1287             rinvsq11         = _mm256_mul_pd(rinv11,rinv11);
1288             rinvsq12         = _mm256_mul_pd(rinv12,rinv12);
1289             rinvsq13         = _mm256_mul_pd(rinv13,rinv13);
1290             rinvsq21         = _mm256_mul_pd(rinv21,rinv21);
1291             rinvsq22         = _mm256_mul_pd(rinv22,rinv22);
1292             rinvsq23         = _mm256_mul_pd(rinv23,rinv23);
1293             rinvsq31         = _mm256_mul_pd(rinv31,rinv31);
1294             rinvsq32         = _mm256_mul_pd(rinv32,rinv32);
1295             rinvsq33         = _mm256_mul_pd(rinv33,rinv33);
1296
1297             fjx0             = _mm256_setzero_pd();
1298             fjy0             = _mm256_setzero_pd();
1299             fjz0             = _mm256_setzero_pd();
1300             fjx1             = _mm256_setzero_pd();
1301             fjy1             = _mm256_setzero_pd();
1302             fjz1             = _mm256_setzero_pd();
1303             fjx2             = _mm256_setzero_pd();
1304             fjy2             = _mm256_setzero_pd();
1305             fjz2             = _mm256_setzero_pd();
1306             fjx3             = _mm256_setzero_pd();
1307             fjy3             = _mm256_setzero_pd();
1308             fjz3             = _mm256_setzero_pd();
1309
1310             /**************************
1311              * CALCULATE INTERACTIONS *
1312              **************************/
1313
1314             /* LENNARD-JONES DISPERSION/REPULSION */
1315
1316             rinvsix          = _mm256_mul_pd(_mm256_mul_pd(rinvsq00,rinvsq00),rinvsq00);
1317             fvdw             = _mm256_mul_pd(_mm256_sub_pd(_mm256_mul_pd(c12_00,rinvsix),c6_00),_mm256_mul_pd(rinvsix,rinvsq00));
1318
1319             fscal            = fvdw;
1320
1321             /* Calculate temporary vectorial force */
1322             tx               = _mm256_mul_pd(fscal,dx00);
1323             ty               = _mm256_mul_pd(fscal,dy00);
1324             tz               = _mm256_mul_pd(fscal,dz00);
1325
1326             /* Update vectorial force */
1327             fix0             = _mm256_add_pd(fix0,tx);
1328             fiy0             = _mm256_add_pd(fiy0,ty);
1329             fiz0             = _mm256_add_pd(fiz0,tz);
1330
1331             fjx0             = _mm256_add_pd(fjx0,tx);
1332             fjy0             = _mm256_add_pd(fjy0,ty);
1333             fjz0             = _mm256_add_pd(fjz0,tz);
1334
1335             /**************************
1336              * CALCULATE INTERACTIONS *
1337              **************************/
1338
1339             /* REACTION-FIELD ELECTROSTATICS */
1340             felec            = _mm256_mul_pd(qq11,_mm256_sub_pd(_mm256_mul_pd(rinv11,rinvsq11),krf2));
1341
1342             fscal            = felec;
1343
1344             /* Calculate temporary vectorial force */
1345             tx               = _mm256_mul_pd(fscal,dx11);
1346             ty               = _mm256_mul_pd(fscal,dy11);
1347             tz               = _mm256_mul_pd(fscal,dz11);
1348
1349             /* Update vectorial force */
1350             fix1             = _mm256_add_pd(fix1,tx);
1351             fiy1             = _mm256_add_pd(fiy1,ty);
1352             fiz1             = _mm256_add_pd(fiz1,tz);
1353
1354             fjx1             = _mm256_add_pd(fjx1,tx);
1355             fjy1             = _mm256_add_pd(fjy1,ty);
1356             fjz1             = _mm256_add_pd(fjz1,tz);
1357
1358             /**************************
1359              * CALCULATE INTERACTIONS *
1360              **************************/
1361
1362             /* REACTION-FIELD ELECTROSTATICS */
1363             felec            = _mm256_mul_pd(qq12,_mm256_sub_pd(_mm256_mul_pd(rinv12,rinvsq12),krf2));
1364
1365             fscal            = felec;
1366
1367             /* Calculate temporary vectorial force */
1368             tx               = _mm256_mul_pd(fscal,dx12);
1369             ty               = _mm256_mul_pd(fscal,dy12);
1370             tz               = _mm256_mul_pd(fscal,dz12);
1371
1372             /* Update vectorial force */
1373             fix1             = _mm256_add_pd(fix1,tx);
1374             fiy1             = _mm256_add_pd(fiy1,ty);
1375             fiz1             = _mm256_add_pd(fiz1,tz);
1376
1377             fjx2             = _mm256_add_pd(fjx2,tx);
1378             fjy2             = _mm256_add_pd(fjy2,ty);
1379             fjz2             = _mm256_add_pd(fjz2,tz);
1380
1381             /**************************
1382              * CALCULATE INTERACTIONS *
1383              **************************/
1384
1385             /* REACTION-FIELD ELECTROSTATICS */
1386             felec            = _mm256_mul_pd(qq13,_mm256_sub_pd(_mm256_mul_pd(rinv13,rinvsq13),krf2));
1387
1388             fscal            = felec;
1389
1390             /* Calculate temporary vectorial force */
1391             tx               = _mm256_mul_pd(fscal,dx13);
1392             ty               = _mm256_mul_pd(fscal,dy13);
1393             tz               = _mm256_mul_pd(fscal,dz13);
1394
1395             /* Update vectorial force */
1396             fix1             = _mm256_add_pd(fix1,tx);
1397             fiy1             = _mm256_add_pd(fiy1,ty);
1398             fiz1             = _mm256_add_pd(fiz1,tz);
1399
1400             fjx3             = _mm256_add_pd(fjx3,tx);
1401             fjy3             = _mm256_add_pd(fjy3,ty);
1402             fjz3             = _mm256_add_pd(fjz3,tz);
1403
1404             /**************************
1405              * CALCULATE INTERACTIONS *
1406              **************************/
1407
1408             /* REACTION-FIELD ELECTROSTATICS */
1409             felec            = _mm256_mul_pd(qq21,_mm256_sub_pd(_mm256_mul_pd(rinv21,rinvsq21),krf2));
1410
1411             fscal            = felec;
1412
1413             /* Calculate temporary vectorial force */
1414             tx               = _mm256_mul_pd(fscal,dx21);
1415             ty               = _mm256_mul_pd(fscal,dy21);
1416             tz               = _mm256_mul_pd(fscal,dz21);
1417
1418             /* Update vectorial force */
1419             fix2             = _mm256_add_pd(fix2,tx);
1420             fiy2             = _mm256_add_pd(fiy2,ty);
1421             fiz2             = _mm256_add_pd(fiz2,tz);
1422
1423             fjx1             = _mm256_add_pd(fjx1,tx);
1424             fjy1             = _mm256_add_pd(fjy1,ty);
1425             fjz1             = _mm256_add_pd(fjz1,tz);
1426
1427             /**************************
1428              * CALCULATE INTERACTIONS *
1429              **************************/
1430
1431             /* REACTION-FIELD ELECTROSTATICS */
1432             felec            = _mm256_mul_pd(qq22,_mm256_sub_pd(_mm256_mul_pd(rinv22,rinvsq22),krf2));
1433
1434             fscal            = felec;
1435
1436             /* Calculate temporary vectorial force */
1437             tx               = _mm256_mul_pd(fscal,dx22);
1438             ty               = _mm256_mul_pd(fscal,dy22);
1439             tz               = _mm256_mul_pd(fscal,dz22);
1440
1441             /* Update vectorial force */
1442             fix2             = _mm256_add_pd(fix2,tx);
1443             fiy2             = _mm256_add_pd(fiy2,ty);
1444             fiz2             = _mm256_add_pd(fiz2,tz);
1445
1446             fjx2             = _mm256_add_pd(fjx2,tx);
1447             fjy2             = _mm256_add_pd(fjy2,ty);
1448             fjz2             = _mm256_add_pd(fjz2,tz);
1449
1450             /**************************
1451              * CALCULATE INTERACTIONS *
1452              **************************/
1453
1454             /* REACTION-FIELD ELECTROSTATICS */
1455             felec            = _mm256_mul_pd(qq23,_mm256_sub_pd(_mm256_mul_pd(rinv23,rinvsq23),krf2));
1456
1457             fscal            = felec;
1458
1459             /* Calculate temporary vectorial force */
1460             tx               = _mm256_mul_pd(fscal,dx23);
1461             ty               = _mm256_mul_pd(fscal,dy23);
1462             tz               = _mm256_mul_pd(fscal,dz23);
1463
1464             /* Update vectorial force */
1465             fix2             = _mm256_add_pd(fix2,tx);
1466             fiy2             = _mm256_add_pd(fiy2,ty);
1467             fiz2             = _mm256_add_pd(fiz2,tz);
1468
1469             fjx3             = _mm256_add_pd(fjx3,tx);
1470             fjy3             = _mm256_add_pd(fjy3,ty);
1471             fjz3             = _mm256_add_pd(fjz3,tz);
1472
1473             /**************************
1474              * CALCULATE INTERACTIONS *
1475              **************************/
1476
1477             /* REACTION-FIELD ELECTROSTATICS */
1478             felec            = _mm256_mul_pd(qq31,_mm256_sub_pd(_mm256_mul_pd(rinv31,rinvsq31),krf2));
1479
1480             fscal            = felec;
1481
1482             /* Calculate temporary vectorial force */
1483             tx               = _mm256_mul_pd(fscal,dx31);
1484             ty               = _mm256_mul_pd(fscal,dy31);
1485             tz               = _mm256_mul_pd(fscal,dz31);
1486
1487             /* Update vectorial force */
1488             fix3             = _mm256_add_pd(fix3,tx);
1489             fiy3             = _mm256_add_pd(fiy3,ty);
1490             fiz3             = _mm256_add_pd(fiz3,tz);
1491
1492             fjx1             = _mm256_add_pd(fjx1,tx);
1493             fjy1             = _mm256_add_pd(fjy1,ty);
1494             fjz1             = _mm256_add_pd(fjz1,tz);
1495
1496             /**************************
1497              * CALCULATE INTERACTIONS *
1498              **************************/
1499
1500             /* REACTION-FIELD ELECTROSTATICS */
1501             felec            = _mm256_mul_pd(qq32,_mm256_sub_pd(_mm256_mul_pd(rinv32,rinvsq32),krf2));
1502
1503             fscal            = felec;
1504
1505             /* Calculate temporary vectorial force */
1506             tx               = _mm256_mul_pd(fscal,dx32);
1507             ty               = _mm256_mul_pd(fscal,dy32);
1508             tz               = _mm256_mul_pd(fscal,dz32);
1509
1510             /* Update vectorial force */
1511             fix3             = _mm256_add_pd(fix3,tx);
1512             fiy3             = _mm256_add_pd(fiy3,ty);
1513             fiz3             = _mm256_add_pd(fiz3,tz);
1514
1515             fjx2             = _mm256_add_pd(fjx2,tx);
1516             fjy2             = _mm256_add_pd(fjy2,ty);
1517             fjz2             = _mm256_add_pd(fjz2,tz);
1518
1519             /**************************
1520              * CALCULATE INTERACTIONS *
1521              **************************/
1522
1523             /* REACTION-FIELD ELECTROSTATICS */
1524             felec            = _mm256_mul_pd(qq33,_mm256_sub_pd(_mm256_mul_pd(rinv33,rinvsq33),krf2));
1525
1526             fscal            = felec;
1527
1528             /* Calculate temporary vectorial force */
1529             tx               = _mm256_mul_pd(fscal,dx33);
1530             ty               = _mm256_mul_pd(fscal,dy33);
1531             tz               = _mm256_mul_pd(fscal,dz33);
1532
1533             /* Update vectorial force */
1534             fix3             = _mm256_add_pd(fix3,tx);
1535             fiy3             = _mm256_add_pd(fiy3,ty);
1536             fiz3             = _mm256_add_pd(fiz3,tz);
1537
1538             fjx3             = _mm256_add_pd(fjx3,tx);
1539             fjy3             = _mm256_add_pd(fjy3,ty);
1540             fjz3             = _mm256_add_pd(fjz3,tz);
1541
1542             fjptrA             = f+j_coord_offsetA;
1543             fjptrB             = f+j_coord_offsetB;
1544             fjptrC             = f+j_coord_offsetC;
1545             fjptrD             = f+j_coord_offsetD;
1546
1547             gmx_mm256_decrement_4rvec_4ptr_swizzle_pd(fjptrA,fjptrB,fjptrC,fjptrD,
1548                                                       fjx0,fjy0,fjz0,fjx1,fjy1,fjz1,
1549                                                       fjx2,fjy2,fjz2,fjx3,fjy3,fjz3);
1550
1551             /* Inner loop uses 273 flops */
1552         }
1553
1554         if(jidx<j_index_end)
1555         {
1556
1557             /* Get j neighbor index, and coordinate index */
1558             jnrlistA         = jjnr[jidx];
1559             jnrlistB         = jjnr[jidx+1];
1560             jnrlistC         = jjnr[jidx+2];
1561             jnrlistD         = jjnr[jidx+3];
1562             /* Sign of each element will be negative for non-real atoms.
1563              * This mask will be 0xFFFFFFFF for dummy entries and 0x0 for real ones,
1564              * so use it as val = _mm_andnot_pd(mask,val) to clear dummy entries.
1565              */
1566             tmpmask0 = gmx_mm_castsi128_ps(_mm_cmplt_epi32(_mm_loadu_si128((const __m128i *)(jjnr+jidx)),_mm_setzero_si128()));
1567
1568             tmpmask1 = _mm_permute_ps(tmpmask0,_GMX_MM_PERMUTE(3,3,2,2));
1569             tmpmask0 = _mm_permute_ps(tmpmask0,_GMX_MM_PERMUTE(1,1,0,0));
1570             dummy_mask = _mm256_castps_pd(gmx_mm256_set_m128(tmpmask1,tmpmask0));
1571
1572             jnrA       = (jnrlistA>=0) ? jnrlistA : 0;
1573             jnrB       = (jnrlistB>=0) ? jnrlistB : 0;
1574             jnrC       = (jnrlistC>=0) ? jnrlistC : 0;
1575             jnrD       = (jnrlistD>=0) ? jnrlistD : 0;
1576             j_coord_offsetA  = DIM*jnrA;
1577             j_coord_offsetB  = DIM*jnrB;
1578             j_coord_offsetC  = DIM*jnrC;
1579             j_coord_offsetD  = DIM*jnrD;
1580
1581             /* load j atom coordinates */
1582             gmx_mm256_load_4rvec_4ptr_swizzle_pd(x+j_coord_offsetA,x+j_coord_offsetB,
1583                                                  x+j_coord_offsetC,x+j_coord_offsetD,
1584                                                  &jx0,&jy0,&jz0,&jx1,&jy1,&jz1,&jx2,
1585                                                  &jy2,&jz2,&jx3,&jy3,&jz3);
1586
1587             /* Calculate displacement vector */
1588             dx00             = _mm256_sub_pd(ix0,jx0);
1589             dy00             = _mm256_sub_pd(iy0,jy0);
1590             dz00             = _mm256_sub_pd(iz0,jz0);
1591             dx11             = _mm256_sub_pd(ix1,jx1);
1592             dy11             = _mm256_sub_pd(iy1,jy1);
1593             dz11             = _mm256_sub_pd(iz1,jz1);
1594             dx12             = _mm256_sub_pd(ix1,jx2);
1595             dy12             = _mm256_sub_pd(iy1,jy2);
1596             dz12             = _mm256_sub_pd(iz1,jz2);
1597             dx13             = _mm256_sub_pd(ix1,jx3);
1598             dy13             = _mm256_sub_pd(iy1,jy3);
1599             dz13             = _mm256_sub_pd(iz1,jz3);
1600             dx21             = _mm256_sub_pd(ix2,jx1);
1601             dy21             = _mm256_sub_pd(iy2,jy1);
1602             dz21             = _mm256_sub_pd(iz2,jz1);
1603             dx22             = _mm256_sub_pd(ix2,jx2);
1604             dy22             = _mm256_sub_pd(iy2,jy2);
1605             dz22             = _mm256_sub_pd(iz2,jz2);
1606             dx23             = _mm256_sub_pd(ix2,jx3);
1607             dy23             = _mm256_sub_pd(iy2,jy3);
1608             dz23             = _mm256_sub_pd(iz2,jz3);
1609             dx31             = _mm256_sub_pd(ix3,jx1);
1610             dy31             = _mm256_sub_pd(iy3,jy1);
1611             dz31             = _mm256_sub_pd(iz3,jz1);
1612             dx32             = _mm256_sub_pd(ix3,jx2);
1613             dy32             = _mm256_sub_pd(iy3,jy2);
1614             dz32             = _mm256_sub_pd(iz3,jz2);
1615             dx33             = _mm256_sub_pd(ix3,jx3);
1616             dy33             = _mm256_sub_pd(iy3,jy3);
1617             dz33             = _mm256_sub_pd(iz3,jz3);
1618
1619             /* Calculate squared distance and things based on it */
1620             rsq00            = gmx_mm256_calc_rsq_pd(dx00,dy00,dz00);
1621             rsq11            = gmx_mm256_calc_rsq_pd(dx11,dy11,dz11);
1622             rsq12            = gmx_mm256_calc_rsq_pd(dx12,dy12,dz12);
1623             rsq13            = gmx_mm256_calc_rsq_pd(dx13,dy13,dz13);
1624             rsq21            = gmx_mm256_calc_rsq_pd(dx21,dy21,dz21);
1625             rsq22            = gmx_mm256_calc_rsq_pd(dx22,dy22,dz22);
1626             rsq23            = gmx_mm256_calc_rsq_pd(dx23,dy23,dz23);
1627             rsq31            = gmx_mm256_calc_rsq_pd(dx31,dy31,dz31);
1628             rsq32            = gmx_mm256_calc_rsq_pd(dx32,dy32,dz32);
1629             rsq33            = gmx_mm256_calc_rsq_pd(dx33,dy33,dz33);
1630
1631             rinv11           = gmx_mm256_invsqrt_pd(rsq11);
1632             rinv12           = gmx_mm256_invsqrt_pd(rsq12);
1633             rinv13           = gmx_mm256_invsqrt_pd(rsq13);
1634             rinv21           = gmx_mm256_invsqrt_pd(rsq21);
1635             rinv22           = gmx_mm256_invsqrt_pd(rsq22);
1636             rinv23           = gmx_mm256_invsqrt_pd(rsq23);
1637             rinv31           = gmx_mm256_invsqrt_pd(rsq31);
1638             rinv32           = gmx_mm256_invsqrt_pd(rsq32);
1639             rinv33           = gmx_mm256_invsqrt_pd(rsq33);
1640
1641             rinvsq00         = gmx_mm256_inv_pd(rsq00);
1642             rinvsq11         = _mm256_mul_pd(rinv11,rinv11);
1643             rinvsq12         = _mm256_mul_pd(rinv12,rinv12);
1644             rinvsq13         = _mm256_mul_pd(rinv13,rinv13);
1645             rinvsq21         = _mm256_mul_pd(rinv21,rinv21);
1646             rinvsq22         = _mm256_mul_pd(rinv22,rinv22);
1647             rinvsq23         = _mm256_mul_pd(rinv23,rinv23);
1648             rinvsq31         = _mm256_mul_pd(rinv31,rinv31);
1649             rinvsq32         = _mm256_mul_pd(rinv32,rinv32);
1650             rinvsq33         = _mm256_mul_pd(rinv33,rinv33);
1651
1652             fjx0             = _mm256_setzero_pd();
1653             fjy0             = _mm256_setzero_pd();
1654             fjz0             = _mm256_setzero_pd();
1655             fjx1             = _mm256_setzero_pd();
1656             fjy1             = _mm256_setzero_pd();
1657             fjz1             = _mm256_setzero_pd();
1658             fjx2             = _mm256_setzero_pd();
1659             fjy2             = _mm256_setzero_pd();
1660             fjz2             = _mm256_setzero_pd();
1661             fjx3             = _mm256_setzero_pd();
1662             fjy3             = _mm256_setzero_pd();
1663             fjz3             = _mm256_setzero_pd();
1664
1665             /**************************
1666              * CALCULATE INTERACTIONS *
1667              **************************/
1668
1669             /* LENNARD-JONES DISPERSION/REPULSION */
1670
1671             rinvsix          = _mm256_mul_pd(_mm256_mul_pd(rinvsq00,rinvsq00),rinvsq00);
1672             fvdw             = _mm256_mul_pd(_mm256_sub_pd(_mm256_mul_pd(c12_00,rinvsix),c6_00),_mm256_mul_pd(rinvsix,rinvsq00));
1673
1674             fscal            = fvdw;
1675
1676             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
1677
1678             /* Calculate temporary vectorial force */
1679             tx               = _mm256_mul_pd(fscal,dx00);
1680             ty               = _mm256_mul_pd(fscal,dy00);
1681             tz               = _mm256_mul_pd(fscal,dz00);
1682
1683             /* Update vectorial force */
1684             fix0             = _mm256_add_pd(fix0,tx);
1685             fiy0             = _mm256_add_pd(fiy0,ty);
1686             fiz0             = _mm256_add_pd(fiz0,tz);
1687
1688             fjx0             = _mm256_add_pd(fjx0,tx);
1689             fjy0             = _mm256_add_pd(fjy0,ty);
1690             fjz0             = _mm256_add_pd(fjz0,tz);
1691
1692             /**************************
1693              * CALCULATE INTERACTIONS *
1694              **************************/
1695
1696             /* REACTION-FIELD ELECTROSTATICS */
1697             felec            = _mm256_mul_pd(qq11,_mm256_sub_pd(_mm256_mul_pd(rinv11,rinvsq11),krf2));
1698
1699             fscal            = felec;
1700
1701             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
1702
1703             /* Calculate temporary vectorial force */
1704             tx               = _mm256_mul_pd(fscal,dx11);
1705             ty               = _mm256_mul_pd(fscal,dy11);
1706             tz               = _mm256_mul_pd(fscal,dz11);
1707
1708             /* Update vectorial force */
1709             fix1             = _mm256_add_pd(fix1,tx);
1710             fiy1             = _mm256_add_pd(fiy1,ty);
1711             fiz1             = _mm256_add_pd(fiz1,tz);
1712
1713             fjx1             = _mm256_add_pd(fjx1,tx);
1714             fjy1             = _mm256_add_pd(fjy1,ty);
1715             fjz1             = _mm256_add_pd(fjz1,tz);
1716
1717             /**************************
1718              * CALCULATE INTERACTIONS *
1719              **************************/
1720
1721             /* REACTION-FIELD ELECTROSTATICS */
1722             felec            = _mm256_mul_pd(qq12,_mm256_sub_pd(_mm256_mul_pd(rinv12,rinvsq12),krf2));
1723
1724             fscal            = felec;
1725
1726             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
1727
1728             /* Calculate temporary vectorial force */
1729             tx               = _mm256_mul_pd(fscal,dx12);
1730             ty               = _mm256_mul_pd(fscal,dy12);
1731             tz               = _mm256_mul_pd(fscal,dz12);
1732
1733             /* Update vectorial force */
1734             fix1             = _mm256_add_pd(fix1,tx);
1735             fiy1             = _mm256_add_pd(fiy1,ty);
1736             fiz1             = _mm256_add_pd(fiz1,tz);
1737
1738             fjx2             = _mm256_add_pd(fjx2,tx);
1739             fjy2             = _mm256_add_pd(fjy2,ty);
1740             fjz2             = _mm256_add_pd(fjz2,tz);
1741
1742             /**************************
1743              * CALCULATE INTERACTIONS *
1744              **************************/
1745
1746             /* REACTION-FIELD ELECTROSTATICS */
1747             felec            = _mm256_mul_pd(qq13,_mm256_sub_pd(_mm256_mul_pd(rinv13,rinvsq13),krf2));
1748
1749             fscal            = felec;
1750
1751             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
1752
1753             /* Calculate temporary vectorial force */
1754             tx               = _mm256_mul_pd(fscal,dx13);
1755             ty               = _mm256_mul_pd(fscal,dy13);
1756             tz               = _mm256_mul_pd(fscal,dz13);
1757
1758             /* Update vectorial force */
1759             fix1             = _mm256_add_pd(fix1,tx);
1760             fiy1             = _mm256_add_pd(fiy1,ty);
1761             fiz1             = _mm256_add_pd(fiz1,tz);
1762
1763             fjx3             = _mm256_add_pd(fjx3,tx);
1764             fjy3             = _mm256_add_pd(fjy3,ty);
1765             fjz3             = _mm256_add_pd(fjz3,tz);
1766
1767             /**************************
1768              * CALCULATE INTERACTIONS *
1769              **************************/
1770
1771             /* REACTION-FIELD ELECTROSTATICS */
1772             felec            = _mm256_mul_pd(qq21,_mm256_sub_pd(_mm256_mul_pd(rinv21,rinvsq21),krf2));
1773
1774             fscal            = felec;
1775
1776             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
1777
1778             /* Calculate temporary vectorial force */
1779             tx               = _mm256_mul_pd(fscal,dx21);
1780             ty               = _mm256_mul_pd(fscal,dy21);
1781             tz               = _mm256_mul_pd(fscal,dz21);
1782
1783             /* Update vectorial force */
1784             fix2             = _mm256_add_pd(fix2,tx);
1785             fiy2             = _mm256_add_pd(fiy2,ty);
1786             fiz2             = _mm256_add_pd(fiz2,tz);
1787
1788             fjx1             = _mm256_add_pd(fjx1,tx);
1789             fjy1             = _mm256_add_pd(fjy1,ty);
1790             fjz1             = _mm256_add_pd(fjz1,tz);
1791
1792             /**************************
1793              * CALCULATE INTERACTIONS *
1794              **************************/
1795
1796             /* REACTION-FIELD ELECTROSTATICS */
1797             felec            = _mm256_mul_pd(qq22,_mm256_sub_pd(_mm256_mul_pd(rinv22,rinvsq22),krf2));
1798
1799             fscal            = felec;
1800
1801             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
1802
1803             /* Calculate temporary vectorial force */
1804             tx               = _mm256_mul_pd(fscal,dx22);
1805             ty               = _mm256_mul_pd(fscal,dy22);
1806             tz               = _mm256_mul_pd(fscal,dz22);
1807
1808             /* Update vectorial force */
1809             fix2             = _mm256_add_pd(fix2,tx);
1810             fiy2             = _mm256_add_pd(fiy2,ty);
1811             fiz2             = _mm256_add_pd(fiz2,tz);
1812
1813             fjx2             = _mm256_add_pd(fjx2,tx);
1814             fjy2             = _mm256_add_pd(fjy2,ty);
1815             fjz2             = _mm256_add_pd(fjz2,tz);
1816
1817             /**************************
1818              * CALCULATE INTERACTIONS *
1819              **************************/
1820
1821             /* REACTION-FIELD ELECTROSTATICS */
1822             felec            = _mm256_mul_pd(qq23,_mm256_sub_pd(_mm256_mul_pd(rinv23,rinvsq23),krf2));
1823
1824             fscal            = felec;
1825
1826             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
1827
1828             /* Calculate temporary vectorial force */
1829             tx               = _mm256_mul_pd(fscal,dx23);
1830             ty               = _mm256_mul_pd(fscal,dy23);
1831             tz               = _mm256_mul_pd(fscal,dz23);
1832
1833             /* Update vectorial force */
1834             fix2             = _mm256_add_pd(fix2,tx);
1835             fiy2             = _mm256_add_pd(fiy2,ty);
1836             fiz2             = _mm256_add_pd(fiz2,tz);
1837
1838             fjx3             = _mm256_add_pd(fjx3,tx);
1839             fjy3             = _mm256_add_pd(fjy3,ty);
1840             fjz3             = _mm256_add_pd(fjz3,tz);
1841
1842             /**************************
1843              * CALCULATE INTERACTIONS *
1844              **************************/
1845
1846             /* REACTION-FIELD ELECTROSTATICS */
1847             felec            = _mm256_mul_pd(qq31,_mm256_sub_pd(_mm256_mul_pd(rinv31,rinvsq31),krf2));
1848
1849             fscal            = felec;
1850
1851             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
1852
1853             /* Calculate temporary vectorial force */
1854             tx               = _mm256_mul_pd(fscal,dx31);
1855             ty               = _mm256_mul_pd(fscal,dy31);
1856             tz               = _mm256_mul_pd(fscal,dz31);
1857
1858             /* Update vectorial force */
1859             fix3             = _mm256_add_pd(fix3,tx);
1860             fiy3             = _mm256_add_pd(fiy3,ty);
1861             fiz3             = _mm256_add_pd(fiz3,tz);
1862
1863             fjx1             = _mm256_add_pd(fjx1,tx);
1864             fjy1             = _mm256_add_pd(fjy1,ty);
1865             fjz1             = _mm256_add_pd(fjz1,tz);
1866
1867             /**************************
1868              * CALCULATE INTERACTIONS *
1869              **************************/
1870
1871             /* REACTION-FIELD ELECTROSTATICS */
1872             felec            = _mm256_mul_pd(qq32,_mm256_sub_pd(_mm256_mul_pd(rinv32,rinvsq32),krf2));
1873
1874             fscal            = felec;
1875
1876             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
1877
1878             /* Calculate temporary vectorial force */
1879             tx               = _mm256_mul_pd(fscal,dx32);
1880             ty               = _mm256_mul_pd(fscal,dy32);
1881             tz               = _mm256_mul_pd(fscal,dz32);
1882
1883             /* Update vectorial force */
1884             fix3             = _mm256_add_pd(fix3,tx);
1885             fiy3             = _mm256_add_pd(fiy3,ty);
1886             fiz3             = _mm256_add_pd(fiz3,tz);
1887
1888             fjx2             = _mm256_add_pd(fjx2,tx);
1889             fjy2             = _mm256_add_pd(fjy2,ty);
1890             fjz2             = _mm256_add_pd(fjz2,tz);
1891
1892             /**************************
1893              * CALCULATE INTERACTIONS *
1894              **************************/
1895
1896             /* REACTION-FIELD ELECTROSTATICS */
1897             felec            = _mm256_mul_pd(qq33,_mm256_sub_pd(_mm256_mul_pd(rinv33,rinvsq33),krf2));
1898
1899             fscal            = felec;
1900
1901             fscal            = _mm256_andnot_pd(dummy_mask,fscal);
1902
1903             /* Calculate temporary vectorial force */
1904             tx               = _mm256_mul_pd(fscal,dx33);
1905             ty               = _mm256_mul_pd(fscal,dy33);
1906             tz               = _mm256_mul_pd(fscal,dz33);
1907
1908             /* Update vectorial force */
1909             fix3             = _mm256_add_pd(fix3,tx);
1910             fiy3             = _mm256_add_pd(fiy3,ty);
1911             fiz3             = _mm256_add_pd(fiz3,tz);
1912
1913             fjx3             = _mm256_add_pd(fjx3,tx);
1914             fjy3             = _mm256_add_pd(fjy3,ty);
1915             fjz3             = _mm256_add_pd(fjz3,tz);
1916
1917             fjptrA             = (jnrlistA>=0) ? f+j_coord_offsetA : scratch;
1918             fjptrB             = (jnrlistB>=0) ? f+j_coord_offsetB : scratch;
1919             fjptrC             = (jnrlistC>=0) ? f+j_coord_offsetC : scratch;
1920             fjptrD             = (jnrlistD>=0) ? f+j_coord_offsetD : scratch;
1921
1922             gmx_mm256_decrement_4rvec_4ptr_swizzle_pd(fjptrA,fjptrB,fjptrC,fjptrD,
1923                                                       fjx0,fjy0,fjz0,fjx1,fjy1,fjz1,
1924                                                       fjx2,fjy2,fjz2,fjx3,fjy3,fjz3);
1925
1926             /* Inner loop uses 273 flops */
1927         }
1928
1929         /* End of innermost loop */
1930
1931         gmx_mm256_update_iforce_4atom_swizzle_pd(fix0,fiy0,fiz0,fix1,fiy1,fiz1,fix2,fiy2,fiz2,fix3,fiy3,fiz3,
1932                                                  f+i_coord_offset,fshift+i_shift_offset);
1933
1934         /* Increment number of inner iterations */
1935         inneriter                  += j_index_end - j_index_start;
1936
1937         /* Outer loop uses 24 flops */
1938     }
1939
1940     /* Increment number of outer iterations */
1941     outeriter        += nri;
1942
1943     /* Update outer/inner flops */
1944
1945     inc_nrnb(nrnb,eNR_NBKERNEL_ELEC_VDW_W4W4_F,outeriter*24 + inneriter*273);
1946 }