list-objects-filter-options.con commit sha1-name.c: for ":/", find detached HEAD commits (6b3351e)
   1#include "cache.h"
   2#include "commit.h"
   3#include "config.h"
   4#include "revision.h"
   5#include "argv-array.h"
   6#include "list-objects.h"
   7#include "list-objects-filter.h"
   8#include "list-objects-filter-options.h"
   9
  10/*
  11 * Parse value of the argument to the "filter" keyword.
  12 * On the command line this looks like:
  13 *       --filter=<arg>
  14 * and in the pack protocol as:
  15 *       "filter" SP <arg>
  16 *
  17 * The filter keyword will be used by many commands.
  18 * See Documentation/rev-list-options.txt for allowed values for <arg>.
  19 *
  20 * Capture the given arg as the "filter_spec".  This can be forwarded to
  21 * subordinate commands when necessary.  We also "intern" the arg for
  22 * the convenience of the current command.
  23 */
  24int parse_list_objects_filter(struct list_objects_filter_options *filter_options,
  25                              const char *arg)
  26{
  27        const char *v0;
  28
  29        if (filter_options->choice)
  30                die(_("multiple object filter types cannot be combined"));
  31
  32        filter_options->filter_spec = strdup(arg);
  33
  34        if (!strcmp(arg, "blob:none")) {
  35                filter_options->choice = LOFC_BLOB_NONE;
  36                return 0;
  37        }
  38
  39        if (skip_prefix(arg, "blob:limit=", &v0)) {
  40                if (!git_parse_ulong(v0, &filter_options->blob_limit_value))
  41                        die(_("invalid filter-spec expression '%s'"), arg);
  42                filter_options->choice = LOFC_BLOB_LIMIT;
  43                return 0;
  44        }
  45
  46        if (skip_prefix(arg, "sparse:oid=", &v0)) {
  47                struct object_context oc;
  48                struct object_id sparse_oid;
  49
  50                /*
  51                 * Try to parse <oid-expression> into an OID for the current
  52                 * command, but DO NOT complain if we don't have the blob or
  53                 * ref locally.
  54                 */
  55                if (!get_oid_with_context(v0, GET_OID_BLOB,
  56                                          &sparse_oid, &oc))
  57                        filter_options->sparse_oid_value = oiddup(&sparse_oid);
  58                filter_options->choice = LOFC_SPARSE_OID;
  59                return 0;
  60        }
  61
  62        if (skip_prefix(arg, "sparse:path=", &v0)) {
  63                filter_options->choice = LOFC_SPARSE_PATH;
  64                filter_options->sparse_path_value = strdup(v0);
  65                return 0;
  66        }
  67
  68        die(_("invalid filter-spec expression '%s'"), arg);
  69        return 0;
  70}
  71
  72int opt_parse_list_objects_filter(const struct option *opt,
  73                                  const char *arg, int unset)
  74{
  75        struct list_objects_filter_options *filter_options = opt->value;
  76
  77        if (unset || !arg) {
  78                list_objects_filter_release(filter_options);
  79                return 0;
  80        }
  81
  82        return parse_list_objects_filter(filter_options, arg);
  83}
  84
  85void list_objects_filter_release(
  86        struct list_objects_filter_options *filter_options)
  87{
  88        free(filter_options->filter_spec);
  89        free(filter_options->sparse_oid_value);
  90        free(filter_options->sparse_path_value);
  91        memset(filter_options, 0, sizeof(*filter_options));
  92}