curl: support XDG_CONFIG_HOME to find .curlrc

Added test433 to verify. Updated documentation.

Reviewed-by: Jay Satiro
Suggested-by: Eli Schwartz
Fixes #5829
Closes #5837
This commit is contained in:
Daniel Stenberg 2020-08-21 23:40:12 +02:00
parent 98c94596f5
commit 4be1f8dc01
No known key found for this signature in database
GPG Key ID: 5CC908FDB71E12C2
7 changed files with 120 additions and 12 deletions

View File

@ -34,13 +34,19 @@ When curl is invoked, it (unless --disable is used) checks for a default
config file and uses it if found. The default config file is checked for in
the following places in this order:
1) curl tries to find the "home dir": It first checks for the CURL_HOME and
then the HOME environment variables. Failing that, it uses getpwuid() on
Unix-like systems (which returns the home dir given the current user in your
system). On Windows, it then checks for the APPDATA variable, or as a last
resort the '%USERPROFILE%\\Application Data'.
1) Use the CURL_HOME environment variable if set
2) On windows, if there is no .curlrc file in the home dir, it checks for one
2) Use the XDG_CONFIG_HOME environment variable if set (Added in 7.73.0)
3) Use the HOME environment variable if set
4) Non-windows: use getpwuid to find the home directory
5) Windows: use APPDATA if set
6) Windows: use "USERPROFILE\Application Data" if set
7) On windows, if there is no .curlrc file in the home dir, it checks for one
in the same dir the curl executable is placed. On Unix-like systems, it will
simply try to load .curlrc from the determined home dir.

View File

@ -25,6 +25,13 @@
# include <pwd.h>
#endif
#ifdef HAVE_SYS_STAT_H
#include <sys/stat.h>
#endif
#ifdef HAVE_FCNTL_H
#include <fcntl.h>
#endif
#include <curl/mprintf.h>
#include "tool_homedir.h"
@ -45,7 +52,27 @@ static char *GetEnv(const char *variable)
}
/* return the home directory of the current user as an allocated string */
char *homedir(void)
/*
* The original logic found a home dir to use (by checking a range of
* environment variables and last using getpwuid) and returned that for the
* parent to use.
*
* With the XDG_CONFIG_HOME support (added much later than the other), this
* variable is treated differently in order to not ruin existing installations
* even if this environment variable is set. If this variable is set, and a
* file name is set to check, then only if that file name exists in that
* directory will it be returned as a "home directory".
*
* 1. use CURL_HOME if set
* 2. use XDG_CONFIG_HOME if set and fname is present
* 3. use HOME if set
* 4. Non-windows: use getpwuid
* 5. Windows: use APPDATA if set
* 6. Windows: use "USERPROFILE\Application Data" is set
*/
char *homedir(const char *fname)
{
char *home;
@ -53,6 +80,22 @@ char *homedir(void)
if(home)
return home;
if(fname) {
home = GetEnv("XDG_CONFIG_HOME");
if(home) {
char *c = curl_maprintf("%s" DIR_CHAR "%s", home, fname);
if(c) {
int fd = open(c, O_RDONLY);
curl_free(c);
if(fd >= 0) {
close(fd);
return home;
}
}
free(home);
}
}
home = GetEnv("HOME");
if(home)
return home;

View File

@ -7,7 +7,7 @@
* | (__| |_| | _ <| |___
* \___|\___/|_| \_\_____|
*
* Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
* Copyright (C) 1998 - 2020, Daniel Stenberg, <daniel@haxx.se>, et al.
*
* This software is licensed as described in the file COPYING, which
* you should have received as part of this distribution. The terms
@ -23,6 +23,6 @@
***************************************************************************/
#include "tool_setup.h"
char *homedir(void);
char *homedir(const char *fname);
#endif /* HEADER_CURL_TOOL_HOMEDIR_H */

View File

@ -1696,7 +1696,7 @@ static CURLcode single_transfer(struct GlobalConfig *global,
char *home;
char *file;
result = CURLE_FAILED_INIT;
home = homedir();
home = homedir(NULL);
if(home) {
file = aprintf("%s/.ssh/known_hosts", home);
if(file) {

View File

@ -82,7 +82,7 @@ int parseconfig(const char *filename, struct GlobalConfig *global)
if(!filename || !*filename) {
/* NULL or no file name attempts to load .curlrc from the homedir! */
char *home = homedir(); /* portable homedir finder */
char *home = homedir(".curlrc");
#ifndef WIN32
if(home) {
pathalloc = curl_maprintf("%s%s.curlrc", home, DIR_CHAR);

View File

@ -66,7 +66,7 @@ test393 test394 test395 test396 test397 \
test400 test401 test402 test403 test404 test405 test406 test407 test408 \
test409 \
\
test430 test431 test432 \
test430 test431 test432 test433 \
\
test490 test491 test492 \
\

59
tests/data/test433 Normal file
View File

@ -0,0 +1,59 @@
<testcase>
<info>
<keywords>
--config
</keywords>
</info>
#
# Server-side
<reply>
<data>
HTTP/1.1 200 OK
Content-Length: 6
Content-Type: text/1
-foo-
</data>
</reply>
#
# Client-side
<client>
<file1 name="log/.curlrc">
--next
header = "a: a"
data = "curlrc read"
</file1>
<server>
http
</server>
<setenv>
XDG_CONFIG_HOME=%PWD/log
</setenv>
<name>
Verify XDG_CONFIG_HOME use to find .curlrc
</name>
<command>
%HOSTIP:%HTTPPORT/433
</command>
</client>
#
# Verify data after the test has been "shot"
<verify>
<strip>
^User-Agent:.*
</strip>
<protocol nonewline="yes">
POST /433 HTTP/1.1
Host: %HOSTIP:%HTTPPORT
Accept: */*
a: a
Content-Length: 11
Content-Type: application/x-www-form-urlencoded
curlrc read
</protocol>
</verify>
</testcase>