s.length());
}
+static bool convertToNum(naRef v, double& result)
+{
+ naRef n = naNumValue(v);
+ if (naIsNil(n)) {
+ return false; // couldn't convert
+ }
+
+ result = n.num;
+ return true;
+}
+
static WayptFlag wayptFlagFromString(const char* s)
{
if (!strcmp(s, "sid")) return WPT_DEPARTURE;
naRef comms = naNewVector(c);
// if we have an explicit type, return a simple vector of frequencies
- if (argc > 0 && naIsScalar(args[0])) {
+ if (argc > 0 && !naIsString(args[0])) {
+ naRuntimeError(c, "airport.comms argument must be a frequency type name");
+ }
+
+ if (argc > 0) {
std::string commName = naStr_data(args[0]);
FGPositioned::Type commType = FGPositioned::typeFromName(commName);
void callDelegateMethod(const char* method)
{
naRef f;
- if (naMember_cget(_nasal->context(), _instance, method, &f) == 0) {
- return; // no method on the delegate
+ naContext ctx = naNewContext();
+
+ if (naMember_cget(ctx, _instance, method, &f) != 0) {
+ naRef arg[1];
+ arg[0] = ghostForFlightPlan(ctx, _plan);
+ _nasal->callMethod(f, _instance, 1, arg, naNil());
}
- naRef arg[1];
- arg[0] = ghostForFlightPlan(_nasal->context(), _plan);
- _nasal->callMethod(f, _instance, 1, arg, naNil());
+ naFreeContext(ctx);
}
FGNasalSys* _nasal;
int _gcSaveKey;
};
+
class NasalFPDelegateFactory : public FlightPlan::DelegateFactory
{
public:
_gcSaveKey = _nasal->gcSave(_func);
}
- ~NasalFPDelegateFactory()
+ virtual ~NasalFPDelegateFactory()
{
_nasal->gcRelease(_gcSaveKey);
}
virtual FlightPlan::Delegate* createFlightPlanDelegate(FlightPlan* fp)
{
naRef args[1];
- args[0] = ghostForFlightPlan(_nasal->context(), fp);
+ naContext ctx = naNewContext();
+ args[0] = ghostForFlightPlan(ctx, fp);
naRef instance = _nasal->call(_func, 1, args, naNil());
- if (naIsNil(instance)) {
- return NULL;
- }
- return new NasalFPDelegate(fp, _nasal, instance);
+ FlightPlan::Delegate* result = NULL;
+ if (!naIsNil(instance)) {
+ // will GC-save instance
+ result = new NasalFPDelegate(fp, _nasal, instance);
+ }
+
+ naFreeContext(ctx);
+ return result;
}
private:
FGNasalSys* _nasal;
int _gcSaveKey;
};
+static std::vector<NasalFPDelegateFactory*> static_nasalDelegateFactories;
+
+void shutdownNasalPositioned()
+{
+ std::vector<NasalFPDelegateFactory*>::iterator it;
+ for (it = static_nasalDelegateFactories.begin();
+ it != static_nasalDelegateFactories.end(); ++it)
+ {
+ FlightPlan::unregisterDelegateFactory(*it);
+ delete (*it);
+ }
+ static_nasalDelegateFactories.clear();
+}
+
static naRef f_registerFPDelegate(naContext c, naRef me, int argc, naRef* args)
{
if ((argc < 1) || !naIsFunc(args[0])) {
NasalFPDelegateFactory* factory = new NasalFPDelegateFactory(args[0]);
FlightPlan::registerDelegateFactory(factory);
-
+ static_nasalDelegateFactories.push_back(factory);
return naNil();
}
if (!leg) {
naRuntimeError(c, "leg.setSpeed called on non-flightplan-leg object");
}
-
- if (argc < 2) {
- naRuntimeError(c, "bad arguments to leg.setSpeed");
- }
-
+
+ double speed = 0.0;
+ if ((argc < 2) || !convertToNum(args[0], speed))
+ naRuntimeError(c, "bad arguments to setSpeed");
+
RouteRestriction rr = routeRestrictionFromString(naStr_data(args[1]));
- leg->setSpeed(rr, args[0].num);
+ leg->setSpeed(rr, speed);
+
return naNil();
}
naRuntimeError(c, "leg.setAltitude called on non-flightplan-leg object");
}
- if (argc < 2) {
- naRuntimeError(c, "bad arguments to leg.setAltitude");
- }
-
+ double alt = 0.0;
+ if ((argc < 2) || !convertToNum(args[0], alt))
+ naRuntimeError(c, "bad arguments to leg.setAltitude");
+
RouteRestriction rr = routeRestrictionFromString(naStr_data(args[1]));
- leg->setAltitude(rr, args[0].num);
+ leg->setAltitude(rr, alt);
+
return naNil();
}
};
-naRef initNasalPositioned(naRef globals, naContext c, naRef gcSave)
+naRef initNasalPositioned(naRef globals, naContext c)
{
airportPrototype = naNewHash(c);
- hashset(c, gcSave, "airportProto", airportPrototype);
+ naSave(c, airportPrototype);
hashset(c, airportPrototype, "runway", naNewFunc(c, naNewCCode(c, f_airport_runway)));
hashset(c, airportPrototype, "runwaysWithoutReciprocals", naNewFunc(c, naNewCCode(c, f_airport_runwaysWithoutReciprocals)));
hashset(c, airportPrototype, "tostring", naNewFunc(c, naNewCCode(c, f_airport_toString)));
flightplanPrototype = naNewHash(c);
- hashset(c, gcSave, "flightplanProto", flightplanPrototype);
+ naSave(c, flightplanPrototype);
hashset(c, flightplanPrototype, "getWP", naNewFunc(c, naNewCCode(c, f_flightplan_getWP)));
hashset(c, flightplanPrototype, "currentWP", naNewFunc(c, naNewCCode(c, f_flightplan_currentWP)));
hashset(c, flightplanPrototype, "finish", naNewFunc(c, naNewCCode(c, f_flightplan_finish)));
waypointPrototype = naNewHash(c);
- hashset(c, gcSave, "wayptProto", waypointPrototype);
+ naSave(c, waypointPrototype);
hashset(c, waypointPrototype, "navaid", naNewFunc(c, naNewCCode(c, f_waypoint_navaid)));
hashset(c, waypointPrototype, "runway", naNewFunc(c, naNewCCode(c, f_waypoint_runway)));
hashset(c, waypointPrototype, "airport", naNewFunc(c, naNewCCode(c, f_waypoint_airport)));
procedurePrototype = naNewHash(c);
- hashset(c, gcSave, "procedureProto", procedurePrototype);
+ naSave(c, procedurePrototype);
hashset(c, procedurePrototype, "transition", naNewFunc(c, naNewCCode(c, f_procedure_transition)));
hashset(c, procedurePrototype, "route", naNewFunc(c, naNewCCode(c, f_procedure_route)));
fpLegPrototype = naNewHash(c);
- hashset(c, gcSave, "fpLegProto", fpLegPrototype);
+ naSave(c, fpLegPrototype);
hashset(c, fpLegPrototype, "setSpeed", naNewFunc(c, naNewCCode(c, f_leg_setSpeed)));
hashset(c, fpLegPrototype, "setAltitude", naNewFunc(c, naNewCCode(c, f_leg_setAltitude)));
hashset(c, fpLegPrototype, "path", naNewFunc(c, naNewCCode(c, f_leg_path)));