SYNOPSIS
--------
-.gitattributes
+$GIT_DIR/info/attributes, gitattributes
DESCRIPTION
Unspecified::
No glob pattern matches the path, and nothing says if
- the path has or does not have the attribute.
+ the path has or does not have the attribute, the
+ attribute for the path is said to be Unspecified.
When more than one glob pattern matches the path, a later line
-overrides an earlier line.
+overrides an earlier line. This overriding is done per
+attribute.
When deciding what attributes are assigned to a path, git
consults `$GIT_DIR/info/attributes` file (which has the highest
-------
Certain operations by git can be influenced by assigning
-particular attributes to a path. Currently, three operations
-are attributes-aware.
+particular attributes to a path. Currently, the following
+operations are attributes-aware.
Checking-out and checking-in
~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-The attribute `crlf` affects how the contents stored in the
+These attributes affect how the contents stored in the
repository are copied to the working tree files when commands
-such as `git checkout` and `git merge` run. It also affects how
+such as `git checkout` and `git merge` run. They also affect how
git stores the contents you prepare in the working tree in the
repository upon `git add` and `git commit`.
+`crlf`
+^^^^^^
+
+This attribute controls the line-ending convention.
+
Set::
Setting the `crlf` attribute on a path is meant to mark
upon checkout.
+`ident`
+^^^^^^^
+
+When the attribute `ident` is set to a path, git replaces
+`$Id$` in the blob object with `$Id:`, followed by
+40-character hexadecimal blob object name, followed by a dollar
+sign `$` upon checkout. Any byte sequence that begins with
+`$Id:` and ends with `$` in the worktree file is replaced
+with `$Id$` upon check-in.
+
+
+`filter`
+^^^^^^^^
+
+A `filter` attribute can be set to a string value. This names
+filter driver specified in the configuration.
+
+A filter driver consists of `clean` command and `smudge`
+command, either of which can be left unspecified. Upon
+checkout, when `smudge` command is specified, the command is fed
+the blob object from its standard input, and its standard output
+is used to update the worktree file. Similarly, `clean` command
+is used to convert the contents of worktree file upon checkin.
+
+Missing filter driver definition in the config is not an error
+but makes the filter a no-op passthru.
+
+The content filtering is done to massage the content into a
+shape that is more convenient for the platform, filesystem, and
+the user to use. The keyword here is "more convenient" and not
+"turning something unusable into usable". In other words, the
+intent is that if someone unsets the filter driver definition,
+or does not have the appropriate filter program, the project
+should still be usable.
+
+
+Interaction between checkin/checkout attributes
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+In the check-in codepath, the worktree file is first converted
+with `filter` driver (if specified and corresponding driver
+defined), then the result is processed with `ident` (if
+specified), and then finally with `crlf` (again, if specified
+and applicable).
+
+In the check-out codepath, the blob content is first converted
+with `crlf`, and then `ident` and fed to `filter`.
+
+
Generating diff text
~~~~~~~~~~~~~~~~~~~~
The attribute `diff` affects if `git diff` generates textual
-patch for the path or just says `Binary files differ`.
+patch for the path or just says `Binary files differ`. It also
+can affect what line is shown on the hunk header `@@ -k,l +n,m @@`
+line.
Set::
text, it is treated as text. Otherwise it would
generate `Binary files differ`.
-Any other value set to `diff` attribute is ignored and git acts
-as if the attribute is left unspecified.
+String::
+
+ Diff is shown using the specified custom diff driver.
+ The driver program is given its input using the same
+ calling convention as used for GIT_EXTERNAL_DIFF
+ program. This name is also used for custom hunk header
+ selection.
+
+
+Defining a custom diff driver
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+The definition of a diff driver is done in `gitconfig`, not
+`gitattributes` file, so strictly speaking this manual page is a
+wrong place to talk about it. However...
+
+To define a custom diff driver `jcdiff`, add a section to your
+`$GIT_DIR/config` file (or `$HOME/.gitconfig` file) like this:
+
+----------------------------------------------------------------
+[diff "jcdiff"]
+ command = j-c-diff
+----------------------------------------------------------------
+
+When git needs to show you a diff for the path with `diff`
+attribute set to `jcdiff`, it calls the command you specified
+with the above configuration, i.e. `j-c-diff`, with 7
+parameters, just like `GIT_EXTERNAL_DIFF` program is called.
+See gitlink:git[7] for details.
+
+
+Defining a custom hunk-header
+^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+Each group of changes (called "hunk") in the textual diff output
+is prefixed with a line of the form:
+
+ @@ -k,l +n,m @@ TEXT
+
+The text is called 'hunk header', and by default a line that
+begins with an alphabet, an underscore or a dollar sign is used,
+which matches what GNU `diff -p` output uses. This default
+selection however is not suited for some contents, and you can
+use customized pattern to make a selection.
+
+First in .gitattributes, you would assign the `diff` attribute
+for paths.
+
+------------------------
+*.tex diff=tex
+------------------------
+
+Then, you would define "diff.tex.funcname" configuration to
+specify a regular expression that matches a line that you would
+want to appear as the hunk header, like this:
+
+------------------------
+[diff "tex"]
+ funcname = "^\\(\\\\\\(sub\\)*section{.*\\)$"
+------------------------
+
+Note. A single level of backslashes are eaten by the
+configuration file parser, so you would need to double the
+backslashes; the pattern above picks a line that begins with a
+backslash, and zero or more occurrences of `sub` followed by
+`section` followed by open brace, to the end of line.
+
+There are a few built-in patterns to make this easier, and `tex`
+is one of them, so you do not have to write the above in your
+configuration file (you still need to enable this with the
+attribute mechanism, via `.gitattributes`). Another built-in
+pattern is defined for `java` that defines a pattern suitable
+for program text in Java language.
Performing a three-way merge
different merge driver to be used for paths to which the
`merge` attribute is unspecified.
-Any other string value::
+String::
3-way merge is performed using the specified custom
merge driver. The built-in 3-way merge driver can be
explicitly specified by asking for "text" driver; the
built-in "take the current branch" driver can be
- requested by "binary".
+ requested with "binary".
Defining a custom merge driver
the attributes given to path `t/abc` are computed as follows:
1. By examining `t/.gitattributes` (which is in the same
- diretory as the path in question), git finds that the first
+ directory as the path in question), git finds that the first
line matches. `merge` attribute is set. It also finds that
the second line matches, and attributes `foo` and `bar`
are unset.
and `bar` attributes should be given to this path, so it
leaves `foo` and `bar` unset. Attribute `baz` is set.
-3. Finally it examines `$GIT_DIR/info/gitattributes`. This file
+3. Finally it examines `$GIT_DIR/info/attributes`. This file
is used to override the in-tree settings. The first line is
a match, and `foo` is set, `bar` is reverted to unspecified
state, and `baz` is unset.
-As the result, the attributes assignement to `t/abc` becomes:
+As the result, the attributes assignment to `t/abc` becomes:
----------------------------------------------------------------
foo set to true