У меня есть эта функция "cost_compare", которую я хотел бы разгрузить на FPGA для некоторых экспериментальных целей.Эта функция, как она вызывается и ее аргументы таковы.
Инструмент синтеза не принимает двойные указатели в качестве аргументов для функций HW (на самом деле он очень требователен к использованию указателей, особенно к структурам данных).
Как избавиться от указателей в списке аргументов функции?Другими словами, как мне преобразовать указатели в этом примере в значения?Как это возможное решение влияет на вызов по ссылке, выполняемый spec_qsort?
Заранее спасибо Хуман
typedef struct arc *arc_p;
typedef LONG cost_t;
typedef struct basket
{
arc_t *a;
cost_t cost;
cost_t abs_cost;
LONG number;
} BASKET;
/* ... */
typedef struct arc
{
int id;
cost_t cost;
node_p tail, head;
short ident;
arc_p nextout, nextin;
flow_t flow;
cost_t org_cost;
} arc;
/* ... */
extern int cost_compare( BASKET **b1, BASKET **b2 );
/* ... */
int cost_compare( BASKET **b1, BASKET **b2 )
{
if( (*b1)->abs_cost < (*b2)->abs_cost )
return 1;
if( (*b1)->abs_cost > (*b2)->abs_cost )
return -1;
if( (*b1)->a->id > (*b2)->a->id )
return 1;
else
return -1;
}
/* ... */
spec_qsort(perm + 1, basket_sizes[thread], sizeof(BASKET*),
(int (*)(const void *, const void *))cost_compare);
/* ... */
BASKET* max, *act;
for (j = 1; j < num_threads; j++) {
act = *perm_p[j];
if (act->number >= 0) {
if (!max || cost_compare(&act, &max) < 0) {
max = act;
max_pos = j;
}
}
/* ... */
BASKET* max_basket;
static BASKET **opt_basket;
for (i = 0; i< num_threads; i++) {
if ((!max_basket && opt_basket[i]) || (opt_basket[i] &&
cost_compare(&opt_basket[i], &max_basket) < 0)) {
max_basket = opt_basket[i];
}
}
/* ... */
========================================
Спасибо @Gerardo Zinno.Когда я запускаю в SW, ваш подход (в последнем абзаце) работает нормально.Однако, когда я синтезирую 'cost_compare' на FPGA, используя Xilinx SDSoC, он работает только для
if(b1->abs_cost < b2->abs_cost)
, но не для
if( b1->a->id > b2->a->id )
, и инструменты выдают мне эту ошибку:
ERROR: [SYNCHK 200-61] /home/a1083898/Xilinx_examples/original_routeplanning/src/pbeampp.c:85: unsupported memory access on variable 'x' which is (or contains) an array with unknown size at compile time.
ERROR: [SYNCHK 200-41] /home/a1083898/Xilinx_examples/original_routeplanning/src/pbeampp.c:89: unsupported pointer reinterpretation from type 'i8*' to type '%struct.arc.1.4.6 = type { i32, i64, %struct.node.0.3.5*, %s...' on variable 'x'.
ERROR: [SYNCHK 200-11] /home/a1083898/Xilinx_examples/original_routeplanning/src/pbeampp.c:89: Argument 'x' has an unsynthesizable type 'i8*' (possible cause(s): pointer to pointer or global pointer).
ERROR: [SYNCHK 200-11] /home/a1083898/Xilinx_examples/original_routeplanning/src/pbeampp.c:89: Argument 'x' has an unsynthesizable type 'i8*' (possible cause(s): structure variable cannot be decomposed due to (1) unsupported type conversion; (2) memory copy operation; (3) function pointer used in struct; (4) unsupported pointer comparison).'
Также при вызове qsort как
qsort(perm + 1, basket_sizes[thread], sizeof(BASKET*), cost_compare);
я получаю это предупреждение:
warning: incompatible pointer types passing 'int (void *, void *)' to parameter of type '__compar_fn_t' (aka 'int (*)(const void *, const void *)') [-Wincompatible-pointer-types]
Я знаю, что эта ошибка не имеет ничего общего с программированием на C, но еслиесть какой-то способ избавиться от 'b1-> a-> id' и 'b2-> a-> id', я считаю, что проблему можно решить с помощью инструмента синтеза HW.
С уважением, Хуман