@@ -141,7 +141,20 @@ void phasing_hmm::INIT_PEAK_HET(int curr_het)
141141{
142142 const std::array <__m256, 2 > emits = {_mm256_load_ps (&EMIT0 [curr_het][0 ]),_mm256_load_ps (&EMIT1 [curr_het][0 ])};
143143 __m256 _sum = _mm256_set1_ps (0 .0f );
144- for (int k = 0 , i = 0 ; k != C->n_states ; ++k, i += HAP_NUMBER )
144+ const unsigned int n_states = C->n_states ;
145+ const unsigned int n_states_full = (n_states / 8 ) * 8 ;
146+ int k = 0 , i = 0 ;
147+ for ( ; k < n_states_full ; k += 8 , i += 8 * HAP_NUMBER )
148+ {
149+ const unsigned char byte = C->Hvar .getByte (curr_rel_locus, k);
150+ for (int b = 0 ; b < 8 ; ++b)
151+ {
152+ const bool ah = (byte >> (7 - b)) & 1 ;
153+ _sum = _mm256_add_ps (_sum, emits[ah]);
154+ _mm256_store_ps (&prob[i + b * HAP_NUMBER ], emits[ah]);
155+ }
156+ }
157+ for ( ; k < n_states ; ++k, i += HAP_NUMBER )
145158 {
146159 const bool ah = C->Hvar .get (curr_rel_locus, k);
147160 _sum = _mm256_add_ps (_sum, emits[ah]);
@@ -156,7 +169,20 @@ void phasing_hmm::INIT_PEAK_HOM(bool ag)
156169{
157170 const std::array <__m256, 2 > emits = {_mm256_set1_ps (1 .0f ),_mm256_set1_ps (C->ed_phs /C->ee_phs )};
158171 __m256 _sum = _mm256_set1_ps (0 .0f );
159- for (int k = 0 , i = 0 ; k != C->n_states ; ++k, i += HAP_NUMBER )
172+ const unsigned int n_states = C->n_states ;
173+ const unsigned int n_states_full = (n_states / 8 ) * 8 ;
174+ int k = 0 , i = 0 ;
175+ for ( ; k < n_states_full ; k += 8 , i += 8 * HAP_NUMBER )
176+ {
177+ const unsigned char byte = C->Hvar .getByte (curr_rel_locus, k);
178+ for (int b = 0 ; b < 8 ; ++b)
179+ {
180+ const bool ag_ah = ((byte >> (7 - b)) & 1 ) != ag;
181+ _sum = _mm256_add_ps (_sum, emits[ag_ah]);
182+ _mm256_store_ps (&prob[i + b * HAP_NUMBER ], emits[ag_ah]);
183+ }
184+ }
185+ for ( ; k < n_states ; ++k, i += HAP_NUMBER )
160186 {
161187 const bool ag_ah = C->Hvar .get (curr_rel_locus, k)!=ag;
162188 _sum = _mm256_add_ps (_sum, emits[ag_ah]);
@@ -180,7 +206,21 @@ void phasing_hmm::RUN_PEAK_HET(int curr_het)
180206 const __m256 _nt = _mm256_set1_ps (nt / probSumT);
181207 const std::array <__m256, 2 > emits = {_mm256_load_ps (&EMIT0 [curr_het][0 ]),_mm256_load_ps (&EMIT1 [curr_het][0 ])};
182208 __m256 _sum = _mm256_set1_ps (0 .0f );
183- for (int k = 0 , i = 0 ; k != C->n_states ; ++k, i += HAP_NUMBER )
209+ const unsigned int n_states = C->n_states ;
210+ const unsigned int n_states_full = (n_states / 8 ) * 8 ;
211+ int k = 0 , i = 0 ;
212+ for ( ; k < n_states_full ; k += 8 , i += 8 * HAP_NUMBER )
213+ {
214+ const unsigned char byte = C->Hvar .getByte (curr_rel_locus, k);
215+ for (int b = 0 ; b < 8 ; ++b)
216+ {
217+ const bool ah = (byte >> (7 - b)) & 1 ;
218+ const __m256 _prob_curr = _mm256_mul_ps (_mm256_fmadd_ps (_mm256_load_ps (&prob[i + b * HAP_NUMBER ]), _nt, _tFreq), emits[ah]);
219+ _sum = _mm256_add_ps (_sum, _prob_curr);
220+ _mm256_store_ps (&prob[i + b * HAP_NUMBER ], _prob_curr);
221+ }
222+ }
223+ for ( ; k < n_states ; ++k, i += HAP_NUMBER )
184224 {
185225 const bool ah = C->Hvar .get (curr_rel_locus, k);
186226 const __m256 _prob_curr = _mm256_mul_ps (_mm256_fmadd_ps (_mm256_load_ps (&prob[i]), _nt, _tFreq), emits[ah]);
@@ -198,7 +238,23 @@ void phasing_hmm::RUN_PEAK_HOM(bool ag)
198238 const __m256 _nt = _mm256_set1_ps (nt / probSumT);
199239 const __m256 _mism = _mm256_set1_ps (C->ed_phs /C->ee_phs );
200240 __m256 _sum = _mm256_set1_ps (0 .0f );
201- for (int k = 0 , i = 0 ; k != C->n_states ; ++k, i += HAP_NUMBER )
241+ const unsigned int n_states = C->n_states ;
242+ const unsigned int n_states_full = (n_states / 8 ) * 8 ;
243+ int k = 0 , i = 0 ;
244+ for ( ; k < n_states_full ; k += 8 , i += 8 * HAP_NUMBER )
245+ {
246+ const unsigned char byte = C->Hvar .getByte (curr_rel_locus, k);
247+ for (int b = 0 ; b < 8 ; ++b)
248+ {
249+ const bool ah = (byte >> (7 - b)) & 1 ;
250+ const __m256 _prob_prev = _mm256_load_ps (&prob[i + b * HAP_NUMBER ]);
251+ __m256 _prob_curr = _mm256_fmadd_ps (_prob_prev, _nt, _tFreq);
252+ if (ag!=ah) _prob_curr = _mm256_mul_ps (_prob_curr, _mism);
253+ _sum = _mm256_add_ps (_sum, _prob_curr);
254+ _mm256_store_ps (&prob[i + b * HAP_NUMBER ], _prob_curr);
255+ }
256+ }
257+ for ( ; k < n_states ; ++k, i += HAP_NUMBER )
202258 {
203259 const bool ah = C->Hvar .get (curr_rel_locus, k);
204260 const __m256 _prob_prev = _mm256_load_ps (&prob[i]);
@@ -234,7 +290,21 @@ void phasing_hmm::COLLAPSE_PEAK_HET(int curr_het)
234290 const __m256 _nt = _mm256_set1_ps (nt / probSumT);
235291 const std::array <__m256, 2 > emits = {_mm256_load_ps (&EMIT0 [curr_het][0 ]),_mm256_load_ps (&EMIT1 [curr_het][0 ])};
236292 __m256 _sum = _mm256_set1_ps (0 .0f );
237- for (int k = 0 , i = 0 ; k != C->n_states ; ++k, i += HAP_NUMBER )
293+ const unsigned int n_states = C->n_states ;
294+ const unsigned int n_states_full = (n_states / 8 ) * 8 ;
295+ int k = 0 , i = 0 ;
296+ for ( ; k < n_states_full ; k += 8 , i += 8 * HAP_NUMBER )
297+ {
298+ const unsigned char byte = C->Hvar .getByte (curr_rel_locus, k);
299+ for (int b = 0 ; b < 8 ; ++b)
300+ {
301+ const bool ah = (byte >> (7 - b)) & 1 ;
302+ const __m256 _prob_curr = _mm256_mul_ps (_mm256_fmadd_ps (_mm256_set1_ps (probSumK[k + b]), _nt, _tFreq), emits[ah]);
303+ _sum = _mm256_add_ps (_sum, _prob_curr);
304+ _mm256_store_ps (&prob[i + b * HAP_NUMBER ], _prob_curr);
305+ }
306+ }
307+ for ( ; k < n_states ; ++k, i += HAP_NUMBER )
238308 {
239309 const bool ah = C->Hvar .get (curr_rel_locus, k);
240310 const __m256 _prob_curr = _mm256_mul_ps (_mm256_fmadd_ps (_mm256_set1_ps (probSumK[k]), _nt, _tFreq), emits[ah]);
@@ -252,8 +322,22 @@ void phasing_hmm::COLLAPSE_PEAK_HOM(bool ag)
252322 const __m256 _nt = _mm256_set1_ps (nt / probSumT);
253323 __m256 _sum = _mm256_set1_ps (0 .0f );
254324 const __m256 _mism = _mm256_set1_ps (C->ed_phs /C->ee_phs );
255-
256- for (int k = 0 , i = 0 ; k != C->n_states ; ++k, i += HAP_NUMBER )
325+ const unsigned int n_states = C->n_states ;
326+ const unsigned int n_states_full = (n_states / 8 ) * 8 ;
327+ int k = 0 , i = 0 ;
328+ for ( ; k < n_states_full ; k += 8 , i += 8 * HAP_NUMBER )
329+ {
330+ const unsigned char byte = C->Hvar .getByte (curr_rel_locus, k);
331+ for (int b = 0 ; b < 8 ; ++b)
332+ {
333+ const bool ah = (byte >> (7 - b)) & 1 ;
334+ __m256 _prob_curr = _mm256_fmadd_ps (_mm256_set1_ps (probSumK[k + b]), _nt, _tFreq);
335+ if (ag!=ah) _prob_curr = _mm256_mul_ps (_prob_curr, _mism);
336+ _sum = _mm256_add_ps (_sum, _prob_curr);
337+ _mm256_store_ps (&prob[i + b * HAP_NUMBER ], _prob_curr);
338+ }
339+ }
340+ for ( ; k < n_states ; ++k, i += HAP_NUMBER )
257341 {
258342 const bool ah = C->Hvar .get (curr_rel_locus, k);
259343 __m256 _prob_curr = _mm256_fmadd_ps (_mm256_set1_ps (probSumK[k]), _nt, _tFreq);
@@ -337,8 +421,21 @@ void phasing_hmm::IMPUTE_FLAT_HET()
337421 _scaleR = _mm256_div_ps (_one, _scaleR);
338422 _scaleL = _mm256_div_ps (_one, _scaleL);
339423 std::array <__m256, 2 > sums = {_mm256_set1_ps (0 .0f ),_mm256_set1_ps (0 .0f )};
340-
341- for (int k = 0 , i = 0 ; k != C->n_states ; ++k, i += HAP_NUMBER ) {
424+ const unsigned int n_states = C->n_states ;
425+ const unsigned int n_states_full = (n_states / 8 ) * 8 ;
426+ int k = 0 , i = 0 ;
427+ for ( ; k < n_states_full ; k += 8 , i += 8 * HAP_NUMBER )
428+ {
429+ const unsigned char byte = C->Hvar .getByte (curr_rel_locus, k);
430+ for (int b = 0 ; b < 8 ; ++b)
431+ {
432+ const bool ah = (byte >> (7 - b)) & 1 ;
433+ const __m256 _p1 = _mm256_mul_ps (_mm256_load_ps (&imputeProb[curr_missing_locus*states_haps + i + b * HAP_NUMBER ]), _scaleR);
434+ const __m256 _p2 = _mm256_mul_ps (_mm256_load_ps (&prob[i + b * HAP_NUMBER ]), _scaleL);
435+ sums[ah] = _mm256_add_ps (sums[ah], _mm256_mul_ps (_p1,_p2));
436+ }
437+ }
438+ for ( ; k < n_states ; ++k, i += HAP_NUMBER ) {
342439 const bool ah = C->Hvar .get (curr_rel_locus, k);
343440 const __m256 _p1 = _mm256_mul_ps (_mm256_load_ps (&imputeProb[curr_missing_locus*states_haps + i]), _scaleR);
344441 const __m256 _p2 = _mm256_mul_ps (_mm256_load_ps (&prob[i]), _scaleL);
0 commit comments