Opened 9 years ago

Closed 9 years ago

Last modified 8 years ago

#3336 closed defect (fixed)

ParModelica: Cannot pass parallel array as argument to function

Reported by: gustaf Owned by: mahge930
Priority: blocker Milestone: 1.9.4
Component: ParModelica Version: trunk
Keywords: Cc:

Description (last modified by gustaf)

Looking at the MPARBenchmarkSuite it's not too uncommon to call an ordinary function with parallel arrays as argument. Eigenvalue.mo does so (note: it uses the 'parallel' prefix rather than 'parglobal' as currently used by ParModelica to annotate parallel variables).

Here is a small test where parallel variables are passed as argument:

package ParArg
 constant Integer nx = 10;
 
  function mult
    input Real a;
    input Real m[nx];
    output Real result[nx];
  protected
    parglobal Real pa;
    parglobal Real pm[nx];
    parglobal Real presult[nx];
  algorithm
    pa := a;
    pm := m;
    parfor i in 1:nx loop
      presult[i] := pm[i]*pa;
    end parfor;
    result := presult;
  end mult;

  function multParArg
    input Real a;
    parglobal input Real mpm[nx];
    parglobal output Real mpresult[nx];
  protected
    parglobal Real pa;
  algorithm
    pa := a;
    parfor i in 1:nx loop
      mpresult[i] := mpm[i]*pa;
    end parfor;
  end multParArg;

  function Test
    input Real a;
    output Real result[nx];
  protected
    Real m[nx] = {i for i in 1:nx};
    Real pm[nx];
  algorithm
    result := mult(a,m);
  end Test;

  function TestParArg
    input Real a;
    output Real result[nx];
  protected
    Real m[nx] = {i for i in 1:nx};
    parglobal Real pa;
    parglobal Real pm[nx];
    parglobal Real presult[nx];
  algorithm
    pa := a;
    pm := m;
    presult := multParArg(pa,pm);
    result := presult;
  end TestParArg;
end ParArg;

Here is a script for testing:

setCommandLineOptions("+d=noevalfunc +g=ParModelica -v=1");
getErrorString();

setDefaultOpenCLDevice(1);
getErrorString();

loadFile("ParArg.mo");
getErrorString();

x:=ParArg.Test(5);
getErrorString();

y:=ParArg.TestParArg(5);
getErrorString();

Here is the result, showing how the second test using parallel variables as argument fails (probably due to wrong code generated):

Error processing file: ParArg.mos
Error: Error building simulator. Build log: g++ -I"/home/gustaf/src/OpenModelica/build/include/omc/c"   -fPIC -O0 -march=native   -c -o ParArg_TestParArg.o ParArg_TestParArg.c
ParArg_TestParArg.c: In function ‘real_array omc_ParArg_TestParArg(threadData_t*, modelica_real)’:
ParArg_TestParArg.c:41:66: error: could not convert ‘_pm’ from ‘device_real_array {aka dev_arr}’ to ‘real_array {aka base_array_s}’
   copy_real_array_data(omc_ParArg_multParArg(threadData, _pa, _pm), &_presult);
                                                                  ^
ParArg_TestParArg.c: In function ‘device_real_array omc_ParArg_multParArg(threadData_t*, modelica_real, real_array)’:
ParArg_TestParArg.c:142:54: error: call of overloaded ‘ocl_set_kernel_arg(_cl_kernel*&, int&, void*&)’ is ambiguous
   ocl_set_kernel_arg(tmp4, parfor_1_arg_nr, _mpm.data); ++parfor_1_arg_nr; 
                                                      ^
ParArg_TestParArg.c:142:54: note: candidates are:
In file included from ParArg_TestParArg.h:8:0,
                 from ParArg_TestParArg.c:1:
/home/gustaf/src/OpenModelica/build/include/omc/c/ParModelica/explicit/openclrt/omc_ocl_interface.h:84:6: note: void ocl_set_kernel_arg(cl_kernel, int, cl_mem) <near match>
 void ocl_set_kernel_arg(cl_kernel kernel, int arg_nr, cl_mem in_arg);
      ^
/home/gustaf/src/OpenModelica/build/include/omc/c/ParModelica/explicit/openclrt/omc_ocl_interface.h:84:6: note:   no known conversion for argument 3 from ‘void*’ to ‘cl_mem {aka _cl_mem*}’
/home/gustaf/src/OpenModelica/build/include/omc/c/ParModelica/explicit/openclrt/omc_ocl_interface.h:88:6: note: void ocl_set_kernel_arg(cl_kernel, int, modelica_integer) <near match>
 void ocl_set_kernel_arg(cl_kernel kernel, int arg_nr, modelica_integer in_arg);
      ^
/home/gustaf/src/OpenModelica/build/include/omc/c/ParModelica/explicit/openclrt/omc_ocl_interface.h:88:6: note:   no known conversion for argument 3 from ‘void*’ to ‘modelica_integer {aka long int}’
ParArg_TestParArg.c:143:50: error: ‘real_array’ has no member named ‘info_dev’
   ocl_set_kernel_arg(tmp4, parfor_1_arg_nr, _mpm.info_dev); ++parfor_1_arg_nr; 
                                                  ^
ParArg_TestParArg.c: In function ‘void* boxptr_ParArg_multParArg(threadData_t*, modelica_metatype, modelica_metatype)’:
ParArg_TestParArg.c:163:49: error: could not convert ‘_mpresult’ from ‘device_real_array {aka dev_arr}’ to ‘base_array_t {aka base_array_s}out_mpresult = mmc_mk_modelica_array(_mpresult);
                                                 ^
ParArg_TestParArg.makefile:18: recipe for target 'ParArg_TestParArg' failed
make: *** [ParArg_TestParArg] Error 1

# Error encountered! Exiting...
# Please check the error message and the flags.

Execution failed!

Change History (5)

comment:1 Changed 9 years ago by gustaf

  • Description modified (diff)

comment:2 Changed 9 years ago by mahge930

  • Resolution set to fixed
  • Status changed from new to closed

comment:3 Changed 9 years ago by dietmarw

  • Milestone changed from Future to 1.9.4

Sorting these closed tickets away from "Future". Since they were closed after the last 1.9.3 release, it's very likely that they should have been part of the 1.9.4 release.

comment:4 Changed 8 years ago by sjoelund.se

  • Milestone changed from 1.9.4 to 1.9.4-1.9.x

Milestone renamed

comment:5 Changed 8 years ago by sjoelund.se

  • Milestone changed from 1.9.4-1.9.x to 1.9.4

Milestone renamed

Note: See TracTickets for help on using tickets.