I'm trying to port the Open Source package QuickFAST C++ to OSS on a
Blade running J06.04. QuickFAST uses 2 further Open Source packages,
Xerces-c and Boost, which i also am attempting to port.
I have been able to compile all of the sources of QuickFAST, but am
now getting an error in the eld step that appears to involve the boost
libraries:
**** FATAL ERROR **** [1597] - linker halting:
Illegal duplicate definition of the initialized data item
c__Q2_5boost6detail (C++ mangling of boost::detail::c) in C and/or C
++,
occurring in Codecs/Decoder.o and Codecs/Encoder.o.
I assume that the boost libraries must be correct, since they are
being used on other platforms, so what I think I should be looking for
is one of:
1) some way of telling eld that duplicate initialized data items are
ok.
2) a way of telling the compiler (perhaps with a toggle/ifdef) to
avoid the conflict.
- I have been trying to identify the code where boost::detail::c is
defined, but I haven't been able to find it so far. A search for
"boost::detail::c" in both QuickFAST and boost subdirectories doesn't
get any hits and I suppose that the "c" part must be substituted at
compile time, but I don't know what to look for.
3) could it be that I need c99 (ie J06.10) to allow the c++ construct.
Do any of you have any ideas?
Thanks in advance
- pete
The Boost libraries might be correct, but perhaps QuickFAST is not using them correctly. I don't know the cause of the problem, but I am wary of your apparent path to solving it by telling the loader to ignore the error. I don't have experience with C++, but other languages that I do know have the rule that you only initialize static data in one place. If your build method is such that the linker sees two initializations of the same data, I think that is a danger sign that you have done something wrong with the build.
I don't know whether you found this, but Decoder and Encoder are in QuickFast (in /src/Codecs). I took a quick look at them, but I don't know enough C++ to spot the problem, if there is one there. But if you had not noticed that Decoder and Encoder were there, I wanted to point that out.
If you have not already studied whatever build instructions are provided for all three of those packages, take a careful look at them to be sure you are building them correctly.
Or it might be that you are using QuickFAST incorrectly. I get the impression that QuickFAST is a library to be used from a program the user writes. Are you getting the eld error when trying to link such a program that you wrote? If so, is it possible that your program combines using encoding and decoding while QuickFAST was designed with the limitation that a program may use encoding or decoding, but not both? I have no idea whether that is a sensible question -- I'm just tossing out ideas, since no one else seems to have stepped up with any.
> I don't know whether you found this, but Decoder and Encoder are in QuickFast (in /src/Codecs). I took a quick look at them, but I don't know enough C++ to spot the problem, if there is one there. But if you had not noticed that Decoder and Encoder were there, I wanted to point that out.
> Thanks, but I did get that far. Presumably, based boost::detail::c, the offending area is somewhere in the boost/src/detail/*.hpp directory
.
> If you have not already studied whatever build instructions are provided for all three of those packages, take a careful look at them to be sure you are building them correctly.
> I have been, but most of the documents presume in depth unix knowledge, which sadly I'm (still) lacking.
> Or it might be that you are using QuickFAST incorrectly. I get the impression that QuickFAST is a library to be used from a program the user writes. Are you getting the eld error when trying to link such a program that you wrote? If so, is it possible that your program combines using encoding and decoding while QuickFAST was designed with the limitation that a program may use encoding or decoding, but not both? I have no idea whether that is a sensible question -- I'm just tossing out ideas, since no one else seems to have stepped up with any.- Hide quoted text -
> I'm only compiling the QF library, so I'm not at that stage yet where my application could be in question. I am interested in the decoding bit and have a working (on unix) test program to use, but that will be the next step. The fact that Encoder and Decoder are together in the same library is a QF thing and not determined by me. In fact, there are more QF objects that have this conflict, not just Encoder.o and Decoder.o, but eld stops at the first.
> - Show quoted text -
The idea to find an option to say duplicate definitions are ok comes
from the eld manual error description.
The boost libraries are maybe 80% header files only, where you use
only the provided typedefs and don't need the actual boost objects, so
it's possible that the offending code isn't really required by
QuickFAST. That's one of the avenues I'm exploring, but I would like
to identify the code where the confict is coming from, which means
identifying the offending boost header file. Does anyone know of a
method that would identify the source file for me using enoft or
something else?
@Keith: Thanks for the feedback. Even if you don't have the solution,
it's always good to have a sounding board.
That linker error explanation is a real tease, isn't it? Tells you that there is the possibility of a solution using appropriate C++ options, but then says that, since we aren't C++, we can't tell you what those solutions are. Bah!
I've just spent more than an hour pawing through the QuickFAST project site looking for anything that seems to be documentation on how to use the product, and, except for a few example programs, I find nothing. I admit that I did not look at the source of the example programs, so perhaps there are extensive comments there that provide some directions on how one goes about building a program that makes use of the QuickFAST classes. But there ought to be some stand alone document giving the rules for using the library. So how did you learn how to construct the program that you are trying to link?
What I was trying to find is whether there are any rules or even hints about whether the project is intended to support both reading FAST messages and creating FAST messages in the same program. I have the feeling that the authors have not tried that and so have not run into the duplicate initialization that you are encountering. Maybe I'm all wet, but that is my feeling about your problem.
I can suggest a few things.
You asked about how to identify the offending source file. The linker is trying to tell you that. It points to Codecs/Encoder.o and Codecs/Decoder.o as the object files in which the duplicate initializations occur, and gives the object name boost::detail::c as the name of the object that is intialized in both object files. That ought to be enough to find the thing, but, like you, I can't find something that looks like that name when looking through Encoder.cpp, Decoder.cpp, and the header files they include. I wonder whether the linker is making a mistake when demangling the actual name. If there still is a way to get the C++ system to output the C code that corresponds to the C++ code, try doing that and look through the C code for c__Q2_5boost6detail.
If it isn't too big a chore, try splitting your program into two programs, one of which does the message reading and the other of which does the message writing and see whether you can get that to work.
Similarly, if it isn't too big a chore, try downloading and installing the binary distribution for Windows and building your program there. If it does not get the duplicate initialization error on Windows and works properly there, then that is good evidence that I'm wrong that QuickFAST was not meant to both read and write FAST messages in the same program. That still would not tell you how to avoid the duplicate initialization on OSS, but it would tell you that it ought to be possible. If you do get the duplicate initialization error on Windows, then you probably don't have a problem with how you built the libraries (since you would be using the pre-built libraries), but a problem with how you are trying to use them.
Join the QuickFAST mailing list (http://groups.google.com/group/quickfast_users) and post a question about your problem. I'll bet that would get you an answer pretty quickly.
Unfortunately I wasn't able to identify the place in the source where
the conflict was coming from, but was able to work around the problem
by moving to an older version of the boost library (1.42.0 instead of
1.47.1), where the problem didn't manifest itself. I'm guessing that
it's a case of the compiler on J06.04 being out of date, but the boost
1.42 library is compatible wit the QuickFAST version I am trying to
implement, so it's moot for now.
@Keith: thanks for your suggestions and the time you put into it
Thanks for telling us the resolution to the matter.
I'm glad you got the program working. Too bad we could not figure out why you were getting the error with Boost 1.47.1. The cause might be some error in the compiler on the NonStop system, it might be that Boost 1.47.1 was doing something on the edge of what is specified as allowed for C++ templates and other compilers are more tolerant than the NonStop compiler is, or it might be something else I'm not thinking of. Anyway, as long as you don't have to move to a later version of the Boost library for some other reason, it doesn't matter for now.