Discussion in "General help Guidance and Discussion" started by    DavesGarage    Nov 7, 2009.
Sat Nov 07 2009, 02:48 AM
#1
At the behest of our website owner, I decided to open a forum thread on software programming techniques. I have been writing software for about 25 years now, and I find I am constantly learning new and innovative ways to get into trouble with my code...

I thought this could be a place where we discuss specific topics - this particular thread is dedicated to the use of GOTO, which is defined within K&R's "The C Programming Language" book as follows:

3.8 Goto and labels
C provides the infinitely-abusable goto statement, and labels to branch to. Formally, the goto statement is never necessary, and in practice it is almost always easy to write code without it. We have not used goto in this book. 
Nevertheless, there are a few situations where gotos may find a place. The most common is to abandon processing in some deeply nested structure, such as breaking out of two or more loops at once. The break statement cannot be used directly since it only exits from the innermost loop. Thus: 

       for ( ... )
           for ( ... ) {
               ...
               if (disaster)
                   goto error;
           }
       ...
   error:
       /* clean up the mess */
This organization is handy if the error-handling code is non-trivial, and if errors can occur in several places. 
A label has the same form as a variable name, and is followed by a colon. It can be attached to any statement in the same function as the goto. The scope of a label is the entire function. 
As another example, consider the problem of determining whether two arrays a and b have an element in common. One possibility is 

       for (i = 0; i < n; i++)
           for (j = 0; j < m; j++)
               if (a[i] == b[j])
                   goto found;
       /* didn't find any common element */
       ...
   found:
       /* got one: a[i] == b[j] */
       ...
Code involving a goto can always be written without one, though perhaps at the price of some repeated tests or an extra variable. For example, the array search becomes 

   found = 0;
   for (i = 0; i < n && !found; i++)
       for (j = 0; j < m && !found; j++)
           if (a[i] == b[j])
               found = 1;
   if (found)
       /* got one: a[i-1] == b[j-1] */
       ...
   else
       /* didn't find any common element */
       ...
With a few exceptions like those cited here, code that relies on goto statements is generally harder to understand and to maintain than code without gotos. Although we are not dogmatic about the matter, it does seem that goto statements should be used rarely, if at all. 



Using GOTO in your software is a widely debated issue. What are your thoughts?

Sat Nov 07 2009, 03:06 PM
#2
I believe if you know what you are doing then its not a problem using goto statement. I sometimes really feel difficult to understand why people abuse so much?

If goto can make you life simple then why not use it? I am not a master in programming but i feel wherever you can use goto just use it.

I have seen uIP 0.9 implementation by Adam Dunkels, he made a heavy use of goto statement just to make things simpler, he could also use switch case statements but he decided to use goto.

Can anyone points to problem that can arise using goto?
Sat Nov 14 2009, 04:17 AM
#3
Searching the web, I ran across a very good description of when to use goto...

The author wrote:

When To Use Goto When Programming in C
Although the use of goto is almost always bad programming practice (surely you can find a better way of doing XYZ), there are times when it really isn't a bad choice. Some might even argue that, when it is useful, it's the best choice.

Most of what I have to say about goto really only applies to C. If you're using C++, there's no sound reason to use goto in place of exceptions. In C, however, you don't have the power of an exception handling mechanism, so if you want to separate out error handling from the rest of your program logic, and you want to avoid rewriting clean up code multiple times throughout your code, then goto can be a good choice.

What do I mean? You might have some code that looks like this:

int big_function()
{
    /* do some work */
    if([error])
    {
        /* clean up*/
        return [error];
    }
    /* do some more work */
    if([error])
    {
        /* clean up*/
        return [error];
    }
    /* do some more work */
    if([error])
    {
        /* clean up*/
        return [error];
    }
    /* do some more work */
    if([error])
    {
        /* clean up*/
        return [error];
    }
    /* clean up*/
    return [success];
}

This is fine until you realize that you need to change your cleanup code. Then you have to go through and make 4 changes. Now, you might decide that you can just encapsulate all of the cleanup into a single function; that's not a bad idea. But it does mean that you'll need to be careful with pointers -- if you plan to free a pointer in your cleanup function, there's no way to set it to then point to NULL unless you pass in a pointer to a pointer. In a lot of cases, you won't be using that pointer again anyway, so that may not be a major concern. On the other hand, if you add in a new pointer, file handle, or other thing that needs cleanup, then you'll need to change your cleanup function again; and then you'll need to change the arguments to that function.

In some cases, this might be acceptable -- but if you're making a lot of changes to your code, adding in new variables, etc. -- it may not be worth the time or the extra lines of code to make that function call.

Instead, since you know that you're going to be executing only one piece of code and then returning from the function, you might as well use a goto to jump to the very end of the function, where you have your cleanup code.

Goto is a pretty simple keyword: you just need to include a "label" placed above the target location (followed by a colon), and then direct the program to go to the label. Note that this only works within the same function; you can't just enter one function from another.

goto label;
/* Code
...
*/
label:

Now, using this, if we want to handle all our errors in one place, we'll need to add in a variable to track the return value of our function so we can return it:

int big_function()
{
    int ret_val = [success];
    /* do some work */
    if([error])
    {
        ret_val = [error];
        goto end;
    }
    /* do some more work */
    if([error])
    {
        ret_val = [error];
        goto end;
    }
    /* do some more work */
    if([error])
    {
        ret_val = [error];
        goto end;
    }
    /* do some more work */
    if([error])
    {
        ret_val = [error];
        goto end;
    }
end:
    /* clean up*/
    return ret_val;
}

The benefit here is that your code following end has access to everything it will need to perform cleanup, and you've managed to reduce the number of change points considerably. Another benefit is that you've gone from having multiple exit points for your function to just one; there's no chance you'll accidentally return from the function without cleaning up.

Moreover, since goto is only being used to jump to a single point, it's not as though you're creating a mass of spaghetti code jumping back and forth in an attempt to simulate function calls. Rather, goto actually helps write more structured code.

There is one thing to be aware of: while your cleanup code should be able to free all of the memory you use, there may be times when you actually want to free that memory yourself and possibly reallocate it later. In these cases, if you do call free on a ptr and then have an if([error]) between that call to free and the subsequent call to malloc, you should definitely set the pointer to point to NULL! This will prevent your jumping to the cleanup code and then calling free on that pointer a second time, which can result in a security hole (the "double free" problem).

Goto should always be used sparingly, and as a last resort -- but there is a time and a place for it. The question should be not "do you have to use it" but "is it the best choice" to use it.



The website is here: http://www.cprogramming.com/tutorial/goto.html


[ Edited Sat Nov 14 2009, 04:19 AM ]
 ajay_bhargav like this.
Sat Nov 14 2009, 11:08 AM
#4
That explains a lot
I really like this method of spreading and gathering good knowledge
Mon Nov 16 2009, 03:19 PM
#5


I believe if you know what you are doing then its not a problem using goto statement. I sometimes really feel difficult to understand why people abuse so much?

If goto can make you life simple then why not use it? I am not a master in programming but i feel wherever you can use goto just use it.

I have seen uIP 0.9 implementation by Adam Dunkels, he made a heavy use of goto statement just to make things simpler, he could also use switch case statements but he decided to use goto.

Can anyone points to problem that can arise using goto?

Ajay Bhargav



The goto statement has run me into alot of problems when I started coding in embedded C. I sometimes find that using goto before closing a while(1) loop can cause 18F series PIC chips to crash. Goto can be used to make things much simpler but I personally think it is down to the programmer. While working on projects in different teams, I find that some programmers code in a style that is similar to the language they started out with.

I've noticed one guy who started out coding in assembly, his C code looks very similar in structure!
Mon Nov 16 2009, 07:39 PM
#6
banked memories may cause a problem with goto i believe. 8051 is fairly simple architecture where you can jump from anywhere in range of 64K. So architectures also play big role on how you code.

but most of time Its on user how he use it or code it.
Mon Nov 16 2009, 09:52 PM
#7


The goto statement has run me into alot of problems when I started coding in embedded C. I sometimes find that using goto before closing a while(1) loop can cause 18F series PIC chips to crash.

Retellect


I suspect that the compiler may be careless as to how it codes while loops.
Useful warning though.


[ Edited Mon Nov 16 2009, 09:53 PM ]

Get Social

Information

Powered by e107 Forum System

Conversation

Sun Sep 27 2020, 04:55 PM
Aleida
side effects levitra vs cialis http://cialistores.com - buy cialis online cheap cialis commercial models does generic cialis work forum canadian cialis buy cialis nz
Sun Sep 27 2020, 03:36 PM
Waldo Avalos
MORE INFO=> https://bit.ly/2ZsKQsz
Sun Sep 27 2020, 08:38 AM
Bryanslj
only
Sun Sep 27 2020, 07:06 AM
Edgar Sharrow
Want no charge advertising for your website? Check out: http://bit.ly/post-free-ads-here
Sat Sep 26 2020, 07:27 PM
Ronald Withrow
This software will help to increase traffic to website to hundreds, thousands times.
Thu Jun 11 2020, 06:27 AM
anudee
sir could please send the code for I2C and wifi interfacing with 8051
scena
Tue May 19 2020, 10:29 PM
Does anyone have microcontroller programming software for STC15F104W (core 8051, 4 k, 128 byte, 6 I/O pin, UART ... DIL8), that works?
Sat May 02 2020, 07:38 PM
Tamu Gurung
Hi I am looking for a assembly language program for a digital decimal counter. Time counts max limit of 2 mins starting from 2.00 mins and ending at 0.00. time is to be displayed on 4 7-segment LED displays. Edsim51 simulator to be used. Thanks
Wed Mar 25 2020, 01:39 PM
Tajammul
Sir kindly send the code file i2c for 8051
ExperimenterUK
Fri Mar 13 2020, 10:36 PM
@ Rohitnani,ABEBE..which project ?

Downloads

Comments

Mirza123
Thu Jun 25 2020, 03:46 PM
eunicelove124
Mon Jun 22 2020, 03:03 PM
cerouno
Tue Jun 16 2020, 05:10 PM
Marce
Sat Jun 13 2020, 09:43 PM
Davidthils
Thu May 21 2020, 12:44 PM
Jakeror
Thu May 21 2020, 01:28 AM
motorCar
Wed May 20 2020, 07:05 PM
Vordrync
Wed May 20 2020, 11:52 AM

Online

Guests: 67, Members: 0 ...

most ever online: 182184
(Members: , Guests: 182184) on 06 Aug 2010: 05:37 AM

Members: 38215
Newest member: Mirza123