(CommandList
  children: [
    (Assignment
      keyword: Assign_None
      pairs: [
        (assign_pair
          lhs: (LhsName name:test_description)
          op: Equal
          rhs: {(SQ <'per path merge controlled by merge attribute'>)}
          spids: [13]
        )
      ]
      spids: [13]
    )
    (C {(.)} {(./test-lib.sh)})
    (C {(test_expect_success)} {(setup)} 
      {
        (SQ <'\n'> <'\n'> <'\tfor f in text binary union\n'> <'\tdo\n'> 
          <'\t\techo Initial >$f && git add $f || return 1\n'> <'\tdone &&\n'> <'\ttest_tick &&\n'> <'\tgit commit -m Initial &&\n'> <'\n'> <'\tgit branch side &&\n'> 
          <'\tfor f in text binary union\n'> <'\tdo\n'> <'\t\techo Master >>$f && git add $f || return 1\n'> <'\tdone &&\n'> <'\ttest_tick &&\n'> 
          <'\tgit commit -m Master &&\n'> <'\n'> <'\tgit checkout side &&\n'> <'\tfor f in text binary union\n'> <'\tdo\n'> 
          <'\t\techo Side >>$f && git add $f || return 1\n'> <'\tdone &&\n'> <'\ttest_tick &&\n'> <'\tgit commit -m Side &&\n'> <'\n'> <'\tgit tag anchor\n'>
        )
      }
    )
    (C {(test_expect_success)} {(merge)} 
      {
        (SQ <'\n'> <'\n'> <'\t{\n'> <'\t\techo "binary -merge"\n'> <'\t\techo "union merge=union"\n'> 
          <'\t} >.gitattributes &&\n'> <'\n'> <'\tif git merge master\n'> <'\tthen\n'> <'\t\techo Gaah, should have conflicted\n'> 
          <'\t\tfalse\n'> <'\telse\n'> <'\t\techo Ok, conflicted.\n'> <'\tfi\n'>
        )
      }
    )
    (C {(test_expect_success)} {(SQ <'check merge result in index'>)} 
      {
        (SQ <'\n'> <'\n'> <'\tgit ls-files -u | grep binary &&\n'> 
          <'\tgit ls-files -u | grep text &&\n'> <'\t! (git ls-files -u | grep union)\n'> <'\n'>
        )
      }
    )
    (C {(test_expect_success)} {(SQ <'check merge result in working tree'>)} 
      {
        (SQ <'\n'> <'\n'> <'\tgit cat-file -p HEAD:binary >binary-orig &&\n'> 
          <'\tgrep "<<<<<<<" text &&\n'> <'\tcmp binary-orig binary &&\n'> <'\t! grep "<<<<<<<" union &&\n'> <'\tgrep Master union &&\n'> 
          <'\tgrep Side union\n'> <'\n'>
        )
      }
    )
    (C {(test_expect_success)} {(SQ <'retry the merge with longer context'>)} 
      {
        (SQ <'\n'> <'\techo text conflict-marker-size=32 >>.gitattributes &&\n'> 
          <'\tgit checkout -m text &&\n'> <'\tsed -ne "/^\\([<=>]\\)\\1\\1\\1*/{\n'> <'\t\ts/ .*$//\n'> <'\t\tp\n'> <'\t}" >actual text &&\n'> 
          <'\tgrep ">>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>" actual &&\n'> <'\tgrep "================================" actual &&\n'> 
          <'\tgrep "<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<" actual\n'>
        )
      }
    )
    (SimpleCommand
      words: [{(cat)}]
      redirects: [
        (Redir op_id:Redir_Great fd:16777215 arg_word:{(./custom-merge)} spids:[137])
        (HereDoc
          op_id: Redir_DLess
          fd: 16777215
          body: 
            {('#!/bin/sh\n') ('\n') ('orig="$1" ours="$2" theirs="$3" exit="$4" path=$5\n') ('(\n') 
              ('\techo "orig is $orig"\n') ('\techo "ours is $ours"\n') ('\techo "theirs is $theirs"\n') ('\techo "path is $path"\n') 
              ('\techo "=== orig ==="\n') ('\tcat "$orig"\n') ('\techo "=== ours ==="\n') ('\tcat "$ours"\n') ('\techo "=== theirs ==="\n') 
              ('\tcat "$theirs"\n') (') >"$ours+"\n') ('cat "$ours+" >"$ours"\n') ('rm -f "$ours+"\n') ('exit "$exit"\n')
            }
          do_expansion: False
          here_end: EOF
          was_filled: True
          spids: [140]
        )
      ]
    )
    (C {(chmod)} {(Lit_Other '+') (x)} {(./custom-merge)})
    (C {(test_expect_success)} {(SQ <'custom merge backend'>)} 
      {
        (SQ <'\n'> <'\n'> <'\techo "* merge=union" >.gitattributes &&\n'> 
          <'\techo "text merge=custom" >>.gitattributes &&\n'> <'\n'> <'\tgit reset --hard anchor &&\n'> <'\tgit config --replace-all \\\n'> 
          <'\tmerge.custom.driver "./custom-merge %O %A %B 0 %P" &&\n'> <'\tgit config --replace-all \\\n'> <'\tmerge.custom.name "custom merge driver for testing" &&\n'> 
          <'\n'> <'\tgit merge master &&\n'> <'\n'> <'\tcmp binary union &&\n'> <'\tsed -e 1,3d text >check-1 &&\n'> 
          <'\to=$(git unpack-file master^:text) &&\n'> <'\ta=$(git unpack-file side^:text) &&\n'> <'\tb=$(git unpack-file master:text) &&\n'> 
          <'\tsh -c "./custom-merge $o $a $b 0 '>
        ) (text) 
        (SQ <'" &&\n'> <'\tsed -e 1,3d $a >check-2 &&\n'> <'\tcmp check-1 check-2 &&\n'> 
          <'\trm -f $o $a $b\n'>
        )
      }
    )
    (C {(test_expect_success)} {(SQ <'custom merge backend'>)} 
      {
        (SQ <'\n'> <'\n'> <'\tgit reset --hard anchor &&\n'> <'\tgit config --replace-all \\\n'> 
          <'\tmerge.custom.driver "./custom-merge %O %A %B 1 %P" &&\n'> <'\tgit config --replace-all \\\n'> <'\tmerge.custom.name "custom merge driver for testing" &&\n'> 
          <'\n'> <'\tif git merge master\n'> <'\tthen\n'> <'\t\techo "Eh? should have conflicted"\n'> <'\t\tfalse\n'> 
          <'\telse\n'> <'\t\techo "Ok, conflicted"\n'> <'\tfi &&\n'> <'\n'> <'\tcmp binary union &&\n'> 
          <'\tsed -e 1,3d text >check-1 &&\n'> <'\to=$(git unpack-file master^:text) &&\n'> <'\ta=$(git unpack-file anchor:text) &&\n'> 
          <'\tb=$(git unpack-file master:text) &&\n'> <'\tsh -c "./custom-merge $o $a $b 0 '>
        ) (text) 
        (SQ <'" &&\n'> <'\tsed -e 1,3d $a >check-2 &&\n'> <'\tcmp check-1 check-2 &&\n'> 
          <'\tsed -e 1,3d -e 4q $a >check-3 &&\n'> <'\techo "path is text" >expect &&\n'> <'\tcmp expect check-3 &&\n'> <'\trm -f $o $a $b\n'>
        )
      }
    )
    (C {(test_expect_success)} {(SQ <'up-to-date merge without common ancestor'>)} 
      {
        (SQ <'\n'> <'\ttest_create_repo repo1 &&\n'> <'\ttest_create_repo repo2 &&\n'> 
          <'\ttest_tick &&\n'> <'\t(\n'> <'\t\tcd repo1 &&\n'> <'\t\t>a &&\n'> <'\t\tgit add a &&\n'> <'\t\tgit commit -m initial\n'> 
          <'\t) &&\n'> <'\ttest_tick &&\n'> <'\t(\n'> <'\t\tcd repo2 &&\n'> <'\t\tgit commit --allow-empty -m initial\n'> 
          <'\t) &&\n'> <'\ttest_tick &&\n'> <'\t(\n'> <'\t\tcd repo1 &&\n'> <'\t\tgit fetch ../repo2 master &&\n'> 
          <'\t\tgit merge --allow-unrelated-histories FETCH_HEAD\n'> <'\t)\n'>
        )
      }
    )
    (C {(test_expect_success)} {(SQ <'custom merge does not lock index'>)} 
      {
        (SQ <'\n'> <'\tgit reset --hard anchor &&\n'> 
          <'\twrite_script sleep-one-second.sh <<-\\EOF &&\n'> <'\t\tsleep 1 &\n'> <'\t\techo $! >sleep.pid\n'> <'\tEOF\n'> 
          <'\ttest_when_finished "kill \\$(cat sleep.pid)" &&\n'> <'\n'> <'\ttest_write_lines >.gitattributes \\\n'> 
          <'\t\t"* merge=ours" "text merge=sleep-one-second" &&\n'> <'\ttest_config merge.ours.driver true &&\n'> 
          <'\ttest_config merge.sleep-one-second.driver ./sleep-one-second.sh &&\n'> <'\tgit merge master\n'>
        )
      }
    )
    (C {(test_done)})
  ]
)