summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorMaxime Coste <frrrwww@gmail.com>2012-01-29 22:24:43 +0000
committerMaxime Coste <frrrwww@gmail.com>2012-01-29 22:24:43 +0000
commit73a8950e73ecb8769848c2c9b993d0d88d7c9fef (patch)
treeffb05898bab9463731b57a38802577fe35c5459d /src
parent589b8e68bbe440bf88e6cb2d46138e01b7ec8651 (diff)
File: parse_filename function which handle ~ and environment variable in filenames
Diffstat (limited to 'src')
-rw-r--r--src/file.cc34
-rw-r--r--src/file.hh4
-rw-r--r--src/main.cc5
3 files changed, 41 insertions, 2 deletions
diff --git a/src/file.cc b/src/file.cc
index 2e105d16..eb01081d 100644
--- a/src/file.cc
+++ b/src/file.cc
@@ -13,6 +13,40 @@
namespace Kakoune
{
+bool isidentifier(char c)
+{
+ return std::isalnum(c) or c == '_';
+}
+
+std::string parse_filename(const std::string& filename)
+{
+ if (filename.length() > 2 and filename[0] == '~' and filename[1] == '/')
+ return parse_filename("$HOME/" + filename.substr(2));
+
+ size_t pos = 0;
+ std::string result;
+ for (size_t i = 0; i < filename.length(); ++i)
+ {
+ if (filename[i] == '$' and (i == 0 or filename[i-1] != '\\'))
+ {
+ result += filename.substr(pos, i - pos);
+ size_t end = i+1;
+ while (end != filename.length() and isidentifier(filename[end]))
+ ++end;
+ std::string var_name = filename.substr(i+1, end - i - 1);
+ const char* var_value = getenv(var_name.c_str());
+ if (var_value)
+ result += var_value;
+
+ pos = end;
+ }
+ }
+ if (pos != filename.length())
+ result += filename.substr(pos);
+
+ return result;
+}
+
std::string read_file(const std::string& filename)
{
int fd = open(filename.c_str(), O_RDONLY);
diff --git a/src/file.hh b/src/file.hh
index b6b7fc6a..3f1c599b 100644
--- a/src/file.hh
+++ b/src/file.hh
@@ -23,6 +23,10 @@ struct file_not_found : file_access_error
};
class Buffer;
+
+// parse ~/ and $env values in filename and returns the translated filename
+std::string parse_filename(const std::string& filename);
+
std::string read_file(const std::string& filename);
Buffer* create_buffer_from_file(const std::string& filename);
void write_buffer_to_file(const Buffer& buffer, const std::string& filename);
diff --git a/src/main.cc b/src/main.cc
index f1a6cdef..d0164737 100644
--- a/src/main.cc
+++ b/src/main.cc
@@ -535,7 +535,8 @@ void write_buffer(const CommandParameters& params, const Context& context)
throw wrong_argument_count();
Buffer& buffer = context.window().buffer();
- std::string filename = params.empty() ? buffer.name() : params[0];
+ std::string filename = params.empty() ? buffer.name()
+ : parse_filename(params[0]);
write_buffer_to_file(buffer, filename);
buffer.notify_saved();
@@ -695,7 +696,7 @@ void exec_commands_in_file(const CommandParameters& params,
if (params.size() != 1)
throw wrong_argument_count();
- std::string file_content = read_file(params[0]);
+ std::string file_content = read_file(parse_filename(params[0]));
CommandManager& cmd_manager = CommandManager::instance();
size_t pos = 0;