Skip to content

Commit 3139b9a

Browse files
committed
projects: eval-powrms: extend precision to 7 point Lagrange interp
For simple measurements 3 point interpolation was not precise enough, using 7 point instead Signed-off-by: rbudai98 <[email protected]>
1 parent 70ca5d4 commit 3139b9a

File tree

4 files changed

+57
-38
lines changed

4 files changed

+57
-38
lines changed

projects/eval-powrms/src/examples/example/iio_powrms.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -78,13 +78,13 @@
7878
#define FLOAT_PRECISION_DIGITS 7
7979

8080
// Frequency range processing constants
81-
#define FREQ_RANGE_VALUES_PER_RANGE 6 // 6 precision values per frequency range
81+
#define FREQ_RANGE_VALUES_PER_RANGE 14 // 14 precision values per frequency range
8282
#define TEMP_COEFFS_PER_RANGE 3 // 3 temperature coefficients per frequency range
8383
#define MAX_FREQ_RANGE_INDEX 7 // 0-7 for 8 frequency ranges
8484
#define MIN_FREQ_RANGE_INDEX 0
8585

8686
// Buffer sizes for parsing calibration data
87-
#define CALIB_VALUES_BUFFER_SIZE 200 // Buffer for 6 float values
87+
#define CALIB_VALUES_BUFFER_SIZE 256 // Buffer for 14 float values
8888
#define TEMP_VALUES_BUFFER_SIZE 150 // Buffer for 3 float values
8989

9090
// String parsing constants

projects/eval-powrms/src/examples/example/powrms_data_processing.c

Lines changed: 47 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -90,8 +90,8 @@ struct powrms_variables input_variables[VARIABLE_NUMBER] = {
9090
},
9191
};
9292

93-
// Storage for the 48 precision values as 32-bit integers
94-
// Order X1, Y1, X2, Y2, X3, Y3 ....
93+
// Storage for the 112 precision values as 32-bit integers
94+
// Order 10MHz: X1, Y1, X2, Y2, X3, Y3 , X4, Y4, X5, Y5, X6, Y6, X7, Y7, 100MHz:...
9595
int32_t precision_values[PRECISION_ARRAY_SIZE];
9696

9797
// Storage for the 24 temperature correction coefficients as 32-bit integers
@@ -181,14 +181,19 @@ int _calc_interpolating_values(double *x_values, double *y_values,
181181
frequency_MHz_ranges[freq_index]);
182182

183183
// Calculate x1, x2, x3, y1, y2, y3 using floating-point interpolation
184-
for (int i = 0; i < 3; i++) {
185-
x_values[i] = (double)((float)precision_values[6 * freq_index + i * 2] +
186-
((float)precision_values[6 * (freq_index + 1) + i * 2] -
187-
(float)precision_values[6 * freq_index + i * 2]) * (*position)) /
184+
for (int i = 0; i < PRECISION_POINTS_FREQ; i++) {
185+
x_values[i] = (double)((float)precision_values[PRECISION_POINTS_FREQ_ALL *
186+
freq_index + i * 2] +
187+
((float)precision_values[PRECISION_POINTS_FREQ_ALL * (freq_index + 1) + i * 2] -
188+
(float)precision_values[PRECISION_POINTS_FREQ_ALL * freq_index + i * 2]) *
189+
(*position)) /
188190
PRECISION_SCALE_FACTOR;
189-
y_values[i] = (double)((float)precision_values[6 * freq_index + i * 2 + 1] +
190-
((float)precision_values[6 * (freq_index + 1) + i * 2 + 1] -
191-
(float)precision_values[6 * freq_index + i * 2 + 1]) * (*position)) /
191+
y_values[i] = (double)((float)precision_values[PRECISION_POINTS_FREQ_ALL *
192+
freq_index + i * 2 + 1] +
193+
((float)precision_values[PRECISION_POINTS_FREQ_ALL * (freq_index + 1) + i * 2 +
194+
1] -
195+
(float)precision_values[PRECISION_POINTS_FREQ_ALL * freq_index + i * 2 + 1]) *
196+
(*position)) /
192197
PRECISION_SCALE_FACTOR;
193198
}
194199
return 0;
@@ -205,11 +210,15 @@ int _calc_interpolating_values(double *x_values, double *y_values,
205210
frequency_MHz_ranges[prev_range_idx]);
206211

207212
// Calculate x1, x2, x3, y1, y2, y3 using linear extrapolation
208-
for (int i = 0; i < 3; i++) {
209-
int32_t prev_x = precision_values[6 * prev_range_idx + i * 2];
210-
int32_t curr_x = precision_values[6 * curr_range_idx + i * 2];
211-
int32_t prev_y = precision_values[6 * prev_range_idx + i * 2 + 1];
212-
int32_t curr_y = precision_values[6 * curr_range_idx + i * 2 + 1];
213+
for (int i = 0; i < PRECISION_POINTS_FREQ; i++) {
214+
int32_t prev_x = precision_values[PRECISION_POINTS_FREQ_ALL * prev_range_idx + i
215+
* 2];
216+
int32_t curr_x = precision_values[PRECISION_POINTS_FREQ_ALL * curr_range_idx + i
217+
* 2];
218+
int32_t prev_y = precision_values[PRECISION_POINTS_FREQ_ALL * prev_range_idx + i
219+
* 2 + 1];
220+
int32_t curr_y = precision_values[PRECISION_POINTS_FREQ_ALL * curr_range_idx + i
221+
* 2 + 1];
213222

214223
// Linear extrapolation: value = curr + (curr - prev) * extrap_factor
215224
x_values[i] = (double)((float)curr_x + (float)(curr_x - prev_x) *
@@ -254,9 +263,9 @@ int calculate_power()
254263
static float
255264
temp_corr_coeffs[6]; // Both bottom and top limit coeffs, A1, A2, A3, B1, B2, B3
256265
static double
257-
y_values[3]; // Values used for POWER calculations, X axis points, input voltage
266+
y_values[PRECISION_POINTS_FREQ]; // Values used for POWER calculations, X axis points, input voltage
258267
static double
259-
x_values[3]; // Values used for POWER calculations, Y axis points, output power
268+
x_values[PRECISION_POINTS_FREQ]; // Values used for POWER calculations, Y axis points, output power
260269
static uint8_t freq_index; // Cached frequency index
261270
int ret;
262271

@@ -315,23 +324,31 @@ int calculate_power()
315324
VIN0_float = (float)VIN0 / (float)PRECISION_SCALE_FACTOR;
316325
VIN1_float = (float)VIN1 / (float)PRECISION_SCALE_FACTOR;
317326

327+
318328
adc_data_input.adc_vin0_voltage_corrected = VIN0_float;
319329
adc_data_input.adc_vin1_voltage_corrected = VIN1_float;
320330

321-
// 3-point Lagrange interpolation
322-
double y_0 = (VIN0_float - x_values[1]) * (VIN0_float - x_values[2]) / ((
323-
x_values[0] - x_values[1]) * (x_values[0] - x_values[2])) * y_values[0]
324-
+ (VIN0_float - x_values[0]) * (VIN0_float - x_values[2]) / ((
325-
x_values[1] - x_values[0]) * (x_values[1] - x_values[2])) * y_values[1]
326-
+ (VIN0_float - x_values[0]) * (VIN0_float - x_values[1]) / ((
327-
x_values[2] - x_values[0]) * (x_values[2] - x_values[1])) * y_values[2];
328-
329-
double y_1 = (VIN1_float - x_values[1]) * (VIN1_float - x_values[2]) / ((
330-
x_values[0] - x_values[1]) * (x_values[0] - x_values[2])) * y_values[0]
331-
+ (VIN1_float - x_values[0]) * (VIN1_float - x_values[2]) / ((
332-
x_values[1] - x_values[0]) * (x_values[1] - x_values[2])) * y_values[1]
333-
+ (VIN1_float - x_values[0]) * (VIN1_float - x_values[1]) / ((
334-
x_values[2] - x_values[0]) * (x_values[2] - x_values[1])) * y_values[2];
331+
// 7 point Lagrange interpolation
332+
double y_0 = 0.0;
333+
for (int i = 0; i < PRECISION_POINTS_FREQ; i++) {
334+
double term = y_values[i];
335+
for (int j = 0; j < PRECISION_POINTS_FREQ; j++) {
336+
if (j != i) {
337+
term *= (VIN0_float - x_values[j]) / (x_values[i] - x_values[j]);
338+
}
339+
}
340+
y_0 += term;
341+
}
342+
double y_1 = 0.0;
343+
for (int i = 0; i < PRECISION_POINTS_FREQ; i++) {
344+
double term = y_values[i];
345+
for (int j = 0; j < PRECISION_POINTS_FREQ; j++) {
346+
if (j != i) {
347+
term *= (VIN1_float - x_values[j]) / (x_values[i] - x_values[j]);
348+
}
349+
}
350+
y_1 += term;
351+
}
335352

336353
// Convert results back to volts using consistent scale factor
337354
// precision_values are stored with 10^7 scale factor (PRECISION_SCALE_FACTOR)

projects/eval-powrms/src/examples/example/powrms_data_processing.h

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -51,7 +51,9 @@
5151

5252
// Precision array definitions
5353
#define FREQUENCY_RANGE_NR 8 // Number of frequency ranges for callibration
54-
#define PRECISION_ARRAY_SIZE 48
54+
#define PRECISION_ARRAY_SIZE 112
55+
#define PRECISION_POINTS_FREQ 7
56+
#define PRECISION_POINTS_FREQ_ALL 14
5557
#define TEMPERATURE_CORRECTION_COEFFS 3
5658

5759

projects/eval-powrms/src/examples/example/powrms_utils.h

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -45,13 +45,13 @@
4545
0x0003: Calibration data usage for temperature compensation (1 byte)
4646
- 0: Do not use temperature compensation
4747
- 1: Use temperature compensation
48-
0x0004 - 0x00C3: Precision values array (48 int32_t values, 4 bytes each, total 192 bytes)
48+
0x0004 - 0x00C3: Precision values array (112 int32_t values, 4 bytes each, total 448 bytes)
4949
- Stored in little-endian format
5050
0x00C4 - 0x0113: Temperature compensation coefficients array (24 int32_t values, 4 bytes each, total 96 bytes)
5151
- Stored in little-endian format
5252
0x0114 - 0x0117: Voltage temperature compensation value (int32_t, 4 bytes)
5353
- Stored in little-endian format
54-
0x0118 - 0x01D7: Default factory precision values array (48 int32_t values, 4 bytes each, total 192 bytes)
54+
0x0118 - 0x01D7: Default factory precision values array (112 int32_t values, 4 bytes each, total 448 bytes)
5555
- Stored in little-endian format
5656
0x01D8 - 0x0237: Default factory temperature compensation coefficients array (24 int32_t values, 4 bytes each, total 96 bytes)
5757
- Stored in little-endian format
@@ -68,7 +68,7 @@
6868
// User configurable parameters in EEPROM
6969

7070
#define MEM_PRECISION_ARRAY_POZ (MEM_TEMP_COMP_DATA_POZ + MEM_TEMP_COMP_DATA_LEN)
71-
#define MEM_PRECISION_ARRAY_SIZE 192
71+
#define MEM_PRECISION_ARRAY_SIZE 448
7272

7373
#define MEM_TEMP_COMP_ARRAY_POZ (MEM_PRECISION_ARRAY_POZ + MEM_PRECISION_ARRAY_SIZE)
7474
#define MEM_TEMP_COMP_ARRAY_SIZE 96
@@ -78,8 +78,8 @@
7878

7979
// Default values in EEPROM
8080

81-
#define MEM_DEF_PRECISION_ARRAY_POZ (MEM_V_TEMP_COMP_VAL_POZ + MEM_V_TEMP_COMP_VAL_SIZE)
82-
#define MEM_DEF_PRECISION_ARRAY_SIZE 192
81+
#define MEM_DEF_PRECISION_ARRAY_POZ (MEM_V_TEMP_COMP_VAL_POZ + MEM_V_TEMP_COMP_VAL_SIZE)
82+
#define MEM_DEF_PRECISION_ARRAY_SIZE 448
8383

8484
#define MEM_DEF_TEMP_COMP_ARRAY_POZ (MEM_DEF_PRECISION_ARRAY_POZ + MEM_DEF_PRECISION_ARRAY_SIZE)
8585
#define MEM_DEF_TEMP_COMP_ARRAY_SIZE 96

0 commit comments

Comments
 (0)