简体   繁体   English

错误:在参数列表中声明的'struct addrinfo'在此定义或声明[-Werror] |之外将不可见

[英]error: ‘struct addrinfo’ declared inside parameter list will not be visible outside of this definition or declaration [-Werror]|

I get this if I try to compile with one of C standards: 如果我尝试使用C标准之一进行编译,我会得到这个:

-std=c99 , -std=c11 or -std=c17 . -std=c99-std=c11-std=c17

If I remove them compiles fine or if I use -std=gnuXX works as well 如果我删除它们编译正常或如果我使用-std=gnuXX也可以

Why is happening that, because I just can't fix it. 为什么会发生这种情况,因为我无法修复它。

program.c: program.c:

#include <string.h>
#include <stdio.h>
#include <netinet/in.h>
#include <net/if.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netdb.h>
#include <stdlib.h>
#include <unistd.h>

#define PORT "5555"
#define BACKLOG 5

int getAdr_fd(struct addrinfo server, struct addrinfo **res );
int create_fd( struct addrinfo **res );
int accept_fd( struct sockaddr_storage *their_addr, int *sockfd );
int list_fd( int *sockfd );
int bind_fd( struct addrinfo **res, int *sockfd );
ssize_t write_fd( const char *const msg, int *new_fd );

int main(void){
    const char *msg = "Hello socket World!\n";
    struct sockaddr_storage their_addr;
    struct addrinfo server, *res;
    int sockfd, new_fd;

    /* create a socket: */
    getAdr_fd( server, &res );
    sockfd = create_fd( &res );

    /* Bind */
    bind_fd( &res, &sockfd );

    /* Listen */
    list_fd( &sockfd );

    /* Accept connection: */
    new_fd = accept_fd( &their_addr, &sockfd );

    /* Write */
    write_fd( msg, &new_fd );

    /* close: */
    close(sockfd);
    freeaddrinfo(res);
 }

 int getAdr_fd(struct addrinfo server, struct addrinfo **res ){
    int getfd;

    /* Create address structs with getaddrinfo(): */

    memset(&server, 0, sizeof server);
    server.ai_family = AF_UNSPEC; // use IPv4 or IPv6, whichever
    server.ai_socktype = SOCK_STREAM;
    server.ai_flags = AI_PASSIVE; // fill in my IP for me

    getfd = getaddrinfo( NULL, PORT, &server, res);
    if (getfd != 0) {
        fprintf(stderr, "getaddrinfo: %s\n", gai_strerror( getfd ));
        exit(EXIT_FAILURE);
    }else{
        printf("getaddrinfo() \tOK\n");
        return getfd;
    }
}

int create_fd( struct addrinfo **res ){
    int sockfd = socket((*res)->ai_family, (*res)->ai_socktype, (*res)->ai_protocol);
    if (sockfd == -1 ){
        printf("Error, socket()\n");
        exit ( EXIT_FAILURE );
    }else{
        printf("socket() \tOK\n");
        return sockfd;
    }
}

int bind_fd( struct addrinfo **res, int *sockfd ){
    int bindfd = bind(*sockfd, (*res)->ai_addr, (*res)->ai_addrlen);
    if (bindfd == -1 ){
        printf("Error, bind(), check line 34\n");
        exit ( EXIT_FAILURE );
    }else{
        printf("bind() \t\tOK\n");
        return bindfd;
    }
}

int accept_fd(  struct sockaddr_storage *their_addr, int *sockfd  ){
    int new_fd;
    socklen_t addr_size = sizeof( *their_addr );
    new_fd = accept(*sockfd, (struct sockaddr *)their_addr, &addr_size);
    if (new_fd == -1 ){
        printf("Error, accept()\n");
        exit ( EXIT_FAILURE );
    }else{
        printf("accept() \tOK\n");
        return new_fd;
    }
}

int list_fd( int *sockfd ){
    int listfd = listen(*sockfd, BACKLOG);
    if (listfd == -1 ){
        printf("Error, listen()\n");
        exit ( EXIT_FAILURE );
    }else{
        printf("listen() \tOK\n");
        return listfd;
    }
}

ssize_t write_fd( const char *const msg, int *new_fd ){
    size_t len = strlen(msg);
    ssize_t wrtfd;
    wrtfd = write(*new_fd, msg, len );
    if (wrtfd == -1 ){
        printf("Error, write()\n");
        exit ( EXIT_FAILURE );
    }else{
        printf("write() \tOK\n");
    }

    return wrtfd;
}

Compiler flags: 编译器标志:

-Wpedantic -Wall -Wextra -Werror -std=c17 -Wstrict-prototypes  -Wmissing-prototypes -Wmisleading-indentation -Wduplicated-cond -Wold-style-definition -Wconversion -Wshadow -Winit-self -Wfloat-equal -Wwrite-strings -Wcast-align=strict -Wformat -O0 -g

Output: 输出:

 program.c:14:22: error: 'struct addrinfo' declared inside parameter list will not be visible outside of this definition or declaration [-Werror] int getAdr_fd(struct addrinfo server, struct addrinfo **res ); ^~~~~~~~ program.c:15:23: error: 'struct addrinfo' declared inside parameter list will not be visible outside of this definition or declaration [-Werror] int create_fd( struct addrinfo **res ); ^~~~~~~~ program.c:18:21: error: 'struct addrinfo' declared inside parameter list will not be visible outside of this definition or declaration [-Werror] int bind_fd( struct addrinfo **res, int *sockfd ); ^~~~~~~~ program.c: In function 'main': program.c:24:21: error: storage size of 'server' isn't known struct addrinfo server, *res; ^~~~~~ program.c:28:16: error: type of formal parameter 1 is incomplete getAdr_fd( server, &res ); ^~~~~~ program.c:28:24: error: passing argument 2 of 'getAdr_fd' from incompatible pointer type [-Werror=incompatible-pointer-types] getAdr_fd( server, &res ); ^~~~ program.c:14:57: note: expected 'struct addrinfo **' but argument is of type 'struct addrinfo **' int getAdr_fd(struct addrinfo server, struct addrinfo **res ); ~~~~~~~~~~~~~~~~~~^~~ program.c:29:25: error: passing argument 1 of 'create_fd' from incompatible pointer type [-Werror=incompatible-pointer-types] sockfd = create_fd( &res ); ^~~~ program.c:15:34: note: expected 'struct addrinfo **' but argument is of type 'struct addrinfo **' int create_fd( struct addrinfo **res ); ~~~~~~~~~~~~~~~~~~^~~ program.c:32:14: error: passing argument 1 of 'bind_fd' from incompatible pointer type [-Werror=incompatible-pointer-types] bind_fd( &res, &sockfd ); ^~~~ program.c:18:32: note: expected 'struct addrinfo **' but argument is of type 'struct addrinfo **' int bind_fd( struct addrinfo **res, int *sockfd ); ~~~~~~~~~~~~~~~~~~^~~ program.c:45:5: error: implicit declaration of function 'freeaddrinfo' [-Werror=implicit-function-declaration] freeaddrinfo(res); ^~~~~~~~~~~~ program.c:24:21: error: unused variable 'server' [-Werror=unused-variable] struct addrinfo server, *res; ^~~~~~ program.c: At top level: program.c:48:23: error: 'struct addrinfo' declared inside parameter list will not be visible outside of this definition or declaration [-Werror] int getAdr_fd(struct addrinfo server, struct addrinfo **res ){ ^~~~~~~~ program.c:48:32: error: parameter 1 ('server') has incomplete type int getAdr_fd(struct addrinfo server, struct addrinfo **res ){ ~~~~~~~~~~~~~~~~^~~~~~ program.c: In function 'getAdr_fd': program.c:56:23: error: 'AI_PASSIVE' undeclared (first use in this function); did you mean 'AF_WANPIPE'? server.ai_flags = AI_PASSIVE; // fill in my IP for me ^~~~~~~~~~ AF_WANPIPE program.c:56:23: note: each undeclared identifier is reported only once for each function it appears in program.c:58:13: error: implicit declaration of function 'getaddrinfo'; did you mean 'getAdr_fd'? [-Werror=implicit-function-declaration] getfd = getaddrinfo( NULL, PORT, &server, res); ^~~~~~~~~~~ getAdr_fd program.c:60:46: error: implicit declaration of function 'gai_strerror'; did you mean 'strerror'? [-Werror=implicit-function-declaration] fprintf(stderr, "getaddrinfo: %s\\n", gai_strerror( getfd )); ^~~~~~~~~~~~ strerror program.c:60:40: error: format '%s' expects argument of type 'char *', but argument 3 has type 'int' [-Werror=format=] fprintf(stderr, "getaddrinfo: %s\\n", gai_strerror( getfd )); ~^ ~~~~~~~~~~~~~~~~~~~~~ %d program.c:48:32: error: unused parameter 'server' [-Werror=unused-parameter] int getAdr_fd(struct addrinfo server, struct addrinfo **res ){ ~~~~~~~~~~~~~~~~^~~~~~ program.c: At top level: program.c:68:23: error: 'struct addrinfo' declared inside parameter list will not be visible outside of this definition or declaration [-Werror] int create_fd( struct addrinfo **res ){ ^~~~~~~~ program.c:68:5: error: conflicting types for 'create_fd' int create_fd( struct addrinfo **res ){ ^~~~~~~~~ program.c:15:5: note: previous declaration of 'create_fd' was here int create_fd( struct addrinfo **res ); ^~~~~~~~~ program.c: In function 'create_fd': program.c:69:31: error: dereferencing pointer to incomplete type 'struct addrinfo' int sockfd = socket((*res)->ai_family, (*res)->ai_socktype, (*res)->ai_protocol); ^~ program.c: At top level: program.c:79:21: error: 'struct addrinfo' declared inside parameter list will not be visible outside of this definition or declaration [-Werror] int bind_fd( struct addrinfo **res, int *sockfd ){ ^~~~~~~~ program.c:79:5: error: conflicting types for 'bind_fd' int bind_fd( struct addrinfo **res, int *sockfd ){ ^~~~~~~ program.c:18:5: note: previous declaration of 'bind_fd' was here int bind_fd( struct addrinfo **res, int *sockfd ); ^~~~~~~ program.c: In function 'bind_fd': program.c:80:38: error: dereferencing pointer to incomplete type 'struct addrinfo' int bindfd = bind(*sockfd, (*res)->ai_addr, (*res)->ai_addrlen); ^~ cc1: all warnings being treated as errors 

Another strange thing which I notice is: 我注意到的另一个奇怪的事情是:

program.c:45:5: error: implicit declaration of function ‘freeaddrinfo’ [-Werror=implicit-function-declaration]
 freeaddrinfo(res);

But the include files are there: 但包含文件在那里:

#include <sys/types.h>
#include <sys/socket.h>
#include <netdb.

Linux Mint 19, GCC-8.0.1. Linux Mint 19,GCC-8.0.1。

The getaddrinfo function, and by extension the struct addrinfo type, are specified by POSIX. getaddrinfo函数和扩展struct addrinfo类型由POSIX指定。 This means that they're not part of the C standard. 这意味着它们不属于C标准。

So when you specify -std=c99 , -std=c11 or -std=c17 , it excludes those types because they are not specified by the standard. 因此,当您指定-std=c99-std=c11-std=c17 ,它会排除这些类型,因为它们未由标准指定。 Specifying a -std=gnuxx option includes the definitions of those types. 指定-std=gnuxx选项包括这些类型的定义。

This borders on a glibc bug. 这与glibc错误接壤。 While it is true that struct addrinfo is not part of the C standard, neither is <netdb.h> , so it would not do any harm to define it in that header (except for very old POSIX versions). 虽然struct addrinfo不是C标准的一部分,但<netdb.h>也不是,所以在该标题中定义它不会有任何损害(除了非常旧的POSIX版本)。

You can still specify any of the C standard options and get the GNU extensions if you compile with -D_GNU_SOURCE . 如果使用-D_GNU_SOURCE编译,仍然可以指定任何C标准选项并获取GNU扩展。 See the glibc documentation and the manual page: 请参阅glibc文档和手册页:

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 在参数列表中声明的在此定义之外将不可见或在 c 中声明错误 - declared inside parameter list will not be visible outside of this definition or declaration error in c 警告:在参数列表中声明的“struct tag”在此定义或声明之外将不可见 void func(struct tag v); - warning: ‘struct tag’ declared inside parameter list will not be visible outside of this definition or declaration void func(struct tag v); 警告:'struct task_struct'“在此定义或声明之外,在参数列表中声明的将不可见” - warning: ‘struct task_struct’ “Declared inside parameter list will not be visible outside of this definition or declaration” 在参数列表中声明的 gcc 窗口在此定义或声明之外将不可见 - gcc windows declared inside parameter list will not be visible outside of this definition or declaration struct&#39;在参数列表中使用头文件声明 - struct’ declared inside parameter list with a header file “警告:&#39;结构矩阵&#39;在参数列表中声明[默认启用]”和错误:&#39;scanToken&#39;的类型冲突 - “warning: 'struct matrix' declared inside parameter list [enabled by default]” and error: conflicting types for 'scanToken' c编译器警告:参数列表内声明了“ struct x” - c compiler warning: 'struct x' declared inside parameter list 警告:在参数列表中声明了“struct user_data_s” - warning: ‘struct user_data_s’ declared inside parameter list 在参数列表中声明的“结构记录”[默认启用] - ‘struct record’ declared inside parameter list [enabled by default] 奇怪的编译器警告 C:警告:在参数列表中声明了“结构” - Strange compiler warning C: warning: ‘struct’ declared inside parameter list
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM