Thread: Infinite Loop in Destructor...

  1. #16
    Registered User P3nGu1N's Avatar
    Join Date
    Feb 2009
    Location
    La Crescent, MN
    Posts
    23
    Quote Originally Posted by laserlight View Post
    It can be, or at least 0 == NULL is true.
    Well, I've known '\0' == NULL, but 0 == NULL? I miss programming in Java...

  2. #17
    C++ Witch laserlight's Avatar
    Join Date
    Oct 2003
    Location
    Singapore
    Posts
    28,413
    Quote Originally Posted by P3nGu1N
    Well, I've known '\0' == NULL, but 0 == NULL?
    You should deduced that transitively since '\0' == 0
    Quote Originally Posted by Bjarne Stroustrup (2000-10-14)
    I get maybe two dozen requests for help with some sort of programming or design problem every day. Most have more sense than to send me hundreds of lines of code. If they do, I ask them to find the smallest example that exhibits the problem and send me that. Mostly, they then find the error themselves. "Finding the smallest program that demonstrates the error" is a powerful debugging tool.
    Look up a C++ Reference and learn How To Ask Questions The Smart Way

  3. #18
    spurious conceit MK27's Avatar
    Join Date
    Jul 2008
    Location
    segmentation fault
    Posts
    8,300
    Quote Originally Posted by P3nGu1N View Post
    I miss programming in Java...
    Maybe it would have been easier if you had missed programming in Java

    lemme know if I was right about my last post
    C programming resources:
    GNU C Function and Macro Index -- glibc reference manual
    The C Book -- nice online learner guide
    Current ISO draft standard
    CCAN -- new CPAN like open source library repository
    3 (different) GNU debugger tutorials: #1 -- #2 -- #3
    cpwiki -- our wiki on sourceforge

  4. #19
    Registered User P3nGu1N's Avatar
    Join Date
    Feb 2009
    Location
    La Crescent, MN
    Posts
    23
    Quote Originally Posted by MK27 View Post

    It looks like you just want to iterate through the array, which would mean the while() inside the for() is superfluous. I think you should choose one or the other.
    you made a very valid point... I'm really just trying to destroy each list item in an array of lists, which means I should only have to access each Contents[i] once provided it wasn't NULL to begin with, then set my pointer p to the beginning of the list only in that senario, which could be done with an if statement. Changed code to:

    Code:
    void DestroySymTab(struct SymTab *ATable) {
    	int i;
    	struct SymEntry *p;
    	
    	for (i = 0; i < ATable->Size; i++) {
    		if(ATable->Contents[i] != NULL) {
    			p = (struct SymEntry*)ATable->Contents[i];
    			while(p->Next != NULL){
    				p = p->Next;
    			}
    			free(p);
    			p = NULL;
    		}
    	}
    	free(ATable);
    };
    and no more infinite loop. I just hope it does what I want.

  5. #20
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Quote Originally Posted by P3nGu1N View Post
    Alright, just tried this:
    Code:
    void DestroySymTab(struct SymTab *ATable) {
    	int i;
    	struct SymEntry *p;
    	
    	for (i = 0; i < ATable->Size; i++) {
    		while(ATable->Contents[i] != NULL) {
    			/*p = (struct SymEntry*)ATable->Contents[i];*/
    			printf("address (Contents[i]): %p\n",ATable->Contents[i]); fflush(stdout);
    			/*while(p->Next != NULL){
    				p = p->Next;
    			}*/
    			free(p);
    			p = NULL;
    		}
    	}
    	free(ATable);
    };
    and it keeps spitting out address (Contents[i]): ffe0b18, which is a valid memory address I'm guessing.

    If that's not how I set p to point to Contents[i], is it supposed to be *p = (struct SymEntry*)ATable->Contents[i]; instead of just p = (struct SymEntry*)ATable->Contents[i]; ?

    I'm seriously bad at this stuff, sorry if you feel like I'm wasting your time.
    This code is absolutely broken, since it's not setting p to anything sensible, and thus tries to free "garbage".

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  6. #21
    Registered User P3nGu1N's Avatar
    Join Date
    Feb 2009
    Location
    La Crescent, MN
    Posts
    23
    The sad thing is I've already created this program in Java last year. It's much easier for me to look at abstract data types like chain bucket hashing from an object oriented language.

  7. #22
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Ok, so the new code only has one slight problem: You probably want to destroy EVERY element in the linked list, not just the last one.

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  8. #23
    Registered User P3nGu1N's Avatar
    Join Date
    Feb 2009
    Location
    La Crescent, MN
    Posts
    23
    Quote Originally Posted by matsp View Post
    This code is absolutely broken, since it's not setting p to anything sensible, and thus tries to free "garbage".

    --
    Mats
    What I'm trying to do is free the contents of a list of SymEntry s in the array associated with Contents of a SymTab. If I can't use a pointer, p to point to the address location where each SymEntry is, or if I'm doing it wrong, then how do I go about it?

  9. #24
    Registered User P3nGu1N's Avatar
    Join Date
    Feb 2009
    Location
    La Crescent, MN
    Posts
    23
    Quote Originally Posted by matsp View Post
    Ok, so the new code only has one slight problem: You probably want to destroy EVERY element in the linked list, not just the last one.

    --
    Mats
    That's true, but how do I access the previous SymEntrys in the list after I destroy the last one? I was trying that outer while loop to destroy the last one, then the new last one, until the first SymEntry was freed, but that didn't work out so well for me.

  10. #25
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    It is fine to use the code you have now - the code you posted that was printing stuff, you never set p to anything.

    Your latest code looks OK, except that you only free the last pointer of the linked list - which is probably not what you want to do. Note that you will need a second pointer to hold the next pointer when you delete the current one.

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  11. #26
    spurious conceit MK27's Avatar
    Join Date
    Jul 2008
    Location
    segmentation fault
    Posts
    8,300
    I see a problem!
    Quote Originally Posted by P3nGu1N View Post
    Code:
    void DestroySymTab(struct SymTab *ATable) {
    	int i;
    	struct SymEntry *p;
    	
    	for (i = 0; i < ATable->Size; i++) {
    		if(ATable->Contents[i] != NULL) {
    			p = (struct SymEntry*)ATable->Contents[i];
    			while(p->Next != NULL){
    				p = p->Next;
    			}
    			free(p);
    			p = NULL;
    		}
    	}
    	free(ATable);
    }; <- also, what is this??!!
    What you are doing there is looping thru until p->Next==NULL, then you free p it and set it to NULL. Meaning the last node, not all of them. To do what you want to do I think you will need a tmp pointer:
    Code:
                            while(p->Next != NULL){
                                    tmp=p;
    				p = p->Next;
                                    free(tmp); tmp=NULL;     /* the previous ones */
    			}
                            free(p); p=NULL;  /* the last one */
    C programming resources:
    GNU C Function and Macro Index -- glibc reference manual
    The C Book -- nice online learner guide
    Current ISO draft standard
    CCAN -- new CPAN like open source library repository
    3 (different) GNU debugger tutorials: #1 -- #2 -- #3
    cpwiki -- our wiki on sourceforge

  12. #27
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Quote Originally Posted by P3nGu1N View Post
    That's true, but how do I access the previous SymEntrys in the list after I destroy the last one? I was trying that outer while loop to destroy the last one, then the new last one, until the first SymEntry was freed, but that didn't work out so well for me.
    Ok, so we're crossing posts. Just have another variable to hold the next pointer, and set the current to next when you have deleted current - that way, you don't have to worry about it.

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  13. #28
    and the Hat of Guessing tabstop's Avatar
    Join Date
    Nov 2007
    Posts
    14,336
    Quote Originally Posted by P3nGu1N View Post
    What I'm trying to do is free the contents of a list of SymEntry s in the array associated with Contents of a SymTab. If I can't use a pointer, p to point to the address location where each SymEntry is, or if I'm doing it wrong, then how do I go about it?
    That's exactly what you want to do -- set p to point to each location you want to free and then free it. Currently you are setting p to nothing in particular, since you commented out any and every assignment involving p. Your original mistake was thinking that if you did something like this:
    Code:
    struct whatever *p = &foo;
    p = 5;
    that foo was later 5 (i.e., you assumed that contents[i] changed because you changed p). Assigning a pointer doesn't bind a reference, it just stores that address.

    A point to remember is that you can free in any order; i.e. you can do something like:
    Code:
    while (next_to_free) is not NULL
        to_be_freed = next_to_free;
        next_to_free = next_to_free->next;
        free(to_be_freed)

  14. #29
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Or this:
    Code:
                            while(p != NULL){
                                    tmp=p;
    				p = p->Next;
                                    free(tmp); 
    			}
    I removed the "tmp = NULL" and "p = NULL", as if you us correct scopign for them, it shouldn't be necessary to set them to NULL to avoid invalid access.

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  15. #30
    spurious conceit MK27's Avatar
    Join Date
    Jul 2008
    Location
    segmentation fault
    Posts
    8,300
    Quote Originally Posted by matsp View Post
    I removed the "tmp = NULL" and "p = NULL", as if you us correct scopign for them, it shouldn't be necessary to set them to NULL to avoid invalid access.
    Yeah, I thought about that -- since you have no way of accessing the pointers now, it doesn't matter if they are NULL, and they have been freed.

    However, if you are just starting out with C I would say setting a pointer to NULL after a free() is a good habit to get into now, as in other circumstances it makes it easier to avoid a double free
    Code:
    if (ptr) free (ptr);
    C programming resources:
    GNU C Function and Macro Index -- glibc reference manual
    The C Book -- nice online learner guide
    Current ISO draft standard
    CCAN -- new CPAN like open source library repository
    3 (different) GNU debugger tutorials: #1 -- #2 -- #3
    cpwiki -- our wiki on sourceforge

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Replies: 2
    Last Post: 06-14-2009, 11:24 PM
  2. Cosine fucntion and infinite loop.
    By youareafever in forum C Programming
    Replies: 2
    Last Post: 11-07-2008, 04:45 AM
  3. Infinite Loop with GetAsyncKeyState
    By guitarist809 in forum Windows Programming
    Replies: 1
    Last Post: 04-18-2008, 12:09 PM
  4. Switch statement = infinite loop
    By Lucid003 in forum C++ Programming
    Replies: 10
    Last Post: 10-10-2005, 12:46 AM
  5. question ab an infinite loop...
    By JohnMayer in forum C Programming
    Replies: 10
    Last Post: 07-26-2002, 10:15 AM