Segmentation fault... - Programmers Heaven

Howdy, Stranger!

It looks like you're new here. If you want to get involved, click one of these buttons!

Categories

Welcome to the new platform of Programmer's Heaven! We apologize for the inconvenience caused, if you visited us from a broken link of the previous version. The main reason to move to a new platform is to provide more effective and collaborative experience to you all. Please feel free to experience the new platform and use its exciting features. Contact us for any issue that you need to get clarified. We are more than happy to help you.

Segmentation fault...

IDKIDK Posts: 1,784Member
I have a segmentation fault again...
It's a little wierd...
This is some piece of code I'm working on:

[code]
#include
#include

char look; // { Lookahead Character }
FILE *ifile; // input stream
FILE *ofile; // output stream
char **KWlist;

//{--------------------------------------------------------------}
//{ Read New Character From Input Stream }

void GetChar(){
look = fgetc(ifile);
}

//{--------------------------------------------------------------}
//{ Report Error}

void Abort(char* s){
printf("
Error %s.", s);
abort();
}

void Expected(char* s){
printf("Error: %s Expected
", s);
abort();
}

//{--------------------------------------------------------------}
//{ Match a Specific Input Character }

void match(char x){
if(look == x)
GetChar();
else{
char* c = "
";
c[0] = x;
Expected(c);
}
}

//{--------------------------------------------------------------}
//{ Recognicion funcs }
char upcase(char c){
if((c >= 'a') & (c <= 'z'))
c += 'A' - 'a';
return c;
}

int IsAlpha(char c){
c = upcase(c);
return ((c >= 'A') & (c <= 'Z'));
}

int IsDigit(char c){
return ((c >= '0') & (c <= '9'));
}

int IsOp(char c){
return (c == '+') | (c == '-') | (c == '*') | (c == '/') | (c == '<') | (c == '>') | (c == ':') | (c == '=') | (c == '!');
}

int IsAlNum(char c){
return IsAlpha(c) | IsDigit(c);
}

int IsWhite(char c){
return (c == ' ') | (c == ' ') | (c == '
');
}


//{--------------------------------------------------------------}
//{ Get an Identifier }

void skipWhite(){
while(IsWhite(look))
GetChar();
}

void Fin(){
if(look == '
') GetChar();
if(look == '
') GetChar();
}

int Lookup(char ** list, char* s, int n){
//++n;
while(n--)
if(list[n][0] == s[0])
if(strcmp(list[n], s) == 0)
return 1;
return 0;
}


char* getName(){
char *c, *p;
if ((c=(char *) malloc(9))==NULL) return NULL;
p = c;
if(!IsAlpha(upcase(look))) Expected("Name");

while(IsAlNum(look)){
*p = upcase(look);
++p;
GetChar();
}
*p = 0;
skipWhite();
return c;
}

char* getNum(){
char *c, *p;
if ((c=(char *) malloc(17))==NULL) return NULL;
p = c;
if(!IsDigit(look)) Expected("Integer");
while(IsDigit(look)){
*p = upcase(look);
++p;
GetChar();
}
*p = 0;
skipWhite();
return c;
}

char* getOp(){
char *c, *p;
if ((c=(char *) malloc(4))==NULL) return NULL;
p = c;
if(!IsOp(look)) Expected("Integer");
while(IsOp(look)){
*p = upcase(look);
++p;
GetChar();
}
*p = 0;
skipWhite();
return c;
}

char* scan(){ //remember to free!!
skipWhite();
char *c;
while(look == '
')
Fin();

if(IsAlpha(look))
c = getName();
else if(IsDigit(look))
c = getNum();
else if(IsOp(look))
c = getOp();
else {
if ((c=(char *) malloc(2))==NULL) return NULL;
*c = look;
++c;
*c = 0;
--c;
GetChar();
}
return c;
}


//{--------------------------------------------------------------}
//{ Initialize }

void init(){
ifile = stdin; //fopen("test.q", "r");
ofile = stdout;
GetChar();

if ((KWlist=(char **) malloc(6))==NULL) Abort("malloc error");
KWlist[0] = "IF";
KWlist[1] = "ELSE";
KWlist[2] = "END";
KWlist[3] = "ENDIF";
KWlist[4] = "1234";
}


//{--------------------------------------------------------------}
//{ Main Program }

int main(){
init();

char* c;
//scanf("%s",c); //this line works
c = scan(); //but this doesn't
printf("%s
", c);
printf("%d
", Lookup(KWlist, c, 4)); //if I put a three here it works but not if it's a four and scan() is used.

free(c);
free(KWlist);

return 0;
}
[/code]

Read the comments in main to understand the prob...
The problem should be with scan() but I can't see why.

It only occures when the third parameter in Lookup is 4 and scan() is used. When the parameters is lower, or scanf() is used it works.

Happy coding wishes
the one and only
[b]Niklas Ulvinge[/b] [white]aka [b]IDK[/b][/white]
«134

Comments

  • gustavosserragustavosserra Posts: 201Member
    You are not using pointers correctly. You declared char*, so you must allocate memory to it before use. Or not declare it as a pointer at all.
    [code]
    char* c = new char; //c++
    char* c = (char*)malloc(sizeof(char) * 1); //c
    char c; //another option
    [/code]

    Hope that helps,
    Mortissus

    : I have a segmentation fault again...
    : It's a little wierd...
    : This is some piece of code I'm working on:
    :
    : [code]
    : #include
    : #include
    :
    : char look; // { Lookahead Character }
    : FILE *ifile; // input stream
    : FILE *ofile; // output stream
    : char **KWlist;
    :
    : //{--------------------------------------------------------------}
    : //{ Read New Character From Input Stream }
    :
    : void GetChar(){
    : look = fgetc(ifile);
    : }
    :
    : //{--------------------------------------------------------------}
    : //{ Report Error}
    :
    : void Abort(char* s){
    : printf("
    Error %s.", s);
    : abort();
    : }
    :
    : void Expected(char* s){
    : printf("Error: %s Expected
    ", s);
    : abort();
    : }
    :
    : //{--------------------------------------------------------------}
    : //{ Match a Specific Input Character }
    :
    : void match(char x){
    : if(look == x)
    : GetChar();
    : else{
    : char* c = "
    ";
    : c[0] = x;
    : Expected(c);
    : }
    : }
    :
    : //{--------------------------------------------------------------}
    : //{ Recognicion funcs }
    : char upcase(char c){
    : if((c >= 'a') & (c <= 'z'))
    : c += 'A' - 'a';
    : return c;
    : }
    :
    : int IsAlpha(char c){
    : c = upcase(c);
    : return ((c >= 'A') & (c <= 'Z'));
    : }
    :
    : int IsDigit(char c){
    : return ((c >= '0') & (c <= '9'));
    : }
    :
    : int IsOp(char c){
    : return (c == '+') | (c == '-') | (c == '*') | (c == '/') | (c == '<') | (c == '>') | (c == ':') | (c == '=') | (c == '!');
    : }
    :
    : int IsAlNum(char c){
    : return IsAlpha(c) | IsDigit(c);
    : }
    :
    : int IsWhite(char c){
    : return (c == ' ') | (c == ' ') | (c == '
    ');
    : }
    :
    :
    : //{--------------------------------------------------------------}
    : //{ Get an Identifier }
    :
    : void skipWhite(){
    : while(IsWhite(look))
    : GetChar();
    : }
    :
    : void Fin(){
    : if(look == '
    ') GetChar();
    : if(look == '
    ') GetChar();
    : }
    :
    : int Lookup(char ** list, char* s, int n){
    : //++n;
    : while(n--)
    : if(list[n][0] == s[0])
    : if(strcmp(list[n], s) == 0)
    : return 1;
    : return 0;
    : }
    :
    :
    : char* getName(){
    : char *c, *p;
    : if ((c=(char *) malloc(9))==NULL) return NULL;
    : p = c;
    : if(!IsAlpha(upcase(look))) Expected("Name");
    :
    : while(IsAlNum(look)){
    : *p = upcase(look);
    : ++p;
    : GetChar();
    : }
    : *p = 0;
    : skipWhite();
    : return c;
    : }
    :
    : char* getNum(){
    : char *c, *p;
    : if ((c=(char *) malloc(17))==NULL) return NULL;
    : p = c;
    : if(!IsDigit(look)) Expected("Integer");
    : while(IsDigit(look)){
    : *p = upcase(look);
    : ++p;
    : GetChar();
    : }
    : *p = 0;
    : skipWhite();
    : return c;
    : }
    :
    : char* getOp(){
    : char *c, *p;
    : if ((c=(char *) malloc(4))==NULL) return NULL;
    : p = c;
    : if(!IsOp(look)) Expected("Integer");
    : while(IsOp(look)){
    : *p = upcase(look);
    : ++p;
    : GetChar();
    : }
    : *p = 0;
    : skipWhite();
    : return c;
    : }
    :
    : char* scan(){ //remember to free!!
    : skipWhite();
    : char *c;
    : while(look == '
    ')
    : Fin();
    :
    : if(IsAlpha(look))
    : c = getName();
    : else if(IsDigit(look))
    : c = getNum();
    : else if(IsOp(look))
    : c = getOp();
    : else {
    : if ((c=(char *) malloc(2))==NULL) return NULL;
    : *c = look;
    : ++c;
    : *c = 0;
    : --c;
    : GetChar();
    : }
    : return c;
    : }
    :
    :
    : //{--------------------------------------------------------------}
    : //{ Initialize }
    :
    : void init(){
    : ifile = stdin; //fopen("test.q", "r");
    : ofile = stdout;
    : GetChar();
    :
    : if ((KWlist=(char **) malloc(6))==NULL) Abort("malloc error");
    : KWlist[0] = "IF";
    : KWlist[1] = "ELSE";
    : KWlist[2] = "END";
    : KWlist[3] = "ENDIF";
    : KWlist[4] = "1234";
    : }
    :
    :
    : //{--------------------------------------------------------------}
    : //{ Main Program }
    :
    : int main(){
    : init();
    :
    : char* c;
    : //scanf("%s",c); //this line works
    : c = scan(); //but this doesn't
    : printf("%s
    ", c);
    : printf("%d
    ", Lookup(KWlist, c, 4)); //if I put a three here it works but not if it's a four and scan() is used.
    :
    : free(c);
    : free(KWlist);
    :
    : return 0;
    : }
    : [/code]
    :
    : Read the comments in main to understand the prob...
    : The problem should be with scan() but I can't see why.
    :
    : It only occures when the third parameter in Lookup is 4 and scan() is used. When the parameters is lower, or scanf() is used it works.
    :
    : Happy coding wishes
    : the one and only
    : [b]Niklas Ulvinge[/b] [white]aka [b]IDK[/b][/white]
    :

  • stephlstephl Posts: 422Member
    Some mistakes I have noticed.

    [code]
    #include
    #include

    char look; // { Lookahead Character }
    FILE *ifile; // input stream
    FILE *ofile; // output stream
    char **KWlist;

    //{--------------------------------------------------------------}
    //{ Read New Character From Input Stream }

    void GetChar(){
    look = fgetc(ifile);
    }

    //{--------------------------------------------------------------}
    //{ Report Error}

    void Abort(char* s){
    printf("
    Error %s.", s);
    abort();
    }

    void Expected(char* s){
    printf("Error: %s Expected
    ", s);
    abort();
    }

    //{--------------------------------------------------------------}
    //{ Match a Specific Input Character }

    void match(char x){
    if(look == x)
    GetChar();
    else{
    char* c = "
    ";
    [blue]/*
    You should not declare c this way, because the string "
    " is then considered
    as a string constant and should not be modified. Because you want to modify it
    on the next line, declare c this way instead:

    char c[3]="
    ";

    This line initializes the array whose elements can be modified later.
    */[/blue]
    c[0] = x;
    Expected(c);
    }
    }

    //{--------------------------------------------------------------}
    //{ Recognicion funcs }
    char upcase(char c){
    if((c >= 'a') & (c <= 'z'))
    [blue]/*
    Here it works but you should use && instead because what you want to perform
    is a logical AND (boolean), not a bitwise AND
    */[/blue]
    c += 'A' - 'a';
    return c;
    }

    int IsAlpha(char c){
    c = upcase(c);
    return ((c >= 'A') & (c <= 'Z'));
    [blue]/*Same thing than above*/[/blue]
    }

    int IsDigit(char c){
    return ((c >= '0') & (c <= '9'));
    [blue]/*Same thing than above*/[/blue]
    }

    int IsOp(char c){
    return (c == '+') | (c == '-') | (c == '*') | (c == '/') | (c == '<') | (c == '>') | (c == ':') | (c == '=') | (c == '!');
    [blue]/*It works, but I think that it is preferable to use || to be clearer*/[/blue]
    }

    int IsAlNum(char c){
    return IsAlpha(c) | IsDigit(c);
    [blue]/* || */[/blue]
    }

    int IsWhite(char c){
    return (c == ' ') | (c == ' ') | (c == '
    ');
    [blue]/* || */[/blue]
    }


    //{--------------------------------------------------------------}
    //{ Get an Identifier }

    void skipWhite(){
    while(IsWhite(look))
    GetChar();
    }

    void Fin(){
    if(look == '
    ') GetChar();
    if(look == '
    ') GetChar();
    }

    int Lookup(char ** list, char* s, int n){
    //++n;
    while(n--)
    if(list[n][0] == s[0])
    if(strcmp(list[n], s) == 0)
    return 1;
    return 0;
    }


    char* getName(){
    char *c, *p;
    if ((c=(char *) malloc(9))==NULL) return NULL;
    p = c;
    if(!IsAlpha(upcase(look))) Expected("Name");

    while(IsAlNum(look)){
    *p = upcase(look);
    ++p;
    GetChar();
    }
    *p = 0;
    skipWhite();
    return c;
    }

    char* getNum(){
    char *c, *p;
    if ((c=(char *) malloc(17))==NULL) return NULL;
    p = c;
    if(!IsDigit(look)) Expected("Integer");
    while(IsDigit(look)){
    *p = upcase(look);
    ++p;
    GetChar();
    }
    *p = 0;
    skipWhite();
    return c;
    }

    char* getOp(){
    char *c, *p;
    if ((c=(char *) malloc(4))==NULL) return NULL;
    p = c;
    if(!IsOp(look)) Expected("Integer");
    while(IsOp(look)){
    *p = upcase(look);
    ++p;
    GetChar();
    }
    *p = 0;
    skipWhite();
    return c;
    }

    char* scan(){ //remember to free!!
    skipWhite();
    char *c;
    while(look == '
    ')
    Fin();

    if(IsAlpha(look))
    c = getName();
    else if(IsDigit(look))
    c = getNum();
    else if(IsOp(look))
    c = getOp();
    else {
    if ((c=(char *) malloc(2))==NULL) return NULL;
    *c = look;
    ++c;
    *c = 0;
    --c;
    GetChar();
    }
    return c;
    }


    //{--------------------------------------------------------------}
    //{ Initialize }

    void init(){
    ifile = stdin; //fopen("test.q", "r");
    ofile = stdout;
    GetChar();

    if ((KWlist=(char **) malloc(6))==NULL) Abort("malloc error");
    [blue]/*
    Here you only allocate space for 6 characters, which is not enough to store the 5
    following strings
    */[/blue]
    KWlist[0] = "IF";
    KWlist[1] = "ELSE";
    KWlist[2] = "END";
    KWlist[3] = "ENDIF";
    KWlist[4] = "1234";
    }


    //{--------------------------------------------------------------}
    //{ Main Program }

    int main(){
    init();

    char* c;
    //scanf("%s",c); //this line works
    [blue]/*
    It's amazing the line with scanf works. Normally, you should allocate space to store
    the chars before calling scanf
    */[/blue]
    c = scan(); //but this doesn't
    printf("%s
    ", c);
    printf("%d
    ", Lookup(KWlist, c, 4)); //if I put a three here it works but not if it's a four and scan() is used.

    free(c);
    free(KWlist);

    return 0;
    }
    [/code]

    Steph
  • IDKIDK Posts: 1,784Member
    : You are not using pointers correctly. You declared char*, so you must allocate memory to it before use. Or not declare it as a pointer at all.
    : [code]
    : char* c = new char; //c++
    : char* c = (char*)malloc(sizeof(char) * 1); //c
    : char c; //another option
    : [/code]
    :
    : Hope that helps,
    : Mortissus
    :

    This is C, it doesn't have new
  • IDKIDK Posts: 1,784Member
    [code]
    : //{--------------------------------------------------------------}
    : //{ Initialize }
    :
    : void init(){
    : ifile = stdin; //fopen("test.q", "r");
    : ofile = stdout;
    : GetChar();
    :
    : if ((KWlist=(char **) malloc(6))==NULL) Abort("malloc error");
    : [blue]/*
    : Here you only allocate space for 6 characters, which is not enough to store the 5
    : following strings
    : */[/blue]
    : KWlist[0] = "IF";
    : KWlist[1] = "ELSE";
    : KWlist[2] = "END";
    : KWlist[3] = "ENDIF";
    : KWlist[4] = "1234";
    : }
    :
    [/code]
    I thought I was declaring a an array of pointers to strings.
    Doesn't "Hello" a 'return' a pointer to char.
    Then I move that pointer to an array of 6 bytes.
    The "Hello" is declared on the heap.
    [code]
    :
    : //{--------------------------------------------------------------}
    : //{ Main Program }
    :
    : int main(){
    : init();
    :
    : char* c;
    : //scanf("%s",c); //this line works
    : [blue]/*
    : It's amazing the line with scanf works. Normally, you should allocate space to store
    : the chars before calling scanf
    : */[/blue]
    : c = scan(); //but this doesn't
    : printf("%s
    ", c);
    : printf("%d
    ", Lookup(KWlist, c, 4)); //if I put a three here it works but not if it's a four and scan() is used.
    :
    : free(c);
    : free(KWlist);
    :
    : return 0;
    : }
    : [/code]
  • stephlstephl Posts: 422Member
    : [code]
    : : //{--------------------------------------------------------------}
    : : //{ Initialize }
    : :
    : : void init(){
    : : ifile = stdin; //fopen("test.q", "r");
    : : ofile = stdout;
    : : GetChar();
    : :
    : : if ((KWlist=(char **) malloc(6))==NULL) Abort("malloc error");
    : : [blue]/*
    : : Here you only allocate space for 6 characters, which is not enough to store the 5
    : : following strings
    : : */[/blue]
    : : KWlist[0] = "IF";
    : : KWlist[1] = "ELSE";
    : : KWlist[2] = "END";
    : : KWlist[3] = "ENDIF";
    : : KWlist[4] = "1234";
    : : }
    : :
    : [/code]
    : I thought I was declaring a an array of pointers to strings.
    : Doesn't "Hello" a 'return' a pointer to char.
    : Then I move that pointer to an array of 6 bytes.
    : The "Hello" is declared on the heap.
    : [code]
    : :
    : : //{--------------------------------------------------------------}
    : : //{ Main Program }
    : :
    : : int main(){
    : : init();
    : :
    : : char* c;
    : : //scanf("%s",c); //this line works
    : : [blue]/*
    : : It's amazing the line with scanf works. Normally, you should allocate space to store
    : : the chars before calling scanf
    : : */[/blue]
    : : c = scan(); //but this doesn't
    : : printf("%s
    ", c);
    : : printf("%d
    ", Lookup(KWlist, c, 4)); //if I put a three here it works but not if it's a four and scan() is used.
    : :
    : : free(c);
    : : free(KWlist);
    : :
    : : return 0;
    : : }
    : : [/code]
    :
    Yes, sorry, you're right. But remember that if you assign these string constants to the pointers in KWlist, you should not modify these strings later.
    I am working on your code now and I'll try to post something later if I have time.

    Steph
  • IDKIDK Posts: 1,784Member
    : : [code]
    : : : //{--------------------------------------------------------------}
    : : : //{ Initialize }
    : : :
    : : : void init(){
    : : : ifile = stdin; //fopen("test.q", "r");
    : : : ofile = stdout;
    : : : GetChar();
    : : :
    : : : if ((KWlist=(char **) malloc(6))==NULL) Abort("malloc error");
    : : : [blue]/*
    : : : Here you only allocate space for 6 characters, which is not enough to store the 5
    : : : following strings
    : : : */[/blue]
    : : : KWlist[0] = "IF";
    : : : KWlist[1] = "ELSE";
    : : : KWlist[2] = "END";
    : : : KWlist[3] = "ENDIF";
    : : : KWlist[4] = "1234";
    : : : }
    : : :
    : : [/code]
    : : I thought I was declaring a an array of pointers to strings.
    : : Doesn't "Hello" a 'return' a pointer to char.
    : : Then I move that pointer to an array of 6 bytes.
    : : The "Hello" is declared on the heap.
    : : [code]
    : : :
    : : : //{--------------------------------------------------------------}
    : : : //{ Main Program }
    : : :
    : : : int main(){
    : : : init();
    : : :
    : : : char* c;
    : : : //scanf("%s",c); //this line works
    : : : [blue]/*
    : : : It's amazing the line with scanf works. Normally, you should allocate space to store
    : : : the chars before calling scanf
    : : : */[/blue]
    : : : c = scan(); //but this doesn't
    : : : printf("%s
    ", c);
    : : : printf("%d
    ", Lookup(KWlist, c, 4)); //if I put a three here it works but not if it's a four and scan() is used.
    : : :
    : : : free(c);
    : : : free(KWlist);
    : : :
    : : : return 0;
    : : : }
    : : : [/code]
    : :
    : Yes, sorry, you're right. But remember that if you assign these string constants to the pointers in KWlist, you should not modify these strings later.
    : I am working on your code now and I'll try to post something later if I have time.
    :
    : Steph
    :
    Why can't I modify them?
    [code]
    int i = 0;
    i = 2;
    [/code]
    Here i is also declared on the heap, and I can modify it too.
  • stephlstephl Posts: 422Member
    : : : [code]
    : : : : //{--------------------------------------------------------------}
    : : : : //{ Initialize }
    : : : :
    : : : : void init(){
    : : : : ifile = stdin; //fopen("test.q", "r");
    : : : : ofile = stdout;
    : : : : GetChar();
    : : : :
    : : : : if ((KWlist=(char **) malloc(6))==NULL) Abort("malloc error");
    : : : : [blue]/*
    : : : : Here you only allocate space for 6 characters, which is not enough to store the 5
    : : : : following strings
    : : : : */[/blue]
    : : : : KWlist[0] = "IF";
    : : : : KWlist[1] = "ELSE";
    : : : : KWlist[2] = "END";
    : : : : KWlist[3] = "ENDIF";
    : : : : KWlist[4] = "1234";
    : : : : }
    : : : :
    : : : [/code]
    : : : I thought I was declaring a an array of pointers to strings.
    : : : Doesn't "Hello" a 'return' a pointer to char.
    : : : Then I move that pointer to an array of 6 bytes.
    : : : The "Hello" is declared on the heap.
    : : : [code]
    : : : :
    : : : : //{--------------------------------------------------------------}
    : : : : //{ Main Program }
    : : : :
    : : : : int main(){
    : : : : init();
    : : : :
    : : : : char* c;
    : : : : //scanf("%s",c); //this line works
    : : : : [blue]/*
    : : : : It's amazing the line with scanf works. Normally, you should allocate space to store
    : : : : the chars before calling scanf
    : : : : */[/blue]
    : : : : c = scan(); //but this doesn't
    : : : : printf("%s
    ", c);
    : : : : printf("%d
    ", Lookup(KWlist, c, 4)); //if I put a three here it works but not if it's a four and scan() is used.
    : : : :
    : : : : free(c);
    : : : : free(KWlist);
    : : : :
    : : : : return 0;
    : : : : }
    : : : : [/code]
    : : :
    : : Yes, sorry, you're right. But remember that if you assign these string constants to the pointers in KWlist, you should not modify these strings later.
    : : I am working on your code now and I'll try to post something later if I have time.
    : :
    : : Steph
    : :
    : Why can't I modify them?
    : [code]
    : int i = 0;
    : i = 2;
    : [/code]
    : Here i is also declared on the heap, and I can modify it too.
    :
    I'll give an example to make things clearer. There's a difference between these two pieces of code:
    [code]
    /*EXAMPLE 1*/
    char *p="Hello";

    /*EXAMPLE 2*/
    char p[]="Hello";

    /*EXAMPLE 3*/
    char p[6]="Hello";
    [/code]

    EX2 and EX3 are the same except the fact that in EX2 the compiler computes the size itself.
    In EX1, what is allocated on the stack is one pointer to char; the string "Hello" is not stored on the stack but in a special segment of memory where constants are stored. This address in the constant memory segment is assigned to the variable p. But the memory block pointed to by p should not be modified because it belongs to the constant segment.

    In EX2 or EX3, 6 bytes are allocated on the stack, one for each character in the string, and these bytes are assigned the corresponding chars in the string. Then p represents the address of this 6-byte-wide block of memory. Of course, these bytes can be freely modified.

    I hope I am clear in my explanations.

    Steph
  • IDKIDK Posts: 1,784Member
    : I'll give an example to make things clearer. There's a difference between these two pieces of code:
    : [code]
    : /*EXAMPLE 1*/
    : char *p="Hello";
    :
    : /*EXAMPLE 2*/
    : char p[]="Hello";
    :
    : /*EXAMPLE 3*/
    : char p[6]="Hello";
    : [/code]
    :
    : EX2 and EX3 are the same except the fact that in EX2 the compiler computes the size itself.
    : In EX1, what is allocated on the stack is one pointer to char; the string "Hello" is not stored on the stack but in a special segment of memory where constants are stored. This address in the constant memory segment is assigned to the variable p. But the memory block pointed to by p should not be modified because it belongs to the constant segment.
    :
    : In EX2 or EX3, 6 bytes are allocated on the stack, one for each character in the string, and these bytes are assigned the corresponding chars in the string. Then p represents the address of this 6-byte-wide block of memory. Of course, these bytes can be freely modified.
    :
    : I hope I am clear in my explanations.
    :
    : Steph
    :
    Thanks for clearing that up.
    I don't want to change those bytes, I only whant to compare them in the Lookup func.

    Is stack and heap the same thing? I'm confusing them...

    ...OK, now I've read a little, and here's a good description:

    Constants are declared in the constant segment, wich is located 'in the code'.
    Variables are declared on the stack, wich is located on the high end of the memmory in a stack way.
    Malloc declares data on the heap, wich is located on the low end of the memmory in a data way.
  • stephlstephl Posts: 422Member
    : : I'll give an example to make things clearer. There's a difference between these two pieces of code:
    : : [code]
    : : /*EXAMPLE 1*/
    : : char *p="Hello";
    : :
    : : /*EXAMPLE 2*/
    : : char p[]="Hello";
    : :
    : : /*EXAMPLE 3*/
    : : char p[6]="Hello";
    : : [/code]
    : :
    : : EX2 and EX3 are the same except the fact that in EX2 the compiler computes the size itself.
    : : In EX1, what is allocated on the stack is one pointer to char; the string "Hello" is not stored on the stack but in a special segment of memory where constants are stored. This address in the constant memory segment is assigned to the variable p. But the memory block pointed to by p should not be modified because it belongs to the constant segment.
    : :
    : : In EX2 or EX3, 6 bytes are allocated on the stack, one for each character in the string, and these bytes are assigned the corresponding chars in the string. Then p represents the address of this 6-byte-wide block of memory. Of course, these bytes can be freely modified.
    : :
    : : I hope I am clear in my explanations.
    : :
    : : Steph
    : :
    : Thanks for clearing that up.
    : I don't want to change those bytes, I only whant to compare them in the Lookup func.
    :
    : Is stack and heap the same thing? I'm confusing them...
    :
    : ...OK, now I've read a little, and here's a good description:
    :
    : Constants are declared in the constant segment, wich is located 'in the code'.
    : Variables are declared on the stack, wich is located on the high end of the memmory in a stack way.
    : Malloc declares data on the heap, wich is located on the low end of the memmory in a data way.
    :

    The stack is used for all the variables declared in the different functions and for parameters. The heap is used to allocate memory dynamically with malloc(), calloc()...
    I've something that compiles, but it has to be tested now.

    [code]
    #include
    #include
    #include


    char look,*KWlist[5];
    FILE *ifile,*ofile;


    void GetChar(void)
    {
    look=fgetc(ifile);
    }


    void Expected(char *s)
    {
    printf("Error: %s Expected
    ",s);
    abort();
    }


    void match(char x)
    {
    char c[3]="
    ";

    if (look==x) GetChar();
    else
    {
    c[0]=x;
    Expected(c);
    }
    }


    char upcase(char c)
    {
    if (c>='a' && c<='z') c+='A'-'a';
    return c;
    }


    int IsAlpha(char c)
    {
    c=upcase(c);
    return c>='A' && c<='Z';
    }


    int IsDigit(char c)
    {
    return c>='0' && c<='9';
    }


    int IsOp(char c)
    {
    return c=='+' || c=='-' || c=='*' || c=='/' || c=='<' || c=='>' || c==':' ||
    c=='=' || c=='!';
    }


    int IsAlNum(char c)
    {
    return IsAlpha(c) || IsDigit(c);
    }


    int IsWhite(char c)
    {
    return c==' ' || c==' ' || c=='
    ';
    }


    void skipWhite(void)
    {
    while (IsWhite(look)) GetChar();
    }


    void Fin(void)
    {
    if (look=='
    ') GetChar();
    if (look=='
    ') GetChar();
    }


    int Lookup(char **list,char *s,int n)
    {
    while (n--)
    if (!strcmp(list[n],s)) return 1;
    return 0;
    }


    char *getName(char *buf)
    {
    char *p;

    p=buf;
    if (!IsAlpha(look)) Expected("Name");
    while (IsAlNum(look))
    {
    *p=upcase(look);
    ++p;
    GetChar();
    }
    *p=0;
    skipWhite();
    return buf;
    }


    char *getNum(char *buf)
    {
    char *p;

    p=buf;
    if (!IsDigit(look)) Expected("Integer");
    while (IsDigit(look))
    {
    *p++=look;
    GetChar();
    }
    *p=0;
    skipWhite();
    return buf;
    }


    char *getOp(char *buf)
    {
    char *p;

    p=buf;
    if (!IsOp(look)) Expected("Operator");
    while (IsOp(look))
    {
    *p++=look;
    GetChar();
    }
    *p=0;
    skipWhite();
    return buf;
    }


    char *scan(char *buf)
    {
    skipWhite();
    /*while (look=='
    ') Fin();*/
    if (IsAlpha(look)) return getName(buf);
    else if (IsDigit(look)) return getNum(buf);
    else if (IsOp(look)) return getOp(buf);
    else
    {
    *buf=look;
    buf[1]=0;
    GetChar();
    return buf;
    }
    }


    void init(void)
    {
    ifile=fopen("test.txt","r");
    ofile=stdout;
    GetChar();
    KWlist[0]="IF";
    KWlist[1]="ELSE";
    KWlist[2]="END";
    KWlist[3]="ENDIF";
    KWlist[4]="1234";
    }


    int main(void)
    {
    char c[512];

    init();
    scan(c);
    fclose(ifile);
    printf("%s
    ",c);
    printf("%d
    ",Lookup(KWlist,c,5));
    return 0;
    }
    [/code]

    Steph
  • IDKIDK Posts: 1,784Member
    : : You are not using pointers correctly. You declared char*, so you must allocate memory to it before use. Or not declare it as a pointer at all.
    : : [code]
    : : char* c = new char; //c++
    : : char* c = (char*)malloc(sizeof(char) * 1); //c
    : : char c; //another option
    : : [/code]
    : :
    : : Hope that helps,
    : : Mortissus
    : :
    :
    : This is C, it doesn't have new
    :
    Opps, I didn't read your post correctly. Disregard the previus post. Sorry.

    But I am using the pointers correctly. If I'm not, wich func is wrong?
«134
Sign In or Register to comment.