This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

[参考译文] TIDM-02008:在模拟过程中无法锁定软件相位锁定循环,并且它会一直振荡

Guru**** 651100 points
Other Parts Discussed in Thread: TIDM-02008
请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

https://e2e.ti.com/support/tools/simulation-hardware-system-design-tools-group/sim-hw-system-design/f/simulation-hardware-system-design-tools-forum/1066576/tidm-02008-the-software-phase-locked-loop-cannot-be-locked-during-the-simulation-process-and-it-keeps-oscillating

部件号:TIDM-02008

尊敬的团队:

我的客户提到在 TIDM-02008项目中对 Solarlib.pdf 的理论介绍:

Simulink 模拟参数:
TTPLPFC_AC_FREQ:50Hz,TTPLPFC_CONTACT_ISR_FRE频率,LPF_B0和 LPF_B1参数与 TIDM-02008使用的参数一致。

Simulink 模拟结果:输入频率为51Hz 的交流信号(频率可能出现在50Hz 交流电网中),并查看波形是否可以锁定,发现 fO 输出频率和 q 轴无法稳定。

function [sin_a,cos_a,fo_out,Q_out] = fcn(acValue,acFreq,isrFrequency,isrFrequencyMAX,lpf_b0,lpf_b1)

persistent sine;
if isempty(sine)
    sine = 0.0;
end
sin_a = sine;

persistent cosine;
if isempty(cosine)
    cosine = 0.0;
end
cos_a = cosine;

persistent cnt;
if isempty(cnt)
    cnt = 0.0;
end

persistent fn;
if isempty(fn)
    fn = acFreq;
end

persistent delta_t;
if isempty(delta_t)
    delta_t = 1.0/isrFrequency;
end

persistent osg_coeff_osg_k;
if isempty(osg_coeff_osg_k)
    osg_coeff_osg_k = 0.5;
end

persistent osg_coeff_osg_x;
if isempty(osg_coeff_osg_x)
    wn = 2.0 * 3.14159265 * fn;
    osg_coeff_osg_x = 2.0 * osg_coeff_osg_k * wn * delta_t;
end

persistent osg_coeff_osg_y;
if isempty(osg_coeff_osg_y)
    wn = 2.0 * 3.14159265 * fn;
    osg_coeff_osg_y = wn * delta_t * wn * delta_t;
end

persistent osg_coeff_osg_b0;
if isempty(osg_coeff_osg_b0)
    osg_coeff_osg_b0 = osg_coeff_osg_x / (osg_coeff_osg_x + osg_coeff_osg_y + 4.0);
end

persistent osg_coeff_osg_b2;
if isempty(osg_coeff_osg_b2)
    osg_coeff_osg_b2 = -osg_coeff_osg_x / (osg_coeff_osg_x + osg_coeff_osg_y + 4.0);
end

persistent osg_coeff_osg_a1;
if isempty(osg_coeff_osg_a1)
    osg_coeff_osg_a1 = 2 * (4.0 - osg_coeff_osg_y) / (osg_coeff_osg_x + osg_coeff_osg_y + 4.0);
end

persistent osg_coeff_osg_a2;
if isempty(osg_coeff_osg_a2)
    osg_coeff_osg_a2 = (osg_coeff_osg_x - osg_coeff_osg_y - 4) / (osg_coeff_osg_x + osg_coeff_osg_y + 4.0);
end

persistent osg_coeff_osg_qb0;
if isempty(osg_coeff_osg_qb0)
    osg_coeff_osg_qb0 = osg_coeff_osg_k * osg_coeff_osg_y / (osg_coeff_osg_x + osg_coeff_osg_y + 4.0);
end

persistent osg_coeff_osg_qb1;
if isempty(osg_coeff_osg_qb1)
    osg_coeff_osg_qb1 = 2 * osg_coeff_osg_k * osg_coeff_osg_y / (osg_coeff_osg_x + osg_coeff_osg_y + 4.0);
end

persistent osg_coeff_osg_qb2;
if isempty(osg_coeff_osg_qb2)
    osg_coeff_osg_qb2 = osg_coeff_osg_k * osg_coeff_osg_y / (osg_coeff_osg_x + osg_coeff_osg_y + 4.0);
end

persistent lpf_coeff_b0;
if isempty(lpf_coeff_b0)
    lpf_coeff_b0 = lpf_b0;
end

persistent lpf_coeff_b1;
if isempty(lpf_coeff_b1)
    lpf_coeff_b1 = lpf_b1;
end

persistent u_0;
if isempty(u_0)
    u_0 = 0.0;
end
persistent u_1;
if isempty(u_1)
    u_1 = 0.0;
end
persistent u_2;
if isempty(u_2)
    u_2 = 0.0;
end

persistent osg_u_0;
if isempty(osg_u_0)
    osg_u_0 = 0.0;
end
persistent osg_u_1;
if isempty(osg_u_1)
    osg_u_1 = 0.0;
end
persistent osg_u_2;
if isempty(osg_u_2)
    osg_u_2 = 0.0;
end

persistent osg_qu_0;
if isempty(osg_qu_0)
    osg_qu_0 = 0.0;
end
persistent osg_qu_1;
if isempty(osg_qu_1)
    osg_qu_1 = 0.0;
end
persistent osg_qu_2;
if isempty(osg_qu_2)
    osg_qu_2 = 0.0;
end

persistent u_Q_0;
if isempty(u_Q_0)
    u_Q_0 = 0.0;
end
Q_out = u_Q_0;
persistent u_Q_1;
if isempty(u_Q_1)
    u_Q_1 = 0.0;
end

persistent u_D_0;
if isempty(u_D_0)
    u_D_0 = 0.0;
end

persistent ylf_0;
if isempty(ylf_0)
    ylf_0 = 0.0;
end
persistent ylf_1;
if isempty(ylf_1)
    ylf_1 = 0.0;
end

persistent fo;
if isempty(fo)
    fo = 0.0;
end
fo_out = fo;
persistent theta;
if isempty(theta)
    theta = 0.0;
end


if cnt >= isrFrequencyMAX
    cnt = cnt - isrFrequencyMAX;
    
    % Update the spll_obj->u[0] with the grid value
    u_0 = acValue;

    % Orthogonal Signal Generator
    osg_u_0 = osg_coeff_osg_b0 * (u_0 - u_2) + osg_coeff_osg_a1 * osg_u_1 + osg_coeff_osg_a2 * osg_u_2;

    osg_u_2 = osg_u_1;
    osg_u_1 = osg_u_0;

    osg_qu_0 = osg_coeff_osg_qb0 * u_0 + osg_coeff_osg_qb1 * u_1 + osg_coeff_osg_qb2 * u_2 + osg_coeff_osg_a1 * osg_qu_1 + osg_coeff_osg_a2 * osg_qu_2;

    osg_qu_2 = osg_qu_1;
    osg_qu_1 = osg_qu_0;

    u_2 = u_1;
    u_1 = u_0;

    % Park Transform from alpha beta to d-q axis   
    u_Q_0 = cosine * osg_u_0 + sine * osg_qu_0;
    u_D_0 = cosine * osg_qu_0 - sine * osg_u_0;
    
    % Loop Filter
    ylf_0 = ylf_1 + lpf_coeff_b0 * u_Q_0 + lpf_coeff_b1 * u_Q_1;
    ylf_1 = ylf_0;

    u_Q_1 = u_Q_0;

    fo = fn + ylf_0;

    theta = theta + (fo * delta_t) * (2.0 * 3.1415926);
    if theta < 0
        theta = 0;
    end
    if(theta > (2.0 * 3.1415926))
        theta = theta - (2.0 * 3.1415926);
        %theta = 0;
    end
    
    sin_a = sin(theta);
    cos_a = cos(theta);
    
    sine = sin_a;
    cosine = cos_a;
end

cnt = cnt + 1;

Simulink 模拟结果 q 轴输出:

输出频率:

我想问为什么会发生这种情况?

在计算 LPF_B0和 LPF_B1的表中,“错误带”的具体含义是什么?

此致

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    您好,格林,

    Sogi PLL 假定50 Hz 或60 Hz 栅格频率,因此,VCO (WO)中的馈电正向术语在50 Hz 栅格中固定为50 Hz。

    如果您需要运行这两种频率以外的其它频率, 请尝试使用 FLL 而不是 SPLL 运行

    ttplpfc.h 文件中有一个 SPLL 选项

    原始: TTPLPFC_SPLL_METHOD_SELECT == TTPLPFC_SPLL_1PH_Sogi_SEL (50 Hz 或60 Hz)

    所需修改: TTPLPFC_SPLL_METHOD_SELECT == TTPLPFC_SPLL_1PH_Sogi_FLL_SEL (50或60 Hz 除外)

    最佳

    约翰