Skip to content

Commit

Permalink
Added documentation and out of how much a dynamic phase shift occurs …
Browse files Browse the repository at this point in the history
…for all clocks per pulse.
  • Loading branch information
rowanG077 committed Jul 28, 2021
1 parent 541e398 commit fc44279
Showing 1 changed file with 64 additions and 4 deletions.
68 changes: 64 additions & 4 deletions libtrellis/tools/ecppll.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,8 @@ struct secondary_params{

float freq;
float phase;
float phase_vco_step;
float phase_div_step;
};

struct pll_params{
Expand All @@ -62,6 +64,10 @@ struct pll_params{
int feedback_div;
int output_div;
int primary_cphase;
int primary_fphase;
float primary_phase_vco_step;
float primary_phase_div_step;

string clkin_name;
string clkout0_name;
int dynamic;
Expand Down Expand Up @@ -245,22 +251,30 @@ int main(int argc, char** argv){
cout << "Feedback divisor: " << params.feedback_div << endl;
cout << "clkout0 divisor: " << params.output_div << "" << endl;
cout << "clkout0 frequency: " << params.fout << " MHz" << endl;
cout << "clkout0 vco step: " << params.primary_phase_vco_step << " degrees" << endl;
cout << "clkout0 div step: " << params.primary_phase_div_step << " degrees" << endl;
if(params.secondary[0].enabled){
cout << "clkout1 divisor: " << params.secondary[0].div << endl;
cout << "clkout1 frequency: " << params.secondary[0].freq << " MHz" << endl;
cout << "clkout1 phase shift: " << params.secondary[0].phase << " degrees" << endl;
cout << "clkout1 vco step: " << params.secondary[0].phase_vco_step << " degrees" << endl;
cout << "clkout1 div step: " << params.secondary[0].phase_div_step << " degrees" << endl;
}
if(params.secondary[1].enabled){
cout << "clkout2 divisor: " << params.secondary[1].div << endl;
cout << "clkout2 frequency: " << params.secondary[1].freq << " MHz" << endl;
cout << "clkout2 phase shift: " << params.secondary[1].phase << " degrees" << endl;
cout << "clkout2 vco step: " << params.secondary[1].phase_vco_step << " degrees" << endl;
cout << "clkout2 div step: " << params.secondary[1].phase_div_step << " degrees" << endl;
}
if(params.secondary[2].enabled){
cout << "clkout3 divisor: " << params.secondary[2].div << endl;
cout << "clkout3 frequency: " << params.secondary[2].freq << " MHz" << endl;
cout << "clkout3 phase shift: " << params.secondary[2].phase << " degrees" << endl;
cout << "clkout3 vco step: " << params.secondary[2].phase_vco_step << " degrees" << endl;
cout << "clkout3 div step: " << params.secondary[2].phase_div_step << " degrees" << endl;
}
cout << "VCO frequency: " << params.fvco << endl;
cout << "VCO frequency: " << params.fvco << " Mhz" << endl;
if(vm.count("file")){
ofstream f;
f.open(vm["file"].as<string>().c_str());
Expand All @@ -269,6 +283,14 @@ int main(int argc, char** argv){
}
}

float calc_vco_phase_step(int fphase, int div){
return (360.f * (float)fphase) / (8.f * (float)div);
}

float calc_div_phase_step(int cphase, int div){
return (360.f * ((float)cphase - (float)div)) / (1.f + (float)div);
}

void calc_pll_params(pll_params &params, float input, float output){
float error = std::numeric_limits<float>::max();
for(int input_div=1;input_div <= 128; input_div++){
Expand All @@ -294,7 +316,12 @@ void calc_pll_params(pll_params &params, float input, float output){
params.fvco = fvco;
// shift the primary by 180 degrees. Lattice seems to do this
float ns_phase = 1/(fout * 1e6) * 0.5;
params.primary_cphase = ns_phase * (fvco * 1e6);
float phase_count = ns_phase * (fvco * 1e6);
params.primary_cphase = phase_count;
int cphase = (int) phase_count;
params.primary_fphase = (int) ((phase_count - cphase) * 8);
params.primary_phase_vco_step = calc_vco_phase_step(params.primary_fphase, params.output_div);
params.primary_phase_div_step = calc_div_phase_step(params.primary_cphase, params.output_div);
}
}
}
Expand Down Expand Up @@ -331,6 +358,15 @@ void calc_pll_params_highres(pll_params &params, float input, float output){
params.secondary[0].freq = fout;
params.fout = fout;
params.fvco = fvco;

// Is this correct for highres mode?
float ns_phase = 1/(fout * 1e6) * 0.5;
float phase_count = ns_phase * (fvco * 1e6);
params.primary_cphase = phase_count;
int cphase = (int) phase_count;
params.primary_fphase = (int) ((phase_count - cphase) * 8);
params.primary_phase_vco_step = calc_vco_phase_step(params.primary_fphase, params.output_div);
params.primary_phase_div_step = calc_div_phase_step(params.primary_cphase, params.output_div);
}
}
}
Expand Down Expand Up @@ -359,6 +395,8 @@ void generate_secondary_output(pll_params &params, int channel, string name, flo
params.secondary[channel].cphase = cphase + params.primary_cphase;
params.secondary[channel].fphase = fphase;
params.secondary[channel].name = name;
params.secondary[channel].phase_vco_step = calc_vco_phase_step(fphase, div);
params.secondary[channel].phase_div_step = calc_div_phase_step(params.secondary[channel].cphase, div);
}

void write_pll_config(const pll_params & params, const string &name, ofstream& file)
Expand All @@ -376,8 +414,30 @@ void write_pll_config(const pll_params & params, const string &name, ofstream& f
{
file << " input [1:0] phasesel, // clkout[] index affected by dynamic phase shift (except clkfb), 5 ns min before apply\n";
file << " input phasedir, // 0:delayed (lagging), 1:advence (leading), 5 ns min before apply\n";
file << " input phasestep, // 45 deg step, high for 5 ns min, falling edge = apply\n";
file << " input phaseloadreg, // high for 10 ns min, falling edge = apply\n";
file << " // high for 5 ns min, falling edge = apply\n";
file << " // " << params.primary_phase_vco_step << " deg step for " << params.clkout0_name << "\n";
if(params.secondary[0].enabled){
file << " // " << params.secondary[0].phase_vco_step << " deg step for " << params.secondary[0].name << "\n";
}
if(params.secondary[1].enabled){
file << " // " << params.secondary[1].phase_vco_step << " deg step for " << params.secondary[1].name << "\n";
}
if(params.secondary[2].enabled){
file << " // " << params.secondary[2].phase_vco_step << " deg step for " << params.secondary[2].name << "\n";
}
file << " input phasestep,\n";
file << " // high for 10 ns min, falling edge = apply\n";
file << " // " << params.primary_phase_div_step << " deg step for " << params.clkout0_name << "\n";
if(params.secondary[0].enabled){
file << " // " << params.secondary[0].phase_div_step << " deg step for " << params.secondary[0].name << "\n";
}
if(params.secondary[1].enabled){
file << " // " << params.secondary[1].phase_div_step << " deg step for " << params.secondary[1].name << "\n";
}
if(params.secondary[2].enabled){
file << " // " << params.secondary[2].phase_div_step << " deg step for " << params.secondary[2].name << "\n";
}
file << " input phaseloadreg,\n";
}
file << " input " << params.clkin_name << ", // " << params.clkin_frequency << " MHz, 0 deg\n";
file << " output " << params.clkout0_name << ", // " << params.fout << " MHz, 0 deg\n";
Expand Down

0 comments on commit fc44279

Please sign in to comment.