2015-05-19 83 views
1

我正在写一个程序,它从参数中获取一个标识符,创建一个UDP套接字,获取一个端口,并打印<identifier>: <port>
然后,从标准输入接收一些标识符和端口并将它们存储在内存中。
在下面的代码,该问题是端口变量(udp_port)得到0。为什么我会在C中获得意外的端口值?

#include <stdio.h> 
#include <stdlib.h> 
#include <string.h> 
#include <strings.h> 
#include <sys/socket.h> 
#include <sys/types.h> 
#include <netinet/in.h> 

typedef struct process { 
    char id[80]; 
    int port; 
    int me; 
} process; 

int main(int argc, char* argv[]) { 

    if(argc<2) { 
     fprintf(stderr,"Use: process <ID>\n"); 
     return 1; 
    } 

    /* NODES */ 
    process * processes; 
    int num_process = 0; 

    /* CONECTION */ 
    int udp_port; 
    int fd; 
    struct sockaddr_in addr, local_addr; 

    /* STDIN READS */ 
    int port; 
    char line[80],proc[80]; 

    /* I/O buffer mode */ 
    setvbuf(stdout,(char*)malloc(sizeof(char)*80),_IOLBF,80); 
    setvbuf(stdin,(char*)malloc(sizeof(char)*80),_IOLBF,80); 

    /* Prepare socket */ 
    bzero(&addr, sizeof(addr)); 
    addr.sin_family = AF_INET; 
    addr.sin_port = htons(0); 
    addr.sin_addr.s_addr = INADDR_ANY; 

    fd = socket(AF_INET, SOCK_DGRAM, 0); 
    if(fd == -1){ 
     perror("SOCKET"); 
     return 1; 
    } 

    if(bind(fd, (struct sockaddr *) &addr, sizeof(addr)) == -1){ 
     perror("BIND"); 
     return 1; 
    } 
    getsockname(fd, (struct sockaddr *)&local_addr, (socklen_t *) sizeof(struct sockaddr)); 

    udp_port=ntohs(local_addr.sin_port); // Gets port 

    fprintf(stdout,"%s: %d\n",argv[1],udp_port); // Prints identifier: port 

    // Reads from stdin 
    for(;fgets(line,80,stdin);) { 
     if(!strcmp(line,"START\n")) 
      break;    

     sscanf(line,"%[^:]: %d",proc,&port); 
     num_process++; 
     processes = realloc(processes,num_process); 
     strcpy(processes[num_process-1].id, proc); 
     processes[num_process-1].port = port; 

     if(!strcmp(proc,argv[1])){ /* Thats me */ 
      processes[num_process-1].me = 1; 
     }else{ 
      processes[num_process-1].me = 0; 
     } 
    } 


    return 0; 
} 

但是,它得到正确的值(随机端口),当我发表意见的realloc线和相关的线路,像这样:

// Reads from stdin 
    for(;fgets(line,80,stdin);) { 
     if(!strcmp(line,"START\n")) 
      break;    

     sscanf(line,"%[^:]: %d",proc,&port); 
     num_process++; 
     //processes = realloc(processes,num_process); 
     //strcpy(processes[num_process-1].id, proc); 
     //processes[num_process-1].port = port; 

     if(!strcmp(proc,argv[1])){ /* Thats me */ 
     // processes[num_process-1].me = 1; 
     }else{ 
     // processes[num_process-1].me = 0; 
     } 
    } 
+0

一个问题:你传递给'realloc'未初始化的指针是危险的。 – Prabhu

+0

不要在'C'中输入'malloc'的返回值。它可以隐藏错误并且不会带来任何好处。 – harper

+1

检查套接字函数的返回值,如'getsockname'。 – harper

回答

1

如果按照原样使用,则代码会崩溃。因为你通过重新分配未初始化的指针。初始化processes为NULL:

process * processes = NULL;

编辑:

否则,udp_port是非零。并且getsockname返回错误的地址。 请尝试以下为getsockname是successsful:

socklen_t tmp = sizeof(struct sockaddr);

getsockname (fd, (struct sockaddr *) &local_addr,&tmp);

0

检查getsockname函数的返回值,我收到了Bad address错误。 的问题是,在getsockname最后一个参数是不正确的:

getsockname(fd, (struct sockaddr *)&local_addr, (socklen_t *) sizeof(struct sockaddr)); 

sizeof返回socklen_t,而不是socklen_t *。我这样解决这个问题:

socklen_t size_sa = sizeof(struct sockaddr); 
if(getsockname(fd, (struct sockaddr *)&local_addr, &size_sa) == -1){ 
    perror("GETSOCKNAME"); 
    return 1; 
} 
相关问题