Diff options
Diffstat (limited to '')
-rw-r--r--source/scan-tree.c66
1 file changed, 32 insertions, 34 deletions
diff --git a/source/scan-tree.c b/source/scan-tree.c
index 10f661d..ec991e0 100644
--- a/source/scan-tree.c
+++ b/source/scan-tree.c
@@ -1,11 +1,7 @@
/*
- * Discovery of repositories on disk, so that an administrator can point cgit
- * at a directory instead of naming every repository in cgitrc. The tree below
- * that directory is walked for bare repositories and working trees, or when a
- * project list is configured only the paths it names are visited. Every
- * repository found is registered under its path relative to the root of the
- * scan, with owner, description and section taken from the files git keeps
- * beside it, and a cgitrc in the repository has the last word over all of them.
+ * Every repository found takes its owner, description and section from the
+ * files git keeps beside it, and a cgitrc in the repository has the last word
+ * over all of them.
*/
#include "cgit.h"
@@ -154,7 +150,6 @@ static void add_repo(const char *base, struct strbuf *path)
size_t pathlen;
struct strbuf relpath = STRBUF_INIT;
char *comma;
- size_t desc_size;
if (stat(path->buf, &st)) {
fprintf(stderr, "[cgit] Unable to access %s: %s (%d)\n", path->buf, strerror(errno), errno);
@@ -185,23 +180,20 @@ static void add_repo(const char *base, struct strbuf *path)
// Drop the trailing slash added above, or the "/.git" suffix test
// below never matches and a working tree is named "repo/.git".
- if (relpath.len && relpath.buf[relpath.len - 1] == '/')
- strbuf_setlen(&relpath, relpath.len - 1);
- if (relpath.len >= 5 && !strcmp(relpath.buf + relpath.len - 5, "/.git"))
- strbuf_setlen(&relpath, relpath.len - 5);
- else if (!strcmp(relpath.buf, ".git"))
+ strbuf_strip_suffix(&relpath, "/");
+ if (!strbuf_strip_suffix(&relpath, "/.git") && !strcmp(relpath.buf, ".git"))
strbuf_setlen(&relpath, 0);
// The scan root may itself be the repository, leaving nothing after
// the base, so that one is named after its directory.
if (!relpath.len) {
- const char *end = path->buf + pathlen - 1, *start;
+ size_t len = pathlen - 1;
+ const char *start;
- if (end - path->buf >= 5 && !strncmp(end - 5, "/.git", 5))
- end -= 5;
- start = end;
+ strip_suffix_mem(path->buf, &len, "/.git");
+ start = path->buf + len;
while (start > path->buf && start[-1] != '/')
start--;
- strbuf_add(&relpath, start, end - start);
+ strbuf_add(&relpath, start, path->buf + len - start);
}
current_repo = cgit_add_repo(relpath.buf);
@@ -226,23 +218,27 @@ static void add_repo(const char *base, struct strbuf *path)
strip_suffix_mem(current_repo->url, &urllen, "/");
current_repo->url[urllen] = '\0';
}
- while (!current_repo->owner) {
+ if (!current_repo->owner) {
+ // A uid with no passwd entry is no error, and getpwuid tells
+ // the two apart only by setting errno on a failure.
+ errno = 0;
if (!(pwd = getpwuid(st.st_uid))) {
- fprintf(stderr, "[cgit] Unable to read the owner of %s: %s (%d)\n",
- path->buf, strerror(errno), errno);
- break;
+ if (errno)
+ fprintf(stderr, "[cgit] Unable to read the owner of %s: %s (%d)\n",
+ path->buf, strerror(errno), errno);
+ } else {
+ // A gecos field puts the owner's name in front of a
+ // comma separated list of office and phone details.
+ if (pwd->pw_gecos && (comma = strchr(pwd->pw_gecos, ',')))
+ *comma = '\0';
+ current_repo->owner =
+ cgit_strdup_first_line(pwd->pw_gecos ? pwd->pw_gecos : pwd->pw_name);
}
- // A gecos field puts the owner's name in front of a comma
- // separated list of office and phone details.
- if (pwd->pw_gecos && (comma = strchr(pwd->pw_gecos, ',')))
- *comma = '\0';
- current_repo->owner = cgit_strdup_first_line(pwd->pw_gecos ? pwd->pw_gecos : pwd->pw_name);
}
- if (current_repo->desc == cgit_default_repo_desc || !current_repo->desc) {
+ if (current_repo->desc == cgit_default_repo_desc) {
strbuf_addstr(path, "description");
- if (!stat(path->buf, &st))
- cgit_read_first_line(path->buf, &current_repo->desc, &desc_size);
+ cgit_read_first_line(path->buf, &current_repo->desc);
strbuf_setlen(path, pathlen);
if (current_repo->desc && !strcmp(current_repo->desc, default_git_desc)) {
free(current_repo->desc);
@@ -254,8 +250,7 @@ static void add_repo(const char *base, struct strbuf *path)
set_section_from_path(&relpath, ctx.cfg.section_from_path);
strbuf_addstr(path, "cgitrc");
- if (!stat(path->buf, &st))
- config_file_parse(path->buf, apply_cgitrc);
+ config_file_parse(path->buf, apply_cgitrc);
strbuf_release(&relpath);
}
@@ -344,7 +339,7 @@ end:
closedir(dir);
}
-void scan_projects(const char *path, const char *projectsfile)
+static void scan_projects(const char *path, const char *projectsfile)
{
struct strbuf line = STRBUF_INIT;
FILE *projects;
@@ -374,5 +369,8 @@ void scan_projects(const char *path, const char *projectsfile)
void scan_tree(const char *path)
{
- scan_path(path, path);
+ if (ctx.cfg.project_list)
+ scan_projects(path, ctx.cfg.project_list);
+ else
+ scan_path(path, path);
}