Shop OBEX P1 Docs P2 Docs Learn Events
Small Program Problem - Page 2 — Parallax Forums

Small Program Problem

2»

Comments

  • Fred HawkinsFred Hawkins Posts: 997
    edited 2007-10-08 01:20
    Sid,
    I looked your code over. And generally, the critique that you have lower methods calling higher ones (that in turn call the lower ones that call the higher... ad infinitum and then STOP) is correct.

    Here's what you should do: In menu, use a repeat until some condition for which you want everything to stop. Then in the lower methods, drop the calls to menu. Just let them come back naturally.

    I suggest that you learn the CASE construct which is perfectly suited for sorting out keypresses.

    Fred
    1020 x 2461 - 22K
  • NewzedNewzed Posts: 2,503
    edited 2007-10-08 13:24
    Fred, are you saying I should write this:

    PUB menu
    ·· text.out(0)
    ·· text.out(13)
    ·· key.clearkeys
    ·· cnto := cnt
    ·· readadc
    ·· readclock2
    ·· menu1
    ·· repeat
    ···· if cnt =>cnto + clkfreq*4 and cnt<cnto + clkfreq*9
    ······ waitcnt(clkfreq + cnt)
    ······ menu
    ···· if key.gotkey
    ······ cmds

    I am quite familiar with the CASE statement.· However, I have found no particular advantage in using it.· On the couple if times I have checked, it uses the same amount of memory as the comparable "if" statements.

    I have noted that sometimes the program will lock up on the repeat statement waiting for:

    if cnt =>cnto + clkfreq*4 and cnt<cnto + clkfreq*9
    ······ waitcnt(clkfreq + cnt)
    ······ menu

    to become true.· I have let the program sit and eventually it cycles, taking various times, sometimes a minute, once as long as 5:30.· Admittedly, the "true' window is quite small.· Hopefully this will improve when I got to a 30-second window - I really don't know.

    Sid

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Yesterday is history, tomorrow is a mystery, and today is a gift.

    That is why they call it the present.

    Don't have VGA?
    Newzed@aol.com
    ·
  • NewzedNewzed Posts: 2,503
    edited 2007-10-08 14:38
    This business of the program waiting for:

    if cnt =>cnto + clkfreq*4 and cnt<cnto + clkfreq*9

    to become true is a bit annoying.· Is there some way I could set one of the counters, say ctra, to 0 and then have the program refresh when ctra is equal to a pre-defined constat, such as time1 = 400_000_000?

    Sid

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Yesterday is history, tomorrow is a mystery, and today is a gift.

    That is why they call it the present.

    Don't have VGA?
    Newzed@aol.com
    ·
  • Stan671Stan671 Posts: 103
    edited 2007-10-08 14:54
    Sid, no, you still have the concept all wrong. You have the MENU method calling itself!! And you cannot have MENU call CMDS because CMDS calls MENU.

    I just figured out the flaw in your thinking: You are trying to use a call to another method like a GOTO. It is certainly not a GOTO, it is more like a subroutine call. Subroutines cannot call themselves and cannot call other subroutines that call the original caller. Wow, that was even hard to type. <grin>

    Stop worrying about saving memory in order to get this to work. The problem is not a shortage of memory. The problem is that your methods (subroutines) are never reaching thier own end and returning to the original caller normally. Therefore your stack goes haywire and crashes your Prop.

    And since you are having stack problems, I would not trust any symptoms you see as having any particular meaning. When you stack goes berzerk, lots of wierdness will happen that seems totally unrelated.

    I don't want to sound harsh to you, Sid, you but need to get your mind right before you can come close to fixing this program. The problems here are not a simple fix by changing a couple of lines of code. Please re-read my two posts, stare at Fred's spaghetti chart, and repeat to yourself "a method call is not a GOTO" until you have the required epifany.

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Stan Dobrowski
  • NewzedNewzed Posts: 2,503
    edited 2007-10-08 15:30
    Sorry, Stan.· I do not know how to do what you are saying.· I have attached a copy of the program I am presently running.· If you have time to fix it, fine.· If not, then I'll just keep on using what I have and reboot every 151 cycles.· I've solved the problem of the program pausing while waiting for

    if cnt =>cnto + clkfreq*4 and cnt<cnto + clkfreq*9

    to become true.· See Line 153.

    Sid

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Yesterday is history, tomorrow is a mystery, and today is a gift.

    That is why they call it the present.

    Don't have VGA?
    Newzed@aol.com
  • Graham StablerGraham Stabler Posts: 2,507
    edited 2007-10-08 16:40
    The concept of a method/function is that you call it, some code is executed and then the program returns to the point where the program was called.

    So in your menu function it does not make any sense to call menu, it would make more sense to put the contents of menu in one big loop and have the second loop where you are waiting for z== 72_00 to end when z=72_00 (use a repeat until loop) this will automatically loop back around to the start of the code in menu.

    pub menu
    
    repeat 
       some code
       some more code
       repeat until z == 72000
          if key.gotkey
             cmds
       
    
    



    And then rather than trying to call menu from cmds (because menu is where cmd was called from) do:

    if cmd == "f"
       return
    
    



    Just to try and clarify what stan was saying, writing call menu is not the same as writing goto menu if that were possible. When you call a function it executes the code in the function until the end of the function or until a return command, then the program jumps back to where it was called from.

    Graham

    Post Edited (Graham Stabler) : 10/8/2007 4:46:52 PM GMT
  • NewzedNewzed Posts: 2,503
    edited 2007-10-08 17:08
    Graham, you wrote:

    if·cmd·==·"f"
    ···return

    Suppose I wanted to do something if cmd == "f", like jump to a method named "alarm".· Would I write:

    if·cmd·==·"f"
    ·· alarm
    ···return

    Sid



    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Yesterday is history, tomorrow is a mystery, and today is a gift.

    That is why they call it the present.

    Don't have VGA?
    Newzed@aol.com
    ·
  • Graham StablerGraham Stabler Posts: 2,507
    edited 2007-10-08 17:14
    That's correct the alarm function would be called, then it would return back to the cmd function then the cmd function would return to the menu function.

    This is what is called program flow, the program flows into a function and then returns back. Unless you are starting a new cog (which allows parallel flows) this is how it always works.

    I think you have just got yourself mixed up because you use functions all the time.

    Graham
  • NewzedNewzed Posts: 2,503
    edited 2007-10-08 17:56
    Graham, I wote:

    PUB menu
    · z := 0
    · text.dec(z)
    · repeat
    ··· text.out(0)
    ··· text.out(13)
    ··· key.clearkeys
    ··· y := y + 1
    ··· text.dec(y)
    ··· readadc
    ··· readclock2
    ··· menu1
    ··· repeat
    ····· z := z + 1
    ····· if key.gotkey
    ······· cmds
    ··· until z == 72_000

    The program locked up on the second cycle.· Then I wrote:

    Pub start1
    ·· menu

    PUB menu
    · z := 0
    · text.dec(z)
    · repeat
    ··· text.out(0)
    ··· text.out(13)
    ··· key.clearkeys
    ··· y := y + 1
    ··· text.dec(y)
    ··· readadc
    ··· readclock2
    ··· menu1
    ··· repeat
    ····· z := z + 1
    ····· if key.gotkey
    ······· cmds
    ··· until z == 72_000
    ··· start1

    Is that acceptable?

    Sid
    ···

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Yesterday is history, tomorrow is a mystery, and today is a gift.

    That is why they call it the present.

    Don't have VGA?
    Newzed@aol.com
    ·
  • Fred HawkinsFred Hawkins Posts: 997
    edited 2007-10-08 17:56
    Sid,
    Take a look at how your initialize routine makes a series of calls (usually masked as assignments). For instance:

    long[noparse][[/noparse]ldr#videoPtr] := ldr.allocatePRI(ldr#videoSize) ' Allocate work area for video

    Control goes out to the called module's routine (in this example, allocatePRI in OSloader) and comes back. Your own code should do the same -- you call the routine (invoke the name), it finishes, control comes back.

    And don't mistake the fact that because initialize is using objects that you loaded (defined) that your own routines are somehow different. Everything is invoked (called) the same way, and returns the same way.

    Fred
  • Graham StablerGraham Stabler Posts: 2,507
    edited 2007-10-08 18:08
    Sid,

    Why would you want to call the function you are already in? That was the point of putting a loop in the function so it automatically repeats when it gets to the end. I gave a very clear example of this.

    If you don't want a loop in the function then the call to the function must be in some other loop. Very commonly you will have a function called main which is the main program loop from which various functions are called. So it could be something like this:

    
    pub main
    do some initialization
    repeat
        call a function
        menu
    
    pub menu
        some code
        return  
    
    
    



    Graham
  • NewzedNewzed Posts: 2,503
    edited 2007-10-08 18:15
    Graham, is this not what were telling me to write:

    PUB menu
    · z := 0
    · text.dec(z)
    · repeat
    ··· text.out(0)
    ··· text.out(13)
    ··· key.clearkeys
    ··· y := y + 1
    ··· text.dec(y)
    ··· readadc
    ··· readclock2
    ··· menu1
    ··· repeat· until z == 72_000···
    ····· z := z + 1
    ····· if key.gotkey
    ······· cmds

    Sid



    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Yesterday is history, tomorrow is a mystery, and today is a gift.

    That is why they call it the present.

    Don't have VGA?
    Newzed@aol.com
    ·
  • NewzedNewzed Posts: 2,503
    edited 2007-10-08 18:30
    Never mind, Graham - I found the problem.· I was not clearing z to 0.· I added;

    z := 0

    right after the first repeat and now it is working OK.· I'm running the program to see if it locks up ater X cycles.· It's up to 170 cycles and still going.· I'll let you know if it locks up.

    Sid

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Yesterday is history, tomorrow is a mystery, and today is a gift.

    That is why they call it the present.

    Don't have VGA?
    Newzed@aol.com
    ·
  • Graham StablerGraham Stabler Posts: 2,507
    edited 2007-10-08 18:32
    Well that in itself looks fine but it does rather depend on what the other functions, cmds and menu1 functions look like now.

    Graham
  • Graham StablerGraham Stabler Posts: 2,507
    edited 2007-10-08 18:36
    Oh good! I suspect your improved understanding about function use may mean your programs behave as you expect more often from now on.

    Graham
  • NewzedNewzed Posts: 2,503
    edited 2007-10-08 18:52
    Graham, it has cycled over 500 times - looks like everything is OK.· Now to·tidy up the program and set the cycle time to what I want.· Thank you very much.· Your very lucid explanation if what I should be doing was invaluable.

    Till next time.

    Sid

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Yesterday is history, tomorrow is a mystery, and today is a gift.

    That is why they call it the present.

    Don't have VGA?
    Newzed@aol.com
    ·
  • Fred HawkinsFred Hawkins Posts: 997
    edited 2007-10-09 07:27
    Sid,
    I'd like to see your new code to compare with the old.
    Fred
  • NewzedNewzed Posts: 2,503
    edited 2007-10-09 11:42
    Here you are, Fred.

    Sid

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Yesterday is history, tomorrow is a mystery, and today is a gift.

    That is why they call it the present.

    Don't have VGA?
    Newzed@aol.com
  • Graham StablerGraham Stabler Posts: 2,507
    edited 2007-10-09 11:58
    That looks a lot better.

    Going back to your original problem what you could do is make the time out period a multiple of the refresh time

    repeat
       waitcnt(cnt+refreshtime)
       refresh the screen
       r := r + 1
       if r > timeout
            display message
            r := 0
    
    
  • NewzedNewzed Posts: 2,503
    edited 2007-10-11 13:09
    Graham, I tidied up my program - found a few more bad "menu" calls and fixed those.· Started running the program yesterday afternoon on a short refresh cycle, and this morning it has completed over 13,800 consecutive·refreshes.

    Sid

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Yesterday is history, tomorrow is a mystery, and today is a gift.

    That is why they call it the present.

    Don't have VGA?
    Newzed@aol.com
    ·
Sign In or Register to comment.