2017-04-02 93 views
0

我已经写了代码,这需要从文件输入一个RPN计算器。Valgrind的错误

代码似乎与我的测试情况下工作,但Valgrind的告诉我有28个错误。我是C新手,并没有使用Valgrind。我不明白这些错误是什么。有人可以帮助我了解它们是什么以及如何解决它们?

没有内存泄漏。

这是我的代码,比较遗憾的是非常混乱的代码。

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


float rpn (char * filename) 
{ 

float result; 

    FILE *in = fopen(filename, "r"); 
if (in == NULL) 
    { 
    fprintf(stderr," input file fopen fail\n"); 
    return EXIT_FAILURE; // if fopen fails, return false 
    }  

int count=0; 
char c; 

for (c = getc(in); c != EOF && c!='\n'; c = getc(in)) 
    { 
    if(c==' ') 
    { 
     count = count + 1; 
    } 
} 
fclose(in); 

if (count==0) 
{ 
    fprintf(stderr,"EMPTY FILE\n"); 
    fclose(in); 
    return EXIT_SUCCESS; 
} 


fprintf(stderr,"count=%d\n",count); 


FILE *in2 = fopen(filename, "r"); 
if (in == NULL) 
    { 
    fprintf(stderr," input file fopen fail\n"); 
    return EXIT_FAILURE; // if fopen fails, return false 
    }    
    int num = 0; 
    int num_op = 0; 
    int index =0; 
    int len = count+1; 

    fprintf(stderr,"len = %d\n",len); 

    char**input = malloc(sizeof(char*)*(len+1)); 

    for(int i =0;i<len; i++) 
    { 

     input[i] = malloc(sizeof(char)); 

     fscanf(in2,"%s",input[i]); 




      if((strcmp(input[i],"+")==0)||(strcmp(input[i],"-")==0)||(strcmp(input[i],"*")==0)||(strcmp(input[i],"/")==0)) 
    { 
     num_op = num_op + 1; 
    } 
    else if(atof(input[i])||(strcmp(input[i],"0")==0)||(strcmp(input[i],"-0")==0)) 
    { 
     index = index+1; 
     num = num+1; 
    } 
    } 
    fclose(in2); 

fprintf(stderr,"numbers= %d\n",num); 
fprintf(stderr,"num_op= %d\n",num_op); 
fprintf(stderr,"index= %d\n",index); 

if((num != (num_op+1))) 
{ 
fprintf(stderr,"Bad Input\n"); 
    return EXIT_FAILURE; 
} 

for (int f=index;f<len;f++) 
{ 
    if(!((strcmp(input[f],"+")==0)||(strcmp(input[f],"-")==0)||(strcmp(input[f],"*")==0)||(strcmp(input[f],"/")==0))) 
     { 
     fprintf(stderr,"Bad Input\n"); 
     return EXIT_FAILURE; 
     } 
} 



float *stack = malloc(sizeof(float)*(index+1)); 

for(int h=0; h<index; h++) 
    { 
    stack[h] = atof(input[h]); 
    } 

    /* for(int l =0;(l<index); l++) 
    { 
    printf("stack[%d] = %lf\n",l,stack[l]); 
}  




for(int j =0;(j<len); j++) 
    { 
    printf("input[%d] = %s\n",j,input[j]); 
    } 
*/ 



    int u = index-1; 
    for(int k=index;k<len;k++) 
    { 
     if ((strcmp(input[k],"+"))==0) 
     { 

       stack[u-1] = (stack[u-1] + stack[u]); 
       printf("Result + = %lf\n",stack[u-1]); 
     }   

    else if ((strcmp(input[k],"-"))==0) 
     { 
       stack[u-1] = (stack[u-1] - stack[u]); 
       printf("Result - = %lf\n",stack[u-1]); 
     } 
    else if ((strcmp(input[k],"*"))==0) 
     { 
       stack[u-1] = (stack[u-1] * stack[u]); 
       printf("Result * = %lf\n",stack[u-1]); 
     }  

    else if ((strcmp(input[k],"/"))==0) 
    { 
       stack[u-1] = (stack[u-1]/stack[u]); 
       printf("Result/= %lf\n",stack[u-1]); 
    } 

     else{ 
       printf("Invalid Operator\n"); 

       return EXIT_FAILURE; 
      } 


        if ((u) == 1) 
        { 
        printf("stack_last= %lf\n",stack[u-1]); 
        result = stack[u-1]; 
        for(int d =0;d<len; d++) 
         { 

          free(input[d]); 
         } 

        free(input); 
        free(stack); 
        return result; 

        } 
       u = u-1; 
    } 



    return EXIT_FAILURE; 


    } 
    int main (int argc, char ** argv) { 
    if (argc != 2) { 
    fprintf(stderr, "Incorrect number of arguments.\n"); 
    fprintf(stderr, "Usage: ./pa11 <input file>\n");   
    return EXIT_FAILURE; 

        } 

    float result; //store the result of your calculation here. 

    result=(rpn(argv[1])); 

fprintf(stdout,"Result = %f\n", result); 

return EXIT_SUCCESS; 
    } 

,这些都是从Valgrind的错误

==7692== Invalid write of size 1 
==7692== at 0x391C858C76: _IO_vfscanf (vfscanf.c:1110) 
==7692== by 0x391C8645EA: __isoc99_fscanf (isoc99_fscanf.c:35) 
==7692== by 0x401320: rpn (pa11.c:70) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== Address 0x4c3e5b1 is 0 bytes after a block of size 1 alloc'd 
==7692== at 0x4A06A2E: malloc (vg_replace_malloc.c:270) 
==7692== by 0x4012F4: rpn (pa11.c:68) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== 
==7692== Invalid read of size 1 
==7692== at 0x391C83AC70: ____strtod_l_internal (strtod_l.c:732) 
==7692== by 0x401411: rpn (pa11.c:79) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== Address 0x4c3e5b1 is 0 bytes after a block of size 1 alloc'd 
==7692== at 0x4A06A2E: malloc (vg_replace_malloc.c:270) 
==7692== by 0x4012F4: rpn (pa11.c:68) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== 
==7692== Invalid read of size 1 
==7692== at 0x391C83A478: ____strtod_l_internal (strtod_l.c:787) 
==7692== by 0x401411: rpn (pa11.c:79) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== Address 0x4c3e5b1 is 0 bytes after a block of size 1 alloc'd 
==7692== at 0x4A06A2E: malloc (vg_replace_malloc.c:270) 
==7692== by 0x4012F4: rpn (pa11.c:68) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== 
==7692== Invalid write of size 1 
==7692== at 0x391C858257: _IO_vfscanf (vfscanf.c:1031) 
==7692== by 0x391C8645EA: __isoc99_fscanf (isoc99_fscanf.c:35) 
==7692== by 0x401320: rpn (pa11.c:70) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== Address 0x4c3e601 is 0 bytes after a block of size 1 alloc'd 
==7692== at 0x4A06A2E: malloc (vg_replace_malloc.c:270) 
==7692== by 0x4012F4: rpn (pa11.c:68) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== 
==7692== Invalid read of size 1 
==7692== at 0x391C839E30: str_to_mpn (strtod_l.c:327) 
==7692== by 0x391C83B3D2: ____strtod_l_internal (strtod_l.c:1115) 
==7692== by 0x401411: rpn (pa11.c:79) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== Address 0x4c3e601 is 0 bytes after a block of size 1 alloc'd 
==7692== at 0x4A06A2E: malloc (vg_replace_malloc.c:270) 
==7692== by 0x4012F4: rpn (pa11.c:68) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== 
==7692== Invalid read of size 1 
==7692== at 0x4A084E8: strcmp (mc_replace_strmem.c:729) 
==7692== by 0x40133D: rpn (pa11.c:75) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== Address 0x4c3e6a1 is 0 bytes after a block of size 1 alloc'd 
==7692== at 0x4A06A2E: malloc (vg_replace_malloc.c:270) 
==7692== by 0x4012F4: rpn (pa11.c:68) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== 
==7692== Invalid read of size 1 
==7692== at 0x4A084E8: strcmp (mc_replace_strmem.c:729) 
==7692== by 0x401374: rpn (pa11.c:75) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== Address 0x4c3e6f1 is 0 bytes after a block of size 1 alloc'd 
==7692== at 0x4A06A2E: malloc (vg_replace_malloc.c:270) 
==7692== by 0x4012F4: rpn (pa11.c:68) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== 
numbers= 3 
num_op= 2 
index= 3 
==7692== Invalid read of size 1 
==7692== at 0x4A084E8: strcmp (mc_replace_strmem.c:729) 
==7692== by 0x401619: rpn (pa11.c:99) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== Address 0x4c3e6a1 is 0 bytes after a block of size 1 alloc'd 
==7692== at 0x4A06A2E: malloc (vg_replace_malloc.c:270) 
==7692== by 0x4012F4: rpn (pa11.c:68) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== 
==7692== Invalid read of size 1 
==7692== at 0x4A084E8: strcmp (mc_replace_strmem.c:729) 
==7692== by 0x401650: rpn (pa11.c:99) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== Address 0x4c3e6f1 is 0 bytes after a block of size 1 alloc'd 
==7692== at 0x4A06A2E: malloc (vg_replace_malloc.c:270) 
==7692== by 0x4012F4: rpn (pa11.c:68) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== 
==7692== Invalid read of size 1 
==7692== at 0x391C83AC70: ____strtod_l_internal (strtod_l.c:732) 
==7692== by 0x40177B: rpn (pa11.c:112) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== Address 0x4c3e5b1 is 0 bytes after a block of size 1 alloc'd 
==7692== at 0x4A06A2E: malloc (vg_replace_malloc.c:270) 
==7692== by 0x4012F4: rpn (pa11.c:68) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== 
==7692== Invalid read of size 1 
==7692== at 0x391C83A478: ____strtod_l_internal (strtod_l.c:787) 
==7692== by 0x40177B: rpn (pa11.c:112) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== Address 0x4c3e5b1 is 0 bytes after a block of size 1 alloc'd 
==7692== at 0x4A06A2E: malloc (vg_replace_malloc.c:270) 
==7692== by 0x4012F4: rpn (pa11.c:68) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== 
==7692== Invalid read of size 1 
==7692== at 0x391C839E30: str_to_mpn (strtod_l.c:327) 
==7692== by 0x391C83B3D2: ____strtod_l_internal (strtod_l.c:1115) 
==7692== by 0x40177B: rpn (pa11.c:112) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== Address 0x4c3e601 is 0 bytes after a block of size 1 alloc'd 
==7692== at 0x4A06A2E: malloc (vg_replace_malloc.c:270) 
==7692== by 0x4012F4: rpn (pa11.c:68) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== 
==7692== Invalid read of size 1 
==7692== at 0x4A084E8: strcmp (mc_replace_strmem.c:729) 
==7692== by 0x4017E8: rpn (pa11.c:134) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== Address 0x4c3e6a1 is 0 bytes after a block of size 1 alloc'd 
==7692== at 0x4A06A2E: malloc (vg_replace_malloc.c:270) 
==7692== by 0x4012F4: rpn (pa11.c:68) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== 
Result + = 12.000000 
==7692== Invalid read of size 1 
==7692== at 0x4A084E8: strcmp (mc_replace_strmem.c:729) 
==7692== by 0x40187C: rpn (pa11.c:141) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== Address 0x4c3e6f1 is 0 bytes after a block of size 1 alloc'd 
==7692== at 0x4A06A2E: malloc (vg_replace_malloc.c:270) 
==7692== by 0x4012F4: rpn (pa11.c:68) 
==7692== by 0x401CAD: main (pa11.c:199) 
==7692== 
Result - = -5.000000 
stack_last= -5.000000 
Result = -5.000000 
==7692== 
==7692== HEAP SUMMARY: 
==7692==  in use at exit: 0 bytes in 0 blocks 
==7692== total heap usage: 10 allocs, 10 frees, 1,773 bytes allocated 
==7692== 
==7692== All heap blocks were freed -- no leaks are possible 
==7692== 
==7692== For counts of detected and suppressed errors, rerun with: -v 
==7692== ERROR SUMMARY: 28 errors from 14 contexts (suppressed: 6 from 6) 

回答

1

显然你有错误的位置:

input[i] = malloc(sizeof(char)); 

    fscanf(in2,"%s",input[i]); 

,如果你想输入一个char你需要使用%c,而不是%s, 为%s您需要分配至少两个char,一个用于符号, 另一个用于尾随'\0'

+0

谢谢! input [i] = malloc(sizeof(char)* 2);解决了。但是,我仍然从srtcmp线获得错误,我不知道如何解决这些问题! – akzh