Search code examples
c++boostboost-program-options

Copying boost::program_options::parsed_options


Consider this function:

po::parsed_options ParserClass::parseOptions(int argc, char *argv[]) {
    return po::command_line_parser(argc, argv)
            .options(desc)
            .positional(pos)
            .run();
}

desc and pos are member variables of ParserClass.

Is this function safe or does it return a parsed_options object that has pointers pointing to released free store memory because the original object's allocated memory is released when the function returns?

How can you know the semantics? I tried to read the source code to find out but it was a little cryptic to me. The documentation doesn't seem to tell.

If the function is not safe, how could it be fixed? Should you extend the class and define a move operation?


Solution

  • If the object can be copied or moved, it can basically mean three things:

    1. The operations are well-defined and behave safely
    2. Library authors have screwed up and copy/move is ill-behaved
    3. You have to follow some non-obvious conventions while use using it (usually due to performance reasons).

    With boost (and so widely-used parts of it as program_options) we can rule out second option, and for the third one you may consult the documentation to see that there is nothing ridiculous there.

    If you really want to know that argv pointer is not escaping the function (I guess it is the only suspicious place there), you can check that the corresponding basic_command_line_parser constructor copies it into a vector of std::strings (via detail::make_vector:)

    template<class charT>
    basic_command_line_parser<charT>::
    basic_command_line_parser(int argc, const charT* const argv[])
    : detail::cmdline(
        // Explicit template arguments are required by gcc 3.3.1 
        // (at least mingw version), and do no harm on other compilers.
        to_internal(detail::make_vector<charT, const charT* const*>(argv+1, argv+argc+!argc))),
        m_desc()
    {}