[nvhpc-22.2] error: use of undefined value '%L.LB26_8163'

Hi.
This is the software project with undefined value.
Describe the bug
I’m trying compile the SU2 software with NVIDIA HPC compiler with openmp. The compile will failed at 708th module with error like this:

error: /../nvhpc/Linux_x86_64/23.5/compilers/share/llvm/bin/llc: /tmp/nvc++jHoQBMAMK7HA.ll:31881:20: error: use of undefined value '%L.B1552'
       br i1  %32, label %L.B1552, label %L.B3113, !llvm.loop !10337, !dbg !10335

To Reproduce
prerequest tool && lib install

sudo apt install gcc g++ python3-pip mpich libatlas-base-dev intel-mkl libfabric-dev

pip install mpi4py
python3 -m pip install numpy
python3 -m pip install scipy
python3 -m pip install rtree
python3 -m pip install petsc
python3 -m pip install petsc4py

[This file was removed because it was flagged as potentially malicious] (76.7 MB)

Then run following commands at terminal window with this project’s root file location as working directory.

set_env
./ninja -C build install

note: in the set_env bash file, you need chang it according each sofawares’ location or put it the same location as mine(F:\work\SU2_NVC).

Expected behavior
ninja failed at 708th module with similar error about undefined value.
If I change the compile flag -O1 to -O3 in ./build/build.ninja, Compile will fall with other error log.

system parameters

  • This is a Windows wsl2 Ubuntu subsystem compile
  • Ubuntu 22.04
  • Python 3.10.6
  • ninja 1.10.1

Thanks for any comments.

Ok, I’ve spent a few hours going through the process. Got hung up on trying to run this from another directory but there’s a lot of files with /mnt/f/work/SU2_NVC hard coded in it, so I just decided to create this directory and work out of there. Then the build fails because it says it can’t detect ninja v1.8.2 or newer. I have ninja v1.11.1 installed. Not sure what to do so giving up.

Can you simplify this by posting stand-alone compilation line to recreate the error or a minimal reproducing example?

-Mat

OK, I will try. This may take a few weeks.

Hi Mat,
Does Nvidia HPC have Pragma directive keyword _Pragma? I have not yet recreate a minimal reproducing about SU2.
I’m confused by the compiler preprocess with -E flag.
Here is a small reproducing example.
Describe the bug
g++ and nvc++ have quit different preprocess output with the same input file.

To Reproduce
global_access.cpp file:

#define PRAGMIZE(X) _Pragma(#X)

#define SU2_OMP(ARGS) PRAGMIZE(omp ARGS)

#define SU2_OMP_MASTER SU2_OMP(master)
#define SU2_OMP_BARRIER SU2_OMP(barrier)

#define END_SU2_OMP_MASTER

#define BEGIN_SU2_OMP_SAFE_GLOBAL_ACCESS \
  SU2_OMP_BARRIER \
  SU2_OMP_MASTER

#define END_SU2_OMP_SAFE_GLOBAL_ACCESS \
  END_SU2_OMP_MASTER \
  SU2_OMP_BARRIER

#define SU2_OMP_SAFE_GLOBAL_ACCESS(...) \
  BEGIN_SU2_OMP_SAFE_GLOBAL_ACCESS \
  { \
    __VA_ARGS__ \
  } \
  END_SU2_OMP_SAFE_GLOBAL_ACCESS
  
void test(){
  
}

int main(){
  SU2_OMP_SAFE_GLOBAL_ACCESS(test();)
}

Expected behavior
g++ preprocess command:

g++ -std=c++11 -fopenmp -E global_access.cpp

nvc++ preprocess command:

nvc++ -std=c++11 -mp -E global_access.cpp

nvc++ preprocess output isn’t similar to g++. Does this mean nvc++ use other keyword as atternative?
The _Pragma preprocessing operator was introduced into the C standard in C99, and the C++ standard in C++11 as above share link says.
Are there any differences between directives and preprocessing operator in compiler domain?

system parameters

  • g++ 11.3.0
  • nvc++ 23.5

Thanks
Rudi

Yes, we support “_Pragma”, it’s just getting processed by the compiler rather than the preprocessor.

% nvc++ -mp -Minfo=mp test.cpp
main:
     30, Barrier
         Begin master region
         End master region

If you want to match what g++ does, use the “-Mcpp” flag so the cpp preprocessor is used instead.

Are there any differences between directives and preprocessing operator in compiler domain?

I’m not 100% clear if you’re asking if there are differences between “_Pragma” and “#pragma”, or asking if there are difference between compilers.

“_Pragma” and “#pragma” are effectively the same, though I believe the reason why “_Pragma” was added was because you can’t use new lines in macros. This severely limited how “#pragma” can be used in macros. “_Pragma” will implicitly add a newline.

As for compilers, there are many common pragmas but it’s up to the individual compiler vendor if a particular pragma is supported.

1 Like

Thanks.
When I using the “-Mcpp” flag with standard library header file(.e.g, cstring, iostream), It will failed with following output:

PREPRO-F-0206-Can't find include file iostream (../main.cpp: 2)
PREPRO/x86-64 Linux 23.5-0: compilation aborted

There is a similar post.
I can solve this error by using “-Xcompiler-Mcpp” flag.

The second question is asking about does compiling souce code with micro (user defined) and directives (something like openmp) have order about which must be done first.
SU2’s design give me illusion about compile. It seems like micro should be translated before openmp directives.
It seems I should dive into compiler theory instead of only waiting compiler update as a black box tool. This may give me some insights.

Does this really not have a space between -Xcompiler and -Mcpp? If so, then this gets interrupted as a single flag and the -Mcpp portion is ignored.

The solution to the issue is to add the system C++ include directories, something like:

nvc++ -Mcpp -c test.cu -I/usr/include/c++/8/ -I/usr/include/c++/8/x86_64-redhat-linux/

Keep in mind that cpp only preprocesses the file. There’s no compilation.

The second question is asking about does compiling souce code with micro (user defined) and directives (something like openmp) have order about which must be done first.

Macros are processed by the preprocessor prior to compilation. Pragmas/directives are processed later by the compiler.

Yes, this flag really work.
Compile command with global_access.cpp as following:
nvc++ -std=c++11 -mp -Xcompiler-Mcpp global_access.cpp
This will get an executable file and a file named ‘compiler-Mcpp’. I think compiler read this flag as ’ -X<file>’ in nvc++ help, then generate cross reference information into the file named ‘compiler-Mcpp’.
Preprocess command:
nvc++ -std=c++11 -mp -E -Xcompiler-Mcpp global_access.cpp
It looks like working well.

Macros are processed by the preprocessor prior to compilation. Pragmas/directives are processed later by the compiler.

SU2 use _Pragma directive keyword as base for SU2’s micro. This order in SU2 micro compile may lead to fail.