All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH v2] t0027: Add tests for get_stream_filter()
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
@ 2016-01-24  7:55 ` tboegi
  2016-01-27  6:34   ` Junio C Hamano
  2016-01-27 15:15 ` [PATCH v1 1/6] " tboegi
                   ` (27 subsequent siblings)
  28 siblings, 1 reply; 47+ messages in thread
From: tboegi @ 2016-01-24  7:55 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

When a filter is configured, a different code-path is used in
convert.c and entry.c via get_stream_filter(), but there are no test cases yet.

Add tests for the filter API by configuring the ident filter.
The result of the SHA1 conversion is not checked, this is already
done in other TC.

Add a parameter to checkout_files() in t0027.
While changing the signature, add another parameter for the eol= attribute.
This is currently unused, tests for e.g.
"* text=auto eol=lf" will be added in a separate commit.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
- This needs to go on top of  tb/ls-files-eol
changes since v1:
- minor type, add signoff (Thanks Eric)
- Can not use sed as intended:
  Non-Gnu sed like Mac OS needs "lines" to have a LF at the end,
  otherwise they add one. Use tr instead.
  
t/t0027-auto-crlf.sh | 262 ++++++++++++++++++++++++++++-----------------------
 1 file changed, 146 insertions(+), 116 deletions(-)

diff --git a/t/t0027-auto-crlf.sh b/t/t0027-auto-crlf.sh
index 504e5a0..f830243 100755
--- a/t/t0027-auto-crlf.sh
+++ b/t/t0027-auto-crlf.sh
@@ -21,32 +21,45 @@ compare_ws_file () {
 	pfx=$1
 	exp=$2.expect
 	act=$pfx.actual.$3
-	tr '\015\000' QN <"$2" >"$exp" &&
-	tr '\015\000' QN <"$3" >"$act" &&
+	tr '\015\000abcdef01234567890' QN00000000000000000 <"$2" >"$exp" &&
+	tr '\015\000abcdef01234567890' QN00000000000000000 <"$3" >"$act" &&
 	test_cmp $exp $act &&
 	rm $exp $act
 }
 
 create_gitattributes () {
 	attr=$1
+	ident=$2
+	case "$2" in
+		"")
+			>.gitattributes
+			;;
+		i)
+			echo "* ident" >.gitattributes
+			;;
+		*)
+			echo >&2 invalid ident: $2
+			exit 1
+	esac
+
 	case "$attr" in
 		auto)
-		echo "*.txt text=auto" >.gitattributes
+		echo "*.txt text=auto" >>.gitattributes
 		;;
 		text)
-		echo "*.txt text" >.gitattributes
+		echo "*.txt text" >>.gitattributes
 		;;
 		-text)
-		echo "*.txt -text" >.gitattributes
+		echo "*.txt -text" >>.gitattributes
 		;;
 		crlf)
-		echo "*.txt eol=crlf" >.gitattributes
+		echo "*.txt eol=crlf" >>.gitattributes
 		;;
 		lf)
-		echo "*.txt eol=lf" >.gitattributes
+		echo "*.txt eol=lf" >>.gitattributes
 		;;
 		"")
-		echo >.gitattributes
+		#echo >.gitattributes
 		;;
 		*)
 		echo >&2 invalid attribute: $attr
@@ -90,7 +103,7 @@ commit_check_warn () {
 	lfmixcr=$6
 	crlfnul=$7
 	pfx=crlf_${crlf}_attr_${attr}
-	create_gitattributes "$attr" &&
+	create_gitattributes "$attr" "" &&
 	for f in LF CRLF LF_mix_CR CRLF_mix_LF LF_nul CRLF_nul
 	do
 		fname=${pfx}_$f.txt &&
@@ -115,7 +128,7 @@ commit_chk_wrnNNO () {
 	crlfnul=$7
 	pfx=NNO_${crlf}_attr_${attr}
 	#Commit files on top of existing file
-	create_gitattributes "$attr" &&
+	create_gitattributes "$attr" "" &&
 	for f in LF CRLF CRLF_mix_LF LF_mix_CR CRLF_nul
 	do
 		fname=${pfx}_$f.txt &&
@@ -208,28 +221,30 @@ check_in_repo_NNO () {
 }
 
 checkout_files () {
-	eol=$1
-	crlf=$2
-	attr=$3
-	lfname=$4
-	crlfname=$5
-	lfmixcrlf=$6
-	lfmixcr=$7
-	crlfnul=$8
-	create_gitattributes $attr &&
+	attr=$1 ; shift
+	ident=$1; shift
+	aeol=$1 ; shift
+	crlf=$1 ; shift
+	ceol=$1 ; shift
+	lfname=$1 ; shift
+	crlfname=$1 ; shift
+	lfmixcrlf=$1 ; shift
+	lfmixcr=$1 ; shift
+	crlfnul=$1 ; shift
+	create_gitattributes "$attr" "$ident" &&
 	git config core.autocrlf $crlf &&
-	pfx=eol_${eol}_crlf_${crlf}_attr_${attr}_ &&
+	pfx=eol_${ceol}_crlf_${crlf}_attr_${attr}_ &&
 	for f in LF CRLF LF_mix_CR CRLF_mix_LF LF_nul
 	do
 		rm crlf_false_attr__$f.txt &&
-		if test -z "$eol"; then
+		if test -z "$ceol"; then
 			git checkout crlf_false_attr__$f.txt
 		else
-			git -c core.eol=$eol checkout crlf_false_attr__$f.txt
+			git -c core.eol=$ceol checkout crlf_false_attr__$f.txt
 		fi
 	done
 
-	test_expect_success "ls-files --eol $lfname ${pfx}LF.txt" '
+	test_expect_success "ls-files --eol i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol" '
 		test_when_finished "rm expect actual" &&
 		sort <<-EOF >expect &&
 		i/crlf w/$(stats_ascii $crlfname) crlf_false_attr__CRLF.txt
@@ -244,19 +259,19 @@ checkout_files () {
 		sort >actual &&
 		test_cmp expect actual
 	'
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=LF" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=LF" "
 		compare_ws_file $pfx $lfname    crlf_false_attr__LF.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=CRLF" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=CRLF" "
 		compare_ws_file $pfx $crlfname  crlf_false_attr__CRLF.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=CRLF_mix_LF" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=CRLF_mix_LF" "
 		compare_ws_file $pfx $lfmixcrlf crlf_false_attr__CRLF_mix_LF.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=LF_mix_CR" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=LF_mix_CR" "
 		compare_ws_file $pfx $lfmixcr   crlf_false_attr__LF_mix_CR.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=LF_nul" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=LF_nul" "
 		compare_ws_file $pfx $crlfnul   crlf_false_attr__LF_nul.txt
 	"
 }
@@ -301,14 +316,13 @@ test_expect_success 'setup master' '
 	git checkout -b master &&
 	git add .gitattributes &&
 	git commit -m "add .gitattributes" "" &&
-	printf "line1\nline2\nline3"     >LF &&
-	printf "line1\r\nline2\r\nline3" >CRLF &&
-	printf "line1\r\nline2\nline3"   >repoMIX &&
-	printf "line1\r\nline2\nline3"   >CRLF_mix_LF &&
-	printf "line1\nline2\rline3"     >LF_mix_CR &&
-	printf "line1\r\nline2\rline3"   >CRLF_mix_CR &&
-	printf "line1Q\r\nline2\r\nline3" | q_to_nul >CRLF_nul &&
-	printf "line1Q\nline2\nline3" | q_to_nul >LF_nul &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONE\nLINETWO\nLINETHREE"     >LF &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\r\nLINEONE\r\nLINETWO\r\nLINETHREE" >CRLF &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONE\r\nLINETWO\nLINETHREE"   >CRLF_mix_LF &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONE\nLINETWO\rLINETHREE"     >LF_mix_CR &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\r\nLINEONE\r\nLINETWO\rLINETHREE"   >CRLF_mix_CR &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\r\nLINEONEQ\r\nLINETWO\r\nLINETHREE" | q_to_nul >CRLF_nul &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONEQ\nLINETWO\nLINETHREE" | q_to_nul >LF_nul &&
 	create_NNO_files CRLF_mix_LF CRLF_mix_LF CRLF_mix_LF CRLF_mix_LF CRLF_mix_LF &&
 	git -c core.autocrlf=false add NNO_*.txt &&
 	git commit -m "mixed line endings" &&
@@ -449,23 +463,18 @@ check_in_repo_NNO input "-text" LF        CRLF      CRLF_mix_LF  LF_mix_CR 	CRLF
 # How to read the table below:
 # - checkout_files will check multiple files with a combination of settings
 #   and attributes (core.autocrlf=input is forbidden with core.eol=crlf)
-# - parameter $1 : core.eol               lf | crlf
-# - parameter $2 : core.autocrlf          false | true | input
-# - parameter $3 : text in .gitattributs  "" (empty) | auto | text | -text
-# - parameter $4 : reference for a file with only LF in the repo
-# - parameter $5 : reference for a file with only CRLF in the repo
-# - parameter $6 : reference for a file with mixed LF and CRLF in the repo
-# - parameter $7 : reference for a file with LF and CR in the repo (does somebody uses this ?)
-# - parameter $8 : reference for a file with CRLF and a NUL (should be handled as binary when auto)
-
-#                                            What we have in the repo:
-#                                            ----------------- EOL in repo ----------------
-#                                            LF    CRLF  CRLF_mix_LF  LF_mix_CR    CRLF_nul
-#                   settings with checkout:
-#                   core.   core.   .gitattr
-#                    eol     acrlf
-#                                            ----------------------------------------------
-#                                            What we want to have in the working tree:
+#
+# - parameter $1 	: text in .gitattributs  "" (empty) | auto | text | -text
+# - parameter $2 	: ident                  "" | i (i == ident)
+# - parameter $3 	: eol in .gitattributs   "" (empty) | lf | crlf
+# - parameter $4 	: core.autocrlf          false | true | input
+# - parameter $5 	: core.eol               "" | lf | crlf | "native"
+# - parameter $6 	: reference for a file with only LF in the repo
+# - parameter $7 	: reference for a file with only CRLF in the repo
+# - parameter $8 	: reference for a file with mixed LF and CRLF in the repo
+# - parameter $9 	: reference for a file with LF and CR in the repo
+# - parameter $10 : reference for a file with CRLF and a NUL (should be handled as binary when auto)
+
 if test_have_prereq NATIVE_CRLF
 then
 MIX_CRLF_LF=CRLF
@@ -480,69 +489,90 @@ LFNUL=LF_nul
 fi
 export CRLF_MIX_LF_CR MIX NL
 
-checkout_files    lf      false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "auto"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    lf      input "auto"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "text"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    lf      input "text"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      input "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      input "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    lf      true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    lf      input "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-
-checkout_files    crlf    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    false "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    crlf    true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    crlf    false "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    crlf    true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    crlf    false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    crlf    true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-
-checkout_files    ""      false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "auto"    $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
-checkout_files    ""      true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    ""      input "auto"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "text"    $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
-checkout_files    ""      true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    ""      input "text"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      input "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      input "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    ""      true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    ""      input "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-
-checkout_files    native  false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  false "auto"    $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
-checkout_files    native  true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    native  false "text"    $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
-checkout_files    native  true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    native  false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    native  true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+checkout_files ""      "" ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    true   crlf     CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    true   lf       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    true   native   CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    false  ""       $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    false  crlf     CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    false  native   $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    true   ""       CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    true   crlf     CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    true   lf       CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    true   native   CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    false  ""       $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    false  native   $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+
+for id in "" i;
+do
+	checkout_files "crlf"  "$id" ""    false  ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    false  crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    false  lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    false  native   CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    input  ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    input  lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   native   CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "lf"    "$id" ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    false  ""       $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
+	checkout_files "text"  "$id" ""    false  crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    false  native   $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
+	checkout_files "text"  "$id" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    true   ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    true   crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    true   lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    true   native   CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "-text" "$id" ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+done
 
 # Should be the last test case: remove some files from the worktree
 test_expect_success 'ls-files --eol -d -z' '
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* Re: [PATCH v2] t0027: Add tests for get_stream_filter()
  2016-01-24  7:55 ` [PATCH v2] t0027: Add tests for get_stream_filter() tboegi
@ 2016-01-27  6:34   ` Junio C Hamano
  2016-01-27  9:05     ` Torsten Bögershausen
  0 siblings, 1 reply; 47+ messages in thread
From: Junio C Hamano @ 2016-01-27  6:34 UTC (permalink / raw)
  To: tboegi; +Cc: git

tboegi@web.de writes:

> From: Torsten Bögershausen <tboegi@web.de>
>
> When a filter is configured, a different code-path is used in
> convert.c and entry.c via get_stream_filter(), but there are no test cases yet.
>
> Add tests for the filter API by configuring the ident filter.
> The result of the SHA1 conversion is not checked, this is already
> done in other TC.
>
> Add a parameter to checkout_files() in t0027.
> While changing the signature, add another parameter for the eol= attribute.
> This is currently unused, tests for e.g.
> "* text=auto eol=lf" will be added in a separate commit.
>
> Signed-off-by: Torsten Bögershausen <tboegi@web.de>
> ---
> - This needs to go on top of  tb/ls-files-eol

With missing "separate commit", I am having a hard time to decide if
this is something I should pick up at this moment, or I should wait
until that separate commit materializes.  What is your intention?

Thanks.

^ permalink raw reply	[flat|nested] 47+ messages in thread

* Re: [PATCH v2] t0027: Add tests for get_stream_filter()
  2016-01-27  6:34   ` Junio C Hamano
@ 2016-01-27  9:05     ` Torsten Bögershausen
  0 siblings, 0 replies; 47+ messages in thread
From: Torsten Bögershausen @ 2016-01-27  9:05 UTC (permalink / raw)
  To: Junio C Hamano, tboegi; +Cc: git


- This needs to go on top of  tb/ls-files-eol

> With missing "separate commit", I am having a hard time to decide if
> this is something I should pick up at this moment, or I should wait
> until that separate commit materializes.  What is your intention?
>
I send a serious including this patch the next days.
If there are more review comments, they are welcome.

^ permalink raw reply	[flat|nested] 47+ messages in thread

* [PATCH v1 1/6] t0027: Add tests for get_stream_filter()
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
  2016-01-24  7:55 ` [PATCH v2] t0027: Add tests for get_stream_filter() tboegi
@ 2016-01-27 15:15 ` tboegi
  2016-02-02 16:53 ` tboegi
                   ` (26 subsequent siblings)
  28 siblings, 0 replies; 47+ messages in thread
From: tboegi @ 2016-01-27 15:15 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

When a filter is configured, a different code-path is used in convert.c
and entry.c via get_stream_filter(), but there are no test cases yet.

Add tests for the filter API by configuring the ident filter.
The result of the SHA1 conversion is not checked, this is already
done in other TC.

Add a parameter to checkout_files() in t0027.
While changing the signature, add another parameter for the eol= attribute.
This is currently unused, tests for e.g.
"* text=auto eol=lf" will be added in a separate commit.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 t/t0027-auto-crlf.sh | 262 ++++++++++++++++++++++++++++-----------------------
 1 file changed, 146 insertions(+), 116 deletions(-)

diff --git a/t/t0027-auto-crlf.sh b/t/t0027-auto-crlf.sh
index 504e5a0..08fe6a5 100755
--- a/t/t0027-auto-crlf.sh
+++ b/t/t0027-auto-crlf.sh
@@ -21,32 +21,45 @@ compare_ws_file () {
 	pfx=$1
 	exp=$2.expect
 	act=$pfx.actual.$3
-	tr '\015\000' QN <"$2" >"$exp" &&
-	tr '\015\000' QN <"$3" >"$act" &&
+	tr '\015\000abcdef01234567890' QN00000000000000000 <"$2" >"$exp" &&
+	tr '\015\000abcdef01234567890' QN00000000000000000 <"$3" >"$act" &&
 	test_cmp $exp $act &&
 	rm $exp $act
 }
 
 create_gitattributes () {
 	attr=$1
+	ident=$2
+	case "$2" in
+		"")
+			>.gitattributes
+			;;
+		i)
+			echo "* ident" >.gitattributes
+			;;
+		*)
+			echo >&2 invalid ident: $2
+			exit 1
+	esac
+		 
 	case "$attr" in
 		auto)
-		echo "*.txt text=auto" >.gitattributes
+		echo "*.txt text=auto" >>.gitattributes
 		;;
 		text)
-		echo "*.txt text" >.gitattributes
+		echo "*.txt text" >>.gitattributes
 		;;
 		-text)
-		echo "*.txt -text" >.gitattributes
+		echo "*.txt -text" >>.gitattributes
 		;;
 		crlf)
-		echo "*.txt eol=crlf" >.gitattributes
+		echo "*.txt eol=crlf" >>.gitattributes
 		;;
 		lf)
-		echo "*.txt eol=lf" >.gitattributes
+		echo "*.txt eol=lf" >>.gitattributes
 		;;
 		"")
-		echo >.gitattributes
+		#echo >.gitattributes
 		;;
 		*)
 		echo >&2 invalid attribute: $attr
@@ -90,7 +103,7 @@ commit_check_warn () {
 	lfmixcr=$6
 	crlfnul=$7
 	pfx=crlf_${crlf}_attr_${attr}
-	create_gitattributes "$attr" &&
+	create_gitattributes "$attr" "" &&
 	for f in LF CRLF LF_mix_CR CRLF_mix_LF LF_nul CRLF_nul
 	do
 		fname=${pfx}_$f.txt &&
@@ -115,7 +128,7 @@ commit_chk_wrnNNO () {
 	crlfnul=$7
 	pfx=NNO_${crlf}_attr_${attr}
 	#Commit files on top of existing file
-	create_gitattributes "$attr" &&
+	create_gitattributes "$attr" "" &&
 	for f in LF CRLF CRLF_mix_LF LF_mix_CR CRLF_nul
 	do
 		fname=${pfx}_$f.txt &&
@@ -208,28 +221,30 @@ check_in_repo_NNO () {
 }
 
 checkout_files () {
-	eol=$1
-	crlf=$2
-	attr=$3
-	lfname=$4
-	crlfname=$5
-	lfmixcrlf=$6
-	lfmixcr=$7
-	crlfnul=$8
-	create_gitattributes $attr &&
+	attr=$1 ; shift
+	ident=$1; shift
+	aeol=$1 ; shift
+	crlf=$1 ; shift
+	ceol=$1 ; shift
+	lfname=$1 ; shift
+	crlfname=$1 ; shift
+	lfmixcrlf=$1 ; shift
+	lfmixcr=$1 ; shift
+	crlfnul=$1 ; shift
+	create_gitattributes "$attr" "$ident" &&
 	git config core.autocrlf $crlf &&
-	pfx=eol_${eol}_crlf_${crlf}_attr_${attr}_ &&
+	pfx=eol_${ceol}_crlf_${crlf}_attr_${attr}_ &&
 	for f in LF CRLF LF_mix_CR CRLF_mix_LF LF_nul
 	do
 		rm crlf_false_attr__$f.txt &&
-		if test -z "$eol"; then
+		if test -z "$ceol"; then
 			git checkout crlf_false_attr__$f.txt
 		else
-			git -c core.eol=$eol checkout crlf_false_attr__$f.txt
+			git -c core.eol=$ceol checkout crlf_false_attr__$f.txt
 		fi
 	done
 
-	test_expect_success "ls-files --eol $lfname ${pfx}LF.txt" '
+	test_expect_success "ls-files --eol attr=$attr i=$ident $aeol core.autocrlf=$crlf core.eol=$ceol" '
 		test_when_finished "rm expect actual" &&
 		sort <<-EOF >expect &&
 		i/crlf w/$(stats_ascii $crlfname) crlf_false_attr__CRLF.txt
@@ -244,19 +259,19 @@ checkout_files () {
 		sort >actual &&
 		test_cmp expect actual
 	'
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=LF" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=LF" "
 		compare_ws_file $pfx $lfname    crlf_false_attr__LF.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=CRLF" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=CRLF" "
 		compare_ws_file $pfx $crlfname  crlf_false_attr__CRLF.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=CRLF_mix_LF" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=CRLF_mix_LF" "
 		compare_ws_file $pfx $lfmixcrlf crlf_false_attr__CRLF_mix_LF.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=LF_mix_CR" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=LF_mix_CR" "
 		compare_ws_file $pfx $lfmixcr   crlf_false_attr__LF_mix_CR.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=LF_nul" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=LF_nul" "
 		compare_ws_file $pfx $crlfnul   crlf_false_attr__LF_nul.txt
 	"
 }
@@ -301,14 +316,13 @@ test_expect_success 'setup master' '
 	git checkout -b master &&
 	git add .gitattributes &&
 	git commit -m "add .gitattributes" "" &&
-	printf "line1\nline2\nline3"     >LF &&
-	printf "line1\r\nline2\r\nline3" >CRLF &&
-	printf "line1\r\nline2\nline3"   >repoMIX &&
-	printf "line1\r\nline2\nline3"   >CRLF_mix_LF &&
-	printf "line1\nline2\rline3"     >LF_mix_CR &&
-	printf "line1\r\nline2\rline3"   >CRLF_mix_CR &&
-	printf "line1Q\r\nline2\r\nline3" | q_to_nul >CRLF_nul &&
-	printf "line1Q\nline2\nline3" | q_to_nul >LF_nul &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONE\nLINETWO\nLINETHREE"     >LF &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\r\nLINEONE\r\nLINETWO\r\nLINETHREE" >CRLF &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONE\r\nLINETWO\nLINETHREE"   >CRLF_mix_LF &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONE\nLINETWO\rLINETHREE"     >LF_mix_CR &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\r\nLINEONE\r\nLINETWO\rLINETHREE"   >CRLF_mix_CR &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\r\nLINEONEQ\r\nLINETWO\r\nLINETHREE" | q_to_nul >CRLF_nul &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONEQ\nLINETWO\nLINETHREE" | q_to_nul >LF_nul &&
 	create_NNO_files CRLF_mix_LF CRLF_mix_LF CRLF_mix_LF CRLF_mix_LF CRLF_mix_LF &&
 	git -c core.autocrlf=false add NNO_*.txt &&
 	git commit -m "mixed line endings" &&
@@ -449,23 +463,18 @@ check_in_repo_NNO input "-text" LF        CRLF      CRLF_mix_LF  LF_mix_CR 	CRLF
 # How to read the table below:
 # - checkout_files will check multiple files with a combination of settings
 #   and attributes (core.autocrlf=input is forbidden with core.eol=crlf)
-# - parameter $1 : core.eol               lf | crlf
-# - parameter $2 : core.autocrlf          false | true | input
-# - parameter $3 : text in .gitattributs  "" (empty) | auto | text | -text
-# - parameter $4 : reference for a file with only LF in the repo
-# - parameter $5 : reference for a file with only CRLF in the repo
-# - parameter $6 : reference for a file with mixed LF and CRLF in the repo
-# - parameter $7 : reference for a file with LF and CR in the repo (does somebody uses this ?)
-# - parameter $8 : reference for a file with CRLF and a NUL (should be handled as binary when auto)
-
-#                                            What we have in the repo:
-#                                            ----------------- EOL in repo ----------------
-#                                            LF    CRLF  CRLF_mix_LF  LF_mix_CR    CRLF_nul
-#                   settings with checkout:
-#                   core.   core.   .gitattr
-#                    eol     acrlf
-#                                            ----------------------------------------------
-#                                            What we want to have in the working tree:
+#
+# - parameter $1 	: text in .gitattributs  "" (empty) | auto | text | -text
+# - parameter $2 	: ident                  "" | i (i == ident)
+# - parameter $3 	: eol in .gitattributs   "" (empty) | lf | crlf
+# - parameter $4 	: core.autocrlf          false | true | input
+# - parameter $5 	: core.eol               "" | lf | crlf | "native"
+# - parameter $6 	: reference for a file with only LF in the repo
+# - parameter $7 	: reference for a file with only CRLF in the repo
+# - parameter $8 	: reference for a file with mixed LF and CRLF in the repo
+# - parameter $9 	: reference for a file with LF and CR in the repo
+# - parameter $10 : reference for a file with CRLF and a NUL (should be handled as binary when auto)
+
 if test_have_prereq NATIVE_CRLF
 then
 MIX_CRLF_LF=CRLF
@@ -480,69 +489,90 @@ LFNUL=LF_nul
 fi
 export CRLF_MIX_LF_CR MIX NL
 
-checkout_files    lf      false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "auto"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    lf      input "auto"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "text"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    lf      input "text"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      input "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      input "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    lf      true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    lf      input "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-
-checkout_files    crlf    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    false "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    crlf    true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    crlf    false "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    crlf    true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    crlf    false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    crlf    true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-
-checkout_files    ""      false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "auto"    $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
-checkout_files    ""      true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    ""      input "auto"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "text"    $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
-checkout_files    ""      true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    ""      input "text"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      input "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      input "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    ""      true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    ""      input "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-
-checkout_files    native  false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  false "auto"    $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
-checkout_files    native  true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    native  false "text"    $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
-checkout_files    native  true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    native  false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    native  true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+checkout_files ""      "" ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    true   crlf     CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    true   lf       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    true   native   CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    false  ""       $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    false  crlf     CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    false  native   $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    true   ""       CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    true   crlf     CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    true   lf       CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    true   native   CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+
+for id in "" i;
+do
+	checkout_files "crlf"  "$id" ""    false  ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    false  crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    false  lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    false  native   CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    input  ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    input  lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   native   CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "lf"    "$id" ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    false  ""       $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
+	checkout_files "text"  "$id" ""    false  crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    false  native   $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
+	checkout_files "text"  "$id" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    true   ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    true   crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    true   lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    true   native   CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "-text" "$id" ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+done
 
 # Should be the last test case: remove some files from the worktree
 test_expect_success 'ls-files --eol -d -z' '
-- 
2.7.0.303.g2c4f448.dirty


From e6124e6a186c736cf030c13b1073a66f43cc5841 Mon Sep 17 00:00:00 2001
In-Reply-To: <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
References: <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
From: =?UTF-8?q?Torsten=20B=C3=B6gershausen?= <tboegi@web.de>
Date: Sat, 2 Jan 2016 22:35:36 +0100
Subject: [PATCH v1 2/6] convert.c: Remove path when not needed
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Some functions get a parameter path, but don't use it.
Remove the unused parameter.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 19 +++++++++----------
 1 file changed, 9 insertions(+), 10 deletions(-)

diff --git a/convert.c b/convert.c
index 4bb4ec1..a24c2a2 100644
--- a/convert.c
+++ b/convert.c
@@ -696,7 +696,7 @@ static int ident_to_worktree(const char *path, const char *src, size_t len,
 	return 1;
 }
 
-static enum crlf_action git_path_check_crlf(const char *path, struct git_attr_check *check)
+static enum crlf_action git_path_check_crlf(struct git_attr_check *check)
 {
 	const char *value = check->value;
 
@@ -713,7 +713,7 @@ static enum crlf_action git_path_check_crlf(const char *path, struct git_attr_ch
 	return CRLF_GUESS;
 }
 
-static enum eol git_path_check_eol(const char *path, struct git_attr_check *check)
+static enum eol git_path_check_eol(struct git_attr_check *check)
 {
 	const char *value = check->value;
 
@@ -726,8 +726,7 @@ static enum eol git_path_check_eol(const char *path, struct git_attr_check *chec
 	return EOL_UNSET;
 }
 
-static struct convert_driver *git_path_check_convert(const char *path,
-					     struct git_attr_check *check)
+static struct convert_driver *git_path_check_convert(struct git_attr_check *check)
 {
 	const char *value = check->value;
 	struct convert_driver *drv;
@@ -740,7 +739,7 @@ static struct convert_driver *git_path_check_convert(const char *path,
 	return NULL;
 }
 
-static int git_path_check_ident(const char *path, struct git_attr_check *check)
+static int git_path_check_ident(struct git_attr_check *check)
 {
 	const char *value = check->value;
 
@@ -783,12 +782,12 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 	}
 
 	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
-		ca->crlf_action = git_path_check_crlf(path, ccheck + 4);
+		ca->crlf_action = git_path_check_crlf( ccheck + 4);
 		if (ca->crlf_action == CRLF_GUESS)
-			ca->crlf_action = git_path_check_crlf(path, ccheck + 0);
-		ca->ident = git_path_check_ident(path, ccheck + 1);
-		ca->drv = git_path_check_convert(path, ccheck + 2);
-		ca->eol_attr = git_path_check_eol(path, ccheck + 3);
+			ca->crlf_action = git_path_check_crlf(ccheck + 0);
+		ca->ident = git_path_check_ident(ccheck + 1);
+		ca->drv = git_path_check_convert(ccheck + 2);
+		ca->eol_attr = git_path_check_eol(ccheck + 3);
 	} else {
 		ca->drv = NULL;
 		ca->crlf_action = CRLF_GUESS;
-- 
2.7.0.303.g2c4f448.dirty


From 2183b7fe810a6567adba8d95dbf4a582d1d92521 Mon Sep 17 00:00:00 2001
In-Reply-To: <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
References: <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
From: =?UTF-8?q?Torsten=20B=C3=B6gershausen?= <tboegi@web.de>
Date: Sun, 3 Jan 2016 22:22:35 +0100
Subject: [PATCH v1 3/6] convert.c: Remove input_crlf_action()
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Integrate the code of input_crlf_action() into convert_attrs(),
so that ca.crlf_action is aleays valid after calling convert_attrs().
Keep a copy of crlf_action in attr_action, this is needed for
get_convert_attr_ascii().

Remove eol_attr from struct conv_attrs, as it is now used temporally.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 35 +++++++++++++----------------------
 1 file changed, 13 insertions(+), 22 deletions(-)

diff --git a/convert.c b/convert.c
index a24c2a2..bca3d0c 100644
--- a/convert.c
+++ b/convert.c
@@ -746,21 +746,10 @@ static int git_path_check_ident(struct git_attr_check *check)
 	return !!ATTR_TRUE(value);
 }
 
-static enum crlf_action input_crlf_action(enum crlf_action text_attr, enum eol eol_attr)
-{
-	if (text_attr == CRLF_BINARY)
-		return CRLF_BINARY;
-	if (eol_attr == EOL_LF)
-		return CRLF_INPUT;
-	if (eol_attr == EOL_CRLF)
-		return CRLF_CRLF;
-	return text_attr;
-}
-
 struct conv_attrs {
 	struct convert_driver *drv;
-	enum crlf_action crlf_action;
-	enum eol eol_attr;
+	enum crlf_action attr_action; /* What attr says */
+	enum crlf_action crlf_action; /* When no attr is set, use core.autocrlf */
 	int ident;
 };
 
@@ -782,16 +771,23 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 	}
 
 	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
+		enum eol eol_attr;
 		ca->crlf_action = git_path_check_crlf( ccheck + 4);
 		if (ca->crlf_action == CRLF_GUESS)
 			ca->crlf_action = git_path_check_crlf(ccheck + 0);
+		ca->attr_action = ca->crlf_action;
 		ca->ident = git_path_check_ident(ccheck + 1);
 		ca->drv = git_path_check_convert(ccheck + 2);
-		ca->eol_attr = git_path_check_eol(ccheck + 3);
+		if (ca->crlf_action == CRLF_BINARY)
+			return;
+		eol_attr = git_path_check_eol(ccheck + 3);
+		if (eol_attr == EOL_LF)
+			ca->crlf_action = CRLF_INPUT;
+		else if (eol_attr == EOL_CRLF)
+			ca->crlf_action = CRLF_CRLF;
 	} else {
 		ca->drv = NULL;
 		ca->crlf_action = CRLF_GUESS;
-		ca->eol_attr = EOL_UNSET;
 		ca->ident = 0;
 	}
 }
@@ -818,11 +814,9 @@ int would_convert_to_git_filter_fd(const char *path)
 const char *get_convert_attr_ascii(const char *path)
 {
 	struct conv_attrs ca;
-	enum crlf_action crlf_action;
 
 	convert_attrs(&ca, path);
-	crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
-	switch (crlf_action) {
+	switch (ca.attr_action) {
 	case CRLF_GUESS:
 		return "";
 	case CRLF_BINARY:
@@ -861,7 +855,6 @@ int convert_to_git(const char *path, const char *src, size_t len,
 		src = dst->buf;
 		len = dst->len;
 	}
-	ca.crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
 	ret |= crlf_to_git(path, src, len, dst, ca.crlf_action, checksafe);
 	if (ret && dst) {
 		src = dst->buf;
@@ -882,7 +875,6 @@ void convert_to_git_filter_fd(const char *path, int fd, struct strbuf *dst,
 	if (!apply_filter(path, NULL, 0, fd, dst, ca.drv->clean))
 		die("%s: clean filter '%s' failed", path, ca.drv->name);
 
-	ca.crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
 	crlf_to_git(path, dst->buf, dst->len, dst, ca.crlf_action, checksafe);
 	ident_to_git(path, dst->buf, dst->len, dst, ca.ident);
 }
@@ -912,7 +904,6 @@ static int convert_to_working_tree_internal(const char *path, const char *src,
 	 * is a smudge filter.  The filter might expect CRLFs.
 	 */
 	if (filter || !normalizing) {
-		ca.crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
 		ret |= crlf_to_worktree(path, src, len, dst, ca.crlf_action);
 		if (ret) {
 			src = dst->buf;
@@ -1381,7 +1372,7 @@ struct stream_filter *get_stream_filter(const char *path, const unsigned char *s
 	if (ca.ident)
 		filter = ident_filter(sha1);
 
-	crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
+	crlf_action = ca.crlf_action;
 
 	if ((crlf_action == CRLF_BINARY) || (crlf_action == CRLF_INPUT) ||
 	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE))
-- 
2.7.0.303.g2c4f448.dirty


From 4b0a119f136ff1b4711cd2e588c8ce183ffd2e8e Mon Sep 17 00:00:00 2001
In-Reply-To: <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
References: <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
From: =?UTF-8?q?Torsten=20B=C3=B6gershausen?= <tboegi@web.de>
Date: Mon, 4 Jan 2016 22:06:11 +0100
Subject: [PATCH v1 4/6] convert.c: Use text_eol_is_crlf()
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Add a helper function to find out, which line endings
text files should get at checkout, depending on
core.autocrlf and core.eol

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 25 +++++++++++++++++--------
 1 file changed, 17 insertions(+), 8 deletions(-)

diff --git a/convert.c b/convert.c
index bca3d0c..a5701a1 100644
--- a/convert.c
+++ b/convert.c
@@ -149,6 +149,19 @@ const char *get_wt_convert_stats_ascii(const char *path)
 	return ret;
 }
 
+static int text_eol_is_crlf(void)
+{
+	if (auto_crlf == AUTO_CRLF_TRUE)
+		return 1;
+	else if (auto_crlf == AUTO_CRLF_INPUT)
+		return 0;
+	if (core_eol == EOL_CRLF)
+		return 1;
+	if (core_eol == EOL_UNSET && EOL_NATIVE == EOL_CRLF)
+		return 1;
+	return 0;
+}
+
 static enum eol output_eol(enum crlf_action crlf_action)
 {
 	switch (crlf_action) {
@@ -164,12 +177,7 @@ static enum eol output_eol(enum crlf_action crlf_action)
 		/* fall through */
 	case CRLF_TEXT:
 	case CRLF_AUTO:
-		if (auto_crlf == AUTO_CRLF_TRUE)
-			return EOL_CRLF;
-		else if (auto_crlf == AUTO_CRLF_INPUT)
-			return EOL_LF;
-		else if (core_eol == EOL_UNSET)
-			return EOL_NATIVE;
+		return text_eol_is_crlf() ? EOL_CRLF : EOL_LF;
 	}
 	return core_eol;
 }
@@ -1378,8 +1386,9 @@ struct stream_filter *get_stream_filter(const char *path, const unsigned char *s
 	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE))
 		filter = cascade_filter(filter, &null_filter_singleton);
 
-	else if (output_eol(crlf_action) == EOL_CRLF &&
-		 !(crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS))
+	else if ((crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS))
+		;
+	else if (output_eol(crlf_action) == EOL_CRLF)
 		filter = cascade_filter(filter, lf_to_crlf_filter());
 
 	return filter;
-- 
2.7.0.303.g2c4f448.dirty


From e6345a0f0972ae5b7c58a00c476a7e2544e6eda8 Mon Sep 17 00:00:00 2001
In-Reply-To: <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
References: <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
From: =?UTF-8?q?Torsten=20B=C3=B6gershausen?= <tboegi@web.de>
Date: Tue, 5 Jan 2016 21:50:15 +0100
Subject: [PATCH v1 5/6] convert: auto_crlf=false and no attributes set: same
 as binary
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

When core.autocrlf is set to false, and no attributes are set, the file
is treated as binary.
Simplify the logic and remove duplicated code when dealing with
(crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE) by setting
crlf_action=CRLF_BINARY already in convert_attrs().

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/convert.c b/convert.c
index a5701a1..50bdc42 100644
--- a/convert.c
+++ b/convert.c
@@ -235,7 +235,6 @@ static int crlf_to_git(const char *path, const char *src, size_t len,
 	char *dst;
 
 	if (crlf_action == CRLF_BINARY ||
-	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE) ||
 	    (src && !len))
 		return 0;
 
@@ -798,6 +797,8 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 		ca->crlf_action = CRLF_GUESS;
 		ca->ident = 0;
 	}
+	if (ca->crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE)
+		ca->crlf_action = CRLF_BINARY;
 }
 
 int would_convert_to_git_filter_fd(const char *path)
@@ -1382,8 +1383,7 @@ struct stream_filter *get_stream_filter(const char *path, const unsigned char *s
 
 	crlf_action = ca.crlf_action;
 
-	if ((crlf_action == CRLF_BINARY) || (crlf_action == CRLF_INPUT) ||
-	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE))
+	if ((crlf_action == CRLF_BINARY) || (crlf_action == CRLF_INPUT))
 		filter = cascade_filter(filter, &null_filter_singleton);
 
 	else if ((crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS))
-- 
2.7.0.303.g2c4f448.dirty


From 44aae1e1e06f7e16e2e8f2db83bfa130f0b89f34 Mon Sep 17 00:00:00 2001
In-Reply-To: <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
References: <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
From: =?UTF-8?q?Torsten=20B=C3=B6gershausen?= <tboegi@web.de>
Date: Wed, 27 Jan 2016 15:48:04 +0100
Subject: [PATCH v1 6/6] convert.c: Refactor crlf_action
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

Refactor the determination and usage of crlf_action.
Today, when no attributes are set on a file,  crlf_action is set to CRLF_GUESS,
and later, CRLF_GUESS is used as an indication that core.autocrlf is not false
and that some automatic eol conversion is needed.
Make more clear, what is what, by defining:

- CRLF_UNDEFINED : No attributes set. Temparally used, until core.autocrlf and
                   core.eol is evaluated and one
                   CRLF_BINARY, CRLF_AUTO_INPUT or CRLF_AUTO_CRLF is selected
- CRLF_BINARY    : No processing of line endings.
- CRLF_TEXT      : attribute "text" is set, line endings are processed.
- CRLF_TEXT_LF   : attribute "input" or "eol=lf" is set. This implies text.
- CRLF_TEXT_CRLF : attribute "eol=crlf" is set. This implies text.
- CRLF_AUTO      : attribute "auto" is set.
- CRLF_AUTO_INPUT: No attributes, core.autocrlf=input
- CRLF_AUTO_CRLF : No attributes, core.autocrlf=true

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 77 ++++++++++++++++++++++++++++++++++++++-------------------------
 1 file changed, 46 insertions(+), 31 deletions(-)

diff --git a/convert.c b/convert.c
index 50bdc42..84fe714 100644
--- a/convert.c
+++ b/convert.c
@@ -19,12 +19,14 @@
 #define CONVERT_STAT_BITS_BIN       0x4
 
 enum crlf_action {
-	CRLF_GUESS = -1,
-	CRLF_BINARY = 0,
+	CRLF_UNDEFINED,
+	CRLF_BINARY,
 	CRLF_TEXT,
-	CRLF_INPUT,
-	CRLF_CRLF,
-	CRLF_AUTO
+	CRLF_TEXT_LF,
+	CRLF_TEXT_CRLF,
+	CRLF_AUTO,
+	CRLF_AUTO_INPUT,
+	CRLF_AUTO_CRLF
 };
 
 struct text_stat {
@@ -167,18 +169,19 @@ static enum eol output_eol(enum crlf_action crlf_action)
 	switch (crlf_action) {
 	case CRLF_BINARY:
 		return EOL_UNSET;
-	case CRLF_CRLF:
+	case CRLF_TEXT_CRLF:
 		return EOL_CRLF;
-	case CRLF_INPUT:
+	case CRLF_TEXT_LF:
 		return EOL_LF;
-	case CRLF_GUESS:
-		if (!auto_crlf)
-			return EOL_UNSET;
-		/* fall through */
+	case CRLF_UNDEFINED:
+	case CRLF_AUTO_CRLF:
+	case CRLF_AUTO_INPUT:
 	case CRLF_TEXT:
 	case CRLF_AUTO:
+		/* fall through */
 		return text_eol_is_crlf() ? EOL_CRLF : EOL_LF;
 	}
+	warning("Illegal crlf_action %d\n", (int)crlf_action);
 	return core_eol;
 }
 
@@ -247,11 +250,11 @@ static int crlf_to_git(const char *path, const char *src, size_t len,
 
 	gather_stats(src, len, &stats);
 
-	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS) {
+	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 		if (convert_is_binary(len, &stats))
 			return 0;
 
-		if (crlf_action == CRLF_GUESS) {
+		if (crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 			/*
 			 * If the file in the index has any CR in it, do not convert.
 			 * This is the new safer autocrlf handling.
@@ -278,7 +281,7 @@ static int crlf_to_git(const char *path, const char *src, size_t len,
 	if (strbuf_avail(buf) + buf->len < len)
 		strbuf_grow(buf, len - buf->len);
 	dst = buf->buf;
-	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS) {
+	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 		/*
 		 * If we guessed, we already know we rejected a file with
 		 * lone CR, and we can strip a CR without looking at what
@@ -319,8 +322,8 @@ static int crlf_to_worktree(const char *path, const char *src, size_t len,
 	if (stats.lf == stats.crlf)
 		return 0;
 
-	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS) {
-		if (crlf_action == CRLF_GUESS) {
+	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
+		if (crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 			/* If we have any CR or CRLF line endings, we do not touch it */
 			/* This is the new safer autocrlf-handling */
 			if (stats.cr > 0 || stats.crlf > 0)
@@ -708,16 +711,16 @@ static enum crlf_action git_path_check_crlf(struct git_attr_check *check)
 	const char *value = check->value;
 
 	if (ATTR_TRUE(value))
-		return CRLF_TEXT;
+		return text_eol_is_crlf() ? CRLF_TEXT_CRLF : CRLF_TEXT_LF;
 	else if (ATTR_FALSE(value))
 		return CRLF_BINARY;
 	else if (ATTR_UNSET(value))
 		;
 	else if (!strcmp(value, "input"))
-		return CRLF_INPUT;
+		return CRLF_TEXT_LF;
 	else if (!strcmp(value, "auto"))
 		return CRLF_AUTO;
-	return CRLF_GUESS;
+	return CRLF_UNDEFINED;
 }
 
 static enum eol git_path_check_eol(struct git_attr_check *check)
@@ -780,7 +783,7 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
 		enum eol eol_attr;
 		ca->crlf_action = git_path_check_crlf( ccheck + 4);
-		if (ca->crlf_action == CRLF_GUESS)
+		if (ca->crlf_action == CRLF_UNDEFINED)
 			ca->crlf_action = git_path_check_crlf(ccheck + 0);
 		ca->attr_action = ca->crlf_action;
 		ca->ident = git_path_check_ident(ccheck + 1);
@@ -789,16 +792,22 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 			return;
 		eol_attr = git_path_check_eol(ccheck + 3);
 		if (eol_attr == EOL_LF)
-			ca->crlf_action = CRLF_INPUT;
+			ca->crlf_action = CRLF_TEXT_LF;
 		else if (eol_attr == EOL_CRLF)
-			ca->crlf_action = CRLF_CRLF;
+			ca->crlf_action = CRLF_TEXT_CRLF;
 	} else {
 		ca->drv = NULL;
-		ca->crlf_action = CRLF_GUESS;
+		ca->crlf_action = CRLF_UNDEFINED;
 		ca->ident = 0;
 	}
-	if (ca->crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE)
+	if (ca->crlf_action == CRLF_TEXT)
+		ca->crlf_action = text_eol_is_crlf() ? CRLF_TEXT_CRLF : CRLF_TEXT_LF;
+	if (ca->crlf_action == CRLF_UNDEFINED && auto_crlf == AUTO_CRLF_FALSE)
 		ca->crlf_action = CRLF_BINARY;
+	if (ca->crlf_action == CRLF_UNDEFINED && auto_crlf == AUTO_CRLF_TRUE)
+		ca->crlf_action = CRLF_AUTO_CRLF;
+	if (ca->crlf_action == CRLF_UNDEFINED && auto_crlf == AUTO_CRLF_INPUT)
+		ca->crlf_action = CRLF_AUTO_INPUT;
 }
 
 int would_convert_to_git_filter_fd(const char *path)
@@ -826,18 +835,22 @@ const char *get_convert_attr_ascii(const char *path)
 
 	convert_attrs(&ca, path);
 	switch (ca.attr_action) {
-	case CRLF_GUESS:
+	case CRLF_UNDEFINED:
 		return "";
 	case CRLF_BINARY:
 		return "-text";
 	case CRLF_TEXT:
 		return "text";
-	case CRLF_INPUT:
+	case CRLF_TEXT_LF:
 		return "text eol=lf";
-	case CRLF_CRLF:
-		return "text=auto eol=crlf";
+	case CRLF_TEXT_CRLF:
+		return "text eol=crlf";
 	case CRLF_AUTO:
 		return "text=auto";
+	case CRLF_AUTO_CRLF:
+		return "text=auto eol=crlf"; /* This is not supported yet */
+	case CRLF_AUTO_INPUT:
+		return "text=auto eol=lf"; /* This is not supported yet */
 	}
 	return "";
 }
@@ -1382,11 +1395,13 @@ struct stream_filter *get_stream_filter(const char *path, const unsigned char *s
 		filter = ident_filter(sha1);
 
 	crlf_action = ca.crlf_action;
-
-	if ((crlf_action == CRLF_BINARY) || (crlf_action == CRLF_INPUT))
+	if ((crlf_action == CRLF_BINARY) ||
+			(crlf_action == CRLF_TEXT_LF))
 		filter = cascade_filter(filter, &null_filter_singleton);
 
-	else if ((crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS))
+	else if ((crlf_action == CRLF_AUTO ||
+						crlf_action == CRLF_AUTO_INPUT ||
+						crlf_action == CRLF_AUTO_CRLF))
 		;
 	else if (output_eol(crlf_action) == EOL_CRLF)
 		filter = cascade_filter(filter, lf_to_crlf_filter());
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v1 1/6] t0027: Add tests for get_stream_filter()
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
  2016-01-24  7:55 ` [PATCH v2] t0027: Add tests for get_stream_filter() tboegi
  2016-01-27 15:15 ` [PATCH v1 1/6] " tboegi
@ 2016-02-02 16:53 ` tboegi
  2016-02-02 21:18   ` Junio C Hamano
  2016-02-02 16:53 ` [PATCH v1 2/6] convert.c: Remove path when not needed tboegi
                   ` (25 subsequent siblings)
  28 siblings, 1 reply; 47+ messages in thread
From: tboegi @ 2016-02-02 16:53 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

When a filter is configured, a different code-path is used in convert.c
and entry.c via get_stream_filter(), but there are no test cases yet.

Add tests for the filter API by configuring the ident filter.
The result of the SHA1 conversion is not checked, this is already
done in other TC.

Add a parameter to checkout_files() in t0027.
While changing the signature, add another parameter for the eol= attribute.
This is currently unused, tests for e.g.
"* text=auto eol=lf" will be added in a separate commit.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 t/t0027-auto-crlf.sh | 262 ++++++++++++++++++++++++++++-----------------------
 1 file changed, 146 insertions(+), 116 deletions(-)

diff --git a/t/t0027-auto-crlf.sh b/t/t0027-auto-crlf.sh
index 504e5a0..681f0c5 100755
--- a/t/t0027-auto-crlf.sh
+++ b/t/t0027-auto-crlf.sh
@@ -21,32 +21,45 @@ compare_ws_file () {
 	pfx=$1
 	exp=$2.expect
 	act=$pfx.actual.$3
-	tr '\015\000' QN <"$2" >"$exp" &&
-	tr '\015\000' QN <"$3" >"$act" &&
+	tr '\015\000abcdef01234567890' QN00000000000000000 <"$2" >"$exp" &&
+	tr '\015\000abcdef01234567890' QN00000000000000000 <"$3" >"$act" &&
 	test_cmp $exp $act &&
 	rm $exp $act
 }
 
 create_gitattributes () {
 	attr=$1
+	ident=$2
+	case "$2" in
+		"")
+			>.gitattributes
+			;;
+		i)
+			echo "* ident" >.gitattributes
+			;;
+		*)
+			echo >&2 invalid ident: $2
+			exit 1
+	esac
+
 	case "$attr" in
 		auto)
-		echo "*.txt text=auto" >.gitattributes
+		echo "*.txt text=auto" >>.gitattributes
 		;;
 		text)
-		echo "*.txt text" >.gitattributes
+		echo "*.txt text" >>.gitattributes
 		;;
 		-text)
-		echo "*.txt -text" >.gitattributes
+		echo "*.txt -text" >>.gitattributes
 		;;
 		crlf)
-		echo "*.txt eol=crlf" >.gitattributes
+		echo "*.txt eol=crlf" >>.gitattributes
 		;;
 		lf)
-		echo "*.txt eol=lf" >.gitattributes
+		echo "*.txt eol=lf" >>.gitattributes
 		;;
 		"")
-		echo >.gitattributes
+		#echo >.gitattributes
 		;;
 		*)
 		echo >&2 invalid attribute: $attr
@@ -90,7 +103,7 @@ commit_check_warn () {
 	lfmixcr=$6
 	crlfnul=$7
 	pfx=crlf_${crlf}_attr_${attr}
-	create_gitattributes "$attr" &&
+	create_gitattributes "$attr" "" &&
 	for f in LF CRLF LF_mix_CR CRLF_mix_LF LF_nul CRLF_nul
 	do
 		fname=${pfx}_$f.txt &&
@@ -115,7 +128,7 @@ commit_chk_wrnNNO () {
 	crlfnul=$7
 	pfx=NNO_${crlf}_attr_${attr}
 	#Commit files on top of existing file
-	create_gitattributes "$attr" &&
+	create_gitattributes "$attr" "" &&
 	for f in LF CRLF CRLF_mix_LF LF_mix_CR CRLF_nul
 	do
 		fname=${pfx}_$f.txt &&
@@ -208,28 +221,30 @@ check_in_repo_NNO () {
 }
 
 checkout_files () {
-	eol=$1
-	crlf=$2
-	attr=$3
-	lfname=$4
-	crlfname=$5
-	lfmixcrlf=$6
-	lfmixcr=$7
-	crlfnul=$8
-	create_gitattributes $attr &&
+	attr=$1 ; shift
+	ident=$1; shift
+	aeol=$1 ; shift
+	crlf=$1 ; shift
+	ceol=$1 ; shift
+	lfname=$1 ; shift
+	crlfname=$1 ; shift
+	lfmixcrlf=$1 ; shift
+	lfmixcr=$1 ; shift
+	crlfnul=$1 ; shift
+	create_gitattributes "$attr" "$ident" &&
 	git config core.autocrlf $crlf &&
-	pfx=eol_${eol}_crlf_${crlf}_attr_${attr}_ &&
+	pfx=eol_${ceol}_crlf_${crlf}_attr_${attr}_ &&
 	for f in LF CRLF LF_mix_CR CRLF_mix_LF LF_nul
 	do
 		rm crlf_false_attr__$f.txt &&
-		if test -z "$eol"; then
+		if test -z "$ceol"; then
 			git checkout crlf_false_attr__$f.txt
 		else
-			git -c core.eol=$eol checkout crlf_false_attr__$f.txt
+			git -c core.eol=$ceol checkout crlf_false_attr__$f.txt
 		fi
 	done
 
-	test_expect_success "ls-files --eol $lfname ${pfx}LF.txt" '
+	test_expect_success "ls-files --eol attr=$attr i=$ident $aeol core.autocrlf=$crlf core.eol=$ceol" '
 		test_when_finished "rm expect actual" &&
 		sort <<-EOF >expect &&
 		i/crlf w/$(stats_ascii $crlfname) crlf_false_attr__CRLF.txt
@@ -244,19 +259,19 @@ checkout_files () {
 		sort >actual &&
 		test_cmp expect actual
 	'
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=LF" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=LF" "
 		compare_ws_file $pfx $lfname    crlf_false_attr__LF.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=CRLF" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=CRLF" "
 		compare_ws_file $pfx $crlfname  crlf_false_attr__CRLF.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=CRLF_mix_LF" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=CRLF_mix_LF" "
 		compare_ws_file $pfx $lfmixcrlf crlf_false_attr__CRLF_mix_LF.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=LF_mix_CR" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=LF_mix_CR" "
 		compare_ws_file $pfx $lfmixcr   crlf_false_attr__LF_mix_CR.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=LF_nul" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=LF_nul" "
 		compare_ws_file $pfx $crlfnul   crlf_false_attr__LF_nul.txt
 	"
 }
@@ -301,14 +316,13 @@ test_expect_success 'setup master' '
 	git checkout -b master &&
 	git add .gitattributes &&
 	git commit -m "add .gitattributes" "" &&
-	printf "line1\nline2\nline3"     >LF &&
-	printf "line1\r\nline2\r\nline3" >CRLF &&
-	printf "line1\r\nline2\nline3"   >repoMIX &&
-	printf "line1\r\nline2\nline3"   >CRLF_mix_LF &&
-	printf "line1\nline2\rline3"     >LF_mix_CR &&
-	printf "line1\r\nline2\rline3"   >CRLF_mix_CR &&
-	printf "line1Q\r\nline2\r\nline3" | q_to_nul >CRLF_nul &&
-	printf "line1Q\nline2\nline3" | q_to_nul >LF_nul &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONE\nLINETWO\nLINETHREE"     >LF &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\r\nLINEONE\r\nLINETWO\r\nLINETHREE" >CRLF &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONE\r\nLINETWO\nLINETHREE"   >CRLF_mix_LF &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONE\nLINETWO\rLINETHREE"     >LF_mix_CR &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\r\nLINEONE\r\nLINETWO\rLINETHREE"   >CRLF_mix_CR &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\r\nLINEONEQ\r\nLINETWO\r\nLINETHREE" | q_to_nul >CRLF_nul &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONEQ\nLINETWO\nLINETHREE" | q_to_nul >LF_nul &&
 	create_NNO_files CRLF_mix_LF CRLF_mix_LF CRLF_mix_LF CRLF_mix_LF CRLF_mix_LF &&
 	git -c core.autocrlf=false add NNO_*.txt &&
 	git commit -m "mixed line endings" &&
@@ -449,23 +463,18 @@ check_in_repo_NNO input "-text" LF        CRLF      CRLF_mix_LF  LF_mix_CR 	CRLF
 # How to read the table below:
 # - checkout_files will check multiple files with a combination of settings
 #   and attributes (core.autocrlf=input is forbidden with core.eol=crlf)
-# - parameter $1 : core.eol               lf | crlf
-# - parameter $2 : core.autocrlf          false | true | input
-# - parameter $3 : text in .gitattributs  "" (empty) | auto | text | -text
-# - parameter $4 : reference for a file with only LF in the repo
-# - parameter $5 : reference for a file with only CRLF in the repo
-# - parameter $6 : reference for a file with mixed LF and CRLF in the repo
-# - parameter $7 : reference for a file with LF and CR in the repo (does somebody uses this ?)
-# - parameter $8 : reference for a file with CRLF and a NUL (should be handled as binary when auto)
-
-#                                            What we have in the repo:
-#                                            ----------------- EOL in repo ----------------
-#                                            LF    CRLF  CRLF_mix_LF  LF_mix_CR    CRLF_nul
-#                   settings with checkout:
-#                   core.   core.   .gitattr
-#                    eol     acrlf
-#                                            ----------------------------------------------
-#                                            What we want to have in the working tree:
+#
+# - parameter $1 	: text in .gitattributs  "" (empty) | auto | text | -text
+# - parameter $2 	: ident                  "" | i (i == ident)
+# - parameter $3 	: eol in .gitattributs   "" (empty) | lf | crlf
+# - parameter $4 	: core.autocrlf          false | true | input
+# - parameter $5 	: core.eol               "" | lf | crlf | "native"
+# - parameter $6 	: reference for a file with only LF in the repo
+# - parameter $7 	: reference for a file with only CRLF in the repo
+# - parameter $8 	: reference for a file with mixed LF and CRLF in the repo
+# - parameter $9 	: reference for a file with LF and CR in the repo
+# - parameter $10 : reference for a file with CRLF and a NUL (should be handled as binary when auto)
+
 if test_have_prereq NATIVE_CRLF
 then
 MIX_CRLF_LF=CRLF
@@ -480,69 +489,90 @@ LFNUL=LF_nul
 fi
 export CRLF_MIX_LF_CR MIX NL
 
-checkout_files    lf      false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "auto"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    lf      input "auto"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "text"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    lf      input "text"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      input "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      input "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    lf      true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    lf      input "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-
-checkout_files    crlf    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    false "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    crlf    true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    crlf    false "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    crlf    true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    crlf    false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    crlf    true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-
-checkout_files    ""      false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "auto"    $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
-checkout_files    ""      true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    ""      input "auto"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "text"    $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
-checkout_files    ""      true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    ""      input "text"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      input "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      input "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    ""      true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    ""      input "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-
-checkout_files    native  false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  false "auto"    $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
-checkout_files    native  true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    native  false "text"    $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
-checkout_files    native  true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    native  false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    native  true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+checkout_files ""      "" ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    true   crlf     CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    true   lf       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    true   native   CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    false  ""       $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    false  crlf     CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    false  native   $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    true   ""       CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    true   crlf     CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    true   lf       CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    true   native   CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+
+for id in "" i;
+do
+	checkout_files "crlf"  "$id" ""    false  ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    false  crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    false  lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    false  native   CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    input  ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    input  lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   native   CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "lf"    "$id" ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    false  ""       $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
+	checkout_files "text"  "$id" ""    false  crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    false  native   $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
+	checkout_files "text"  "$id" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    true   ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    true   crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    true   lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    true   native   CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "-text" "$id" ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+done
 
 # Should be the last test case: remove some files from the worktree
 test_expect_success 'ls-files --eol -d -z' '
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v1 2/6] convert.c: Remove path when not needed
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (2 preceding siblings ...)
  2016-02-02 16:53 ` tboegi
@ 2016-02-02 16:53 ` tboegi
  2016-02-02 21:32   ` Junio C Hamano
  2016-02-02 16:53 ` [PATCH v1 3/6] convert.c: Remove input_crlf_action() tboegi
                   ` (24 subsequent siblings)
  28 siblings, 1 reply; 47+ messages in thread
From: tboegi @ 2016-02-02 16:53 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Some functions get a parameter path, but don't use it.
Remove the unused parameter.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 19 +++++++++----------
 1 file changed, 9 insertions(+), 10 deletions(-)

diff --git a/convert.c b/convert.c
index 4bb4ec1..a24c2a2 100644
--- a/convert.c
+++ b/convert.c
@@ -696,7 +696,7 @@ static int ident_to_worktree(const char *path, const char *src, size_t len,
 	return 1;
 }
 
-static enum crlf_action git_path_check_crlf(const char *path, struct git_attr_check *check)
+static enum crlf_action git_path_check_crlf(struct git_attr_check *check)
 {
 	const char *value = check->value;
 
@@ -713,7 +713,7 @@ static enum crlf_action git_path_check_crlf(const char *path, struct git_attr_ch
 	return CRLF_GUESS;
 }
 
-static enum eol git_path_check_eol(const char *path, struct git_attr_check *check)
+static enum eol git_path_check_eol(struct git_attr_check *check)
 {
 	const char *value = check->value;
 
@@ -726,8 +726,7 @@ static enum eol git_path_check_eol(const char *path, struct git_attr_check *chec
 	return EOL_UNSET;
 }
 
-static struct convert_driver *git_path_check_convert(const char *path,
-					     struct git_attr_check *check)
+static struct convert_driver *git_path_check_convert(struct git_attr_check *check)
 {
 	const char *value = check->value;
 	struct convert_driver *drv;
@@ -740,7 +739,7 @@ static struct convert_driver *git_path_check_convert(const char *path,
 	return NULL;
 }
 
-static int git_path_check_ident(const char *path, struct git_attr_check *check)
+static int git_path_check_ident(struct git_attr_check *check)
 {
 	const char *value = check->value;
 
@@ -783,12 +782,12 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 	}
 
 	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
-		ca->crlf_action = git_path_check_crlf(path, ccheck + 4);
+		ca->crlf_action = git_path_check_crlf( ccheck + 4);
 		if (ca->crlf_action == CRLF_GUESS)
-			ca->crlf_action = git_path_check_crlf(path, ccheck + 0);
-		ca->ident = git_path_check_ident(path, ccheck + 1);
-		ca->drv = git_path_check_convert(path, ccheck + 2);
-		ca->eol_attr = git_path_check_eol(path, ccheck + 3);
+			ca->crlf_action = git_path_check_crlf(ccheck + 0);
+		ca->ident = git_path_check_ident(ccheck + 1);
+		ca->drv = git_path_check_convert(ccheck + 2);
+		ca->eol_attr = git_path_check_eol(ccheck + 3);
 	} else {
 		ca->drv = NULL;
 		ca->crlf_action = CRLF_GUESS;
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v1 3/6] convert.c: Remove input_crlf_action()
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (3 preceding siblings ...)
  2016-02-02 16:53 ` [PATCH v1 2/6] convert.c: Remove path when not needed tboegi
@ 2016-02-02 16:53 ` tboegi
  2016-02-02 21:44   ` Junio C Hamano
  2016-02-02 16:53 ` [PATCH v1 4/6] convert.c: Use text_eol_is_crlf() tboegi
                   ` (23 subsequent siblings)
  28 siblings, 1 reply; 47+ messages in thread
From: tboegi @ 2016-02-02 16:53 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Integrate the code of input_crlf_action() into convert_attrs(),
so that ca.crlf_action is aleays valid after calling convert_attrs().
Keep a copy of crlf_action in attr_action, this is needed for
get_convert_attr_ascii().

Remove eol_attr from struct conv_attrs, as it is now used temporally.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 35 +++++++++++++----------------------
 1 file changed, 13 insertions(+), 22 deletions(-)

diff --git a/convert.c b/convert.c
index a24c2a2..bca3d0c 100644
--- a/convert.c
+++ b/convert.c
@@ -746,21 +746,10 @@ static int git_path_check_ident(struct git_attr_check *check)
 	return !!ATTR_TRUE(value);
 }
 
-static enum crlf_action input_crlf_action(enum crlf_action text_attr, enum eol eol_attr)
-{
-	if (text_attr == CRLF_BINARY)
-		return CRLF_BINARY;
-	if (eol_attr == EOL_LF)
-		return CRLF_INPUT;
-	if (eol_attr == EOL_CRLF)
-		return CRLF_CRLF;
-	return text_attr;
-}
-
 struct conv_attrs {
 	struct convert_driver *drv;
-	enum crlf_action crlf_action;
-	enum eol eol_attr;
+	enum crlf_action attr_action; /* What attr says */
+	enum crlf_action crlf_action; /* When no attr is set, use core.autocrlf */
 	int ident;
 };
 
@@ -782,16 +771,23 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 	}
 
 	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
+		enum eol eol_attr;
 		ca->crlf_action = git_path_check_crlf( ccheck + 4);
 		if (ca->crlf_action == CRLF_GUESS)
 			ca->crlf_action = git_path_check_crlf(ccheck + 0);
+		ca->attr_action = ca->crlf_action;
 		ca->ident = git_path_check_ident(ccheck + 1);
 		ca->drv = git_path_check_convert(ccheck + 2);
-		ca->eol_attr = git_path_check_eol(ccheck + 3);
+		if (ca->crlf_action == CRLF_BINARY)
+			return;
+		eol_attr = git_path_check_eol(ccheck + 3);
+		if (eol_attr == EOL_LF)
+			ca->crlf_action = CRLF_INPUT;
+		else if (eol_attr == EOL_CRLF)
+			ca->crlf_action = CRLF_CRLF;
 	} else {
 		ca->drv = NULL;
 		ca->crlf_action = CRLF_GUESS;
-		ca->eol_attr = EOL_UNSET;
 		ca->ident = 0;
 	}
 }
@@ -818,11 +814,9 @@ int would_convert_to_git_filter_fd(const char *path)
 const char *get_convert_attr_ascii(const char *path)
 {
 	struct conv_attrs ca;
-	enum crlf_action crlf_action;
 
 	convert_attrs(&ca, path);
-	crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
-	switch (crlf_action) {
+	switch (ca.attr_action) {
 	case CRLF_GUESS:
 		return "";
 	case CRLF_BINARY:
@@ -861,7 +855,6 @@ int convert_to_git(const char *path, const char *src, size_t len,
 		src = dst->buf;
 		len = dst->len;
 	}
-	ca.crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
 	ret |= crlf_to_git(path, src, len, dst, ca.crlf_action, checksafe);
 	if (ret && dst) {
 		src = dst->buf;
@@ -882,7 +875,6 @@ void convert_to_git_filter_fd(const char *path, int fd, struct strbuf *dst,
 	if (!apply_filter(path, NULL, 0, fd, dst, ca.drv->clean))
 		die("%s: clean filter '%s' failed", path, ca.drv->name);
 
-	ca.crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
 	crlf_to_git(path, dst->buf, dst->len, dst, ca.crlf_action, checksafe);
 	ident_to_git(path, dst->buf, dst->len, dst, ca.ident);
 }
@@ -912,7 +904,6 @@ static int convert_to_working_tree_internal(const char *path, const char *src,
 	 * is a smudge filter.  The filter might expect CRLFs.
 	 */
 	if (filter || !normalizing) {
-		ca.crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
 		ret |= crlf_to_worktree(path, src, len, dst, ca.crlf_action);
 		if (ret) {
 			src = dst->buf;
@@ -1381,7 +1372,7 @@ struct stream_filter *get_stream_filter(const char *path, const unsigned char *s
 	if (ca.ident)
 		filter = ident_filter(sha1);
 
-	crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
+	crlf_action = ca.crlf_action;
 
 	if ((crlf_action == CRLF_BINARY) || (crlf_action == CRLF_INPUT) ||
 	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE))
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v1 4/6] convert.c: Use text_eol_is_crlf()
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (4 preceding siblings ...)
  2016-02-02 16:53 ` [PATCH v1 3/6] convert.c: Remove input_crlf_action() tboegi
@ 2016-02-02 16:53 ` tboegi
  2016-02-02 16:53 ` [PATCH v1 5/6] convert: auto_crlf=false and no attributes set: same as binary tboegi
                   ` (22 subsequent siblings)
  28 siblings, 0 replies; 47+ messages in thread
From: tboegi @ 2016-02-02 16:53 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Add a helper function to find out, which line endings
text files should get at checkout, depending on
core.autocrlf and core.eol

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 25 +++++++++++++++++--------
 1 file changed, 17 insertions(+), 8 deletions(-)

diff --git a/convert.c b/convert.c
index bca3d0c..a5701a1 100644
--- a/convert.c
+++ b/convert.c
@@ -149,6 +149,19 @@ const char *get_wt_convert_stats_ascii(const char *path)
 	return ret;
 }
 
+static int text_eol_is_crlf(void)
+{
+	if (auto_crlf == AUTO_CRLF_TRUE)
+		return 1;
+	else if (auto_crlf == AUTO_CRLF_INPUT)
+		return 0;
+	if (core_eol == EOL_CRLF)
+		return 1;
+	if (core_eol == EOL_UNSET && EOL_NATIVE == EOL_CRLF)
+		return 1;
+	return 0;
+}
+
 static enum eol output_eol(enum crlf_action crlf_action)
 {
 	switch (crlf_action) {
@@ -164,12 +177,7 @@ static enum eol output_eol(enum crlf_action crlf_action)
 		/* fall through */
 	case CRLF_TEXT:
 	case CRLF_AUTO:
-		if (auto_crlf == AUTO_CRLF_TRUE)
-			return EOL_CRLF;
-		else if (auto_crlf == AUTO_CRLF_INPUT)
-			return EOL_LF;
-		else if (core_eol == EOL_UNSET)
-			return EOL_NATIVE;
+		return text_eol_is_crlf() ? EOL_CRLF : EOL_LF;
 	}
 	return core_eol;
 }
@@ -1378,8 +1386,9 @@ struct stream_filter *get_stream_filter(const char *path, const unsigned char *s
 	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE))
 		filter = cascade_filter(filter, &null_filter_singleton);
 
-	else if (output_eol(crlf_action) == EOL_CRLF &&
-		 !(crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS))
+	else if ((crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS))
+		;
+	else if (output_eol(crlf_action) == EOL_CRLF)
 		filter = cascade_filter(filter, lf_to_crlf_filter());
 
 	return filter;
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v1 5/6] convert: auto_crlf=false and no attributes set: same as binary
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (5 preceding siblings ...)
  2016-02-02 16:53 ` [PATCH v1 4/6] convert.c: Use text_eol_is_crlf() tboegi
@ 2016-02-02 16:53 ` tboegi
  2016-02-02 16:53 ` [PATCH v1 6/6] convert.c: Refactor crlf_action tboegi
                   ` (21 subsequent siblings)
  28 siblings, 0 replies; 47+ messages in thread
From: tboegi @ 2016-02-02 16:53 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

When core.autocrlf is set to false, and no attributes are set, the file
is treated as binary.
Simplify the logic and remove duplicated code when dealing with
(crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE) by setting
crlf_action=CRLF_BINARY already in convert_attrs().

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/convert.c b/convert.c
index a5701a1..50bdc42 100644
--- a/convert.c
+++ b/convert.c
@@ -235,7 +235,6 @@ static int crlf_to_git(const char *path, const char *src, size_t len,
 	char *dst;
 
 	if (crlf_action == CRLF_BINARY ||
-	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE) ||
 	    (src && !len))
 		return 0;
 
@@ -798,6 +797,8 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 		ca->crlf_action = CRLF_GUESS;
 		ca->ident = 0;
 	}
+	if (ca->crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE)
+		ca->crlf_action = CRLF_BINARY;
 }
 
 int would_convert_to_git_filter_fd(const char *path)
@@ -1382,8 +1383,7 @@ struct stream_filter *get_stream_filter(const char *path, const unsigned char *s
 
 	crlf_action = ca.crlf_action;
 
-	if ((crlf_action == CRLF_BINARY) || (crlf_action == CRLF_INPUT) ||
-	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE))
+	if ((crlf_action == CRLF_BINARY) || (crlf_action == CRLF_INPUT))
 		filter = cascade_filter(filter, &null_filter_singleton);
 
 	else if ((crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS))
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v1 6/6] convert.c: Refactor crlf_action
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (6 preceding siblings ...)
  2016-02-02 16:53 ` [PATCH v1 5/6] convert: auto_crlf=false and no attributes set: same as binary tboegi
@ 2016-02-02 16:53 ` tboegi
  2016-02-04 17:49 ` [PATCH v2 1/7] t0027: Add tests for get_stream_filter() tboegi
                   ` (20 subsequent siblings)
  28 siblings, 0 replies; 47+ messages in thread
From: tboegi @ 2016-02-02 16:53 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Refactor the determination and usage of crlf_action.
Today, when no attributes are set on a file,
crlf_action is set to CRLF_GUESS, and later, CRLF_GUESS is used as an
indication that core.autocrlf is not false and that some automatic eol
conversion is needed.
Make more clear, what is what, by defining:

- CRLF_UNDEFINED : No attributes set. Temparally used, until core.autocrlf
                   and core.eol is evaluated and one of CRLF_BINARY,
                   CRLF_AUTO_INPUT or CRLF_AUTO_CRLF is selected
- CRLF_BINARY    : No processing of line endings.
- CRLF_TEXT      : attribute "text" is set, line endings are processed.
- CRLF_TEXT_INPUT: attribute "input" or "eol=lf" is set. This implies text.
- CRLF_TEXT_CRLF : attribute "eol=crlf" is set. This implies text.
- CRLF_AUTO      : attribute "auto" is set.
- CRLF_AUTO_INPUT: No attributes, core.autocrlf=input
- CRLF_AUTO_CRLF : No attributes, core.autocrlf=true

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 77 ++++++++++++++++++++++++++++++++++++++-------------------------
 1 file changed, 46 insertions(+), 31 deletions(-)

diff --git a/convert.c b/convert.c
index 50bdc42..f6ad9d6 100644
--- a/convert.c
+++ b/convert.c
@@ -19,12 +19,14 @@
 #define CONVERT_STAT_BITS_BIN       0x4
 
 enum crlf_action {
-	CRLF_GUESS = -1,
-	CRLF_BINARY = 0,
+	CRLF_UNDEFINED,
+	CRLF_BINARY,
 	CRLF_TEXT,
-	CRLF_INPUT,
-	CRLF_CRLF,
-	CRLF_AUTO
+	CRLF_TEXT_INPUT,
+	CRLF_TEXT_CRLF,
+	CRLF_AUTO,
+	CRLF_AUTO_INPUT,
+	CRLF_AUTO_CRLF
 };
 
 struct text_stat {
@@ -167,18 +169,19 @@ static enum eol output_eol(enum crlf_action crlf_action)
 	switch (crlf_action) {
 	case CRLF_BINARY:
 		return EOL_UNSET;
-	case CRLF_CRLF:
+	case CRLF_TEXT_CRLF:
 		return EOL_CRLF;
-	case CRLF_INPUT:
+	case CRLF_TEXT_INPUT:
 		return EOL_LF;
-	case CRLF_GUESS:
-		if (!auto_crlf)
-			return EOL_UNSET;
-		/* fall through */
+	case CRLF_UNDEFINED:
+	case CRLF_AUTO_CRLF:
+	case CRLF_AUTO_INPUT:
 	case CRLF_TEXT:
 	case CRLF_AUTO:
+		/* fall through */
 		return text_eol_is_crlf() ? EOL_CRLF : EOL_LF;
 	}
+	warning("Illegal crlf_action %d\n", (int)crlf_action);
 	return core_eol;
 }
 
@@ -247,11 +250,11 @@ static int crlf_to_git(const char *path, const char *src, size_t len,
 
 	gather_stats(src, len, &stats);
 
-	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS) {
+	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 		if (convert_is_binary(len, &stats))
 			return 0;
 
-		if (crlf_action == CRLF_GUESS) {
+		if (crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 			/*
 			 * If the file in the index has any CR in it, do not convert.
 			 * This is the new safer autocrlf handling.
@@ -278,7 +281,7 @@ static int crlf_to_git(const char *path, const char *src, size_t len,
 	if (strbuf_avail(buf) + buf->len < len)
 		strbuf_grow(buf, len - buf->len);
 	dst = buf->buf;
-	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS) {
+	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 		/*
 		 * If we guessed, we already know we rejected a file with
 		 * lone CR, and we can strip a CR without looking at what
@@ -319,8 +322,8 @@ static int crlf_to_worktree(const char *path, const char *src, size_t len,
 	if (stats.lf == stats.crlf)
 		return 0;
 
-	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS) {
-		if (crlf_action == CRLF_GUESS) {
+	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
+		if (crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 			/* If we have any CR or CRLF line endings, we do not touch it */
 			/* This is the new safer autocrlf-handling */
 			if (stats.cr > 0 || stats.crlf > 0)
@@ -708,16 +711,16 @@ static enum crlf_action git_path_check_crlf(struct git_attr_check *check)
 	const char *value = check->value;
 
 	if (ATTR_TRUE(value))
-		return CRLF_TEXT;
+		return text_eol_is_crlf() ? CRLF_TEXT_CRLF : CRLF_TEXT_INPUT;
 	else if (ATTR_FALSE(value))
 		return CRLF_BINARY;
 	else if (ATTR_UNSET(value))
 		;
 	else if (!strcmp(value, "input"))
-		return CRLF_INPUT;
+		return CRLF_TEXT_INPUT;
 	else if (!strcmp(value, "auto"))
 		return CRLF_AUTO;
-	return CRLF_GUESS;
+	return CRLF_UNDEFINED;
 }
 
 static enum eol git_path_check_eol(struct git_attr_check *check)
@@ -780,7 +783,7 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
 		enum eol eol_attr;
 		ca->crlf_action = git_path_check_crlf( ccheck + 4);
-		if (ca->crlf_action == CRLF_GUESS)
+		if (ca->crlf_action == CRLF_UNDEFINED)
 			ca->crlf_action = git_path_check_crlf(ccheck + 0);
 		ca->attr_action = ca->crlf_action;
 		ca->ident = git_path_check_ident(ccheck + 1);
@@ -789,16 +792,22 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 			return;
 		eol_attr = git_path_check_eol(ccheck + 3);
 		if (eol_attr == EOL_LF)
-			ca->crlf_action = CRLF_INPUT;
+			ca->crlf_action = CRLF_TEXT_INPUT;
 		else if (eol_attr == EOL_CRLF)
-			ca->crlf_action = CRLF_CRLF;
+			ca->crlf_action = CRLF_TEXT_CRLF;
 	} else {
 		ca->drv = NULL;
-		ca->crlf_action = CRLF_GUESS;
+		ca->crlf_action = CRLF_UNDEFINED;
 		ca->ident = 0;
 	}
-	if (ca->crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE)
+	if (ca->crlf_action == CRLF_TEXT)
+		ca->crlf_action = text_eol_is_crlf() ? CRLF_TEXT_CRLF : CRLF_TEXT_INPUT;
+	if (ca->crlf_action == CRLF_UNDEFINED && auto_crlf == AUTO_CRLF_FALSE)
 		ca->crlf_action = CRLF_BINARY;
+	if (ca->crlf_action == CRLF_UNDEFINED && auto_crlf == AUTO_CRLF_TRUE)
+		ca->crlf_action = CRLF_AUTO_CRLF;
+	if (ca->crlf_action == CRLF_UNDEFINED && auto_crlf == AUTO_CRLF_INPUT)
+		ca->crlf_action = CRLF_AUTO_INPUT;
 }
 
 int would_convert_to_git_filter_fd(const char *path)
@@ -826,18 +835,22 @@ const char *get_convert_attr_ascii(const char *path)
 
 	convert_attrs(&ca, path);
 	switch (ca.attr_action) {
-	case CRLF_GUESS:
+	case CRLF_UNDEFINED:
 		return "";
 	case CRLF_BINARY:
 		return "-text";
 	case CRLF_TEXT:
 		return "text";
-	case CRLF_INPUT:
+	case CRLF_TEXT_INPUT:
 		return "text eol=lf";
-	case CRLF_CRLF:
-		return "text=auto eol=crlf";
+	case CRLF_TEXT_CRLF:
+		return "text eol=crlf";
 	case CRLF_AUTO:
 		return "text=auto";
+	case CRLF_AUTO_CRLF:
+		return "text=auto eol=crlf"; /* This is not supported yet */
+	case CRLF_AUTO_INPUT:
+		return "text=auto eol=lf"; /* This is not supported yet */
 	}
 	return "";
 }
@@ -1382,11 +1395,13 @@ struct stream_filter *get_stream_filter(const char *path, const unsigned char *s
 		filter = ident_filter(sha1);
 
 	crlf_action = ca.crlf_action;
-
-	if ((crlf_action == CRLF_BINARY) || (crlf_action == CRLF_INPUT))
+	if ((crlf_action == CRLF_BINARY) ||
+			(crlf_action == CRLF_TEXT_INPUT))
 		filter = cascade_filter(filter, &null_filter_singleton);
 
-	else if ((crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS))
+	else if ((crlf_action == CRLF_AUTO ||
+						crlf_action == CRLF_AUTO_INPUT ||
+						crlf_action == CRLF_AUTO_CRLF))
 		;
 	else if (output_eol(crlf_action) == EOL_CRLF)
 		filter = cascade_filter(filter, lf_to_crlf_filter());
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* Re: [PATCH v1 1/6] t0027: Add tests for get_stream_filter()
  2016-02-02 16:53 ` tboegi
@ 2016-02-02 21:18   ` Junio C Hamano
  0 siblings, 0 replies; 47+ messages in thread
From: Junio C Hamano @ 2016-02-02 21:18 UTC (permalink / raw)
  To: tboegi; +Cc: git

tboegi@web.de writes:

> From: Torsten Bögershausen <tboegi@web.de>
>
> When a filter is configured, a different code-path is used in convert.c
> and entry.c via get_stream_filter(), but there are no test cases yet.
>
> Add tests for the filter API by configuring the ident filter.
> The result of the SHA1 conversion is not checked, this is already
> done in other TC.
>
> Add a parameter to checkout_files() in t0027.
> While changing the signature, add another parameter for the eol= attribute.
> This is currently unused, tests for e.g.
> "* text=auto eol=lf" will be added in a separate commit.
>
> Signed-off-by: Torsten Bögershausen <tboegi@web.de>
> ---
>  t/t0027-auto-crlf.sh | 262 ++++++++++++++++++++++++++++-----------------------
>  1 file changed, 146 insertions(+), 116 deletions(-)
>
> diff --git a/t/t0027-auto-crlf.sh b/t/t0027-auto-crlf.sh
> index 504e5a0..681f0c5 100755
> --- a/t/t0027-auto-crlf.sh
> +++ b/t/t0027-auto-crlf.sh
> @@ -21,32 +21,45 @@ compare_ws_file () {
>  	pfx=$1
>  	exp=$2.expect
>  	act=$pfx.actual.$3
> -	tr '\015\000' QN <"$2" >"$exp" &&
> -	tr '\015\000' QN <"$3" >"$act" &&
> +	tr '\015\000abcdef01234567890' QN00000000000000000 <"$2" >"$exp" &&
> +	tr '\015\000abcdef01234567890' QN00000000000000000 <"$3" >"$act" &&

'0' is listed twice on purpose?

>  	test_cmp $exp $act &&
>  	rm $exp $act

As we are not forcing all the future callers of this helper
functions to feed only non problematic pathnames, we should quote
these variable references, but this is not a new issue this patch
introduces.

>  }
>  
>  create_gitattributes () {
>  	attr=$1
> +	ident=$2
> +	case "$2" in
> +		"")
> +			>.gitattributes
> +			;;
> +		i)
> +			echo "* ident" >.gitattributes
> +			;;
> +		*)
> +			echo >&2 invalid ident: $2
> +			exit 1

This is overindented.  Case arms align with case/esac, and their
bodies indent one level down, i.e.

	case "$2" in
        "")
        	>.gitattributes
                ;;
	esac

By the way, I somehow find it hard to follow to assign magic
meanings "clear" and "prepare ident for everybody" to a short
and cryptic "" (empty string) and "i".  If you were taking advantage
of the fact that all existing uses of this helper function pass only
one argument to it and you will get $ident="" automatically from the
ones that you did not touch, that might be a reasonable way to reduce
patch noise, but because you are doing things like this

> -	create_gitattributes "$attr" &&
> +	create_gitattributes "$attr" "" &&

anyway, it may make sense to be slightly more verbose and readable.

> +	esac
> +
>  	case "$attr" in
>  		auto)
> -		echo "*.txt text=auto" >.gitattributes
> +		echo "*.txt text=auto" >>.gitattributes
>  		;;
>  		...
>  		;;
>  		*)
>  		echo >&2 invalid attribute: $attr

As you are touching this helper to emit more than one thing into the
file, I'd consider doing 

	{
                case "$2" in
                clear)	;;
                ident)	echo '* ident' ;;
                ...
                esac &&
                case "$1" in
                auto)	echo '*.txt auto' ;;
                ...
                esac
	} >.gitattributes

or even

	{
                while test "$#" != 1
                do
                        printf "%s\n" "$1"
                        shift
                done &&
                case "$1" in
                auto)	echo '*.txt auto' ;;
                ...
                esac &&
	} >.gitattributes

anticipating that we may want more things added to the output in the
future.  The latter form allows your callers to say things like

	create_gitattributes "auto" "* ident" "*.bin binary" 

without having to touch the helper function.

^ permalink raw reply	[flat|nested] 47+ messages in thread

* Re: [PATCH v1 2/6] convert.c: Remove path when not needed
  2016-02-02 16:53 ` [PATCH v1 2/6] convert.c: Remove path when not needed tboegi
@ 2016-02-02 21:32   ` Junio C Hamano
  0 siblings, 0 replies; 47+ messages in thread
From: Junio C Hamano @ 2016-02-02 21:32 UTC (permalink / raw)
  To: tboegi; +Cc: git

tboegi@web.de writes:


> Subject: Re: [PATCH v1 2/6] convert.c: Remove path when not needed

At least s/: Remove/: remove/, but I think

s/: Remove.*/: remove unused parameter 'path'/

would be easier to read.

All of these functions seem to have "path" in their name, sounding
as if they meant to ask "What is the crlf-ness for THIS PATH?"  Is
it still sensible to have "path" in their names?

The necessary information that is specific to the path was already
gathered when we prepared the 'check' thing, so they are still
asking and answering their questions specific to the path by
accepting 'check', but it still feels somewhat funny.

With or without "path" in their names, they are horribly misnamed
(e.g. "check crlf---are we asking if the file has crlf?  if the
file must be written out with crlf?  something else?").

Your later patches seem to refactor and reorganize this internal
calling mess in some way, so let's read on and see how the whole
thing improves ;-)

> -static enum crlf_action git_path_check_crlf(const char *path, struct git_attr_check *check)
> +static enum crlf_action git_path_check_crlf(struct git_attr_check *check)
>  {
>  	const char *value = check->value;
>  
> @@ -713,7 +713,7 @@ static enum crlf_action git_path_check_crlf(const char *path, struct git_attr_ch
>  	return CRLF_GUESS;
>  }
>  
> -static enum eol git_path_check_eol(const char *path, struct git_attr_check *check)
> +static enum eol git_path_check_eol(struct git_attr_check *check)
>  {
>  	const char *value = check->value;
>  
> @@ -726,8 +726,7 @@ static enum eol git_path_check_eol(const char *path, struct git_attr_check *chec
>  	return EOL_UNSET;
>  }
>  
> -static struct convert_driver *git_path_check_convert(const char *path,
> -					     struct git_attr_check *check)
> +static struct convert_driver *git_path_check_convert(struct git_attr_check *check)
>  {
>  	const char *value = check->value;
>  	struct convert_driver *drv;
> @@ -740,7 +739,7 @@ static struct convert_driver *git_path_check_convert(const char *path,
>  	return NULL;
>  }
>  
> -static int git_path_check_ident(const char *path, struct git_attr_check *check)
> +static int git_path_check_ident(struct git_attr_check *check)
>  {
>  	const char *value = check->value;
>  
> @@ -783,12 +782,12 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
>  	}
>  
>  	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
> -		ca->crlf_action = git_path_check_crlf(path, ccheck + 4);
> +		ca->crlf_action = git_path_check_crlf( ccheck + 4);
>  		if (ca->crlf_action == CRLF_GUESS)
> -			ca->crlf_action = git_path_check_crlf(path, ccheck + 0);
> -		ca->ident = git_path_check_ident(path, ccheck + 1);
> -		ca->drv = git_path_check_convert(path, ccheck + 2);
> -		ca->eol_attr = git_path_check_eol(path, ccheck + 3);
> +			ca->crlf_action = git_path_check_crlf(ccheck + 0);
> +		ca->ident = git_path_check_ident(ccheck + 1);
> +		ca->drv = git_path_check_convert(ccheck + 2);
> +		ca->eol_attr = git_path_check_eol(ccheck + 3);
>  	} else {
>  		ca->drv = NULL;
>  		ca->crlf_action = CRLF_GUESS;

^ permalink raw reply	[flat|nested] 47+ messages in thread

* Re: [PATCH v1 3/6] convert.c: Remove input_crlf_action()
  2016-02-02 16:53 ` [PATCH v1 3/6] convert.c: Remove input_crlf_action() tboegi
@ 2016-02-02 21:44   ` Junio C Hamano
  0 siblings, 0 replies; 47+ messages in thread
From: Junio C Hamano @ 2016-02-02 21:44 UTC (permalink / raw)
  To: tboegi; +Cc: git

tboegi@web.de writes:

> From: Torsten Bögershausen <tboegi@web.de>
>
> Integrate the code of input_crlf_action() into convert_attrs(),
> so that ca.crlf_action is aleays valid after calling convert_attrs().

s/aleays/always/

> Keep a copy of crlf_action in attr_action, this is needed for
> get_convert_attr_ascii().
>
> Remove eol_attr from struct conv_attrs, as it is now used temporally.
>
> Signed-off-by: Torsten Bögershausen <tboegi@web.de>
> ---
>  convert.c | 35 +++++++++++++----------------------
>  1 file changed, 13 insertions(+), 22 deletions(-)
>
> diff --git a/convert.c b/convert.c
> index a24c2a2..bca3d0c 100644
> --- a/convert.c
> +++ b/convert.c
> @@ -746,21 +746,10 @@ static int git_path_check_ident(struct git_attr_check *check)
>  	return !!ATTR_TRUE(value);
>  }
>  
> -static enum crlf_action input_crlf_action(enum crlf_action text_attr, enum eol eol_attr)
> -{
> -	if (text_attr == CRLF_BINARY)
> -		return CRLF_BINARY;
> -	if (eol_attr == EOL_LF)
> -		return CRLF_INPUT;
> -	if (eol_attr == EOL_CRLF)
> -		return CRLF_CRLF;
> -	return text_attr;
> -}
> -
>  struct conv_attrs {
>  	struct convert_driver *drv;
> -	enum crlf_action crlf_action;
> -	enum eol eol_attr;
> +	enum crlf_action attr_action; /* What attr says */
> +	enum crlf_action crlf_action; /* When no attr is set, use core.autocrlf */
>  	int ident;
>  };
>  
> @@ -782,16 +771,23 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
>  	}
>  
>  	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
> +		enum eol eol_attr;
>  		ca->crlf_action = git_path_check_crlf( ccheck + 4);

I guess this extra SP after opening paren was a misconversion from
the previous step...

>  		if (ca->crlf_action == CRLF_GUESS)
>  			ca->crlf_action = git_path_check_crlf(ccheck + 0);
> +		ca->attr_action = ca->crlf_action;
>  		ca->ident = git_path_check_ident(ccheck + 1);
>  		ca->drv = git_path_check_convert(ccheck + 2);
> -		ca->eol_attr = git_path_check_eol(ccheck + 3);
> +		if (ca->crlf_action == CRLF_BINARY)
> +			return;
> +		eol_attr = git_path_check_eol(ccheck + 3);
> +		if (eol_attr == EOL_LF)
> +			ca->crlf_action = CRLF_INPUT;
> +		else if (eol_attr == EOL_CRLF)
> +			ca->crlf_action = CRLF_CRLF;
>  	} else {
>  		ca->drv = NULL;
>  		ca->crlf_action = CRLF_GUESS;
> -		ca->eol_attr = EOL_UNSET;
>  		ca->ident = 0;
>  	}
>  }
> @@ -818,11 +814,9 @@ int would_convert_to_git_filter_fd(const char *path)
>  const char *get_convert_attr_ascii(const char *path)
>  {
>  	struct conv_attrs ca;
> -	enum crlf_action crlf_action;
>  
>  	convert_attrs(&ca, path);
> -	crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
> -	switch (crlf_action) {
> +	switch (ca.attr_action) {
>  	case CRLF_GUESS:
>  		return "";
>  	case CRLF_BINARY:
> @@ -861,7 +855,6 @@ int convert_to_git(const char *path, const char *src, size_t len,
>  		src = dst->buf;
>  		len = dst->len;
>  	}
> -	ca.crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
>  	ret |= crlf_to_git(path, src, len, dst, ca.crlf_action, checksafe);
>  	if (ret && dst) {
>  		src = dst->buf;
> @@ -882,7 +875,6 @@ void convert_to_git_filter_fd(const char *path, int fd, struct strbuf *dst,
>  	if (!apply_filter(path, NULL, 0, fd, dst, ca.drv->clean))
>  		die("%s: clean filter '%s' failed", path, ca.drv->name);
>  
> -	ca.crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
>  	crlf_to_git(path, dst->buf, dst->len, dst, ca.crlf_action, checksafe);
>  	ident_to_git(path, dst->buf, dst->len, dst, ca.ident);
>  }
> @@ -912,7 +904,6 @@ static int convert_to_working_tree_internal(const char *path, const char *src,
>  	 * is a smudge filter.  The filter might expect CRLFs.
>  	 */
>  	if (filter || !normalizing) {
> -		ca.crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
>  		ret |= crlf_to_worktree(path, src, len, dst, ca.crlf_action);
>  		if (ret) {
>  			src = dst->buf;
> @@ -1381,7 +1372,7 @@ struct stream_filter *get_stream_filter(const char *path, const unsigned char *s
>  	if (ca.ident)
>  		filter = ident_filter(sha1);
>  
> -	crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
> +	crlf_action = ca.crlf_action;
>  
>  	if ((crlf_action == CRLF_BINARY) || (crlf_action == CRLF_INPUT) ||
>  	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE))

So the idea is that the code before this prepared eol_attr and
crlf_action fields in convert_attrs() and consumers of these fields
called input_crlf_action() with them as parameters to choose one of
CRLF_X, but with this change, that is precomputed and left in the
new field crlf_action.

I didn't find a code where ca.eol_attr is redefined after
convert_attrs() returned, and all the codepaths that redefine
ca.crlf_action do so by assigning the result of the call to
input_crlf_action(), _and_ they do not use the value before doing
so.  So it appears that this should not change any behaviour.

OK.

^ permalink raw reply	[flat|nested] 47+ messages in thread

* [PATCH v2 1/7] t0027: Add tests for get_stream_filter()
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (7 preceding siblings ...)
  2016-02-02 16:53 ` [PATCH v1 6/6] convert.c: Refactor crlf_action tboegi
@ 2016-02-04 17:49 ` tboegi
  2016-02-04 19:52   ` Junio C Hamano
  2016-02-04 17:49 ` [PATCH v2 2/7] convert.c: remove unused parameter 'path' tboegi
                   ` (19 subsequent siblings)
  28 siblings, 1 reply; 47+ messages in thread
From: tboegi @ 2016-02-04 17:49 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

When a filter is configured, a different code-path is used in convert.c
and entry.c via get_stream_filter(), but there are no test cases yet.

Add tests for the filter API by configuring the ident filter.
The result of the SHA1 conversion is not checked, this is already
done in other TC.

Add a parameter to checkout_files() in t0027.
While changing the signature, add another parameter for the eol= attribute.
This is currently unused, tests for e.g.
"* text=auto eol=lf" will be added in a separate commit.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 Changes since v1:
 - t0027: Comments from Junio, create_gitattributes() and others
 - convert.c: Minor whitespace fixes, changed the commit message
 - Added 7/7: convert.c: simplify text_stat from the TODO stack
t/t0027-auto-crlf.sh | 281 ++++++++++++++++++++++++++-------------------------
 1 file changed, 146 insertions(+), 135 deletions(-)

diff --git a/t/t0027-auto-crlf.sh b/t/t0027-auto-crlf.sh
index 504e5a0..1d84ed3 100755
--- a/t/t0027-auto-crlf.sh
+++ b/t/t0027-auto-crlf.sh
@@ -21,38 +21,32 @@ compare_ws_file () {
 	pfx=$1
 	exp=$2.expect
 	act=$pfx.actual.$3
-	tr '\015\000' QN <"$2" >"$exp" &&
-	tr '\015\000' QN <"$3" >"$act" &&
-	test_cmp $exp $act &&
-	rm $exp $act
+	tr '\015\000abcdef0123456789' QN00000000000000000 <"$2" >"$exp" &&
+	tr '\015\000abcdef0123456789' QN00000000000000000 <"$3" >"$act" &&
+	test_cmp "$exp" "$act" &&
+	rm "$exp" "$act"
 }
 
 create_gitattributes () {
-	attr=$1
-	case "$attr" in
-		auto)
-		echo "*.txt text=auto" >.gitattributes
-		;;
-		text)
-		echo "*.txt text" >.gitattributes
-		;;
-		-text)
-		echo "*.txt -text" >.gitattributes
-		;;
-		crlf)
-		echo "*.txt eol=crlf" >.gitattributes
-		;;
-		lf)
-		echo "*.txt eol=lf" >.gitattributes
-		;;
-		"")
-		echo >.gitattributes
-		;;
-		*)
-		echo >&2 invalid attribute: $attr
-		exit 1
-		;;
-	esac
+	{
+		while test "$#" != 0
+		do
+			case "$1" in
+				auto)	 echo '*.txt text=auto' ;;
+				i)     echo '* ident' ;;
+				text)	 echo '*.txt text' ;;
+				-text) echo '*.txt -text' ;;
+				crlf)  echo '*.txt eol=crlf' ;;
+				lf)    echo '*.txt eol=lf' ;;
+				"") echo '' ;;
+				*)
+				echo >&2 invalid attribute: $attr
+				exit 1
+				;;
+			esac &&
+			shift
+		done
+	} >.gitattributes
 }
 
 create_NNO_files () {
@@ -208,28 +202,30 @@ check_in_repo_NNO () {
 }
 
 checkout_files () {
-	eol=$1
-	crlf=$2
-	attr=$3
-	lfname=$4
-	crlfname=$5
-	lfmixcrlf=$6
-	lfmixcr=$7
-	crlfnul=$8
-	create_gitattributes $attr &&
+	attr=$1 ; shift
+	ident=$1; shift
+	aeol=$1 ; shift
+	crlf=$1 ; shift
+	ceol=$1 ; shift
+	lfname=$1 ; shift
+	crlfname=$1 ; shift
+	lfmixcrlf=$1 ; shift
+	lfmixcr=$1 ; shift
+	crlfnul=$1 ; shift
+	create_gitattributes "$attr" "$ident" &&
 	git config core.autocrlf $crlf &&
-	pfx=eol_${eol}_crlf_${crlf}_attr_${attr}_ &&
+	pfx=eol_${ceol}_crlf_${crlf}_attr_${attr}_ &&
 	for f in LF CRLF LF_mix_CR CRLF_mix_LF LF_nul
 	do
 		rm crlf_false_attr__$f.txt &&
-		if test -z "$eol"; then
+		if test -z "$ceol"; then
 			git checkout crlf_false_attr__$f.txt
 		else
-			git -c core.eol=$eol checkout crlf_false_attr__$f.txt
+			git -c core.eol=$ceol checkout crlf_false_attr__$f.txt
 		fi
 	done
 
-	test_expect_success "ls-files --eol $lfname ${pfx}LF.txt" '
+	test_expect_success "ls-files --eol attr=$attr i=$ident $aeol core.autocrlf=$crlf core.eol=$ceol" '
 		test_when_finished "rm expect actual" &&
 		sort <<-EOF >expect &&
 		i/crlf w/$(stats_ascii $crlfname) crlf_false_attr__CRLF.txt
@@ -244,19 +240,19 @@ checkout_files () {
 		sort >actual &&
 		test_cmp expect actual
 	'
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=LF" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=LF" "
 		compare_ws_file $pfx $lfname    crlf_false_attr__LF.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=CRLF" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=CRLF" "
 		compare_ws_file $pfx $crlfname  crlf_false_attr__CRLF.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=CRLF_mix_LF" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=CRLF_mix_LF" "
 		compare_ws_file $pfx $lfmixcrlf crlf_false_attr__CRLF_mix_LF.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=LF_mix_CR" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=LF_mix_CR" "
 		compare_ws_file $pfx $lfmixcr   crlf_false_attr__LF_mix_CR.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=LF_nul" "
+	test_expect_success "checkout i=$ident attributes=$attr $aeol core.autocrlf=$crlf core.eol=$ceol file=LF_nul" "
 		compare_ws_file $pfx $crlfnul   crlf_false_attr__LF_nul.txt
 	"
 }
@@ -301,14 +297,13 @@ test_expect_success 'setup master' '
 	git checkout -b master &&
 	git add .gitattributes &&
 	git commit -m "add .gitattributes" "" &&
-	printf "line1\nline2\nline3"     >LF &&
-	printf "line1\r\nline2\r\nline3" >CRLF &&
-	printf "line1\r\nline2\nline3"   >repoMIX &&
-	printf "line1\r\nline2\nline3"   >CRLF_mix_LF &&
-	printf "line1\nline2\rline3"     >LF_mix_CR &&
-	printf "line1\r\nline2\rline3"   >CRLF_mix_CR &&
-	printf "line1Q\r\nline2\r\nline3" | q_to_nul >CRLF_nul &&
-	printf "line1Q\nline2\nline3" | q_to_nul >LF_nul &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONE\nLINETWO\nLINETHREE"     >LF &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\r\nLINEONE\r\nLINETWO\r\nLINETHREE" >CRLF &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONE\r\nLINETWO\nLINETHREE"   >CRLF_mix_LF &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONE\nLINETWO\rLINETHREE"     >LF_mix_CR &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\r\nLINEONE\r\nLINETWO\rLINETHREE"   >CRLF_mix_CR &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\r\nLINEONEQ\r\nLINETWO\r\nLINETHREE" | q_to_nul >CRLF_nul &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONEQ\nLINETWO\nLINETHREE" | q_to_nul >LF_nul &&
 	create_NNO_files CRLF_mix_LF CRLF_mix_LF CRLF_mix_LF CRLF_mix_LF CRLF_mix_LF &&
 	git -c core.autocrlf=false add NNO_*.txt &&
 	git commit -m "mixed line endings" &&
@@ -449,23 +444,18 @@ check_in_repo_NNO input "-text" LF        CRLF      CRLF_mix_LF  LF_mix_CR 	CRLF
 # How to read the table below:
 # - checkout_files will check multiple files with a combination of settings
 #   and attributes (core.autocrlf=input is forbidden with core.eol=crlf)
-# - parameter $1 : core.eol               lf | crlf
-# - parameter $2 : core.autocrlf          false | true | input
-# - parameter $3 : text in .gitattributs  "" (empty) | auto | text | -text
-# - parameter $4 : reference for a file with only LF in the repo
-# - parameter $5 : reference for a file with only CRLF in the repo
-# - parameter $6 : reference for a file with mixed LF and CRLF in the repo
-# - parameter $7 : reference for a file with LF and CR in the repo (does somebody uses this ?)
-# - parameter $8 : reference for a file with CRLF and a NUL (should be handled as binary when auto)
-
-#                                            What we have in the repo:
-#                                            ----------------- EOL in repo ----------------
-#                                            LF    CRLF  CRLF_mix_LF  LF_mix_CR    CRLF_nul
-#                   settings with checkout:
-#                   core.   core.   .gitattr
-#                    eol     acrlf
-#                                            ----------------------------------------------
-#                                            What we want to have in the working tree:
+#
+# - parameter $1 	: text in .gitattributs  "" (empty) | auto | text | -text
+# - parameter $2 	: ident                  "" | i (i == ident)
+# - parameter $3 	: eol in .gitattributs   "" (empty) | lf | crlf
+# - parameter $4 	: core.autocrlf          false | true | input
+# - parameter $5 	: core.eol               "" | lf | crlf | "native"
+# - parameter $6 	: reference for a file with only LF in the repo
+# - parameter $7 	: reference for a file with only CRLF in the repo
+# - parameter $8 	: reference for a file with mixed LF and CRLF in the repo
+# - parameter $9 	: reference for a file with LF and CR in the repo
+# - parameter $10 : reference for a file with CRLF and a NUL (should be handled as binary when auto)
+
 if test_have_prereq NATIVE_CRLF
 then
 MIX_CRLF_LF=CRLF
@@ -480,69 +470,90 @@ LFNUL=LF_nul
 fi
 export CRLF_MIX_LF_CR MIX NL
 
-checkout_files    lf      false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "auto"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    lf      input "auto"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "text"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    lf      input "text"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      input "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      input "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    lf      true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    lf      input "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-
-checkout_files    crlf    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    false "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    crlf    true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    crlf    false "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    crlf    true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    crlf    false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    crlf    true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-
-checkout_files    ""      false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "auto"    $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
-checkout_files    ""      true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    ""      input "auto"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "text"    $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
-checkout_files    ""      true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    ""      input "text"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      input "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      input "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    ""      true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    ""      input "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-
-checkout_files    native  false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  false "auto"    $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
-checkout_files    native  true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    native  false "text"    $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
-checkout_files    native  true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    native  false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    native  true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+checkout_files ""      "" ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    true   crlf     CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    true   lf       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" ""    true   native   CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      i  ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    false  ""       $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    false  crlf     CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    false  native   $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    true   ""       CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    true   crlf     CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    true   lf       CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" ""    true   native   CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  i  ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+
+for id in "" i;
+do
+	checkout_files "crlf"  "$id" ""    false  ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    false  crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    false  lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    false  native   CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    input  ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    input  lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   native   CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "lf"    "$id" ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    false  ""       $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
+	checkout_files "text"  "$id" ""    false  crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    false  native   $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
+	checkout_files "text"  "$id" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    true   ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    true   crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    true   lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    true   native   CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "-text" "$id" ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+done
 
 # Should be the last test case: remove some files from the worktree
 test_expect_success 'ls-files --eol -d -z' '
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v2 2/7] convert.c: remove unused parameter 'path'
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (8 preceding siblings ...)
  2016-02-04 17:49 ` [PATCH v2 1/7] t0027: Add tests for get_stream_filter() tboegi
@ 2016-02-04 17:49 ` tboegi
  2016-02-04 17:49 ` [PATCH v2 3/7] convert.c: Remove input_crlf_action() tboegi
                   ` (18 subsequent siblings)
  28 siblings, 0 replies; 47+ messages in thread
From: tboegi @ 2016-02-04 17:49 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Some functions get a parameter path, but don't use it.
Remove the unused parameter.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 19 +++++++++----------
 1 file changed, 9 insertions(+), 10 deletions(-)

diff --git a/convert.c b/convert.c
index 4bb4ec1..a24c2a2 100644
--- a/convert.c
+++ b/convert.c
@@ -696,7 +696,7 @@ static int ident_to_worktree(const char *path, const char *src, size_t len,
 	return 1;
 }
 
-static enum crlf_action git_path_check_crlf(const char *path, struct git_attr_check *check)
+static enum crlf_action git_path_check_crlf(struct git_attr_check *check)
 {
 	const char *value = check->value;
 
@@ -713,7 +713,7 @@ static enum crlf_action git_path_check_crlf(const char *path, struct git_attr_ch
 	return CRLF_GUESS;
 }
 
-static enum eol git_path_check_eol(const char *path, struct git_attr_check *check)
+static enum eol git_path_check_eol(struct git_attr_check *check)
 {
 	const char *value = check->value;
 
@@ -726,8 +726,7 @@ static enum eol git_path_check_eol(const char *path, struct git_attr_check *chec
 	return EOL_UNSET;
 }
 
-static struct convert_driver *git_path_check_convert(const char *path,
-					     struct git_attr_check *check)
+static struct convert_driver *git_path_check_convert(struct git_attr_check *check)
 {
 	const char *value = check->value;
 	struct convert_driver *drv;
@@ -740,7 +739,7 @@ static struct convert_driver *git_path_check_convert(const char *path,
 	return NULL;
 }
 
-static int git_path_check_ident(const char *path, struct git_attr_check *check)
+static int git_path_check_ident(struct git_attr_check *check)
 {
 	const char *value = check->value;
 
@@ -783,12 +782,12 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 	}
 
 	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
-		ca->crlf_action = git_path_check_crlf(path, ccheck + 4);
+		ca->crlf_action = git_path_check_crlf( ccheck + 4);
 		if (ca->crlf_action == CRLF_GUESS)
-			ca->crlf_action = git_path_check_crlf(path, ccheck + 0);
-		ca->ident = git_path_check_ident(path, ccheck + 1);
-		ca->drv = git_path_check_convert(path, ccheck + 2);
-		ca->eol_attr = git_path_check_eol(path, ccheck + 3);
+			ca->crlf_action = git_path_check_crlf(ccheck + 0);
+		ca->ident = git_path_check_ident(ccheck + 1);
+		ca->drv = git_path_check_convert(ccheck + 2);
+		ca->eol_attr = git_path_check_eol(ccheck + 3);
 	} else {
 		ca->drv = NULL;
 		ca->crlf_action = CRLF_GUESS;
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v2 3/7] convert.c: Remove input_crlf_action()
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (9 preceding siblings ...)
  2016-02-04 17:49 ` [PATCH v2 2/7] convert.c: remove unused parameter 'path' tboegi
@ 2016-02-04 17:49 ` tboegi
  2016-02-04 17:49 ` [PATCH v2 4/7] convert.c: Use text_eol_is_crlf() tboegi
                   ` (17 subsequent siblings)
  28 siblings, 0 replies; 47+ messages in thread
From: tboegi @ 2016-02-04 17:49 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Integrate the code of input_crlf_action() into convert_attrs(),
so that ca.crlf_action is always valid after calling convert_attrs().
Keep a copy of crlf_action in attr_action, this is needed for
get_convert_attr_ascii().

Remove eol_attr from struct conv_attrs, as it is now used temporally.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 37 ++++++++++++++-----------------------
 1 file changed, 14 insertions(+), 23 deletions(-)

diff --git a/convert.c b/convert.c
index a24c2a2..d0c8c66 100644
--- a/convert.c
+++ b/convert.c
@@ -746,21 +746,10 @@ static int git_path_check_ident(struct git_attr_check *check)
 	return !!ATTR_TRUE(value);
 }
 
-static enum crlf_action input_crlf_action(enum crlf_action text_attr, enum eol eol_attr)
-{
-	if (text_attr == CRLF_BINARY)
-		return CRLF_BINARY;
-	if (eol_attr == EOL_LF)
-		return CRLF_INPUT;
-	if (eol_attr == EOL_CRLF)
-		return CRLF_CRLF;
-	return text_attr;
-}
-
 struct conv_attrs {
 	struct convert_driver *drv;
-	enum crlf_action crlf_action;
-	enum eol eol_attr;
+	enum crlf_action attr_action; /* What attr says */
+	enum crlf_action crlf_action; /* When no attr is set, use core.autocrlf */
 	int ident;
 };
 
@@ -782,16 +771,23 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 	}
 
 	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
-		ca->crlf_action = git_path_check_crlf( ccheck + 4);
+		enum eol eol_attr;
+		ca->crlf_action = git_path_check_crlf(ccheck + 4);
 		if (ca->crlf_action == CRLF_GUESS)
 			ca->crlf_action = git_path_check_crlf(ccheck + 0);
+		ca->attr_action = ca->crlf_action;
 		ca->ident = git_path_check_ident(ccheck + 1);
 		ca->drv = git_path_check_convert(ccheck + 2);
-		ca->eol_attr = git_path_check_eol(ccheck + 3);
+		if (ca->crlf_action == CRLF_BINARY)
+			return;
+		eol_attr = git_path_check_eol(ccheck + 3);
+		if (eol_attr == EOL_LF)
+			ca->crlf_action = CRLF_INPUT;
+		else if (eol_attr == EOL_CRLF)
+			ca->crlf_action = CRLF_CRLF;
 	} else {
 		ca->drv = NULL;
 		ca->crlf_action = CRLF_GUESS;
-		ca->eol_attr = EOL_UNSET;
 		ca->ident = 0;
 	}
 }
@@ -818,11 +814,9 @@ int would_convert_to_git_filter_fd(const char *path)
 const char *get_convert_attr_ascii(const char *path)
 {
 	struct conv_attrs ca;
-	enum crlf_action crlf_action;
 
 	convert_attrs(&ca, path);
-	crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
-	switch (crlf_action) {
+	switch (ca.attr_action) {
 	case CRLF_GUESS:
 		return "";
 	case CRLF_BINARY:
@@ -861,7 +855,6 @@ int convert_to_git(const char *path, const char *src, size_t len,
 		src = dst->buf;
 		len = dst->len;
 	}
-	ca.crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
 	ret |= crlf_to_git(path, src, len, dst, ca.crlf_action, checksafe);
 	if (ret && dst) {
 		src = dst->buf;
@@ -882,7 +875,6 @@ void convert_to_git_filter_fd(const char *path, int fd, struct strbuf *dst,
 	if (!apply_filter(path, NULL, 0, fd, dst, ca.drv->clean))
 		die("%s: clean filter '%s' failed", path, ca.drv->name);
 
-	ca.crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
 	crlf_to_git(path, dst->buf, dst->len, dst, ca.crlf_action, checksafe);
 	ident_to_git(path, dst->buf, dst->len, dst, ca.ident);
 }
@@ -912,7 +904,6 @@ static int convert_to_working_tree_internal(const char *path, const char *src,
 	 * is a smudge filter.  The filter might expect CRLFs.
 	 */
 	if (filter || !normalizing) {
-		ca.crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
 		ret |= crlf_to_worktree(path, src, len, dst, ca.crlf_action);
 		if (ret) {
 			src = dst->buf;
@@ -1381,7 +1372,7 @@ struct stream_filter *get_stream_filter(const char *path, const unsigned char *s
 	if (ca.ident)
 		filter = ident_filter(sha1);
 
-	crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
+	crlf_action = ca.crlf_action;
 
 	if ((crlf_action == CRLF_BINARY) || (crlf_action == CRLF_INPUT) ||
 	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE))
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v2 4/7] convert.c: Use text_eol_is_crlf()
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (10 preceding siblings ...)
  2016-02-04 17:49 ` [PATCH v2 3/7] convert.c: Remove input_crlf_action() tboegi
@ 2016-02-04 17:49 ` tboegi
  2016-02-04 20:13   ` Junio C Hamano
  2016-02-04 17:49 ` [PATCH v2 5/7] convert: auto_crlf=false and no attributes set: same as binary tboegi
                   ` (16 subsequent siblings)
  28 siblings, 1 reply; 47+ messages in thread
From: tboegi @ 2016-02-04 17:49 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Add a helper function to find out, which line endings
text files should get at checkout, depending on
core.autocrlf and core.eol

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 25 +++++++++++++++++--------
 1 file changed, 17 insertions(+), 8 deletions(-)

diff --git a/convert.c b/convert.c
index d0c8c66..9ffd043 100644
--- a/convert.c
+++ b/convert.c
@@ -149,6 +149,19 @@ const char *get_wt_convert_stats_ascii(const char *path)
 	return ret;
 }
 
+static int text_eol_is_crlf(void)
+{
+	if (auto_crlf == AUTO_CRLF_TRUE)
+		return 1;
+	else if (auto_crlf == AUTO_CRLF_INPUT)
+		return 0;
+	if (core_eol == EOL_CRLF)
+		return 1;
+	if (core_eol == EOL_UNSET && EOL_NATIVE == EOL_CRLF)
+		return 1;
+	return 0;
+}
+
 static enum eol output_eol(enum crlf_action crlf_action)
 {
 	switch (crlf_action) {
@@ -164,12 +177,7 @@ static enum eol output_eol(enum crlf_action crlf_action)
 		/* fall through */
 	case CRLF_TEXT:
 	case CRLF_AUTO:
-		if (auto_crlf == AUTO_CRLF_TRUE)
-			return EOL_CRLF;
-		else if (auto_crlf == AUTO_CRLF_INPUT)
-			return EOL_LF;
-		else if (core_eol == EOL_UNSET)
-			return EOL_NATIVE;
+		return text_eol_is_crlf() ? EOL_CRLF : EOL_LF;
 	}
 	return core_eol;
 }
@@ -1378,8 +1386,9 @@ struct stream_filter *get_stream_filter(const char *path, const unsigned char *s
 	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE))
 		filter = cascade_filter(filter, &null_filter_singleton);
 
-	else if (output_eol(crlf_action) == EOL_CRLF &&
-		 !(crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS))
+	else if ((crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS))
+		;
+	else if (output_eol(crlf_action) == EOL_CRLF)
 		filter = cascade_filter(filter, lf_to_crlf_filter());
 
 	return filter;
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v2 5/7] convert: auto_crlf=false and no attributes set: same as binary
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (11 preceding siblings ...)
  2016-02-04 17:49 ` [PATCH v2 4/7] convert.c: Use text_eol_is_crlf() tboegi
@ 2016-02-04 17:49 ` tboegi
  2016-02-04 17:49 ` [PATCH v2 6/7] convert.c: Refactor crlf_action tboegi
                   ` (15 subsequent siblings)
  28 siblings, 0 replies; 47+ messages in thread
From: tboegi @ 2016-02-04 17:49 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

When core.autocrlf is set to false, and no attributes are set, the file
is treated as binary.
Simplify the logic and remove duplicated code when dealing with
(crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE) by setting
crlf_action=CRLF_BINARY already in convert_attrs().

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/convert.c b/convert.c
index 9ffd043..4e33db1 100644
--- a/convert.c
+++ b/convert.c
@@ -235,7 +235,6 @@ static int crlf_to_git(const char *path, const char *src, size_t len,
 	char *dst;
 
 	if (crlf_action == CRLF_BINARY ||
-	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE) ||
 	    (src && !len))
 		return 0;
 
@@ -798,6 +797,8 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 		ca->crlf_action = CRLF_GUESS;
 		ca->ident = 0;
 	}
+	if (ca->crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE)
+		ca->crlf_action = CRLF_BINARY;
 }
 
 int would_convert_to_git_filter_fd(const char *path)
@@ -1382,8 +1383,7 @@ struct stream_filter *get_stream_filter(const char *path, const unsigned char *s
 
 	crlf_action = ca.crlf_action;
 
-	if ((crlf_action == CRLF_BINARY) || (crlf_action == CRLF_INPUT) ||
-	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE))
+	if ((crlf_action == CRLF_BINARY) || (crlf_action == CRLF_INPUT))
 		filter = cascade_filter(filter, &null_filter_singleton);
 
 	else if ((crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS))
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v2 6/7] convert.c: Refactor crlf_action
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (12 preceding siblings ...)
  2016-02-04 17:49 ` [PATCH v2 5/7] convert: auto_crlf=false and no attributes set: same as binary tboegi
@ 2016-02-04 17:49 ` tboegi
  2016-02-04 17:50 ` [PATCH v2 7/7] convert.c: simplify text_stat tboegi
                   ` (14 subsequent siblings)
  28 siblings, 0 replies; 47+ messages in thread
From: tboegi @ 2016-02-04 17:49 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Refactor the determination and usage of crlf_action.
Today, when no attributes are set on a file,
crlf_action is set to CRLF_GUESS, and later, CRLF_GUESS is used as an
indication that core.autocrlf is not false and that some automatic eol
conversion is needed.
Make more clear, what is what, by defining:

- CRLF_UNDEFINED : No attributes set. Temparally used, until core.autocrlf
                   and core.eol is evaluated and one of CRLF_BINARY,
                   CRLF_AUTO_INPUT or CRLF_AUTO_CRLF is selected
- CRLF_BINARY    : No processing of line endings.
- CRLF_TEXT      : attribute "text" is set, line endings are processed.
- CRLF_TEXT_INPUT: attribute "input" or "eol=lf" is set. This implies text.
- CRLF_TEXT_CRLF : attribute "eol=crlf" is set. This implies text.
- CRLF_AUTO      : attribute "auto" is set.
- CRLF_AUTO_INPUT: No attributes, core.autocrlf=input
- CRLF_AUTO_CRLF : No attributes, core.autocrlf=true

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 77 ++++++++++++++++++++++++++++++++++++++-------------------------
 1 file changed, 46 insertions(+), 31 deletions(-)

diff --git a/convert.c b/convert.c
index 4e33db1..dd9646a 100644
--- a/convert.c
+++ b/convert.c
@@ -19,12 +19,14 @@
 #define CONVERT_STAT_BITS_BIN       0x4
 
 enum crlf_action {
-	CRLF_GUESS = -1,
-	CRLF_BINARY = 0,
+	CRLF_UNDEFINED,
+	CRLF_BINARY,
 	CRLF_TEXT,
-	CRLF_INPUT,
-	CRLF_CRLF,
-	CRLF_AUTO
+	CRLF_TEXT_INPUT,
+	CRLF_TEXT_CRLF,
+	CRLF_AUTO,
+	CRLF_AUTO_INPUT,
+	CRLF_AUTO_CRLF
 };
 
 struct text_stat {
@@ -167,18 +169,19 @@ static enum eol output_eol(enum crlf_action crlf_action)
 	switch (crlf_action) {
 	case CRLF_BINARY:
 		return EOL_UNSET;
-	case CRLF_CRLF:
+	case CRLF_TEXT_CRLF:
 		return EOL_CRLF;
-	case CRLF_INPUT:
+	case CRLF_TEXT_INPUT:
 		return EOL_LF;
-	case CRLF_GUESS:
-		if (!auto_crlf)
-			return EOL_UNSET;
-		/* fall through */
+	case CRLF_UNDEFINED:
+	case CRLF_AUTO_CRLF:
+	case CRLF_AUTO_INPUT:
 	case CRLF_TEXT:
 	case CRLF_AUTO:
+		/* fall through */
 		return text_eol_is_crlf() ? EOL_CRLF : EOL_LF;
 	}
+	warning("Illegal crlf_action %d\n", (int)crlf_action);
 	return core_eol;
 }
 
@@ -247,11 +250,11 @@ static int crlf_to_git(const char *path, const char *src, size_t len,
 
 	gather_stats(src, len, &stats);
 
-	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS) {
+	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 		if (convert_is_binary(len, &stats))
 			return 0;
 
-		if (crlf_action == CRLF_GUESS) {
+		if (crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 			/*
 			 * If the file in the index has any CR in it, do not convert.
 			 * This is the new safer autocrlf handling.
@@ -278,7 +281,7 @@ static int crlf_to_git(const char *path, const char *src, size_t len,
 	if (strbuf_avail(buf) + buf->len < len)
 		strbuf_grow(buf, len - buf->len);
 	dst = buf->buf;
-	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS) {
+	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 		/*
 		 * If we guessed, we already know we rejected a file with
 		 * lone CR, and we can strip a CR without looking at what
@@ -319,8 +322,8 @@ static int crlf_to_worktree(const char *path, const char *src, size_t len,
 	if (stats.lf == stats.crlf)
 		return 0;
 
-	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS) {
-		if (crlf_action == CRLF_GUESS) {
+	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
+		if (crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 			/* If we have any CR or CRLF line endings, we do not touch it */
 			/* This is the new safer autocrlf-handling */
 			if (stats.cr > 0 || stats.crlf > 0)
@@ -708,16 +711,16 @@ static enum crlf_action git_path_check_crlf(struct git_attr_check *check)
 	const char *value = check->value;
 
 	if (ATTR_TRUE(value))
-		return CRLF_TEXT;
+		return text_eol_is_crlf() ? CRLF_TEXT_CRLF : CRLF_TEXT_INPUT;
 	else if (ATTR_FALSE(value))
 		return CRLF_BINARY;
 	else if (ATTR_UNSET(value))
 		;
 	else if (!strcmp(value, "input"))
-		return CRLF_INPUT;
+		return CRLF_TEXT_INPUT;
 	else if (!strcmp(value, "auto"))
 		return CRLF_AUTO;
-	return CRLF_GUESS;
+	return CRLF_UNDEFINED;
 }
 
 static enum eol git_path_check_eol(struct git_attr_check *check)
@@ -780,7 +783,7 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
 		enum eol eol_attr;
 		ca->crlf_action = git_path_check_crlf(ccheck + 4);
-		if (ca->crlf_action == CRLF_GUESS)
+		if (ca->crlf_action == CRLF_UNDEFINED)
 			ca->crlf_action = git_path_check_crlf(ccheck + 0);
 		ca->attr_action = ca->crlf_action;
 		ca->ident = git_path_check_ident(ccheck + 1);
@@ -789,16 +792,22 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 			return;
 		eol_attr = git_path_check_eol(ccheck + 3);
 		if (eol_attr == EOL_LF)
-			ca->crlf_action = CRLF_INPUT;
+			ca->crlf_action = CRLF_TEXT_INPUT;
 		else if (eol_attr == EOL_CRLF)
-			ca->crlf_action = CRLF_CRLF;
+			ca->crlf_action = CRLF_TEXT_CRLF;
 	} else {
 		ca->drv = NULL;
-		ca->crlf_action = CRLF_GUESS;
+		ca->crlf_action = CRLF_UNDEFINED;
 		ca->ident = 0;
 	}
-	if (ca->crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE)
+	if (ca->crlf_action == CRLF_TEXT)
+		ca->crlf_action = text_eol_is_crlf() ? CRLF_TEXT_CRLF : CRLF_TEXT_INPUT;
+	if (ca->crlf_action == CRLF_UNDEFINED && auto_crlf == AUTO_CRLF_FALSE)
 		ca->crlf_action = CRLF_BINARY;
+	if (ca->crlf_action == CRLF_UNDEFINED && auto_crlf == AUTO_CRLF_TRUE)
+		ca->crlf_action = CRLF_AUTO_CRLF;
+	if (ca->crlf_action == CRLF_UNDEFINED && auto_crlf == AUTO_CRLF_INPUT)
+		ca->crlf_action = CRLF_AUTO_INPUT;
 }
 
 int would_convert_to_git_filter_fd(const char *path)
@@ -826,18 +835,22 @@ const char *get_convert_attr_ascii(const char *path)
 
 	convert_attrs(&ca, path);
 	switch (ca.attr_action) {
-	case CRLF_GUESS:
+	case CRLF_UNDEFINED:
 		return "";
 	case CRLF_BINARY:
 		return "-text";
 	case CRLF_TEXT:
 		return "text";
-	case CRLF_INPUT:
+	case CRLF_TEXT_INPUT:
 		return "text eol=lf";
-	case CRLF_CRLF:
-		return "text=auto eol=crlf";
+	case CRLF_TEXT_CRLF:
+		return "text eol=crlf";
 	case CRLF_AUTO:
 		return "text=auto";
+	case CRLF_AUTO_CRLF:
+		return "text=auto eol=crlf"; /* This is not supported yet */
+	case CRLF_AUTO_INPUT:
+		return "text=auto eol=lf"; /* This is not supported yet */
 	}
 	return "";
 }
@@ -1382,11 +1395,13 @@ struct stream_filter *get_stream_filter(const char *path, const unsigned char *s
 		filter = ident_filter(sha1);
 
 	crlf_action = ca.crlf_action;
-
-	if ((crlf_action == CRLF_BINARY) || (crlf_action == CRLF_INPUT))
+	if ((crlf_action == CRLF_BINARY) ||
+			(crlf_action == CRLF_TEXT_INPUT))
 		filter = cascade_filter(filter, &null_filter_singleton);
 
-	else if ((crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS))
+	else if ((crlf_action == CRLF_AUTO ||
+						crlf_action == CRLF_AUTO_INPUT ||
+						crlf_action == CRLF_AUTO_CRLF))
 		;
 	else if (output_eol(crlf_action) == EOL_CRLF)
 		filter = cascade_filter(filter, lf_to_crlf_filter());
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v2 7/7] convert.c: simplify text_stat
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (13 preceding siblings ...)
  2016-02-04 17:49 ` [PATCH v2 6/7] convert.c: Refactor crlf_action tboegi
@ 2016-02-04 17:50 ` tboegi
  2016-02-04 20:37   ` Junio C Hamano
  2016-02-05 16:13 ` [PATCH v3 1/7] t0027: Add tests for get_stream_filter() tboegi
                   ` (13 subsequent siblings)
  28 siblings, 1 reply; 47+ messages in thread
From: tboegi @ 2016-02-04 17:50 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Simplify the statistics:
lonecr counts the CR which is not followed by a LF,
lonelf counts the LF which is not preceded by a CR,
crlf counts CRLF combinations.
This simplifies the evaluation of the statistics.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 58 +++++++++++++++++++++++++++-------------------------------
 1 file changed, 27 insertions(+), 31 deletions(-)

diff --git a/convert.c b/convert.c
index dd9646a..ebf4d0e 100644
--- a/convert.c
+++ b/convert.c
@@ -31,7 +31,7 @@ enum crlf_action {
 
 struct text_stat {
 	/* NUL, CR, LF and CRLF counts */
-	unsigned nul, cr, lf, crlf;
+	unsigned nul, lonecr, lonelf, crlf;
 
 	/* These are just approximations! */
 	unsigned printable, nonprintable;
@@ -46,13 +46,15 @@ static void gather_stats(const char *buf, unsigned long size, struct text_stat *
 	for (i = 0; i < size; i++) {
 		unsigned char c = buf[i];
 		if (c == '\r') {
-			stats->cr++;
-			if (i+1 < size && buf[i+1] == '\n')
+			if (i+1 < size && buf[i+1] == '\n') {
 				stats->crlf++;
+				i++;
+			} else
+				stats->lonecr++;
 			continue;
 		}
 		if (c == '\n') {
-			stats->lf++;
+			stats->lonelf++;
 			continue;
 		}
 		if (c == 127)
@@ -86,7 +88,7 @@ static void gather_stats(const char *buf, unsigned long size, struct text_stat *
  */
 static int convert_is_binary(unsigned long size, const struct text_stat *stats)
 {
-	if (stats->cr != stats->crlf)
+	if (stats->lonecr)
 		return 1;
 	if (stats->nul)
 		return 1;
@@ -98,19 +100,18 @@ static int convert_is_binary(unsigned long size, const struct text_stat *stats)
 static unsigned int gather_convert_stats(const char *data, unsigned long size)
 {
 	struct text_stat stats;
+	int ret = 0;
 	if (!data || !size)
-		return 0;
+		return ret;
 	gather_stats(data, size, &stats);
 	if (convert_is_binary(size, &stats))
-		return CONVERT_STAT_BITS_BIN;
-	else if (stats.crlf && stats.crlf == stats.lf)
-		return CONVERT_STAT_BITS_TXT_CRLF;
-	else if (stats.crlf && stats.lf)
-		return CONVERT_STAT_BITS_TXT_CRLF | CONVERT_STAT_BITS_TXT_LF;
-	else if (stats.lf)
-		return CONVERT_STAT_BITS_TXT_LF;
-	else
-		return 0;
+		ret |= CONVERT_STAT_BITS_BIN;
+	if (stats.crlf)
+		ret |= CONVERT_STAT_BITS_TXT_CRLF;
+	if (stats.lonelf)
+		ret |=  CONVERT_STAT_BITS_TXT_LF;
+
+	return ret;
 }
 
 static const char *gather_convert_stats_ascii(const char *data, unsigned long size)
@@ -207,7 +208,7 @@ static void check_safe_crlf(const char *path, enum crlf_action crlf_action,
 		 * CRLFs would be added by checkout:
 		 * check if we have "naked" LFs
 		 */
-		if (stats->lf != stats->crlf) {
+		if (stats->lonelf) {
 			if (checksafe == SAFE_CRLF_WARN)
 				warning("LF will be replaced by CRLF in %s.\nThe file will have its original line endings in your working directory.", path);
 			else /* i.e. SAFE_CRLF_FAIL */
@@ -266,8 +267,8 @@ static int crlf_to_git(const char *path, const char *src, size_t len,
 
 	check_safe_crlf(path, crlf_action, &stats, checksafe);
 
-	/* Optimization: No CR? Nothing to convert, regardless. */
-	if (!stats.cr)
+	/* Optimization: No CRLF? Nothing to convert, regardless. */
+	if (!stats.crlf)
 		return 0;
 
 	/*
@@ -315,21 +316,16 @@ static int crlf_to_worktree(const char *path, const char *src, size_t len,
 	gather_stats(src, len, &stats);
 
 	/* No LF? Nothing to convert, regardless. */
-	if (!stats.lf)
-		return 0;
-
-	/* Was it already in CRLF format? */
-	if (stats.lf == stats.crlf)
+	if (!stats.lonelf)
 		return 0;
 
+	if (crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
+		/* If we have any CRLF line endings, we do not touch it */
+		/* This is the new safer autocrlf-handling */
+		if (stats.crlf)
+			return 0;
+	}
 	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
-		if (crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
-			/* If we have any CR or CRLF line endings, we do not touch it */
-			/* This is the new safer autocrlf-handling */
-			if (stats.cr > 0 || stats.crlf > 0)
-				return 0;
-		}
-
 		if (convert_is_binary(len, &stats))
 			return 0;
 	}
@@ -338,7 +334,7 @@ static int crlf_to_worktree(const char *path, const char *src, size_t len,
 	if (src == buf->buf)
 		to_free = strbuf_detach(buf, NULL);
 
-	strbuf_grow(buf, len + stats.lf - stats.crlf);
+	strbuf_grow(buf, len + stats.crlf);
 	for (;;) {
 		const char *nl = memchr(src, '\n', len);
 		if (!nl)
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* Re: [PATCH v2 1/7] t0027: Add tests for get_stream_filter()
  2016-02-04 17:49 ` [PATCH v2 1/7] t0027: Add tests for get_stream_filter() tboegi
@ 2016-02-04 19:52   ` Junio C Hamano
  0 siblings, 0 replies; 47+ messages in thread
From: Junio C Hamano @ 2016-02-04 19:52 UTC (permalink / raw)
  To: tboegi; +Cc: git

tboegi@web.de writes:

> +		while test "$#" != 0
> +		do
> +			case "$1" in
> +				auto)	 echo '*.txt text=auto' ;;
> +				i)     echo '* ident' ;;
> +				text)	 echo '*.txt text' ;;
> +				-text) echo '*.txt -text' ;;
> +				crlf)  echo '*.txt eol=crlf' ;;
> +				lf)    echo '*.txt eol=lf' ;;
> +				"") echo '' ;;
> +				*)
> +				echo >&2 invalid attribute: $attr
> +				exit 1
> +				;;

Perhaps use the right style as you are rewriting pretty much
everything in this helper function?  case/esac aligns with the
labels of case arms, and commands under each arm are indented one
level down, i.e.

	case "$var" in
        $arm1)	... do short thing ...;;
        $arm2)
        	... do a lot of
                ... things
                ;;
	esac


I still do not see the value of accepting a cryptic 'i' (or an empty
string) to this thing, though.  Also what $attr does the error
message refer to now?  Perhaps it wants to refer to "$1" (quoted)
instead?

^ permalink raw reply	[flat|nested] 47+ messages in thread

* Re: [PATCH v2 4/7] convert.c: Use text_eol_is_crlf()
  2016-02-04 17:49 ` [PATCH v2 4/7] convert.c: Use text_eol_is_crlf() tboegi
@ 2016-02-04 20:13   ` Junio C Hamano
  0 siblings, 0 replies; 47+ messages in thread
From: Junio C Hamano @ 2016-02-04 20:13 UTC (permalink / raw)
  To: tboegi; +Cc: git

tboegi@web.de writes:

> From: Torsten Bögershausen <tboegi@web.de>
>
> Add a helper function to find out, which line endings
> text files should get at checkout, depending on
> core.autocrlf and core.eol
>
> Signed-off-by: Torsten Bögershausen <tboegi@web.de>
> ---
>  convert.c | 25 +++++++++++++++++--------
>  1 file changed, 17 insertions(+), 8 deletions(-)
>
> diff --git a/convert.c b/convert.c
> index d0c8c66..9ffd043 100644
> --- a/convert.c
> +++ b/convert.c
> @@ -149,6 +149,19 @@ const char *get_wt_convert_stats_ascii(const char *path)
>  	return ret;
>  }
>  
> +static int text_eol_is_crlf(void)
> +{
> +	if (auto_crlf == AUTO_CRLF_TRUE)
> +		return 1;
> +	else if (auto_crlf == AUTO_CRLF_INPUT)
> +		return 0;
> +	if (core_eol == EOL_CRLF)
> +		return 1;
> +	if (core_eol == EOL_UNSET && EOL_NATIVE == EOL_CRLF)
> +		return 1;
> +	return 0;
> +}
> +
>  static enum eol output_eol(enum crlf_action crlf_action)
>  {
>  	switch (crlf_action) {
> @@ -164,12 +177,7 @@ static enum eol output_eol(enum crlf_action crlf_action)
>  		/* fall through */
>  	case CRLF_TEXT:
>  	case CRLF_AUTO:
> -		if (auto_crlf == AUTO_CRLF_TRUE)
> -			return EOL_CRLF;
> -		else if (auto_crlf == AUTO_CRLF_INPUT)
> -			return EOL_LF;
> -		else if (core_eol == EOL_UNSET)
> -			return EOL_NATIVE;
> +		return text_eol_is_crlf() ? EOL_CRLF : EOL_LF;
>  	}
>  	return core_eol;
>  }
> @@ -1378,8 +1386,9 @@ struct stream_filter *get_stream_filter(const char *path, const unsigned char *s
>  	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE))
>  		filter = cascade_filter(filter, &null_filter_singleton);
>  
> -	else if (output_eol(crlf_action) == EOL_CRLF &&
> -		 !(crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS))
> +	else if ((crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS))
> +		;
> +	else if (output_eol(crlf_action) == EOL_CRLF)
>  		filter = cascade_filter(filter, lf_to_crlf_filter());
>  
>  	return filter;

I am a bit slow today so let me talk this change through aloud.

The condition under which we called cascade_filter() used to be that
output_eol(crlf_action) yields EOL_CRLF and crlf_action is not set
to one of these two values.  Now, we say if crlf_action is one of
these two values, we wouldn't call it, and then we check
output_eol().

So they do the same thing, even though it smells that this change is
outside the scope of "Add a helper and use it" theme of the patch.

While I do not think this new "split" conditions particularly easier
to read compared to the previous one, if you plan to do something
different in later patches when crlf_action is set to specific
values, ignoring what output_eol() says, a patch to implement such a
change would become easier to understand what is going on with this
preparatory rewrite.  So if such a preparatory rewrite is coming (I
haven't checked 5-7/7 yet), perhaps have this hunk as a single patch
that is separate from "add a helper text_eol_is_crlf()" patch.

By the way, your new 1/7 has s/: Remove/: remove/ applied to the
subject, but not other ones like this one.  Intended, or you forgot
to do s/: Use/: use/ here?

^ permalink raw reply	[flat|nested] 47+ messages in thread

* Re: [PATCH v2 7/7] convert.c: simplify text_stat
  2016-02-04 17:50 ` [PATCH v2 7/7] convert.c: simplify text_stat tboegi
@ 2016-02-04 20:37   ` Junio C Hamano
  0 siblings, 0 replies; 47+ messages in thread
From: Junio C Hamano @ 2016-02-04 20:37 UTC (permalink / raw)
  To: tboegi; +Cc: git

tboegi@web.de writes:

>  static int convert_is_binary(unsigned long size, const struct text_stat *stats)
>  {
> -	if (stats->cr != stats->crlf)
> +	if (stats->lonecr)
>  		return 1;

This is an equivalent conversion, but...

> @@ -266,8 +267,8 @@ static int crlf_to_git(const char *path, const char *src, size_t len,
>  
>  	check_safe_crlf(path, crlf_action, &stats, checksafe);
>  
> -	/* Optimization: No CR? Nothing to convert, regardless. */
> -	if (!stats.cr)
> +	/* Optimization: No CRLF? Nothing to convert, regardless. */
> +	if (!stats.crlf)
>  		return 0;

... this is not.  In fact this is even better, as we used to try the
remainder of the function when we saw a lone CR, but we no longer
do.  I am of course assuming that the original turned into a no-op
if we had a lone CR in the input--otherwise this patch changes the
behaviour.

However, I see this comment after the function returns with the
above optimization:

       /*
        * If we guessed, we already know we rejected a file with
        * lone CR, and we can strip a CR without looking at what
        * follow it.
        */

So the code around there used to have a reason to worry about a lone
CR (i.e. it didn't want to lose them).  With the change in this hunk
for the "optimization", it no longer is necessary to do so, i.e. we
know we do not have a lone CR so every CR can be stripped because it
must be followed by LF, isn't it?

But I do not see a matching change to simplify that here.  Am I
following the current code incorrectly or something?

Puzzled...

>  	/*
> @@ -315,21 +316,16 @@ static int crlf_to_worktree(const char *path, const char *src, size_t len,
>  	gather_stats(src, len, &stats);
>  
>  	/* No LF? Nothing to convert, regardless. */
> -	if (!stats.lf)
> -		return 0;
> -
> -	/* Was it already in CRLF format? */
> -	if (stats.lf == stats.crlf)
> +	if (!stats.lonelf)

Doesn't the comment above need adjustment?

>  		return 0;

Otherwise, the output side looks correct to me.

^ permalink raw reply	[flat|nested] 47+ messages in thread

* [PATCH v3 1/7] t0027: Add tests for get_stream_filter()
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (14 preceding siblings ...)
  2016-02-04 17:50 ` [PATCH v2 7/7] convert.c: simplify text_stat tboegi
@ 2016-02-05 16:13 ` tboegi
  2016-02-08 17:59   ` Junio C Hamano
  2016-02-05 16:13 ` [PATCH v3 2/7] convert.c: remove unused parameter 'path' tboegi
                   ` (12 subsequent siblings)
  28 siblings, 1 reply; 47+ messages in thread
From: tboegi @ 2016-02-05 16:13 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

When a filter is configured, a different code-path is used in convert.c
and entry.c via get_stream_filter(), but there are no test cases yet.

Add tests for the filter API by configuring the ident filter.
The result of the SHA1 conversion is not checked, this is already
done in other TC.

Add a parameter to checkout_files() in t0027.
While changing the signature, add another parameter for the eol= attribute.
This is currently unused, tests for e.g.
"* text=auto eol=lf" will be added in a separate commit.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
Changes since v2:
1/7 t0027 uses ident instead of i (the empty "" is still there)
    better ident of case..esac (thanks for the patience)
    (And again the question, if there is an official init.el, please)
4/7 don't change the logic which stream filter to use    
7/7 had been broken (wrong bufferlen) , should be OK now


t/t0027-auto-crlf.sh | 281 ++++++++++++++++++++++++++-------------------------
 1 file changed, 146 insertions(+), 135 deletions(-)

diff --git a/t/t0027-auto-crlf.sh b/t/t0027-auto-crlf.sh
index 504e5a0..fc4c628 100755
--- a/t/t0027-auto-crlf.sh
+++ b/t/t0027-auto-crlf.sh
@@ -21,38 +21,32 @@ compare_ws_file () {
 	pfx=$1
 	exp=$2.expect
 	act=$pfx.actual.$3
-	tr '\015\000' QN <"$2" >"$exp" &&
-	tr '\015\000' QN <"$3" >"$act" &&
-	test_cmp $exp $act &&
-	rm $exp $act
+	tr '\015\000abcdef0123456789' QN00000000000000000 <"$2" >"$exp" &&
+	tr '\015\000abcdef0123456789' QN00000000000000000 <"$3" >"$act" &&
+	test_cmp "$exp" "$act" &&
+	rm "$exp" "$act"
 }
 
 create_gitattributes () {
-	attr=$1
-	case "$attr" in
-		auto)
-		echo "*.txt text=auto" >.gitattributes
-		;;
-		text)
-		echo "*.txt text" >.gitattributes
-		;;
-		-text)
-		echo "*.txt -text" >.gitattributes
-		;;
-		crlf)
-		echo "*.txt eol=crlf" >.gitattributes
-		;;
-		lf)
-		echo "*.txt eol=lf" >.gitattributes
-		;;
-		"")
-		echo >.gitattributes
-		;;
-		*)
-		echo >&2 invalid attribute: $attr
-		exit 1
-		;;
-	esac
+	{
+		while test "$#" != 0
+		do
+			case "$1" in
+			auto)	 echo '*.txt text=auto' ;;
+			ident) echo '*.txt ident' ;;
+			text)	 echo '*.txt text' ;;
+			-text) echo '*.txt -text' ;;
+			crlf)  echo '*.txt eol=crlf' ;;
+			lf)    echo '*.txt eol=lf' ;;
+			"") ;;
+			*)
+				echo >&2 invalid attribute: "$1"
+				exit 1
+				;;
+			esac &&
+			shift
+		done
+	} >.gitattributes
 }
 
 create_NNO_files () {
@@ -208,28 +202,30 @@ check_in_repo_NNO () {
 }
 
 checkout_files () {
-	eol=$1
-	crlf=$2
-	attr=$3
-	lfname=$4
-	crlfname=$5
-	lfmixcrlf=$6
-	lfmixcr=$7
-	crlfnul=$8
-	create_gitattributes $attr &&
+	attr=$1 ; shift
+	ident=$1; shift
+	aeol=$1 ; shift
+	crlf=$1 ; shift
+	ceol=$1 ; shift
+	lfname=$1 ; shift
+	crlfname=$1 ; shift
+	lfmixcrlf=$1 ; shift
+	lfmixcr=$1 ; shift
+	crlfnul=$1 ; shift
+	create_gitattributes "$attr" "$ident" &&
 	git config core.autocrlf $crlf &&
-	pfx=eol_${eol}_crlf_${crlf}_attr_${attr}_ &&
+	pfx=eol_${ceol}_crlf_${crlf}_attr_${attr}_ &&
 	for f in LF CRLF LF_mix_CR CRLF_mix_LF LF_nul
 	do
 		rm crlf_false_attr__$f.txt &&
-		if test -z "$eol"; then
+		if test -z "$ceol"; then
 			git checkout crlf_false_attr__$f.txt
 		else
-			git -c core.eol=$eol checkout crlf_false_attr__$f.txt
+			git -c core.eol=$ceol checkout crlf_false_attr__$f.txt
 		fi
 	done
 
-	test_expect_success "ls-files --eol $lfname ${pfx}LF.txt" '
+	test_expect_success "ls-files --eol attr=$attr $ident $aeol core.autocrlf=$crlf core.eol=$ceol" '
 		test_when_finished "rm expect actual" &&
 		sort <<-EOF >expect &&
 		i/crlf w/$(stats_ascii $crlfname) crlf_false_attr__CRLF.txt
@@ -244,19 +240,19 @@ checkout_files () {
 		sort >actual &&
 		test_cmp expect actual
 	'
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=LF" "
+	test_expect_success "checkout $ident $attr $aeol core.autocrlf=$crlf core.eol=$ceol file=LF" "
 		compare_ws_file $pfx $lfname    crlf_false_attr__LF.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=CRLF" "
+	test_expect_success "checkout $ident $attr $aeol core.autocrlf=$crlf core.eol=$ceol file=CRLF" "
 		compare_ws_file $pfx $crlfname  crlf_false_attr__CRLF.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=CRLF_mix_LF" "
+	test_expect_success "checkout $ident $attr $aeol core.autocrlf=$crlf core.eol=$ceol file=CRLF_mix_LF" "
 		compare_ws_file $pfx $lfmixcrlf crlf_false_attr__CRLF_mix_LF.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=LF_mix_CR" "
+	test_expect_success "checkout $ident $attr $aeol core.autocrlf=$crlf core.eol=$ceol file=LF_mix_CR" "
 		compare_ws_file $pfx $lfmixcr   crlf_false_attr__LF_mix_CR.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=LF_nul" "
+	test_expect_success "checkout $ident $attr $aeol core.autocrlf=$crlf core.eol=$ceol file=LF_nul" "
 		compare_ws_file $pfx $crlfnul   crlf_false_attr__LF_nul.txt
 	"
 }
@@ -301,14 +297,13 @@ test_expect_success 'setup master' '
 	git checkout -b master &&
 	git add .gitattributes &&
 	git commit -m "add .gitattributes" "" &&
-	printf "line1\nline2\nline3"     >LF &&
-	printf "line1\r\nline2\r\nline3" >CRLF &&
-	printf "line1\r\nline2\nline3"   >repoMIX &&
-	printf "line1\r\nline2\nline3"   >CRLF_mix_LF &&
-	printf "line1\nline2\rline3"     >LF_mix_CR &&
-	printf "line1\r\nline2\rline3"   >CRLF_mix_CR &&
-	printf "line1Q\r\nline2\r\nline3" | q_to_nul >CRLF_nul &&
-	printf "line1Q\nline2\nline3" | q_to_nul >LF_nul &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONE\nLINETWO\nLINETHREE"     >LF &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\r\nLINEONE\r\nLINETWO\r\nLINETHREE" >CRLF &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONE\r\nLINETWO\nLINETHREE"   >CRLF_mix_LF &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONE\nLINETWO\rLINETHREE"     >LF_mix_CR &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\r\nLINEONE\r\nLINETWO\rLINETHREE"   >CRLF_mix_CR &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\r\nLINEONEQ\r\nLINETWO\r\nLINETHREE" | q_to_nul >CRLF_nul &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONEQ\nLINETWO\nLINETHREE" | q_to_nul >LF_nul &&
 	create_NNO_files CRLF_mix_LF CRLF_mix_LF CRLF_mix_LF CRLF_mix_LF CRLF_mix_LF &&
 	git -c core.autocrlf=false add NNO_*.txt &&
 	git commit -m "mixed line endings" &&
@@ -449,23 +444,18 @@ check_in_repo_NNO input "-text" LF        CRLF      CRLF_mix_LF  LF_mix_CR 	CRLF
 # How to read the table below:
 # - checkout_files will check multiple files with a combination of settings
 #   and attributes (core.autocrlf=input is forbidden with core.eol=crlf)
-# - parameter $1 : core.eol               lf | crlf
-# - parameter $2 : core.autocrlf          false | true | input
-# - parameter $3 : text in .gitattributs  "" (empty) | auto | text | -text
-# - parameter $4 : reference for a file with only LF in the repo
-# - parameter $5 : reference for a file with only CRLF in the repo
-# - parameter $6 : reference for a file with mixed LF and CRLF in the repo
-# - parameter $7 : reference for a file with LF and CR in the repo (does somebody uses this ?)
-# - parameter $8 : reference for a file with CRLF and a NUL (should be handled as binary when auto)
-
-#                                            What we have in the repo:
-#                                            ----------------- EOL in repo ----------------
-#                                            LF    CRLF  CRLF_mix_LF  LF_mix_CR    CRLF_nul
-#                   settings with checkout:
-#                   core.   core.   .gitattr
-#                    eol     acrlf
-#                                            ----------------------------------------------
-#                                            What we want to have in the working tree:
+#
+# - parameter $1 	: text in .gitattributs  "" (empty) | auto | text | -text
+# - parameter $2 	: ident                  "" | i (i == ident)
+# - parameter $3 	: eol in .gitattributs   "" (empty) | lf | crlf
+# - parameter $4 	: core.autocrlf          false | true | input
+# - parameter $5 	: core.eol               "" | lf | crlf | "native"
+# - parameter $6 	: reference for a file with only LF in the repo
+# - parameter $7 	: reference for a file with only CRLF in the repo
+# - parameter $8 	: reference for a file with mixed LF and CRLF in the repo
+# - parameter $9 	: reference for a file with LF and CR in the repo
+# - parameter $10 : reference for a file with CRLF and a NUL (should be handled as binary when auto)
+
 if test_have_prereq NATIVE_CRLF
 then
 MIX_CRLF_LF=CRLF
@@ -480,69 +470,90 @@ LFNUL=LF_nul
 fi
 export CRLF_MIX_LF_CR MIX NL
 
-checkout_files    lf      false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "auto"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    lf      input "auto"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "text"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    lf      input "text"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      input "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      input "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    lf      true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    lf      input "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-
-checkout_files    crlf    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    false "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    crlf    true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    crlf    false "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    crlf    true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    crlf    false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    crlf    true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-
-checkout_files    ""      false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "auto"    $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
-checkout_files    ""      true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    ""      input "auto"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "text"    $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
-checkout_files    ""      true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    ""      input "text"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      input "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      input "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    ""      true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    ""      input "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-
-checkout_files    native  false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  false "auto"    $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
-checkout_files    native  true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    native  false "text"    $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
-checkout_files    native  true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    native  false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    native  true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+checkout_files ""      "" 	 ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" 	 ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" 	 ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" 	 ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" 	 ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" 	 ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" 	 ""    true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" 	 ""    true   crlf     CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" 	 ""    true   lf       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" 	 ""    true   native   CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    false  ""       $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    false  crlf     CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    false  native   $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    true   ""       CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    true   crlf     CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    true   lf       CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    true   native   CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+
+for id in "" ident;
+do
+	checkout_files "crlf"  "$id" ""    false  ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    false  crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    false  lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    false  native   CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    input  ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    input  lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   native   CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "lf"    "$id" ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    false  ""       $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
+	checkout_files "text"  "$id" ""    false  crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    false  native   $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
+	checkout_files "text"  "$id" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    true   ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    true   crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    true   lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    true   native   CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "-text" "$id" ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+done
 
 # Should be the last test case: remove some files from the worktree
 test_expect_success 'ls-files --eol -d -z' '
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v3 2/7] convert.c: remove unused parameter 'path'
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (15 preceding siblings ...)
  2016-02-05 16:13 ` [PATCH v3 1/7] t0027: Add tests for get_stream_filter() tboegi
@ 2016-02-05 16:13 ` tboegi
  2016-02-05 16:13 ` [PATCH v3 3/7] convert.c: Remove input_crlf_action() tboegi
                   ` (11 subsequent siblings)
  28 siblings, 0 replies; 47+ messages in thread
From: tboegi @ 2016-02-05 16:13 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Some functions get a parameter path, but don't use it.
Remove the unused parameter.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 19 +++++++++----------
 1 file changed, 9 insertions(+), 10 deletions(-)

diff --git a/convert.c b/convert.c
index 4bb4ec1..a24c2a2 100644
--- a/convert.c
+++ b/convert.c
@@ -696,7 +696,7 @@ static int ident_to_worktree(const char *path, const char *src, size_t len,
 	return 1;
 }
 
-static enum crlf_action git_path_check_crlf(const char *path, struct git_attr_check *check)
+static enum crlf_action git_path_check_crlf(struct git_attr_check *check)
 {
 	const char *value = check->value;
 
@@ -713,7 +713,7 @@ static enum crlf_action git_path_check_crlf(const char *path, struct git_attr_ch
 	return CRLF_GUESS;
 }
 
-static enum eol git_path_check_eol(const char *path, struct git_attr_check *check)
+static enum eol git_path_check_eol(struct git_attr_check *check)
 {
 	const char *value = check->value;
 
@@ -726,8 +726,7 @@ static enum eol git_path_check_eol(const char *path, struct git_attr_check *chec
 	return EOL_UNSET;
 }
 
-static struct convert_driver *git_path_check_convert(const char *path,
-					     struct git_attr_check *check)
+static struct convert_driver *git_path_check_convert(struct git_attr_check *check)
 {
 	const char *value = check->value;
 	struct convert_driver *drv;
@@ -740,7 +739,7 @@ static struct convert_driver *git_path_check_convert(const char *path,
 	return NULL;
 }
 
-static int git_path_check_ident(const char *path, struct git_attr_check *check)
+static int git_path_check_ident(struct git_attr_check *check)
 {
 	const char *value = check->value;
 
@@ -783,12 +782,12 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 	}
 
 	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
-		ca->crlf_action = git_path_check_crlf(path, ccheck + 4);
+		ca->crlf_action = git_path_check_crlf( ccheck + 4);
 		if (ca->crlf_action == CRLF_GUESS)
-			ca->crlf_action = git_path_check_crlf(path, ccheck + 0);
-		ca->ident = git_path_check_ident(path, ccheck + 1);
-		ca->drv = git_path_check_convert(path, ccheck + 2);
-		ca->eol_attr = git_path_check_eol(path, ccheck + 3);
+			ca->crlf_action = git_path_check_crlf(ccheck + 0);
+		ca->ident = git_path_check_ident(ccheck + 1);
+		ca->drv = git_path_check_convert(ccheck + 2);
+		ca->eol_attr = git_path_check_eol(ccheck + 3);
 	} else {
 		ca->drv = NULL;
 		ca->crlf_action = CRLF_GUESS;
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v3 3/7] convert.c: Remove input_crlf_action()
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (16 preceding siblings ...)
  2016-02-05 16:13 ` [PATCH v3 2/7] convert.c: remove unused parameter 'path' tboegi
@ 2016-02-05 16:13 ` tboegi
  2016-02-05 16:13 ` [PATCH v3 4/7] convert.c: use text_eol_is_crlf() tboegi
                   ` (10 subsequent siblings)
  28 siblings, 0 replies; 47+ messages in thread
From: tboegi @ 2016-02-05 16:13 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Integrate the code of input_crlf_action() into convert_attrs(),
so that ca.crlf_action is always valid after calling convert_attrs().
Keep a copy of crlf_action in attr_action, this is needed for
get_convert_attr_ascii().

Remove eol_attr from struct conv_attrs, as it is now used temporally.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 37 ++++++++++++++-----------------------
 1 file changed, 14 insertions(+), 23 deletions(-)

diff --git a/convert.c b/convert.c
index a24c2a2..d0c8c66 100644
--- a/convert.c
+++ b/convert.c
@@ -746,21 +746,10 @@ static int git_path_check_ident(struct git_attr_check *check)
 	return !!ATTR_TRUE(value);
 }
 
-static enum crlf_action input_crlf_action(enum crlf_action text_attr, enum eol eol_attr)
-{
-	if (text_attr == CRLF_BINARY)
-		return CRLF_BINARY;
-	if (eol_attr == EOL_LF)
-		return CRLF_INPUT;
-	if (eol_attr == EOL_CRLF)
-		return CRLF_CRLF;
-	return text_attr;
-}
-
 struct conv_attrs {
 	struct convert_driver *drv;
-	enum crlf_action crlf_action;
-	enum eol eol_attr;
+	enum crlf_action attr_action; /* What attr says */
+	enum crlf_action crlf_action; /* When no attr is set, use core.autocrlf */
 	int ident;
 };
 
@@ -782,16 +771,23 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 	}
 
 	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
-		ca->crlf_action = git_path_check_crlf( ccheck + 4);
+		enum eol eol_attr;
+		ca->crlf_action = git_path_check_crlf(ccheck + 4);
 		if (ca->crlf_action == CRLF_GUESS)
 			ca->crlf_action = git_path_check_crlf(ccheck + 0);
+		ca->attr_action = ca->crlf_action;
 		ca->ident = git_path_check_ident(ccheck + 1);
 		ca->drv = git_path_check_convert(ccheck + 2);
-		ca->eol_attr = git_path_check_eol(ccheck + 3);
+		if (ca->crlf_action == CRLF_BINARY)
+			return;
+		eol_attr = git_path_check_eol(ccheck + 3);
+		if (eol_attr == EOL_LF)
+			ca->crlf_action = CRLF_INPUT;
+		else if (eol_attr == EOL_CRLF)
+			ca->crlf_action = CRLF_CRLF;
 	} else {
 		ca->drv = NULL;
 		ca->crlf_action = CRLF_GUESS;
-		ca->eol_attr = EOL_UNSET;
 		ca->ident = 0;
 	}
 }
@@ -818,11 +814,9 @@ int would_convert_to_git_filter_fd(const char *path)
 const char *get_convert_attr_ascii(const char *path)
 {
 	struct conv_attrs ca;
-	enum crlf_action crlf_action;
 
 	convert_attrs(&ca, path);
-	crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
-	switch (crlf_action) {
+	switch (ca.attr_action) {
 	case CRLF_GUESS:
 		return "";
 	case CRLF_BINARY:
@@ -861,7 +855,6 @@ int convert_to_git(const char *path, const char *src, size_t len,
 		src = dst->buf;
 		len = dst->len;
 	}
-	ca.crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
 	ret |= crlf_to_git(path, src, len, dst, ca.crlf_action, checksafe);
 	if (ret && dst) {
 		src = dst->buf;
@@ -882,7 +875,6 @@ void convert_to_git_filter_fd(const char *path, int fd, struct strbuf *dst,
 	if (!apply_filter(path, NULL, 0, fd, dst, ca.drv->clean))
 		die("%s: clean filter '%s' failed", path, ca.drv->name);
 
-	ca.crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
 	crlf_to_git(path, dst->buf, dst->len, dst, ca.crlf_action, checksafe);
 	ident_to_git(path, dst->buf, dst->len, dst, ca.ident);
 }
@@ -912,7 +904,6 @@ static int convert_to_working_tree_internal(const char *path, const char *src,
 	 * is a smudge filter.  The filter might expect CRLFs.
 	 */
 	if (filter || !normalizing) {
-		ca.crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
 		ret |= crlf_to_worktree(path, src, len, dst, ca.crlf_action);
 		if (ret) {
 			src = dst->buf;
@@ -1381,7 +1372,7 @@ struct stream_filter *get_stream_filter(const char *path, const unsigned char *s
 	if (ca.ident)
 		filter = ident_filter(sha1);
 
-	crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
+	crlf_action = ca.crlf_action;
 
 	if ((crlf_action == CRLF_BINARY) || (crlf_action == CRLF_INPUT) ||
 	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE))
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v3 4/7] convert.c: use text_eol_is_crlf()
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (17 preceding siblings ...)
  2016-02-05 16:13 ` [PATCH v3 3/7] convert.c: Remove input_crlf_action() tboegi
@ 2016-02-05 16:13 ` tboegi
  2016-02-05 16:13 ` [PATCH v3 5/7] convert: auto_crlf=false and no attributes set: same as binary tboegi
                   ` (9 subsequent siblings)
  28 siblings, 0 replies; 47+ messages in thread
From: tboegi @ 2016-02-05 16:13 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Add a helper function to find out, which line endings
text files should get at checkout, depending on
core.autocrlf and core.eol

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 20 ++++++++++++++------
 1 file changed, 14 insertions(+), 6 deletions(-)

diff --git a/convert.c b/convert.c
index d0c8c66..557e574 100644
--- a/convert.c
+++ b/convert.c
@@ -149,6 +149,19 @@ const char *get_wt_convert_stats_ascii(const char *path)
 	return ret;
 }
 
+static int text_eol_is_crlf(void)
+{
+	if (auto_crlf == AUTO_CRLF_TRUE)
+		return 1;
+	else if (auto_crlf == AUTO_CRLF_INPUT)
+		return 0;
+	if (core_eol == EOL_CRLF)
+		return 1;
+	if (core_eol == EOL_UNSET && EOL_NATIVE == EOL_CRLF)
+		return 1;
+	return 0;
+}
+
 static enum eol output_eol(enum crlf_action crlf_action)
 {
 	switch (crlf_action) {
@@ -164,12 +177,7 @@ static enum eol output_eol(enum crlf_action crlf_action)
 		/* fall through */
 	case CRLF_TEXT:
 	case CRLF_AUTO:
-		if (auto_crlf == AUTO_CRLF_TRUE)
-			return EOL_CRLF;
-		else if (auto_crlf == AUTO_CRLF_INPUT)
-			return EOL_LF;
-		else if (core_eol == EOL_UNSET)
-			return EOL_NATIVE;
+		return text_eol_is_crlf() ? EOL_CRLF : EOL_LF;
 	}
 	return core_eol;
 }
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v3 5/7] convert: auto_crlf=false and no attributes set: same as binary
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (18 preceding siblings ...)
  2016-02-05 16:13 ` [PATCH v3 4/7] convert.c: use text_eol_is_crlf() tboegi
@ 2016-02-05 16:13 ` tboegi
  2016-02-08 18:27   ` Junio C Hamano
  2016-02-05 16:13 ` [PATCH v3 6/7] convert.c: refactor crlf_action tboegi
                   ` (8 subsequent siblings)
  28 siblings, 1 reply; 47+ messages in thread
From: tboegi @ 2016-02-05 16:13 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

When core.autocrlf is set to false, and no attributes are set, the file
is treated as binary.
Simplify the logic and remove duplicated code when dealing with
(crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE) by setting
crlf_action=CRLF_BINARY already in convert_attrs().

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/convert.c b/convert.c
index 557e574..e9c9448 100644
--- a/convert.c
+++ b/convert.c
@@ -235,7 +235,6 @@ static int crlf_to_git(const char *path, const char *src, size_t len,
 	char *dst;
 
 	if (crlf_action == CRLF_BINARY ||
-	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE) ||
 	    (src && !len))
 		return 0;
 
@@ -798,6 +797,8 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 		ca->crlf_action = CRLF_GUESS;
 		ca->ident = 0;
 	}
+	if (ca->crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE)
+		ca->crlf_action = CRLF_BINARY;
 }
 
 int would_convert_to_git_filter_fd(const char *path)
@@ -1382,8 +1383,7 @@ struct stream_filter *get_stream_filter(const char *path, const unsigned char *s
 
 	crlf_action = ca.crlf_action;
 
-	if ((crlf_action == CRLF_BINARY) || (crlf_action == CRLF_INPUT) ||
-	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE))
+	if ((crlf_action == CRLF_BINARY) || (crlf_action == CRLF_INPUT))
 		filter = cascade_filter(filter, &null_filter_singleton);
 
 	else if (output_eol(crlf_action) == EOL_CRLF &&
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v3 6/7] convert.c: refactor crlf_action
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (19 preceding siblings ...)
  2016-02-05 16:13 ` [PATCH v3 5/7] convert: auto_crlf=false and no attributes set: same as binary tboegi
@ 2016-02-05 16:13 ` tboegi
  2016-02-05 16:13 ` [PATCH v3 7/7] convert.c: simplify text_stat tboegi
                   ` (7 subsequent siblings)
  28 siblings, 0 replies; 47+ messages in thread
From: tboegi @ 2016-02-05 16:13 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Refactor the determination and usage of crlf_action.
Today, when no attributes are set on a file,
crlf_action is set to CRLF_GUESS, and later, CRLF_GUESS is used as an
indication that core.autocrlf is not false and that some automatic eol
conversion is needed.
Make more clear, what is what, by defining:

- CRLF_UNDEFINED : No attributes set. Temparally used, until core.autocrlf
                   and core.eol is evaluated and one of CRLF_BINARY,
                   CRLF_AUTO_INPUT or CRLF_AUTO_CRLF is selected
- CRLF_BINARY    : No processing of line endings.
- CRLF_TEXT      : attribute "text" is set, line endings are processed.
- CRLF_TEXT_INPUT: attribute "input" or "eol=lf" is set. This implies text.
- CRLF_TEXT_CRLF : attribute "eol=crlf" is set. This implies text.
- CRLF_AUTO      : attribute "auto" is set.
- CRLF_AUTO_INPUT: No attributes, core.autocrlf=input
- CRLF_AUTO_CRLF : No attributes, core.autocrlf=true

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 75 ++++++++++++++++++++++++++++++++++++++-------------------------
 1 file changed, 45 insertions(+), 30 deletions(-)

diff --git a/convert.c b/convert.c
index e9c9448..e4e2877 100644
--- a/convert.c
+++ b/convert.c
@@ -19,12 +19,14 @@
 #define CONVERT_STAT_BITS_BIN       0x4
 
 enum crlf_action {
-	CRLF_GUESS = -1,
-	CRLF_BINARY = 0,
+	CRLF_UNDEFINED,
+	CRLF_BINARY,
 	CRLF_TEXT,
-	CRLF_INPUT,
-	CRLF_CRLF,
-	CRLF_AUTO
+	CRLF_TEXT_INPUT,
+	CRLF_TEXT_CRLF,
+	CRLF_AUTO,
+	CRLF_AUTO_INPUT,
+	CRLF_AUTO_CRLF
 };
 
 struct text_stat {
@@ -167,18 +169,19 @@ static enum eol output_eol(enum crlf_action crlf_action)
 	switch (crlf_action) {
 	case CRLF_BINARY:
 		return EOL_UNSET;
-	case CRLF_CRLF:
+	case CRLF_TEXT_CRLF:
 		return EOL_CRLF;
-	case CRLF_INPUT:
+	case CRLF_TEXT_INPUT:
 		return EOL_LF;
-	case CRLF_GUESS:
-		if (!auto_crlf)
-			return EOL_UNSET;
-		/* fall through */
+	case CRLF_UNDEFINED:
+	case CRLF_AUTO_CRLF:
+	case CRLF_AUTO_INPUT:
 	case CRLF_TEXT:
 	case CRLF_AUTO:
+		/* fall through */
 		return text_eol_is_crlf() ? EOL_CRLF : EOL_LF;
 	}
+	warning("Illegal crlf_action %d\n", (int)crlf_action);
 	return core_eol;
 }
 
@@ -247,11 +250,11 @@ static int crlf_to_git(const char *path, const char *src, size_t len,
 
 	gather_stats(src, len, &stats);
 
-	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS) {
+	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 		if (convert_is_binary(len, &stats))
 			return 0;
 
-		if (crlf_action == CRLF_GUESS) {
+		if (crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 			/*
 			 * If the file in the index has any CR in it, do not convert.
 			 * This is the new safer autocrlf handling.
@@ -278,7 +281,7 @@ static int crlf_to_git(const char *path, const char *src, size_t len,
 	if (strbuf_avail(buf) + buf->len < len)
 		strbuf_grow(buf, len - buf->len);
 	dst = buf->buf;
-	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS) {
+	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 		/*
 		 * If we guessed, we already know we rejected a file with
 		 * lone CR, and we can strip a CR without looking at what
@@ -319,8 +322,8 @@ static int crlf_to_worktree(const char *path, const char *src, size_t len,
 	if (stats.lf == stats.crlf)
 		return 0;
 
-	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS) {
-		if (crlf_action == CRLF_GUESS) {
+	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
+		if (crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 			/* If we have any CR or CRLF line endings, we do not touch it */
 			/* This is the new safer autocrlf-handling */
 			if (stats.cr > 0 || stats.crlf > 0)
@@ -708,16 +711,16 @@ static enum crlf_action git_path_check_crlf(struct git_attr_check *check)
 	const char *value = check->value;
 
 	if (ATTR_TRUE(value))
-		return CRLF_TEXT;
+		return text_eol_is_crlf() ? CRLF_TEXT_CRLF : CRLF_TEXT_INPUT;
 	else if (ATTR_FALSE(value))
 		return CRLF_BINARY;
 	else if (ATTR_UNSET(value))
 		;
 	else if (!strcmp(value, "input"))
-		return CRLF_INPUT;
+		return CRLF_TEXT_INPUT;
 	else if (!strcmp(value, "auto"))
 		return CRLF_AUTO;
-	return CRLF_GUESS;
+	return CRLF_UNDEFINED;
 }
 
 static enum eol git_path_check_eol(struct git_attr_check *check)
@@ -780,7 +783,7 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
 		enum eol eol_attr;
 		ca->crlf_action = git_path_check_crlf(ccheck + 4);
-		if (ca->crlf_action == CRLF_GUESS)
+		if (ca->crlf_action == CRLF_UNDEFINED)
 			ca->crlf_action = git_path_check_crlf(ccheck + 0);
 		ca->attr_action = ca->crlf_action;
 		ca->ident = git_path_check_ident(ccheck + 1);
@@ -789,16 +792,22 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 			return;
 		eol_attr = git_path_check_eol(ccheck + 3);
 		if (eol_attr == EOL_LF)
-			ca->crlf_action = CRLF_INPUT;
+			ca->crlf_action = CRLF_TEXT_INPUT;
 		else if (eol_attr == EOL_CRLF)
-			ca->crlf_action = CRLF_CRLF;
+			ca->crlf_action = CRLF_TEXT_CRLF;
 	} else {
 		ca->drv = NULL;
-		ca->crlf_action = CRLF_GUESS;
+		ca->crlf_action = CRLF_UNDEFINED;
 		ca->ident = 0;
 	}
-	if (ca->crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE)
+	if (ca->crlf_action == CRLF_TEXT)
+		ca->crlf_action = text_eol_is_crlf() ? CRLF_TEXT_CRLF : CRLF_TEXT_INPUT;
+	if (ca->crlf_action == CRLF_UNDEFINED && auto_crlf == AUTO_CRLF_FALSE)
 		ca->crlf_action = CRLF_BINARY;
+	if (ca->crlf_action == CRLF_UNDEFINED && auto_crlf == AUTO_CRLF_TRUE)
+		ca->crlf_action = CRLF_AUTO_CRLF;
+	if (ca->crlf_action == CRLF_UNDEFINED && auto_crlf == AUTO_CRLF_INPUT)
+		ca->crlf_action = CRLF_AUTO_INPUT;
 }
 
 int would_convert_to_git_filter_fd(const char *path)
@@ -826,18 +835,22 @@ const char *get_convert_attr_ascii(const char *path)
 
 	convert_attrs(&ca, path);
 	switch (ca.attr_action) {
-	case CRLF_GUESS:
+	case CRLF_UNDEFINED:
 		return "";
 	case CRLF_BINARY:
 		return "-text";
 	case CRLF_TEXT:
 		return "text";
-	case CRLF_INPUT:
+	case CRLF_TEXT_INPUT:
 		return "text eol=lf";
-	case CRLF_CRLF:
-		return "text=auto eol=crlf";
+	case CRLF_TEXT_CRLF:
+		return "text eol=crlf";
 	case CRLF_AUTO:
 		return "text=auto";
+	case CRLF_AUTO_CRLF:
+		return "text=auto eol=crlf"; /* This is not supported yet */
+	case CRLF_AUTO_INPUT:
+		return "text=auto eol=lf"; /* This is not supported yet */
 	}
 	return "";
 }
@@ -1383,11 +1396,13 @@ struct stream_filter *get_stream_filter(const char *path, const unsigned char *s
 
 	crlf_action = ca.crlf_action;
 
-	if ((crlf_action == CRLF_BINARY) || (crlf_action == CRLF_INPUT))
+	if ((crlf_action == CRLF_BINARY) ||
+			crlf_action == CRLF_AUTO_INPUT ||
+			(crlf_action == CRLF_TEXT_INPUT))
 		filter = cascade_filter(filter, &null_filter_singleton);
 
 	else if (output_eol(crlf_action) == EOL_CRLF &&
-		 !(crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS))
+		 !(crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_CRLF))
 		filter = cascade_filter(filter, lf_to_crlf_filter());
 
 	return filter;
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v3 7/7] convert.c: simplify text_stat
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (20 preceding siblings ...)
  2016-02-05 16:13 ` [PATCH v3 6/7] convert.c: refactor crlf_action tboegi
@ 2016-02-05 16:13 ` tboegi
  2016-02-10 16:24 ` [PATCH v4 1/6] t0027: add tests for get_stream_filter() tboegi
                   ` (6 subsequent siblings)
  28 siblings, 0 replies; 47+ messages in thread
From: tboegi @ 2016-02-05 16:13 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Simplify the statistics:
lonecr counts the CR which is not followed by a LF,
lonelf counts the LF which is not preceded by a CR,
crlf counts CRLF combinations.
This simplifies the evaluation of the statistics.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 47 ++++++++++++++++++++++-------------------------
 1 file changed, 22 insertions(+), 25 deletions(-)

diff --git a/convert.c b/convert.c
index e4e2877..18af685 100644
--- a/convert.c
+++ b/convert.c
@@ -31,7 +31,7 @@ enum crlf_action {
 
 struct text_stat {
 	/* NUL, CR, LF and CRLF counts */
-	unsigned nul, cr, lf, crlf;
+	unsigned nul, lonecr, lonelf, crlf;
 
 	/* These are just approximations! */
 	unsigned printable, nonprintable;
@@ -46,13 +46,15 @@ static void gather_stats(const char *buf, unsigned long size, struct text_stat *
 	for (i = 0; i < size; i++) {
 		unsigned char c = buf[i];
 		if (c == '\r') {
-			stats->cr++;
-			if (i+1 < size && buf[i+1] == '\n')
+			if (i+1 < size && buf[i+1] == '\n') {
 				stats->crlf++;
+				i++;
+			} else
+				stats->lonecr++;
 			continue;
 		}
 		if (c == '\n') {
-			stats->lf++;
+			stats->lonelf++;
 			continue;
 		}
 		if (c == 127)
@@ -86,7 +88,7 @@ static void gather_stats(const char *buf, unsigned long size, struct text_stat *
  */
 static int convert_is_binary(unsigned long size, const struct text_stat *stats)
 {
-	if (stats->cr != stats->crlf)
+	if (stats->lonecr)
 		return 1;
 	if (stats->nul)
 		return 1;
@@ -98,19 +100,18 @@ static int convert_is_binary(unsigned long size, const struct text_stat *stats)
 static unsigned int gather_convert_stats(const char *data, unsigned long size)
 {
 	struct text_stat stats;
+	int ret = 0;
 	if (!data || !size)
 		return 0;
 	gather_stats(data, size, &stats);
 	if (convert_is_binary(size, &stats))
-		return CONVERT_STAT_BITS_BIN;
-	else if (stats.crlf && stats.crlf == stats.lf)
-		return CONVERT_STAT_BITS_TXT_CRLF;
-	else if (stats.crlf && stats.lf)
-		return CONVERT_STAT_BITS_TXT_CRLF | CONVERT_STAT_BITS_TXT_LF;
-	else if (stats.lf)
-		return CONVERT_STAT_BITS_TXT_LF;
-	else
-		return 0;
+		ret |= CONVERT_STAT_BITS_BIN;
+	if (stats.crlf)
+		ret |= CONVERT_STAT_BITS_TXT_CRLF;
+	if (stats.lonelf)
+		ret |=  CONVERT_STAT_BITS_TXT_LF;
+
+	return ret;
 }
 
 static const char *gather_convert_stats_ascii(const char *data, unsigned long size)
@@ -207,7 +208,7 @@ static void check_safe_crlf(const char *path, enum crlf_action crlf_action,
 		 * CRLFs would be added by checkout:
 		 * check if we have "naked" LFs
 		 */
-		if (stats->lf != stats->crlf) {
+		if (stats->lonelf) {
 			if (checksafe == SAFE_CRLF_WARN)
 				warning("LF will be replaced by CRLF in %s.\nThe file will have its original line endings in your working directory.", path);
 			else /* i.e. SAFE_CRLF_FAIL */
@@ -266,8 +267,8 @@ static int crlf_to_git(const char *path, const char *src, size_t len,
 
 	check_safe_crlf(path, crlf_action, &stats, checksafe);
 
-	/* Optimization: No CR? Nothing to convert, regardless. */
-	if (!stats.cr)
+	/* Optimization: No CRLF? Nothing to convert, regardless. */
+	if (!stats.crlf)
 		return 0;
 
 	/*
@@ -314,19 +315,15 @@ static int crlf_to_worktree(const char *path, const char *src, size_t len,
 
 	gather_stats(src, len, &stats);
 
-	/* No LF? Nothing to convert, regardless. */
-	if (!stats.lf)
-		return 0;
-
-	/* Was it already in CRLF format? */
-	if (stats.lf == stats.crlf)
+	/* No "naked" LF? Nothing to convert, regardless. */
+	if (!stats.lonelf)
 		return 0;
 
 	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 		if (crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 			/* If we have any CR or CRLF line endings, we do not touch it */
 			/* This is the new safer autocrlf-handling */
-			if (stats.cr > 0 || stats.crlf > 0)
+			if (stats.lonecr || stats.crlf )
 				return 0;
 		}
 
@@ -338,7 +335,7 @@ static int crlf_to_worktree(const char *path, const char *src, size_t len,
 	if (src == buf->buf)
 		to_free = strbuf_detach(buf, NULL);
 
-	strbuf_grow(buf, len + stats.lf - stats.crlf);
+	strbuf_grow(buf, len + stats.lonelf);
 	for (;;) {
 		const char *nl = memchr(src, '\n', len);
 		if (!nl)
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* Re: [PATCH v3 1/7] t0027: Add tests for get_stream_filter()
  2016-02-05 16:13 ` [PATCH v3 1/7] t0027: Add tests for get_stream_filter() tboegi
@ 2016-02-08 17:59   ` Junio C Hamano
  0 siblings, 0 replies; 47+ messages in thread
From: Junio C Hamano @ 2016-02-08 17:59 UTC (permalink / raw)
  To: tboegi; +Cc: git

tboegi@web.de writes:

> From: Torsten Bögershausen <tboegi@web.de>
> Subject: Re: [PATCH v3 1/7] t0027: Add tests for get_stream_filter()

s/: Add/: add/ (no need to resend this)

> When a filter is configured, a different code-path is used in convert.c
> and entry.c via get_stream_filter(), but there are no test cases yet.
>
> Add tests for the filter API by configuring the ident filter.
> The result of the SHA1 conversion is not checked, this is already
> done in other TC.
>
> Add a parameter to checkout_files() in t0027.
> While changing the signature, add another parameter for the eol= attribute.
> This is currently unused, tests for e.g.
> "* text=auto eol=lf" will be added in a separate commit.
>
> Signed-off-by: Torsten Bögershausen <tboegi@web.de>
> ---
> Changes since v2:
> 1/7 t0027 uses ident instead of i (the empty "" is still there)

Thanks, much easier to understand with that spelled out.

And making "" a noop makes sense given the way this helper is called
(i.e. it is fed "$ident" and "$attr" quoted in dq, and they could
become empty string--it is not worth doing ${ident:+"$ident"} there).

^ permalink raw reply	[flat|nested] 47+ messages in thread

* Re: [PATCH v3 5/7] convert: auto_crlf=false and no attributes set: same as binary
  2016-02-05 16:13 ` [PATCH v3 5/7] convert: auto_crlf=false and no attributes set: same as binary tboegi
@ 2016-02-08 18:27   ` Junio C Hamano
  2016-02-09 14:34     ` Torsten Bögershausen
  0 siblings, 1 reply; 47+ messages in thread
From: Junio C Hamano @ 2016-02-08 18:27 UTC (permalink / raw)
  To: tboegi; +Cc: git

tboegi@web.de writes:

> From: Torsten Bögershausen <tboegi@web.de>
>
> When core.autocrlf is set to false, and no attributes are set, the file
> is treated as binary.

This, and also on the title, I know by "binary" you mean "no
conversion is attempted", and it is the word used in the code around
there, but it still makes my heart skip a beat every time I read
this sentence--it is not like we do not treat the contents as text
after all.

In any case, I take the above sentence the statement of the fact,
describing how the world currently is, not declaring a new world
order.

> Simplify the logic and remove duplicated code when dealing with
> (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE) by
> setting crlf_action=CRLF_BINARY already in convert_attrs().

I looked at all the places where CRLF_BINARY is checked.  The ones
that are in this patch are clearly where "Is it BINARY?" and "Is
AUTO_CRLF_FALSE and CRLF_GUESS both true?" mean the same thing, so
this is a correct simplification to these places.

It is not easy to see what the effect of this change to the other
places that use CRLF_BINARY, though.

 * output_eol() used to return EOL_UNSET when auto_crlf is not in
   effect and CRLF_GUESS is.  The function will see CRLF_BINARY with
   this patch in such a case, and returns EOL_UNSET.  So there is no
   change to the function and its callers.

 * convert_attrs() has "If BINARY don't do anything and return".
   Will the patch change behaviour for the "not-autocrlf,
   CRLF_GUESS" case in this codepath?  I think ca->crlf_action used
   to be left as CRLF_GUESS here before the patch, and now by the
   time the control flow reaches here it is already CRLF_BINARY.
   Would it affect the callers, and if so how?

 * get_convert_attr_ascii() would change the behaviour, right?  It
   runs convert_attrs(), and with this change a path without
   attribute when autocrlf is not in effect would get BINARY and
   would show "-text", while the code before this change would give
   an empty string.  Am I misreading the code, or is the change
   intended?

Thanks.

^ permalink raw reply	[flat|nested] 47+ messages in thread

* Re: [PATCH v3 5/7] convert: auto_crlf=false and no attributes set: same as binary
  2016-02-08 18:27   ` Junio C Hamano
@ 2016-02-09 14:34     ` Torsten Bögershausen
  2016-02-09 18:06       ` Junio C Hamano
  0 siblings, 1 reply; 47+ messages in thread
From: Torsten Bögershausen @ 2016-02-09 14:34 UTC (permalink / raw)
  To: Junio C Hamano, tboegi; +Cc: git

On 02/08/2016 07:27 PM, Junio C Hamano wrote:
> tboegi@web.de writes:
>
>> From: Torsten Bögershausen <tboegi@web.de>
>>
>> When core.autocrlf is set to false, and no attributes are set, the file
>> is treated as binary.
> This, and also on the title, I know by "binary" you mean "no
> conversion is attempted", and it is the word used in the code around
> there, but it still makes my heart skip a beat every time I read
> this sentence--it is not like we do not treat the contents as text
> after all.
>
> In any case, I take the above sentence the statement of the fact,
> describing how the world currently is, not declaring a new world
> order.
The word binary is indeed not ideal here: no eol conversion is done.
(And the commit message could use "-text")
>> Simplify the logic and remove duplicated code when dealing with
>> (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE) by
>> setting crlf_action=CRLF_BINARY already in convert_attrs().
> I looked at all the places where CRLF_BINARY is checked.  The ones
> that are in this patch are clearly where "Is it BINARY?" and "Is
> AUTO_CRLF_FALSE and CRLF_GUESS both true?" mean the same thing, so
> this is a correct simplification to these places.
>
> It is not easy to see what the effect of this change to the other
> places that use CRLF_BINARY, though.
>
>  * output_eol() used to return EOL_UNSET when auto_crlf is not in
>    effect and CRLF_GUESS is.  The function will see CRLF_BINARY with
>    this patch in such a case, and returns EOL_UNSET.  So there is no
>    change to the function and its callers.
OK
>  * convert_attrs() has "If BINARY don't do anything and return".
>    Will the patch change behaviour for the "not-autocrlf,
>    CRLF_GUESS" case in this codepath?  I think ca->crlf_action used
>    to be left as CRLF_GUESS here before the patch, and now by the
>    time the control flow reaches here it is already CRLF_BINARY.
>    Would it affect the callers, and if so how?
Not sure if I fully understand the question:

The old CRLF_GUESS could mean (a) core.autocrlf=true,
(b) core.autocrlf=input or (c) core.autocrlf=false.
The callers had to look at the core.autocrlf them self.
This patch removes (c), the next (or over next) (a) and (b)

    if (ca->crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE)
        ca->crlf_action = CRLF_BINARY;
}
The next patch 6/7 removes "GUESS" completely.



>  * get_convert_attr_ascii() would change the behaviour, right?  It
>    runs convert_attrs(), and with this change a path without
>    attribute when autocrlf is not in effect would get BINARY and
>    would show "-text", while the code before this change would give
>    an empty string.  Am I misreading the code, or is the change
>    intended?
>
> Thanks.
(That happened in my first (not published) version,
today we have this:)
struct conv_attrs {
    struct convert_driver *drv;
    enum crlf_action attr_action; /* What attr says */
    enum crlf_action crlf_action; /* When no attr is set, use core.autocrlf */
    int ident;
};

The idea is (after this and the next commit 6/7) is
that once we had run  convert_attrs() there is a clear picture
what should be done with the eols, and it is stored in crlf_action.

No further check with core.autocrlf in any calling party should be needed.

In a future series it should be possible to set
*text=auto
*eol=clrf
to behave exactly as if core.autocrlf=true.
But that is a change in behavior, and needs a separate series.
This series should not change the behavior, so a critical review is appreciated.


Does this answers the questions ?
Is a local amend possible ?

^ permalink raw reply	[flat|nested] 47+ messages in thread

* Re: [PATCH v3 5/7] convert: auto_crlf=false and no attributes set: same as binary
  2016-02-09 14:34     ` Torsten Bögershausen
@ 2016-02-09 18:06       ` Junio C Hamano
  0 siblings, 0 replies; 47+ messages in thread
From: Junio C Hamano @ 2016-02-09 18:06 UTC (permalink / raw)
  To: Torsten Bögershausen; +Cc: git

Torsten Bögershausen <tboegi@web.de> writes:

>>  * convert_attrs() has "If BINARY don't do anything and return".
>>    Will the patch change behaviour for the "not-autocrlf,
>>    CRLF_GUESS" case in this codepath?  I think ca->crlf_action used
>>    to be left as CRLF_GUESS here before the patch, and now by the
>>    time the control flow reaches here it is already CRLF_BINARY.
>>    Would it affect the callers, and if so how?
> Not sure if I fully understand the question:
>
> The old CRLF_GUESS could mean (a) core.autocrlf=true,
> (b) core.autocrlf=input or (c) core.autocrlf=false.
> The callers had to look at the core.autocrlf them self.
> This patch removes (c), the next (or over next) (a) and (b)

That part I understand and fully agree.

If a function that appears much later in the control flow depends
on seeing CRLF_GUESS to do certain things, and showing CRLF_BINARY
to the code would make it behave differently, that would make this
patch incorrect.

That is, if some function that you did not touch (hence did not
appear in the context of this patch) did this:

	if (CRLF_GUESS)
        	do the "guess thing"
	else if (CRLF_BINARY)
        	do the "binary thing"
	else
        	do other things

then depending on how 'guess thing' and 'binary thing' work
differently, this patch would change the outcome.  If the
"guess thing" had

		if (!AUTOCRLF) goto "binary thing"

upfront, then it obviously is OK, though ;-)

If the _ONLY_ way all the code that use CRLF_GUESS is

	if ((CRLF_GUESS && !AUTOCRLF) || CRLF_BINARY)
        	do the "binary thing"

then the conversion done by the patch is perfectly fine.  It was
unclear from the patch text and the proposed log message if you made
sure that is the case.  And with your response, it still isn't clear
to me.

^ permalink raw reply	[flat|nested] 47+ messages in thread

* [PATCH v4 1/6] t0027: add tests for get_stream_filter()
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (21 preceding siblings ...)
  2016-02-05 16:13 ` [PATCH v3 7/7] convert.c: simplify text_stat tboegi
@ 2016-02-10 16:24 ` tboegi
  2016-02-10 16:24 ` [PATCH v4 2/6] convert.c: remove unused parameter 'path' tboegi
                   ` (5 subsequent siblings)
  28 siblings, 0 replies; 47+ messages in thread
From: tboegi @ 2016-02-10 16:24 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

When a filter is configured, a different code-path is used in convert.c
and entry.c via get_stream_filter(), but there are no test cases yet.

Add tests for the filter API by configuring the ident filter.
The result of the SHA1 conversion is not checked, this is already
done in other TC.

Add a parameter to checkout_files() in t0027.
While changing the signature, add another parameter for the eol= attribute.
This is currently unused, tests for e.g.
"* text=auto eol=lf" will be added in a separate commit.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
Changes against tb/conversion:
- 1..4 unchanged
- Merged together 5/7 6/7 into 5/6, improved the commit message 1%
- 7/7 becomes 6/6

 t/t0027-auto-crlf.sh | 281 ++++++++++++++++++++++++++-------------------------
 1 file changed, 146 insertions(+), 135 deletions(-)

diff --git a/t/t0027-auto-crlf.sh b/t/t0027-auto-crlf.sh
index 504e5a0..fc4c628 100755
--- a/t/t0027-auto-crlf.sh
+++ b/t/t0027-auto-crlf.sh
@@ -21,38 +21,32 @@ compare_ws_file () {
 	pfx=$1
 	exp=$2.expect
 	act=$pfx.actual.$3
-	tr '\015\000' QN <"$2" >"$exp" &&
-	tr '\015\000' QN <"$3" >"$act" &&
-	test_cmp $exp $act &&
-	rm $exp $act
+	tr '\015\000abcdef0123456789' QN00000000000000000 <"$2" >"$exp" &&
+	tr '\015\000abcdef0123456789' QN00000000000000000 <"$3" >"$act" &&
+	test_cmp "$exp" "$act" &&
+	rm "$exp" "$act"
 }
 
 create_gitattributes () {
-	attr=$1
-	case "$attr" in
-		auto)
-		echo "*.txt text=auto" >.gitattributes
-		;;
-		text)
-		echo "*.txt text" >.gitattributes
-		;;
-		-text)
-		echo "*.txt -text" >.gitattributes
-		;;
-		crlf)
-		echo "*.txt eol=crlf" >.gitattributes
-		;;
-		lf)
-		echo "*.txt eol=lf" >.gitattributes
-		;;
-		"")
-		echo >.gitattributes
-		;;
-		*)
-		echo >&2 invalid attribute: $attr
-		exit 1
-		;;
-	esac
+	{
+		while test "$#" != 0
+		do
+			case "$1" in
+			auto)	 echo '*.txt text=auto' ;;
+			ident) echo '*.txt ident' ;;
+			text)	 echo '*.txt text' ;;
+			-text) echo '*.txt -text' ;;
+			crlf)  echo '*.txt eol=crlf' ;;
+			lf)    echo '*.txt eol=lf' ;;
+			"") ;;
+			*)
+				echo >&2 invalid attribute: "$1"
+				exit 1
+				;;
+			esac &&
+			shift
+		done
+	} >.gitattributes
 }
 
 create_NNO_files () {
@@ -208,28 +202,30 @@ check_in_repo_NNO () {
 }
 
 checkout_files () {
-	eol=$1
-	crlf=$2
-	attr=$3
-	lfname=$4
-	crlfname=$5
-	lfmixcrlf=$6
-	lfmixcr=$7
-	crlfnul=$8
-	create_gitattributes $attr &&
+	attr=$1 ; shift
+	ident=$1; shift
+	aeol=$1 ; shift
+	crlf=$1 ; shift
+	ceol=$1 ; shift
+	lfname=$1 ; shift
+	crlfname=$1 ; shift
+	lfmixcrlf=$1 ; shift
+	lfmixcr=$1 ; shift
+	crlfnul=$1 ; shift
+	create_gitattributes "$attr" "$ident" &&
 	git config core.autocrlf $crlf &&
-	pfx=eol_${eol}_crlf_${crlf}_attr_${attr}_ &&
+	pfx=eol_${ceol}_crlf_${crlf}_attr_${attr}_ &&
 	for f in LF CRLF LF_mix_CR CRLF_mix_LF LF_nul
 	do
 		rm crlf_false_attr__$f.txt &&
-		if test -z "$eol"; then
+		if test -z "$ceol"; then
 			git checkout crlf_false_attr__$f.txt
 		else
-			git -c core.eol=$eol checkout crlf_false_attr__$f.txt
+			git -c core.eol=$ceol checkout crlf_false_attr__$f.txt
 		fi
 	done
 
-	test_expect_success "ls-files --eol $lfname ${pfx}LF.txt" '
+	test_expect_success "ls-files --eol attr=$attr $ident $aeol core.autocrlf=$crlf core.eol=$ceol" '
 		test_when_finished "rm expect actual" &&
 		sort <<-EOF >expect &&
 		i/crlf w/$(stats_ascii $crlfname) crlf_false_attr__CRLF.txt
@@ -244,19 +240,19 @@ checkout_files () {
 		sort >actual &&
 		test_cmp expect actual
 	'
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=LF" "
+	test_expect_success "checkout $ident $attr $aeol core.autocrlf=$crlf core.eol=$ceol file=LF" "
 		compare_ws_file $pfx $lfname    crlf_false_attr__LF.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=CRLF" "
+	test_expect_success "checkout $ident $attr $aeol core.autocrlf=$crlf core.eol=$ceol file=CRLF" "
 		compare_ws_file $pfx $crlfname  crlf_false_attr__CRLF.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=CRLF_mix_LF" "
+	test_expect_success "checkout $ident $attr $aeol core.autocrlf=$crlf core.eol=$ceol file=CRLF_mix_LF" "
 		compare_ws_file $pfx $lfmixcrlf crlf_false_attr__CRLF_mix_LF.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=LF_mix_CR" "
+	test_expect_success "checkout $ident $attr $aeol core.autocrlf=$crlf core.eol=$ceol file=LF_mix_CR" "
 		compare_ws_file $pfx $lfmixcr   crlf_false_attr__LF_mix_CR.txt
 	"
-	test_expect_success "checkout core.eol=$eol core.autocrlf=$crlf gitattributes=$attr file=LF_nul" "
+	test_expect_success "checkout $ident $attr $aeol core.autocrlf=$crlf core.eol=$ceol file=LF_nul" "
 		compare_ws_file $pfx $crlfnul   crlf_false_attr__LF_nul.txt
 	"
 }
@@ -301,14 +297,13 @@ test_expect_success 'setup master' '
 	git checkout -b master &&
 	git add .gitattributes &&
 	git commit -m "add .gitattributes" "" &&
-	printf "line1\nline2\nline3"     >LF &&
-	printf "line1\r\nline2\r\nline3" >CRLF &&
-	printf "line1\r\nline2\nline3"   >repoMIX &&
-	printf "line1\r\nline2\nline3"   >CRLF_mix_LF &&
-	printf "line1\nline2\rline3"     >LF_mix_CR &&
-	printf "line1\r\nline2\rline3"   >CRLF_mix_CR &&
-	printf "line1Q\r\nline2\r\nline3" | q_to_nul >CRLF_nul &&
-	printf "line1Q\nline2\nline3" | q_to_nul >LF_nul &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONE\nLINETWO\nLINETHREE"     >LF &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\r\nLINEONE\r\nLINETWO\r\nLINETHREE" >CRLF &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONE\r\nLINETWO\nLINETHREE"   >CRLF_mix_LF &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONE\nLINETWO\rLINETHREE"     >LF_mix_CR &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\r\nLINEONE\r\nLINETWO\rLINETHREE"   >CRLF_mix_CR &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\r\nLINEONEQ\r\nLINETWO\r\nLINETHREE" | q_to_nul >CRLF_nul &&
+	printf "\$Id: 0000000000000000000000000000000000000000 \$\nLINEONEQ\nLINETWO\nLINETHREE" | q_to_nul >LF_nul &&
 	create_NNO_files CRLF_mix_LF CRLF_mix_LF CRLF_mix_LF CRLF_mix_LF CRLF_mix_LF &&
 	git -c core.autocrlf=false add NNO_*.txt &&
 	git commit -m "mixed line endings" &&
@@ -449,23 +444,18 @@ check_in_repo_NNO input "-text" LF        CRLF      CRLF_mix_LF  LF_mix_CR 	CRLF
 # How to read the table below:
 # - checkout_files will check multiple files with a combination of settings
 #   and attributes (core.autocrlf=input is forbidden with core.eol=crlf)
-# - parameter $1 : core.eol               lf | crlf
-# - parameter $2 : core.autocrlf          false | true | input
-# - parameter $3 : text in .gitattributs  "" (empty) | auto | text | -text
-# - parameter $4 : reference for a file with only LF in the repo
-# - parameter $5 : reference for a file with only CRLF in the repo
-# - parameter $6 : reference for a file with mixed LF and CRLF in the repo
-# - parameter $7 : reference for a file with LF and CR in the repo (does somebody uses this ?)
-# - parameter $8 : reference for a file with CRLF and a NUL (should be handled as binary when auto)
-
-#                                            What we have in the repo:
-#                                            ----------------- EOL in repo ----------------
-#                                            LF    CRLF  CRLF_mix_LF  LF_mix_CR    CRLF_nul
-#                   settings with checkout:
-#                   core.   core.   .gitattr
-#                    eol     acrlf
-#                                            ----------------------------------------------
-#                                            What we want to have in the working tree:
+#
+# - parameter $1 	: text in .gitattributs  "" (empty) | auto | text | -text
+# - parameter $2 	: ident                  "" | i (i == ident)
+# - parameter $3 	: eol in .gitattributs   "" (empty) | lf | crlf
+# - parameter $4 	: core.autocrlf          false | true | input
+# - parameter $5 	: core.eol               "" | lf | crlf | "native"
+# - parameter $6 	: reference for a file with only LF in the repo
+# - parameter $7 	: reference for a file with only CRLF in the repo
+# - parameter $8 	: reference for a file with mixed LF and CRLF in the repo
+# - parameter $9 	: reference for a file with LF and CR in the repo
+# - parameter $10 : reference for a file with CRLF and a NUL (should be handled as binary when auto)
+
 if test_have_prereq NATIVE_CRLF
 then
 MIX_CRLF_LF=CRLF
@@ -480,69 +470,90 @@ LFNUL=LF_nul
 fi
 export CRLF_MIX_LF_CR MIX NL
 
-checkout_files    lf      false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "auto"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    lf      input "auto"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "text"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    lf      input "text"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      input "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      input "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    lf      false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    lf      true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    lf      input "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-
-checkout_files    crlf    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    false "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    crlf    true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    crlf    false "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    crlf    true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    crlf    false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    crlf    false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    crlf    true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-
-checkout_files    ""      false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "auto"    $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
-checkout_files    ""      true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    ""      input "auto"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "text"    $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
-checkout_files    ""      true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    ""      input "text"    LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      input "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      input "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    ""      false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    ""      true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    ""      input "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-
-checkout_files    native  false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  false "auto"    $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
-checkout_files    native  true  "auto"    CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
-checkout_files    native  false "text"    $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
-checkout_files    native  true  "text"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    native  false "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  true  "-text"   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  false "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  true  "lf"      LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
-checkout_files    native  false "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
-checkout_files    native  true  "crlf"    CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+checkout_files ""      "" 	 ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" 	 ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" 	 ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" 	 ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" 	 ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" 	 ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" 	 ""    true   ""       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" 	 ""    true   crlf     CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" 	 ""    true   lf       CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      "" 	 ""    true   native   CRLF  CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files ""      ident ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    false  ""       $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    false  crlf     CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    false  native   $NL   CRLF  $MIX_CRLF_LF LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    true   ""       CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    true   crlf     CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    true   lf       CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  "" 	 ""    true   native   CRLF  CRLF  CRLF         LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+checkout_files "auto"  ident ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+
+for id in "" ident;
+do
+	checkout_files "crlf"  "$id" ""    false  ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    false  crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    false  lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    false  native   CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    input  ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    input  lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "crlf"  "$id" ""    true   native   CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "lf"    "$id" ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "lf"    "$id" ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    false  ""       $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
+	checkout_files "text"  "$id" ""    false  crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    false  native   $NL   CRLF  $MIX_CRLF_LF $MIX_LF_CR   $LFNUL
+	checkout_files "text"  "$id" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "text"  "$id" ""    true   ""       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    true   crlf     CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    true   lf       CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "text"  "$id" ""    true   native   CRLF  CRLF  CRLF         CRLF_mix_CR  CRLF_nul
+	checkout_files "-text" "$id" ""    false  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    false  crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    false  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    false  native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    input  ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    input  lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   ""       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   crlf     LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   lf       LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+	checkout_files "-text" "$id" ""    true   native   LF    CRLF  CRLF_mix_LF  LF_mix_CR    LF_nul
+done
 
 # Should be the last test case: remove some files from the worktree
 test_expect_success 'ls-files --eol -d -z' '
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v4 2/6] convert.c: remove unused parameter 'path'
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (22 preceding siblings ...)
  2016-02-10 16:24 ` [PATCH v4 1/6] t0027: add tests for get_stream_filter() tboegi
@ 2016-02-10 16:24 ` tboegi
  2016-02-10 16:24 ` [PATCH v4 3/6] convert.c: remove input_crlf_action() tboegi
                   ` (4 subsequent siblings)
  28 siblings, 0 replies; 47+ messages in thread
From: tboegi @ 2016-02-10 16:24 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Some functions get a parameter path, but don't use it.
Remove the unused parameter.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 19 +++++++++----------
 1 file changed, 9 insertions(+), 10 deletions(-)

diff --git a/convert.c b/convert.c
index 4bb4ec1..a24c2a2 100644
--- a/convert.c
+++ b/convert.c
@@ -696,7 +696,7 @@ static int ident_to_worktree(const char *path, const char *src, size_t len,
 	return 1;
 }
 
-static enum crlf_action git_path_check_crlf(const char *path, struct git_attr_check *check)
+static enum crlf_action git_path_check_crlf(struct git_attr_check *check)
 {
 	const char *value = check->value;
 
@@ -713,7 +713,7 @@ static enum crlf_action git_path_check_crlf(const char *path, struct git_attr_ch
 	return CRLF_GUESS;
 }
 
-static enum eol git_path_check_eol(const char *path, struct git_attr_check *check)
+static enum eol git_path_check_eol(struct git_attr_check *check)
 {
 	const char *value = check->value;
 
@@ -726,8 +726,7 @@ static enum eol git_path_check_eol(const char *path, struct git_attr_check *chec
 	return EOL_UNSET;
 }
 
-static struct convert_driver *git_path_check_convert(const char *path,
-					     struct git_attr_check *check)
+static struct convert_driver *git_path_check_convert(struct git_attr_check *check)
 {
 	const char *value = check->value;
 	struct convert_driver *drv;
@@ -740,7 +739,7 @@ static struct convert_driver *git_path_check_convert(const char *path,
 	return NULL;
 }
 
-static int git_path_check_ident(const char *path, struct git_attr_check *check)
+static int git_path_check_ident(struct git_attr_check *check)
 {
 	const char *value = check->value;
 
@@ -783,12 +782,12 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 	}
 
 	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
-		ca->crlf_action = git_path_check_crlf(path, ccheck + 4);
+		ca->crlf_action = git_path_check_crlf( ccheck + 4);
 		if (ca->crlf_action == CRLF_GUESS)
-			ca->crlf_action = git_path_check_crlf(path, ccheck + 0);
-		ca->ident = git_path_check_ident(path, ccheck + 1);
-		ca->drv = git_path_check_convert(path, ccheck + 2);
-		ca->eol_attr = git_path_check_eol(path, ccheck + 3);
+			ca->crlf_action = git_path_check_crlf(ccheck + 0);
+		ca->ident = git_path_check_ident(ccheck + 1);
+		ca->drv = git_path_check_convert(ccheck + 2);
+		ca->eol_attr = git_path_check_eol(ccheck + 3);
 	} else {
 		ca->drv = NULL;
 		ca->crlf_action = CRLF_GUESS;
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v4 3/6] convert.c: remove input_crlf_action()
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (23 preceding siblings ...)
  2016-02-10 16:24 ` [PATCH v4 2/6] convert.c: remove unused parameter 'path' tboegi
@ 2016-02-10 16:24 ` tboegi
  2016-02-10 16:24 ` [PATCH v4 4/6] convert.c: use text_eol_is_crlf() tboegi
                   ` (3 subsequent siblings)
  28 siblings, 0 replies; 47+ messages in thread
From: tboegi @ 2016-02-10 16:24 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Integrate the code of input_crlf_action() into convert_attrs(),
so that ca.crlf_action is always valid after calling convert_attrs().
Keep a copy of crlf_action in attr_action, this is needed for
get_convert_attr_ascii().

Remove eol_attr from struct conv_attrs, as it is now used temporally.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 37 ++++++++++++++-----------------------
 1 file changed, 14 insertions(+), 23 deletions(-)

diff --git a/convert.c b/convert.c
index a24c2a2..d0c8c66 100644
--- a/convert.c
+++ b/convert.c
@@ -746,21 +746,10 @@ static int git_path_check_ident(struct git_attr_check *check)
 	return !!ATTR_TRUE(value);
 }
 
-static enum crlf_action input_crlf_action(enum crlf_action text_attr, enum eol eol_attr)
-{
-	if (text_attr == CRLF_BINARY)
-		return CRLF_BINARY;
-	if (eol_attr == EOL_LF)
-		return CRLF_INPUT;
-	if (eol_attr == EOL_CRLF)
-		return CRLF_CRLF;
-	return text_attr;
-}
-
 struct conv_attrs {
 	struct convert_driver *drv;
-	enum crlf_action crlf_action;
-	enum eol eol_attr;
+	enum crlf_action attr_action; /* What attr says */
+	enum crlf_action crlf_action; /* When no attr is set, use core.autocrlf */
 	int ident;
 };
 
@@ -782,16 +771,23 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 	}
 
 	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
-		ca->crlf_action = git_path_check_crlf( ccheck + 4);
+		enum eol eol_attr;
+		ca->crlf_action = git_path_check_crlf(ccheck + 4);
 		if (ca->crlf_action == CRLF_GUESS)
 			ca->crlf_action = git_path_check_crlf(ccheck + 0);
+		ca->attr_action = ca->crlf_action;
 		ca->ident = git_path_check_ident(ccheck + 1);
 		ca->drv = git_path_check_convert(ccheck + 2);
-		ca->eol_attr = git_path_check_eol(ccheck + 3);
+		if (ca->crlf_action == CRLF_BINARY)
+			return;
+		eol_attr = git_path_check_eol(ccheck + 3);
+		if (eol_attr == EOL_LF)
+			ca->crlf_action = CRLF_INPUT;
+		else if (eol_attr == EOL_CRLF)
+			ca->crlf_action = CRLF_CRLF;
 	} else {
 		ca->drv = NULL;
 		ca->crlf_action = CRLF_GUESS;
-		ca->eol_attr = EOL_UNSET;
 		ca->ident = 0;
 	}
 }
@@ -818,11 +814,9 @@ int would_convert_to_git_filter_fd(const char *path)
 const char *get_convert_attr_ascii(const char *path)
 {
 	struct conv_attrs ca;
-	enum crlf_action crlf_action;
 
 	convert_attrs(&ca, path);
-	crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
-	switch (crlf_action) {
+	switch (ca.attr_action) {
 	case CRLF_GUESS:
 		return "";
 	case CRLF_BINARY:
@@ -861,7 +855,6 @@ int convert_to_git(const char *path, const char *src, size_t len,
 		src = dst->buf;
 		len = dst->len;
 	}
-	ca.crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
 	ret |= crlf_to_git(path, src, len, dst, ca.crlf_action, checksafe);
 	if (ret && dst) {
 		src = dst->buf;
@@ -882,7 +875,6 @@ void convert_to_git_filter_fd(const char *path, int fd, struct strbuf *dst,
 	if (!apply_filter(path, NULL, 0, fd, dst, ca.drv->clean))
 		die("%s: clean filter '%s' failed", path, ca.drv->name);
 
-	ca.crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
 	crlf_to_git(path, dst->buf, dst->len, dst, ca.crlf_action, checksafe);
 	ident_to_git(path, dst->buf, dst->len, dst, ca.ident);
 }
@@ -912,7 +904,6 @@ static int convert_to_working_tree_internal(const char *path, const char *src,
 	 * is a smudge filter.  The filter might expect CRLFs.
 	 */
 	if (filter || !normalizing) {
-		ca.crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
 		ret |= crlf_to_worktree(path, src, len, dst, ca.crlf_action);
 		if (ret) {
 			src = dst->buf;
@@ -1381,7 +1372,7 @@ struct stream_filter *get_stream_filter(const char *path, const unsigned char *s
 	if (ca.ident)
 		filter = ident_filter(sha1);
 
-	crlf_action = input_crlf_action(ca.crlf_action, ca.eol_attr);
+	crlf_action = ca.crlf_action;
 
 	if ((crlf_action == CRLF_BINARY) || (crlf_action == CRLF_INPUT) ||
 	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE))
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v4 4/6] convert.c: use text_eol_is_crlf()
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (24 preceding siblings ...)
  2016-02-10 16:24 ` [PATCH v4 3/6] convert.c: remove input_crlf_action() tboegi
@ 2016-02-10 16:24 ` tboegi
  2016-02-10 16:24 ` [PATCH v4 5/6] convert.c: refactor crlf_action tboegi
                   ` (2 subsequent siblings)
  28 siblings, 0 replies; 47+ messages in thread
From: tboegi @ 2016-02-10 16:24 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen, Junio C Hamano

From: Torsten Bögershausen <tboegi@web.de>

Add a helper function to find out, which line endings text files
should get at checkout, depending on core.autocrlf and core.eol
configuration variables.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
Signed-off-by: Junio C Hamano <gitster@pobox.com>
---
 convert.c | 20 ++++++++++++++------
 1 file changed, 14 insertions(+), 6 deletions(-)

diff --git a/convert.c b/convert.c
index d0c8c66..557e574 100644
--- a/convert.c
+++ b/convert.c
@@ -149,6 +149,19 @@ const char *get_wt_convert_stats_ascii(const char *path)
 	return ret;
 }
 
+static int text_eol_is_crlf(void)
+{
+	if (auto_crlf == AUTO_CRLF_TRUE)
+		return 1;
+	else if (auto_crlf == AUTO_CRLF_INPUT)
+		return 0;
+	if (core_eol == EOL_CRLF)
+		return 1;
+	if (core_eol == EOL_UNSET && EOL_NATIVE == EOL_CRLF)
+		return 1;
+	return 0;
+}
+
 static enum eol output_eol(enum crlf_action crlf_action)
 {
 	switch (crlf_action) {
@@ -164,12 +177,7 @@ static enum eol output_eol(enum crlf_action crlf_action)
 		/* fall through */
 	case CRLF_TEXT:
 	case CRLF_AUTO:
-		if (auto_crlf == AUTO_CRLF_TRUE)
-			return EOL_CRLF;
-		else if (auto_crlf == AUTO_CRLF_INPUT)
-			return EOL_LF;
-		else if (core_eol == EOL_UNSET)
-			return EOL_NATIVE;
+		return text_eol_is_crlf() ? EOL_CRLF : EOL_LF;
 	}
 	return core_eol;
 }
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v4 5/6] convert.c: refactor crlf_action
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (25 preceding siblings ...)
  2016-02-10 16:24 ` [PATCH v4 4/6] convert.c: use text_eol_is_crlf() tboegi
@ 2016-02-10 16:24 ` tboegi
  2016-02-10 16:24 ` [PATCH v4 6/6] convert.c: simplify text_stat tboegi
  2016-02-22  5:11 ` [PATCH 1/1] convert.c: correct attr_action tboegi
  28 siblings, 0 replies; 47+ messages in thread
From: tboegi @ 2016-02-10 16:24 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Refactor the determination and usage of crlf_action.
Today, when no "crlf" attribute are set on a file, crlf_action is set to
CRLF_GUESS. Use CRLF_UNDEFINED instead, and search for "text" or "eol" as
before.
After searching for line ending attributes, save the value in
struct conv_attrs.crlf_action attr_action,
so that get_convert_attr_ascii() is able report the attributes.

Replace the old CRLF_GUESS usage:
CRLF_GUESS && core.autocrlf=true -> CRLF_AUTO_CRLF
CRLF_GUESS && core.autocrlf=false -> CRLF_BINARY
CRLF_GUESS && core.autocrlf=input -> CRLF_AUTO_INPUT

Save the action in conv_attrs.crlf_action (as before) and change
all callers.

Make more clear, what is what, by defining:

- CRLF_UNDEFINED : No attributes set. Temparally used, until core.autocrlf
                   and core.eol is evaluated and one of CRLF_BINARY,
                   CRLF_AUTO_INPUT or CRLF_AUTO_CRLF is selected
- CRLF_BINARY    : No processing of line endings.
- CRLF_TEXT      : attribute "text" is set, line endings are processed.
- CRLF_TEXT_INPUT: attribute "input" or "eol=lf" is set. This implies text.
- CRLF_TEXT_CRLF : attribute "eol=crlf" is set. This implies text.
- CRLF_AUTO      : attribute "auto" is set.
- CRLF_AUTO_INPUT: core.autocrlf=input (no attributes)
- CRLF_AUTO_CRLF : core.autocrlf=true  (no attributes)

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 77 ++++++++++++++++++++++++++++++++++++++-------------------------
 1 file changed, 46 insertions(+), 31 deletions(-)

diff --git a/convert.c b/convert.c
index 557e574..e4e2877 100644
--- a/convert.c
+++ b/convert.c
@@ -19,12 +19,14 @@
 #define CONVERT_STAT_BITS_BIN       0x4
 
 enum crlf_action {
-	CRLF_GUESS = -1,
-	CRLF_BINARY = 0,
+	CRLF_UNDEFINED,
+	CRLF_BINARY,
 	CRLF_TEXT,
-	CRLF_INPUT,
-	CRLF_CRLF,
-	CRLF_AUTO
+	CRLF_TEXT_INPUT,
+	CRLF_TEXT_CRLF,
+	CRLF_AUTO,
+	CRLF_AUTO_INPUT,
+	CRLF_AUTO_CRLF
 };
 
 struct text_stat {
@@ -167,18 +169,19 @@ static enum eol output_eol(enum crlf_action crlf_action)
 	switch (crlf_action) {
 	case CRLF_BINARY:
 		return EOL_UNSET;
-	case CRLF_CRLF:
+	case CRLF_TEXT_CRLF:
 		return EOL_CRLF;
-	case CRLF_INPUT:
+	case CRLF_TEXT_INPUT:
 		return EOL_LF;
-	case CRLF_GUESS:
-		if (!auto_crlf)
-			return EOL_UNSET;
-		/* fall through */
+	case CRLF_UNDEFINED:
+	case CRLF_AUTO_CRLF:
+	case CRLF_AUTO_INPUT:
 	case CRLF_TEXT:
 	case CRLF_AUTO:
+		/* fall through */
 		return text_eol_is_crlf() ? EOL_CRLF : EOL_LF;
 	}
+	warning("Illegal crlf_action %d\n", (int)crlf_action);
 	return core_eol;
 }
 
@@ -235,7 +238,6 @@ static int crlf_to_git(const char *path, const char *src, size_t len,
 	char *dst;
 
 	if (crlf_action == CRLF_BINARY ||
-	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE) ||
 	    (src && !len))
 		return 0;
 
@@ -248,11 +250,11 @@ static int crlf_to_git(const char *path, const char *src, size_t len,
 
 	gather_stats(src, len, &stats);
 
-	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS) {
+	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 		if (convert_is_binary(len, &stats))
 			return 0;
 
-		if (crlf_action == CRLF_GUESS) {
+		if (crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 			/*
 			 * If the file in the index has any CR in it, do not convert.
 			 * This is the new safer autocrlf handling.
@@ -279,7 +281,7 @@ static int crlf_to_git(const char *path, const char *src, size_t len,
 	if (strbuf_avail(buf) + buf->len < len)
 		strbuf_grow(buf, len - buf->len);
 	dst = buf->buf;
-	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS) {
+	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 		/*
 		 * If we guessed, we already know we rejected a file with
 		 * lone CR, and we can strip a CR without looking at what
@@ -320,8 +322,8 @@ static int crlf_to_worktree(const char *path, const char *src, size_t len,
 	if (stats.lf == stats.crlf)
 		return 0;
 
-	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS) {
-		if (crlf_action == CRLF_GUESS) {
+	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
+		if (crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 			/* If we have any CR or CRLF line endings, we do not touch it */
 			/* This is the new safer autocrlf-handling */
 			if (stats.cr > 0 || stats.crlf > 0)
@@ -709,16 +711,16 @@ static enum crlf_action git_path_check_crlf(struct git_attr_check *check)
 	const char *value = check->value;
 
 	if (ATTR_TRUE(value))
-		return CRLF_TEXT;
+		return text_eol_is_crlf() ? CRLF_TEXT_CRLF : CRLF_TEXT_INPUT;
 	else if (ATTR_FALSE(value))
 		return CRLF_BINARY;
 	else if (ATTR_UNSET(value))
 		;
 	else if (!strcmp(value, "input"))
-		return CRLF_INPUT;
+		return CRLF_TEXT_INPUT;
 	else if (!strcmp(value, "auto"))
 		return CRLF_AUTO;
-	return CRLF_GUESS;
+	return CRLF_UNDEFINED;
 }
 
 static enum eol git_path_check_eol(struct git_attr_check *check)
@@ -781,7 +783,7 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
 		enum eol eol_attr;
 		ca->crlf_action = git_path_check_crlf(ccheck + 4);
-		if (ca->crlf_action == CRLF_GUESS)
+		if (ca->crlf_action == CRLF_UNDEFINED)
 			ca->crlf_action = git_path_check_crlf(ccheck + 0);
 		ca->attr_action = ca->crlf_action;
 		ca->ident = git_path_check_ident(ccheck + 1);
@@ -790,14 +792,22 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 			return;
 		eol_attr = git_path_check_eol(ccheck + 3);
 		if (eol_attr == EOL_LF)
-			ca->crlf_action = CRLF_INPUT;
+			ca->crlf_action = CRLF_TEXT_INPUT;
 		else if (eol_attr == EOL_CRLF)
-			ca->crlf_action = CRLF_CRLF;
+			ca->crlf_action = CRLF_TEXT_CRLF;
 	} else {
 		ca->drv = NULL;
-		ca->crlf_action = CRLF_GUESS;
+		ca->crlf_action = CRLF_UNDEFINED;
 		ca->ident = 0;
 	}
+	if (ca->crlf_action == CRLF_TEXT)
+		ca->crlf_action = text_eol_is_crlf() ? CRLF_TEXT_CRLF : CRLF_TEXT_INPUT;
+	if (ca->crlf_action == CRLF_UNDEFINED && auto_crlf == AUTO_CRLF_FALSE)
+		ca->crlf_action = CRLF_BINARY;
+	if (ca->crlf_action == CRLF_UNDEFINED && auto_crlf == AUTO_CRLF_TRUE)
+		ca->crlf_action = CRLF_AUTO_CRLF;
+	if (ca->crlf_action == CRLF_UNDEFINED && auto_crlf == AUTO_CRLF_INPUT)
+		ca->crlf_action = CRLF_AUTO_INPUT;
 }
 
 int would_convert_to_git_filter_fd(const char *path)
@@ -825,18 +835,22 @@ const char *get_convert_attr_ascii(const char *path)
 
 	convert_attrs(&ca, path);
 	switch (ca.attr_action) {
-	case CRLF_GUESS:
+	case CRLF_UNDEFINED:
 		return "";
 	case CRLF_BINARY:
 		return "-text";
 	case CRLF_TEXT:
 		return "text";
-	case CRLF_INPUT:
+	case CRLF_TEXT_INPUT:
 		return "text eol=lf";
-	case CRLF_CRLF:
-		return "text=auto eol=crlf";
+	case CRLF_TEXT_CRLF:
+		return "text eol=crlf";
 	case CRLF_AUTO:
 		return "text=auto";
+	case CRLF_AUTO_CRLF:
+		return "text=auto eol=crlf"; /* This is not supported yet */
+	case CRLF_AUTO_INPUT:
+		return "text=auto eol=lf"; /* This is not supported yet */
 	}
 	return "";
 }
@@ -1382,12 +1396,13 @@ struct stream_filter *get_stream_filter(const char *path, const unsigned char *s
 
 	crlf_action = ca.crlf_action;
 
-	if ((crlf_action == CRLF_BINARY) || (crlf_action == CRLF_INPUT) ||
-	    (crlf_action == CRLF_GUESS && auto_crlf == AUTO_CRLF_FALSE))
+	if ((crlf_action == CRLF_BINARY) ||
+			crlf_action == CRLF_AUTO_INPUT ||
+			(crlf_action == CRLF_TEXT_INPUT))
 		filter = cascade_filter(filter, &null_filter_singleton);
 
 	else if (output_eol(crlf_action) == EOL_CRLF &&
-		 !(crlf_action == CRLF_AUTO || crlf_action == CRLF_GUESS))
+		 !(crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_CRLF))
 		filter = cascade_filter(filter, lf_to_crlf_filter());
 
 	return filter;
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH v4 6/6] convert.c: simplify text_stat
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (26 preceding siblings ...)
  2016-02-10 16:24 ` [PATCH v4 5/6] convert.c: refactor crlf_action tboegi
@ 2016-02-10 16:24 ` tboegi
  2016-02-22  5:11 ` [PATCH 1/1] convert.c: correct attr_action tboegi
  28 siblings, 0 replies; 47+ messages in thread
From: tboegi @ 2016-02-10 16:24 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Simplify the statistics:
lonecr counts the CR which is not followed by a LF,
lonelf counts the LF which is not preceded by a CR,
crlf counts CRLF combinations.
This simplifies the evaluation of the statistics.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c | 47 ++++++++++++++++++++++-------------------------
 1 file changed, 22 insertions(+), 25 deletions(-)

diff --git a/convert.c b/convert.c
index e4e2877..18af685 100644
--- a/convert.c
+++ b/convert.c
@@ -31,7 +31,7 @@ enum crlf_action {
 
 struct text_stat {
 	/* NUL, CR, LF and CRLF counts */
-	unsigned nul, cr, lf, crlf;
+	unsigned nul, lonecr, lonelf, crlf;
 
 	/* These are just approximations! */
 	unsigned printable, nonprintable;
@@ -46,13 +46,15 @@ static void gather_stats(const char *buf, unsigned long size, struct text_stat *
 	for (i = 0; i < size; i++) {
 		unsigned char c = buf[i];
 		if (c == '\r') {
-			stats->cr++;
-			if (i+1 < size && buf[i+1] == '\n')
+			if (i+1 < size && buf[i+1] == '\n') {
 				stats->crlf++;
+				i++;
+			} else
+				stats->lonecr++;
 			continue;
 		}
 		if (c == '\n') {
-			stats->lf++;
+			stats->lonelf++;
 			continue;
 		}
 		if (c == 127)
@@ -86,7 +88,7 @@ static void gather_stats(const char *buf, unsigned long size, struct text_stat *
  */
 static int convert_is_binary(unsigned long size, const struct text_stat *stats)
 {
-	if (stats->cr != stats->crlf)
+	if (stats->lonecr)
 		return 1;
 	if (stats->nul)
 		return 1;
@@ -98,19 +100,18 @@ static int convert_is_binary(unsigned long size, const struct text_stat *stats)
 static unsigned int gather_convert_stats(const char *data, unsigned long size)
 {
 	struct text_stat stats;
+	int ret = 0;
 	if (!data || !size)
 		return 0;
 	gather_stats(data, size, &stats);
 	if (convert_is_binary(size, &stats))
-		return CONVERT_STAT_BITS_BIN;
-	else if (stats.crlf && stats.crlf == stats.lf)
-		return CONVERT_STAT_BITS_TXT_CRLF;
-	else if (stats.crlf && stats.lf)
-		return CONVERT_STAT_BITS_TXT_CRLF | CONVERT_STAT_BITS_TXT_LF;
-	else if (stats.lf)
-		return CONVERT_STAT_BITS_TXT_LF;
-	else
-		return 0;
+		ret |= CONVERT_STAT_BITS_BIN;
+	if (stats.crlf)
+		ret |= CONVERT_STAT_BITS_TXT_CRLF;
+	if (stats.lonelf)
+		ret |=  CONVERT_STAT_BITS_TXT_LF;
+
+	return ret;
 }
 
 static const char *gather_convert_stats_ascii(const char *data, unsigned long size)
@@ -207,7 +208,7 @@ static void check_safe_crlf(const char *path, enum crlf_action crlf_action,
 		 * CRLFs would be added by checkout:
 		 * check if we have "naked" LFs
 		 */
-		if (stats->lf != stats->crlf) {
+		if (stats->lonelf) {
 			if (checksafe == SAFE_CRLF_WARN)
 				warning("LF will be replaced by CRLF in %s.\nThe file will have its original line endings in your working directory.", path);
 			else /* i.e. SAFE_CRLF_FAIL */
@@ -266,8 +267,8 @@ static int crlf_to_git(const char *path, const char *src, size_t len,
 
 	check_safe_crlf(path, crlf_action, &stats, checksafe);
 
-	/* Optimization: No CR? Nothing to convert, regardless. */
-	if (!stats.cr)
+	/* Optimization: No CRLF? Nothing to convert, regardless. */
+	if (!stats.crlf)
 		return 0;
 
 	/*
@@ -314,19 +315,15 @@ static int crlf_to_worktree(const char *path, const char *src, size_t len,
 
 	gather_stats(src, len, &stats);
 
-	/* No LF? Nothing to convert, regardless. */
-	if (!stats.lf)
-		return 0;
-
-	/* Was it already in CRLF format? */
-	if (stats.lf == stats.crlf)
+	/* No "naked" LF? Nothing to convert, regardless. */
+	if (!stats.lonelf)
 		return 0;
 
 	if (crlf_action == CRLF_AUTO || crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 		if (crlf_action == CRLF_AUTO_INPUT || crlf_action == CRLF_AUTO_CRLF) {
 			/* If we have any CR or CRLF line endings, we do not touch it */
 			/* This is the new safer autocrlf-handling */
-			if (stats.cr > 0 || stats.crlf > 0)
+			if (stats.lonecr || stats.crlf )
 				return 0;
 		}
 
@@ -338,7 +335,7 @@ static int crlf_to_worktree(const char *path, const char *src, size_t len,
 	if (src == buf->buf)
 		to_free = strbuf_detach(buf, NULL);
 
-	strbuf_grow(buf, len + stats.lf - stats.crlf);
+	strbuf_grow(buf, len + stats.lonelf);
 	for (;;) {
 		const char *nl = memchr(src, '\n', len);
 		if (!nl)
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* [PATCH 1/1] convert.c: correct attr_action
       [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
                   ` (27 preceding siblings ...)
  2016-02-10 16:24 ` [PATCH v4 6/6] convert.c: simplify text_stat tboegi
@ 2016-02-22  5:11 ` tboegi
  2016-02-22  5:34   ` Eric Sunshine
                     ` (2 more replies)
  28 siblings, 3 replies; 47+ messages in thread
From: tboegi @ 2016-02-22  5:11 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Commit "convert.c: refactor crlf_action" unified the crlf_handling
and introdused a bug for "git ls-files --eol".
The "text" attribute was shown as "text eol=lf" or "text eol=crlf",
depending on core.autocrlf or core.eol.
Correct this and add test cases in t0027.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
This fix needs to go on top of tb/conversion
convert.c            |  3 ++-
 t/t0027-auto-crlf.sh | 47 ++++++++++++++++++++++++++++++++++++++++-------
 2 files changed, 42 insertions(+), 8 deletions(-)

diff --git a/convert.c b/convert.c
index 18af685..0bc32ec 100644
--- a/convert.c
+++ b/convert.c
@@ -708,7 +708,7 @@ static enum crlf_action git_path_check_crlf(struct git_attr_check *check)
 	const char *value = check->value;
 
 	if (ATTR_TRUE(value))
-		return text_eol_is_crlf() ? CRLF_TEXT_CRLF : CRLF_TEXT_INPUT;
+		return CRLF_TEXT;
 	else if (ATTR_FALSE(value))
 		return CRLF_BINARY;
 	else if (ATTR_UNSET(value))
@@ -792,6 +792,7 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 			ca->crlf_action = CRLF_TEXT_INPUT;
 		else if (eol_attr == EOL_CRLF)
 			ca->crlf_action = CRLF_TEXT_CRLF;
+		ca->attr_action = ca->crlf_action;
 	} else {
 		ca->drv = NULL;
 		ca->crlf_action = CRLF_UNDEFINED;
diff --git a/t/t0027-auto-crlf.sh b/t/t0027-auto-crlf.sh
index fc4c628..f9c92c6 100755
--- a/t/t0027-auto-crlf.sh
+++ b/t/t0027-auto-crlf.sh
@@ -159,6 +159,39 @@ stats_ascii () {
 
 }
 
+attr_ascii () {
+	case "$1" in
+	"-text") echo "-text"	;;
+	lf)	echo "text eol=lf" ;;
+	crlf)	echo "text eol=crlf" ;;
+	text)
+		case "$2" in
+		"")	echo "text" ;;
+		lf)	echo "text eol=lf" ;;
+		crlf)	echo "text eol=crlf" ;;
+		*) echo invalid_attr2 "$2" ;;
+		esac
+		;;
+	auto)
+		case "$2" in
+		"")	echo "text=auto" ;;
+		lf)	echo "text=auto eol=lf" ;;
+		crlf)	echo "text=auto eol=crlf" ;;
+		*) echo invalid_attr2 "$2"	;;
+		esac
+		;;
+	"")
+		case "$2" in
+		"")	echo "" ;;
+		lf)	echo "text eol=lf" ;;
+		crlf)	echo "text eol=crlf" ;;
+		*) echo invalid_attr2 "$2" ;;
+		esac
+		;;
+	*)echo invalid_attr1 "$1"	;;
+	esac
+}
+
 check_files_in_repo () {
 	crlf=$1
 	attr=$2
@@ -228,15 +261,15 @@ checkout_files () {
 	test_expect_success "ls-files --eol attr=$attr $ident $aeol core.autocrlf=$crlf core.eol=$ceol" '
 		test_when_finished "rm expect actual" &&
 		sort <<-EOF >expect &&
-		i/crlf w/$(stats_ascii $crlfname) crlf_false_attr__CRLF.txt
-		i/mixed w/$(stats_ascii $lfmixcrlf) crlf_false_attr__CRLF_mix_LF.txt
-		i/lf w/$(stats_ascii $lfname) crlf_false_attr__LF.txt
-		i/-text w/$(stats_ascii $lfmixcr) crlf_false_attr__LF_mix_CR.txt
-		i/-text w/$(stats_ascii $crlfnul) crlf_false_attr__CRLF_nul.txt
-		i/-text w/$(stats_ascii $crlfnul) crlf_false_attr__LF_nul.txt
+		i/crlf w/$(stats_ascii $crlfname) attr/$(attr_ascii $attr $aeol) crlf_false_attr__CRLF.txt
+		i/mixed w/$(stats_ascii $lfmixcrlf) attr/$(attr_ascii $attr $aeol) crlf_false_attr__CRLF_mix_LF.txt
+		i/lf w/$(stats_ascii $lfname) attr/$(attr_ascii $attr $aeol) crlf_false_attr__LF.txt
+		i/-text w/$(stats_ascii $lfmixcr) attr/$(attr_ascii $attr $aeol) crlf_false_attr__LF_mix_CR.txt
+		i/-text w/$(stats_ascii $crlfnul) attr/$(attr_ascii $attr $aeol) crlf_false_attr__CRLF_nul.txt
+		i/-text w/$(stats_ascii $crlfnul) attr/$(attr_ascii $attr $aeol) crlf_false_attr__LF_nul.txt
 		EOF
 		git ls-files --eol crlf_false_attr__* |
-		sed -e "s!attr/[^	]*!!g" -e "s/	/ /g" -e "s/  */ /g" |
+		sed -e "s/	/ /g" -e "s/  */ /g" |
 		sort >actual &&
 		test_cmp expect actual
 	'
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* Re: [PATCH 1/1] convert.c: correct attr_action
  2016-02-22  5:11 ` [PATCH 1/1] convert.c: correct attr_action tboegi
@ 2016-02-22  5:34   ` Eric Sunshine
  2016-02-22  8:04   ` Junio C Hamano
  2016-02-22  8:20   ` Junio C Hamano
  2 siblings, 0 replies; 47+ messages in thread
From: Eric Sunshine @ 2016-02-22  5:34 UTC (permalink / raw)
  To: Torsten Bögershausen; +Cc: Git List

On Mon, Feb 22, 2016 at 12:11 AM,  <tboegi@web.de> wrote:
> Commit "convert.c: refactor crlf_action" unified the crlf_handling
> and introdused a bug for "git ls-files --eol".

s/introdused/introduced/

> The "text" attribute was shown as "text eol=lf" or "text eol=crlf",
> depending on core.autocrlf or core.eol.
> Correct this and add test cases in t0027.
>
> Signed-off-by: Torsten Bögershausen <tboegi@web.de>

^ permalink raw reply	[flat|nested] 47+ messages in thread

* Re: [PATCH 1/1] convert.c: correct attr_action
  2016-02-22  5:11 ` [PATCH 1/1] convert.c: correct attr_action tboegi
  2016-02-22  5:34   ` Eric Sunshine
@ 2016-02-22  8:04   ` Junio C Hamano
  2016-02-22  8:20   ` Junio C Hamano
  2 siblings, 0 replies; 47+ messages in thread
From: Junio C Hamano @ 2016-02-22  8:04 UTC (permalink / raw)
  To: tboegi; +Cc: git

tboegi@web.de writes:

> diff --git a/t/t0027-auto-crlf.sh b/t/t0027-auto-crlf.sh
> index fc4c628..f9c92c6 100755
> --- a/t/t0027-auto-crlf.sh
> +++ b/t/t0027-auto-crlf.sh
> @@ -159,6 +159,39 @@ stats_ascii () {
>  
>  }
>  
> +attr_ascii () {
> +	case "$1" in
> +	"-text") echo "-text"	;;

 - I do not think you need to quote the case label.

 - Why the excessive trailing whitespaces before double-semicolons?

> +	lf)	echo "text eol=lf" ;;
> +	crlf)	echo "text eol=crlf" ;;
> +	text)
> +		case "$2" in
> +		"")	echo "text" ;;
> +		lf)	echo "text eol=lf" ;;
> +		crlf)	echo "text eol=crlf" ;;
> +		*) echo invalid_attr2 "$2" ;;
> +		esac
> +		;;
> +	auto)
> +		case "$2" in
> +		"")	echo "text=auto" ;;
> +		lf)	echo "text=auto eol=lf" ;;
> +		crlf)	echo "text=auto eol=crlf" ;;
> +		*) echo invalid_attr2 "$2"	;;
> +		esac
> +		;;
> +	"")
> +		case "$2" in
> +		"")	echo "" ;;
> +		lf)	echo "text eol=lf" ;;
> +		crlf)	echo "text eol=crlf" ;;
> +		*) echo invalid_attr2 "$2" ;;
> +		esac
> +		;;

I wonder if the above is easier to read if written like this:

	case "$1,$2" in
        "-text,*")		echo "-text" ;;
        lf,*)   	        echo text eol=lf" ;;
	...
	auto,)			echo "text=auto" ;;
	auto,lf | auto,crlf)	echo "text=auto eol=$2" ;;
	auto,*)			echo invalid_attr2 "$2" ;;
	...
        esac

as $1 and $2 are not arbitrary words, but you know exactly from what
vocabulary they are taken.

^ permalink raw reply	[flat|nested] 47+ messages in thread

* Re: [PATCH 1/1] convert.c: correct attr_action
  2016-02-22  5:11 ` [PATCH 1/1] convert.c: correct attr_action tboegi
  2016-02-22  5:34   ` Eric Sunshine
  2016-02-22  8:04   ` Junio C Hamano
@ 2016-02-22  8:20   ` Junio C Hamano
  2016-02-23  5:26     ` Torsten Bögershausen
  2 siblings, 1 reply; 47+ messages in thread
From: Junio C Hamano @ 2016-02-22  8:20 UTC (permalink / raw)
  To: tboegi; +Cc: git

tboegi@web.de writes:

> diff --git a/convert.c b/convert.c
> index 18af685..0bc32ec 100644
> --- a/convert.c
> +++ b/convert.c
> @@ -708,7 +708,7 @@ static enum crlf_action git_path_check_crlf(struct git_attr_check *check)
>  	const char *value = check->value;
>  
>  	if (ATTR_TRUE(value))
> -		return text_eol_is_crlf() ? CRLF_TEXT_CRLF : CRLF_TEXT_INPUT;
> +		return CRLF_TEXT;
>  	else if (ATTR_FALSE(value))
>  		return CRLF_BINARY;
>  	else if (ATTR_UNSET(value))

Hmph, this function has exactly two callers, and they call it like
this:

	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
		enum eol eol_attr;
		ca->crlf_action = git_path_check_crlf(ccheck + 4);
		if (ca->crlf_action == CRLF_UNDEFINED)
			ca->crlf_action = git_path_check_crlf(ccheck + 0);
		ca->attr_action = ca->crlf_action;

where ccheck+0 refers to "crlf" and ccheck+4 refers to "text".

So, we say "first check 'text' attribute, and if it is true we say
CRLF_TEXT and stop."  We also say "first check 'text', and if it is
not there, the first call returns undef, in which case we check 'crlf'
attribute, and if it is true we say CRLF_TEXT".

And ca->attr_action retains this value.

However, immediately after this assignment to ca->attr_action, we
have this:

		ca->ident = git_path_check_ident(ccheck + 1);
		ca->drv = git_path_check_convert(ccheck + 2);
		if (ca->crlf_action == CRLF_BINARY)
			return;
		eol_attr = git_path_check_eol(ccheck + 3);
		if (eol_attr == EOL_LF)
			ca->crlf_action = CRLF_TEXT_INPUT;
		else if (eol_attr == EOL_CRLF)
			ca->crlf_action = CRLF_TEXT_CRLF;
		ca->attr_action = ca->crlf_action;

We check ident (ccheck+1) and filter (ccheck+2); if the value of
ca->crlf_action (which was determined by checking 'text' and then
'crlf') is not CRLF_BINARY, we further check eol (ccheck+3) and
update ca->crlf_action based on it.  And ca->attr_action gets
updated again.

This feels unnecessarily convoluted.  Perhaps if you get rid of the
early return for CRLF_BINARY, the flow may become a lot clearer,
i.e.

	ca->crlf_action = check 'text';
        if (ca->crlf_action == undef)
        	ca->crlf_action = check 'crlf';
	// DO NOT ASSIGN ca->attr_action HERE YET
        ca->ident = check 'ident';
        ca->drv = check 'filter';
        if (crlf_action != CRLF_BINARY) {
                eol_attr = check 'eol';
                if (eol == LF)
                        ca->crlf_action = ...
                else if (eol == EOL_CRLF)
                        ca->crlf_action = ...
	}
        ca->attr_action = ca->crlf_action;

Hmm?

^ permalink raw reply	[flat|nested] 47+ messages in thread

* Re: [PATCH 1/1] convert.c: correct attr_action
  2016-02-22  8:20   ` Junio C Hamano
@ 2016-02-23  5:26     ` Torsten Bögershausen
  2016-02-23 17:07       ` [PATCH v2 " tboegi
  0 siblings, 1 reply; 47+ messages in thread
From: Torsten Bögershausen @ 2016-02-23  5:26 UTC (permalink / raw)
  To: Junio C Hamano, tboegi; +Cc: git

On 02/22/2016 09:20 AM, Junio C Hamano wrote:
Thanks for all the comments,
I will send a new version the next days.

^ permalink raw reply	[flat|nested] 47+ messages in thread

* [PATCH v2 1/1] convert.c: correct attr_action
  2016-02-23  5:26     ` Torsten Bögershausen
@ 2016-02-23 17:07       ` tboegi
  2016-02-23 20:52         ` Junio C Hamano
  0 siblings, 1 reply; 47+ messages in thread
From: tboegi @ 2016-02-23 17:07 UTC (permalink / raw)
  To: git; +Cc: Torsten Bögershausen

From: Torsten Bögershausen <tboegi@web.de>

Commit "convert.c: refactor crlf_action" unified the crlf_handling
and introdused a bug for "git ls-files --eol".
The "text" attribute was shown as "text eol=lf" or "text eol=crlf",
depending on core.autpcrlf or core.eol.
Correct this and add test cases in t0027.

Signed-off-by: Torsten Bögershausen <tboegi@web.de>
---
 convert.c            | 18 +++++++++---------
 t/t0027-auto-crlf.sh | 33 ++++++++++++++++++++++++++-------
 2 files changed, 35 insertions(+), 16 deletions(-)

diff --git a/convert.c b/convert.c
index 18af685..d8b1f17 100644
--- a/convert.c
+++ b/convert.c
@@ -708,7 +708,7 @@ static enum crlf_action git_path_check_crlf(struct git_attr_check *check)
 	const char *value = check->value;
 
 	if (ATTR_TRUE(value))
-		return text_eol_is_crlf() ? CRLF_TEXT_CRLF : CRLF_TEXT_INPUT;
+		return CRLF_TEXT;
 	else if (ATTR_FALSE(value))
 		return CRLF_BINARY;
 	else if (ATTR_UNSET(value))
@@ -778,20 +778,20 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
 	}
 
 	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
-		enum eol eol_attr;
 		ca->crlf_action = git_path_check_crlf(ccheck + 4);
 		if (ca->crlf_action == CRLF_UNDEFINED)
 			ca->crlf_action = git_path_check_crlf(ccheck + 0);
 		ca->attr_action = ca->crlf_action;
 		ca->ident = git_path_check_ident(ccheck + 1);
 		ca->drv = git_path_check_convert(ccheck + 2);
-		if (ca->crlf_action == CRLF_BINARY)
-			return;
-		eol_attr = git_path_check_eol(ccheck + 3);
-		if (eol_attr == EOL_LF)
-			ca->crlf_action = CRLF_TEXT_INPUT;
-		else if (eol_attr == EOL_CRLF)
-			ca->crlf_action = CRLF_TEXT_CRLF;
+		if (ca->crlf_action != CRLF_BINARY) {
+			enum eol eol_attr = git_path_check_eol(ccheck + 3);
+			if (eol_attr == EOL_LF)
+				ca->crlf_action = CRLF_TEXT_INPUT;
+			else if (eol_attr == EOL_CRLF)
+				ca->crlf_action = CRLF_TEXT_CRLF;
+		}
+		ca->attr_action = ca->crlf_action;
 	} else {
 		ca->drv = NULL;
 		ca->crlf_action = CRLF_UNDEFINED;
diff --git a/t/t0027-auto-crlf.sh b/t/t0027-auto-crlf.sh
index fc4c628..f33962b 100755
--- a/t/t0027-auto-crlf.sh
+++ b/t/t0027-auto-crlf.sh
@@ -159,6 +159,25 @@ stats_ascii () {
 
 }
 
+
+# contruct the attr/ returned by git ls-files --eol
+# Take none (=empty), one or two args
+attr_ascii () {
+	case $1,$2 in
+	-text,*)   echo "-text" ;;
+	text,)     echo "text" ;;
+	text,lf)   echo "text eol=lf" ;;
+	text,crlf) echo "text eol=crlf" ;;
+	auto,)     echo "text=auto" ;;
+	auto,lf)   echo "text=auto eol=lf" ;;
+	auto,crlf) echo "text=auto eol=crlf" ;;
+	lf,)       echo "text eol=lf" ;;
+	crlf,)     echo "text eol=crlf" ;;
+	,) echo "" ;;
+	*) echo invalid_attr "$1,$2" ;;
+	esac
+}
+
 check_files_in_repo () {
 	crlf=$1
 	attr=$2
@@ -228,15 +247,15 @@ checkout_files () {
 	test_expect_success "ls-files --eol attr=$attr $ident $aeol core.autocrlf=$crlf core.eol=$ceol" '
 		test_when_finished "rm expect actual" &&
 		sort <<-EOF >expect &&
-		i/crlf w/$(stats_ascii $crlfname) crlf_false_attr__CRLF.txt
-		i/mixed w/$(stats_ascii $lfmixcrlf) crlf_false_attr__CRLF_mix_LF.txt
-		i/lf w/$(stats_ascii $lfname) crlf_false_attr__LF.txt
-		i/-text w/$(stats_ascii $lfmixcr) crlf_false_attr__LF_mix_CR.txt
-		i/-text w/$(stats_ascii $crlfnul) crlf_false_attr__CRLF_nul.txt
-		i/-text w/$(stats_ascii $crlfnul) crlf_false_attr__LF_nul.txt
+		i/crlf w/$(stats_ascii $crlfname) attr/$(attr_ascii $attr $aeol) crlf_false_attr__CRLF.txt
+		i/mixed w/$(stats_ascii $lfmixcrlf) attr/$(attr_ascii $attr $aeol) crlf_false_attr__CRLF_mix_LF.txt
+		i/lf w/$(stats_ascii $lfname) attr/$(attr_ascii $attr $aeol) crlf_false_attr__LF.txt
+		i/-text w/$(stats_ascii $lfmixcr) attr/$(attr_ascii $attr $aeol) crlf_false_attr__LF_mix_CR.txt
+		i/-text w/$(stats_ascii $crlfnul) attr/$(attr_ascii $attr $aeol) crlf_false_attr__CRLF_nul.txt
+		i/-text w/$(stats_ascii $crlfnul) attr/$(attr_ascii $attr $aeol) crlf_false_attr__LF_nul.txt
 		EOF
 		git ls-files --eol crlf_false_attr__* |
-		sed -e "s!attr/[^	]*!!g" -e "s/	/ /g" -e "s/  */ /g" |
+		sed -e "s/	/ /g" -e "s/  */ /g" |
 		sort >actual &&
 		test_cmp expect actual
 	'
-- 
2.7.0.303.g2c4f448.dirty

^ permalink raw reply related	[flat|nested] 47+ messages in thread

* Re: [PATCH v2 1/1] convert.c: correct attr_action
  2016-02-23 17:07       ` [PATCH v2 " tboegi
@ 2016-02-23 20:52         ` Junio C Hamano
  0 siblings, 0 replies; 47+ messages in thread
From: Junio C Hamano @ 2016-02-23 20:52 UTC (permalink / raw)
  To: tboegi; +Cc: git

tboegi@web.de writes:

> From: Torsten Bögershausen <tboegi@web.de>
>
> Commit "convert.c: refactor crlf_action" unified the crlf_handling
> and introdused a bug for "git ls-files --eol".
> The "text" attribute was shown as "text eol=lf" or "text eol=crlf",
> depending on core.autpcrlf or core.eol.
> Correct this and add test cases in t0027.

Sigh.  I think I typofixed this when I queued the previous version
while commenting on it.

Do people not pay attention to what is queued in 'pu' these days?

>
> Signed-off-by: Torsten Bögershausen <tboegi@web.de>
> ---
>  convert.c            | 18 +++++++++---------
>  t/t0027-auto-crlf.sh | 33 ++++++++++++++++++++++++++-------
>  2 files changed, 35 insertions(+), 16 deletions(-)

I looked at the interdiff from the previous version; the updated
parts looked sensible.

Thanks, will queue.

>
> diff --git a/convert.c b/convert.c
> index 18af685..d8b1f17 100644
> --- a/convert.c
> +++ b/convert.c
> @@ -708,7 +708,7 @@ static enum crlf_action git_path_check_crlf(struct git_attr_check *check)
>  	const char *value = check->value;
>  
>  	if (ATTR_TRUE(value))
> -		return text_eol_is_crlf() ? CRLF_TEXT_CRLF : CRLF_TEXT_INPUT;
> +		return CRLF_TEXT;
>  	else if (ATTR_FALSE(value))
>  		return CRLF_BINARY;
>  	else if (ATTR_UNSET(value))
> @@ -778,20 +778,20 @@ static void convert_attrs(struct conv_attrs *ca, const char *path)
>  	}
>  
>  	if (!git_check_attr(path, NUM_CONV_ATTRS, ccheck)) {
> -		enum eol eol_attr;
>  		ca->crlf_action = git_path_check_crlf(ccheck + 4);
>  		if (ca->crlf_action == CRLF_UNDEFINED)
>  			ca->crlf_action = git_path_check_crlf(ccheck + 0);
>  		ca->attr_action = ca->crlf_action;
>  		ca->ident = git_path_check_ident(ccheck + 1);
>  		ca->drv = git_path_check_convert(ccheck + 2);
> -		if (ca->crlf_action == CRLF_BINARY)
> -			return;
> -		eol_attr = git_path_check_eol(ccheck + 3);
> -		if (eol_attr == EOL_LF)
> -			ca->crlf_action = CRLF_TEXT_INPUT;
> -		else if (eol_attr == EOL_CRLF)
> -			ca->crlf_action = CRLF_TEXT_CRLF;
> +		if (ca->crlf_action != CRLF_BINARY) {
> +			enum eol eol_attr = git_path_check_eol(ccheck + 3);
> +			if (eol_attr == EOL_LF)
> +				ca->crlf_action = CRLF_TEXT_INPUT;
> +			else if (eol_attr == EOL_CRLF)
> +				ca->crlf_action = CRLF_TEXT_CRLF;
> +		}
> +		ca->attr_action = ca->crlf_action;
>  	} else {
>  		ca->drv = NULL;
>  		ca->crlf_action = CRLF_UNDEFINED;
> diff --git a/t/t0027-auto-crlf.sh b/t/t0027-auto-crlf.sh
> index fc4c628..f33962b 100755
> --- a/t/t0027-auto-crlf.sh
> +++ b/t/t0027-auto-crlf.sh
> @@ -159,6 +159,25 @@ stats_ascii () {
>  
>  }
>  
> +
> +# contruct the attr/ returned by git ls-files --eol
> +# Take none (=empty), one or two args
> +attr_ascii () {
> +	case $1,$2 in
> +	-text,*)   echo "-text" ;;
> +	text,)     echo "text" ;;
> +	text,lf)   echo "text eol=lf" ;;
> +	text,crlf) echo "text eol=crlf" ;;
> +	auto,)     echo "text=auto" ;;
> +	auto,lf)   echo "text=auto eol=lf" ;;
> +	auto,crlf) echo "text=auto eol=crlf" ;;
> +	lf,)       echo "text eol=lf" ;;
> +	crlf,)     echo "text eol=crlf" ;;
> +	,) echo "" ;;
> +	*) echo invalid_attr "$1,$2" ;;
> +	esac
> +}
> +
>  check_files_in_repo () {
>  	crlf=$1
>  	attr=$2
> @@ -228,15 +247,15 @@ checkout_files () {
>  	test_expect_success "ls-files --eol attr=$attr $ident $aeol core.autocrlf=$crlf core.eol=$ceol" '
>  		test_when_finished "rm expect actual" &&
>  		sort <<-EOF >expect &&
> -		i/crlf w/$(stats_ascii $crlfname) crlf_false_attr__CRLF.txt
> -		i/mixed w/$(stats_ascii $lfmixcrlf) crlf_false_attr__CRLF_mix_LF.txt
> -		i/lf w/$(stats_ascii $lfname) crlf_false_attr__LF.txt
> -		i/-text w/$(stats_ascii $lfmixcr) crlf_false_attr__LF_mix_CR.txt
> -		i/-text w/$(stats_ascii $crlfnul) crlf_false_attr__CRLF_nul.txt
> -		i/-text w/$(stats_ascii $crlfnul) crlf_false_attr__LF_nul.txt
> +		i/crlf w/$(stats_ascii $crlfname) attr/$(attr_ascii $attr $aeol) crlf_false_attr__CRLF.txt
> +		i/mixed w/$(stats_ascii $lfmixcrlf) attr/$(attr_ascii $attr $aeol) crlf_false_attr__CRLF_mix_LF.txt
> +		i/lf w/$(stats_ascii $lfname) attr/$(attr_ascii $attr $aeol) crlf_false_attr__LF.txt
> +		i/-text w/$(stats_ascii $lfmixcr) attr/$(attr_ascii $attr $aeol) crlf_false_attr__LF_mix_CR.txt
> +		i/-text w/$(stats_ascii $crlfnul) attr/$(attr_ascii $attr $aeol) crlf_false_attr__CRLF_nul.txt
> +		i/-text w/$(stats_ascii $crlfnul) attr/$(attr_ascii $attr $aeol) crlf_false_attr__LF_nul.txt
>  		EOF
>  		git ls-files --eol crlf_false_attr__* |
> -		sed -e "s!attr/[^	]*!!g" -e "s/	/ /g" -e "s/  */ /g" |
> +		sed -e "s/	/ /g" -e "s/  */ /g" |
>  		sort >actual &&
>  		test_cmp expect actual
>  	'

^ permalink raw reply	[flat|nested] 47+ messages in thread

end of thread, other threads:[~2016-02-23 20:52 UTC | newest]

Thread overview: 47+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
     [not found] <Message-Id=1453558101-6858-1-git-send-email-tboegi@web.de>
2016-01-24  7:55 ` [PATCH v2] t0027: Add tests for get_stream_filter() tboegi
2016-01-27  6:34   ` Junio C Hamano
2016-01-27  9:05     ` Torsten Bögershausen
2016-01-27 15:15 ` [PATCH v1 1/6] " tboegi
2016-02-02 16:53 ` tboegi
2016-02-02 21:18   ` Junio C Hamano
2016-02-02 16:53 ` [PATCH v1 2/6] convert.c: Remove path when not needed tboegi
2016-02-02 21:32   ` Junio C Hamano
2016-02-02 16:53 ` [PATCH v1 3/6] convert.c: Remove input_crlf_action() tboegi
2016-02-02 21:44   ` Junio C Hamano
2016-02-02 16:53 ` [PATCH v1 4/6] convert.c: Use text_eol_is_crlf() tboegi
2016-02-02 16:53 ` [PATCH v1 5/6] convert: auto_crlf=false and no attributes set: same as binary tboegi
2016-02-02 16:53 ` [PATCH v1 6/6] convert.c: Refactor crlf_action tboegi
2016-02-04 17:49 ` [PATCH v2 1/7] t0027: Add tests for get_stream_filter() tboegi
2016-02-04 19:52   ` Junio C Hamano
2016-02-04 17:49 ` [PATCH v2 2/7] convert.c: remove unused parameter 'path' tboegi
2016-02-04 17:49 ` [PATCH v2 3/7] convert.c: Remove input_crlf_action() tboegi
2016-02-04 17:49 ` [PATCH v2 4/7] convert.c: Use text_eol_is_crlf() tboegi
2016-02-04 20:13   ` Junio C Hamano
2016-02-04 17:49 ` [PATCH v2 5/7] convert: auto_crlf=false and no attributes set: same as binary tboegi
2016-02-04 17:49 ` [PATCH v2 6/7] convert.c: Refactor crlf_action tboegi
2016-02-04 17:50 ` [PATCH v2 7/7] convert.c: simplify text_stat tboegi
2016-02-04 20:37   ` Junio C Hamano
2016-02-05 16:13 ` [PATCH v3 1/7] t0027: Add tests for get_stream_filter() tboegi
2016-02-08 17:59   ` Junio C Hamano
2016-02-05 16:13 ` [PATCH v3 2/7] convert.c: remove unused parameter 'path' tboegi
2016-02-05 16:13 ` [PATCH v3 3/7] convert.c: Remove input_crlf_action() tboegi
2016-02-05 16:13 ` [PATCH v3 4/7] convert.c: use text_eol_is_crlf() tboegi
2016-02-05 16:13 ` [PATCH v3 5/7] convert: auto_crlf=false and no attributes set: same as binary tboegi
2016-02-08 18:27   ` Junio C Hamano
2016-02-09 14:34     ` Torsten Bögershausen
2016-02-09 18:06       ` Junio C Hamano
2016-02-05 16:13 ` [PATCH v3 6/7] convert.c: refactor crlf_action tboegi
2016-02-05 16:13 ` [PATCH v3 7/7] convert.c: simplify text_stat tboegi
2016-02-10 16:24 ` [PATCH v4 1/6] t0027: add tests for get_stream_filter() tboegi
2016-02-10 16:24 ` [PATCH v4 2/6] convert.c: remove unused parameter 'path' tboegi
2016-02-10 16:24 ` [PATCH v4 3/6] convert.c: remove input_crlf_action() tboegi
2016-02-10 16:24 ` [PATCH v4 4/6] convert.c: use text_eol_is_crlf() tboegi
2016-02-10 16:24 ` [PATCH v4 5/6] convert.c: refactor crlf_action tboegi
2016-02-10 16:24 ` [PATCH v4 6/6] convert.c: simplify text_stat tboegi
2016-02-22  5:11 ` [PATCH 1/1] convert.c: correct attr_action tboegi
2016-02-22  5:34   ` Eric Sunshine
2016-02-22  8:04   ` Junio C Hamano
2016-02-22  8:20   ` Junio C Hamano
2016-02-23  5:26     ` Torsten Bögershausen
2016-02-23 17:07       ` [PATCH v2 " tboegi
2016-02-23 20:52         ` Junio C Hamano

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.