UPGRADE YOUR BROWSER

We have detected your current browser version is not the latest one. Xilinx.com uses the latest web technologies to bring you the best online experience possible. Please upgrade to a Xilinx.com supported browser:Chrome, Firefox, Internet Explorer 11, Safari. Thank you!

cancel
Showing results for 
Search instead for 
Did you mean: 
Highlighted
Visitor spl1nk
Visitor
593 Views
Registered: ‎07-01-2018

SDK: program failure when casting int to float

Jump to solution

Hello everybody,

I am a little bit stuck with this issue, and was hoping if maybe one of you had a clue what might be going on.

 

I am implementing a Microblaze in a Kintex-7 FPGA. A key element i want to utilize is a dynamically configurable Clocking Wizard IP, connected via AXI-Lite. Now, using the SDK, i generated a standart peripheral test program, which among other things performs a single dynamic reconfiguration of the Clocking Wizard.

 

Now, the issue arrises when i try to change the values of the reconfiguration. In the original template, 'xclk_wiz_intr_example.c', values like the VCO frequency, dynamic input frequency, and dynamic output frequency were given via '#define VCO_FREQ 100' etc. . I am trying to change the actual function 'Clk_Wiz_Reconfig()' such that the values can be passed via parameter, specifically speaking i want to pass the output frequency to the function, and calculate the rest in the function (the input frequency is fixed). Here is how it should look:

int Clk_Wiz_Reconfig(XClk_Wiz_Config *CfgPtr_Dynamic, u32 Dynamic_output_freq)
{

    u32 Dynamic_input_freq = 100.0;
    u32 Clk_wiz_vco_freq = <insert calculation routine here>;
    u32 MultiplicationFactor = <insert calculation routine here>;
    u32 DivisionFactor = <insert calculation routine here>;
    *(u32 *)(CfgPtr_Dynamic->BaseAddr + 0x200) = MultiplicationFactor;
    *(u32 *)(CfgPtr_Dynamic->BaseAddr + 0x208) = DivisionFactor;

return Error;
}

Of course, leaving a few things which the SDK generated out. For this however, i would like to utilize the modulo operation, which would make a lot of things easier.

 

But now for the part which confuses me: In the example design the values are used to calculate floating point numbers. If i use float numbers for the vco/input/output frequency, everything works fine.

 

But if i try to use u32 values for the vco/input/output frequency, the routine fails at a later point.

This ALSO happens if i give the values as u32 initially, but cast them to float immediately before the routine uses them.

So, THIS works:

int Clk_Wiz_Reconfig(float DYNAMIC_INPUT_FREQ)
{
float DYNAMIC_INPUT_FREQ_FACTOR = (DYNAMIC_INPUT_FREQ * 10000.0);
.
.
.
<more stuff happening>
}

But THIS does not:

int Clk_Wiz_Reconfig(u32 INPUT_FREQ)
{
    float DYNAMIC_INPUT_FREQ = (float)INPUT_FREQ;
float DYNAMIC_INPUT_FREQ_FACTOR = (DYNAMIC_INPUT_FREQ * 10000.0);
.
.
.
<more stuff happening>
}

 The same thing happens if i use int instead of u32, although i do not think this matters. In both versions, the values later calculated and passed to the register are the same (at least according to xil_printf() ),  but then the relevant function 'ClkWiz_IntrExample' in which 'Clk_Wiz_Reconfig' is used fails at a later point where the function 'XClk_Wiz_InterruptEnable' is used, without any report to why.

The thing i am wondering is simply why this makes a difference, what is going on in this case. Does anyone have a clue?

0 Kudos
1 Solution

Accepted Solutions
Xilinx Employee
Xilinx Employee
561 Views
Registered: ‎02-01-2008

Re: SDK: program failure when casting int to float

Jump to solution

I'm not sure how you made sure that CLK_WIZ_VCO_FACTOR and DYNAMIC_INPUT_FREQ_FACTOR were floats in your 'original code'.

 

One other change I had to make was the VCO_FREQ. I'm running the design on Zynq UltraScale+, via a microblaze. The VCO range is higher than the example app so I pegged VCO_FREQ to the middle at 1200.

 

In the orig example, the defines are integer since there is no decimal places. It may help if the defines were values such as 1200.0 but I haven't verified.

 

Also, you make reference to interrupts. I'm not using them and am not using the portion of example code that uses two MMCMs.

 

And, I wanted to add flexibility to the design by placing the reconfigurable MMCM outside of the IPI design. The downfall to this approach is that SDK will not add the clk_wiz driver to the BSP. But, luckily the driver is very minimal and basically only contains a structure that holds the MMCM base address. So I now pass the base address to Clk_wiz_reconfig(u32 base) and Wait_For_Lock(u32 base).

0 Kudos
4 Replies
Xilinx Employee
Xilinx Employee
578 Views
Registered: ‎02-01-2008

Re: SDK: program failure when casting int to float

Jump to solution

I just finished going through the same sort of excersize although I'm using the defines for the new freq.

 

I did find a bug in the example code. It subtracts a u32 from a float in order to determine the fractional divide. But what I found is the line Freq=CLK_WIZ_VCO_FACTOR /DYNAMIC_OUTPUT_FREQFACTOR was not creating a float decimal equivalent so I was never getting a fractional enable.

 

By changing the above to type cast both defines as floats, I was able to get the correct results.I now have:

Freq = (float)CLK_WIZ_VCO_FACTOR / (float)DYNAMIC_OUTPUT_FREQFACTOR;

 

Note: xil_print() can not print floats, so you will need to use printf() to print floats.

0 Kudos
Visitor spl1nk
Visitor
573 Views
Registered: ‎07-01-2018

Re: SDK: program failure when casting int to float

Jump to solution

Interestingly, this worked, although i still do not understand why, in my original code design, CLK_WIZ_VCO_FACTOR and DYNAMIC_INPUT_FREQ_FACTOR already were floating point numbers.

0 Kudos
Xilinx Employee
Xilinx Employee
562 Views
Registered: ‎02-01-2008

Re: SDK: program failure when casting int to float

Jump to solution

I'm not sure how you made sure that CLK_WIZ_VCO_FACTOR and DYNAMIC_INPUT_FREQ_FACTOR were floats in your 'original code'.

 

One other change I had to make was the VCO_FREQ. I'm running the design on Zynq UltraScale+, via a microblaze. The VCO range is higher than the example app so I pegged VCO_FREQ to the middle at 1200.

 

In the orig example, the defines are integer since there is no decimal places. It may help if the defines were values such as 1200.0 but I haven't verified.

 

Also, you make reference to interrupts. I'm not using them and am not using the portion of example code that uses two MMCMs.

 

And, I wanted to add flexibility to the design by placing the reconfigurable MMCM outside of the IPI design. The downfall to this approach is that SDK will not add the clk_wiz driver to the BSP. But, luckily the driver is very minimal and basically only contains a structure that holds the MMCM base address. So I now pass the base address to Clk_wiz_reconfig(u32 base) and Wait_For_Lock(u32 base).

0 Kudos
Scholar ericv
Scholar
536 Views
Registered: ‎04-13-2015

Re: SDK: program failure when casting int to float

Jump to solution

Hi @spl1nk

 

The way you initialize the 2 variables may end up been done in reverse your code.

 

    float DYNAMIC_INPUT_FREQ = (float)INPUT_FREQ;
float DYNAMIC_INPUT_FREQ_FACTOR = (DYNAMIC_INPUT_FREQ * 10000.0);

 

I don't think "C" guarantees the initialization will be done in the same order as the variables are declared.

This is what may be happening

 

    float DYNAMIC_INPUT_FREQ;
float DYNAMIC_INPUT_FREQ_FACTOR;

DYNAMIC_FREQ_FACTOR = (DYNAMIC_INPUT_FREQ * 10000.0);
DYNAMIC_INPUT_FREQ = (float)INPUT_FREQ;

 

0 Kudos