获取信号强度

本文介绍了一种用于获取DVB-T信号强度的算法实现细节。该算法通过读取设备寄存器来获取RF与IF AGC值,并依据这些值及误差修正计算出信号的相对功率。此外,还介绍了如何根据调制方式和编码率确定参考功率。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

MS_U16 DTV_GetSignalStrength(void)

{
    MS_U8 status = true;
    MS_U16 u16Strength;
    MS_U8 reg_tmp, reg_frz;
    MS_U8 rf_agc_val;
    MS_U8 if_agc_val;
    MS_U8 if_agc_err;
    MS_U8 i;
    MS_U8 ssi_tbl_len;
    MS_U8 err_tbl_len;
    MS_U8 tps_cnstl;
    MS_U8 tps_cr;
    MS_FLOAT ch_power_db;
    MS_FLOAT ch_power_rf=0;
    MS_FLOAT ch_power_if=0;
    MS_FLOAT ch_power_ref=0;
    MS_FLOAT ch_power_rel;
    S_IFAGC_SSI        *ifagc_ssi;
    S_IFAGC_ERR        *ifagc_err;

    DBG_DOMOD_MSB(HB_printf("Get DVB-T signal strength\n"));

    if(FECLock == TRUE)
    {
        status &= ReadReg(0x8512+1, &reg_tmp);
        DBG_DOMOD_MSB(HB_printf("AGC_REF = %d\n", (int)reg_tmp));
        if (reg_tmp > 200)
        {
            ifagc_ssi = IfagcSsi_HiRef;
            ssi_tbl_len = sizeof(IfagcSsi_HiRef)/sizeof(S_IFAGC_SSI);
            ifagc_err = IfagcErr_HiRef;
            err_tbl_len = sizeof(IfagcErr_HiRef)/sizeof(S_IFAGC_ERR);
        }
        else
        {
            ifagc_ssi = IfagcSsi_LoRef;
            ssi_tbl_len = sizeof(IfagcSsi_LoRef)/sizeof(S_IFAGC_SSI);
            ifagc_err = IfagcErr_LoRef;
            err_tbl_len = sizeof(IfagcErr_LoRef)/sizeof(S_IFAGC_ERR);
        }


        / RF/IF-AGC Gain Out /
        #if 0 // Sidney
            //rf_agc_val = MDrv_ReadByte(0x3A1C);
            rf_agc_val=MDrv_SAR_Adc_GetValue(2);
        #else
            rf_agc_val=0x3F;
        #endif
        WriteReg(0x8522, 0x03); // select IF gain to read
        WriteReg(0x8504+1, 0x03); // hold values of 0x8524 and 0x8525


        status &= ReadReg(0x8524+1, &reg_tmp);

        WriteReg(0x8504+1, 0x00); // release values of 0x8524 and 0x8525


        if_agc_val = reg_tmp;

        DBG_DOMOD_MSB(HB_printf("SSI_RFAGC (SAR-2) = 0x%x\n", rf_agc_val));
        DBG_DOMOD_MSB(HB_printf("SSI_IFAGC_H = 0x%x\n", if_agc_val));

        for(i = 0; i < sizeof(RfagcSsi)/sizeof(S_RFAGC_SSI); i++)
        {
            if (rf_agc_val <= RfagcSsi[i].sar3_val)
            {
                ch_power_rf = RfagcSsi[i].power_db;
                break;
            }
        }

        for(i = 0; i < ssi_tbl_len; i++)
        {
            if (if_agc_val <= ifagc_ssi[i].agc_val)
            {
                ch_power_if = ifagc_ssi[i].power_db;
                break;
            }
        }

        DBG_DOMOD_MSB(HB_printf("ch_power_rf = %f\n", ch_power_rf));
        DBG_DOMOD_MSB(HB_printf("ch_power_if = %f\n", ch_power_if));

        ch_power_db = (ch_power_rf > ch_power_if)? ch_power_rf : ch_power_if;

        / IF-AGC Error for Add. Attnuation /

        // bank 5 0x04 [15] reg_tdp_lat
        status &= ReadReg(0x8504+1, &reg_frz);
        status &= WriteReg(0x8504+1, reg_frz|0x80);

        // bank 5 0x2c [9:0] reg_agc_error
        status &= ReadReg(0x852C+1, &reg_tmp);
        if_agc_err = reg_tmp & 0x03;
        status &= ReadReg(0x852C, &reg_tmp);
        if_agc_err = (if_agc_err << 6)|(reg_tmp >> 2);

        status &= WriteReg(0x8504+1, reg_frz&(~0x80));

        for(i = 0; i < err_tbl_len; i++)
        {
            if ((MS_S8)if_agc_err <= ifagc_err[i].agc_err)        // signed char comparison
            {
                ch_power_db += ifagc_err[i].attn_db;
                break;
            }
        }

        DBG_DOMOD_MSB(HB_printf("if_agc_err = 0x%x\n", if_agc_err));
    }
    else
    {
        ch_power_db = -99.0;
    }

    DBG_DOMOD_MSB(HB_printf(">>> SSI_CH_PWR(dB) = %f <<<\n", ch_power_db));

    / Get Constellation and Code Rate to determine Ref. Power //
    / (refer to Teracom min. spec 2.0 4.1.1.6) /

    status &= ReadReg(0x8624, &reg_tmp);
    tps_cnstl = reg_tmp & 0x03;

    status &= ReadReg(0x8624+1, &reg_tmp);
    tps_cr = (reg_tmp & 0x70) >> 4;

    for(i = 0; i < sizeof(SsiPref)/sizeof(S_SSI_PREF); i++)
    {
        if ( (tps_cnstl == SsiPref[i].constel)
            && (tps_cr == SsiPref[i].code_rate) )
        {
            ch_power_ref = SsiPref[i].p_ref;
            break;
        }

    }


    ch_power_rel = ch_power_db - ch_power_ref;

    if (ch_power_rel < -15.0)
        u16Strength = 0;
    else if (ch_power_rel < 0.0)
        u16Strength = (MS_U16)((ch_power_rel + 15.0)*(10.0/15.0));
    else if (ch_power_rel < 20.0)
        u16Strength = (MS_U16)(ch_power_rel*4.0 + 10.0);
    else if (ch_power_rel < 35.0)
        u16Strength = (MS_U16)((ch_power_rel - 20.0)*(10.0/15.0) + 90.0);
    else
        u16Strength = 100;


    DBG_DOMOD_MSB(HB_printf(">>> SSI = %d <<<\n", (int)u16Strength));

    if (status == true)
        return u16Strength;
    else
        return 0;

}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值