C: incompatible types in assignment

前端 未结 4 1408
感情败类
感情败类 2021-01-27 14:02

I\'m writing a program to check to see if a port is open in C. One line in particular copies one of the arguments to a char array. However, when I try to compile, it says:

相关标签:
4条回答
  • 2021-01-27 14:36

    addr is an array so you can't assign to it directly.

    Change addr = strncpy(addr, argv[2], 1023); to strncpy(addr, argv[2], 1023);

    A pointer to what you passed in is returned, but this value isn't needed. The call to strncpy alone will copy the string from argv[2] to addr.


    Note: I notice sometimes you pass in the address of your array and sometimes you pass in the array itself without the address of operator.

    When the parameter only asks for char*...

    Although both will work passing in addr instead of &addr is more correct. &addr gives a pointer to a char array char (*)[1023] whereas addr gives you a char* which is the address of the first element. It usually doesn't matter but if you do pointer arithmetic then it will make a big difference.

    0 讨论(0)
  • 2021-01-27 14:41

    You've gotten a couple of answers that address exactly what you asked. My advice would be to step back and just eliminate that step, as it's completely unnecessary. I'd change these lines:

    u_short port;                /* user specified port number */
    char addr[1023];             /* will be a copy of the address entered by u */
    struct sockaddr_in address;  /* the libc network address data structure */
    
    port = atoi(argv[1]);
    addr = strncpy(addr, argv[2], 1023);
    bzero((char *)&address, sizeof(address));  /* init addr struct */
    address.sin_addr.s_addr = inet_addr(addr); /* assign the address */
    address.sin_port = htons(port);            /* translate int2port num */
    

    to something like this:

    struct sockaddr_in address = {0};
    
    address.sin_port = htons(atoi(argv[1]));        
    address.sin_addr.s_addr = inet_addr(argv[2]);
    

    The existing code is doing a lot of unnecessary copying, making the code bigger and slower without accomplishing anything.

    Edit: looking at it again, you should probably add a bit of error checking code (before what's above), something like:

    if (argc != 3) {
        fprintf(stderr, "Usage: %s <port_num> <address>", argv[0]);
        return EXIT_FAILURE;
    }
    
    0 讨论(0)
  • 2021-01-27 14:54

    an alternative is to use a char * instead:

    char *addr;
    
    addr = strdup(argv[2]);
    

    strdup is basically a shortcut that does a malloc and a strcpy, and you don't have to worry about the size of addr upfront. Don't forget to free addr once you're done.
    Note that if argv[2] is NULL you will get a segfault.

    0 讨论(0)
  • 2021-01-27 14:59

    The line

    addr = strncpy(addr, argv[2], 1023);
    

    should be just

    strncpy(addr, argv[2], 1023);
    

    note that strncpy doesn't null-terminate if the 1023 limit is reached so you should also have

    addr[1023] = `\0`;
    

    though I suppose there's other assumptions made in the code as well.

    0 讨论(0)
提交回复
热议问题