// 秒寻科技
// 傅里叶变换
// cl
// 2023-03-04

#include "../includes/includes.h"

const uint32 gFFT_adwBKList[14] = {1, 2, 4, 8, 16, 32, 64, 128, 256, 512, 1024, 2048, 4096, 8192};

static flt32 gFFT_afCos1[1] = {0};
static flt32 gFFT_afSin1[1] = {0};

static flt32 gFFT_afCos2[2] = {0};
static flt32 gFFT_afSin2[2] = {0};

static flt32 gFFT_afCos4[4] = {0};
static flt32 gFFT_afSin4[4] = {0};

static flt32 gFFT_afCos8[8] = {0};
static flt32 gFFT_afSin8[8] = {0};

static flt32 gFFT_afCos16[16] = {0};
static flt32 gFFT_afSin16[16] = {0};

static flt32 gFFT_afCos32[32] = {0};
static flt32 gFFT_afSin32[32] = {0};

static flt32 gFFT_afCos64[64] = {0};
static flt32 gFFT_afSin64[64] = {0};

static flt32 gFFT_afCos128[128] = {0};
static flt32 gFFT_afSin128[128] = {0};

static flt32 gFFT_afCos256[256] = {0};
static flt32 gFFT_afSin256[256] = {0};

static flt32 gFFT_afCos512[512] = {0};
static flt32 gFFT_afSin512[512] = {0};

static flt32 gFFT_afCos1024[1024] = {0};
static flt32 gFFT_afSin1024[1024] = {0};

static flt32 gFFT_afCos2048[2048] = {0};
static flt32 gFFT_afSin2048[2048] = {0};

static flt32 gFFT_afCos4096[4096] = {0};
static flt32 gFFT_afSin4096[4096] = {0};

static flt32 gFFT_afCos8192[8192] = {0};
static flt32 gFFT_afSin8192[8192] = {0};

void util_fft_init()
{
    int i = 0;
    int j = 0;
    int k = 0;

    int P = 0; // 旋转因子指数
    int L = 0; // 蝶形运算的级数
    int B = 0; // 蝶形运算的两个输入数据的间隔

    flt32 fCosValue = 0;
    flt32 fSinValue = 0;
    flt32 *pfCosData = NULL;
    flt32 *pfSinData = NULL;

    int data_frame_bit_count = UTIL_FFT_FRAME_LEN_BIT_NUM;
    for (L = 1; L <= data_frame_bit_count; L++)
    {
        switch (L - 1)
        {
        case 0:
            pfCosData = gFFT_afCos1;
            pfSinData = gFFT_afSin1;
            break;
        case 1:
            pfCosData = gFFT_afCos2;
            pfSinData = gFFT_afSin2;
            break;
        case 2:
            pfCosData = gFFT_afCos4;
            pfSinData = gFFT_afSin4;
            break;
        case 3:
            pfCosData = gFFT_afCos8;
            pfSinData = gFFT_afSin8;
            break;
        case 4:
            pfCosData = gFFT_afCos16;
            pfSinData = gFFT_afSin16;
            break;
        case 5:
            pfCosData = gFFT_afCos32;
            pfSinData = gFFT_afSin32;
            break;
        case 6:
            pfCosData = gFFT_afCos64;
            pfSinData = gFFT_afSin64;
            break;
        case 7:
            pfCosData = gFFT_afCos128;
            pfSinData = gFFT_afSin128;
            break;
        case 8:
            pfCosData = gFFT_afCos256;
            pfSinData = gFFT_afSin256;
            break;
        case 9:
            pfCosData = gFFT_afCos512;
            pfSinData = gFFT_afSin512;
            break;
        case 10:
            pfCosData = gFFT_afCos1024;
            pfSinData = gFFT_afSin1024;
            break;
        case 11:
            pfCosData = gFFT_afCos2048;
            pfSinData = gFFT_afSin2048;
            break;
        case 12:
            pfCosData = gFFT_afCos4096;
            pfSinData = gFFT_afSin4096;
            break;
        case 13:
            pfCosData = gFFT_afCos8192;
            pfSinData = gFFT_afSin8192;
            break;
        default:
            printf("fft init error \n");
        }

        k = gFFT_adwBKList[data_frame_bit_count - L];
        B = gFFT_adwBKList[L - 1];
        for (j = 0; j <= B - 1; j++)
        {
            P = j * k;

            pfCosData[j] = cos(UTIL_FFT_2PI * P);
            pfSinData[j] = sin(UTIL_FFT_2PI * P);
        }
    }

    return;
}

// 获得数据指针
void util_fft_get_data_ptr(uint8 byIndex, flt32 **pfCosData, flt32 **pfSinData)
{
    switch (byIndex)
    {
    case 0:
        *pfCosData = gFFT_afCos1;
        *pfSinData = gFFT_afSin1;
        break;
    case 1:
        *pfCosData = gFFT_afCos2;
        *pfSinData = gFFT_afSin2;
        break;
    case 2:
        *pfCosData = gFFT_afCos4;
        *pfSinData = gFFT_afSin4;
        break;
    case 3:
        *pfCosData = gFFT_afCos8;
        *pfSinData = gFFT_afSin8;
        break;
    case 4:
        *pfCosData = gFFT_afCos16;
        *pfSinData = gFFT_afSin16;
        break;
    case 5:
        *pfCosData = gFFT_afCos32;
        *pfSinData = gFFT_afSin32;
        break;
    case 6:
        *pfCosData = gFFT_afCos64;
        *pfSinData = gFFT_afSin64;
        break;
    case 7:
        *pfCosData = gFFT_afCos128;
        *pfSinData = gFFT_afSin128;
        break;
    case 8:
        *pfCosData = gFFT_afCos256;
        *pfSinData = gFFT_afSin256;
        break;
    case 9:
        *pfCosData = gFFT_afCos512;
        *pfSinData = gFFT_afSin512;
        break;
    case 10:
        *pfCosData = gFFT_afCos1024;
        *pfSinData = gFFT_afSin1024;
        break;
    case 11:
        *pfCosData = gFFT_afCos2048;
        *pfSinData = gFFT_afSin2048;
        break;
    case 12:
        *pfCosData = gFFT_afCos4096;
        *pfSinData = gFFT_afSin4096;
        break;
    case 13:
        *pfCosData = gFFT_afCos8192;
        *pfSinData = gFFT_afSin8192;
        break;
    default:
        printf("fft init error \n");
    }

    return;
}

// 初始化蝶形运算抽取顺序码表数据
// @param data_frame_length 数据帧长度
// @param butterfly_table_ptr 蝶形运算抽取顺序码表内存空间指针，内存空间由调用者申请并管理
int util_fft_init_butterfly_table(int data_frame_length, short *butterfly_table_ptr)
{
    if (butterfly_table_ptr == NULL)
    {
        return 0;
    }

    // 初始化蝶形运算抽取顺序码表数据
    int data_frame_bit_count = log2(data_frame_length);
    for (int i = 0; i < data_frame_length; i++)
    {
        butterfly_table_ptr[i] = util_fft_reverse_number_bit(i, data_frame_bit_count);
    }

    return 1;
}

// 复数fft计算
// @param data_frame_length 数据帧长度
// @param [inout]data_real_ptr 序列实部的数据空间地址
// @param [inout]data_imag_ptr 序列虚部的数据空间地址
// @param butterfly_table_ptr 蝶形运算抽取顺序码表
// @return 操作结果 0失败 1成功
int util_fft_fft(int data_frame_length, float *data_real_ptr, float *data_imag_ptr, short *butterfly_table_ptr)
{
    if (data_real_ptr == NULL || data_imag_ptr == NULL || data_frame_length == 0 || butterfly_table_ptr == NULL)
    {
        return 0;
    }

    int i = 0;
    short index = 0;
    float temp = 0.0;

    // 根据蝶形运算抽取顺序码表对data_real_ptr和data_imag_ptr输入序列进行调换
    for (i = 0; i < data_frame_length; i++)
    {
        index = butterfly_table_ptr[i];
        if (i < index)
        {
            temp = data_real_ptr[i];
            data_real_ptr[i] = data_real_ptr[index];
            data_real_ptr[index] = temp;

            temp = data_imag_ptr[i];
            data_imag_ptr[i] = data_imag_ptr[index];
            data_imag_ptr[index] = temp;
        }
    }

    int j = 0;
    int k = 0;
    int r = 0;

    int P = 0; // 旋转因子指数
    int L = 0; // 蝶形运算的级数
    int B = 0; // 蝶形运算的两个输入数据的间隔

    float temp_real = 0;
    float temp_imag = 0;
    flt32 *pfCosPtr = NULL;
    flt32 *pfSinPtr = NULL;

    // int data_frame_bit_count = log2(data_frame_length);
    int data_frame_bit_count = UTIL_FFT_FRAME_LEN_BIT_NUM;

    // 进行FFT
    // Tr = Xr(J+B)cos(2.0*PI*P/data_frame_length) + Xi(J+B)sin(2.0*PI*P/data_frame_length)
    // Ti = Xi(J+B)cos(2.0*PI*P/data_frame_length) - Xr(J+B)sin(2.0*PI*P/data_frame_length)
    // Ar[J] = Xr(J) + Tr
    // Ai[J] = Xi(J) + Ti
    // Ar[J+B] = Xr(J) - Tr
    // Ai[J+B] = Xi(J) - Ti
    // (其中 Xr为上一级的Ar, Xi为上一级的Ai)
    for (L = 1; L <= data_frame_bit_count; L++)
    { // FFT蝶形级数L从1--data_frame_bit_count
        // 第L级的运算:
        // 然后对于第L级，我们在问题五种提到，蝶形运算的种类数目等于间隔B:有多少种蝶形运算就要需要循环多少次;
        // 随着循环的不同，旋转指数P也不同，P的增量为k=2^(data_frame_bit_count-L)
        // 先计算一下间隔 B = 2^(L-1);

        // 获得数据地址
        util_fft_get_data_ptr((L - 1), &pfCosPtr, &pfSinPtr); // add by zt
        k = gFFT_adwBKList[data_frame_bit_count - L];

        // B = (int)pow(2, L - 1);
        B = gFFT_adwBKList[L - 1]; // add by zt
        for (j = 0; j <= B - 1; j++)
        {
            // j = 0,1,2,...,2^(L-1) - 1
            // 同种蝶形运算
            // 先计算增量k=2^(data_frame_bit_count-L)
            // k = (int)pow(2, data_frame_bit_count - L);
            k = gFFT_adwBKList[data_frame_bit_count - L]; // add by zt
            // 计算旋转指数P，增量为k时，则P=j*k
            // P = j * k;
            // 接下来，由问题六我们可以知道同种蝶形运算的次数刚好为增量k=2^(data_frame_bit_count-L)；
            // 同种蝶形的运算次数即为蝶形运算的次数
            for (i = 0; i <= k - 1; i++)
            {
                // 数组下标定为r
                r = j + 2 * B * i;
                // temp_real = data_real_ptr[r + B] * cos(2.0 * PUB_M_PI * P / data_frame_length) + data_imag_ptr[r + B] * sin(2.0 * PUB_M_PI * P / data_frame_length);
                // temp_imag = data_imag_ptr[r + B] * cos(2.0 * PUB_M_PI * P / data_frame_length) - data_real_ptr[r + B] * sin(2.0 * PUB_M_PI * P / data_frame_length);

                // add by zt
                temp_real = data_real_ptr[r + B] * pfCosPtr[j] + data_imag_ptr[r + B] * pfSinPtr[j];
                temp_imag = data_imag_ptr[r + B] * pfCosPtr[j] - data_real_ptr[r + B] * pfSinPtr[j];

                data_real_ptr[r + B] = data_real_ptr[r] - temp_real;
                data_imag_ptr[r + B] = data_imag_ptr[r] - temp_imag;
                data_real_ptr[r] = data_real_ptr[r] + temp_real;
                data_imag_ptr[r] = data_imag_ptr[r] + temp_imag;
            }
        }
    }

    return 1;
}

// 复数ifft计算
// @param data_frame_length 数据帧长度
// @param [inout]data_real_ptr 序列实部的数据空间地址
// @param [inout]data_imag_ptr 序列虚部的数据空间地址
// @param butterfly_table_ptr 蝶形运算抽取顺序码表
// @return 操作结果 0失败 1成功
int util_fft_ifft(int data_frame_length, float *data_real_ptr, float *data_imag_ptr, short *butterfly_table_ptr)
{
    if (data_real_ptr == NULL || data_imag_ptr == NULL || data_frame_length == 0 || butterfly_table_ptr == NULL)
    {
        return 0;
    }

    int i = 0;
    short index = 0;
    float temp = 0.0;

    // 根据蝶形运算抽取顺序码表对data_real_ptr和data_imag_ptr输入序列进行调换
    for (i = 0; i < data_frame_length; i++)
    {
        index = butterfly_table_ptr[i];
        if (i < index)
        {
            temp = data_real_ptr[i];
            data_real_ptr[i] = data_real_ptr[index];
            data_real_ptr[index] = temp;

            temp = data_imag_ptr[i];
            data_imag_ptr[i] = data_imag_ptr[index];
            data_imag_ptr[index] = temp;
        }
    }

    int j = 0;
    int k = 0;
    int r = 0;

    int P = 0; // 旋转因子指数
    int L = 0; // 蝶形运算的级数
    int B = 0; // 蝶形运算的两个输入数据的间隔

    float temp_real = 0;
    float temp_imag = 0;
    flt32 *pfCosPtr = NULL;
    flt32 *pfSinPtr = NULL;

    // int data_frame_bit_count = log2(data_frame_length);
    int data_frame_bit_count = UTIL_FFT_FRAME_LEN_BIT_NUM; // add by zt

    // 进行IFFT
    // Tr = Xr(J+B)cos(2.0*PI*P/data_frame_length) - Xi(J+B)sin(2.0*PI*P/data_frame_length)
    // Ti = Xi(J+B)cos(2.0*PI*P/data_frame_length) + Xr(J+B)sin(2.0*PI*P/data_frame_length)
    // Ar[J] = Xr(J) + Tr
    // Ai[J] = Xi(J) + Ti
    // Ar[J+B] = Xr(J) - Tr
    // Ai[J+B] = Xi(J) - Ti
    // (其中 Xr为上一级的Ar, Xi为上一级的Ai)
    for (L = 1; L <= data_frame_bit_count; L++)
    { // FFT蝶形级数L从1--data_frame_bit_count
        // 第L级的运算:
        // 然后对于第L级，我们在问题五种提到，蝶形运算的种类数目等于间隔B:有多少种蝶形运算就要需要循环多少次;
        // 随着循环的不同，旋转指数P也不同，P的增量为k=2^(data_frame_bit_count-L)
        // 先计算一下间隔 B = 2^(L-1);

        // 获得数据地址
        util_fft_get_data_ptr((L - 1), &pfCosPtr, &pfSinPtr); // add by zt
        k = gFFT_adwBKList[data_frame_bit_count - L];         // add by zt

        // B = (int)pow(2, L - 1);
        B = gFFT_adwBKList[L - 1]; // add by zt
        for (j = 0; j <= B - 1; j++)
        {
            // j = 0,1,2,...,2^(L-1) - 1
            // 同种蝶形运算
            // 先计算增量k=2^(data_frame_bit_count-L)
            // k = (int)pow(2, data_frame_bit_count - L);

            // 计算旋转指数p，增量为k时，则P=j*k
            // P = j * k;

            // 接下来，由问题六我们可以知道同种蝶形运算的次数刚好为增量k=2^(data_frame_bit_count-L)；
            // 同种蝶形的运算次数即为蝶形运算的次数
            for (i = 0; i <= k - 1; i++)
            {
                // 数组下标定为r
                r = j + 2 * B * i;
                // temp_real = data_real_ptr[r + B] * cos(UTIL_FFT_2PI * P / data_frame_length) - data_imag_ptr[r + B] * sin(UTIL_FFT_2PI * P / data_frame_length);
                // temp_imag = data_imag_ptr[r + B] * cos(UTIL_FFT_2PI * P / data_frame_length) + data_real_ptr[r + B] * sin(UTIL_FFT_2PI * P / data_frame_length);

                // add by zt
                temp_real = data_real_ptr[r + B] * pfCosPtr[j] - data_imag_ptr[r + B] * pfSinPtr[j];
                temp_imag = data_imag_ptr[r + B] * pfCosPtr[j] + data_real_ptr[r + B] * pfSinPtr[j];

                data_real_ptr[r + B] = data_real_ptr[r] - temp_real;
                data_real_ptr[r + B] = data_real_ptr[r + B] / 2;
                data_imag_ptr[r + B] = data_imag_ptr[r] - temp_imag;
                data_imag_ptr[r + B] = data_imag_ptr[r + B] / 2;
                data_real_ptr[r] = data_real_ptr[r] + temp_real;
                data_real_ptr[r] = data_real_ptr[r] / 2;
                data_imag_ptr[r] = data_imag_ptr[r] + temp_imag;
                data_imag_ptr[r] = data_imag_ptr[r] / 2;
            }
        }
    }

    return 1;
}

// 计算结果序列长度（调用者分配结果空间使用）
// @param data_frame_length 数据帧长度
// @result 结果帧长度
int util_fft_calc_result_sequence_length(int data_frame_length)
{
    return data_frame_length / 2 + 1;
}

// 计算经fft处理后的数据序列的频率序列
// @param data_frame_length 数据帧长度
// @param sample_rate 序列的数据采样率
// @param [inout] frequency_sequence_ptr 频率序列数据空间地址(其空间长度需大于等于data_frame_length / 2 + 1)
// @return 操作结果 0失败 1成功
int util_fft_calc_frequency_sequence(int data_frame_length, int sample_rate, float *frequency_sequence_ptr)
{
    if (data_frame_length == 0 || sample_rate == 0 || frequency_sequence_ptr == NULL)
    {
        return 0;
    }

    int i = 0;
    int sequence_length = util_fft_calc_result_sequence_length(data_frame_length);
    float ratio = (float)sample_rate / (float)data_frame_length; // 计算频率化系数（采样率与fft数据帧长度的比值）

    for (i = 0; i < sequence_length; i++)
    {
        // 计算频率，计算公式：f(x) = x * (sample_rate / data_frame_length)
        frequency_sequence_ptr[i] = i * ratio;
    }

    return 1;
}

// 计算经fft处理后的数据序列的幅值序列（频谱）
// @param data_real_ptr 经fft后的序列实部的数据空间地址
// @param data_imag_ptr 经fft后的序列虚部的数据空间地址
// @param data_frame_length 数据帧长度
// @param [inout] amplitude_sequence_ptr 幅值序列数据空间地址(其空间长度需大于等于data_frame_length / 2 + 1)
// @return 操作结果 0失败 1成功
int util_fft_calc_amplitude_sequence(float *data_real_ptr, float *data_imag_ptr, int data_frame_length, float *amplitude_sequence_ptr)
{
    if (data_real_ptr == NULL || data_imag_ptr == NULL || data_frame_length == 0 || amplitude_sequence_ptr == NULL)
    {
        return 0;
    }

    int i = 0;
    int sequence_length = util_fft_calc_result_sequence_length(data_frame_length);

    for (i = 0; i < sequence_length; i++)
    {
        // 计算幅值，计算公式：复数取模z = x + iy, |z| = sqrt(x * x + y * y)
        amplitude_sequence_ptr[i] = sqrt(data_real_ptr[i] * data_real_ptr[i] + data_imag_ptr[i] * data_imag_ptr[i]);

        // 归一化处理
        if (i == 0 || i == sequence_length - 1)
        {                                                                              // 左右两头的点
            amplitude_sequence_ptr[i] = amplitude_sequence_ptr[i] / data_frame_length; // 对量纲进行还原
        }
        else
        {                                                                                  // 除左右两头的点外的中间点
            amplitude_sequence_ptr[i] = amplitude_sequence_ptr[i] / data_frame_length * 2; // 对量纲进行还原，并进行能量守恒的还原
        }
    }

    return 1;
}

// 计算经fft处理后的数据序列的功率谱序列（功率谱）
// @param data_real_ptr 经fft后的序列实部的数据空间地址
// @param data_imag_ptr 经fft后的序列虚部的数据空间地址
// @param data_frame_length 数据帧长度
// @param [inout] power_sequence_ptr 功率谱序列数据空间地址
// @return 操作结果 0失败 1成功
int util_fft_calc_power_sequence(float *data_real_ptr, float *data_imag_ptr, int data_frame_length, float *power_sequence_ptr)
{
    if (data_real_ptr == NULL || data_imag_ptr == NULL || data_frame_length == 0 || power_sequence_ptr == NULL)
    {
        return 0;
    }

    int result = util_fft_calc_amplitude_sequence(data_real_ptr, data_imag_ptr, data_frame_length, power_sequence_ptr);
    if (result == 0)
    {
        return 0;
    }

    int i = 0;
    int sequence_length = util_fft_calc_result_sequence_length(data_frame_length);

    for (i = 0; i < sequence_length; i++)
    {
        // 计算功率谱，计算公式：power = 10*log10(amplitude*amplitude)
        power_sequence_ptr[i] = 10 * log10(power_sequence_ptr[i] * power_sequence_ptr[i]);
    }

    return 1;
}

// 计算经fft处理后的数据序列的相位角序列（相位谱）
// @param data_real_ptr 经fft后的序列实部的数据空间地址
// @param data_imag_ptr 经fft后的序列虚部的数据空间地址
// @param data_frame_length 数据帧长度
// @param radian2angle 是否将弧度转换成角度 0不转换 1转换
// @param [inout] phase_sequence_ptr 相位角序列数据空间地址
// @return 操作结果 0失败 1成功
int util_fft_calc_phase_sequence(float *data_real_ptr, float *data_imag_ptr, int data_frame_length, int radian2angle, float *phase_sequence_ptr)
{
    if (data_real_ptr == NULL || data_imag_ptr == NULL || data_frame_length == 0 || phase_sequence_ptr == NULL)
    {
        return 0;
    }

    int i = 0;

    for (i = 0; i < data_frame_length; i++)
    {
        // 计算相位角（z = x + iy）
        // 当x>0时，arctan(y/x)
        // 当x=0且y>0时，PI/2
        // 当x=0且y<0时，-PI/2
        // 当x<0且y>=0时，arctan(y/x)+PI
        // 当x<0且y<0时，arctan(y/x)-PI
        if (data_real_ptr[i] > 0)
        {
            phase_sequence_ptr[i] = atan(data_imag_ptr[i] / data_real_ptr[i]);
        }
        else if (data_real_ptr[i] == 0)
        {
            if (data_imag_ptr[i] > 0)
            {
                phase_sequence_ptr[i] = PUB_M_PI_2;
            }
            else if (data_imag_ptr[i] < 0)
            {
                phase_sequence_ptr[i] = -PUB_M_PI_2;
            }
            else
            {
                phase_sequence_ptr[i] = 0;
            }
        }
        else
        {
            if (data_imag_ptr[i] >= 0)
            {
                phase_sequence_ptr[i] = atan(data_imag_ptr[i] / data_real_ptr[i]) + PUB_M_PI;
            }
            else
            {
                phase_sequence_ptr[i] = atan(data_imag_ptr[i] / data_real_ptr[i]) - PUB_M_PI;
            }
        }

        if (radian2angle == 1)
        { // 弧度转换成角度
            phase_sequence_ptr[i] = phase_sequence_ptr[i] / PUB_M_PI * 180;
        }
    }

    return 1;
}

// 将数字进行二进制码位倒序
// @param number 要进行二进制码位倒序的数字
// @param 数字的二进制位数
// @return 进行二进制码位倒序后的数值
int util_fft_reverse_number_bit(int number, int total_bit_count)
{
    int original_data = number;
    int reverse_data = 0;

    int i = 0;
    int low_bit_mask = 0;   // 低位二进制数据
    int high_bit_mask = 0;  // 高位二进制数据
    int low_part_data = 0;  // 低位部分数据
    int high_part_data = 0; // 高位部分数据

    for (i = 0; i < (total_bit_count / 2 + 0.5); i++)
    {
        low_bit_mask = 1;                                          // low_bit_mask是最低位为1的二进制数
        high_bit_mask = (unsigned int)pow(2, total_bit_count - 1); // high_bit_mask是第total_bit_count位为1的二进制数
        low_bit_mask <<= i;                                        // 对low_bit_mask左移i位
        high_bit_mask >>= i;                                       // 对high_bit_mask右移i位

        low_part_data = original_data & low_bit_mask;   // original_data与low_bit_mask按位与提取出低位部分第i位
        high_part_data = original_data & high_bit_mask; // original_data与high_bit_mask按位与提取出高位部分第i位

        if (high_part_data != 0)
        {                                               // 将高位部分的1转移到低位部分对应的位置上
            reverse_data = reverse_data | low_bit_mask; // reverse_data与low_bit_mask按位或使high_part_data对应低位为1
        }
        if (low_part_data != 0)
        {                                                // 将低位部分的1转移到高位部分对应的位置上
            reverse_data = reverse_data | high_bit_mask; // reverse_data与high_bit_mask按位或使low_part_data对应高位为1
        }
    }

    return reverse_data;
}
