7 years, 11 months ago.

do while function not working?

I fixed the file by editing hal_tic.h, but in my code the program jumps to if after do while loop, where it should first execute do while, I made this code on STM32L152RE WHICH WORKED fine. Please help me.

 #include "mbed.h"
#include "TextLCD.h"

TextLCD lcd(A0, A1, A2, A3, A4, A5);
DigitalOut switchengine(LED3);
DigitalIn pin_up(D3);
DigitalIn pin_down(D4);
InterruptIn pin_start(D5);
DigitalIn pin_delay(D6);
InterruptIn Pin_rain(D9);

Timer timer;
int Quarters;
void displayUpdate();
void startRun() ;
void callstart();
void timerf();
void pumpoff();
bool status ;
float delay;
int i;
int d;
int s;
int m;
float reverse;
float h;
float tim;
int begin;
void rainsense();
time_t seconds = time(NULL);
//called when 15min has passed

void pumpoff()
{
    switchengine=0;
    status = true;
    //update display
    lcd.cls();
    lcd.locate(3,0);
    lcd.printf("PUMP OFF!");
    lcd.locate(0,1);
    lcd.printf("Ran T:%1.2f Hr",i*0.25);

    pin_start.rise(&timerf);
    pin_start.fall(&callstart);
    Pin_rain.rise(&rainsense);

}
void rainsense()
{
    switchengine=0;
    lcd.cls();
    lcd.locate(0,0);
    lcd.printf("%s",ctime(&seconds));
    if(h<1.1) {
        lcd.locate(0,1);
        lcd.printf("Ran T:%1.2f Hr ",m);
    } else {
        lcd.locate(0,1);
        lcd.printf("Ran T:%1.2f Hr ",h);
    }


    while(1) {
        switchengine=0;
    }
}

void timerf()
{
    timer.start();
    begin = timer.read();
}

void callstart()
{
    int end = timer.read();
    timer.stop();
    int t = end - begin;

    if(status==true ) {
        if(t==2) {
            startRun();
            timer.reset();
        }
    }
}
void displayUpdate()
{
    //engine should be running

    if (i==0) {
        pumpoff();
    } else {
        switchengine=1;

        if(i<4) {
            m = i*2;
            s = 60;
            while(m > 0) {
                lcd.cls();
                lcd.locate(3,0);
                lcd.printf("Time= %d min ",i*2);
                lcd.locate(2,1);
                lcd.printf(" %d min %d",m-1, s);
                wait(1);
                s--;
                if(s==0) {
                    m--;
                    s = 60;
                }
                if(m==0) {
                    pumpoff();
                }

                Pin_rain.rise(&rainsense);
            }
        }

        else {
            s = 60;
            h = i*0.25;

            while(h > 0) {

                if(h<1.1) {
                    lcd.cls();
                    lcd.locate(1,0);
                    lcd.printf("Time= %1.2f Hr ",i*0.25);
                    lcd.locate(2,1);
                    lcd.printf(" %1.1f min  %d",(h-0.01)*100, s);
                } else {
                    lcd.cls();
                    lcd.locate(1,0);
                    lcd.printf("Time =%1.2f Hr ",i*0.25);
                    lcd.locate(2,1);
                    lcd.printf(" %1.2f Hr  %d",h-0.01, s);
                }
                wait(1);
                s--;
                if(s==0) {
                    h= h-0.01;
                    reverse = reverse+0.01;
                    s = 60;
                }
                if(h==0) {
                    pumpoff();
                }

                Pin_rain.rise(&rainsense);
            }

        }
    }
}

//update the display and start/stop the engine

// init and start the run
void startRun()
{

    status = false;
    lcd.cls();
    lcd.locate(3,0);
    lcd.printf("PUMP START");
    wait(1);
    lcd.cls();
    displayUpdate();
}

int main()
{

    pin_up.mode(PullDown);
    pin_down.mode(PullDown);
    pin_start.mode(PullDown);
    pin_delay.mode(PullDown);

//mkdir("/sd/mydir", 0777);
    set_time(1458986114);

    if(reverse < (i*0.25)) {

        lcd.locate(0,1);
        lcd.printf("Ran T:%1.2f Hr",reverse);
    }
    if(switchengine==0) {
        lcd.cls();
        lcd.locate(5,0);
        lcd.printf("READY");
        wait(1);
    }


    lcd.cls();
    lcd.locate(3,0);
    lcd.printf("SET TIME");

   do {


        if(pin_up==1) {
            i= i++;
            wait(0.1);
            if (i>200)
                i=200;
            tim = i;
            if(i<4) {
                lcd.cls();
                lcd.locate(1,0);
                lcd.printf("Time= %1.2f mn", tim*15);

            } else {
                lcd.cls();
                lcd.locate(1,0);
                lcd.printf("Time= %1.2f Hr", tim*15/60);

            }
        } else if(pin_down==1) {
            i=i--;
            wait(0.1);
            if( i<0)
                i=0;
            tim = i;
            if(i<4) {
                lcd.cls();
                lcd.locate(1,0);
                lcd.printf("Time= %1.2f mn", tim*15);
            } else {
                lcd.cls();
                lcd.locate(1,0);
                lcd.printf("Time= %1.2f Hr",tim*15/60);

            }
        }
    } while(pin_start==0);

    if(i==0) {
        while(1) {
            lcd.cls();
            lcd.locate(3,0);
            lcd.printf("Error!!!");
            lcd.locate(1,1);
            lcd.printf("Time not set");
            wait(3);
        }
    }

    tim = Quarters; //Initial selected number of quarters

    if(d==0) {
        startRun() ;
    } else {

        int sec = 60;
        int min = d*15;

        if(d<4) {
            while(min>0) {
                lcd.cls();
                lcd.locate(1,0);
                lcd.printf("Wait =%d min %d",min-1, sec);
                wait(1);
                sec--;
                if(sec==0) {
                    min--;
                    sec = 60;
                }
                if(min==0) {
                    d=0;
                }
                Pin_rain.rise(&rainsense);
            }
        } else {
            int sec = 60;
            float hr = d*0.25;
            while(hr>0) {
                lcd.cls();
                lcd.locate(0,0);
                lcd.printf("Wait= %1.2f Hr %d",hr-0.01, sec);
                wait(1);
                sec--;
                if(sec==0) {
                    hr= hr-0.01;
                    sec = 60;
                }
                if(hr==0) {
                    d = 0;
                }
                Pin_rain.rise(&rainsense);
            }
        }
        startRun();
    }

    // call to (re)start engine run)&& status == true if(runtimeleft == 0 )
    while(1);       // just wait for keypress

}

even if I remove the while loop from the do while loop, it still skips.

posted by jayendra mishra 08 Jun 2016

in function rainsense() there is a while(1) loop. you will never return from this function.

Are you sure this is what you want? Why not set the variable and return. I have no looked at the mbed source code but I think you are trapped in the interrupt handler if you never return.

posted by David Thedens 08 Jun 2016

yes i want that if this function is called...

posted by jayendra mishra 08 Jun 2016

So i performed some analysis by trying do while loop seperately. It counted untill i pressed the button in while loop. But I found that if I implement do while loop, for some reason it just counts till and comes out of loop. Is this strange behavior due to ARM M0 cortex? It doesnt even clear screen correctly if I put an interrupt to come out of do while loop, as in this case pin_start is pressed, and place a print f command after the loop.

posted by jayendra mishra 08 Jun 2016

Well this isn't exactly an answer but I notice the lines:

i=i++;

and

i=i--;

and I think these may be a problem because depending on execution order they may result in nothing happening or an increment/decrement. The commands should be:

i++;

or

i--;

The problem with i=i++; is that as an operator i++ returns the value of i, then increments i. The assignment then overwrites this with the original value. Some compilers might assign first then increment.

posted by Oliver Broad 08 Jun 2016

oops. Ignore

posted by Andy A 09 Jun 2016

Is the possible reason of its not working is error in mbed library for stm L031k6?

posted by jayendra mishra 09 Jun 2016

1 Answer

7 years, 11 months ago.

If you use the online compiler, please do right mouse button, format, on the file you are showing. Now the indents are all over the place and it is very hard to read.

It also seems it does not follow the normal syntax of a do while loop, that is shown here for example: http://www.tutorialspoint.com/cprogramming/c_do_while_loop.htm

Accepted Answer

He has a while {} loop inside a do { } while loop but the formatting doesn't make that very clear.

posted by Andy A 08 Jun 2016

Yeah I noticed, and now on another look I think his do loop ends with the while at line 73, in which case the syntax would make sense. Still without proper formatting this is not really handy.

posted by Erik - 08 Jun 2016

But this program worked absolutely fine on stm l152re. why is it not working in l031k6?

posted by jayendra mishra 08 Jun 2016

how should I do proper formatting.

posted by jayendra mishra 08 Jun 2016

If you use the online compiler, please do right mouse button, format, on the file you are showing. Now the indents are all over the place and it is very hard to read.

posted by Erik - 08 Jun 2016

So i performed some analysis by trying do while loop seperately. It counted untill i pressed the button in while loop. But I found that if I implement do while loop, for some reason it just counts till and comes out of loop. Is this strange behavior due to ARM M0 cortex? It doesnt even clear screen correctly if I put an interrupt to come out of do while loop, as in this case pin_start is pressed, and place a print f command after the loop.

posted by jayendra mishra 08 Jun 2016