summaryrefslogtreecommitdiff
path: root/builtin/cat-file.c
diff options
context:
space:
mode:
authorJunio C Hamano <gitster@pobox.com>2015-06-01 19:45:16 (GMT)
committerJunio C Hamano <gitster@pobox.com>2015-06-01 19:45:16 (GMT)
commit67f0b6f3b2226ea858c616028375dcc3c46ccc37 (patch)
tree598a4db2b8e80916be9c2074490070bdd15e4df4 /builtin/cat-file.c
parent4ba5bb5531c6ec64a57ae2754ba51ce477eebaf0 (diff)
parent122d53464b29d3ac20891c5ee2f75ac5ecbb7b20 (diff)
downloadgit-67f0b6f3b2226ea858c616028375dcc3c46ccc37.zip
git-67f0b6f3b2226ea858c616028375dcc3c46ccc37.tar.gz
git-67f0b6f3b2226ea858c616028375dcc3c46ccc37.tar.bz2
Merge branch 'dt/cat-file-follow-symlinks'
"git cat-file --batch(-check)" learned the "--follow-symlinks" option that follows an in-tree symbolic link when asked about an object via extended SHA-1 syntax, e.g. HEAD:RelNotes that points at Documentation/RelNotes/2.5.0.txt. With the new option, the command behaves as if HEAD:Documentation/RelNotes/2.5.0.txt was given as input instead. * dt/cat-file-follow-symlinks: cat-file: add --follow-symlinks to --batch sha1_name: get_sha1_with_context learns to follow symlinks tree-walk: learn get_tree_entry_follow_symlinks
Diffstat (limited to 'builtin/cat-file.c')
-rw-r--r--builtin/cat-file.c51
1 files changed, 45 insertions, 6 deletions
diff --git a/builtin/cat-file.c b/builtin/cat-file.c
index ecb4888..049a95f 100644
--- a/builtin/cat-file.c
+++ b/builtin/cat-file.c
@@ -8,6 +8,7 @@
#include "parse-options.h"
#include "userdiff.h"
#include "streaming.h"
+#include "tree-walk.h"
static int cat_one_file(int opt, const char *exp_type, const char *obj_name,
int unknown_type)
@@ -233,6 +234,7 @@ static void print_object_or_die(int fd, struct expand_data *data)
struct batch_options {
int enabled;
+ int follow_symlinks;
int print_contents;
const char *format;
};
@@ -241,12 +243,44 @@ static int batch_one_object(const char *obj_name, struct batch_options *opt,
struct expand_data *data)
{
struct strbuf buf = STRBUF_INIT;
+ struct object_context ctx;
+ int flags = opt->follow_symlinks ? GET_SHA1_FOLLOW_SYMLINKS : 0;
+ enum follow_symlinks_result result;
if (!obj_name)
return 1;
- if (get_sha1(obj_name, data->sha1)) {
- printf("%s missing\n", obj_name);
+ result = get_sha1_with_context(obj_name, flags, data->sha1, &ctx);
+ if (result != FOUND) {
+ switch (result) {
+ case MISSING_OBJECT:
+ printf("%s missing\n", obj_name);
+ break;
+ case DANGLING_SYMLINK:
+ printf("dangling %"PRIuMAX"\n%s\n",
+ (uintmax_t)strlen(obj_name), obj_name);
+ break;
+ case SYMLINK_LOOP:
+ printf("loop %"PRIuMAX"\n%s\n",
+ (uintmax_t)strlen(obj_name), obj_name);
+ break;
+ case NOT_DIR:
+ printf("notdir %"PRIuMAX"\n%s\n",
+ (uintmax_t)strlen(obj_name), obj_name);
+ break;
+ default:
+ die("BUG: unknown get_sha1_with_context result %d\n",
+ result);
+ break;
+ }
+ fflush(stdout);
+ return 0;
+ }
+
+ if (ctx.mode == 0) {
+ printf("symlink %"PRIuMAX"\n%s\n",
+ (uintmax_t)ctx.symlink_path.len,
+ ctx.symlink_path.buf);
fflush(stdout);
return 0;
}
@@ -333,7 +367,7 @@ static int batch_objects(struct batch_options *opt)
static const char * const cat_file_usage[] = {
N_("git cat-file (-t [--allow-unknown-type]|-s [--allow-unknown-type]|-e|-p|<type>|--textconv) <object>"),
- N_("git cat-file (--batch | --batch-check) < <list-of-objects>"),
+ N_("git cat-file (--batch | --batch-check) [--follow-symlinks] < <list-of-objects>"),
NULL
};
@@ -351,9 +385,8 @@ static int batch_option_callback(const struct option *opt,
{
struct batch_options *bo = opt->value;
- if (unset) {
- memset(bo, 0, sizeof(*bo));
- return 0;
+ if (bo->enabled) {
+ return 1;
}
bo->enabled = 1;
@@ -387,6 +420,8 @@ int cmd_cat_file(int argc, const char **argv, const char *prefix)
{ OPTION_CALLBACK, 0, "batch-check", &batch, "format",
N_("show info about objects fed from the standard input"),
PARSE_OPT_OPTARG, batch_option_callback },
+ OPT_BOOL(0, "follow-symlinks", &batch.follow_symlinks,
+ N_("follow in-tree symlinks (used with --batch or --batch-check)")),
OPT_END()
};
@@ -411,6 +446,10 @@ int cmd_cat_file(int argc, const char **argv, const char *prefix)
usage_with_options(cat_file_usage, options);
}
+ if (batch.follow_symlinks && !batch.enabled) {
+ usage_with_options(cat_file_usage, options);
+ }
+
if (batch.enabled)
return batch_objects(&batch);