Skip to content

Commit 472e535

Browse files
kusmadscho
authored andcommitted
core.hideDotFiles: hide '.git' dir by default
At least for cross-platform projects, it makes sense to hide the files starting with a dot, as this is the behavior on Unix/MacOSX. However, at least Eclipse has problems interpreting the hidden flag correctly, so the default is to hide only the .git/ directory. The config setting core.hideDotFiles therefore supports not only 'true' and 'false', but also 'dotGitOnly'. [jes: clarified the commit message, made git init respect the setting by marking the .git/ directory only after reading the config, and added documentation, and rebased on top of current junio/next] Signed-off-by: Erik Faye-Lund <[email protected]> Signed-off-by: Johannes Schindelin <[email protected]>
1 parent 7864e64 commit 472e535

File tree

7 files changed

+79
-0
lines changed

7 files changed

+79
-0
lines changed

Documentation/config.txt

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -269,6 +269,12 @@ See linkgit:git-update-index[1].
269269
+
270270
The default is true (when core.filemode is not specified in the config file).
271271

272+
core.hideDotFiles::
273+
(Windows-only) If true (which is the default), mark newly-created
274+
directories and files whose name starts with a dot as hidden.
275+
If 'dotGitOnly', only the .git/ directory is hidden, but no other
276+
files starting with a dot.
277+
272278
core.ignoreCase::
273279
If true, this option enables various workarounds to enable
274280
Git to work better on filesystems that are not case sensitive,

builtin/init-db.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -405,6 +405,7 @@ int init_db(const char *template_dir, unsigned int flags)
405405
check_repository_format();
406406

407407
reinit = create_default_files(template_dir);
408+
mark_as_git_dir(get_git_dir());
408409

409410
create_object_directory();
410411

cache.h

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -628,6 +628,13 @@ extern int ref_paranoia;
628628
extern char comment_line_char;
629629
extern int auto_comment_line_char;
630630

631+
enum hide_dotfiles_type {
632+
HIDE_DOTFILES_FALSE = 0,
633+
HIDE_DOTFILES_TRUE,
634+
HIDE_DOTFILES_DOTGITONLY,
635+
};
636+
extern enum hide_dotfiles_type hide_dotfiles;
637+
631638
enum branch_track {
632639
BRANCH_TRACK_UNSPECIFIED = -1,
633640
BRANCH_TRACK_NEVER = 0,

compat/mingw.c

Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@
77
#include "../cache.h"
88

99
static const int delay[] = { 0, 1, 10, 20, 40 };
10+
unsigned int _CRT_fmode = _O_BINARY;
1011

1112
int err_win_to_posix(DWORD winerr)
1213
{
@@ -284,13 +285,40 @@ int mingw_rmdir(const char *pathname)
284285
return ret;
285286
}
286287

288+
static int make_hidden(const wchar_t *path)
289+
{
290+
DWORD attribs = GetFileAttributesW(path);
291+
if (SetFileAttributesW(path, FILE_ATTRIBUTE_HIDDEN | attribs))
292+
return 0;
293+
errno = err_win_to_posix(GetLastError());
294+
return -1;
295+
}
296+
297+
void mingw_mark_as_git_dir(const char *dir)
298+
{
299+
wchar_t wdir[MAX_PATH];
300+
if (hide_dotfiles != HIDE_DOTFILES_FALSE && !is_bare_repository())
301+
if (xutftowcs_path(wdir, dir) < 0 || make_hidden(wdir))
302+
warning("Failed to make '%s' hidden", dir);
303+
}
304+
287305
int mingw_mkdir(const char *path, int mode)
288306
{
289307
int ret;
290308
wchar_t wpath[MAX_PATH];
291309
if (xutftowcs_path(wpath, path) < 0)
292310
return -1;
293311
ret = _wmkdir(wpath);
312+
if (!ret && hide_dotfiles == HIDE_DOTFILES_TRUE) {
313+
/*
314+
* In Windows a file or dir starting with a dot is not
315+
* automatically hidden. So lets mark it as hidden when
316+
* such a directory is created.
317+
*/
318+
const char *start = basename((char*)path);
319+
if (*start == '.')
320+
return make_hidden(wpath);
321+
}
294322
return ret;
295323
}
296324

@@ -317,6 +345,17 @@ int mingw_open (const char *filename, int oflags, ...)
317345
if (attrs != INVALID_FILE_ATTRIBUTES && (attrs & FILE_ATTRIBUTE_DIRECTORY))
318346
errno = EISDIR;
319347
}
348+
if ((oflags & O_CREAT) && fd >= 0 &&
349+
hide_dotfiles == HIDE_DOTFILES_TRUE) {
350+
/*
351+
* In Windows a file or dir starting with a dot is not
352+
* automatically hidden. So lets mark it as hidden when
353+
* such a file is created.
354+
*/
355+
const char *start = basename((char*)filename);
356+
if (*start == '.' && make_hidden(wfilename))
357+
warning("Could not mark '%s' as hidden.", filename);
358+
}
320359
return fd;
321360
}
322361

@@ -348,27 +387,39 @@ int mingw_fgetc(FILE *stream)
348387
#undef fopen
349388
FILE *mingw_fopen (const char *filename, const char *otype)
350389
{
390+
int hide = 0;
351391
FILE *file;
352392
wchar_t wfilename[MAX_PATH], wotype[4];
393+
if (hide_dotfiles == HIDE_DOTFILES_TRUE &&
394+
basename((char*)filename)[0] == '.')
395+
hide = access(filename, F_OK);
353396
if (filename && !strcmp(filename, "/dev/null"))
354397
filename = "nul";
355398
if (xutftowcs_path(wfilename, filename) < 0 ||
356399
xutftowcs(wotype, otype, ARRAY_SIZE(wotype)) < 0)
357400
return NULL;
358401
file = _wfopen(wfilename, wotype);
402+
if (file && hide && make_hidden(wfilename))
403+
warning("Could not mark '%s' as hidden.", filename);
359404
return file;
360405
}
361406

362407
FILE *mingw_freopen (const char *filename, const char *otype, FILE *stream)
363408
{
409+
int hide = 0;
364410
FILE *file;
365411
wchar_t wfilename[MAX_PATH], wotype[4];
412+
if (hide_dotfiles == HIDE_DOTFILES_TRUE &&
413+
basename((char*)filename)[0] == '.')
414+
hide = access(filename, F_OK);
366415
if (filename && !strcmp(filename, "/dev/null"))
367416
filename = "nul";
368417
if (xutftowcs_path(wfilename, filename) < 0 ||
369418
xutftowcs(wotype, otype, ARRAY_SIZE(wotype)) < 0)
370419
return NULL;
371420
file = _wfreopen(wfilename, wotype, stream);
421+
if (file && hide && make_hidden(wfilename))
422+
warning("Could not mark '%s' as hidden.", filename);
372423
return file;
373424
}
374425

config.c

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -911,6 +911,15 @@ static int git_default_core_config(const char *var, const char *value)
911911
return 0;
912912
}
913913

914+
if (!strcmp(var, "core.hidedotfiles")) {
915+
if (value && !strcasecmp(value, "dotgitonly")) {
916+
hide_dotfiles = HIDE_DOTFILES_DOTGITONLY;
917+
return 0;
918+
}
919+
hide_dotfiles = git_config_bool(var, value);
920+
return 0;
921+
}
922+
914923
/* Add other config variables here and to Documentation/config.txt. */
915924
return 0;
916925
}

environment.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,7 @@ int merge_log_config = -1;
6464
int precomposed_unicode = -1; /* see probe_utf8_pathname_composition() */
6565
struct startup_info *startup_info;
6666
unsigned long pack_size_limit_cfg;
67+
enum hide_dotfiles_type hide_dotfiles = HIDE_DOTFILES_DOTGITONLY;
6768

6869
#ifndef PROTECT_HFS_DEFAULT
6970
#define PROTECT_HFS_DEFAULT 0

git-compat-util.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -883,4 +883,8 @@ struct tm *git_gmtime_r(const time_t *, struct tm *);
883883
# define SHELL_PATH "/bin/sh"
884884
#endif
885885

886+
#ifndef mark_as_git_dir
887+
#define mark_as_git_dir(x) /* noop */
888+
#endif
889+
886890
#endif

0 commit comments

Comments
 (0)