Project::OSiRiON - Git repositories
Project::OSiRiON
News . About . Screenshots . Downloads . Forum . Wiki . Tracker . Git
summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/client/console.cc4
-rw-r--r--src/client/keyboard.cc4
-rw-r--r--src/client/video.cc4
-rw-r--r--src/core/application.cc12
-rw-r--r--src/filesystem/diskfile.cc44
-rw-r--r--src/filesystem/filesystem.cc145
-rw-r--r--src/filesystem/filesystem.h26
-rw-r--r--src/sys/sys.cc14
-rw-r--r--src/sys/sys.h3
9 files changed, 169 insertions, 87 deletions
diff --git a/src/client/console.cc b/src/client/console.cc
index ddcaa32..60e2a7f 100644
--- a/src/client/console.cc
+++ b/src/client/console.cc
@@ -190,7 +190,7 @@ void Console::save_history()
if (history.size() <= 1)
return;
- std::string filename(filesystem::writedir);
+ std::string filename(filesystem::writedir());
filename.append("history.txt");
std::ofstream ofs(filename.c_str());
@@ -211,7 +211,7 @@ void Console::save_history()
void Console::load_history()
{
- std::string filename(filesystem::writedir);
+ std::string filename(filesystem::writedir());
filename.append("history.txt");
std::ifstream ifs(filename.c_str(), std::ifstream::in);
diff --git a/src/client/keyboard.cc b/src/client/keyboard.cc
index 420d1bb..1ebba12 100644
--- a/src/client/keyboard.cc
+++ b/src/client/keyboard.cc
@@ -229,7 +229,7 @@ Keyboard::~Keyboard()
void Keyboard::save_binds()
{
- std::string filename(filesystem::writedir);
+ std::string filename(filesystem::writedir());
filename.append("binds.cfg");
std::ofstream ofs(filename.c_str());
@@ -269,7 +269,7 @@ void Keyboard::save_binds()
void Keyboard::load_binds()
{
- std::string filename(filesystem::writedir);
+ std::string filename(filesystem::writedir());
filename.append("binds.cfg");
std::ifstream ifs(filename.c_str(), std::ifstream::in);
diff --git a/src/client/video.cc b/src/client/video.cc
index 56514a9..ceea25d 100644
--- a/src/client/video.cc
+++ b/src/client/video.cc
@@ -158,7 +158,7 @@ void screenshot()
std::string filename;
// make sure the screenshots folder exists
- filename.assign(filesystem::writedir);
+ filename.assign(filesystem::writedir());
filename.append("screenshots/");
sys::mkdir(filename);
@@ -174,7 +174,7 @@ void screenshot()
shortname.insert(0, "screenshots/osirion");
shortname.append(".tga");
- filename.assign(filesystem::writedir);
+ filename.assign(filesystem::writedir());
filename.append(shortname);
FILE *handle = fopen(filename.c_str(), "r");
diff --git a/src/core/application.cc b/src/core/application.cc
index 4d1ef86..5cf4d66 100644
--- a/src/core/application.cc
+++ b/src/core/application.cc
@@ -139,7 +139,7 @@ void Application::init(int count, char **arguments)
con_debug << "Debug messages enabled\n";
con_print << "^BInitializing core...\n";
- filesystem::init();
+ filesystem::init("base", "");
CommandBuffer::init();
@@ -328,7 +328,7 @@ void Application::frame(float seconds)
void Application::save_config()
{
- std::string filename(filesystem::writedir);
+ std::string filename(filesystem::writedir());
if (!Cvar::sv_dedicated->value())
filename.append("client.cfg");
else
@@ -350,15 +350,17 @@ void Application::save_config()
ofs << "# this file is automaticly generated" << std::endl;
for (Cvar::Registry::iterator it = Cvar::registry().begin(); it != Cvar::registry().end(); it++) {
- if (((*it).second->flags() & Cvar::Archive) == Cvar::Archive)
+ if (((*it).second->flags() & Cvar::Archive) == Cvar::Archive) {
+ ofs << "# " << (*it).first << " " << (*it).second->info() << std::endl;
ofs << "set " << (*it).first << " " << (*it).second->str() << std::endl;
+ }
}
ofs.close();
}
void Application::load_config()
{
- std::string filename(filesystem::writedir);
+ std::string filename(filesystem::writedir());
if (!Cvar::sv_dedicated->value())
filename.append("client.cfg");
else
@@ -387,7 +389,7 @@ void Application::load_autoexec()
if (Cvar::sv_dedicated->value())
return;
- std::string filename(filesystem::writedir);
+ std::string filename(filesystem::writedir());
filename.append("autoexec.cfg");
std::ifstream ifs(filename.c_str(), std::ifstream::in);
diff --git a/src/filesystem/diskfile.cc b/src/filesystem/diskfile.cc
index a01a327..56e2727 100644
--- a/src/filesystem/diskfile.cc
+++ b/src/filesystem/diskfile.cc
@@ -4,6 +4,7 @@
the terms of the GNU General Public License version 2
*/
+#include "filesystem/filesystem.h"
#include "filesystem/diskfile.h"
namespace filesystem {
@@ -27,46 +28,19 @@ bool DiskFile::open(const char *filename)
}
file_name.assign(filename);
- std::string fn;
-
- // if moddir is set, try the mods subdir first
- if (moddir.size()) {
- // try homedir + moddir
- file_path = homedir;
- file_path.append(moddir);
- fn = file_path;
- fn.append(filename);
- diskfile_handle = fopen(fn.c_str(), "rb");
- if (diskfile_handle)
- return true;
+ file_path.clear();
- // try datadir + moddir
- file_path = datadir;
- file_path.append(moddir);
- fn = file_path;
+ for (SearchPath::iterator path = searchpath().begin(); path != searchpath().end(); path++) {
+ std::string fn((*path));
fn.append(filename);
+
diskfile_handle = fopen(fn.c_str(), "rb");
- if (diskfile_handle)
+ if (diskfile_handle) {
+ file_path.assign((*path));
return true;
- }
- // try homedir + basedir
- file_path = homedir;
- file_path.append(basedir);
- fn = file_path;
- fn.append(filename);
- diskfile_handle = fopen(fn.c_str(), "rb");
- if (diskfile_handle)
- return true;
+ }
+ }
- // try datadir + basedir
- file_path = datadir;
- file_path.append(basedir);
- fn = file_path;
- fn.append(filename);
- diskfile_handle = fopen(fn.c_str(), "rb");
- if (diskfile_handle)
- return true;
-
//con_error << "Could not open " << filename << std::endl;
return false;
}
diff --git a/src/filesystem/filesystem.cc b/src/filesystem/filesystem.cc
index dd694ee..1cb13e9 100644
--- a/src/filesystem/filesystem.cc
+++ b/src/filesystem/filesystem.cc
@@ -5,6 +5,7 @@
*/
// project headers
+#include <list>
#include "filesystem/filesystem.h"
#include "filesystem/diskfile.h"
@@ -14,49 +15,139 @@
namespace filesystem
{
-std::string datadir = "";
-std::string homedir = "";
-std::string basedir = "";
-std::string moddir = "";
-std::string writedir = "";
+SearchPath filesystem_searchpath;
+std::string filesystem_basename;
+std::string filesystem_modname;
-void init()
+std::string filesystem_homedir;
+std::string filesystem_writedir;
+std::string filesystem_datadir;
+
+std::string const & writedir()
{
- con_print << "^BInitializing filesystem..." << std::endl;
+ return filesystem_writedir;
+}
- // initialize game data locations
- // FIXME datadir should by set by ./configure and read from config.h
- datadir = "./data/";
+std::string const & homedir()
+{
+ return filesystem_homedir;
+}
- // FIXME a local or remote game module must be able to set these
- basedir = "base/";
- moddir = "";
+SearchPath & searchpath()
+{
+ return filesystem_searchpath;
+}
+void init(std::string const & basename, std::string const & modname)
+{
+ con_print << "^BInitializing filesystem..." << std::endl;
+
+ // clear everything
+ filesystem_searchpath.clear();
+ filesystem_basename.assign(basename);
+ if (!filesystem_basename.size())
+ filesystem_basename.assign("base");
+
+ filesystem_modname.assign(modname);
#ifndef _WIN32
- homedir = getenv("HOME");
- homedir = homedir + "/.osirion/";
+ filesystem_homedir.assign(getenv("HOME"));
+ filesystem_homedir.append("/.osirion/");
#else
// FIXME win32
- homedir = "./home/";
+ filesystem_homedir.assign("./home/");
#endif
-
- sys::mkdir(homedir);
- sys::mkdir(homedir+basedir);
-
- writedir = homedir;
- if (moddir.size()) {
- writedir.append(moddir);
- } else
- writedir.append(basedir);
- sys::mkdir(writedir);
+ std::string current_datadir("data/");
+ std::string package_datadir(PACKAGE_DATADIR);
+ std::string dir;
- con_print << " files are created in " << writedir << std::endl;
+ // set writedir depending on modname and add home paths to the searchpath
+ filesystem_writedir.assign(filesystem_homedir);
+ if (filesystem_modname.size()) {
+ // append modname to writedir
+ filesystem_writedir.append(filesystem_modname);
+ filesystem_writedir += '/';
+ } else {
+ // append basename to writedir
+ filesystem_writedir.append(filesystem_basename);
+ filesystem_writedir += '/';
+ }
+
+ sys::mkdir(filesystem_homedir);
+ sys::mkdir(filesystem_writedir);
+
+
+ // modname search path
+ if (filesystem_modname.size()) {
+ // HOME/modname
+ dir.assign(filesystem_homedir + filesystem_modname);
+ if (sys::isdirectory(dir)) {
+ dir += '/';
+ filesystem_searchpath.push_back(dir);
+ }
+
+ // CURRENT/data/modname
+ dir.assign(current_datadir + filesystem_modname);
+ if (sys::isdirectory(dir)) {
+ dir += '/';
+ filesystem_searchpath.push_back(dir);
+ }
+
+ // PACKAGE_DATADIR/modname
+ std::string dir(package_datadir + '/' + filesystem_modname);
+ if (sys::isdirectory(dir)) {
+ dir += '/';
+ filesystem_searchpath.push_back(dir);
+ }
+ }
+
+ // basename search path
+ // HOME/basename
+ dir.assign(filesystem_homedir + filesystem_basename);
+ if (sys::isdirectory(dir)) {
+ dir += '/';
+ filesystem_searchpath.push_back(dir);
+ }
+
+ // PACKAGE_DATADIR/basename
+ dir.assign(package_datadir + '/' + filesystem_basename);
+ if (sys::isdirectory(dir)) {
+ dir += '/';
+ filesystem_searchpath.push_back(dir);
+ filesystem_datadir.assign(dir);
+ } else {
+ // CURRENT/data/basename
+ dir.assign(current_datadir + filesystem_basename);
+ if (sys::isdirectory(dir)) {
+ dir += '/';
+ filesystem_searchpath.push_back(dir);
+ filesystem_datadir.assign(dir);
+ } else {
+ con_warn << "data/" << basename << " not found!" << std::endl;
+ }
+ }
+
+ // print search path
+ for (SearchPath::iterator path = filesystem_searchpath.begin(); path != filesystem_searchpath.end(); ++path) {
+ con_print << " " << (*path) << std::endl;
+ }
+ con_print << " " << filesystem_searchpath.size() << " directories added to searchpath" << std::endl;
+
+ // create writedir
+ con_print << " files are created in " << filesystem_writedir << std::endl;
}
void shutdown()
{
con_print << "^BShutting down filesystem..." << std::endl;
+
+ filesystem_searchpath.clear();
+ filesystem_basename.clear();
+
+ filesystem_modname.clear();
+ filesystem_homedir.clear();
+
+ filesystem_writedir.clear();
}
File *open(const char *filename)
diff --git a/src/filesystem/filesystem.h b/src/filesystem/filesystem.h
index 83e93c0..f8740d1 100644
--- a/src/filesystem/filesystem.h
+++ b/src/filesystem/filesystem.h
@@ -11,37 +11,35 @@
#include "filesystem/diskfile.h"
#include <string>
+#include <list>
/// The filesystem namespace contains classes and functions for common file operations.
/** filesystem is a core subsystem
*/
namespace filesystem {
-/// location of the main data files, includes trailing /
-extern std::string datadir;
+typedef std::list<std::string> SearchPath;
-/// location of the personal data files, includes trailing /
-extern std::string homedir;
-
-/// writeable location
-extern std::string writedir;
-
-/// subdirectory with the base data files, includes trailing /
-extern std::string basedir;
-
-/// subdirectory for the current mod, includes trailing /
-extern std::string moddir;
+SearchPath & searchpath();
/// initialize the filesystem subsystem
-void init();
+void init(std::string const & basename, std::string const & modname);
/// shutdown the filesystem subsystem
void shutdown();
+/// current home directory e.g. ~/.osirion/
+std::string const & homedir();
+
+/// current write directory e.g. ~/.osirion/base/
+std::string const & writedir();
+
/// open a file and return a pointer to a File instance
File *open(const char *filename);
+
/// open a file and return a pointer to a File instance
File *open(const std::string &filename);
+
/// close and delete a file instance
void close(File *file);
diff --git a/src/sys/sys.cc b/src/sys/sys.cc
index da9b08d..9526166 100644
--- a/src/sys/sys.cc
+++ b/src/sys/sys.cc
@@ -27,6 +27,20 @@
namespace sys {
+bool isdirectory(std::string const &path)
+{
+ struct stat path_stat;
+ memset(&path_stat, 0, sizeof(path_stat));
+ if (stat(path.c_str(), &path_stat) != 0)
+ return false;
+
+ if (path_stat.st_mode & S_IFDIR) {
+ return true;
+ }
+
+ return false;
+}
+
void mkdir(std::string const &path)
{
#ifdef _WIN32
diff --git a/src/sys/sys.h b/src/sys/sys.h
index e455b82..66040f0 100644
--- a/src/sys/sys.h
+++ b/src/sys/sys.h
@@ -21,6 +21,9 @@ namespace sys
{
typedef void (* signalfunc)(int signum);
+/// check if a path exists and if it is a directory
+bool isdirectory(std::string const &path);
+
/// create a directory
void mkdir(std::string const &path);