1

I am trying to write a c program, which will take an input from Linux pipe and puts each word up to the point when it encounters \n into arrays. Then it outputs the words. It works when array contain less than 3 \n but it gives me segmentation error if there is 3 \n`s in the input. Here is the code that I wrote, please help. I am new to programming,so please try to live the code as intact as possible.

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

int main()
{
  int out=0;
  int in=0;
  char **arr2D;
  int i;
  int flag = 1;
  arr2D=(char**)malloc(out*sizeof(char*));
  for(i=0;i<out;i++)
    arr2D[i]=(char*)malloc(in*sizeof(char*));

  while (!feof(stdin))
    {
      in = in +1;
      arr2D[out]=(char*)realloc(arr2D[out],(in)*sizeof(char*));
      scanf("%c",&arr2D[out][i]);

      i=i+1;
      if(arr2D[out][i-1]=='\n')
        {
        out=out+1;
        arr2D=(char**)realloc(arr2D,out*sizeof(char*));
        i=0;
        in=0;
        }
    }

  int out2=0;
  int in2=0;
  do
    {
      do
        {
          printf("%c",arr2D[out2][in2]);
          in2++;
        }
      while(in2<=in-1);
      out2++;
      in2=0;
    }
  while(out2<=out);

  printf("\n");
  return 0;
}
3
  • First, indent your code. Commented Feb 7, 2015 at 21:32
  • int out=0; : begin with a number greater than zero Commented Feb 7, 2015 at 21:43
  • while(feof is a bug Commented Feb 7, 2015 at 22:30

4 Answers 4

2

Following code work correctly:

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


int main(int argc, char *argv[])
{
    int out = 1;
    int in = 1;
    char **arr2D;
    int i = 0;

    arr2D = malloc(out * sizeof(char *));
    for (i = 0; i < out; i++)
          /* IMPORTANT */
          arr2D[i] = malloc(in * sizeof(char));

    while (!feof(stdin)) {

        scanf("%c", &arr2D[out - 1][in - 1]);

        in++;
        if (arr2D[out - 1][in - 2] == '\n') {
            arr2D[out - 1][in - 2] = '\0';
            out++;
            arr2D = realloc(arr2D, out * sizeof(char *));
            /* IMPORTANT */
            arr2D[out - 1] = NULL;
            in = 1;
        }

        /* IMPORTANT */
        arr2D[out - 1] = realloc(arr2D[out - 1],in * sizeof(char));


    }

    int out2 = 0;
    do {
        printf("%s\n", arr2D[out2++]);
    } while(out2 < out);
    printf("\n");
    return 0;
}
Sign up to request clarification or add additional context in comments.

4 Comments

Even though that's a bug, it's definitely not the cause for the segmentation fault: sizeof(char*) is always greater than sizeof(char) (unless you are on an 8 bit architecture, that is...).
That seem not to change anything my friend.
Sorry, I still reading your code if find something I will tell you.
@cmaster there are non-8bit architectures where those sizes are equal. (Also I never heard of an 8bit architecture that didn't actually use 16bit pointers, although theoretically they're possible)
0

You haven't properly initialized the variable i within your while loop.

int i;
scanf("%c",&arr2D[out][i]);

6 Comments

i is initialized at the beginning of the program, how can I initialize it in the loop and why ?
@user1335175 You declare the variable i, but you don't initialize it. For that you would need int i = 0;
As a matter of fact, he does initialize i: in the initialization statement of the first for() loop, which is executed even though the loop body is never executed...
@cmaster Whoops, didn't notice that
@cmaster Either way, though, the loop initializes it to the value of the variable 'out'. Though I'm not sure whether or not this caused the Segfault, it is a bug in its own right.
|
0

First you allocate a buffer for out elements, but then you proceed to access arr2D[out] which is out of bounds in the first line with realloc(). Remember that indexing of an array int arr[size] in C is always from 0 to size-1, arr[size] is never ok.

For reference: the allocation line is the first malloc() call:

arr2D=(char**)malloc(out*sizeof(char*));

and the line with the first undefined behavior is the second line within the while() loop:

arr2D[out]=(char*)realloc(arr2D[out],(in)*sizeof(char*));

within the first while() loop. That is the point that invokes undefined behavior, and after which anything is allowed to happen.

6 Comments

Im note sure which part of the code you are referring to, even if I am commenting the output part, I still get the error, so I know the bug is in the part when I construct my arrays.
I added the offending lines to my answer, hope that helps you to find what I mean.
Im sorry for redundant questioning my friend, can you specify how exactly can I fix that line ? Because in my understanding, the first parameter of realloc should be the arr2D[out] itself.
First, the element at arr2D[out] must exist. That is, you first need to realloc() the outer array so that you have room for at least one more element. Then, and only then can you proceed to write to that new element. The first time you get to the realloc() line, there is zero elements in the out array arr2D.
Oh I see what do you mean, any explanation why it works in the case when there is less than 3 \n in the input tough ?
|
0

Parham`s method seems to work, Also I found another way, altough Im not sure if there is something wrong in doing this, but it works.

Evey time when I am allocating or reallocating, I multiply the *sizeof(char) buy a buffer size which is a big number.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.