diff options
author | Adam <Adam@anope.org> | 2011-08-08 00:32:09 -0400 |
---|---|---|
committer | Adam <Adam@anope.org> | 2011-08-08 00:32:09 -0400 |
commit | c4da49683406f15f591e3b98a0e30f434c96e100 (patch) | |
tree | c3d69190d5c3e4c60f6ff394dcc97ee12db6a2d8 /src/modulemanager.cpp | |
parent | ade92395a0f08b125b60fbbd488eecb5c3258e76 (diff) |
Copy modules to the runtime directory in one big read/write if we can instead of this 1 byte at a time thing, significantly improves startup loading time.
Diffstat (limited to 'src/modulemanager.cpp')
-rw-r--r-- | src/modulemanager.cpp | 57 |
1 files changed, 31 insertions, 26 deletions
diff --git a/src/modulemanager.cpp b/src/modulemanager.cpp index 8f5e15146..82f7cec24 100644 --- a/src/modulemanager.cpp +++ b/src/modulemanager.cpp @@ -84,45 +84,50 @@ void ModuleManager::LoadModuleList(std::list<Anope::string> &ModuleList) static ModuleReturn moduleCopyFile(const Anope::string &name, Anope::string &output) { Anope::string input = services_dir + "/modules/" + name + ".so"; - FILE *source = fopen(input.c_str(), "rb"); - if (!source) - return MOD_ERR_NOEXIST; + int source = open(input.c_str(), O_RDONLY); + if (source == -1) + return MOD_ERR_NOEXIST; + + struct stat s; + if (stat(input.c_str(), &s) == -1) + return MOD_ERR_NOEXIST; + else if (!S_ISREG(s.st_mode)) + return MOD_ERR_NOEXIST; + char *tmp_output = strdup(output.c_str()); -#ifndef _WIN32 - int srcfp = mkstemp(tmp_output); - if (srcfp == -1) -#else - if (!mktemp(tmp_output)) -#endif + int target = mkstemp(tmp_output); + if (target == -1) { free(tmp_output); - fclose(source); + close(source); return MOD_ERR_FILE_IO; } output = tmp_output; - free(tmp_output); // XXX + free(tmp_output); Log(LOG_DEBUG) << "Runtime module location: " << output; - FILE *target; -#ifndef _WIN32 - target = fdopen(srcfp, "w"); -#else - target = fopen(output.c_str(), "wb"); -#endif - if (!target) + char *buffer = new char[s.st_size]; + bool err = false; + for (;;) { - fclose(source); - return MOD_ERR_FILE_IO; + int read_len = read(source, buffer, s.st_size); + if (read_len <= 0) + break; + int writ_len = write(target, buffer, read_len); + if (writ_len < 0) + { + err = true; + break; + } } - - int ch; - while ((ch = fgetc(source)) != EOF) - fputc(ch, target); - fclose(source); - if (fclose(target)) + delete [] buffer; + + close(source); + if (close(target) == -1 || err == true) return MOD_ERR_FILE_IO; + return MOD_ERR_OK; } |