带有pthread_join的指针无效

时间:2012-03-03 22:05:54

标签: c

#include <pthread.h>            /* Thread related functions*/
#include <stdio.h>              /* Standard buffered input/output        */
#include <stdlib.h>             /* Standard library functions            */
#include <string.h>             /* String operations                     */

struct element{
FILE* file1;
FILE* file2;
int alone;
 };
int comp( const void* a, const void* b) //function for qsort
{


const int *a1 = (const int *)a; // casting pointer types 
const int *b1 = (const int *)b;
return *a1  - *b1; 
}

void* merge(void* filenames) //writes out files to two arrays, merges them and writes output to temp file and passes this tempfile through pthread_exit.
{
struct element* Data;
Data = (struct element*) filenames;
//char* fileA = Data->file1;
//char* fileB = Data->file2;
FILE* A = Data->file1;
FILE* B = Data->file2;

if(Data->alone!=1)
{
    //A = fopen(fileA, "r");
    int linesA = 0;
    int val=0;

        printf("FILE* A: %p \n", A);
        rewind(A);
    while(fscanf(A, "%d", &val) != EOF) 
        linesA++;
    printf("scanf\n");

    rewind(A);

    int* intarrA = (int*) malloc(linesA*sizeof(int));

    int i =0;

    for(;fscanf(A, "%d", &val) != EOF; i++)
        intarrA[i] = val;

    fclose(A);

    //FILE* B;
    //B = fopen(fileB, "r");
    int linesB = 0;

    while(fscanf(B, "%d", &val) != EOF) 
        linesB++;
    rewind(B);

    int* intarrB = (int*) malloc(linesB*sizeof(int));

    i =0;

    for(;fscanf(B, "%d", &val) != EOF; i++)
        intarrB[i] = val;

    fclose(B);

    int templength = linesA+linesB;
    int* inttemp = (int*) malloc(templength*sizeof(int));
    int help1 = 0;
    int help2 = 0;
    int temph = 0;
    for(i=0; i<templength; i++)
    {
        if(help1 == linesA)
        {
            int j = 0;
            for(j=help2; j<linesB; j++)
            {
                inttemp[temph] = intarrB[j];
                temph++;
            }
            break;
        }
        else if(help2 == linesB)
        {
            int j = 0;
            for(j=help1; j<linesA; j++)
            {
                inttemp[temph] = intarrA[j];
                temph++;
            }
            break;
        }
        else if(intarrA[help1]==intarrB[help2])
        {
            inttemp[temph]=intarrA[help1];
            help1++;
            help2++;
            temph++;
        }
        else if (intarrA[help1]<intarrB[help2])
        {
            inttemp[temph]=intarrA[help1];
            help1++;
            temph++;
        }
        else if(intarrA[help1]>intarrB[help2])
        {
            inttemp[temph]=intarrB[help2];
            help2++;
            temph++;
        }
    }
    FILE* filetowrite;
    filetowrite = tmpfile();
    for(i=0; i<temph; i++)
        fprintf(filetowrite ,"%d\n",inttemp[i]);
    printf("Merged %d lines and %d lines into %d lines\n",linesA,linesB,temph);
   // free(intarrA);
  //  free(intarrB);
  //  free(inttemp);
        printf("thread exit\n");
    pthread_exit((void*)filetowrite);
}
else{
    pthread_exit((void*)Data->file1);
        printf("ELSE MERGE \n");
}
}




void* worker(void* filen)
{
//left out to keep code short
}

int main(int argc, char **argv) //gets files through terminal, and sorts each one trhough worker function and then merges them with merge function and pthreads.
{
int zit =0;
void* tempf;
// tempf = malloc(sizeof(FILE));
argc = argc-1;
struct element* filenamelist; //I make an array of this to merge threads till there is only one element left
pthread_t *threadid;
threadid = (pthread_t*) malloc(sizeof(pthread_t)*argc);
int i;

for(i=1; i<=argc; i++) // part 1 passing the files to be qsorted
{
    pthread_create(&threadid[i-1], NULL, worker, (void*) argv[i]);
}
 //sorts each file fine. saves it as filename.sorted
for(i=0; i<argc; i++)
{
    pthread_join(threadid[i], NULL);
}
printf(" DONE WORKER\n");
int mall=0;
int size = 0;
if(size%2 ==0)
size = argc/2;
else
    size = argc/2 +1;
//int Osize = size;
int z=0;
int truth = 0;
// filenamelist = (struct element**) malloc(sizeof(struct element*)*argc);
// for(i=0; i<argc; i++)
    filenamelist = (struct element*) malloc(argc*(sizeof(struct element)));
FILE** inputFiles = malloc(sizeof(FILE*) * (argc+argc));
for(i=1; i<=argc; i++)   //creates a list of elements with file ptrs
{
    filenamelist[(i-1)/2].alone = 0;

    if(i==argc  && i%2!=0)
    {

        char* tedious1 = (char*) malloc( (strlen(argv[i]) + 8 ));
        //char* tedious1 = (char*) malloc((strlen(argv[i+1]+7))*sizeof(char));
        strcpy(tedious1,argv[i]);

        filenamelist[(i-1)/2].file1 = fopen(strcat(tedious1,".sorted"),"r");
        filenamelist[(i-1)/2].file2 = NULL;
        filenamelist[(i-1)/2].alone = 1;
        free(tedious1);
    }
    else
    {        

        char* tedious3 = (char*)malloc( (strlen(argv[i]) + 8 ));
        strcpy(tedious3,argv[i]);
//            printf("%s\n", tedious3);
        if(i%2 ==0)
        filenamelist[i/2].file2 = fopen(strcat(tedious3,".sorted"),"r");
        else
            filenamelist[i/2].file1 = fopen(strcat(tedious3,".sorted"), "r");
        free(tedious3);
    }    

}
/* for(i=0; i<size; i++)
{
    printf("THIS IS: %d\n", i);
    if(filenamelist[i].alone ==1)
      {
          printf(" Alone \n");
        printf(" %p \n", filenamelist[i].file1);
      }
      else
      {
        printf("1 %p \n", filenamelist[i].file1);
        printf("2 %p \n", filenamelist[i].file2);
        }
}*/
//  pthread_t* threadid2;
//    threadid2 = (pthread_t*) malloc(sizeof(pthread_t)*(2*argc));
int xyz = 0;
int arab = 0;
int saudi = 0;
while(size>1) //Iterates through list till only one element left
{

    i = 0;
    pthread_t* threadid2;
    threadid2 = (pthread_t*) malloc(sizeof(pthread_t)*argc);
        printf("before create: %d, %p \n", i, tempf);
    for ( ; i<size;i++ )
    {
            pthread_create(&threadid2[i], NULL, merge, &filenamelist[i]); //<--- invalid pointer
        printf("AFTER create: %d, %p \n", i, threadid2[i]);
    }
    i = 0;
    for ( ; i<size; i++)
    {
        printf("before join JOIN: %d, %p \n", i, tempf);
            pthread_join(threadid2[i], &tempf);
        printf("AFTER JOIN: %d, %p \n", i, tempf);
        if (i%2 == 0)
        {
            filenamelist[i/2].file1 = (FILE*)(tempf);
        }
        else
        {
            filenamelist[i/2].file2 = (FILE*)(tempf);
        }
        if(i%2==0 && i ==size-1)
            filenamelist[i].alone = 1;

        zit=0;
        truth = 0;
        while(zit<z)
        {
            if(inputFiles[zit] == (FILE*)(tempf))
                truth = 1;
            zit++;
        }
        if(truth != 1)
        {  
            inputFiles[z] = (FILE*)(tempf);
            z++;
        }
    }
    if(size==1)
    size = 0;
    else if (size % 2 == 0) 
    size = size/2;
    else
    size = (size/2)+1;
    free(threadid2);

}
pthread_t throwthread;
pthread_create(&throwthread, NULL, merge, &filenamelist[0]);
FILE* final;
pthread_join(throwthread, tempf);
int chd = 0;
final = (FILE*) tempf;
// if(0!=feof(tempf))
//   rewind(tempf);
//rewind(filenamelist[0]->file1);
int finish = 0;
//printf("file 1:%p",tempf);

while(fscanf(final, "%d", &chd) != EOF) 
    finish++;
rewind(final);

int* finarr = (int*) malloc(finish*sizeof(int));

int xx =0;

for(;fscanf(final, "%d", &chd) != EOF; xx++)
    finarr[xx] = chd;

//fclose(filetosort);

//qsort(intarr, i, sizeof(int),comp);

FILE* filetowrites;

filetowrites = fopen("sorted.txt", "w");

for(xx=0; xx<finish; xx++)
    fprintf(filetowrites, "%d\n", finarr[xx]);

fclose(filetowrites);

for(xx=0; xx<z; xx++)
    fclose(inputFiles[xx]);

free(inputFiles);
free(filenamelist);
free(finarr);
return 0;
}//end main func

这给了我一个无效的指针错误。 threadid是指向数组的pthread_t*。 我正在将void* pthread_exit((void*)fileptr);中的文件指针传递给fileptr 其中FILE*tempf

是否可以(FILE*) tempf作为{{1}}访问?

编辑:我已经尝试了对我有意义的一切。不知道为什么threadid2 [i]或tempf会在合并函数中成为无效指针。这不是我可以调试的,请帮助!

第一次加入的错误

0 个答案:

没有答案