简体   繁体   English

为什么我的printf打印错误的值?

[英]Why is my printf printing the wrong values?

I can't figure out why my code is not working. 我不知道为什么我的代码无法正常工作。 I am trying to create something similar to P2P file transfer where multiple threads simultaneously grab different parts of a file from a pre-existing server program. 我正在尝试创建与P2P文件传输类似的东西,其中多个线程同时从预先存在的服务器程序中获取文件的不同部分。 The actual problem I am having right now, is much simpler, however. 我现在遇到的实际问题要简单得多。

Since you cannot pass multiple arguments into pthread_create, I created a structure that had the two pieces of information I want to pass. 由于您不能将多个参数传递给pthread_create,因此我创建了一个结构,其中包含我想传递的两条信息。 I also created an array of pointers to these structures and initialize each one individually before passing it's pointer in. 我还创建了一个指向这些结构的指针数组,并在将其指针传入之前分别初始化了每个结构。

printf("In thread: port=%d & ipAddr=%s\n",conn->port,conn->ipAddr);

When that line runs, everything prints out correctly with the correct port number and IP address. 当该行运行时,所有内容都会正确打印,并带有正确的端口号和IP地址。

printf("Size of chunk %d received by %lu on port %d: %d bytes\n",chunkNum,pthread_self(),conn->port,sizeRec);

However, when that line runs shortly after, the port number does not print out correctly. 但是,当该行不久之后运行时,端口号无法正确打印。 Instead of 9210 and 9211, I get 0 and 134520848. Otherwise, everything seems to be working so I'm thinking it may just be a printf problem of some sort, but I want to be sure before I move on to implementing the next part of my project. 而不是9210和9211,我得到0和134520848。否则,一切似乎都在起作用,因此我认为这可能只是某种printf问题,但我想确定在继续实施下一部分之前我的项目。

If anyone has any idea why the same variable would print with one value and a completely different a few lines later when no changes were made, it would be very helpful for me. 如果有人知道为什么相同的变量在不进行任何更改的情况下会打印一个值而在几行后显示完全不同的变量,那么这对我很有帮助。 I have included all of my code below for reference. 我在下面包括了所有代码以供参考。 Thanks for your help! 谢谢你的帮助!

#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>

#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <pthread.h>

char * file_name = "output.txt";
int nextChunk = 0;

pthread_mutex_t lock1 = PTHREAD_MUTEX_INITIALIZER;

struct connection{
  int port;
  char* ipAddr;
};

void* getFile(void* args) {
  int con_fd = 0;
  int ret = 0;  
  struct sockaddr_in serv_addr;
  struct connection* conn = (struct connection*)args;
  printf("In thread: port=%d & ipAddr=%s\n",conn->port,conn->ipAddr);

memset(&serv_addr, 0, sizeof(struct sockaddr));
serv_addr.sin_family = AF_INET;
//printf("port number: %d\n",conn->port);
serv_addr.sin_port = htons(conn->port);
serv_addr.sin_addr.s_addr = inet_addr(conn->ipAddr);
int sizeRec;
char buf[1024];
while(1) {
    con_fd = socket(PF_INET, SOCK_STREAM, 0);
    if (con_fd == -1) {
        printf("Socket Error\n");
        fflush(stdout);
        return 0;
    }
    ret = connect(con_fd, (struct sockaddr *)&serv_addr, sizeof(struct sockaddr));
    if (ret < 0) {
        printf("Connect error\n");
        fflush(stdout);
        return 0;
    }
    char chunkStr[128];
    pthread_mutex_lock(&lock1);
    int chunkNum = nextChunk++;
    pthread_mutex_unlock(&lock1);
    sprintf(chunkStr,"%d",chunkNum);
    send(con_fd,chunkStr,128,0);
    sizeRec = recv(con_fd,buf,1024,0);
    printf("Size of chunk %d received by %lu on port %d: %d bytes\n",chunkNum,pthread_self(),conn->port,sizeRec);
    if (sizeRec <= 0) {
        return 0;
    }
} 
/*FILE *f = fopen(filename, "w");
if (!f) {
    printf("Can't open %s for input. Program halting\n",filename);
    exit(0);
}*/
/*while ((sizeReceived = recv(sock,buf,1024,0)) > 0) {
    if (fwrite(buf,sizeof(char),sizeReceived,f) == -1) {
        printf("Error writing file");
        exit(0);
    }
}
fclose(f);*/
close(con_fd);
return 0;
}

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

if (argc < 3 || argc % 2 == 0) {
printf("Usage: ./client <ipaddr1> <port1> <ipaddr2> <port2> . . .\n");
return -1;
}
int numThreads = argc / 2;
pthread_t threads[numThreads];
struct connection** connections = malloc(sizeof(struct connection*)*numThreads);
//char* args[numThreads][2];
printf("numThreads: %d\n",numThreads);
for (int i=0; i<numThreads; i++) {
    connections[i] = malloc(sizeof(struct connection));
    connections[i]->ipAddr = argv[2*i+1];
    connections[i]->port = atoi(argv[2*i+2]);
    printf("port number: %d\n",connections[i]->port);
    pthread_create(&threads[i], NULL, getFile, (void*)(connections[i]));
}
for (int i=0; i<numThreads; i++) {
    free(connections[i]);
    pthread_join(threads[i], NULL);
}
pthread_mutex_destroy(&lock1);
return 0;
}

Your main problem is the second for loop in main() . 您的主要问题是main()的第二个for循环。

You first free the data structure and then call pthread_join() . 您首先要释放数据结构,然后调用pthread_join() Reverse these two statements and it should work reliable. 颠倒这两个陈述,它应该工作可靠。

If you use Linux, I suggest to use valgrind tool, which easily helps to spot such issues. 如果您使用Linux,则建议使用valgrind工具,该工具可以轻松帮助发现此类问题。 For windows I only know expensive commercial tools doing the same (like Purify). 对于Windows,我只知道这样做的昂贵商业工具(例如Purify)。

Change this : 改变这个:

for (int i=0; i<numThreads; i++) {
    free(connections[i]);
    pthread_join(threads[i], NULL);

To : 至 :

for (int i=0; i<numThreads; i++) {
    pthread_join(threads[i], NULL);        
    free(connections[i]);

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

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM