Clang does not compile a g++ project - boost

When trying to compile a g++ project with the clang compiler, there is a strange error showing up.
Here is the snippet of the source file:
std::set<TTransportNetworkId> l_transportNetworkIds;
SelectionResultContainer l_searchResult = p_repo.rootMoc() / LnAny("LNBTS") / LnAny("LNMME");
BOOST_FOREACH(const SelectionResult & l_lnmmeSR, l_searchResult)
{
const MoLnmme & l_lnmme = l_lnmmeSR;
l_transportNetworkIds.insert(*l_lnmme.transportNwId);
}
The error message is:
conditional expression is ambiguous; 'rvalue_probe<Rrom::DataRep::SelectionResultContainer>' can be converted to 'Rrom::DataRep::SelectionResultContainer' and vice versa
BOOST_FOREACH(const SelectionResult & l_lnmmeSR, l_searchResult)
Conditions are:
The file compiles fine with gcc_4.3.2
clang in version 3.2 throws the above error
Already tried to include the latest boost library which results in the same error
My guess is that clang handles rvalue conditions differently than this gcc version does.
clang is supposed to be a drop-in-replacement for gcc, so how can one get rid of this error without touching the source file?
Are there any options in clang which somehow disables these kind of errors?!
UPDATE:
I could create an example source file, which you can reproduce for yourself:
#include <vector>
#include <boost/foreach.hpp>
class A : public std::vector<int>
{
public:
template <class T>
operator const T &() const;
};
void foo(){
A colA;
int b = 1;
BOOST_FOREACH(b, colA)
{
;
}
}
When compiled with clang 3.2 the above error is raised, with some additional insights to where exactly the error occurs:
error: conditional expression is ambiguous; 'rvalue_probe<A>' can be converted to 'A' and vice versa BOOST_FOREACH(b, colA)
expanded from macro 'BOOST_FOREACH' f (boost::foreach_detail_::auto_any_t BOOST_FOREACH_ID(_foreach_col) = BOOST_FOREACH_CONTAIN(COL))
expanded from macro 'BOOST_FOREACH_CONTAIN' BOOST_FOREACH_EVALUATE(COL)
expanded from macro 'BOOST_FOREACH_EVALUATE' (true ? boost::foreach_detail_::make_probe((COL), BOOST_FOREACH_ID(_foreach_is_rvalue)) : (COL))
This code is compiled without errors with gcc_4.7.2.
Any ideas why the two compilers behave differently?

I found the solution in this document, see http://www.boost.org/doc/libs/1_43_0/boost/foreach.hpp
Snippet:
// Some compilers do not correctly implement the lvalue/rvalue conversion
// rules of the ternary conditional operator.
# if defined(BOOST_FOREACH_NO_RVALUE_DETECTION)
So, when providing a -DBOOST_FOREACH_NO_RVALUE_DETECTION definition option to clang, the error disappears.
Still the question remains whether gcc or clang is right or wrong on this point.

Related

How to query GCC warnings for C++?

GCC allows querying available warning flags specific for C++ language with the syntax:
g++ -Q --help=warning,c++
Adding warning flags to the call includes them in the result:
g++ -Wall -Q --help=warning,c++
However, it seems the call is done from the C point of view and I don't know how to do it from the C++ point of view. If the call includes C++-only warning, like:
g++ -Wnon-virtual-dtor -Q --help=warning,c++
the output contains a message:
cc1: warning: command line option ‘-Wnon-virtual-dtor’ is valid for C++/ObjC++ but not for C
and still shows the warning as disabled:
-Wnon-virtual-dtor [disabled]
Note, that this happens regardless of whether the call is done using g++ or gcc.
The same with C-only -Wbad-function-cast behaves in an expected way:
gcc -Wbad-function-cast -Q --help=warning,c
There is no extra message and reported warning status changes between [disabled] and [enabled]. Again, regardless of whether g++ or gcc is used.
I'm using GCC version 7.3.0. Although the issue seems to apply to many if not all versions. It can be observed through Compiler Explorer.
So, is there a way to do this query with respect to given language?
Yes, your observations are correct.
Probably this is not the intended behavior, and if you care about this feature, then I suggest reporting it upstream.
Note that this works, however:
touch 1.cc
g++ -Wnon-virtual-dtor -Q --help=warning,c++ 1.cc
I.e. if there's an input file with a proper extension, then the correct compiler proper executable is invoked: cc1plus, not cc1. The latter is the default if no input files are present. I did some quick debugging, and here's how that happens:
// gcc.c:
driver::do_spec_on_infiles () const
{
...
for (i = 0; (int) i < n_infiles; i++)
{
...
/* Figure out which compiler from the file's suffix. */
input_file_compiler
= lookup_compiler (infiles[i].name, input_filename_length,
infiles[i].language);
if (input_file_compiler)
{
...
value = do_spec (input_file_compiler->spec);
And input_file_compiler at that point is the C compiler, because
p n_infiles
$9 = 1
(gdb) p infiles[0]
$10 = {name = 0x4cbfb0 "help-dummy", language = 0x4cbfae "c", incompiler = 0x58a920, compiled = false, preprocessed = false}
Here's how the dummy file got created (function process_command in the same file):
if (n_infiles == 0
&& (print_subprocess_help || print_help_list || print_version))
{
/* Create a dummy input file, so that we can pass
the help option on to the various sub-processes. */
add_infile ("help-dummy", "c");
}

Botan build error 'AutoSeeded_RNG' does not name a type

Trying to build the Botan executable, I am getting the following error:
../src/cli/timing_tests.cpp: In static member function 'static Botan::RandomNumberGenerator& Botan_CLI::Timing_Test::timing_test_rng()':
../src/cli/timing_tests.cpp:100:17: error: 'AutoSeeded_RNG' does not name a type
static AutoSeeded_RNG static_timing_test_rng(Botan::Entropy_Sources::global_sources(), 0);
^~~~~~~~~~~~~~
../src/cli/timing_tests.cpp:101:17: error: 'static_timing_test_rng' was not declared in this scope
return static_timing_test_rng;
^~~~~~~~~~~~~~~~~~~~~~
../src/cli/timing_tests.cpp:101:17: note: suggested alternative: 'timing_test_rng'
return static_timing_test_rng;
^~~~~~~~~~~~~~~~~~~~~~
timing_test_rng
make: *** [Makefile:606: build/obj/cli/timing_tests.o] Error 1
this is the C++ code:
static Botan::RandomNumberGenerator& timing_test_rng()
{
#if defined(BOTAN_HAS_SYSTEM_RNG)
return Botan::system_rng();
#elif defined(BOTAN_HAS_AUTO_SEEDING_RNG)
static AutoSeeded_RNG static_timing_test_rng(Botan::Entropy_Sources::global_sources(), 0);
return static_timing_test_rng;
#else
// we could just use SHA-256 in OFB mode for these purposes
throw CLI_Error("Timing tests require a PRNG");
#endif
}
I am using these settings:
configure.py --prefix=$BUILD_DIR --with-external-includedir=$OPENSSL_PREFIX/include --with-external-libdir=$OPENSSL_PREFIX/lib --os=mingw --cpu=i386 --minimized-build --enable- modules=rsa,dsa,ecdsa,ed25519,hmac,hmac_drbg,mode_pad,bigint,filters,block,auto_rng,x509,cbc,dh --with-openssl
(building with mingw32, in Windows 10. Botan version 2.11.0)
I am pretty new on this. Any ideas?
EDIT: Changed to version 2.10.0, since 2.11.0 is not yet official, however the error did now change, to :
undefined reference to 'Botan::CPUID::state()'
Seems like adding entropy source system_rng solves this problem. Just add it to the enable-modules list. Got this from Jack Lloyd, creator of the Botan lib,

how to fix wrong stack alignment with Eigen library under Workbench3.0 (vxworks 6.6 IDE)

I am using Eigen(3.2.0) Library under Workbench3.0 (vxworks 6.6). The compiler in this distribution is GCC version 4.1.2.
Language : c++; Operating System: winXP
the problem code is as followed:
Eigen::Matrix3d mOrigin;
/* initial mOrigin */
...
Eigen::Quaterniond qOrigin(mOrigin);
I debuged the program and found that when it runs :
Eigen::Quaterniond qOrigin(mOrigin);
it comes out the assertion and prints:
assertion failed: (reinterpret_cast(array) & 0xf) == 0 && "this assertion is explained here: " "http://eigen.tuxfamily.org/dox-devel/group__TopicUnalignedArrayAssert.html" " **** READ THIS WEB PAGE !!
! ****" in function Eigen::internal::plain_array::plain_array() [with T = double, int Size = 4, int MatrixOrArrayOptions = 0] at C:/WindRiver-GPPVE-3.6-IA-Eval/vxworks-6.6/target/h/Eigen/src/Core/DenseStorage.h:78
it said, fixed-size vectorizable Eigen objects must absolutely be created at 16-byte-aligned locations, otherwise SIMD instructions adressing them will crash. And that is why the assertion arises.
I think the problem is:
Compiler making a wrong assumption on stack alignment
http://eigen.tuxfamily.org/dox-devel/group__TopicWrongStackAlignment.html
it said, It appears that this was a GCC bug that has been fixed in GCC 4.5. If you hit this issue, please upgrade to GCC 4.5 and report to us, so we can update this page.
However, GCC is the intergation compiler of Workbench and I don't know how to upgrade it.
And I think I have tested the Local Solution and Global Solution, but they don't work.
Local Solution:
add "__attribute__((force_align_arg_pointer))"
class Interpolation : public InterpMath/*,public Colleague*/
{
public:
EIGEN_MAKE_ALIGNED_OPERATOR_NEW
...
__attribute__((force_align_arg_pointer)) ErrorID LineInterp(
const Position_MCS_rad &targetPoint,
const Position_MCS_rad &originPoint,
const Position_ACS_rad &originACS,
double Ts, double maxVel, double maxAcc,
double maxDecel, double maxJerk,
N_AxisSeqPtr &nAglSeqPtr, GrpTcpSeq *pGrpTcp = NULL)
{
Eigen::Matrix3d mOrigin;
/* initial mOrigin */
...
Eigen::Quaterniond qOrigin(mOrigin);
}
}
warning: 'force_align_arg_pointer' attribute directive ignored
Global Solution:
add compile option -mstackrealign
ccpentium -g -mtune=pentium4 -march=pentium4 -ansi -Wall -MD -MP -Xlinker -mstackrealign -IC:/WindRiver-GPPVE-3.6-IA-Eval/vxworks-6.6/target/h -IC:/WindRiver-GPPVE-3.6-IA-Eval/vxworks-6.6/target/h/wrn/coreip -IC:/WindRiver-GPPVE-3.6-IA-Eval/workspace/RobotInterface_2_2/h -DCPU=PENTIUM4 -DTOOL_FAMILY=gnu -DTOOL=gnu -D_WRS_KERNEL -o
So how can I upgrade the intergration compiler to gcc 4.5 or newer, or whether there is other solution to fix this problem ?
Thanks for reading and help.

How to access parsed C++11 attributes via clang tooling

This answer suggests that clang post revision 165082 should retain all parsed attributes in the AST.
I first took this to mean that all attributes would be retained, but this does not appear to be the case:
$ clang++ -v
Apple LLVM version 5.0 (clang-500.2.79) (based on LLVM 3.3svn)
Target: x86_64-apple-darwin13.0.0
Thread model: posix
$ cat att.cpp
void f [[noreturn, foo]] () {}
$ clang++ att.cpp -Xclang -ast-dump -fsyntax-only -std=c++11
att.cpp:1:20: warning: unknown attribute 'foo' ignored [-Wattributes]
void f [[noreturn, foo]] () {}
^
att.cpp:1:30: warning: function declared 'noreturn' should not return [-Winvalid-noreturn]
void f [[noreturn, foo]] () {}
^
TranslationUnitDecl 0x102021cd0 <<invalid sloc>>
|-TypedefDecl 0x102022210 <<invalid sloc>> __int128_t '__int128'
|-TypedefDecl 0x102022270 <<invalid sloc>> __uint128_t 'unsigned __int128'
|-TypedefDecl 0x102022630 <<invalid sloc>> __builtin_va_list '__va_list_tag [1]'
`-FunctionDecl 0x1020226d0 <att.cpp:1:1, col:30> f 'void (void)'
|-CompoundStmt 0x1020227b0 <col:29, col:30>
`-CXX11NoReturnAttr 0x102022770 <col:10>
2 warnings generated.
In the above, note that attribute 'foo' has indeed been ignored, and is not present in the AST, as opposed to the attribute 'noreturn'.
Will attribute 'foo' be retained in the AST at some point, or will all attributes have to be part of the actual compiler (defined in Attr.td etc., as described in the Clang Internals Manual) to be retained in the AST?
The attributes are only retained in the AST if they are already known by Clang, which are most of the GCC attribs and the ones that clang defines itself. However you can(sort of) add your own attribs using the hints from this link. This enables you to define any new attribute and then process it in the ast in the following manner:
For example you took the line of code from the above link
__attribute__((annotate("async"))) uint c;
Then in your RecursiveASTVisitor instantiation you can do as follows:
bool MyRecursiveASTVisitor::VisitVarDecl(VarDecl* v)
{
v->dump();
if(v->hasAttrs()){
clang::AttrVec vec = v->getAttrs();
printf("%s\n",vec[0]->getSpelling());
printf("%s\n", Lexer::getSourceText(
CharSourceRange::getTokenRange(
vec[0]->getRange()),
compiler.getSourceManager(),
langOpts).str().c_str());
}
return true;
}
The first printf only prints the "annotate" since that is the original attribute, to get the value which is of interest to use we get the actual token from the lexer as a string.
Since we did not create a new attribute we only get the append attribute type but we can dig further and distinguish our newly created attribute. Not as elegant as a newly created attribute ( which though possible needs changing clang code itself) but still works.

Compiling OpenMCU in Linux (Fedora12)

I am tring to compile OpenMCU in fedora 12. Since the orignal project was compiled in VC++, it has some compatiility issues with gcc.
I am using gcc 4.4.4 and febora 12.
The error shows somehting like this.
In file included from mcu.h:84,
from main.cxx:56:
filemembers.h:123: error: ISO C++ forbids declaration of ‘deque’ with no type
filemembers.h:123: error: typedef name may not be a nested-name-specifier
filemembers.h:123: error: expected ‘;’ before ‘<’ token
filemembers.h:124: error: ISO C++ forbids declaration of ‘FilenameList’ with no type
filemembers.h:124: error: expected ‘,’ or ‘...’ before ‘&’ token
In file included from mcu.h:84,
from main.cxx:56:
filemembers.h:149: error: ‘FilenameList’ does not name a type
make: *** [obj_linux_x86_r/main.o] Error 1
when checked in the source code of that perticular file it was something like this...
class ConferenceFileMember : public ConferenceMember
{
PCLASSINFO(ConferenceFileMember, ConferenceMember);
public:
ConferenceFileMember(Conference * conference, const PFilePath & _fn, PFile::OpenMode mode);
*typedef std::deque<PFilePath> FilenameList; //Line 123..*
ConferenceFileMember(Conference * conference, const FilenameList & _fns, PFile::OpenMode mode);
~ConferenceFileMember();
void Unlisten();
Seems to be a simple syntax issue. Can someone help me in this regards?
Thanx in advance..
Looks like std::deque is not defined. Did you #include <deque>?

Resources