Merge branch 'ab/fsck-api-cleanup'
Fsck API clean-up. * ab/fsck-api-cleanup: fetch-pack: use new fsck API to printing dangling submodules fetch-pack: use file-scope static struct for fsck_options fetch-pack: don't needlessly copy fsck_options fsck.c: move gitmodules_{found,done} into fsck_options fsck.c: add an fsck_set_msg_type() API that takes enums fsck.c: pass along the fsck_msg_id in the fsck_error callback fsck.[ch]: move FOREACH_FSCK_MSG_ID & fsck_msg_id from *.c to *.h fsck.c: give "FOREACH_MSG_ID" a more specific name fsck.c: undefine temporary STR macro after use fsck.c: call parse_msg_type() early in fsck_set_msg_type() fsck.h: re-order and re-assign "enum fsck_msg_type" fsck.h: move FSCK_{FATAL,INFO,ERROR,WARN,IGNORE} into an enum fsck.c: refactor fsck_msg_type() to limit scope of "int msg_type" fsck.c: rename remaining fsck_msg_id "id" to "msg_id" fsck.c: remove (mostly) redundant append_msg_id() function fsck.c: rename variables in fsck_set_msg_type() for less confusion fsck.h: use "enum object_type" instead of "int" fsck.h: use designed initializers for FSCK_OPTIONS_{DEFAULT,STRICT} fsck.c: refactor and rename common config callback
This commit is contained in:
commit
5644419d04
@ -71,11 +71,6 @@ static const char *printable_type(const struct object_id *oid,
|
||||
return ret;
|
||||
}
|
||||
|
||||
static int fsck_config(const char *var, const char *value, void *cb)
|
||||
{
|
||||
return fsck_config_internal(var, value, cb, &fsck_obj_options);
|
||||
}
|
||||
|
||||
static int objerror(struct object *obj, const char *err)
|
||||
{
|
||||
errors_found |= ERROR_OBJECT;
|
||||
@ -89,7 +84,9 @@ static int objerror(struct object *obj, const char *err)
|
||||
static int fsck_error_func(struct fsck_options *o,
|
||||
const struct object_id *oid,
|
||||
enum object_type object_type,
|
||||
int msg_type, const char *message)
|
||||
enum fsck_msg_type msg_type,
|
||||
enum fsck_msg_id msg_id,
|
||||
const char *message)
|
||||
{
|
||||
switch (msg_type) {
|
||||
case FSCK_WARN:
|
||||
@ -197,7 +194,8 @@ static int traverse_reachable(void)
|
||||
return !!result;
|
||||
}
|
||||
|
||||
static int mark_used(struct object *obj, int type, void *data, struct fsck_options *options)
|
||||
static int mark_used(struct object *obj, enum object_type object_type,
|
||||
void *data, struct fsck_options *options)
|
||||
{
|
||||
if (!obj)
|
||||
return 1;
|
||||
@ -803,7 +801,7 @@ int cmd_fsck(int argc, const char **argv, const char *prefix)
|
||||
if (name_objects)
|
||||
fsck_enable_object_names(&fsck_walk_options);
|
||||
|
||||
git_config(fsck_config, NULL);
|
||||
git_config(git_fsck_config, &fsck_obj_options);
|
||||
|
||||
if (connectivity_only) {
|
||||
for_each_loose_object(mark_loose_for_connectivity, NULL, 0);
|
||||
|
@ -120,7 +120,7 @@ static int nr_threads;
|
||||
static int from_stdin;
|
||||
static int strict;
|
||||
static int do_fsck_object;
|
||||
static struct fsck_options fsck_options = FSCK_OPTIONS_STRICT;
|
||||
static struct fsck_options fsck_options = FSCK_OPTIONS_MISSING_GITMODULES;
|
||||
static int verbose;
|
||||
static int show_resolving_progress;
|
||||
static int show_stat;
|
||||
@ -212,7 +212,8 @@ static void cleanup_thread(void)
|
||||
free(thread_data);
|
||||
}
|
||||
|
||||
static int mark_link(struct object *obj, int type, void *data, struct fsck_options *options)
|
||||
static int mark_link(struct object *obj, enum object_type type,
|
||||
void *data, struct fsck_options *options)
|
||||
{
|
||||
if (!obj)
|
||||
return -1;
|
||||
@ -1712,22 +1713,6 @@ static void show_pack_info(int stat_only)
|
||||
}
|
||||
}
|
||||
|
||||
static int print_dangling_gitmodules(struct fsck_options *o,
|
||||
const struct object_id *oid,
|
||||
enum object_type object_type,
|
||||
int msg_type, const char *message)
|
||||
{
|
||||
/*
|
||||
* NEEDSWORK: Plumb the MSG_ID (from fsck.c) here and use it
|
||||
* instead of relying on this string check.
|
||||
*/
|
||||
if (starts_with(message, "gitmodulesMissing")) {
|
||||
printf("%s\n", oid_to_hex(oid));
|
||||
return 0;
|
||||
}
|
||||
return fsck_error_function(o, oid, object_type, msg_type, message);
|
||||
}
|
||||
|
||||
int cmd_index_pack(int argc, const char **argv, const char *prefix)
|
||||
{
|
||||
int i, fix_thin_pack = 0, verify = 0, stat_only = 0, rev_index;
|
||||
@ -1948,13 +1933,8 @@ int cmd_index_pack(int argc, const char **argv, const char *prefix)
|
||||
else
|
||||
close(input_fd);
|
||||
|
||||
if (do_fsck_object) {
|
||||
struct fsck_options fo = fsck_options;
|
||||
|
||||
fo.error_func = print_dangling_gitmodules;
|
||||
if (fsck_finish(&fo))
|
||||
die(_("fsck error in pack objects"));
|
||||
}
|
||||
if (do_fsck_object && fsck_finish(&fsck_options))
|
||||
die(_("fsck error in pack objects"));
|
||||
|
||||
free(objects);
|
||||
strbuf_release(&index_name_buf);
|
||||
|
@ -14,15 +14,12 @@ static int option_strict = 1;
|
||||
|
||||
static struct fsck_options fsck_options = FSCK_OPTIONS_STRICT;
|
||||
|
||||
static int mktag_config(const char *var, const char *value, void *cb)
|
||||
{
|
||||
return fsck_config_internal(var, value, cb, &fsck_options);
|
||||
}
|
||||
|
||||
static int mktag_fsck_error_func(struct fsck_options *o,
|
||||
const struct object_id *oid,
|
||||
enum object_type object_type,
|
||||
int msg_type, const char *message)
|
||||
enum fsck_msg_type msg_type,
|
||||
enum fsck_msg_id msg_id,
|
||||
const char *message)
|
||||
{
|
||||
switch (msg_type) {
|
||||
case FSCK_WARN:
|
||||
@ -91,9 +88,10 @@ int cmd_mktag(int argc, const char **argv, const char *prefix)
|
||||
die_errno(_("could not read from stdin"));
|
||||
|
||||
fsck_options.error_func = mktag_fsck_error_func;
|
||||
fsck_set_msg_type(&fsck_options, "extraheaderentry", "warn");
|
||||
fsck_set_msg_type_from_ids(&fsck_options, FSCK_MSG_EXTRA_HEADER_ENTRY,
|
||||
FSCK_WARN);
|
||||
/* config might set fsck.extraHeaderEntry=* again */
|
||||
git_config(mktag_config, NULL);
|
||||
git_config(git_fsck_config, &fsck_options);
|
||||
if (fsck_tag_standalone(NULL, buf.buf, buf.len, &fsck_options,
|
||||
&tagged_oid, &tagged_type))
|
||||
die(_("tag on stdin did not pass our strict fsck check"));
|
||||
|
@ -187,7 +187,8 @@ static void write_cached_object(struct object *obj, struct obj_buffer *obj_buf)
|
||||
* that have reachability requirements and calls this function.
|
||||
* Verify its reachability and validity recursively and write it out.
|
||||
*/
|
||||
static int check_object(struct object *obj, int type, void *data, struct fsck_options *options)
|
||||
static int check_object(struct object *obj, enum object_type type,
|
||||
void *data, struct fsck_options *options)
|
||||
{
|
||||
struct obj_buffer *obj_buf;
|
||||
|
||||
|
31
fetch-pack.c
31
fetch-pack.c
@ -38,6 +38,7 @@ static int server_supports_filtering;
|
||||
static int advertise_sid;
|
||||
static struct shallow_lock shallow_lock;
|
||||
static const char *alternate_shallow_file;
|
||||
static struct fsck_options fsck_options = FSCK_OPTIONS_MISSING_GITMODULES;
|
||||
static struct strbuf fsck_msg_types = STRBUF_INIT;
|
||||
static struct string_list uri_protocols = STRING_LIST_INIT_DUP;
|
||||
|
||||
@ -987,22 +988,6 @@ static int cmp_ref_by_name(const void *a_, const void *b_)
|
||||
return strcmp(a->name, b->name);
|
||||
}
|
||||
|
||||
static void fsck_gitmodules_oids(struct oidset *gitmodules_oids)
|
||||
{
|
||||
struct oidset_iter iter;
|
||||
const struct object_id *oid;
|
||||
struct fsck_options fo = FSCK_OPTIONS_STRICT;
|
||||
|
||||
if (!oidset_size(gitmodules_oids))
|
||||
return;
|
||||
|
||||
oidset_iter_init(gitmodules_oids, &iter);
|
||||
while ((oid = oidset_iter_next(&iter)))
|
||||
register_found_gitmodules(oid);
|
||||
if (fsck_finish(&fo))
|
||||
die("fsck failed");
|
||||
}
|
||||
|
||||
static struct ref *do_fetch_pack(struct fetch_pack_args *args,
|
||||
int fd[2],
|
||||
const struct ref *orig_ref,
|
||||
@ -1017,7 +1002,6 @@ static struct ref *do_fetch_pack(struct fetch_pack_args *args,
|
||||
int agent_len;
|
||||
struct fetch_negotiator negotiator_alloc;
|
||||
struct fetch_negotiator *negotiator;
|
||||
struct oidset gitmodules_oids = OIDSET_INIT;
|
||||
|
||||
negotiator = &negotiator_alloc;
|
||||
fetch_negotiator_init(r, negotiator);
|
||||
@ -1134,9 +1118,10 @@ static struct ref *do_fetch_pack(struct fetch_pack_args *args,
|
||||
else
|
||||
alternate_shallow_file = NULL;
|
||||
if (get_pack(args, fd, pack_lockfiles, NULL, sought, nr_sought,
|
||||
&gitmodules_oids))
|
||||
&fsck_options.gitmodules_found))
|
||||
die(_("git fetch-pack: fetch failed."));
|
||||
fsck_gitmodules_oids(&gitmodules_oids);
|
||||
if (fsck_finish(&fsck_options))
|
||||
die("fsck failed");
|
||||
|
||||
all_done:
|
||||
if (negotiator)
|
||||
@ -1587,7 +1572,6 @@ static struct ref *do_fetch_pack_v2(struct fetch_pack_args *args,
|
||||
struct string_list packfile_uris = STRING_LIST_INIT_DUP;
|
||||
int i;
|
||||
struct strvec index_pack_args = STRVEC_INIT;
|
||||
struct oidset gitmodules_oids = OIDSET_INIT;
|
||||
|
||||
negotiator = &negotiator_alloc;
|
||||
fetch_negotiator_init(r, negotiator);
|
||||
@ -1678,7 +1662,7 @@ static struct ref *do_fetch_pack_v2(struct fetch_pack_args *args,
|
||||
process_section_header(&reader, "packfile", 0);
|
||||
if (get_pack(args, fd, pack_lockfiles,
|
||||
packfile_uris.nr ? &index_pack_args : NULL,
|
||||
sought, nr_sought, &gitmodules_oids))
|
||||
sought, nr_sought, &fsck_options.gitmodules_found))
|
||||
die(_("git fetch-pack: fetch failed."));
|
||||
do_check_stateless_delimiter(args, &reader);
|
||||
|
||||
@ -1721,7 +1705,7 @@ static struct ref *do_fetch_pack_v2(struct fetch_pack_args *args,
|
||||
|
||||
packname[the_hash_algo->hexsz] = '\0';
|
||||
|
||||
parse_gitmodules_oids(cmd.out, &gitmodules_oids);
|
||||
parse_gitmodules_oids(cmd.out, &fsck_options.gitmodules_found);
|
||||
|
||||
close(cmd.out);
|
||||
|
||||
@ -1742,7 +1726,8 @@ static struct ref *do_fetch_pack_v2(struct fetch_pack_args *args,
|
||||
string_list_clear(&packfile_uris, 0);
|
||||
strvec_clear(&index_pack_args);
|
||||
|
||||
fsck_gitmodules_oids(&gitmodules_oids);
|
||||
if (fsck_finish(&fsck_options))
|
||||
die("fsck failed");
|
||||
|
||||
if (negotiator)
|
||||
negotiator->release(negotiator);
|
||||
|
207
fsck.c
207
fsck.c
@ -19,90 +19,19 @@
|
||||
#include "credential.h"
|
||||
#include "help.h"
|
||||
|
||||
static struct oidset gitmodules_found = OIDSET_INIT;
|
||||
static struct oidset gitmodules_done = OIDSET_INIT;
|
||||
|
||||
#define FSCK_FATAL -1
|
||||
#define FSCK_INFO -2
|
||||
|
||||
#define FOREACH_MSG_ID(FUNC) \
|
||||
/* fatal errors */ \
|
||||
FUNC(NUL_IN_HEADER, FATAL) \
|
||||
FUNC(UNTERMINATED_HEADER, FATAL) \
|
||||
/* errors */ \
|
||||
FUNC(BAD_DATE, ERROR) \
|
||||
FUNC(BAD_DATE_OVERFLOW, ERROR) \
|
||||
FUNC(BAD_EMAIL, ERROR) \
|
||||
FUNC(BAD_NAME, ERROR) \
|
||||
FUNC(BAD_OBJECT_SHA1, ERROR) \
|
||||
FUNC(BAD_PARENT_SHA1, ERROR) \
|
||||
FUNC(BAD_TAG_OBJECT, ERROR) \
|
||||
FUNC(BAD_TIMEZONE, ERROR) \
|
||||
FUNC(BAD_TREE, ERROR) \
|
||||
FUNC(BAD_TREE_SHA1, ERROR) \
|
||||
FUNC(BAD_TYPE, ERROR) \
|
||||
FUNC(DUPLICATE_ENTRIES, ERROR) \
|
||||
FUNC(MISSING_AUTHOR, ERROR) \
|
||||
FUNC(MISSING_COMMITTER, ERROR) \
|
||||
FUNC(MISSING_EMAIL, ERROR) \
|
||||
FUNC(MISSING_NAME_BEFORE_EMAIL, ERROR) \
|
||||
FUNC(MISSING_OBJECT, ERROR) \
|
||||
FUNC(MISSING_SPACE_BEFORE_DATE, ERROR) \
|
||||
FUNC(MISSING_SPACE_BEFORE_EMAIL, ERROR) \
|
||||
FUNC(MISSING_TAG, ERROR) \
|
||||
FUNC(MISSING_TAG_ENTRY, ERROR) \
|
||||
FUNC(MISSING_TREE, ERROR) \
|
||||
FUNC(MISSING_TREE_OBJECT, ERROR) \
|
||||
FUNC(MISSING_TYPE, ERROR) \
|
||||
FUNC(MISSING_TYPE_ENTRY, ERROR) \
|
||||
FUNC(MULTIPLE_AUTHORS, ERROR) \
|
||||
FUNC(TREE_NOT_SORTED, ERROR) \
|
||||
FUNC(UNKNOWN_TYPE, ERROR) \
|
||||
FUNC(ZERO_PADDED_DATE, ERROR) \
|
||||
FUNC(GITMODULES_MISSING, ERROR) \
|
||||
FUNC(GITMODULES_BLOB, ERROR) \
|
||||
FUNC(GITMODULES_LARGE, ERROR) \
|
||||
FUNC(GITMODULES_NAME, ERROR) \
|
||||
FUNC(GITMODULES_SYMLINK, ERROR) \
|
||||
FUNC(GITMODULES_URL, ERROR) \
|
||||
FUNC(GITMODULES_PATH, ERROR) \
|
||||
FUNC(GITMODULES_UPDATE, ERROR) \
|
||||
/* warnings */ \
|
||||
FUNC(BAD_FILEMODE, WARN) \
|
||||
FUNC(EMPTY_NAME, WARN) \
|
||||
FUNC(FULL_PATHNAME, WARN) \
|
||||
FUNC(HAS_DOT, WARN) \
|
||||
FUNC(HAS_DOTDOT, WARN) \
|
||||
FUNC(HAS_DOTGIT, WARN) \
|
||||
FUNC(NULL_SHA1, WARN) \
|
||||
FUNC(ZERO_PADDED_FILEMODE, WARN) \
|
||||
FUNC(NUL_IN_COMMIT, WARN) \
|
||||
/* infos (reported as warnings, but ignored by default) */ \
|
||||
FUNC(GITMODULES_PARSE, INFO) \
|
||||
FUNC(BAD_TAG_NAME, INFO) \
|
||||
FUNC(MISSING_TAGGER_ENTRY, INFO) \
|
||||
/* ignored (elevated when requested) */ \
|
||||
FUNC(EXTRA_HEADER_ENTRY, IGNORE)
|
||||
|
||||
#define MSG_ID(id, msg_type) FSCK_MSG_##id,
|
||||
enum fsck_msg_id {
|
||||
FOREACH_MSG_ID(MSG_ID)
|
||||
FSCK_MSG_MAX
|
||||
};
|
||||
#undef MSG_ID
|
||||
|
||||
#define STR(x) #x
|
||||
#define MSG_ID(id, msg_type) { STR(id), NULL, NULL, FSCK_##msg_type },
|
||||
static struct {
|
||||
const char *id_string;
|
||||
const char *downcased;
|
||||
const char *camelcased;
|
||||
int msg_type;
|
||||
enum fsck_msg_type msg_type;
|
||||
} msg_id_info[FSCK_MSG_MAX + 1] = {
|
||||
FOREACH_MSG_ID(MSG_ID)
|
||||
FOREACH_FSCK_MSG_ID(MSG_ID)
|
||||
{ NULL, NULL, NULL, -1 }
|
||||
};
|
||||
#undef MSG_ID
|
||||
#undef STR
|
||||
|
||||
static void prepare_msg_ids(void)
|
||||
{
|
||||
@ -164,25 +93,23 @@ void list_config_fsck_msg_ids(struct string_list *list, const char *prefix)
|
||||
list_config_item(list, prefix, msg_id_info[i].camelcased);
|
||||
}
|
||||
|
||||
static int fsck_msg_type(enum fsck_msg_id msg_id,
|
||||
static enum fsck_msg_type fsck_msg_type(enum fsck_msg_id msg_id,
|
||||
struct fsck_options *options)
|
||||
{
|
||||
int msg_type;
|
||||
|
||||
assert(msg_id >= 0 && msg_id < FSCK_MSG_MAX);
|
||||
|
||||
if (options->msg_type)
|
||||
msg_type = options->msg_type[msg_id];
|
||||
else {
|
||||
msg_type = msg_id_info[msg_id].msg_type;
|
||||
if (!options->msg_type) {
|
||||
enum fsck_msg_type msg_type = msg_id_info[msg_id].msg_type;
|
||||
|
||||
if (options->strict && msg_type == FSCK_WARN)
|
||||
msg_type = FSCK_ERROR;
|
||||
return msg_type;
|
||||
}
|
||||
|
||||
return msg_type;
|
||||
return options->msg_type[msg_id];
|
||||
}
|
||||
|
||||
static int parse_msg_type(const char *str)
|
||||
static enum fsck_msg_type parse_msg_type(const char *str)
|
||||
{
|
||||
if (!strcmp(str, "error"))
|
||||
return FSCK_ERROR;
|
||||
@ -202,28 +129,35 @@ int is_valid_msg_type(const char *msg_id, const char *msg_type)
|
||||
return 1;
|
||||
}
|
||||
|
||||
void fsck_set_msg_type(struct fsck_options *options,
|
||||
const char *msg_id, const char *msg_type)
|
||||
void fsck_set_msg_type_from_ids(struct fsck_options *options,
|
||||
enum fsck_msg_id msg_id,
|
||||
enum fsck_msg_type msg_type)
|
||||
{
|
||||
int id = parse_msg_id(msg_id), type;
|
||||
|
||||
if (id < 0)
|
||||
die("Unhandled message id: %s", msg_id);
|
||||
type = parse_msg_type(msg_type);
|
||||
|
||||
if (type != FSCK_ERROR && msg_id_info[id].msg_type == FSCK_FATAL)
|
||||
die("Cannot demote %s to %s", msg_id, msg_type);
|
||||
|
||||
if (!options->msg_type) {
|
||||
int i;
|
||||
int *msg_type;
|
||||
ALLOC_ARRAY(msg_type, FSCK_MSG_MAX);
|
||||
enum fsck_msg_type *severity;
|
||||
ALLOC_ARRAY(severity, FSCK_MSG_MAX);
|
||||
for (i = 0; i < FSCK_MSG_MAX; i++)
|
||||
msg_type[i] = fsck_msg_type(i, options);
|
||||
options->msg_type = msg_type;
|
||||
severity[i] = fsck_msg_type(i, options);
|
||||
options->msg_type = severity;
|
||||
}
|
||||
|
||||
options->msg_type[id] = type;
|
||||
options->msg_type[msg_id] = msg_type;
|
||||
}
|
||||
|
||||
void fsck_set_msg_type(struct fsck_options *options,
|
||||
const char *msg_id_str, const char *msg_type_str)
|
||||
{
|
||||
int msg_id = parse_msg_id(msg_id_str);
|
||||
enum fsck_msg_type msg_type = parse_msg_type(msg_type_str);
|
||||
|
||||
if (msg_id < 0)
|
||||
die("Unhandled message id: %s", msg_id_str);
|
||||
|
||||
if (msg_type != FSCK_ERROR && msg_id_info[msg_id].msg_type == FSCK_FATAL)
|
||||
die("Cannot demote %s to %s", msg_id_str, msg_type_str);
|
||||
|
||||
fsck_set_msg_type_from_ids(options, msg_id, msg_type);
|
||||
}
|
||||
|
||||
void fsck_set_msg_types(struct fsck_options *options, const char *values)
|
||||
@ -264,24 +198,6 @@ void fsck_set_msg_types(struct fsck_options *options, const char *values)
|
||||
free(to_free);
|
||||
}
|
||||
|
||||
static void append_msg_id(struct strbuf *sb, const char *msg_id)
|
||||
{
|
||||
for (;;) {
|
||||
char c = *(msg_id)++;
|
||||
|
||||
if (!c)
|
||||
break;
|
||||
if (c != '_')
|
||||
strbuf_addch(sb, tolower(c));
|
||||
else {
|
||||
assert(*msg_id);
|
||||
strbuf_addch(sb, *(msg_id)++);
|
||||
}
|
||||
}
|
||||
|
||||
strbuf_addstr(sb, ": ");
|
||||
}
|
||||
|
||||
static int object_on_skiplist(struct fsck_options *opts,
|
||||
const struct object_id *oid)
|
||||
{
|
||||
@ -291,11 +207,12 @@ static int object_on_skiplist(struct fsck_options *opts,
|
||||
__attribute__((format (printf, 5, 6)))
|
||||
static int report(struct fsck_options *options,
|
||||
const struct object_id *oid, enum object_type object_type,
|
||||
enum fsck_msg_id id, const char *fmt, ...)
|
||||
enum fsck_msg_id msg_id, const char *fmt, ...)
|
||||
{
|
||||
va_list ap;
|
||||
struct strbuf sb = STRBUF_INIT;
|
||||
int msg_type = fsck_msg_type(id, options), result;
|
||||
enum fsck_msg_type msg_type = fsck_msg_type(msg_id, options);
|
||||
int result;
|
||||
|
||||
if (msg_type == FSCK_IGNORE)
|
||||
return 0;
|
||||
@ -308,12 +225,13 @@ static int report(struct fsck_options *options,
|
||||
else if (msg_type == FSCK_INFO)
|
||||
msg_type = FSCK_WARN;
|
||||
|
||||
append_msg_id(&sb, msg_id_info[id].id_string);
|
||||
prepare_msg_ids();
|
||||
strbuf_addf(&sb, "%s: ", msg_id_info[msg_id].camelcased);
|
||||
|
||||
va_start(ap, fmt);
|
||||
strbuf_vaddf(&sb, fmt, ap);
|
||||
result = options->error_func(options, oid, object_type,
|
||||
msg_type, sb.buf);
|
||||
msg_type, msg_id, sb.buf);
|
||||
strbuf_release(&sb);
|
||||
va_end(ap);
|
||||
|
||||
@ -685,7 +603,7 @@ static int fsck_tree(const struct object_id *oid,
|
||||
|
||||
if (is_hfs_dotgitmodules(name) || is_ntfs_dotgitmodules(name)) {
|
||||
if (!S_ISLNK(mode))
|
||||
oidset_insert(&gitmodules_found, oid);
|
||||
oidset_insert(&options->gitmodules_found, oid);
|
||||
else
|
||||
retval += report(options,
|
||||
oid, OBJ_TREE,
|
||||
@ -699,7 +617,7 @@ static int fsck_tree(const struct object_id *oid,
|
||||
has_dotgit |= is_ntfs_dotgit(backslash);
|
||||
if (is_ntfs_dotgitmodules(backslash)) {
|
||||
if (!S_ISLNK(mode))
|
||||
oidset_insert(&gitmodules_found, oid);
|
||||
oidset_insert(&options->gitmodules_found, oid);
|
||||
else
|
||||
retval += report(options, oid, OBJ_TREE,
|
||||
FSCK_MSG_GITMODULES_SYMLINK,
|
||||
@ -1211,9 +1129,9 @@ static int fsck_blob(const struct object_id *oid, const char *buf,
|
||||
struct fsck_gitmodules_data data;
|
||||
struct config_options config_opts = { 0 };
|
||||
|
||||
if (!oidset_contains(&gitmodules_found, oid))
|
||||
if (!oidset_contains(&options->gitmodules_found, oid))
|
||||
return 0;
|
||||
oidset_insert(&gitmodules_done, oid);
|
||||
oidset_insert(&options->gitmodules_done, oid);
|
||||
|
||||
if (object_on_skiplist(options, oid))
|
||||
return 0;
|
||||
@ -1266,7 +1184,9 @@ int fsck_object(struct object *obj, void *data, unsigned long size,
|
||||
int fsck_error_function(struct fsck_options *o,
|
||||
const struct object_id *oid,
|
||||
enum object_type object_type,
|
||||
int msg_type, const char *message)
|
||||
enum fsck_msg_type msg_type,
|
||||
enum fsck_msg_id msg_id,
|
||||
const char *message)
|
||||
{
|
||||
if (msg_type == FSCK_WARN) {
|
||||
warning("object %s: %s", fsck_describe_object(o, oid), message);
|
||||
@ -1276,24 +1196,19 @@ int fsck_error_function(struct fsck_options *o,
|
||||
return 1;
|
||||
}
|
||||
|
||||
void register_found_gitmodules(const struct object_id *oid)
|
||||
{
|
||||
oidset_insert(&gitmodules_found, oid);
|
||||
}
|
||||
|
||||
int fsck_finish(struct fsck_options *options)
|
||||
{
|
||||
int ret = 0;
|
||||
struct oidset_iter iter;
|
||||
const struct object_id *oid;
|
||||
|
||||
oidset_iter_init(&gitmodules_found, &iter);
|
||||
oidset_iter_init(&options->gitmodules_found, &iter);
|
||||
while ((oid = oidset_iter_next(&iter))) {
|
||||
enum object_type type;
|
||||
unsigned long size;
|
||||
char *buf;
|
||||
|
||||
if (oidset_contains(&gitmodules_done, oid))
|
||||
if (oidset_contains(&options->gitmodules_done, oid))
|
||||
continue;
|
||||
|
||||
buf = read_object_file(oid, &type, &size);
|
||||
@ -1318,14 +1233,14 @@ int fsck_finish(struct fsck_options *options)
|
||||
}
|
||||
|
||||
|
||||
oidset_clear(&gitmodules_found);
|
||||
oidset_clear(&gitmodules_done);
|
||||
oidset_clear(&options->gitmodules_found);
|
||||
oidset_clear(&options->gitmodules_done);
|
||||
return ret;
|
||||
}
|
||||
|
||||
int fsck_config_internal(const char *var, const char *value, void *cb,
|
||||
struct fsck_options *options)
|
||||
int git_fsck_config(const char *var, const char *value, void *cb)
|
||||
{
|
||||
struct fsck_options *options = cb;
|
||||
if (strcmp(var, "fsck.skiplist") == 0) {
|
||||
const char *path;
|
||||
struct strbuf sb = STRBUF_INIT;
|
||||
@ -1346,3 +1261,21 @@ int fsck_config_internal(const char *var, const char *value, void *cb,
|
||||
|
||||
return git_default_config(var, value, cb);
|
||||
}
|
||||
|
||||
/*
|
||||
* Custom error callbacks that are used in more than one place.
|
||||
*/
|
||||
|
||||
int fsck_error_cb_print_missing_gitmodules(struct fsck_options *o,
|
||||
const struct object_id *oid,
|
||||
enum object_type object_type,
|
||||
enum fsck_msg_type msg_type,
|
||||
enum fsck_msg_id msg_id,
|
||||
const char *message)
|
||||
{
|
||||
if (msg_id == FSCK_MSG_GITMODULES_MISSING) {
|
||||
puts(oid_to_hex(oid));
|
||||
return 0;
|
||||
}
|
||||
return fsck_error_function(o, oid, object_type, msg_type, msg_id, message);
|
||||
}
|
||||
|
127
fsck.h
127
fsck.h
@ -3,15 +3,90 @@
|
||||
|
||||
#include "oidset.h"
|
||||
|
||||
#define FSCK_ERROR 1
|
||||
#define FSCK_WARN 2
|
||||
#define FSCK_IGNORE 3
|
||||
enum fsck_msg_type {
|
||||
/* for internal use only */
|
||||
FSCK_IGNORE,
|
||||
FSCK_INFO,
|
||||
FSCK_FATAL,
|
||||
/* "public", fed to e.g. error_func callbacks */
|
||||
FSCK_ERROR,
|
||||
FSCK_WARN,
|
||||
};
|
||||
|
||||
#define FOREACH_FSCK_MSG_ID(FUNC) \
|
||||
/* fatal errors */ \
|
||||
FUNC(NUL_IN_HEADER, FATAL) \
|
||||
FUNC(UNTERMINATED_HEADER, FATAL) \
|
||||
/* errors */ \
|
||||
FUNC(BAD_DATE, ERROR) \
|
||||
FUNC(BAD_DATE_OVERFLOW, ERROR) \
|
||||
FUNC(BAD_EMAIL, ERROR) \
|
||||
FUNC(BAD_NAME, ERROR) \
|
||||
FUNC(BAD_OBJECT_SHA1, ERROR) \
|
||||
FUNC(BAD_PARENT_SHA1, ERROR) \
|
||||
FUNC(BAD_TAG_OBJECT, ERROR) \
|
||||
FUNC(BAD_TIMEZONE, ERROR) \
|
||||
FUNC(BAD_TREE, ERROR) \
|
||||
FUNC(BAD_TREE_SHA1, ERROR) \
|
||||
FUNC(BAD_TYPE, ERROR) \
|
||||
FUNC(DUPLICATE_ENTRIES, ERROR) \
|
||||
FUNC(MISSING_AUTHOR, ERROR) \
|
||||
FUNC(MISSING_COMMITTER, ERROR) \
|
||||
FUNC(MISSING_EMAIL, ERROR) \
|
||||
FUNC(MISSING_NAME_BEFORE_EMAIL, ERROR) \
|
||||
FUNC(MISSING_OBJECT, ERROR) \
|
||||
FUNC(MISSING_SPACE_BEFORE_DATE, ERROR) \
|
||||
FUNC(MISSING_SPACE_BEFORE_EMAIL, ERROR) \
|
||||
FUNC(MISSING_TAG, ERROR) \
|
||||
FUNC(MISSING_TAG_ENTRY, ERROR) \
|
||||
FUNC(MISSING_TREE, ERROR) \
|
||||
FUNC(MISSING_TREE_OBJECT, ERROR) \
|
||||
FUNC(MISSING_TYPE, ERROR) \
|
||||
FUNC(MISSING_TYPE_ENTRY, ERROR) \
|
||||
FUNC(MULTIPLE_AUTHORS, ERROR) \
|
||||
FUNC(TREE_NOT_SORTED, ERROR) \
|
||||
FUNC(UNKNOWN_TYPE, ERROR) \
|
||||
FUNC(ZERO_PADDED_DATE, ERROR) \
|
||||
FUNC(GITMODULES_MISSING, ERROR) \
|
||||
FUNC(GITMODULES_BLOB, ERROR) \
|
||||
FUNC(GITMODULES_LARGE, ERROR) \
|
||||
FUNC(GITMODULES_NAME, ERROR) \
|
||||
FUNC(GITMODULES_SYMLINK, ERROR) \
|
||||
FUNC(GITMODULES_URL, ERROR) \
|
||||
FUNC(GITMODULES_PATH, ERROR) \
|
||||
FUNC(GITMODULES_UPDATE, ERROR) \
|
||||
/* warnings */ \
|
||||
FUNC(BAD_FILEMODE, WARN) \
|
||||
FUNC(EMPTY_NAME, WARN) \
|
||||
FUNC(FULL_PATHNAME, WARN) \
|
||||
FUNC(HAS_DOT, WARN) \
|
||||
FUNC(HAS_DOTDOT, WARN) \
|
||||
FUNC(HAS_DOTGIT, WARN) \
|
||||
FUNC(NULL_SHA1, WARN) \
|
||||
FUNC(ZERO_PADDED_FILEMODE, WARN) \
|
||||
FUNC(NUL_IN_COMMIT, WARN) \
|
||||
/* infos (reported as warnings, but ignored by default) */ \
|
||||
FUNC(GITMODULES_PARSE, INFO) \
|
||||
FUNC(BAD_TAG_NAME, INFO) \
|
||||
FUNC(MISSING_TAGGER_ENTRY, INFO) \
|
||||
/* ignored (elevated when requested) */ \
|
||||
FUNC(EXTRA_HEADER_ENTRY, IGNORE)
|
||||
|
||||
#define MSG_ID(id, msg_type) FSCK_MSG_##id,
|
||||
enum fsck_msg_id {
|
||||
FOREACH_FSCK_MSG_ID(MSG_ID)
|
||||
FSCK_MSG_MAX
|
||||
};
|
||||
#undef MSG_ID
|
||||
|
||||
struct fsck_options;
|
||||
struct object;
|
||||
|
||||
void fsck_set_msg_type_from_ids(struct fsck_options *options,
|
||||
enum fsck_msg_id msg_id,
|
||||
enum fsck_msg_type msg_type);
|
||||
void fsck_set_msg_type(struct fsck_options *options,
|
||||
const char *msg_id, const char *msg_type);
|
||||
const char *msg_id, const char *msg_type);
|
||||
void fsck_set_msg_types(struct fsck_options *options, const char *values);
|
||||
int is_valid_msg_type(const char *msg_id, const char *msg_type);
|
||||
|
||||
@ -23,28 +98,55 @@ int is_valid_msg_type(const char *msg_id, const char *msg_type);
|
||||
* <0 error signaled and abort
|
||||
* >0 error signaled and do not abort
|
||||
*/
|
||||
typedef int (*fsck_walk_func)(struct object *obj, int type, void *data, struct fsck_options *options);
|
||||
typedef int (*fsck_walk_func)(struct object *obj, enum object_type object_type,
|
||||
void *data, struct fsck_options *options);
|
||||
|
||||
/* callback for fsck_object, type is FSCK_ERROR or FSCK_WARN */
|
||||
typedef int (*fsck_error)(struct fsck_options *o,
|
||||
const struct object_id *oid, enum object_type object_type,
|
||||
int msg_type, const char *message);
|
||||
enum fsck_msg_type msg_type, enum fsck_msg_id msg_id,
|
||||
const char *message);
|
||||
|
||||
int fsck_error_function(struct fsck_options *o,
|
||||
const struct object_id *oid, enum object_type object_type,
|
||||
int msg_type, const char *message);
|
||||
enum fsck_msg_type msg_type, enum fsck_msg_id msg_id,
|
||||
const char *message);
|
||||
int fsck_error_cb_print_missing_gitmodules(struct fsck_options *o,
|
||||
const struct object_id *oid,
|
||||
enum object_type object_type,
|
||||
enum fsck_msg_type msg_type,
|
||||
enum fsck_msg_id msg_id,
|
||||
const char *message);
|
||||
|
||||
struct fsck_options {
|
||||
fsck_walk_func walk;
|
||||
fsck_error error_func;
|
||||
unsigned strict:1;
|
||||
int *msg_type;
|
||||
enum fsck_msg_type *msg_type;
|
||||
struct oidset skiplist;
|
||||
struct oidset gitmodules_found;
|
||||
struct oidset gitmodules_done;
|
||||
kh_oid_map_t *object_names;
|
||||
};
|
||||
|
||||
#define FSCK_OPTIONS_DEFAULT { NULL, fsck_error_function, 0, NULL, OIDSET_INIT }
|
||||
#define FSCK_OPTIONS_STRICT { NULL, fsck_error_function, 1, NULL, OIDSET_INIT }
|
||||
#define FSCK_OPTIONS_DEFAULT { \
|
||||
.skiplist = OIDSET_INIT, \
|
||||
.gitmodules_found = OIDSET_INIT, \
|
||||
.gitmodules_done = OIDSET_INIT, \
|
||||
.error_func = fsck_error_function \
|
||||
}
|
||||
#define FSCK_OPTIONS_STRICT { \
|
||||
.strict = 1, \
|
||||
.gitmodules_found = OIDSET_INIT, \
|
||||
.gitmodules_done = OIDSET_INIT, \
|
||||
.error_func = fsck_error_function, \
|
||||
}
|
||||
#define FSCK_OPTIONS_MISSING_GITMODULES { \
|
||||
.strict = 1, \
|
||||
.gitmodules_found = OIDSET_INIT, \
|
||||
.gitmodules_done = OIDSET_INIT, \
|
||||
.error_func = fsck_error_cb_print_missing_gitmodules, \
|
||||
}
|
||||
|
||||
/* descend in all linked child objects
|
||||
* the return value is:
|
||||
@ -62,8 +164,6 @@ int fsck_walk(struct object *obj, void *data, struct fsck_options *options);
|
||||
int fsck_object(struct object *obj, void *data, unsigned long size,
|
||||
struct fsck_options *options);
|
||||
|
||||
void register_found_gitmodules(const struct object_id *oid);
|
||||
|
||||
/*
|
||||
* fsck a tag, and pass info about it back to the caller. This is
|
||||
* exposed fsck_object() internals for git-mktag(1).
|
||||
@ -109,7 +209,6 @@ const char *fsck_describe_object(struct fsck_options *options,
|
||||
* git_config() callback for use by fsck-y tools that want to support
|
||||
* fsck.<msg> fsck.skipList etc.
|
||||
*/
|
||||
int fsck_config_internal(const char *var, const char *value, void *cb,
|
||||
struct fsck_options *options);
|
||||
int git_fsck_config(const char *var, const char *value, void *cb);
|
||||
|
||||
#endif
|
||||
|
Loading…
Reference in New Issue
Block a user