0

I've searched for solutions to that problem and couldn't find any that match mine.

I wrote a program that gets two arrays of integers and return the scalar product between them. It works fine when I'm submitting the input manually, but when I try to read the input from a text file, I encounter that Segmentation fault.

Edit: I'm talking about stdin redirection

I would be grateful for some help.

The code is:

#include <stdio.h>
#define MAXLIMIT 100

int scalar_product(int[], int[], int);
void set_array(int[]);

int main(){
    int arr1[MAXLIMIT], arr2[MAXLIMIT];
    int size, result;

    set_array(arr1);
    set_array(arr2);

    printf("Enter the vectors' dimension: ");
    scanf("%d", &size);

    result = scalar_product(arr1, arr2, size);
    printf("The scalar product is: %d \n", result);
    
    return 0;
}

void set_array(int a[]){
    int i;
    printf("Please enter a vector with up to %d elements: \n", MAXLIMIT);
    for (i = 0; i < MAXLIMIT - 1 && (scanf("%d", &a[i]) != EOF); i++);
}

int scalar_product(int a1[], int a2[], int size){
    int product = 0, i;
    for (i = 0; i < size; i++){
        product += a1[i] * a2[i];
    }
    return product;
}

and the text file contains:

1 -2 3 -4
6 7 1 -2
4
Ben Arviv
  • 3
  • 4
  • 1
    "*I've searched*". This is not something you search for. You need to debug the issue. Run your program in a debugger. At a minimum it will give you the exact line of code that triggers the seg fault. Can also use it to trace and examine the program as it runs. – kaylum Mar 20 '22 at 23:45
  • "*when I try to read the input from a text file*". The code shown does not read from file. Do you mean you are redirecting the file as stdin? – kaylum Mar 20 '22 at 23:46
  • 2
    Seems to me the first `set_array` call will read all of the data, the second will fail due to `EOF`, and the next `scanf` call doesn't check the return value so `size` is used uninitialized. – Retired Ninja Mar 20 '22 at 23:47
  • Thank you for your answer, @kaylum. As written, when I provide the input the standard way, the program works absolutely fine. Only when I redirect the input to read from a file, I get that segmentation error. How can I debug the rediretion process? When I debug in VS Code, I can submit the input only from the terminal, as far as I know. Let me know please if that possible to debug with the file. Yes, I'm talking about redirecting the stdin. – Ben Arviv Mar 20 '22 at 23:50
  • Thank you, @RetiredNinja. I get what you're saying. How can I inform the first `set_array` to stop at the fourth number? can I write EOF manually within the text file for it to stop reading? – Ben Arviv Mar 20 '22 at 23:57
  • Does this answer your question? [What is a segmentation fault?](https://stackoverflow.com/questions/2346806/what-is-a-segmentation-fault) – Colonel Thirty Two Mar 21 '22 at 00:04
  • No, @ColonelThirtyTwo, the question is why did it happened when I tried to redirect stdin to a text file, although it worked fine by manually inserting the numbers. – Ben Arviv Mar 21 '22 at 00:09

1 Answers1

-1

HEre

   void set_array(int a[]) {
       int i;
       printf("Please enter a vector with up to %d elements: \n", MAXLIMIT);
         for (i = 0; i < MAXLIMIT - 1 && (scanf("%d", &a[i]) != EOF); i++);
    }

When reading from the console you will never hit EOF (unless you enter ctrl-D which I guess you didnt) so your set_array loops just keep going, reading from the file. You read all the data in the first set_array and read nothing in the second one because you have finished the input file

the actualk failure was that you ran off the end of the file, so the scanf of size failed and you were trying to read a random sized array in the function scalar_product.

Test the return from scanf always

What you need to do is put a count in the file before the first array so you know how many items to read into arr1 and I suggest a count before the second lot too.

ie

 void set_array(int a[]) {
    int i;
    int count = 0;
    
    printf("Please enter how many elements you want to enter, max = %d \n", MAXLIMIT);
    scanf("%d", &count);
    if(count > MAXLIMIT) count = MAXLIMIT;
    for (i = 0; i < count && (scanf("%d", &a[i]) != EOF); i++);
 }
pm100
  • 48,078
  • 23
  • 82
  • 145
  • Thank you @pm100, it did solve my problem. Is there a way that inside the text file I'll inform the program that it has to stop reading from that point, while not reading the whole text? Just like CTRL+D in the terminal (which I did use, actually). – Ben Arviv Mar 21 '22 at 00:06
  • @BenArviv no - the only way is to put counts in the file. – pm100 Mar 21 '22 at 00:14
  • 1
    @BenArviv I was wondering what you did, ctrl-D will have stopped all reading from stdin, so your second loop would read nothing and the scanf of size would fail too, it was just failing in a non obvious way . Once you get into UB (Undefined Behaviour) anything can happen – pm100 Mar 21 '22 at 00:15
  • Well, I believe that after hitting CTRL-D it just ended the scanning in the for loop, exited to main and entered the second `set_array`, which made the program scan again for input, and so on? – Ben Arviv Mar 21 '22 at 00:48
  • 1
    @BenArviv nope, once you hit CTRL-D all scanf will return EOF – pm100 Mar 21 '22 at 00:49