Changeset - r15503:084a4ba274a8
[Not reviewed]
master
0 2 0
rubidium - 14 years ago 2010-07-16 19:32:39
rubidium@openttd.org
(svn r20166) -Fix [FS#3949]: do not scan /data and ~/data (if they happen to be your working directory). If it's the directory where your binary is located it will still scan them.
2 files changed with 43 insertions and 2 deletions:
0 comments (0 inline, 0 general)
readme.txt
Show inline comments
 
@@ -244,24 +244,27 @@ OpenTTD can read inside tar files but it
 
itself.
 
To figure out which libraries you need for an AI you have to start the AI and
 
wait for an error message to pop up. The error message will tell you
 
"couldn't find library 'lib-name'". Download that library and try again.
 

	
 
4.2) OpenTTD directories
 
---- -------------------------------
 

	
 
The required 3rd party files listed in the section 4.1 "(Required) 3rd party files"
 
as well as other non-compulsory extensions (NewGRFs, AI, heightmaps, scenarios) can be
 
placed in a few different locations:
 
	1. The current working directory (from where you started OpenTTD)
 
		For non-Windows operating systems OpenTTD will not scan for files in this
 
		directory if it is your personal directory, i.e. "~/", or when it is the
 
		root directory, i.e. "/".
 
	2. Your personal directory
 
		Windows: C:\My Documents (95, 98, ME)
 
		         C:\Documents and Settings\<username>\My Documents\OpenTTD (2000, XP)
 
		         C:\Users\<username>\Documents\OpenTTD (Vista, 7)
 
		Mac OSX: ~/Documents/OpenTTD
 
		Linux:   ~/.openttd
 
	3. The shared directory
 
		Windows: C:\Documents and Settings\All Users\Shared Documents\OpenTTD (2000, XP)
 
		         C:\Users\Public\Documents\OpenTTD (Vista, 7)
 
		Mac OSX: /Library/Application Support/OpenTTD
 
		Linux:   not available
 
	4. The binary directory (where the OpenTTD executable is)
src/fileio.cpp
Show inline comments
 
@@ -35,33 +35,36 @@
 
/*************************************************/
 

	
 
#define FIO_BUFFER_SIZE 512
 

	
 
struct Fio {
 
	byte *buffer, *buffer_end;             ///< position pointer in local buffer and last valid byte of buffer
 
	size_t pos;                            ///< current (system) position in file
 
	FILE *cur_fh;                          ///< current file handle
 
	const char *filename;                  ///< current filename
 
	FILE *handles[MAX_FILE_SLOTS];         ///< array of file handles we can have open
 
	byte buffer_start[FIO_BUFFER_SIZE];    ///< local buffer when read from file
 
	const char *filenames[MAX_FILE_SLOTS]; ///< array of filenames we (should) have open
 
	char *shortnames[MAX_FILE_SLOTS];///< array of short names for spriteloader's use
 
	char *shortnames[MAX_FILE_SLOTS];      ///< array of short names for spriteloader's use
 
#if defined(LIMITED_FDS)
 
	uint open_handles;                     ///< current amount of open handles
 
	uint usage_count[MAX_FILE_SLOTS];      ///< count how many times this file has been opened
 
#endif /* LIMITED_FDS */
 
};
 

	
 
static Fio _fio;
 

	
 
/** Whether the working directory should be scanned. */
 
static bool _do_scan_working_directory = true;
 

	
 
/* Get current position in file */
 
size_t FioGetPos()
 
{
 
	return _fio.pos + (_fio.buffer - _fio.buffer_end);
 
}
 

	
 
const char *FioGetFilename(uint8 slot)
 
{
 
	return _fio.shortnames[slot];
 
}
 

	
 
void FioSeekTo(size_t pos, int mode)
 
@@ -867,24 +870,51 @@ void ChangeWorkingDirectory(const char *
 
		/* If we want to go to the root, we can't use cd C:, but we must use '/' */
 
		if (s[-1] == ':') chdir("/");
 
#endif
 
		if (chdir(exe) != 0) DEBUG(misc, 0, "Directory with the binary does not exist?");
 
		*s = PATHSEPCHAR;
 
	}
 
#ifdef WITH_COCOA
 
	if (app_bundle != NULL) app_bundle[0] = '.';
 
#endif /* WITH_COCOA */
 
}
 

	
 
/**
 
 * Whether we should scan the working directory.
 
 * It should not be scanned if it's the root or
 
 * the home directory as in both cases a big data
 
 * directory can cause huge amounts of unrelated
 
 * files scanned. Furthermore there are nearly no
 
 * use cases for the home/root directory to have
 
 * OpenTTD directories.
 
 * @return true if it should be scanned.
 
 */
 
bool DoScanWorkingDirectory()
 
{
 
	/* No working directory, so nothing to do. */
 
	if (_searchpaths[SP_WORKING_DIR] == NULL) return false;
 

	
 
	/* Working directory is root, so do nothing. */
 
	if (strcmp(_searchpaths[SP_WORKING_DIR], PATHSEP) == 0) return false;
 

	
 
	/* No personal/home directory, so the working directory won't be that. */
 
	if (_searchpaths[SP_PERSONAL_DIR] == NULL) return true;
 

	
 
	char tmp[MAX_PATH];
 
	snprintf(tmp, lengthof(tmp), "%s%s", _searchpaths[SP_WORKING_DIR], PERSONAL_DIR);
 
	AppendPathSeparator(tmp, MAX_PATH);
 
	return strcmp(tmp, _searchpaths[SP_PERSONAL_DIR]) != 0;
 
}
 

	
 
/**
 
 * Determine the base (personal dir and game data dir) paths
 
 * @param exe the path to the executable
 
 */
 
void DetermineBasePaths(const char *exe)
 
{
 
	char tmp[MAX_PATH];
 
#if defined(__MORPHOS__) || defined(__AMIGA__) || defined(DOS) || defined(OS2) || !defined(WITH_PERSONAL_DIR)
 
	_searchpaths[SP_PERSONAL_DIR] = NULL;
 
#else
 
#ifdef __HAIKU__
 
	BPath path;
 
	find_directory(B_USER_SETTINGS_DIRECTORY, &path);
 
@@ -911,24 +941,26 @@ void DetermineBasePaths(const char *exe)
 
#else
 
	_searchpaths[SP_SHARED_DIR] = NULL;
 
#endif
 

	
 
#if defined(__MORPHOS__) || defined(__AMIGA__)
 
	_searchpaths[SP_WORKING_DIR] = NULL;
 
#else
 
	if (getcwd(tmp, MAX_PATH) == NULL) *tmp = '\0';
 
	AppendPathSeparator(tmp, MAX_PATH);
 
	_searchpaths[SP_WORKING_DIR] = strdup(tmp);
 
#endif
 

	
 
	_do_scan_working_directory = DoScanWorkingDirectory();
 

	
 
	/* Change the working directory to that one of the executable */
 
	ChangeWorkingDirectory(exe);
 
	if (getcwd(tmp, MAX_PATH) == NULL) *tmp = '\0';
 
	AppendPathSeparator(tmp, MAX_PATH);
 
	_searchpaths[SP_BINARY_DIR] = strdup(tmp);
 

	
 
	if (_searchpaths[SP_WORKING_DIR] != NULL) {
 
		/* Go back to the current working directory. */
 
		ChangeWorkingDirectory(_searchpaths[SP_WORKING_DIR]);
 
	}
 

	
 
#if defined(__MORPHOS__) || defined(__AMIGA__) || defined(DOS) || defined(OS2)
 
@@ -951,25 +983,28 @@ char *_personal_dir;
 

	
 
/**
 
 * Acquire the base paths (personal dir and game data dir),
 
 * fill all other paths (save dir, autosave dir etc) and
 
 * make the save and scenario directories.
 
 * @param exe the path from the current path to the executable
 
 */
 
void DeterminePaths(const char *exe)
 
{
 
	DetermineBasePaths(exe);
 

	
 
	Searchpath sp;
 
	FOR_ALL_SEARCHPATHS(sp) DEBUG(misc, 4, "%s added as search path", _searchpaths[sp]);
 
	FOR_ALL_SEARCHPATHS(sp) {
 
		if (sp == SP_WORKING_DIR && !_do_scan_working_directory) continue;
 
		DEBUG(misc, 4, "%s added as search path", _searchpaths[sp]);
 
	}
 

	
 
	if (_config_file != NULL) {
 
		_personal_dir = strdup(_config_file);
 
		char *end = strrchr(_personal_dir, PATHSEPCHAR);
 
		if (end == NULL) {
 
			_personal_dir[0] = '\0';
 
		} else {
 
			end[1] = '\0';
 
		}
 
	} else {
 
		char personal_dir[MAX_PATH];
 
		FioFindFullPath(personal_dir, lengthof(personal_dir), BASE_DIR, "openttd.cfg");
 
@@ -1169,24 +1204,27 @@ static uint ScanTar(FileScanner *fs, con
 
 * @param recursive whether to search recursively
 
 * @return the number of found files, i.e. the number of times that
 
 *         AddFile returned true.
 
 */
 
uint FileScanner::Scan(const char *extension, Subdirectory sd, bool tars, bool recursive)
 
{
 
	Searchpath sp;
 
	char path[MAX_PATH];
 
	TarFileList::iterator tar;
 
	uint num = 0;
 

	
 
	FOR_ALL_SEARCHPATHS(sp) {
 
		/* Don't search in the working directory */
 
		if (sp == SP_WORKING_DIR && !_do_scan_working_directory) continue;
 

	
 
		FioAppendDirectory(path, MAX_PATH, sp, sd);
 
		num += ScanPath(this, extension, path, strlen(path), recursive);
 
	}
 

	
 
	if (tars) {
 
		FOR_ALL_TARS(tar) {
 
			num += ScanTar(this, extension, tar);
 
		}
 
	}
 

	
 
	return num;
 
}
0 comments (0 inline, 0 general)