summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/filelist.c28
-rw-r--r--src/filelist.h1
-rw-r--r--src/options.c21
-rw-r--r--src/slideshow.c2
-rw-r--r--src/thumbnail.c1
-rw-r--r--src/wallpaper.h3
6 files changed, 51 insertions, 5 deletions
diff --git a/src/filelist.c b/src/filelist.c
index ae8d7b2..9d8b38a 100644
--- a/src/filelist.c
+++ b/src/filelist.c
@@ -28,6 +28,10 @@ CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
#include <libexif/exif-data.h>
#endif
+#ifdef HAVE_LIBCURL
+#include <curl/curl.h>
+#endif
+
#include "feh.h"
#include "filelist.h"
#include "signals.h"
@@ -678,3 +682,27 @@ void feh_save_filelist()
free(tmpname);
return;
}
+
+#ifdef HAVE_LIBCURL
+
+char *feh_http_unescape(char *url)
+{
+ CURL *curl = curl_easy_init();
+ if (!curl) {
+ return NULL;
+ }
+ char *tmp_url = curl_easy_unescape(curl, url, 0, NULL);
+ char *new_url = estrdup(tmp_url);
+ curl_free(tmp_url);
+ curl_easy_cleanup(curl);
+ return new_url;
+}
+
+#else
+
+char *feh_http_unescape(char *url)
+{
+ return NULL;
+}
+
+#endif
diff --git a/src/filelist.h b/src/filelist.h
index e24a6a6..ff0645e 100644
--- a/src/filelist.h
+++ b/src/filelist.h
@@ -97,6 +97,7 @@ gib_list *feh_read_filelist(char *filename);
char *feh_absolute_path(char *path);
gib_list *feh_file_remove_from_list(gib_list * list, gib_list * l);
void feh_save_filelist();
+char *feh_http_unescape(char * url);
int feh_cmp_name(void *file1, void *file2);
int feh_cmp_dirname(void *file1, void *file2);
diff --git a/src/options.c b/src/options.c
index 0bc1a5e..4744bb0 100644
--- a/src/options.c
+++ b/src/options.c
@@ -859,11 +859,26 @@ static void feh_parse_option_array(int argc, char **argv, int finalrun)
*/
if (opt.start_list_at && path_is_url(opt.start_list_at) && (strlen(opt.start_list_at) <= 8 || strncmp(opt.start_list_at, "file:///", 8) != 0)) {
add_file_to_filelist_recursively(opt.start_list_at, FILELIST_FIRST);
+ /*
+ * Otherwise, make "feh --start-at dir/file.jpg" behave like
+ * "feh --start-at dir/file.jpg dir".
+ */
} else if (opt.start_list_at && strrchr(opt.start_list_at, '/')) {
+ /*
+ * feh can't candle urlencoded path components ("some%20dir" etc).
+ * Use libcurl to unescape them if --start-at is file://...
+ */
if (strlen(opt.start_list_at) > 8 && strncmp(opt.start_list_at, "file:///", 8) == 0) {
- char *start_at_path = estrdup(opt.start_list_at + 7);
- free(opt.start_list_at);
- opt.start_list_at = start_at_path;
+ char *unescaped_path = feh_http_unescape(opt.start_list_at);
+ if (unescaped_path != NULL) {
+ free(opt.start_list_at);
+ opt.start_list_at = estrdup(unescaped_path + 7);
+ free(unescaped_path);
+ } else {
+ char *new_path = estrdup(opt.start_list_at + 7);
+ free(opt.start_list_at);
+ opt.start_list_at = new_path;
+ }
}
char *target_directory = estrdup(opt.start_list_at);
char *filename_start = strrchr(target_directory, '/');
diff --git a/src/slideshow.c b/src/slideshow.c
index 3a3cd0a..9154d2d 100644
--- a/src/slideshow.c
+++ b/src/slideshow.c
@@ -57,6 +57,7 @@ void init_slideshow_mode(void)
// Try finding an exact filename match first
for (; l && opt.start_list_at; l = l->next) {
if (!strcmp(opt.start_list_at, FEH_FILE(l->data)->filename)) {
+ free(opt.start_list_at);
opt.start_list_at = NULL;
break;
}
@@ -83,6 +84,7 @@ void init_slideshow_mode(void)
current_filename = FEH_FILE(l->data)->filename;
}
if (!strcmp(start_at_filename, current_filename)) {
+ free(opt.start_list_at);
opt.start_list_at = NULL;
break;
}
diff --git a/src/thumbnail.c b/src/thumbnail.c
index e7b05a8..9781027 100644
--- a/src/thumbnail.c
+++ b/src/thumbnail.c
@@ -411,6 +411,7 @@ void init_thumbnail_mode(void)
else if (opt.start_list_at) {
for (l = thumbnails; l; l = l->next) {
if (!strcmp(opt.start_list_at, FEH_THUMB(l->data)->file->filename)) {
+ free(opt.start_list_at);
opt.start_list_at = NULL;
feh_thumbnail_select(winwid, FEH_THUMB(l->data));
break;
diff --git a/src/wallpaper.h b/src/wallpaper.h
index cf52d2d..77769f8 100644
--- a/src/wallpaper.h
+++ b/src/wallpaper.h
@@ -42,7 +42,7 @@ CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
extern Window ipc_win;
extern Atom ipc_atom;
-_XFUNCPROTOBEGIN extern Window enl_ipc_get_win(void);
+extern Window enl_ipc_get_win(void);
extern void enl_ipc_send(char *);
extern char *enl_wait_for_reply(void);
extern char *enl_ipc_get(const char *);
@@ -53,5 +53,4 @@ extern int feh_wm_get_num_desks(void);
extern signed char feh_wm_get_wm_is_e(void);
void feh_wm_set_bg_filelist(unsigned char bgmode);
-_XFUNCPROTOEND
#endif