Merge branch 'kn/ref-filter-branch-list'
[gitweb.git] / builtin / add.c
index b1dddb4ac635ab7e2cc55be546002f8e68efa331..9f53f020d0fc7184ac803a4346bdf426a814ed72 100644 (file)
@@ -26,10 +26,25 @@ static int patch_interactive, add_interactive, edit_interactive;
 static int take_worktree_changes;
 
 struct update_callback_data {
-       int flags, force_mode;
+       int flags;
        int add_errors;
 };
 
+static void chmod_pathspec(struct pathspec *pathspec, int force_mode)
+{
+       int i;
+
+       for (i = 0; i < active_nr; i++) {
+               struct cache_entry *ce = active_cache[i];
+
+               if (pathspec && !ce_path_match(ce, pathspec, NULL))
+                       continue;
+
+               if (chmod_cache_entry(ce, force_mode) < 0)
+                       fprintf(stderr, "cannot chmod '%s'", ce->name);
+       }
+}
+
 static int fix_unmerged_status(struct diff_filepair *p,
                               struct update_callback_data *data)
 {
@@ -65,8 +80,7 @@ static void update_callback(struct diff_queue_struct *q,
                        die(_("unexpected diff status %c"), p->status);
                case DIFF_STATUS_MODIFIED:
                case DIFF_STATUS_TYPE_CHANGED:
-                       if (add_file_to_index(&the_index, path,
-                                       data->flags, data->force_mode)) {
+                       if (add_file_to_index(&the_index, path, data->flags)) {
                                if (!(data->flags & ADD_CACHE_IGNORE_ERRORS))
                                        die(_("updating files failed"));
                                data->add_errors++;
@@ -84,15 +98,14 @@ static void update_callback(struct diff_queue_struct *q,
        }
 }
 
-int add_files_to_cache(const char *prefix, const struct pathspec *pathspec,
-       int flags, int force_mode)
+int add_files_to_cache(const char *prefix,
+                      const struct pathspec *pathspec, int flags)
 {
        struct update_callback_data data;
        struct rev_info rev;
 
        memset(&data, 0, sizeof(data));
        data.flags = flags;
-       data.force_mode = force_mode;
 
        init_revisions(&rev, prefix);
        setup_revisions(0, NULL, &rev, NULL);
@@ -281,7 +294,7 @@ static int add_config(const char *var, const char *value, void *cb)
        return git_default_config(var, value, cb);
 }
 
-static int add_files(struct dir_struct *dir, int flags, int force_mode)
+static int add_files(struct dir_struct *dir, int flags)
 {
        int i, exit_status = 0;
 
@@ -294,8 +307,7 @@ static int add_files(struct dir_struct *dir, int flags, int force_mode)
        }
 
        for (i = 0; i < dir->nr; i++)
-               if (add_file_to_index(&the_index, dir->entries[i]->name,
-                               flags, force_mode)) {
+               if (add_file_to_index(&the_index, dir->entries[i]->name, flags)) {
                        if (!ignore_add_errors)
                                die(_("adding files failed"));
                        exit_status = 1;
@@ -308,7 +320,7 @@ int cmd_add(int argc, const char **argv, const char *prefix)
        int exit_status = 0;
        struct pathspec pathspec;
        struct dir_struct dir;
-       int flags, force_mode;
+       int flags;
        int add_new_files;
        int require_pathspec;
        char *seen = NULL;
@@ -342,19 +354,14 @@ int cmd_add(int argc, const char **argv, const char *prefix)
        if (!show_only && ignore_missing)
                die(_("Option --ignore-missing can only be used together with --dry-run"));
 
-       if (!chmod_arg)
-               force_mode = 0;
-       else if (!strcmp(chmod_arg, "-x"))
-               force_mode = 0666;
-       else if (!strcmp(chmod_arg, "+x"))
-               force_mode = 0777;
-       else
+       if (chmod_arg && ((chmod_arg[0] != '-' && chmod_arg[0] != '+') ||
+                         chmod_arg[1] != 'x' || chmod_arg[2]))
                die(_("--chmod param '%s' must be either -x or +x"), chmod_arg);
 
        add_new_files = !take_worktree_changes && !refresh_only;
        require_pathspec = !(take_worktree_changes || (0 < addremove_explicit));
 
-       hold_locked_index(&lock_file, 1);
+       hold_locked_index(&lock_file, LOCK_DIE_ON_ERROR);
 
        flags = ((verbose ? ADD_CACHE_VERBOSE : 0) |
                 (show_only ? ADD_CACHE_PRETEND : 0) |
@@ -441,11 +448,13 @@ int cmd_add(int argc, const char **argv, const char *prefix)
 
        plug_bulk_checkin();
 
-       exit_status |= add_files_to_cache(prefix, &pathspec, flags, force_mode);
+       exit_status |= add_files_to_cache(prefix, &pathspec, flags);
 
        if (add_new_files)
-               exit_status |= add_files(&dir, flags, force_mode);
+               exit_status |= add_files(&dir, flags);
 
+       if (chmod_arg && pathspec.nr)
+               chmod_pathspec(&pathspec, chmod_arg[0]);
        unplug_bulk_checkin();
 
 finish: