Fix a problem with two concurent 'round to multiple of basic simulation
time' code paths. The problem may lead to skipped fdm updates at very high frame rates. The most visible effect of that was that the aircraft slips backwards wrt the forward moving carrier. Remove unused stuff. Modified Files: configure.ac projects/VC7.1/FlightGear.vcproj projects/VC8/FlightGearLib.vcproj src/Cockpit/cockpit.cxx src/FDM/Makefile.am src/FDM/flight.cxx src/FDM/flight.hxx src/FDM/SP/Balloon.cxx src/FDM/SP/BalloonSim.cpp src/FDM/SP/BalloonSim.h src/Main/Makefile.am src/Main/fg_init.cxx src/Main/main.cxx src/Time/Makefile.am Removed Files: src/Time/fg_timer.cxx src/Time/fg_timer.hxx
This commit is contained in:
parent
aadf568c91
commit
183b871b48
9 changed files with 16 additions and 270 deletions
|
@ -2223,12 +2223,6 @@
|
|||
<Filter
|
||||
Name="Lib_Time"
|
||||
Filter="">
|
||||
<File
|
||||
RelativePath="..\..\src\Time\fg_timer.cxx">
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\..\src\Time\fg_timer.hxx">
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\..\src\Time\light.cxx">
|
||||
</File>
|
||||
|
|
|
@ -488,10 +488,6 @@
|
|||
RelativePath="..\..\src\include\fg_stl_config.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\..\src\time\fg_timer.hxx"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\..\src\include\fg_typedefs.h"
|
||||
>
|
||||
|
@ -2198,10 +2194,6 @@
|
|||
RelativePath="..\..\src\main\fg_props.cxx"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\..\src\time\fg_timer.cxx"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath="..\..\src\FDM\JSBSim\models\flight_control\FGActuator.cpp"
|
||||
>
|
||||
|
|
|
@ -45,7 +45,6 @@
|
|||
#include <Main/fg_props.hxx>
|
||||
#include <Main/viewmgr.hxx>
|
||||
#include <Scenery/scenery.hxx>
|
||||
#include <Time/fg_timer.hxx>
|
||||
#include <GUI/gui.h>
|
||||
|
||||
#include "cockpit.hxx"
|
||||
|
|
|
@ -44,23 +44,15 @@ static inline void assign(double* ptr, const SGVec3d& vec)
|
|||
ptr[2] = vec[2];
|
||||
}
|
||||
|
||||
// base_fdm_state is the internal state that is updated in integer
|
||||
// multiples of "dt". This leads to "jitter" with respect to the real
|
||||
// world time, so we introduce cur_fdm_state which is extrapolated by
|
||||
// the difference between sim time and real world time
|
||||
|
||||
FGInterface *cur_fdm_state = 0;
|
||||
FGInterface base_fdm_state;
|
||||
|
||||
// Constructor
|
||||
FGInterface::FGInterface()
|
||||
: remainder(0)
|
||||
{
|
||||
_setup();
|
||||
}
|
||||
|
||||
FGInterface::FGInterface( double dt )
|
||||
: remainder(0)
|
||||
{
|
||||
_setup();
|
||||
}
|
||||
|
@ -70,33 +62,18 @@ FGInterface::~FGInterface() {
|
|||
// unbind(); // FIXME: should be called explicitly
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
FGInterface::_calc_multiloop (double dt)
|
||||
{
|
||||
// Since some time the simulation time increments we get here are
|
||||
// already a multiple of the basic update freqency.
|
||||
// So, there is no need to do our own multiloop rounding with all bad
|
||||
// roundoff problems when we already have nearly accurate values.
|
||||
// Only the speedup thing must be still handled here
|
||||
int hz = fgGetInt("/sim/model-hz");
|
||||
int multiloop = SGMiscd::roundToInt(dt*hz);
|
||||
int speedup = fgGetInt("/sim/speed-up");
|
||||
|
||||
dt += remainder;
|
||||
remainder = 0;
|
||||
double ml = dt * hz;
|
||||
// Avoid roundoff problems by adding the roundoff itself.
|
||||
// ... ok, two times the roundoff to have enough room.
|
||||
int multiloop = int(floor(ml * (1.0 + 2.0*DBL_EPSILON)));
|
||||
remainder = (ml - multiloop) / hz;
|
||||
|
||||
// If we artificially inflate ml above by a tiny amount to get the
|
||||
// closest integer, then subtract the integer from the original
|
||||
// slightly smaller value, we can get a negative remainder.
|
||||
// Logically this should never happen, and we definitely don't want
|
||||
// to carry a negative remainder over to the next iteration, so
|
||||
// never let the remainder go below zero.
|
||||
//
|
||||
// Note: this fixes a problem where we run 1, 3, 1, 3, 1, 3... loops
|
||||
// of the FDM when in fact we want to run 2, 2, 2, 2, 2...
|
||||
if ( remainder < 0 ) { remainder = 0; }
|
||||
|
||||
return (multiloop * speedup);
|
||||
return multiloop * speedup;
|
||||
}
|
||||
|
||||
|
||||
|
@ -165,9 +142,6 @@ FGInterface::common_init ()
|
|||
|
||||
ground_cache.set_cache_time_offset(globals->get_sim_time_sec());
|
||||
|
||||
// stamp();
|
||||
// set_remainder( 0 );
|
||||
|
||||
// Set initial position
|
||||
SG_LOG( SG_FLIGHT, SG_INFO, "...initializing position..." );
|
||||
double lon = fgGetDouble("/sim/presets/longitude-deg")
|
||||
|
@ -261,16 +235,6 @@ FGInterface::bind ()
|
|||
{
|
||||
bound = true;
|
||||
|
||||
// Time management (read-only)
|
||||
// fgTie("/fdm/time/delta_t", this,
|
||||
// &FGInterface::get_delta_t); // read-only
|
||||
// fgTie("/fdm/time/elapsed", this,
|
||||
// &FGInterface::get_elapsed); // read-only
|
||||
// fgTie("/fdm/time/remainder", this,
|
||||
// &FGInterface::get_remainder); // read-only
|
||||
// fgTie("/fdm/time/multi_loop", this,
|
||||
// &FGInterface::get_multi_loop); // read-only
|
||||
|
||||
// Aircraft position
|
||||
fgTie("/position/latitude-deg", this,
|
||||
&FGInterface::get_Latitude_deg,
|
||||
|
@ -429,10 +393,6 @@ FGInterface::unbind ()
|
|||
{
|
||||
bound = false;
|
||||
|
||||
// fgUntie("/fdm/time/delta_t");
|
||||
// fgUntie("/fdm/time/elapsed");
|
||||
// fgUntie("/fdm/time/remainder");
|
||||
// fgUntie("/fdm/time/multi_loop");
|
||||
fgUntie("/position/latitude-deg");
|
||||
fgUntie("/position/longitude-deg");
|
||||
fgUntie("/position/altitude-ft");
|
||||
|
|
|
@ -111,8 +111,6 @@ private:
|
|||
// next elapsed time. This yields a small amount of temporal
|
||||
// jitter ( < dt ) but in practice seems to work well.
|
||||
|
||||
double remainder; // remainder time from last run
|
||||
|
||||
// CG position w.r.t. ref. point
|
||||
SGVec3d d_cg_rp_body_v;
|
||||
|
||||
|
|
|
@ -67,7 +67,6 @@
|
|||
#include <ATCDCL/ATCmgr.hxx>
|
||||
#include <ATCDCL/AIMgr.hxx>
|
||||
#include <Time/tmp.hxx>
|
||||
#include <Time/fg_timer.hxx>
|
||||
#include <Environment/environment_mgr.hxx>
|
||||
#include <GUI/new_gui.hxx>
|
||||
#include <MultiPlayer/multiplaymgr.hxx>
|
||||
|
@ -304,15 +303,12 @@ static void fgMainLoop( void ) {
|
|||
|
||||
// round the real time down to a multiple of 1/model-hz.
|
||||
// this way all systems are updated the _same_ amount of dt.
|
||||
{
|
||||
static double rem = 0.0;
|
||||
real_delta_time_sec += rem;
|
||||
double hz = model_hz;
|
||||
double nit = floor(real_delta_time_sec*hz);
|
||||
rem = real_delta_time_sec - nit/hz;
|
||||
real_delta_time_sec = nit/hz;
|
||||
}
|
||||
|
||||
static double reminder = 0.0;
|
||||
real_delta_time_sec += reminder;
|
||||
global_multi_loop = long(floor(real_delta_time_sec*model_hz));
|
||||
global_multi_loop = SGMisc<long>::max(0, global_multi_loop);
|
||||
reminder = real_delta_time_sec - double(global_multi_loop)/double(model_hz);
|
||||
real_delta_time_sec = double(global_multi_loop)/double(model_hz);
|
||||
|
||||
if (clock_freeze->getBoolValue() || wait_for_scenery) {
|
||||
delta_time_sec = 0;
|
||||
|
@ -326,8 +322,6 @@ static void fgMainLoop( void ) {
|
|||
fgSetDouble("/sim/time/delta-realtime-sec", real_delta_time_sec);
|
||||
fgSetDouble("/sim/time/delta-sec", delta_time_sec);
|
||||
|
||||
static long remainder = 0;
|
||||
long elapsed;
|
||||
#ifdef FANCY_FRAME_COUNTER
|
||||
int i;
|
||||
double accum;
|
||||
|
@ -400,12 +394,6 @@ static void fgMainLoop( void ) {
|
|||
altitude->getDoubleValue() * SG_FEET_TO_METER,
|
||||
globals->get_time_params()->getJD() );
|
||||
|
||||
// Get elapsed time (in usec) for this past frame
|
||||
elapsed = fgGetTimeInterval();
|
||||
SG_LOG( SG_ALL, SG_DEBUG,
|
||||
"Elapsed time interval is = " << elapsed
|
||||
<< ", previous remainder is = " << remainder );
|
||||
|
||||
// Calculate frame rate average
|
||||
#ifdef FANCY_FRAME_COUNTER
|
||||
/* old fps calculation */
|
||||
|
@ -452,27 +440,10 @@ static void fgMainLoop( void ) {
|
|||
globals->get_AI_mgr()->update(delta_time_sec);
|
||||
|
||||
// Run flight model
|
||||
|
||||
// Calculate model iterations needed for next frame
|
||||
elapsed += remainder;
|
||||
|
||||
global_multi_loop = (long)(((double)elapsed * 0.000001) * model_hz );
|
||||
remainder = elapsed - ( (global_multi_loop*1000000) / model_hz );
|
||||
SG_LOG( SG_ALL, SG_DEBUG,
|
||||
"Model iterations needed = " << global_multi_loop
|
||||
<< ", new remainder = " << remainder );
|
||||
|
||||
// chop max iterations to something reasonable if the sim was
|
||||
// delayed for an excessive amount of time
|
||||
if ( global_multi_loop > 2.0 * model_hz ) {
|
||||
global_multi_loop = (int)(2.0 * model_hz );
|
||||
remainder = 0;
|
||||
}
|
||||
|
||||
// flight model
|
||||
if ( global_multi_loop > 0) {
|
||||
if (0 < global_multi_loop) {
|
||||
// first run the flight model each frame until it is initialized
|
||||
// then continue running each frame only after initial scenery load is complete.
|
||||
// then continue running each frame only after initial scenery
|
||||
// load is complete.
|
||||
fgUpdateTimeDepCalcs();
|
||||
} else {
|
||||
SG_LOG( SG_ALL, SG_DEBUG,
|
||||
|
|
|
@ -1,7 +1,6 @@
|
|||
noinst_LIBRARIES = libTime.a
|
||||
|
||||
libTime_a_SOURCES = \
|
||||
fg_timer.cxx fg_timer.hxx \
|
||||
light.cxx light.hxx \
|
||||
sunsolver.cxx sunsolver.hxx \
|
||||
tmp.cxx tmp.hxx
|
||||
|
|
|
@ -1,120 +0,0 @@
|
|||
// fg_timer.cxx -- time handling routines
|
||||
//
|
||||
// Written by Curtis Olson, started June 1997.
|
||||
//
|
||||
// Copyright (C) 1997 Curtis L. Olson - http://www.flightgear.org/~curt
|
||||
//
|
||||
// This program is free software; you can redistribute it and/or
|
||||
// modify it under the terms of the GNU General Public License as
|
||||
// published by the Free Software Foundation; either version 2 of the
|
||||
// License, or (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful, but
|
||||
// WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
// General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program; if not, write to the Free Software
|
||||
// Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
//
|
||||
// $Id$
|
||||
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include <config.h>
|
||||
#endif
|
||||
|
||||
#include <signal.h> // for timer routines
|
||||
#include <stdio.h> // for printf()
|
||||
|
||||
#ifdef HAVE_STDLIB_H
|
||||
# include <stdlib.h>
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_SYS_TIME_H
|
||||
# include <sys/time.h> // for get/setitimer, gettimeofday, struct timeval
|
||||
#endif
|
||||
|
||||
#include <simgear/timing/timestamp.hxx>
|
||||
|
||||
#include "fg_timer.hxx"
|
||||
|
||||
|
||||
unsigned long int fgSimTime;
|
||||
|
||||
#ifdef HAVE_SETITIMER
|
||||
static struct itimerval t, ot;
|
||||
static void (*callbackfunc)(int multi_loop);
|
||||
|
||||
|
||||
// This routine catches the SIGALRM
|
||||
void fgTimerCatch( int dummy ) {
|
||||
int warning_avoider;
|
||||
|
||||
// get past a compiler warning
|
||||
warning_avoider = dummy;
|
||||
|
||||
// ignore any SIGALRM's until we come back from our EOM iteration
|
||||
signal(SIGALRM, SIG_IGN);
|
||||
|
||||
// printf("In fgTimerCatch()\n");
|
||||
|
||||
// -1 tells the routine to use default interval rather than
|
||||
// something dynamically calculated based on frame rate
|
||||
callbackfunc(-1);
|
||||
|
||||
signal(SIGALRM, fgTimerCatch);
|
||||
}
|
||||
|
||||
|
||||
// this routine initializes the interval timer to generate a SIGALRM
|
||||
// after the specified interval (dt)
|
||||
void fgTimerInit(float dt, void (*f)( int )) {
|
||||
int terr;
|
||||
int isec;
|
||||
int usec;
|
||||
|
||||
callbackfunc = f;
|
||||
|
||||
isec = (int) dt;
|
||||
usec = 1000000 * ((int)dt - isec);
|
||||
|
||||
t.it_interval.tv_sec = isec;
|
||||
t.it_interval.tv_usec = usec;
|
||||
t.it_value.tv_sec = isec;
|
||||
t.it_value.tv_usec = usec;
|
||||
// printf("fgTimerInit() called\n");
|
||||
fgTimerCatch(0); // set up for SIGALRM signal catch
|
||||
terr = setitimer( ITIMER_REAL, &t, &ot );
|
||||
if (terr) {
|
||||
printf("Error returned from setitimer");
|
||||
exit(0);
|
||||
}
|
||||
}
|
||||
#endif // HAVE_SETITIMER
|
||||
|
||||
|
||||
// This function returns the number of microseconds since the last
|
||||
// time it was called.
|
||||
int fgGetTimeInterval( void ) {
|
||||
int interval;
|
||||
static int inited = 0;
|
||||
static SGTimeStamp last;
|
||||
SGTimeStamp current;
|
||||
|
||||
|
||||
if ( ! inited ) {
|
||||
inited = 1;
|
||||
last.stamp();
|
||||
interval = 0;
|
||||
} else {
|
||||
current.stamp();
|
||||
interval = (current - last).toUSecs();
|
||||
last = current;
|
||||
}
|
||||
|
||||
return interval;
|
||||
}
|
||||
|
||||
|
|
@ -1,47 +0,0 @@
|
|||
// fg_timer.hxx -- time handling routines
|
||||
//
|
||||
// Written by Curtis Olson, started June 1997.
|
||||
//
|
||||
// Copyright (C) 1997 Curtis L. Olson - http://www.flightgear.org/~curt
|
||||
//
|
||||
// This program is free software; you can redistribute it and/or
|
||||
// modify it under the terms of the GNU General Public License as
|
||||
// published by the Free Software Foundation; either version 2 of the
|
||||
// License, or (at your option) any later version.
|
||||
//
|
||||
// This program is distributed in the hope that it will be useful, but
|
||||
// WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
// General Public License for more details.
|
||||
//
|
||||
// You should have received a copy of the GNU General Public License
|
||||
// along with this program; if not, write to the Free Software
|
||||
// Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
//
|
||||
// $Id$
|
||||
|
||||
|
||||
#ifndef _FG_TIMER_HXX
|
||||
#define _FG_TIMER_HXX
|
||||
|
||||
|
||||
#ifndef __cplusplus
|
||||
# error This library requires C++
|
||||
#endif
|
||||
|
||||
|
||||
extern unsigned long int fgSimTime;
|
||||
|
||||
// this routine initializes the interval timer to generate a SIGALRM
|
||||
// after the specified interval (dt) the function f() will be called
|
||||
// at each signal
|
||||
void fgTimerInit( float dt, void (*f)( int ) );
|
||||
|
||||
// This function returns the number of milleseconds since the last
|
||||
// time it was called.
|
||||
int fgGetTimeInterval( void );
|
||||
|
||||
|
||||
#endif // _FG_TIMER_HXX
|
||||
|
||||
|
Loading…
Add table
Reference in a new issue