GNU Radio 3.6.5 C++ API
|
00001 #ifndef INCLUDED_volk_8ic_deinterleave_16i_x2_a_H 00002 #define INCLUDED_volk_8ic_deinterleave_16i_x2_a_H 00003 00004 #include <inttypes.h> 00005 #include <stdio.h> 00006 00007 #ifdef LV_HAVE_SSE4_1 00008 #include <smmintrin.h> 00009 /*! 00010 \brief Deinterleaves the complex 8 bit vector into I & Q 16 bit vector data 00011 \param complexVector The complex input vector 00012 \param iBuffer The I buffer output data 00013 \param qBuffer The Q buffer output data 00014 \param num_points The number of complex data values to be deinterleaved 00015 */ 00016 static inline void volk_8ic_deinterleave_16i_x2_a_sse4_1(int16_t* iBuffer, int16_t* qBuffer, const lv_8sc_t* complexVector, unsigned int num_points){ 00017 unsigned int number = 0; 00018 const int8_t* complexVectorPtr = (int8_t*)complexVector; 00019 int16_t* iBufferPtr = iBuffer; 00020 int16_t* qBufferPtr = qBuffer; 00021 __m128i iMoveMask = _mm_set_epi8(0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 14, 12, 10, 8, 6, 4, 2, 0); 00022 __m128i qMoveMask = _mm_set_epi8(0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 0x80, 15, 13, 11, 9, 7, 5, 3, 1); 00023 __m128i complexVal, iOutputVal, qOutputVal; 00024 00025 unsigned int eighthPoints = num_points / 8; 00026 00027 for(number = 0; number < eighthPoints; number++){ 00028 complexVal = _mm_load_si128((__m128i*)complexVectorPtr); complexVectorPtr += 16; 00029 00030 iOutputVal = _mm_shuffle_epi8(complexVal, iMoveMask); 00031 qOutputVal = _mm_shuffle_epi8(complexVal, qMoveMask); 00032 00033 iOutputVal = _mm_cvtepi8_epi16(iOutputVal); 00034 iOutputVal = _mm_slli_epi16(iOutputVal, 8); 00035 00036 qOutputVal = _mm_cvtepi8_epi16(qOutputVal); 00037 qOutputVal = _mm_slli_epi16(qOutputVal, 8); 00038 00039 _mm_store_si128((__m128i*)iBufferPtr, iOutputVal); 00040 _mm_store_si128((__m128i*)qBufferPtr, qOutputVal); 00041 00042 iBufferPtr += 8; 00043 qBufferPtr += 8; 00044 } 00045 00046 number = eighthPoints * 8; 00047 for(; number < num_points; number++){ 00048 *iBufferPtr++ = ((int16_t)*complexVectorPtr++) * 256; 00049 *qBufferPtr++ = ((int16_t)*complexVectorPtr++) * 256; 00050 } 00051 } 00052 #endif /* LV_HAVE_SSE4_1 */ 00053 00054 #ifdef LV_HAVE_GENERIC 00055 /*! 00056 \brief Deinterleaves the complex 8 bit vector into I & Q 16 bit vector data 00057 \param complexVector The complex input vector 00058 \param iBuffer The I buffer output data 00059 \param qBuffer The Q buffer output data 00060 \param num_points The number of complex data values to be deinterleaved 00061 */ 00062 static inline void volk_8ic_deinterleave_16i_x2_a_generic(int16_t* iBuffer, int16_t* qBuffer, const lv_8sc_t* complexVector, unsigned int num_points){ 00063 const int8_t* complexVectorPtr = (const int8_t*)complexVector; 00064 int16_t* iBufferPtr = iBuffer; 00065 int16_t* qBufferPtr = qBuffer; 00066 unsigned int number; 00067 for(number = 0; number < num_points; number++){ 00068 *iBufferPtr++ = (int16_t)(*complexVectorPtr++)*256; 00069 *qBufferPtr++ = (int16_t)(*complexVectorPtr++)*256; 00070 } 00071 } 00072 #endif /* LV_HAVE_GENERIC */ 00073 00074 00075 00076 00077 #endif /* INCLUDED_volk_8ic_deinterleave_16i_x2_a_H */