Please login or register.

Login with username, password and session length
Advanced search  

News:

This forum provides RSS feed. To query recent posts use this url. More...


Author Topic: weird call stack behavior  (Read 9397 times)

0 Members and 1 Guest are viewing this topic.

princezna

  • Lurker
  • *
  • Karma: 0
  • Offline Offline
  • Posts: 1
    • View Profile
weird call stack behavior
« on: September 04, 2007, 02:42:05 PM »

Dear community members,
while developing a new project using WME, I came across some very strange behavior, that might lead us to bugs in the WME call stack. But it might as well just be me. ;) So here's the deal:

1) This one seems to be event related. A running event is interrupted by invoking the same event again. This is perfectly fine as long as we don't have custom subroutine (method) calls inside the event handler. The problem is that only the top subroutine on the call stack gets interrupted and the event handler continues execution until the end or until a return statement is found. Not following me? That's alright, because here's some code to demonstrate my point:

This is a script file attached to a rock object that is normally accessible to the player on the current scene.
Code: [Select]
on "LookAt"
{
  actor.GoTo( this.X, this.Y );
  actor.Talk( "It's just a small rock, but it might come in handy." )
}

Let's say the player triggers the "LookAt" event and while the actor is still walking to the rock, he triggers the event again. The actor stops and the event is restarted. That's fine - nothing unexpected here. Now we want the actor to perform some generic action as he tries to reach the selected object.

This is a script file attached to the main actor.
Code: [Select]
method GoToLocation( px, py )
{
  // perform some action, doesn't really matter what, might be nothing
  this.GoTo( px, py );
}

Now we change the item script to include this new method. It's not the event that gets interrupted now - it's the GoToLocation method only. How does it affect the game? The main actor stops, says "It's just a small rock, ..." and the event is restarted - the actor starts moving towards the rock again. Of course we could check, if the required conditions are met after each call to a subroutine inside the event handler, but this introduces a lot of redundant code and makes custom methods kind of useless in this or similar situations. So tell me: Is this intended behaviour or a bug? By the way this happens both in stable and beta.

2) I discovered this one when playing around with the last stable version of WME (didn't try it yet in beta). I had a few events I needed to trigger after a certain period of time, so I wrote this little script that basicly works as timers. (A timer class would be a nice addition to the next WME version, don't you think? ;))

Here's the code:
Code: [Select]
#include "scripts\base.inc"

global timers = new Array();

method timer_set( obj, time, event, loop )
{
  var index = timers.Length;
  var timer = new Object();

  timer.master = obj; // the object we're going to apply the event to
  timer.start = Game.CurrentTime;
  timer.interval = time;
  timer.event = event; // event to be applied
  timer.loop = loop; // True = loop the timer, False = only one shot

  timers[index] = timer;

  return (index);
}

/* this method is supposed to remove the timer

   btw I wouldn't mind if someone explained to me in detail how does
   garbage collection in WME work */
method timer_remove( index )
{
  timers[index] = null;
}

/* update all active timers

   this method should be called everytime in the main loop */
method timer_update()
{
  var current, master;
  var delta, i;

  for( i = 0; i < timers.Length; i = i + 1 )
  {
    current = timers[i];
    if ( !current )
      continue;

    delta = Game.CurrentTime - current.start;
    if ( delta >= current.interval )
    {
      master = current.master;
      if ( master.CanHandleEvent( current.event ) )
        master.ApplyEvent( current.event );

      if ( !current.loop )
        timers[i] = null;
    }
  }
}

The problem here is that WME jumps almost randomly in the script! When the execution reaches this line:
Code: [Select]
delta = Game.CurrentTime - current.start;It always jumps at the end of the method, not even trying to evaluate the following if condition. I tried to step through the code using the build-in debugger several times and I'm sure the condition is met, but never evaluated. So I wonder, what's up with that? ??? (Please restrain yourself from commenting on the timer implementation itself and concentrate on the problem in question.)

Everything was tested on my laptop running WinXP PRO SP2.
Any help would be very appreciated, thank you.
Logged

Mnemonic

  • WME developer
  • Administrator
  • Addicted to WME forum
  • *
  • Karma: 41
  • Offline Offline
  • Gender: Male
  • Posts: 5683
    • View Profile
    • Dead:Code Site
Re: weird call stack behavior
« Reply #1 on: September 04, 2007, 08:45:09 PM »

So tell me: Is this intended behaviour or a bug? By the way this happens both in stable and beta.
Well, let's say it's expected behavior, albeit far from ideal. I'm aware of this issue, but I'm a little afraid to change it now, because such change could be theoretically quite destructive for existing games. But I agree it *should* be addressed so I think I'll add some compatibility setting once it's corrected, so that people can restore the current behavior when necessary.


The problem here is that WME jumps almost randomly in the script!
The problem here is that the code generated by WME's script compiler was never designed to be debugger friendly. It keeps track of the current script line for the purposes of error reporting (which it does well), but the actual code flow can look quite erratic sometimes (the debugger has been added much later in development and this shortcoming became very visible since then).
That said, the "delta = Game.CurrentTime - current.start;" line isn't actually executed, the "continue;" line is. The debugger highlights a wrong line briefly because of how the compiled code is structured internally..

So, technically it's not a bug, just a cosmetic issue ;)
Logged
Yes, I do have a twitter account
Please don't send me technical questions in private messages, use the forum. ::wave
 

Page created in 0.048 seconds with 21 queries.