+static naRef f_findDataDir(naContext c, naRef me, int argc, naRef* args)
+{
+ if(argc != 1 || !naIsString(args[0]))
+ naRuntimeError(c, "bad arguments to findDataDir()");
+
+ SGPath p = globals->find_data_dir(naStr_data(args[0]));
+ const char* pdata = p.c_str();
+ return naStr_fromdata(naNewString(c), const_cast<char*>(pdata), strlen(pdata));
+}
+
+class NasalCommand : public SGCommandMgr::Command
+{
+public:
+ NasalCommand(FGNasalSys* sys, naRef f, const std::string& name) :
+ _sys(sys),
+ _func(f),
+ _name(name)
+ {
+ globals->get_commands()->addCommandObject(_name, this);
+ _gcRoot = sys->gcSave(f);
+ }
+
+ virtual ~NasalCommand()
+ {
+ _sys->gcRelease(_gcRoot);
+ }
+
+ virtual bool operator()(const SGPropertyNode* aNode)
+ {
+ _sys->setCmdArg(const_cast<SGPropertyNode*>(aNode));
+ naRef args[1];
+ args[0] = _sys->wrappedPropsNode(const_cast<SGPropertyNode*>(aNode));
+
+ _sys->callMethod(_func, naNil(), 1, args, naNil() /* locals */);
+
+ return true;
+ }
+
+private:
+ FGNasalSys* _sys;
+ naRef _func;
+ int _gcRoot;
+ std::string _name;
+};
+
+static naRef f_addCommand(naContext c, naRef me, int argc, naRef* args)
+{
+ if(argc != 2 || !naIsString(args[0]) || !naIsFunc(args[1]))
+ naRuntimeError(c, "bad arguments to addcommand()");
+
+ nasalSys->addCommand(args[1], naStr_data(args[0]));
+ return naNil();
+}
+
+static naRef f_removeCommand(naContext c, naRef me, int argc, naRef* args)
+{
+ if ((argc < 1) || !naIsString(args[0]))
+ naRuntimeError(c, "bad argument to removecommand()");
+
+ globals->get_commands()->removeCommand(naStr_data(args[0]));
+ return naNil();
+}
+
+static naRef f_open(naContext c, naRef me, int argc, naRef* args)
+{
+ FILE* f;
+ naRef file = argc > 0 ? naStringValue(c, args[0]) : naNil();
+ naRef mode = argc > 1 ? naStringValue(c, args[1]) : naNil();
+ if(!naStr_data(file)) naRuntimeError(c, "bad argument to open()");
+ const char* modestr = naStr_data(mode) ? naStr_data(mode) : "rb";
+ std::string filename = fgValidatePath(naStr_data(file),
+ strcmp(modestr, "rb") && strcmp(modestr, "r"));
+ if(filename.empty()) {
+ naRuntimeError(c, "open(): reading/writing '%s' denied "
+ "(unauthorized access)", naStr_data(file));
+ return naNil();
+ }
+ f = fopen(filename.c_str(), modestr);
+ if(!f) naRuntimeError(c, strerror(errno));
+ return naIOGhost(c, f);
+}
+