Misbehaving recursive functions

I realize that recursive functions are likely to be subject to some limitations, but it appears that the generated code is invalid. Here is a simple example to illustrate the problem.

using Toybox.Application as App;
using Toybox.System as Sys;

function recursive_function(lo, hi) {
Sys.println(Lang.format("lo=$1$ hi=$2$", [ lo, hi ]));

if (lo == hi) {
Sys.println("end recurse!");
return;
}

++lo;
recursive_function(lo, hi);
}

class ZebraApp extends App.AppBase {

function onStart() {
recursive_function(0, 3);
}

function onStop() {
}

function getInitialView() {
return [ new ZebraView() ];
}
}


When I run the program, I see the following output...

Shell Version 0.1.0
lo=0 hi=3
lo=1 hi=3
lo=2 hi=3
lo=3 hi=3
end recurse!
lo=4 hi=3
lo=5 hi=3
lo=6 hi=3
lo=7 hi=3
lo=8 hi=3
lo=9 hi=3
lo=10 hi=3
lo=11 hi=3
lo=12 hi=3
lo=13 hi=3
lo=14 hi=3
lo=15 hi=3
lo=16 hi=3
lo=17 hi=3
lo=18 hi=3
Stack Overflow Error
in recursive_function (source\ZebraApp.mc:5)
in recursive_function (source\ZebraApp.mc:13)
in recursive_function (source\ZebraApp.mc:13)
in recursive_function (source\ZebraApp.mc:13)
in recursive_function (source\ZebraApp.mc:13)
in recursive_function (source\ZebraApp.mc:13)
in recursive_function (source\ZebraApp.mc:13)
in recursive_function (source\ZebraApp.mc:13)
in recursive_function (source\ZebraApp.mc:13)
in recursive_function (source\ZebraApp.mc:13)
in recursive_function (source\ZebraApp.mc:13)
in recursive_function (source\ZebraApp.mc:13)
in recursive_function (source\ZebraApp.mc:13)
in recursive_function (source\ZebraApp.mc:13)
in recursive_function (source\ZebraApp.mc:13)
in recursive_function (source\ZebraApp.mc:13)
in recursive_function (source\ZebraApp.mc:13)
in recursive_function (source\ZebraApp.mc:13)
in recursive_function (source\ZebraApp.mc:13)
in recursive_function (source\ZebraApp.mc:13)
in onStart (source\ZebraApp.mc:19)
Stack Overflow Error
Complete
Connection Finished
Closing shell and port


As you can see, the recursion was supposed to end, but it just keeps on going. I've found that if I update the code to terminate the recursion a little differently, the problem can be avoided.

using Toybox.Application as App;
using Toybox.System as Sys;

function recursive_function(lo, hi) {
Sys.println(Lang.format("lo=$1$ hi=$2$", [ lo, hi ]));

if (lo == hi) {
Sys.println("end recurse!");
return;
}
else {
++lo;
recursive_function(lo, hi);
}
}
  • Former Member
    Former Member over 10 years ago
    I don't think you can have an empty return. Try return 0;
  • The MonkeyC documentation states...

    You can specify the return value with a return statement, but if your function doesn’t have a return statement it will return the last value on the stack.


    Since my program doesn't use the return value, it doesn't make sense to explicitly provide one.

    That said, it does seem to fix the problem. Thanks.
  • Wow, so I'm not proud of this one. That's a compiler bug you've identified - if the return doesn't have an expression it just skips providing return opcode. We'll have it fixed in Preview 2. In the meantime "return null" instead of "return" will fix the problem.

    -Alpha Monkey