Compile Error, open -std=C++11

Hi C++ expert:

I found a problem.
I wrote a demo that opened and read a special file. It runs in qnx 7.0.
When I used "x86_64-pc-nto-qnx7.0.0-g ++ FileTest.cc -o FileTest", it compiled and runs successfully.
When I compiled with "x86_64-pc-nto-qnx7.0.0-g ++ -std = c ++ 11 FileTest.cc -o FileTest", some errors is reported:

FileTest.cc: In function 'int main()':
FileTest.cc:13:40: error: 'open' was not declared in this scope
int fd = open("./Zqm.bin", O_RDONLY);
^
FileTest.cc:15:25: error: 'read' was not declared in this scope
read(fd, buffer, 100);
^
FileTest.cc:21:13: error: 'close' was not declared in this scope
close(fd);
^

Demo:
#include <iostream>
#include <unistd.h>
#include <fcntl.h>

using namespace std;

int main()
{
char buffer[100];

memset(buffer, 0, 100);

int fd = open("./Zqm.bin", O_RDONLY);

read(fd, buffer, 100);

cout << buffer << endl;

cout << "open file" << endl;

close(fd);

cout << "close file" << endl;
}

Please help analyze the cause of the error, thank you.
Not sure, but I would guess the -std flag is breaking it.
why not use normal file I/O?
I don't have experience in this (POSIX functions), but you might need to add -lc (that's LC, not IC) to your command-line to link with the C library (clib).

But as jonnin said, since you're clearly using C++, I would used std::ifstream instead of Unix functions.
You should include <cstring> for memset.
You can zero the buffer with {}.
You shouldn't try to print buffer with cout unless you are sure it is zero-terminated. Even then, if it's binary data you should loop through it and print its byte values.

Works for me (compiled as C++14). However, I also see no reason to use the low-level functions here.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
#include <iostream>
#include <iomanip>
#include <cstdio>  // perror
#include <cstring> // memset
#include <unistd.h>
#include <fcntl.h>
using namespace std;

int main()
{
    char buffer[101] {};

    int fd = open("./Zqm.bin", O_RDONLY);
    if (fd == -1)
    {
        perror("open");
        exit(EXIT_FAILURE);
    }

    ssize_t sz = read(fd, buffer, 100);
    if (sz == -1)
    {
        perror("read");
        exit(EXIT_FAILURE);
    }

    cout << "sz: " << sz << "\n\n";

    buffer[sz] = 0; // ensure zero-termination
    
    cout << buffer << "\n\n";  // may print garbage

    cout << hex << setfill('0');
    for (ssize_t i = 0; i < sz; ++i)
        cout << setw(2) << int(buffer[i]) << ' ';
    cout << '\n';
        
    close(fd);
}

Last edited on
I thought memcpy/memset/etc were in <memory> (or cmemory?)
There's a C++ <memory> where, e.g., unique_ptr lives. But I guess because strings are basically just sequences of bytes (in the common case) the "memory" functions in C are in <string.h>, hence <cstring>.

BTW, I don't think I actually answered his question since I don't think he was compiling on desktop linux (qnx is a linux-based embedded thing). So I'm not sure what the problem was.
Thanks all.

Need to add the compile option XOPEN_SOURCE.
like this:
x86_64-pc-nto-qnx7.0.0-g++ -D_XOPEN_SOURCE=500 -std=c++11 -L/home/xxx/3rd-party/qnx-x86_64/protobuf/lib -L/home/xxx/3rd-party/qnx-x86_64/zeromq/lib -lprotobuf -lzmq -I/home/xxx/3rd-party/qnx-x86_64/protobuf/include -I/home/xxx/3rd-party/qnx-x86_64/zeromq/include simple.pb.cc ZmqDumpTest.cc -o ZmqDumpTest

details:
In the program, in order to achieve the above functions, it is necessary to define a corresponding macro. As the second function POSIX, _POSIX_SOURCE should be defined. Similar to _BSD_SOURCE, _SVID_SOURCE, _XOPEN_SOURCE.
That is:
#define _XOPEN_SOURCE
It is for the purpose of using the 5. The X/Open Portability Guide.
Last edited on
http://man7.org/linux/man-pages/man7/feature_test_macros.7.html

These are part of GNU C library:
POSIX Standard: Symbolic Constants       <unistd.h>
POSIX Standard: File Control Operations  <fcntl.h>


QNX-g++ is a GCC variant. GCC's language default includes GNU extensions.
The -std=c++11 disables GNU extensions.

man g++:
c++11
The 2011 ISO C++ standard plus amendments.

gnu++11
GNU dialect of -std=c++11.



There are thus multiple options:
* Define a macro on command line or in source
* Tell g++ to use the GNU extensions (to enable your POSIX functions)
* Use Standard C functions
* Use Standard C++ functions
Registered users can post here. Sign in or register to post.