Error segmentation fault not able to identify

1

Hello, friends!

I am creating a program that will read a text. This text should be allocated one line at a time (up to 75 characters per line).

The program receives, at the input, the user's text until the string "the end!" is typed.

However when I run the program, I'm getting the error: Segmentation fault (core dumped). (Detail: This error is common to me, and for several times I have tried to solve it, but without success). Please tell why this error happens, not only in this code but also its common causes.)

Later, I'll use the stringUpper function to leave my text in uppercase.

#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>
#include <string.h>
#define MAX_CHAR 75

const char THE_END[] = "the end!";
void stringUpper(char*, int);

void main() {
    char **texto;
    int i = 0;
    int j;
    texto = NULL;
    for( ; ; ) {
        texto = (char**)realloc(texto,(i+1)*sizeof(char*));
        texto[i] = (char*)malloc(MAX_CHAR*sizeof(char));
        fgets(texto[i],MAX_CHAR,stdin);
        texto[strlen(texto[i]-1)] = '
#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>
#include <string.h>
#define MAX_CHAR 75

const char THE_END[] = "the end!";
void stringUpper(char*, int);

void main() {
    char **texto;
    int i = 0;
    int j;
    texto = NULL;
    for( ; ; ) {
        texto = (char**)realloc(texto,(i+1)*sizeof(char*));
        texto[i] = (char*)malloc(MAX_CHAR*sizeof(char));
        fgets(texto[i],MAX_CHAR,stdin);
        texto[strlen(texto[i]-1)] = '%pre%'; // troca o '\n' (úlimo dígito da string) pelo terminador nulo
        if(strcmp(THE_END,texto[i]) == 0) break;
        i++;
    }

    for(j = 0; j < i; i++) {
        free(texto[j]);
    }

    free(texto);






}

void stringUpper(char *s, int tam) {
    int i = 0;
    for(i = 0; i < tam; i++) {
        s[i] = toupper(s[i]);
    }
}
'; // troca o '\n' (úlimo dígito da string) pelo terminador nulo if(strcmp(THE_END,texto[i]) == 0) break; i++; } for(j = 0; j < i; i++) { free(texto[j]); } free(texto); } void stringUpper(char *s, int tam) { int i = 0; for(i = 0; i < tam; i++) { s[i] = toupper(s[i]); } }
    
asked by anonymous 12.11.2016 / 20:35

3 answers

1

The friend Emoon found the first part of the problem in his answer, that fgets puts a \n at the end of the string read and that he needs to give free in each of the strings allocated.

As for this \n , the solution would be to replace it with \n and that's what you did. Or rather, that's what you tried to do! !

You've made this code to replace j++ with i++ :

texto[strlen(texto[i]-1)] = '
texto[i][strlen(texto[i]) - 1] = '
for(j = 0; j < i; i++)
';
';

This is wrong. The correct would be this:

texto[strlen(texto[i]-1)] = '
texto[i][strlen(texto[i]) - 1] = '
for(j = 0; j < i; i++)
';
';

Then, when dealing with strings, see your loop:

%pre%

This loop is wrong! It was to be %code% instead of %code% .

Fixing these issues, the code worked for me as expected.

    
15.11.2016 / 20:29
1

There are some problems with your program. strcmp , in case of equality, returns 0, not the other way around. In addition, fgets has the drawback of not deleting \n at the end of the entry. You can fix this by replacing it with a free or by putting it in the comparison. A possible solution would then be:

if (strcmp("the end!\n", texto[i]) == 0) break;

Also, do not forget that you need to give texto not only at the realloc address, but on each of the lines as well.

I was not able to re-create your SegFault, but the problem may be in this texto which is called when the malloc pointer initially contains garbage. Try to make a %code% to it before.

    
12.11.2016 / 20:53
0

I finished the code. He is like this now:

 #include <stdio.h> 
 #include <stdlib.h>
 #include <ctype.h>
 #include <string.h>
 #define MAX_CHAR 75

const char THE_END[] = "the end!";
void stringUpper(char*, int);
void clearBuffer();
void textUpper(char**,int);
void printText(char**,int);
char **desalocaTexto(char**,int);

void main() {
    char **texto;
    int i = 0;
    int j;
    texto = NULL;
    for( ; ; ) {
        texto = (char**)realloc(texto,(i+1)*sizeof(char*));
        texto[i] = (char*)malloc(MAX_CHAR*sizeof(char));
        //clearBuffer();
        fgets(texto[i],MAX_CHAR,stdin);
        texto[i][strlen(texto[i]) - 1] = '
 #include <stdio.h> 
 #include <stdlib.h>
 #include <ctype.h>
 #include <string.h>
 #define MAX_CHAR 75

const char THE_END[] = "the end!";
void stringUpper(char*, int);
void clearBuffer();
void textUpper(char**,int);
void printText(char**,int);
char **desalocaTexto(char**,int);

void main() {
    char **texto;
    int i = 0;
    int j;
    texto = NULL;
    for( ; ; ) {
        texto = (char**)realloc(texto,(i+1)*sizeof(char*));
        texto[i] = (char*)malloc(MAX_CHAR*sizeof(char));
        //clearBuffer();
        fgets(texto[i],MAX_CHAR,stdin);
        texto[i][strlen(texto[i]) - 1] = '%pre%';// troca o '\n' (úlimo dígito da string) pelo terminador nulo

        if(strcmp(THE_END,texto[i]) == 0) break;
        i++;
    }

    textUpper(texto, i);
    printText(texto,i);

    texto = desalocaTexto(texto,i);
}

void stringUpper(char *s, int tam) {
    int i = 0;
    for(i = 0; i < tam; i++) {
        s[i] = toupper(s[i]);
    }
}


void clearBuffer() {
    char c;
    while((c = getchar()) != '\n' && c != EOF);

}

void textUpper(char **texto ,int tam) {
    int i;
    for(i = 0; i < tam; i++) {
        stringUpper(texto[i],MAX_CHAR);
    }
}

void printText(char **texto,int tam) {
    int i;
    for(i = 0; i < tam; i++) {
        printf("%s\n",texto[i]);
    }

}

char **desalocaTexto(char **t ,int linhas) {
    int j;
    for(j = 0; j < linhas; j++) {
        free(t[j]);
    }

    free(t);
    return NULL;
}
';// troca o '\n' (úlimo dígito da string) pelo terminador nulo if(strcmp(THE_END,texto[i]) == 0) break; i++; } textUpper(texto, i); printText(texto,i); texto = desalocaTexto(texto,i); } void stringUpper(char *s, int tam) { int i = 0; for(i = 0; i < tam; i++) { s[i] = toupper(s[i]); } } void clearBuffer() { char c; while((c = getchar()) != '\n' && c != EOF); } void textUpper(char **texto ,int tam) { int i; for(i = 0; i < tam; i++) { stringUpper(texto[i],MAX_CHAR); } } void printText(char **texto,int tam) { int i; for(i = 0; i < tam; i++) { printf("%s\n",texto[i]); } } char **desalocaTexto(char **t ,int linhas) { int j; for(j = 0; j < linhas; j++) { free(t[j]); } free(t); return NULL; }

Personally, considering I'm a beginner, is the code well done in your opinion? How much time on average can I become a professional in C?

    
13.11.2016 / 12:31