Recent changes to this wiki:

devblog
diff --git a/doc/devblog/day_581__starting_import_from_S3.mdwn b/doc/devblog/day_581__starting_import_from_S3.mdwn
new file mode 100644
index 000000000..a9682bd0d
--- /dev/null
+++ b/doc/devblog/day_581__starting_import_from_S3.mdwn
@@ -0,0 +1,27 @@
+Started today on `git annex import` from S3, in the "import-from-s3"
+branch.
+
+It looks like I'm going to support both versioned and unversioned buckets;
+the latter will need --force to initialize since it can lose data. 
+
+One thought I had about that is: It's probably better for git-annex to be
+able to import data from an unversioned S3 bucket with caveats about
+avoiding unsafe operations (export) that could lose data, than it is for
+git-annex to not be able to import from the bucket at all, guaranteeing
+that past versions of modified files will be lost. (Rationalization is a
+powerful drug.)
+
+To support unversioned buckets, some kind of stable content identifier is
+needed other than the S3 version id. Luckily, S3 has etags, which are
+md5sum of the content, so will work great. But, the `aws` haskell library
+needs one small change to return an etag, so this will be
+blocked on that change.
+
+I've gotten listing importable contents from S3 working for unversioned
+buckets, including dealing with S3's 1000 item limit by paging.
+Listing importable contents from versioned buckets is harder, because
+it needs to synthesize a git version history from the information that S3
+provides. I think I have a method for doing this that will generate the
+trees that users will expect to see, and also will generate the same past
+trees every time, avoiding a proliferation of git trees. Next step: 
+Converting my prose description of how to do that into haskell.

removed
diff --git a/doc/forum/git_annex_hanging_in_smudge_on_2k_file_on_rpi/comment_4_a22bbccec641864ddbd23128d5630f7d._comment b/doc/forum/git_annex_hanging_in_smudge_on_2k_file_on_rpi/comment_4_a22bbccec641864ddbd23128d5630f7d._comment
deleted file mode 100644
index 755d09596..000000000
--- a/doc/forum/git_annex_hanging_in_smudge_on_2k_file_on_rpi/comment_4_a22bbccec641864ddbd23128d5630f7d._comment
+++ /dev/null
@@ -1,9 +0,0 @@
-[[!comment format=mdwn
- username="maryjil2596"
- avatar="http://cdn.libravatar.org/avatar/2ce6b78d907f10b244c92330a4f0bd00"
- subject="samsung printer error code u1-2320"
- date="2019-04-18T10:10:14Z"
- content="""
-Those who are facing an issue with their Samsung printer follow this link <a href=\"https://errorcode0x.com/fixed-samsung-printer-error-code-u1-2320/\">samsung printer error code u1-2320</a> and immediately eliminate all the technical errors.
-
-"""]]

Added a comment: samsung printer error code u1-2320
diff --git a/doc/forum/git_annex_hanging_in_smudge_on_2k_file_on_rpi/comment_4_a22bbccec641864ddbd23128d5630f7d._comment b/doc/forum/git_annex_hanging_in_smudge_on_2k_file_on_rpi/comment_4_a22bbccec641864ddbd23128d5630f7d._comment
new file mode 100644
index 000000000..755d09596
--- /dev/null
+++ b/doc/forum/git_annex_hanging_in_smudge_on_2k_file_on_rpi/comment_4_a22bbccec641864ddbd23128d5630f7d._comment
@@ -0,0 +1,9 @@
+[[!comment format=mdwn
+ username="maryjil2596"
+ avatar="http://cdn.libravatar.org/avatar/2ce6b78d907f10b244c92330a4f0bd00"
+ subject="samsung printer error code u1-2320"
+ date="2019-04-18T10:10:14Z"
+ content="""
+Those who are facing an issue with their Samsung printer follow this link <a href=\"https://errorcode0x.com/fixed-samsung-printer-error-code-u1-2320/\">samsung printer error code u1-2320</a> and immediately eliminate all the technical errors.
+
+"""]]

Added a comment: Unusual behavior
diff --git a/doc/forum/Added_file_to_annex_but_it_doesn__39__t_show_up_in_here/comment_1_6757bfdc2876b5b763c338ad414e74dc._comment b/doc/forum/Added_file_to_annex_but_it_doesn__39__t_show_up_in_here/comment_1_6757bfdc2876b5b763c338ad414e74dc._comment
new file mode 100644
index 000000000..5ddcce813
--- /dev/null
+++ b/doc/forum/Added_file_to_annex_but_it_doesn__39__t_show_up_in_here/comment_1_6757bfdc2876b5b763c338ad414e74dc._comment
@@ -0,0 +1,38 @@
+[[!comment format=mdwn
+ username="jasonb@ab4484d9961a46440958fa1a528e0fc435599057"
+ nickname="jasonb"
+ avatar="http://cdn.libravatar.org/avatar/c7330f4da122c671b935fc1d58bb02b1"
+ subject="Unusual behavior"
+ date="2019-04-18T01:36:04Z"
+ content="""
+So I ran:
+
+```
+git annex --numcopies=0 dropunused 1-2
+dropunused 1 ok
+dropunused 2 ok
+(recording state in git...)
+```
+
+Which is fine, then:
+
+```
+cat Harry\ Brown\ \(2009\)\ 1080p.mp4
+/annex/objects/WORM-s2046008512-m1537755616--Harry,32Brown,32,402009,41,321080p.mp4
+```
+
+And that is strange.
+
+```
+$ rm Harry\ Brown\ \(2009\)\ 1080p.mp4
+override r--r--r--  jasonb/staff for Harry Brown (2009) 1080p.mp4? y
+$ cp -a ~/Downloads/Harry\ Brown\ \(2009\)\ 1080p.mp4 .
+$ git annex add Harry\ Brown\ \(2009\)\ 1080p.mp4
+add Harry Brown (2009) 1080p.mp4 ok
+(recording state in git...)
+$ ls -l Harry\ Brown\ \(2009\)\ 1080p.mp4
+lrwxr-xr-x  1 jasonb  staff  162 Apr 17 21:24 Harry Brown (2009) 1080p.mp4 -> .git/annex/objects/XV/Wx/WORM-s2046008512-m1555550686--Harry,32Brown,32,402009,41,321080p.mp4/WORM-s2046008512-m1555550686--Harry,32Brown,32,402009,41,321080p.mp4
+```
+
+And that's what I expected. I'm lost as to what happened.
+"""]]

diff --git a/doc/forum/Added_file_to_annex_but_it_doesn__39__t_show_up_in_here.mdwn b/doc/forum/Added_file_to_annex_but_it_doesn__39__t_show_up_in_here.mdwn
new file mode 100644
index 000000000..03dcf5a8f
--- /dev/null
+++ b/doc/forum/Added_file_to_annex_but_it_doesn__39__t_show_up_in_here.mdwn
@@ -0,0 +1,75 @@
+I recently added a file and for some reason it doesn't show up as being available locally, but I just added it.
+
+```
+find .git/annex | grep -i harry
+.git/annex/objects/f1/36/WORM-s2046008512-m1537755616--Harry,32Brown,32,402009,41,321080p.mp4
+.git/annex/objects/f1/36/WORM-s2046008512-m1537755616--Harry,32Brown,32,402009,41,321080p.mp4/WORM-s2046008512-m1537755616--Harry,32Brown,32,402009,41,321080p.mp4
+```
+
+```
+git annex find --in here --debug
+[2019-04-16 17:45:49.540555] read: git ["--git-dir=.git","--work-tree=.","--literal-pathspecs","symbolic-ref","-q","HEAD"]
+[2019-04-16 17:45:49.5474] process done ExitSuccess
+[2019-04-16 17:45:49.547482] read: git ["--git-dir=.git","--work-tree=.","--literal-pathspecs","show-ref","refs/heads/master"]
+[2019-04-16 17:45:49.557155] process done ExitSuccess
+[2019-04-16 17:45:49.557621] read: git ["--git-dir=.git","--work-tree=.","--literal-pathspecs","ls-files","--cached","-z","--"]
+[2019-04-16 17:45:49.565683] read: git ["--git-dir=.git","--work-tree=.","--literal-pathspecs","show-ref","git-annex"]
+[2019-04-16 17:45:49.571062] process done ExitSuccess
+[2019-04-16 17:45:49.571143] read: git ["--git-dir=.git","--work-tree=.","--literal-pathspecs","show-ref","--hash","refs/heads/git-annex"]
+[2019-04-16 17:45:49.576242] process done ExitSuccess
+[2019-04-16 17:45:49.577407] read: git ["--git-dir=.git","--work-tree=.","--literal-pathspecs","log","refs/heads/git-annex..739c33e04bd4d714eff432f630d1dcbb69625d6a","--pretty=%H","-n1"]
+[2019-04-16 17:45:49.584986] process done ExitSuccess
+[2019-04-16 17:45:49.585072] read: git ["--git-dir=.git","--work-tree=.","--literal-pathspecs","log","refs/heads/git-annex..404abbb2b903597ee753eba0f9213125d41a31f6","--pretty=%H","-n1"]
+[2019-04-16 17:45:49.591936] process done ExitSuccess
+[2019-04-16 17:45:49.636082] chat: git ["--git-dir=.git","--work-tree=.","--literal-pathspecs","cat-file","--batch"]
+[2019-04-16 17:45:49.638359] chat: git ["--git-dir=.git","--work-tree=.","--literal-pathspecs","cat-file","--batch-check=%(objectname) %(objecttype) %(objectsize)"]
+[2019-04-16 17:45:49.643613] read: git ["config","--null","--list"]
+[2019-04-16 17:45:49.727427] process done ExitSuccess
+[2019-04-16 17:45:49.727735] process done ExitSuccess
+```
+
+In the past, adding the file always resulted in behavior that made sense. I'm at a loss as to what to do. If I try to add it again, nothing happens. I can't copy it to another remote; it's like it doesn't actually exist.
+
+
+```
+git annex version
+git-annex version: 7.20190220-g1812ec5da
+build flags: Assistant Webapp Pairing S3(multipartupload)(storageclasses) WebDAV FsEvents TorrentParser MagicMime Feeds Testsuite
+dependency versions: aws-0.21.1 bloomfilter-2.0.1.0 cryptonite-0.25 DAV-1.3.3 feed-1.0.1.0 ghc-8.6.3 http-client-0.5.14 persistent-sqlite-2.9.2 torrent-10000.1.1 uuid-1.3.13 yesod-1.6.0
+key/value backends: SHA256E SHA256 SHA512E SHA512 SHA224E SHA224 SHA384E SHA384 SHA3_256E SHA3_256 SHA3_512E SHA3_512 SHA3_224E SHA3_224 SHA3_384E SHA3_384 SKEIN256E SKEIN256 SKEIN512E SKEIN512 BLAKE2B256E BLAKE2B256 BLAKE2B512E BLAKE2B512 BLAKE2B160E BLAKE2B160 BLAKE2B224E BLAKE2B224 BLAKE2B384E BLAKE2B384 BLAKE2S256E BLAKE2S256 BLAKE2S160E BLAKE2S160 BLAKE2S224E BLAKE2S224 BLAKE2SP256E BLAKE2SP256 BLAKE2SP224E BLAKE2SP224 SHA1E SHA1 MD5E MD5 WORM URL
+remote types: git gcrypt p2p S3 bup directory rsync web bittorrent webdav adb tahoe glacier ddar hook external
+operating system: darwin x86_64
+supported repository versions: 5 7
+upgrade supported from repository versions: 0 1 2 3 4 5 6
+
+cat .gitattributes
+* annex.largefiles=(largerthan=500kb)
+* annex.backend=WORM
+
+cat .git/config
+[core]
+	repositoryformatversion = 0
+	filemode = true
+	bare = false
+	logallrefupdates = true
+	ignorecase = true
+	precomposeunicode = true
+[annex]
+	thin = true
+	uuid = UUID
+	version = 5
+	direct = false
+[filter "annex"]
+	smudge = git-annex smudge %f
+	clean = git-annex smudge --clean %f
+[remote "WD-1TB-USB"]
+	url = /Volumes/WD-1TB-USB/repos/film
+	fetch = +refs/heads/*:refs/remotes/WD-1TB-USB/*
+	annex-uuid = UUID
+[remote "quorra"]
+	url = 192.168.70.10:/home/jasonb/repos/film
+	fetch = +refs/heads/*:refs/remotes/quorra/*
+	annex-uuid = UUID
+	#annex-rsync-transport = ssh -c blowfish
+	annex-ssh-options = -c aes128-gcm@openssh.com
+```

hmm
diff --git a/doc/todo/support_multiple_special_remotes_with_same_uuid/comment_1_620388b7ef3ebcc1f9228533f07a1f86._comment b/doc/todo/support_multiple_special_remotes_with_same_uuid/comment_1_620388b7ef3ebcc1f9228533f07a1f86._comment
new file mode 100644
index 000000000..209935ec2
--- /dev/null
+++ b/doc/todo/support_multiple_special_remotes_with_same_uuid/comment_1_620388b7ef3ebcc1f9228533f07a1f86._comment
@@ -0,0 +1,23 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 1"""
+ date="2019-04-16T17:09:39Z"
+ content="""
+Dug a little into implementing this.
+
+One problem is that things like `git annex dead` look up a name
+in the remote list, and then use the uuid of the returned remote. 
+But if remote foo has sameas=bar-uuid, then the remote in the remote
+list that it looks up will have that uuid, and so the uuid that will
+be marked as dead is almost certianly not the one that the user expected.
+
+And the user can't pass the masked uuid of the sameas remote to `git-annex
+dead`, because there will be no remote in the list with that uuid.
+
+And for that matter, the user is not likely to know the masked uuid,
+because things like `git annex info` won't display it..
+
+Another gotcha is that the user might make remote B with sameas=A-uuid,
+and remote C with sameas=B-uuid. Which really needs to resolve to A-uuid,
+so it needs to do multiple lookups, but then a sameas loop becomes a problem.
+"""]]

split out section on common configuration parameters
diff --git a/doc/git-annex-initremote.mdwn b/doc/git-annex-initremote.mdwn
index 62b910d9c..13471cccc 100644
--- a/doc/git-annex-initremote.mdwn
+++ b/doc/git-annex-initremote.mdwn
@@ -19,36 +19,20 @@ For a list and details, see <https://git-annex.branchable.com/special_remotes/>
  
 The remote's configuration is specified by the parameters passed
 to this command. Different types of special remotes need different
-configuration values. The command will prompt for parameters as needed.
-
-All special remotes support encryption. You can specify
-`encryption=none` to disable encryption, or specify
-`encryption=hybrid keyid=$keyid ...` to specify a GPG key id (or an email
-address associated with a key). For details about ways to configure
-encryption, see <https://git-annex.branchable.com/encryption/>
+configuration values. The command will prompt for parameters as needed. A
+few parameters that are supported by all special remotes are documented in
+the next section below.
 
 Once a special remote has been initialized once with this command,
 other clones of the repository can also be set up to access it using
 `git annex enableremote`.
 
-To avoid `git annex enableremote` needing to be run,
-you can pass "autoenable=true". Then when [[git-annex-init]](1)
-is run in a new clone, it will attempt to enable the special remote. Of
-course, this works best when the special remote does not need anything
-special to be done to get it enabled.
-
 The name you provide for the remote can't be one that's been used for any
 other special remote before, because `git-annex enableremote` uses the name
 to identify which special remote to enable. If some old special remote
 that's no longer used has taken the name you want to reuse, you might
 want to use `git annex renameremote`.
 
-Normally, git-annex generates a new UUID for the new special remote.
-If you want to, you can specify a UUID for it to use, by passing a
-uuid=whatever parameter. This can be useful in some situations, eg when the
-same data can be accessed via two different remote backends.
-But if in doubt, don't do this.
-
 # OPTIONS
 
 * `--fast`
@@ -59,6 +43,36 @@ But if in doubt, don't do this.
   and re-run with `--fast`, which causes it to use a lower-quality source of
   randomness. (Ie, /dev/urandom instead of /dev/random)
 
+# COMMON CONFIGURATION PARAMETERS
+
+* `encryption`
+
+  All special remotes support encryption. You will need to specify
+  what encryption, if any, to use. 
+
+  If you do not want any encryption, use `encryption=none`
+
+  To encrypt to a GPG key, use `encryption=hybrid keyid=$keyid ...`
+  and fill in the GPG key id (or an email address associated with a GPG key).
+  
+  For details about this and other encrpytion settings, see
+  <https://git-annex.branchable.com/encryption/>
+
+* `autoenable`
+
+  To avoid `git annex enableremote` needing to be run,
+  you can pass "autoenable=true". Then when [[git-annex-init]](1)
+  is run in a new clone, it will attempt to enable the special remote. Of
+  course, this works best when the special remote does not need anything
+  special to be done to get it enabled.
+
+* `uuid`
+
+  Normally, git-annex initremote generates a new UUID for the new special
+  remote. If you want to, you can specify a UUID for it to use, by passing a
+  uuid=whatever parameter. This can be useful in some unusual situations.
+  But if in doubt, don't do this.
+
 # SEE ALSO
 
 [[git-annex]](1)

forgot to add man page
diff --git a/doc/git-annex-renameremote.mdwn b/doc/git-annex-renameremote.mdwn
new file mode 100644
index 000000000..13d2a007b
--- /dev/null
+++ b/doc/git-annex-renameremote.mdwn
@@ -0,0 +1,41 @@
+# NAME
+
+git-annex renameremote - changes name of a special remote
+
+# SYNOPSIS
+
+git annex renameremote `name|uuid|desc newname`
+
+# DESCRIPTION
+
+Changes the name that is used to enable a special remote.
+
+Normally the current name is used to identify the special remote, 
+but its uuid or description can also be used.
+
+This is especially useful when an old special remote used a name, and now you
+want to use that name for a new special remote. `git annex initremote`
+won't let you create a remote with a conflicting name, so rename the old
+remote first.
+
+	git annex renameremote phone lost-phone
+	git annex initremote phone ...
+
+This only updates the name that git-annex has stored for use 
+by `git annex enableremote`. It does not update the git config stanza
+for the special remote to use the new name, but of course you can edit
+the git config if you want to rename it there.
+
+# SEE ALSO
+
+[[git-annex]](1)
+
+[[git-annex-initremote]](1)
+
+[[git-annex-enableremote]](1)
+
+# AUTHOR
+
+Joey Hess <id@joeyh.name>
+
+Warning: Automatically converted into a man page by mdwn2man. Edit with care.

Added a comment
diff --git a/doc/forum/Recommended_way_to_work_with_semi-permanent_filename_changes/comment_2_47b248b36146c5ad9986b69c8d212b4e._comment b/doc/forum/Recommended_way_to_work_with_semi-permanent_filename_changes/comment_2_47b248b36146c5ad9986b69c8d212b4e._comment
new file mode 100644
index 000000000..e9713bb32
--- /dev/null
+++ b/doc/forum/Recommended_way_to_work_with_semi-permanent_filename_changes/comment_2_47b248b36146c5ad9986b69c8d212b4e._comment
@@ -0,0 +1,21 @@
+[[!comment format=mdwn
+ username="strmd"
+ avatar="http://cdn.libravatar.org/avatar/035707b9756129bbdea6b36a7f7b38d3"
+ subject="comment 2"
+ date="2019-04-16T15:12:57Z"
+ content="""
+Thanks for your reply.
+
+One example is when working with scanned images and digitized sound recordings:
+
+The original file names [`unmodified`] are needed to source which analog original they are paired with in an archival system beyond my control, but as I manually work with these files, the structure changes to [`modified`], which I'd like to be the repo's default state. So when new data arrives (via a remote) new files should be checked into the [`unmodified`] state with their original file names, and then be worked on in the [`modified`] state. I'd like this [`unmodified`] state to be singular, as opposed to checking out a specific commit for a specific subset of files.
+
+Another, perhaps simpler, example is music files:
+They come in various combinations of file and folder names as they are ripped from CD or downloaded. I'd like an external program (beets) to handle organizing these files (the symlinks, really) into a folder structure, as I need them to be presented in a particular way to an indexer/player, i.e. as [`modified`]. So again, I'd like to ingest (from a remote) into git-annex using the original file names (if needed at a later point) while still letting beets move things around structurally. At some point in time, I'd like to be able to easily hop back to my music library in its [`unmodified`] state without having to find the particular point in time when I added that particular subset.
+
+I'm trying to achieve this with as little manual massaging as possible.
+
+Metadata and views are a great option to have, but from what I understand not the right fit here.
+
+This was long but I hope it made some sense.
+"""]]

Added a comment
diff --git a/doc/forum/Recommended_way_to_work_with_semi-permanent_filename_changes/comment_1_ec1c86e41ce3ee243df9a5008db87070._comment b/doc/forum/Recommended_way_to_work_with_semi-permanent_filename_changes/comment_1_ec1c86e41ce3ee243df9a5008db87070._comment
new file mode 100644
index 000000000..decd65cd1
--- /dev/null
+++ b/doc/forum/Recommended_way_to_work_with_semi-permanent_filename_changes/comment_1_ec1c86e41ce3ee243df9a5008db87070._comment
@@ -0,0 +1,10 @@
+[[!comment format=mdwn
+ username="CandyAngel"
+ avatar="http://cdn.libravatar.org/avatar/15c0aade8bec5bf004f939dd73cf9ed8"
+ subject="comment 1"
+ date="2019-04-16T13:10:03Z"
+ content="""
+Depends on how often and what \"work\" is done with the original filenames. Can you explain more what you are trying to do?
+
+Perhaps you can use metadata/metadata views.. though this would give you the original filename as a directory, containing a file with the current filename. e.g. ~/annex/originalfilename.txt/currentfilename.txt
+"""]]

diff --git a/doc/forum/Recommended_way_to_work_with_semi-permanent_filename_changes.mdwn b/doc/forum/Recommended_way_to_work_with_semi-permanent_filename_changes.mdwn
new file mode 100644
index 000000000..f6aebafd6
--- /dev/null
+++ b/doc/forum/Recommended_way_to_work_with_semi-permanent_filename_changes.mdwn
@@ -0,0 +1,8 @@
+Hi,
+I'm still wrapping my head around various aspects of the relationship between git and git-annex in everyday use.
+
+I have a set of files whose original filenames I want to keep, but only very rarely work with. That is, the everyday, "normal" use for these files will happen with the filenames changed. I want to have the watcher running in this repository, handling syncing with remotes, changes in filenames and directory structure etc.
+
+How would you set this up? A shared clone (not sure I fully get how that works), a separate branch for the original filenames that is checked out when needed (i.e. everyday changes are committed to master) or something else?
+
+Many thanks!  

Added a comment: Thanks
diff --git a/doc/forum/copy_symlinks/comment_2_198f3e9db08ebcdb7ec36b76cc1d9473._comment b/doc/forum/copy_symlinks/comment_2_198f3e9db08ebcdb7ec36b76cc1d9473._comment
new file mode 100644
index 000000000..859c1ae2e
--- /dev/null
+++ b/doc/forum/copy_symlinks/comment_2_198f3e9db08ebcdb7ec36b76cc1d9473._comment
@@ -0,0 +1,8 @@
+[[!comment format=mdwn
+ username="mario"
+ avatar="http://cdn.libravatar.org/avatar/4c63b0935789d29210d0bd8cad8d7ac7"
+ subject="Thanks"
+ date="2019-04-16T11:07:10Z"
+ content="""
+Great, thanks for the confirmation.
+"""]]

added renameremote command
diff --git a/CHANGELOG b/CHANGELOG
index 6b693b376..e791d5790 100644
--- a/CHANGELOG
+++ b/CHANGELOG
@@ -11,6 +11,9 @@ git-annex (7.20190323) UNRELEASED; urgency=medium
     syncing with are export/import remotes.
   * sync: When listing contents on an import remote fails, proceed with
     other syncing instead of aborting.
+  * renameremote: New command, changes the name that is used to enable 
+    a special remote. Especially useful when you want to reuse the name
+    of an old remote for something new.
 
  -- Joey Hess <id@joeyh.name>  Tue, 09 Apr 2019 14:07:53 -0400
 
diff --git a/CmdLine/GitAnnex.hs b/CmdLine/GitAnnex.hs
index 2fdfe4bcc..9fc0d272a 100644
--- a/CmdLine/GitAnnex.hs
+++ b/CmdLine/GitAnnex.hs
@@ -54,6 +54,7 @@ import qualified Command.Init
 import qualified Command.Describe
 import qualified Command.InitRemote
 import qualified Command.EnableRemote
+import qualified Command.RenameRemote
 import qualified Command.EnableTor
 import qualified Command.Multicast
 import qualified Command.Expire
@@ -145,6 +146,7 @@ cmds testoptparser testrunner mkbenchmarkgenerator =
 	, Command.Describe.cmd
 	, Command.InitRemote.cmd
 	, Command.EnableRemote.cmd
+	, Command.RenameRemote.cmd
 	, Command.EnableTor.cmd
 	, Command.Multicast.cmd
 	, Command.Reinject.cmd
diff --git a/Command/RenameRemote.hs b/Command/RenameRemote.hs
new file mode 100644
index 000000000..608471094
--- /dev/null
+++ b/Command/RenameRemote.hs
@@ -0,0 +1,41 @@
+{- git-annex command
+ -
+ - Copyright 2019 Joey Hess <id@joeyh.name>
+ -
+ - Licensed under the GNU AGPL version 3 or higher.
+ -}
+
+module Command.RenameRemote where
+
+import Command
+import qualified Logs.Remote
+import qualified Types.Remote as R
+import qualified Remote
+
+import qualified Data.Map as M
+
+cmd :: Command
+cmd = command "renameremote" SectionSetup
+	"changes name of special remote"
+	(paramPair paramName paramName)
+	(withParams seek)
+
+seek :: CmdParams -> CommandSeek
+seek = withWords (commandAction . start)
+
+start :: [String] -> CommandStart
+start (oldname:newname:[]) = do
+	m <- Logs.Remote.readRemoteLog
+	Remote.nameToUUID' oldname >>= \case
+		Left e -> giveup e
+		Right u -> case M.lookup u m of
+			Nothing -> giveup "That is not a special remote."
+			Just cfg -> do
+				showStart' "rename" Nothing
+				next $ perform u cfg newname
+start _ = giveup "Specify an old name (or uuid or description) and a new name."
+
+perform :: UUID -> R.RemoteConfig -> String -> CommandPerform
+perform u cfg newname = do
+	Logs.Remote.configSet u (M.insert "name" newname cfg)
+	next $ return True
diff --git a/doc/git-annex-dead.mdwn b/doc/git-annex-dead.mdwn
index d7acaa2d5..a13934033 100644
--- a/doc/git-annex-dead.mdwn
+++ b/doc/git-annex-dead.mdwn
@@ -32,6 +32,8 @@ by using eg, `git-annex reinject`.)
 
 [[git-annex-untrust]](1)
 
+[[git-annex-renameremote]](1)
+
 [[git-annex-expire]](1)
 
 [[git-annex-fsck]](1)
diff --git a/doc/git-annex-initremote.mdwn b/doc/git-annex-initremote.mdwn
index d47c66506..62b910d9c 100644
--- a/doc/git-annex-initremote.mdwn
+++ b/doc/git-annex-initremote.mdwn
@@ -27,16 +27,26 @@ All special remotes support encryption. You can specify
 address associated with a key). For details about ways to configure
 encryption, see <https://git-annex.branchable.com/encryption/>
 
-If you anticipate using the new special remote in other clones of the
-repository, you can pass "autoenable=true". Then when [[git-annex-init]](1)
+Once a special remote has been initialized once with this command,
+other clones of the repository can also be set up to access it using
+`git annex enableremote`.
+
+To avoid `git annex enableremote` needing to be run,
+you can pass "autoenable=true". Then when [[git-annex-init]](1)
 is run in a new clone, it will attempt to enable the special remote. Of
 course, this works best when the special remote does not need anything
 special to be done to get it enabled.
 
+The name you provide for the remote can't be one that's been used for any
+other special remote before, because `git-annex enableremote` uses the name
+to identify which special remote to enable. If some old special remote
+that's no longer used has taken the name you want to reuse, you might
+want to use `git annex renameremote`.
+
 Normally, git-annex generates a new UUID for the new special remote.
 If you want to, you can specify a UUID for it to use, by passing a
 uuid=whatever parameter. This can be useful in some situations, eg when the
-same data can be accessed via two different special remote backends.
+same data can be accessed via two different remote backends.
 But if in doubt, don't do this.
 
 # OPTIONS
@@ -55,6 +65,8 @@ But if in doubt, don't do this.
 
 [[git-annex-enableremote]](1)
 
+[[git-annex-renameremote]](1)
+
 # AUTHOR
 
 Joey Hess <id@joeyh.name>
diff --git a/doc/git-annex.mdwn b/doc/git-annex.mdwn
index 6e11904e6..6987e5d37 100644
--- a/doc/git-annex.mdwn
+++ b/doc/git-annex.mdwn
@@ -225,6 +225,12 @@ subdirectories).
   
   See [[git-annex-enableremote]](1) for details.
 
+* `renameremote`
+
+  Renames a special remote.
+
+  See [[git-annex-renameremote]](1) for details.
+
 * `enable-tor`
 
   Sets up tor hidden service.
diff --git a/doc/todo/renameremote.mdwn b/doc/todo/renameremote.mdwn
index 3a92bf507..360043d6b 100644
--- a/doc/todo/renameremote.mdwn
+++ b/doc/todo/renameremote.mdwn
@@ -9,16 +9,15 @@ with the same name, and so enableremote would need to be run with a uuid
 instead of a name to specify which one to enable, which is not a desirable
 state of affairs.
 
-So, add `git annex renameremote oldname newname`. This could also do a `git
+So, add `git annex renameremote oldname newname`. Updates the remote.log
+with the new name.
+
+This could also do a `git
 remote rename`, or equivilant. (`git remote rename` gets confused by special
 remotes not having a fetch url and fails; this can be worked around by
-manually renaming the stanza in git config.)
-
-Implementing that would need a way to remove the old name from remote.log.
-We can't remove lines from union merged files, but what we could do is
-add a new line like:
-
-	- name=oldname timestamp=<latest>
+manually renaming the stanza in git config.) But.. Perhaps it's better to
+keep it simple and not do that. There's no necessarily a correspondance
+between the name of a remote in the local repo and the name of a
+special remote in the remote.log.
 
-And in parsing remote.log, if the UUID is "-", don't include the
-remote with that name in the the resulting map.
+[[done]] --[[Joey]]
diff --git a/git-annex.cabal b/git-annex.cabal
index 8057b91a5..d49640ae8 100644
--- a/git-annex.cabal
+++ b/git-annex.cabal
@@ -104,6 +104,7 @@ Extra-Source-Files:
   doc/git-annex-reinject.mdwn
   doc/git-annex-rekey.mdwn
   doc/git-annex-remotedaemon.mdwn
+  doc/git-annex-renameremote.mdwn
   doc/git-annex-repair.mdwn
   doc/git-annex-required.mdwn
   doc/git-annex-resolvemerge.mdwn
@@ -766,6 +767,7 @@ Executable git-annex
     Command.Reinit
     Command.Reinject
     Command.RemoteDaemon

(Diff truncated)
don't list subpages of todos
diff --git a/doc/todo.mdwn b/doc/todo.mdwn
index e2661da38..a4ee9d55d 100644
--- a/doc/todo.mdwn
+++ b/doc/todo.mdwn
@@ -1,5 +1,5 @@
 This is git-annex's todo list. Link items to [[todo/done]] when done. A more complete [[design/roadmap/]] is also available.
 
-[[!inline pages="./todo/* and !./todo/done and !link(done) 
+[[!inline pages="./todo/* and !./todo/*/* and !./todo/done and !link(done) 
 and !*/Discussion" actions=yes postform=yes postformtext="Add a new todo titled:"
 show=0 feedlimit=10 archive=yes]]

update
diff --git a/doc/todo/import_tree.mdwn b/doc/todo/import_tree.mdwn
index 5ae92dd00..6db10e9ce 100644
--- a/doc/todo/import_tree.mdwn
+++ b/doc/todo/import_tree.mdwn
@@ -13,14 +13,15 @@ and `git annex sync --content` can be configured to use it.
 
 ## remaining todo
 
-* Currently only directory special remote supports importing, at least S3
-  can also support it.
+* Currently only directory and adb special remotes support importing,
+  at least S3 can also support it.
 
 * Write a tip or tips to document using this new feature.
+  (Have one for adb now.)
 
 * Add to external special remote protocol.
 
-* Support importing from adb special remotes, webdav, etc?
+* Support importing from webdav, etc?
   Problem is that these may have no way to avoid an export
   overwriting changed content that would have been imported otherwise.
   So if they're supported the docs need to reflect the problem so the user

close
diff --git a/doc/todo/adb_special_remote.mdwn b/doc/todo/adb_special_remote.mdwn
index f89eeac6d..d183511e4 100644
--- a/doc/todo/adb_special_remote.mdwn
+++ b/doc/todo/adb_special_remote.mdwn
@@ -17,3 +17,5 @@ excluding some files from a tree exported to android.
 
 > Status: Remote implemented, but not yet [[import tree]] and
 > [[export preferred content]]. --[[Joey]]
+
+> Update: Import from adb is now implemented. Closing [[done]] --[[Joey]]

todo
diff --git a/doc/todo/globus_special_remote_as_a___34__transport__34___layer/comment_2_89be9eea4304897c639fa80db92cfe2c._comment b/doc/todo/globus_special_remote_as_a___34__transport__34___layer/comment_2_89be9eea4304897c639fa80db92cfe2c._comment
new file mode 100644
index 000000000..e248e0ea4
--- /dev/null
+++ b/doc/todo/globus_special_remote_as_a___34__transport__34___layer/comment_2_89be9eea4304897c639fa80db92cfe2c._comment
@@ -0,0 +1,7 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 2"""
+ date="2019-04-15T16:55:36Z"
+ content="""
+See [[todo/support_multiple_special_remotes_with_same_uuid]]
+"""]]
diff --git a/doc/todo/support_multiple_special_remotes_with_same_uuid.mdwn b/doc/todo/support_multiple_special_remotes_with_same_uuid.mdwn
new file mode 100644
index 000000000..c3861af4c
--- /dev/null
+++ b/doc/todo/support_multiple_special_remotes_with_same_uuid.mdwn
@@ -0,0 +1,31 @@
+If the same data storage can be accessed via two protocols, two different
+special remotes could be configured that access the same data, and so
+should have the same uuids.
+
+This is not possible though, because remote.log is uuid-based and so
+the special remote configs stored in it for a given uuid would apply to
+both special remotes.
+
+It is already possible of course for two git remotes to have the same uuid,
+and also for a special remote and git remotes to have the same uuid.
+
+----
+
+One approach would be to add some kind of namespace to the configs in
+remote.log. But this seems problematic, the user would need to juggle
+remote names and namespaces.
+
+Another approach is to have a way to make two uuids be treated as
+equivilant. Eg, to make uuid B be treated the same as uuid A. 
+
+Suppose there's an equivilance.log that contains "ts B A". Then when git
+config is read, a remote with uuid B will result in constuction of a
+`Remote` with uuid A, but with the `RemoteConfig` of uuid B.
+
+Seems like this would be the only place the equivilance.log would need to
+be used, once the `Remote` is constucted using the equivilant uuid the rest
+of the code will work as-is.
+
+That would add overhead of an additional git-annex branch read on every
+program start. That could be avoided by instead putting the equivilance in
+the remote.log. Eg, "B sameas=A foo=bar ..."

Added a comment
diff --git a/doc/forum/copy_symlinks/comment_1_950de173a042a7671a43adbab02e0669._comment b/doc/forum/copy_symlinks/comment_1_950de173a042a7671a43adbab02e0669._comment
new file mode 100644
index 000000000..7350464a5
--- /dev/null
+++ b/doc/forum/copy_symlinks/comment_1_950de173a042a7671a43adbab02e0669._comment
@@ -0,0 +1,10 @@
+[[!comment format=mdwn
+ username="CandyAngel"
+ avatar="http://cdn.libravatar.org/avatar/15c0aade8bec5bf004f939dd73cf9ed8"
+ subject="comment 1"
+ date="2019-04-15T07:34:21Z"
+ content="""
+`git add` and `git annex add` do both behave the same on symlinks (at least, in indirect annexes).
+
+They are just staged (then fixed on commit, if required).
+"""]]

diff --git a/doc/forum/copy_symlinks.mdwn b/doc/forum/copy_symlinks.mdwn
new file mode 100644
index 000000000..5f7499474
--- /dev/null
+++ b/doc/forum/copy_symlinks.mdwn
@@ -0,0 +1,11 @@
+Hi,
+
+I'm always confused when I try to copy a file within an annex repository. I know that I can just copy the symlink, so I don't have to move the actual data around. But what do I do with the new symlink: "git add" or "git annex add"? And what happens when I do the wrong one?
+
+Since "git annex add FILE" usually creates a symlink to FILE (and then git add on the symlink) I wonder if I'll end up with a symlink to a symlink. Would be somehow logical but pretty confusing.
+
+So I think both "git add LINK" and "git annex add LINK" should behave identical when LINK is a copy of symlink of an annexed file. However, this would still be confusing, since one would not expect that both commands behave identical in some situations but different in other situations.
+
+So, what's the best way to copy an already annexed file (destination in the same repository)?
+
+Best, Mario

todo
diff --git a/doc/todo/import_tree_from_rsync_special_remote.mdwn b/doc/todo/import_tree_from_rsync_special_remote.mdwn
new file mode 100644
index 000000000..92aef7576
--- /dev/null
+++ b/doc/todo/import_tree_from_rsync_special_remote.mdwn
@@ -0,0 +1,38 @@
+The rsync special remote supports exporttree; it would be useful to also
+support importtree.
+
+The adb special remote shows this is possible using just some fairly
+standard commands, although `find` and `stat` are not well enough
+standardized to work on all unixes, it would be easy to at least support
+linux.
+
+So far, the rsync special remote really only needs rsync on the server.
+And can be used with servers that lock down their shell to only 
+allow rsync to be run. It would be good to also only need rsync for
+importtree, but there are several roadblocks:
+
+* listing contents: Using rsync would involve a command like
+  `rsync --checksum -avz -i --dry-run --out-format='%C %l %M %f\n' $rsync-url empty-directory`;
+  that makes the remote rsync checksum all the files, which could be very
+  expensive. But without checksum, only mtime and size is available,
+  which is not really enough to be sure all edits to a file are imported
+  (eg a rename swap of two files that have the same mtime would not be
+  noticed).
+
+  It would be a lot nicer to use `find | stat`
+
+* retrieving file with a specific content identifier:
+  If rsync --checksum is used, git-annex can just do the same checksum
+  on the downloaded file and make sure rsync retrieved the same content
+  identifier that was requested.
+
+* store/remove/checkpresent with a content identifier:
+  If the only way available to check a content identifier is to run
+  rsync to get the current remote checksum of a file, very wide race
+  windows will be open when the file is large. So a file that is unmodified
+  at the start may get modified and that modification be overwritten.
+
+  **This is not acceptable**
+
+So, it seems that, importtree would need to be able to run commands
+other than rsync on the server. --[[Joey]]

added suggestion for git-annex-get --batch --key
diff --git a/doc/todo/git-annex-get_--batch_--key.mdwn b/doc/todo/git-annex-get_--batch_--key.mdwn
new file mode 100644
index 000000000..4d210fa38
--- /dev/null
+++ b/doc/todo/git-annex-get_--batch_--key.mdwn
@@ -0,0 +1 @@
+Can git-annex-get be extended so that "git-annex-get --batch --key" fetches the keys (rather than filenames) given in the input?

simpler setup instructions
This commit was sponsored by Denis Dzyubenko on Patreon.
diff --git a/doc/tips/android_sync_with_adb.mdwn b/doc/tips/android_sync_with_adb.mdwn
index a8230547d..cf2070f5b 100644
--- a/doc/tips/android_sync_with_adb.mdwn
+++ b/doc/tips/android_sync_with_adb.mdwn
@@ -26,48 +26,32 @@ Android device, so it will only import photos and videos, not other files.
 If you wanted to import everything, you could instead use 
 "androiddirectory=/sdcard".
 
-## initial import
+Next, configure how file trees imported from it will be merged into your
+git repository.
 
-Now you can import all files from your Android device:
-
-	git annex import master:android --from android
-	git merge --allow-unrelated-histories android/master
-
-That merges the imported files into the existing contents of your git-annex
-repository. In the example above, the imported files were put into an
-"android" subdirectory, to keep them separate from your other files.
-If you leave off the ":android", the files will be imported into the top of
-the repository.
-
-## initial export
-
-With the files from the Android device imported, you might want to remove
-them from it, to free up space on it. Or, you might add more files that you
-want to export to it, or change files. Whatever changes you make,
-you can `git annex add` and `git commit` as usual. Then to export
-the changed branch to the Android device:
-
-	git annex export master:android --to android
-
-(Again the ":android" limits it to the android directory,
-so leave thatoff if you want to export everything.)
+        git config remote.android.annex-tracking-branch master:android
 
-It's fine to export and import in any order and at any time, and you can
-make changes to files on the Android device at any time too. git-annex will
-keep it all in sync.
+Setting "master:android" makes the phone be treated as containing a branch
+of the master branch, and makes all its files appear to be inside a
+subdirectory named `android`. If you want its files to not be in a
+subdirectory, set it to "master" instead.
 
-## automation
+## syncing with it
 
-Let's automate that syncing process some more.
+	git annex sync --content android
 
-        git config remote.android.annex-tracking-branch master:android
+This command does a bi-directional sync with the phone, first importing
+new and changed files from it, merging that into the master branch,
+and then exporting from the master branch back to the android device so any
+modifications you have made get synced over to it.
 
-That configures git-annex to know that you want sync up the master
-branch (specifically the android subdirectory) and your Android device.
+See [[git-annex-import, [[git-annex-export]], and [[git-annex-sync]]
+for more details, and bear in mind that you can also use commands like
+these to only import from or export to the android device:
 
-Now, you only have to run a single command to sync everything:
-        
-	git annex sync --content
+	git annex import master:android --from android
+	git merge android/master
+	git annex export master:android --to android
 
 ## sample workflows
 
@@ -87,24 +71,25 @@ Android device:
 Set up the remote to use the /sdcard/Music directory:
 
 	initremote android type=adb androiddirectory=/sdcard/Music encryption=none exporttree=yes importtree=yes
+       
+The annex-tracking-branch can be the same as before, to limit
+the files that are synced to those in an android directory:
+	
+	git config remote.android.annex-tracking-branch master:android
 
-The rest of the commands are unchanged:
+And then do an initial sync:
 
-	git annex import master:android --from android
-	git merge --allow-unrelated-histories android/master
-	git annex export master:android --to android
-        git config remote.android.annex-tracking-branch master:android
-	git annex sync --content
+	git annex sync --content android
 
-With this setup, you can copy music and podcasts you want to listen 
+Now, you can copy music and podcasts you want to listen 
 to over to the Android device, by first copying them to the Android
 directory of your git-annex repo:
 
 	cp -a podcasts/LibreLounge/Episode_14__Secure_Scuttlebutt_with_Joey_Hess.ogg android/
 	git annex add android
-	git annex sync --content
+	git annex sync --content android
 
 Once you're done with listening to something on the Android device,
 you can simply delete on the device, and the next time git-annex syncs, it
-will get removed from the android directory.
-
+will get removed from the android directory. Or, you can delete it from the
+android directory and the next sync will delete it from the Android device.

thoughts
diff --git a/doc/todo/export_preferred_content.mdwn b/doc/todo/export_preferred_content.mdwn
index 491998669..76e90f703 100644
--- a/doc/todo/export_preferred_content.mdwn
+++ b/doc/todo/export_preferred_content.mdwn
@@ -12,3 +12,30 @@ been listened to.
 It seems doable to make `git annex export` honor whatever
 preferred content settings have been configured for the remote.
 (And `git annex sync --content` too.)
+
+> `git annex import` of a tree from a special remote would also be
+> influenced by this.
+> 
+> It would make sense for the ImportableContents to have files
+> that are not preferred content filtered out of it. Eg, if a .wav file
+> is added to the remote, it shouldn't be downloaded. Or a better example,
+> if directory Music is excluded from an android remote, importing from
+> it should exclude that directory.
+
+> Problem: If a tree is exported with eg, no .wav files, and then an import
+> is made from the remote, and necessarily lacks .wav files, the remote
+> tracking branch will have a tree with no .wav
+> files. Merging that into master will delete all the .wav files.
+> 
+> If the remote tracking branch has a disconnected history from master,
+> then git wouldn't delete files on
+> merge. But: This would prevent actual deletions made on the special
+> remote from happening in master too. So not a good idea.
+> 
+> So it seems that, when updating the remote tracking branch, the files
+> that were excluded from being exported to it need to be added back in.
+> That can be done by keeping a pointer to the tree that was last exported, 
+> including all exported files, and generating a tree from it that deletes
+> all exported files. The diff between those trees is all the excluded
+> files, so when updating the remote tracking branch, take the tree that
+> was imported, and merge that diff into it.

followup
diff --git a/doc/bugs/Unable_to_get__47__addurl_to_http_link__58___download_failed__58___InvalidHeader___34__preload__34__.mdwn b/doc/bugs/Unable_to_get__47__addurl_to_http_link__58___download_failed__58___InvalidHeader___34__preload__34__.mdwn
index 28198a5ad..6e2f327bd 100644
--- a/doc/bugs/Unable_to_get__47__addurl_to_http_link__58___download_failed__58___InvalidHeader___34__preload__34__.mdwn
+++ b/doc/bugs/Unable_to_get__47__addurl_to_http_link__58___download_failed__58___InvalidHeader___34__preload__34__.mdwn
@@ -73,3 +73,7 @@ local repository version: 5
 
 
 [[!meta author=yoh]]
+
+> closing as there are no code changes to git-annex that can fix this,
+> it has to be fixed in either http-client or the web server. [[done]]
+> --[[Joey]]
diff --git a/doc/bugs/Unable_to_get__47__addurl_to_http_link__58___download_failed__58___InvalidHeader___34__preload__34__/comment_1_247f3c1dfea3cdb0b398c015f4c4d44b._comment b/doc/bugs/Unable_to_get__47__addurl_to_http_link__58___download_failed__58___InvalidHeader___34__preload__34__/comment_1_247f3c1dfea3cdb0b398c015f4c4d44b._comment
new file mode 100644
index 000000000..9f7a345b9
--- /dev/null
+++ b/doc/bugs/Unable_to_get__47__addurl_to_http_link__58___download_failed__58___InvalidHeader___34__preload__34__/comment_1_247f3c1dfea3cdb0b398c015f4c4d44b._comment
@@ -0,0 +1,44 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 1"""
+ date="2019-04-10T13:58:03Z"
+ content="""
+curl -v shows the problem response
+
+	< Server: openresty/1.7.10.1
+	< Date: Wed, 10 Apr 2019 13:57:10 GMT
+	< Content-Type: application/octet-stream
+	< Content-Length: 773788987
+	< Connection: keep-alive
+	< Last-Modified: Mon, 11 Mar 2019 16:35:02 GMT
+	< ETag: "5c868e36-2e1f153b"
+	< Accept-Ranges: bytes
+	< Strict-Transport-Security: max-age=15768000; includeSubdomains;
+	< preload
+	< X-Frame-Options: DENY
+	< X-Content-Type-Options: nosniff
+
+It looks like the server is sending "preload" on its own line rather
+than being part of the Strict-Transport-Security header.
+
+Just in case, I found another url that uses HSTS preload, and git-annex
+can download that:
+
+	joey@darkstar:~>curl -v -o foo https://www.torproject.org/ 2>&1 | grep preload
+	< Strict-Transport-Security: max-age=15768000; preload
+	joey@darkstar:~/tmp/c>git annex addurl https://www.torproject.org/
+	addurl https://www.torproject.org/ 
+	(to www.torproject.org_) ok
+
+The web server is probably violating standard HTTP to some extent with that
+response. Of course, it's possible to parse the response less strictly and
+not fail on the malformed header. Still, fixing the web server is probably the
+fastest way to fix the immediate problem (as well as make HSTS preloading
+actually be used).
+
+Issue filed on http-client, <https://github.com/snoyberg/http-client/issues/398>
+with a prospective patch.
+
+I don't see any changes to git-annex that can help with the problem, so
+I'll close this bug report.
+"""]]

document importtree=yes
diff --git a/doc/special_remotes/adb.mdwn b/doc/special_remotes/adb.mdwn
index d21120568..4eed62daf 100644
--- a/doc/special_remotes/adb.mdwn
+++ b/doc/special_remotes/adb.mdwn
@@ -5,10 +5,10 @@ allows connecting to it in various ways like a USB cable or wifi.
 
 ## example
 
-To make git-annex store files in the /sdcard/annex directory
-on the Android device, and export the current master tree to it:
+To add a remote for the /sdcard/DCIM directory
+on the Android device, allowing to import and export photos:
 
-	git annex initremote android type=adb androiddirectory=/sdcard/annex encryption=none exporttree=yes
+	git annex initremote android type=adb androiddirectory=/sdcard/DCIM encryption=none exporttree=yes importtree=yes
 	git annex export master --to android
 
 ## configuration
@@ -28,6 +28,10 @@ the adb remote.
   special remote. Since this makes the exported files easily browsable
   on the Android device, you will almost always want to enable this.
 
+* `importtree` - Set to "yes" to make this special remote usable
+  by [[git-annex-import]]. When set in combination with exporttree,
+  this lets files be imported from it, and changes exported back to it.
+
 * `encryption` - One of "none", "hybrid", "shared", or "pubkey".
   See [[encryption]].
 

original report on inability to get a url
diff --git a/doc/bugs/Unable_to_get__47__addurl_to_http_link__58___download_failed__58___InvalidHeader___34__preload__34__.mdwn b/doc/bugs/Unable_to_get__47__addurl_to_http_link__58___download_failed__58___InvalidHeader___34__preload__34__.mdwn
new file mode 100644
index 000000000..28198a5ad
--- /dev/null
+++ b/doc/bugs/Unable_to_get__47__addurl_to_http_link__58___download_failed__58___InvalidHeader___34__preload__34__.mdwn
@@ -0,0 +1,75 @@
+Originally reported [here](https://github.com/CONP-PCNO/conp-dataset/pull/14)
+
+[[!format sh """
+$> wget https://datahub-khvul4ng.udes.genap.ca/ALL.chr10.phase3_shapeit2_mvncall_integrated_v5a.20130502.genotypes.vcf.gz
+--2019-04-10 09:26:54--  https://datahub-khvul4ng.udes.genap.ca/ALL.chr10.phase3_shapeit2_mvncall_integrated_v5a.20130502.genotypes.vcf.gz
+Resolving datahub-khvul4ng.udes.genap.ca (datahub-khvul4ng.udes.genap.ca)... 204.19.23.238
+Connecting to datahub-khvul4ng.udes.genap.ca (datahub-khvul4ng.udes.genap.ca)|204.19.23.238|:443... connected.
+HTTP request sent, awaiting response... 200 OK
+Length: 773788987 (738M) [application/octet-stream]
+Saving to: ‘ALL.chr10.phase3_shapeit2_mvncall_integrated_v5a.20130502.genotypes.vcf.gz’
+
+hr10.phase3_shapeit2_mvncall_integr   1%[                                                                  ]   9.44M  2.02MB/s    eta 6m 16s ^C
+# so wget works - I interrupted
+
+$> git annex addurl -d https://datahub-khvul4ng.udes.genap.ca/ALL.chr10.phase3_shapeit2_mvncall_integrated_v5a.20130502.genotypes.vcf.gz 
+[2019-04-10 09:27:04.412248] read: git ["--git-dir=.git","--work-tree=.","--literal-pathspecs","show-ref","git-annex"]
+[2019-04-10 09:27:04.416582] process done ExitSuccess
+[2019-04-10 09:27:04.416692] read: git ["--git-dir=.git","--work-tree=.","--literal-pathspecs","show-ref","--hash","refs/heads/git-annex"]
+[2019-04-10 09:27:04.420688] process done ExitSuccess
+[2019-04-10 09:27:04.420852] read: git ["--git-dir=.git","--work-tree=.","--literal-pathspecs","log","refs/heads/git-annex..3db4e3c3bf941c1cff0936d4441366bd10c9b2f1","--pretty=%H","-n1"]
+[2019-04-10 09:27:04.424774] process done ExitSuccess
+[2019-04-10 09:27:04.425311] chat: git ["--git-dir=.git","--work-tree=.","--literal-pathspecs","cat-file","--batch"]
+[2019-04-10 09:27:04.42596] chat: git ["--git-dir=.git","--work-tree=.","--literal-pathspecs","cat-file","--batch-check=%(objectname) %(objecttype) %(objectsize)"]
+addurl https://datahub-khvul4ng.udes.genap.ca/ALL.chr10.phase3_shapeit2_mvncall_integrated_v5a.20130502.genotypes.vcf.gz [2019-04-10 09:27:04.449013] Request {
+  host                 = "datahub-khvul4ng.udes.genap.ca"
+  port                 = 443
+  secure               = True
+  requestHeaders       = [("Accept-Encoding",""),("User-Agent","git-annex/7.20190322+git23-g9662cb332-1~ndallstack+1")]
+  path                 = "/ALL.chr10.phase3_shapeit2_mvncall_integrated_v5a.20130502.genotypes.vcf.gz"
+  queryString          = ""
+  method               = "HEAD"
+  proxy                = Nothing
+  rawBody              = False
+  redirectCount        = 10
+  responseTimeout      = ResponseTimeoutDefault
+  requestVersion       = HTTP/1.1
+}
+
+
+[2019-04-10 09:27:04.711525] Request {
+  host                 = "datahub-khvul4ng.udes.genap.ca"
+  port                 = 443
+  secure               = True
+  requestHeaders       = [("Accept-Encoding","identity"),("User-Agent","git-annex/7.20190322+git23-g9662cb332-1~ndallstack+1")]
+  path                 = "/ALL.chr10.phase3_shapeit2_mvncall_integrated_v5a.20130502.genotypes.vcf.gz"
+  queryString          = ""
+  method               = "GET"
+  proxy                = Nothing
+  rawBody              = False
+  redirectCount        = 10
+  responseTimeout      = ResponseTimeoutDefault
+  requestVersion       = HTTP/1.1
+}
+
+download failed: InvalidHeader "preload"
+failed
+[2019-04-10 09:27:04.956626] process done ExitSuccess
+[2019-04-10 09:27:04.957293] process done ExitSuccess
+git-annex: addurl: 1 failed
+
+$> git annex version
+git-annex version: 7.20190322+git23-g9662cb332-1~ndallstack+1
+build flags: Assistant Webapp Pairing S3(multipartupload)(storageclasses) WebDAV Inotify TorrentParser MagicMime Feeds Testsuite
+dependency versions: aws-0.17.1 bloomfilter-2.0.1.0 cryptonite-0.23 DAV-1.3.1 feed-0.3.12.0 ghc-8.0.2 http-client-0.5.7.0 persistent-sqlite-2.6.2 torrent-10000.1.1 uuid-1.3.13 yesod-1.4.5
+key/value backends: SHA256E SHA256 SHA512E SHA512 SHA224E SHA224 SHA384E SHA384 SHA3_256E SHA3_256 SHA3_512E SHA3_512 SHA3_224E SHA3_224 SHA3_384E SHA3_384 SKEIN256E SKEIN256 SKEIN512E SKEIN512 BLAKE2B256E BLAKE2B256 BLAKE2B512E BLAKE2B512 BLAKE2B160E BLAKE2B160 BLAKE2B224E BLAKE2B224 BLAKE2B384E BLAKE2B384 BLAKE2S256E BLAKE2S256 BLAKE2S160E BLAKE2S160 BLAKE2S224E BLAKE2S224 BLAKE2SP256E BLAKE2SP256 BLAKE2SP224E BLAKE2SP224 SHA1E SHA1 MD5E MD5 WORM URL
+remote types: git gcrypt p2p S3 bup directory rsync web bittorrent webdav adb tahoe glacier ddar hook external
+operating system: linux x86_64
+supported repository versions: 5 7
+upgrade supported from repository versions: 0 1 2 3 4 5 6
+local repository version: 5
+
+"""]]
+
+
+[[!meta author=yoh]]

remove wrong uniqueness constraint from ContentIdentifier db
Fix bug that caused importing from a special remote to repeatedly download
unchanged files when multiple files in the remote have the same content.
Unfortunately, there's really no good way to remove a uniqueness constraint
from a sqlite database. The best that can be done is to make a new table
and copy the data over. But that would require using persistent's
migrations or raw sql, and I don't want to do either.
Instead, a sledgehammer approach: Renamed .git/annex/cid to
.git/annex/cids. When the new database doesn't exist, it will be populated
from the git-annex branch.
Noting deletes the old database. Don't want to delete it out from under
some long-running git-annex process that might be using it. It could
eventually be deleted. But this is such a new feature, probably few repos
have the database in any case.
diff --git a/Annex/Locations.hs b/Annex/Locations.hs
index 07abad2b2..8d212fe10 100644
--- a/Annex/Locations.hs
+++ b/Annex/Locations.hs
@@ -355,9 +355,13 @@ gitAnnexExportLock u r = gitAnnexExportDbDir u r ++ ".lck"
 gitAnnexExportUpdateLock :: UUID -> Git.Repo -> FilePath
 gitAnnexExportUpdateLock u r = gitAnnexExportDbDir u r ++ ".upl"
 
-{- Directory containing database used to record remote content ids. -}
+{- Directory containing database used to record remote content ids.
+ -
+ - (This used to be "cid", but a problem with the database caused it to
+ - need to be rebuilt with a new name.)
+ -}
 gitAnnexContentIdentifierDbDir :: Git.Repo -> FilePath
-gitAnnexContentIdentifierDbDir r = gitAnnexDir r </> "cid"
+gitAnnexContentIdentifierDbDir r = gitAnnexDir r </> "cids"
 
 {- Lock file for writing to the content id database. -}
 gitAnnexContentIdentifierLock :: Git.Repo -> FilePath
diff --git a/CHANGELOG b/CHANGELOG
index 1770449af..97ff44461 100644
--- a/CHANGELOG
+++ b/CHANGELOG
@@ -4,6 +4,9 @@ git-annex (7.20190323) UNRELEASED; urgency=medium
     to allow git-annex import of files from an Android device. This can be
     combined with exporttree=yes and git-annex export used to send changes
     back to the Android device.
+  * Fix bug that caused importing from a special remote to repeatedly
+    download unchanged files when multiple files in the remote have the same
+    content.
 
  -- Joey Hess <id@joeyh.name>  Tue, 09 Apr 2019 14:07:53 -0400
 
diff --git a/Database/ContentIdentifier.hs b/Database/ContentIdentifier.hs
index 75e5c545d..4180c5854 100644
--- a/Database/ContentIdentifier.hs
+++ b/Database/ContentIdentifier.hs
@@ -6,7 +6,7 @@
  -}
 
 {-# LANGUAGE QuasiQuotes, TypeFamilies, TemplateHaskell #-}
-{-# LANGUAGE OverloadedStrings, GADTs, FlexibleContexts #-}
+{-# LANGUAGE OverloadedStrings, GADTs, FlexibleContexts, EmptyDataDecls #-}
 {-# LANGUAGE MultiParamTypeClasses, GeneralizedNewtypeDeriving #-}
 {-# LANGUAGE RankNTypes #-}
 
@@ -51,9 +51,6 @@ ContentIdentifiers
   remote UUID
   cid ContentIdentifier
   key IKey
-  ContentIdentifiersIndexRemoteKey remote key
-  ContentIdentifiersIndexRemoteCID remote cid
-  UniqueRemoteCidKey remote cid key
 -- The last git-annex branch tree sha that was used to update
 -- ContentIdentifiers
 AnnexBranch
@@ -93,7 +90,7 @@ flushDbQueue (ContentIdentifierHandle h) = H.flushDbQueue h
 -- Be sure to also update the git-annex branch when using this.
 recordContentIdentifier :: ContentIdentifierHandle -> UUID -> ContentIdentifier -> Key -> IO ()
 recordContentIdentifier h u cid k = queueDb h $ do
-	void $ insertUnique $ ContentIdentifiers u cid (toIKey k)
+	void $ insert_ $ ContentIdentifiers u cid (toIKey k)
 
 getContentIdentifiers :: ContentIdentifierHandle -> UUID -> Key -> IO [ContentIdentifier]
 getContentIdentifiers (ContentIdentifierHandle h) u k = H.queryDbQueue h $ do
diff --git a/doc/bugs/repeated_import_of_same_content_files_from_remote.mdwn b/doc/bugs/repeated_import_of_same_content_files_from_remote.mdwn
index 4fcf10f4a..083898f4c 100644
--- a/doc/bugs/repeated_import_of_same_content_files_from_remote.mdwn
+++ b/doc/bugs/repeated_import_of_same_content_files_from_remote.mdwn
@@ -7,3 +7,5 @@ unncessarly importing in that case. --[[Joey]]
 Seems that the ContentIdentifier database can actually only store one cid
 for a given key at a time, not multiples needed by this. This needs a
 change to the db schema to fix, unfortunately.
+
+> [[done]] --[[Joey]]

analysis
diff --git a/doc/bugs/repeated_import_of_same_content_files_from_remote.mdwn b/doc/bugs/repeated_import_of_same_content_files_from_remote.mdwn
index 0fff4235c..4fcf10f4a 100644
--- a/doc/bugs/repeated_import_of_same_content_files_from_remote.mdwn
+++ b/doc/bugs/repeated_import_of_same_content_files_from_remote.mdwn
@@ -3,3 +3,7 @@ over from my phone. Not all files, just a few of them. The affected
 files all seem to have multiple copies in the imported tree, with different
 ContentIdentifiers for each. Seems the import code is getting confused and
 unncessarly importing in that case. --[[Joey]]
+
+Seems that the ContentIdentifier database can actually only store one cid
+for a given key at a time, not multiples needed by this. This needs a
+change to the db schema to fix, unfortunately.

devblog
diff --git a/doc/devblog/day_580__import_from_android.mdwn b/doc/devblog/day_580__import_from_android.mdwn
new file mode 100644
index 000000000..c69649d0c
--- /dev/null
+++ b/doc/devblog/day_580__import_from_android.mdwn
@@ -0,0 +1,11 @@
+It was not very hard to get `git annex import` working with adb special
+remotes. This is a nice alternative to installing git-annex on an Android
+device for syncing with it. See [[tips/android_sync_with_adb]].
+
+I'm still thinking about supporting import from special remotes that can't
+avoid most race conditions. But for adb, the only race conditions that
+I couldn't avoid are reasonably narrow, nearly as narrow as `git
+checkout`'s own race conditions, with only the added overhead of
+adb. So I let them slide.
+
+Today's work was sponsored by Trenton Cronholm on Patreon.

bug I noticed
diff --git a/doc/bugs/repeated_import_of_same_content_files_from_remote.mdwn b/doc/bugs/repeated_import_of_same_content_files_from_remote.mdwn
new file mode 100644
index 000000000..0fff4235c
--- /dev/null
+++ b/doc/bugs/repeated_import_of_same_content_files_from_remote.mdwn
@@ -0,0 +1,5 @@
+`git-annex import master --from phone` imports the same files over and
+over from my phone. Not all files, just a few of them. The affected
+files all seem to have multiple copies in the imported tree, with different
+ContentIdentifiers for each. Seems the import code is getting confused and
+unncessarly importing in that case. --[[Joey]]

adb import
As well as adding the necessary methods, a few other changes to the adb
remote:
* Use ".annextmp" extension for temp files, to avoid conflict with other
temp files.
* Stop using "echo $?" to get exit status of command inside adb.
There were two problems; first the "echo" just before it meant it was
always 0! And secondly, it seems kind of random on my phone whether it's
1 or 0, not dependant on whether the command seems to have succeeded.
diff --git a/CHANGELOG b/CHANGELOG
index 60af4137f..1770449af 100644
--- a/CHANGELOG
+++ b/CHANGELOG
@@ -1,3 +1,12 @@
+git-annex (7.20190323) UNRELEASED; urgency=medium
+
+  * adb special remote supports being configured with importree=yes,
+    to allow git-annex import of files from an Android device. This can be
+    combined with exporttree=yes and git-annex export used to send changes
+    back to the Android device.
+
+ -- Joey Hess <id@joeyh.name>  Tue, 09 Apr 2019 14:07:53 -0400
+
 git-annex (7.20190322) upstream; urgency=medium
 
   * New feature allows importing from special remotes, using
diff --git a/Remote/Adb.hs b/Remote/Adb.hs
index c0bc89a14..7a0ee60b4 100644
--- a/Remote/Adb.hs
+++ b/Remote/Adb.hs
@@ -1,18 +1,17 @@
 {- Remote on Android device accessed using adb.
  -
- - Copyright 2018 Joey Hess <id@joeyh.name>
+ - Copyright 2018-2019 Joey Hess <id@joeyh.name>
  -
  - Licensed under the GNU AGPL version 3 or higher.
  -}
 
 module Remote.Adb (remote) where
 
-import qualified Data.Map as M
-
 import Annex.Common
 import Types.Remote
 import Types.Creds
 import Types.Export
+import Types.Import
 import qualified Git
 import Config.Cost
 import Remote.Helper.Special
@@ -21,6 +20,9 @@ import Remote.Helper.ExportImport
 import Annex.UUID
 import Utility.Metered
 
+import qualified Data.Map as M
+import qualified System.FilePath.Posix as Posix
+
 -- | Each Android device has a serial number.
 newtype AndroidSerial = AndroidSerial { fromAndroidSerial :: String }
 	deriving (Show, Eq)
@@ -35,7 +37,7 @@ remote = RemoteType
 	, generate = gen
 	, setup = adbSetup
 	, exportSupported = exportIsSupported
-	, importSupported = importUnsupported
+	, importSupported = importIsSupported
 	}
 
 gen :: Git.Repo -> UUID -> RemoteConfig -> RemoteGitConfig -> Annex (Maybe Remote)
@@ -62,7 +64,14 @@ gen r u c gc = do
 			, removeExportDirectory = Just $ removeExportDirectoryM serial adir
 			, renameExport = renameExportM serial adir
 			}
-		, importActions = importUnsupported
+		, importActions = ImportActions
+			{ listImportableContents = listImportableContentsM serial adir
+			, retrieveExportWithContentIdentifier = retrieveExportWithContentIdentifierM serial adir
+			, storeExportWithContentIdentifier = storeExportWithContentIdentifierM serial adir
+			, removeExportWithContentIdentifier = removeExportWithContentIdentifierM serial adir
+			, removeExportDirectoryWhenEmpty = Nothing
+			, checkPresentExportWithContentIdentifier = checkPresentExportWithContentIdentifierM serial adir
+			}
 		, whereisKey = Nothing
 		, remoteFsck = Nothing
 		, repairRepo = Nothing
@@ -136,15 +145,26 @@ store serial adir = fileStorer $ \k src _p ->
 	in store' serial dest src
 
 store' :: AndroidSerial -> AndroidPath -> FilePath -> Annex Bool
-store' serial dest src = do
+store' serial dest src = store'' serial dest src False (return (Just True))
+
+store'' :: AndroidSerial -> AndroidPath -> FilePath -> a -> Annex (Maybe a) -> Annex a
+store'' serial dest src onfail postcheck = do
 	let destdir = takeDirectory $ fromAndroidPath dest
 	liftIO $ void $ adbShell serial [Param "mkdir", Param "-p", File destdir]
 	showOutput -- make way for adb push output
-	let tmpdest = fromAndroidPath dest ++ ".tmp"
+	let tmpdest = fromAndroidPath dest ++ ".annextmp"
 	ifM (liftIO $ boolSystem "adb" (mkAdbCommand serial [Param "push", File src, File tmpdest]))
-		-- move into place atomically
-		( liftIO $ adbShellBool serial [Param "mv", File tmpdest, File (fromAndroidPath dest)]
-		, return False
+		( postcheck >>= \case
+			Just r ->
+				-- move into place atomically
+				ifM (liftIO $ adbShellBool serial [Param "mv", File tmpdest, File (fromAndroidPath dest)])
+					( return r
+					, return onfail
+					)
+			Nothing -> do
+				void $ remove' serial (AndroidPath tmpdest)
+				return onfail
+		, return onfail
 		)
 
 retrieve :: AndroidSerial -> AndroidPath -> Retriever
@@ -175,16 +195,16 @@ checkKey r serial adir k = checkKey' r serial (androidLocation adir k)
 checkKey' :: Remote -> AndroidSerial -> AndroidPath -> Annex Bool
 checkKey' r serial aloc = do
 	showChecking r
-	(out, st) <- liftIO $ adbShellRaw serial $ unwords
+	out <- liftIO $ adbShellRaw serial $ unwords
 		[ "if test -e ", shellEscape (fromAndroidPath aloc)
 		, "; then echo y"
 		, "; else echo n"
 		, "; fi"
 		]
-	case (out, st) of
-		(["y"], ExitSuccess) -> return True
-		(["n"], ExitSuccess) -> return False
-		_ -> giveup $ "unable to access Android device" ++ show out
+	case out of
+		Just ["y"] -> return True
+		Just ["n"] -> return False
+		_ -> giveup "unable to access Android device"
 
 androidLocation :: AndroidPath -> Key -> AndroidPath
 androidLocation adir k = AndroidPath $
@@ -229,6 +249,83 @@ renameExportM serial adir _k old new = liftIO $ Just <$>
 	oldloc = fromAndroidPath $ androidExportLocation adir old
 	newloc = fromAndroidPath $ androidExportLocation adir new
 
+listImportableContentsM :: AndroidSerial -> AndroidPath -> Annex (Maybe (ImportableContents (ContentIdentifier, ByteSize)))
+listImportableContentsM serial adir = liftIO $
+	process <$> adbShell serial
+		[ Param "find"
+		-- trailing slash is needed, or android's find command
+		-- won't recurse into the directory
+		, File $ fromAndroidPath adir ++ "/"
+		, Param "-type", Param "f"
+		, Param "-exec", Param "stat"
+		, Param "-c", Param statformat
+		, Param "{}", Param "+"
+		]
+  where
+	process Nothing = Nothing
+	process (Just ls) = Just $ ImportableContents (mapMaybe mk ls) []
+
+	statformat = adbStatFormat ++ "\t%n"
+
+	mk ('S':'T':'\t':l) =
+		let (stat, fn) = separate (== '\t') l
+		    sz = fromMaybe 0 (readish (takeWhile (/= ' ') stat))
+		    cid = ContentIdentifier (encodeBS' stat)
+		    loc = mkImportLocation $ 
+		    	Posix.makeRelative (fromAndroidPath adir) fn
+		in Just (loc, (cid, sz))
+	mk _ = Nothing
+
+-- This does not guard against every possible race. As long as the adb
+-- connection is resonably fast, it's probably as good as
+-- git's handling of similar situations with files being modified while
+-- it's updating the working tree for a merge.
+retrieveExportWithContentIdentifierM :: AndroidSerial -> AndroidPath -> ExportLocation -> ContentIdentifier -> FilePath -> Annex (Maybe Key) -> MeterUpdate -> Annex (Maybe Key)
+retrieveExportWithContentIdentifierM serial adir loc cid dest mkkey _p = catchDefaultIO Nothing $
+	ifM (retrieve' serial src dest)
+		( do
+			k <- mkkey
+			currcid <- liftIO $ getExportContentIdentifier serial adir loc
+			return $ if currcid == Right (Just cid)
+				then k
+				else Nothing
+		, return Nothing
+		)
+  where
+	src = androidExportLocation adir loc
+
+storeExportWithContentIdentifierM :: AndroidSerial -> AndroidPath -> FilePath -> Key -> ExportLocation -> [ContentIdentifier] -> MeterUpdate -> Annex (Maybe ContentIdentifier)
+storeExportWithContentIdentifierM serial adir src _k loc overwritablecids _p = catchDefaultIO Nothing $
+	-- Check if overwrite is safe before sending, because sending the
+	-- file is expensive and don't want to do it unncessarily.
+	liftIO (getExportContentIdentifier serial adir loc) >>= \case
+		Right Nothing -> go
+		Right (Just cid) | cid `elem` overwritablecids -> go
+		_ -> return Nothing
+  where
+	go = store'' serial dest src Nothing checkcanoverwrite
+	dest = androidExportLocation adir loc
+	checkcanoverwrite = liftIO $
+		getExportContentIdentifier serial adir loc >>= return . \case
+			Right (Just cid) | cid `elem` overwritablecids ->
+				Just (Just cid)
+			_ -> Nothing
+
+removeExportWithContentIdentifierM :: AndroidSerial -> AndroidPath -> Key -> ExportLocation -> [ContentIdentifier] -> Annex Bool
+removeExportWithContentIdentifierM serial adir k loc removeablecids = catchBoolIO $
+	liftIO (getExportContentIdentifier serial adir loc) >>= \case

(Diff truncated)
add tip for new adb import feature
This commit was sponsored by Jake Vosloo on Patreon.
diff --git a/doc/tips/android_sync_with_adb.mdwn b/doc/tips/android_sync_with_adb.mdwn
new file mode 100644
index 000000000..a8230547d
--- /dev/null
+++ b/doc/tips/android_sync_with_adb.mdwn
@@ -0,0 +1,110 @@
+While git-annex can be [[installed_on_your_Android_device|/Android]],
+it might be easier not to install it there, but run it on your computer
+using `adb` to pull and push changes to the Android device.
+
+A few reasons for going this route:
+
+* Easier than installing git-annex on Android.
+* Avoids needing to type commands into a terminal on Android.
+* Avoids problems with putting a git-annex repository on Android's `/sdcard`,
+  which is crippled by not supporting hard links etc.
+
+All you should need is a USB cable (or adb over wifi), and the `adb`
+command.
+
+## setting it up
+
+First, initialize your git-annex repository on your computer, if you haven't
+already.
+
+Then, in that repository, set up an adb special remote:
+
+	initremote android type=adb androiddirectory=/sdcard/DCIM encryption=none exporttree=yes importtree=yes
+
+The above example imports files from the /sdcard/DCIM directory of the
+Android device, so it will only import photos and videos, not other files.
+If you wanted to import everything, you could instead use 
+"androiddirectory=/sdcard".
+
+## initial import
+
+Now you can import all files from your Android device:
+
+	git annex import master:android --from android
+	git merge --allow-unrelated-histories android/master
+
+That merges the imported files into the existing contents of your git-annex
+repository. In the example above, the imported files were put into an
+"android" subdirectory, to keep them separate from your other files.
+If you leave off the ":android", the files will be imported into the top of
+the repository.
+
+## initial export
+
+With the files from the Android device imported, you might want to remove
+them from it, to free up space on it. Or, you might add more files that you
+want to export to it, or change files. Whatever changes you make,
+you can `git annex add` and `git commit` as usual. Then to export
+the changed branch to the Android device:
+
+	git annex export master:android --to android
+
+(Again the ":android" limits it to the android directory,
+so leave thatoff if you want to export everything.)
+
+It's fine to export and import in any order and at any time, and you can
+make changes to files on the Android device at any time too. git-annex will
+keep it all in sync.
+
+## automation
+
+Let's automate that syncing process some more.
+
+        git config remote.android.annex-tracking-branch master:android
+
+That configures git-annex to know that you want sync up the master
+branch (specifically the android subdirectory) and your Android device.
+
+Now, you only have to run a single command to sync everything:
+        
+	git annex sync --content
+
+## sample workflows
+
+### photos
+
+The examples above showed how to import photos from your Android device
+into an android subdirectory. If you don't want to keep old photos on your
+Android device, you can simply `git mv` the files out of the android
+directory, and the next sync with the phone will delete them from the
+Android device:
+
+	git mv android/* .
+	git annex sync --content
+
+### music and podcasts
+
+Set up the remote to use the /sdcard/Music directory:
+
+	initremote android type=adb androiddirectory=/sdcard/Music encryption=none exporttree=yes importtree=yes
+
+The rest of the commands are unchanged:
+
+	git annex import master:android --from android
+	git merge --allow-unrelated-histories android/master
+	git annex export master:android --to android
+        git config remote.android.annex-tracking-branch master:android
+	git annex sync --content
+
+With this setup, you can copy music and podcasts you want to listen 
+to over to the Android device, by first copying them to the Android
+directory of your git-annex repo:
+
+	cp -a podcasts/LibreLounge/Episode_14__Secure_Scuttlebutt_with_Joey_Hess.ogg android/
+	git annex add android
+	git annex sync --content
+
+Once you're done with listening to something on the Android device,
+you can simply delete on the device, and the next time git-annex syncs, it
+will get removed from the android directory.
+

thoughts
diff --git a/doc/design/importing_trees_from_special_remotes.mdwn b/doc/design/importing_trees_from_special_remotes.mdwn
index 34ca8eecf..ca5def33e 100644
--- a/doc/design/importing_trees_from_special_remotes.mdwn
+++ b/doc/design/importing_trees_from_special_remotes.mdwn
@@ -193,12 +193,23 @@ The situations to keep in mind are these:
    and before it's downloaded, so the wrong version gets downloaded.
    Need to detect this and fail the import.
 
-The api design has some requirements that, if followed, makes those
-situations be handled well.
-
-## api design
-
-This is an extension to the ExportActions api.
+The API design has some requirements that, if followed, makes those
+situations be handled well. The directory special remote is thus
+able to avoid these situations as well as git does, and the S3 special
+remote with versioning is able to recover data after those situations.
+
+But.. Other types of remotes are limited by remote APIs that don't
+let this be dealt with. If the limitation is explained to the user,
+and they understand how to avoid these situations, importing from
+such remotes could still be supported. Eg, if a user understands
+that modifications they make to files using their phone may get overwritten
+while git-annex is exporting to it, and so avoids using their phone during
+that process (or chooses to only ever modify certian files on their phone),
+then git-annex can safely support importing from their phone.
+
+## API design
+
+This is an extension to the ExportActions API.
 
 	listContents :: Annex (ContentHistory [(ExportLocation, ContentIdentifier)])
 

todo
diff --git a/doc/todo/adb_import.mdwn b/doc/todo/adb_import.mdwn
new file mode 100644
index 000000000..1bfe0a707
--- /dev/null
+++ b/doc/todo/adb_import.mdwn
@@ -0,0 +1,34 @@
+Make adb special remote support import tree.
+
+This would be very useful for syncing with an android device without
+needing to run git-annex on it. While git-annex works well enough in
+termux, the horribleness of android's /sdcard makes it unappealing to put a
+git annex repository on it (direct mode is still the best option there;
+v7 unlocked works but without hard links has to store two copies of each
+file).
+
+This needs at a minimum a way to list files in a directory via adb,
+in order to find new files. `adb shell find /sdcard/ -type f` seems to work
+across a range of android versions (5.1, 8.1).
+
+To avoid re-downloading each file each import, a way to list files
+along with a good content identifier is needed.
+`adb shell find /sdcard/ -type f -exec stat -c "'%d %i %s %Y %n'" {} +`
+works on (5.1, 8.1) (note the weird quoting that it needs)
+
+To avoid losing modifications to files 
+that the user makes using the android device while the same files are being
+exported to it would need an upload to a temp location followed by a check
+that the original is unmodified before renaming. This needs
+shell scripting in android's limited shell environment, or
+`adb shell stat 'origfile'` followed by `adb shell mv 'tmpfile' 'origfile'`.
+
+That is necessarily racy, although the race window is
+probably not much wider than the similar races when git checkout stats
+work tree files before overwriting them.
+
+Alternatively, the documentation could tell the user to avoid modifying files
+on their android device while git-annex is exporting to it, or to instead
+only ever modify files on the android device, and import from it, but not
+export any changes to it. (Or some combination of those 
+for different subdirectories on it.)

update design doc with final design choices
diff --git a/Remote/Helper/ExportImport.hs b/Remote/Helper/ExportImport.hs
index 0053c25c9..6b81ba6ee 100644
--- a/Remote/Helper/ExportImport.hs
+++ b/Remote/Helper/ExportImport.hs
@@ -308,7 +308,7 @@ adjustExportImport r = case M.lookup "exporttree" (config r) of
 			Just () -> Export.updateExportTreeFromLog db >>= \case
 				Export.ExportUpdateSuccess -> return ()
 				Export.ExportUpdateConflict -> do
-					warnExportConflict r
+					warnExportImportConflict r
 					liftIO $ atomically $
 						writeTVar exportinconflict True
 			Nothing -> return ()
diff --git a/doc/design/importing_trees_from_special_remotes.mdwn b/doc/design/importing_trees_from_special_remotes.mdwn
index 4b4d71bc4..34ca8eecf 100644
--- a/doc/design/importing_trees_from_special_remotes.mdwn
+++ b/doc/design/importing_trees_from_special_remotes.mdwn
@@ -50,6 +50,9 @@ to expect there to be one, and if it later turns out that the last exported
 commit needs to be available across clones, store it in the git-annex
 branch then.
 
+Currently: There's a remote tracking branch, but no storage of tracking
+branch info in the git-annex branch.
+
 ## command line interface
 
 `git annex import master --from foo` will import a tree from the remote
@@ -68,7 +71,7 @@ it does not makes sense to import *to* a particular sha.
 Should `git annex import` merge the tracking branch by itself, or leave it
 up to the user? Seems most ergonomic to merge by default; if the user
 wants to not merge it could be `git annex import --fetch --from remote`
-or a separate command.
+or a separate command. Currently: It does not merge.
 
 Also, there should be a way to configure the default tracking branch, so
 `git annex sync --content` first imports from a remote, merges that, and
@@ -77,7 +80,8 @@ configure the latter. It seems to only make sense to import and export the
 same tracking branch. So, should `git annex export --tracking` set the same
 thing, or perhaps it would be better to move the tracking branch
 configuration out of `git annex export` and into an interface that
-explicitly configures both import and export?
+explicitly configures both import and export? Decision: Moved to
+remote.name.annex-tracking-branch setting.
 
 ## content identifiers
 
@@ -144,6 +148,10 @@ could be limited to the size of a typical hash, and if a remote for some
 reason gets something larger, it could simply hash it to generate
 the content identifier.
 
+Decision: Content identifiers do get stored in the git-annex branch.
+It's up to the remote to generate content identifiers that are reasonably
+short.
+
 ## safety
 
 Since the special remote can be written to at any time by something other
@@ -185,6 +193,9 @@ The situations to keep in mind are these:
    and before it's downloaded, so the wrong version gets downloaded.
    Need to detect this and fail the import.
 
+The api design has some requirements that, if followed, makes those
+situations be handled well.
+
 ## api design
 
 This is an extension to the ExportActions api.

reorg section and expand
conflict detection at import time is not detected, but I think it's ok
given this reasoning
diff --git a/doc/design/importing_trees_from_special_remotes.mdwn b/doc/design/importing_trees_from_special_remotes.mdwn
index 3a1db625d..4b4d71bc4 100644
--- a/doc/design/importing_trees_from_special_remotes.mdwn
+++ b/doc/design/importing_trees_from_special_remotes.mdwn
@@ -50,26 +50,6 @@ to expect there to be one, and if it later turns out that the last exported
 commit needs to be available across clones, store it in the git-annex
 branch then.
 
-## export conflict resolution
-
-What if the export log indicates an unresolved export conflict,
-and the user tries to import from the special remote?
-
-Well, two trees got exported to the remote independently. The content of
-the remote is not known to export code when there's a conflict, but import
-will resolve that by getting a list of its contents. Although that may be
-an admixture of the two exported trees, and so not necessarily a change the
-user will want to merge into master.
-
-One approach is to not allow imports in this situation; require the export
-conflict be resolved first. (--force could override if the user just wants
-to import whatever ended up on the special remote.)
-
-Another approach, if the commits that contain the trees that were exported
-is known, is to do the import and make a commit that uses those commits
-as its parents. Which nicely indicates to git that there was a conflict and
-it got "resolved".
-
 ## command line interface
 
 `git annex import master --from foo` will import a tree from the remote
@@ -306,3 +286,36 @@ update the export log to say that the remote has that treeish exported
 to it. A conflict between two export log entries will be handled as
 usual, with the user being prompted to re-export the tree they want
 to be on the remote. (May need to reword that prompt.)
+
+----
+
+What if the export log indicates an unresolved export conflict,
+and the user tries to import from the special remote?
+
+Well, two trees got exported to the remote independently. The content of
+the remote is not known to export code when there's a conflict, but import
+will resolve that by getting a list of its contents. Although that may be
+an admixture of the two exported trees, and so not necessarily a change the
+user will want to merge into master.
+
+One approach is to not allow imports in this situation; require the export
+conflict be resolved first. (--force could override if the user just wants
+to import whatever ended up on the special remote.)
+
+Another approach, if the commits that contain the trees that were exported
+is known, is to do the import and make a commit that uses those commits
+as its parents. Which nicely indicates to git that there was a conflict and
+it got "resolved".
+
+However, note that there can be an export conflict that occurred on another
+clone, and that the local repo does not know about yet (git-annex branch 
+not synced). Importing will then import whatever the current state of the
+export conflict is. The export conflict will eventually be caught at export
+time, and the user can resolve it then. Since this is unavoidable, the two
+approaches above don't seem worth bothering with.
+
+Also, if an export is running at the same time as an import
+(presumably on two different clones), part of the
+changes made by the export will be imported and part not. Again this will
+lead to an export conflict being recorded and the user will have to sort it
+out later at export time.

remove old forum post that is a spam magnet
This was never a useful forum post, so I'm willing to sacrifice it.
diff --git a/doc/forum/Git_annex_on_Windows.mdwn b/doc/forum/Git_annex_on_Windows.mdwn
deleted file mode 100644
index b5ca80bee..000000000
--- a/doc/forum/Git_annex_on_Windows.mdwn
+++ /dev/null
@@ -1,11 +0,0 @@
-Hi,
-I want to download some files in git and git annex in Windows OS.
-I have installed msysgit for git-scm in D:\Git directory,
-Now I download git-annex assistant for Windows, and install it
-in D:\Git\cmd directory.
-But when I run the command "git annex" in git-bash, it says it can not
-found the "git annex" command.
-My question is that, how should I use git annex in Windows to download files?
-For example, git annex get <filename>.
-Doea anyone has any idear to help me figure it out?
-Thanks in advance!
diff --git a/doc/forum/Git_annex_on_Windows/comment_1_6377864848596a7a9ec2577bc1290562._comment b/doc/forum/Git_annex_on_Windows/comment_1_6377864848596a7a9ec2577bc1290562._comment
deleted file mode 100644
index d08f4973d..000000000
--- a/doc/forum/Git_annex_on_Windows/comment_1_6377864848596a7a9ec2577bc1290562._comment
+++ /dev/null
@@ -1,8 +0,0 @@
-[[!comment format=mdwn
- username="joey"
- subject="""comment 1"""
- date="2019-04-09T15:41:32Z"
- content="""
-Seems to me that you must have not followed the windows installation
-process correctly.
-"""]]

response
diff --git a/doc/forum/Git_annex_on_Windows/comment_1_6377864848596a7a9ec2577bc1290562._comment b/doc/forum/Git_annex_on_Windows/comment_1_6377864848596a7a9ec2577bc1290562._comment
new file mode 100644
index 000000000..d08f4973d
--- /dev/null
+++ b/doc/forum/Git_annex_on_Windows/comment_1_6377864848596a7a9ec2577bc1290562._comment
@@ -0,0 +1,8 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 1"""
+ date="2019-04-09T15:41:32Z"
+ content="""
+Seems to me that you must have not followed the windows installation
+process correctly.
+"""]]

remove massive amount of spam comments on this forum post
diff --git a/doc/forum/Git_annex_on_Windows/comment_10_935f41e0dea23e75ae00a7478daf4376._comment b/doc/forum/Git_annex_on_Windows/comment_10_935f41e0dea23e75ae00a7478daf4376._comment
deleted file mode 100644
index 210fecb5d..000000000
--- a/doc/forum/Git_annex_on_Windows/comment_10_935f41e0dea23e75ae00a7478daf4376._comment
+++ /dev/null
@@ -1,8 +0,0 @@
-[[!comment format=mdwn
- username="maryjil2596"
- avatar="http://cdn.libravatar.org/avatar/2ce6b78d907f10b244c92330a4f0bd00"
- subject="Epson Printer Error Code 0x9d"
- date="2019-03-06T07:44:26Z"
- content="""
-Epson is an incredible product. However, there is one thing in my mind, therefore, I want to share issues related to my printer. Whenever I am trying to print any file from the printer an error message shows up on my screen stating \"Error Code 0x9d\". Can anyone guide me <a href=\"https://errorcode0x.com/fix-epson-printer-error-code-0x9d/\">How To Recover the Epson Printer Error Code 0x9d issue?</a> I had tried different methods to solve it but failed. 
-"""]]
diff --git a/doc/forum/Git_annex_on_Windows/comment_11_5aac79a8e1d0a07c669a26ca39d26496._comment b/doc/forum/Git_annex_on_Windows/comment_11_5aac79a8e1d0a07c669a26ca39d26496._comment
deleted file mode 100644
index 726f8e3b2..000000000
--- a/doc/forum/Git_annex_on_Windows/comment_11_5aac79a8e1d0a07c669a26ca39d26496._comment
+++ /dev/null
@@ -1,40 +0,0 @@
-[[!comment format=mdwn
- username="publiwebmaxter@739143dcf7422b8de1502bf2925640bed6ef7014"
- nickname="publiwebmaxter"
- avatar="http://cdn.libravatar.org/avatar/a1a1f6653cc7358140d53785ef7f5f5f"
- subject="comment 11"
- date="2019-03-09T08:33:49Z"
- content="""
-more links info:
-<a href=\"https://www.eurekavideo.co.uk/users/sushi\">https://www.eurekavideo.co.uk/users/sushi</a>
-<a href=\"http://tale-of-tales.com/forum/profile.php?mode=viewprofile&amp;u=43289\">http://tale-of-tales.com/forum/profile.php?mode=viewprofile&amp;u=43289</a>
-<a href=\"https://comfortinstitute.org/members/tocnaza/profile/\">https://comfortinstitute.org/members/tocnaza/profile/</a>
-<a href=\"https://www.wpion.com/members/users/tocnaza/\">https://www.wpion.com/members/users/tocnaza/</a>
-<a href=\"https://www.haikudeck.com/phim-sex-vietnamese-education-presentation-1e8559de6e\">https://www.haikudeck.com/phim-sex-vietnamese-education-presentation-1e8559de6e</a>
-<a href=\"https://www.haikudeck.com/hd-porno-zdarma-education-presentation-8092f474b4\">https://www.haikudeck.com/hd-porno-zdarma-education-presentation-8092f474b4</a>
-<a href=\"https://www.haikudeck.com/german-porno-xxx-education-presentation-eb0b236e55\">https://www.haikudeck.com/german-porno-xxx-education-presentation-eb0b236e55</a>
-<a href=\"http://blossary.termwiki.com/User/tocnaza\">http://blossary.termwiki.com/User/tocnaza</a>
-<a href=\"http://blossary.termwiki.com/Blossary/svensk_porr_twgid1551698734568230\">http://blossary.termwiki.com/Blossary/svensk_porr_twgid1551698734568230</a>
-<a href=\"http://blossary.termwiki.com/Blossary/webcams_x_twgid1551698863480237\">http://blossary.termwiki.com/Blossary/webcams_x_twgid1551698863480237</a>
-<a href=\"https://www.instructables.com/member/tocnaza/\">https://www.instructables.com/member/tocnaza/</a>
-<a href=\"https://forums.aas.org/viewtopic.php?t=10742\">https://forums.aas.org/viewtopic.php?t=10742</a>
-<a href=\"https://forums.aas.org/viewtopic.php?t=10743\">https://forums.aas.org/viewtopic.php?t=10743</a>
-<a href=\"https://www.wpdownloadmanager.com/support/users/micuki/\">https://www.wpdownloadmanager.com/support/users/micuki/</a>
-<a href=\"http://commons.pelagios.org/members/javimuro/\">http://commons.pelagios.org/members/javimuro/</a>
-<a href=\"https://forum.mratwork.com/profile/?u=10404\">https://forum.mratwork.com/profile/?u=10404</a>
-<a href=\"https://help.altmetric.com/support/discussions/topics/6000038049\">https://help.altmetric.com/support/discussions/topics/6000038049</a>
-<a href=\"https://refind.com/carlos-lachaplan\">https://refind.com/carlos-lachaplan</a>
-<a href=\"https://www.treiber.de/forum/thema/68451/Samsung-Wave-2-Gt-8530-Upgrade/\">https://www.treiber.de/forum/thema/68451/Samsung-Wave-2-Gt-8530-Upgrade/</a>
-<a href=\"https://www.designnominees.com/profile/solero\">https://www.designnominees.com/profile/solero</a>
-<a href=\"https://projectnursery.com/author/tocnaza/\">https://projectnursery.com/author/tocnaza/</a>
-<a href=\"http://flyfreemedia.com/forums/users/tocnazax\">http://flyfreemedia.com/forums/users/tocnazax</a>
-<a href=\"https://www.invoiceninja.com/forums/users/tocnazax/\">https://www.invoiceninja.com/forums/users/tocnazax/</a>
-<a href=\"https://www.bikramyoga.com/forums/users/tocnazax/\">https://www.bikramyoga.com/forums/users/tocnazax/</a>
-<a href=\"http://support.themely.com/forums/users/tocnazax/\">http://support.themely.com/forums/users/tocnazax/</a>
-<a href=\"http://forum.newzimbabwe.com/forums/users/tocnazax/\">http://forum.newzimbabwe.com/forums/users/tocnazax/</a>
-<a href=\"https://warptheme.com/forums/users/tocnazax/\">https://warptheme.com/forums/users/tocnazax/</a>
-<a href=\"https://www.motorists.org/forums/users/tocnazax/\">https://www.motorists.org/forums/users/tocnazax/</a>
-<a href=\"https://www.fmylife.com/index.php/user/357687733\">https://www.fmylife.com/index.php/user/357687733</a>
-<a href=\"https://www.hondencentrum.com/tocnaza/\">https://www.hondencentrum.com/tocnaza/</a>
-<a href=\"https://my.olympus-consumer.com/members/javimurox\">https://my.olympus-consumer.com/members/javimurox</a>
-"""]]
diff --git a/doc/forum/Git_annex_on_Windows/comment_12_ea0c0eda7a0e57da3a78e82a0fd0bab5._comment b/doc/forum/Git_annex_on_Windows/comment_12_ea0c0eda7a0e57da3a78e82a0fd0bab5._comment
deleted file mode 100644
index 61ffca642..000000000
--- a/doc/forum/Git_annex_on_Windows/comment_12_ea0c0eda7a0e57da3a78e82a0fd0bab5._comment
+++ /dev/null
@@ -1,9 +0,0 @@
-[[!comment format=mdwn
- username="adamdwalker"
- avatar="http://cdn.libravatar.org/avatar/b1363a1838d2caa87b4fede9af2eb660"
- subject="IIHF"
- date="2019-04-05T12:37:57Z"
- content="""
-Get the latest New Jersey Devils news, photos, rankings, lists and more on Bleacher Report. ... Which NJ Devils could play in the IIHF World Championships?
-Searches related to <a href=\"https://iihfworldchampionships2019.com/\">IIHF Hockey World Championship</a>.
-"""]]
diff --git a/doc/forum/Git_annex_on_Windows/comment_13_f42e453b9956ddc5c9c2bb6f16e98837._comment b/doc/forum/Git_annex_on_Windows/comment_13_f42e453b9956ddc5c9c2bb6f16e98837._comment
deleted file mode 100644
index fd1089977..000000000
--- a/doc/forum/Git_annex_on_Windows/comment_13_f42e453b9956ddc5c9c2bb6f16e98837._comment
+++ /dev/null
@@ -1,10 +0,0 @@
-[[!comment format=mdwn
- username="jillcaballero"
- avatar="http://cdn.libravatar.org/avatar/9ba850742492f7e44e93448daa17fe76"
- subject="Kentucky Derby"
- date="2019-04-06T13:14:50Z"
- content="""
-Welcome to Horse Racing Nation’s <a href=\"https://kentuckyderbystream.com/\">Kentucky Derby Live Stream</a>  Daily, which will each day leading up to the May 4 race at Churchill Downs detail all the news and notes related to contenders in one convenient space.
-
-
-"""]]
diff --git a/doc/forum/Git_annex_on_Windows/comment_1_da24ba0219a164f9ab93fe75dd85127e._comment b/doc/forum/Git_annex_on_Windows/comment_1_da24ba0219a164f9ab93fe75dd85127e._comment
deleted file mode 100644
index be50ece07..000000000
--- a/doc/forum/Git_annex_on_Windows/comment_1_da24ba0219a164f9ab93fe75dd85127e._comment
+++ /dev/null
@@ -1,11 +0,0 @@
-[[!comment format=mdwn
- username="http://joeyh.name/"
- ip="4.153.251.174"
- subject="comment 1"
- date="2013-09-07T17:00:03Z"
- content="""
-Are you able to run git commands? IIRC msysgit prompts when it's installed about whether you want to put it in the path or not. git-annex just piggybacks on this path setting. It is installed in the same folder as the git.exe and should work as long as that is in path.
-Otherwise, consult windows documentation to add git-annex to the path, or you can copy the git-annex.exe to somewhere else I suppose.
-
-I built a clean Windows system yesterday and have just re-tested it and it does work.
-"""]]
diff --git a/doc/forum/Git_annex_on_Windows/comment_2_c0880ce3ee13d388ab5b46a740170845._comment b/doc/forum/Git_annex_on_Windows/comment_2_c0880ce3ee13d388ab5b46a740170845._comment
deleted file mode 100644
index bdf30b3b7..000000000
--- a/doc/forum/Git_annex_on_Windows/comment_2_c0880ce3ee13d388ab5b46a740170845._comment
+++ /dev/null
@@ -1,50 +0,0 @@
-[[!comment format=mdwn
- username="https://www.google.com/accounts/o8/id?id=AItOawkQrsXK-icnYXg6kJNd-jDjMgOixnhwE34"
- nickname="x"
- subject="reply to Comment 1"
- date="2013-09-10T13:46:45Z"
- content="""
-Thanks for your helpful comment.I add the path to windows, and the
-problem disappears now.
-But I meet another problem when I download the data using git annex.
-I use the command \"git annex get foo.nc\" to download data. The foo.nc
-is actually symlink. For example:
-foo.nc -> ../../.git/annex/objects/jK/v7/WORM-s16009120-m1337754158--
-foo.nc/WORM-s16009120-m1337754158--foo.nc
-Could you help me to figure it out?
-Thank you.
-
-The erro information when using git annex in Windows, is as below:
-
-$ git annex get tau.nc
- 
-   Detected a crippled filesystem.
-
-   Enabling direct mode.
-
-   Detected a filesystem without fifo support.
-
-   Disabling ssh connection caching.
-
-*** Please tell me who you are.
- 
- 
-
-Run 
-
-    git config --global user.email \"you@example.com\"
-
-    git config --user.name \"Your Name\"
- 
-to set your account's default identity.
-
-Omit --global to set the identity only in this repository.
-
- 
-
-fatal: unable to auto-detect email address (got 'xshao@DELL-PC.(none')
- 
-git-annex :tau.nc not found
-
-(Recording state in git ...)
-"""]]
diff --git a/doc/forum/Git_annex_on_Windows/comment_3_70c22716fde60d14fd0c7e74acf4a224._comment b/doc/forum/Git_annex_on_Windows/comment_3_70c22716fde60d14fd0c7e74acf4a224._comment
deleted file mode 100644
index 772d9348a..000000000
--- a/doc/forum/Git_annex_on_Windows/comment_3_70c22716fde60d14fd0c7e74acf4a224._comment
+++ /dev/null
@@ -1,11 +0,0 @@
-[[!comment format=mdwn
- username="https://www.google.com/accounts/o8/id?id=AItOawkQrsXK-icnYXg6kJNd-jDjMgOixnhwE34"
- nickname="x"
- subject="Comment3"
- date="2013-09-10T15:36:57Z"
- content="""
-In addition, because the file is actually symlink direct to the data stored in Amazon S3
-How could I get the URL, given the symlink for git annex. For example:
-foo.nc -> ../../.git/annex/objects/jK/v7/WORM-s16009120-m1337754158--foo.nc/WORM-s16009120-m1337754158--foo.nc
-Thank you.
-"""]]
diff --git a/doc/forum/Git_annex_on_Windows/comment_4_b9232deab6bc5036d7339aa202013218._comment b/doc/forum/Git_annex_on_Windows/comment_4_b9232deab6bc5036d7339aa202013218._comment
deleted file mode 100644
index 6fd2f8c3d..000000000
--- a/doc/forum/Git_annex_on_Windows/comment_4_b9232deab6bc5036d7339aa202013218._comment
+++ /dev/null
@@ -1,12 +0,0 @@
-[[!comment format=mdwn
- username="http://joeyh.name/"
- ip="4.154.4.51"
- subject="comment 4"
- date="2013-09-12T20:58:30Z"
- content="""
-Once `git annex get` has downloaded the file, it will replace the symlink with the contents of the file.
-
-If that is not happening, you might try running `git annex fsck`
-
-
-"""]]
diff --git a/doc/forum/Git_annex_on_Windows/comment_5_27af3c431b50b540d2bd1d3af3f21080._comment b/doc/forum/Git_annex_on_Windows/comment_5_27af3c431b50b540d2bd1d3af3f21080._comment

(Diff truncated)
doc clarification
diff --git a/doc/forum/short_exlusive_refspec_notation_for_git_annex_unused_/comment_1_0aeb5702e74fcf158f1e9aca16ca9e6b._comment b/doc/forum/short_exlusive_refspec_notation_for_git_annex_unused_/comment_1_0aeb5702e74fcf158f1e9aca16ca9e6b._comment
new file mode 100644
index 000000000..4184ccff8
--- /dev/null
+++ b/doc/forum/short_exlusive_refspec_notation_for_git_annex_unused_/comment_1_0aeb5702e74fcf158f1e9aca16ca9e6b._comment
@@ -0,0 +1,19 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 1"""
+ date="2019-04-09T15:16:12Z"
+ content="""
+       Each - is matched against the set of refs accu‐
+       mulated  so far.  Any matching refs are removed
+       from the set.
+
+It matches against the literal text of the ref that was added, so if you
+ use "+*", it adds refs/heads/master, and then to remove that, you need
+ "-refs/heads/master" not "-master". On the other hand, "+master:-master"
+results in "master" being added and then removed.
+
+Clarified to mention that it matches by name; I suppose perhaps you were
+thinking it matches based on what sha1 the ref name resolves to. The reason it
+doesn't do that is that it would be surprising for "+foo:-master" to not include
+ref foo just because it happens to currently have the same sha1 as master does.
+"""]]
diff --git a/doc/git-annex-unused.mdwn b/doc/git-annex-unused.mdwn
index 36bab6951..5dbb25247 100644
--- a/doc/git-annex-unused.mdwn
+++ b/doc/git-annex-unused.mdwn
@@ -64,7 +64,7 @@ Each + without a glob adds the literal value to the set.
 For example, "+HEAD^" adds "HEAD^".
 
 Each - is matched against the set of refs accumulated so far.
-Any matching refs are removed from the set.
+Any refs with names that match are removed from the set.
 
 "reflog" adds all the refs from the reflog. This will make past versions
 of files not be considered to be unused until the ref expires from the

comment
diff --git a/doc/forum/git_lfs_special_remote_implementation/comment_1_a61494b02c831e84903f28d9900850ac._comment b/doc/forum/git_lfs_special_remote_implementation/comment_1_a61494b02c831e84903f28d9900850ac._comment
new file mode 100644
index 000000000..e903b3343
--- /dev/null
+++ b/doc/forum/git_lfs_special_remote_implementation/comment_1_a61494b02c831e84903f28d9900850ac._comment
@@ -0,0 +1,7 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 1"""
+ date="2019-04-09T15:12:22Z"
+ content="""
+See [[todo/LFS_API_support]].
+"""]]

comment
diff --git a/doc/forum/Git-annex_with_dumb_FAT32_devices_not_a_valid_use_case__63__/comment_4_a8a79961d97fe773c1855632b4772c5b._comment b/doc/forum/Git-annex_with_dumb_FAT32_devices_not_a_valid_use_case__63__/comment_4_a8a79961d97fe773c1855632b4772c5b._comment
new file mode 100644
index 000000000..4361c9583
--- /dev/null
+++ b/doc/forum/Git-annex_with_dumb_FAT32_devices_not_a_valid_use_case__63__/comment_4_a8a79961d97fe773c1855632b4772c5b._comment
@@ -0,0 +1,11 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 4"""
+ date="2019-04-09T15:09:24Z"
+ content="""
+I see no reason to add such filename munging to git-annex, controlling the
+names of files in the working tree is well out of its scope. It could be in
+scope for git, but more likely, if this is a problem for you, you need to
+set up your own policy for what filenames are allowed in your repository,
+and use existing facilities to enforce it (git hooks, etc).
+"""]]

comment
diff --git a/doc/todo/globus_special_remote_as_a___34__transport__34___layer/comment_1_f2c68afc949f54939fc760bd0d916b89._comment b/doc/todo/globus_special_remote_as_a___34__transport__34___layer/comment_1_f2c68afc949f54939fc760bd0d916b89._comment
new file mode 100644
index 000000000..b3ad72aaa
--- /dev/null
+++ b/doc/todo/globus_special_remote_as_a___34__transport__34___layer/comment_1_f2c68afc949f54939fc760bd0d916b89._comment
@@ -0,0 +1,21 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 1"""
+ date="2019-04-09T14:54:51Z"
+ content="""
+It's not currently possible for two special remotes to have the same uuid,
+because the remote.log is indexed by uuid, and so their configurations would
+overlap, including the type= and remotetype= settings.
+
+But I think in this case, that may not be a problem, it seems you have a
+regular remote accessed via ssh, and you want to add a special remote with
+the same uuid that transfers from the same remote using globus. This is
+like accessing the same repo via two ssh remotes etc, should work ok.
+
+You can pass uuid=whatever to git-annex initremote to force it to use the
+same uuid as the ssh remote.
+
+(Returning to the question of two special remotes with the same uuid,
+supporting that would need some way to separate their configurations
+in remote.log into different namespaces. Seems doable.)
+"""]]

Added a comment: Kentucky Derby
diff --git a/doc/forum/Git_annex_on_Windows/comment_13_f42e453b9956ddc5c9c2bb6f16e98837._comment b/doc/forum/Git_annex_on_Windows/comment_13_f42e453b9956ddc5c9c2bb6f16e98837._comment
new file mode 100644
index 000000000..fd1089977
--- /dev/null
+++ b/doc/forum/Git_annex_on_Windows/comment_13_f42e453b9956ddc5c9c2bb6f16e98837._comment
@@ -0,0 +1,10 @@
+[[!comment format=mdwn
+ username="jillcaballero"
+ avatar="http://cdn.libravatar.org/avatar/9ba850742492f7e44e93448daa17fe76"
+ subject="Kentucky Derby"
+ date="2019-04-06T13:14:50Z"
+ content="""
+Welcome to Horse Racing Nation’s <a href=\"https://kentuckyderbystream.com/\">Kentucky Derby Live Stream</a>  Daily, which will each day leading up to the May 4 race at Churchill Downs detail all the news and notes related to contenders in one convenient space.
+
+
+"""]]

update
diff --git a/doc/thanks/list b/doc/thanks/list
index cf382a4e6..f5dff19b4 100644
--- a/doc/thanks/list
+++ b/doc/thanks/list
@@ -55,3 +55,5 @@ Nicolas Pouillard,
 Tyler Cipriani, 
 Josh Moller-Mara, 
 Lp and Nick Daly, 
+Walltime, 
+Caleb Allen, 

Added a comment: IIHF
diff --git a/doc/forum/Git_annex_on_Windows/comment_12_ea0c0eda7a0e57da3a78e82a0fd0bab5._comment b/doc/forum/Git_annex_on_Windows/comment_12_ea0c0eda7a0e57da3a78e82a0fd0bab5._comment
new file mode 100644
index 000000000..61ffca642
--- /dev/null
+++ b/doc/forum/Git_annex_on_Windows/comment_12_ea0c0eda7a0e57da3a78e82a0fd0bab5._comment
@@ -0,0 +1,9 @@
+[[!comment format=mdwn
+ username="adamdwalker"
+ avatar="http://cdn.libravatar.org/avatar/b1363a1838d2caa87b4fede9af2eb660"
+ subject="IIHF"
+ date="2019-04-05T12:37:57Z"
+ content="""
+Get the latest New Jersey Devils news, photos, rankings, lists and more on Bleacher Report. ... Which NJ Devils could play in the IIHF World Championships?
+Searches related to <a href=\"https://iihfworldchampionships2019.com/\">IIHF Hockey World Championship</a>.
+"""]]

initial question about possible "globus" special remote
diff --git a/doc/todo/globus_special_remote_as_a___34__transport__34___layer.mdwn b/doc/todo/globus_special_remote_as_a___34__transport__34___layer.mdwn
new file mode 100644
index 000000000..9380d6835
--- /dev/null
+++ b/doc/todo/globus_special_remote_as_a___34__transport__34___layer.mdwn
@@ -0,0 +1,4 @@
+One of my collaborators needs to orchestrate data between local desktop and HPC cluster (you probably have heard enough already about some of the "experiences" with that NFS). Connection to the cluster goes through VPN, which is flaky (can fall within an hour or two) and requires 2FA to get in - so not that easy to transfer large amounts of data back and forth. BUT we were told that the same data is available via globus, without requiring VPNC.  So looking at https://docs.globus.org/cli/examples/ I wonder if there would be anything which would preclude having an additional special remote to provide an alternative access to the same remote (same UUID) to just take care about depositing, obtaining, and may be removing files via globus, instead of ssh.  We kinda have already similarish scenarios where we publish annex via ssh, but making it available via http for downloads.  If remote location is a typical indirect annex (not a super thin version of it without duplicate copy under .git/annex/objects), it should be quite easy I guess to figure out full path to the key (although might need to watch out for bare ones) -- should be as it was locally -- and just get the file via globus cli instead of ssh session.
+Decided to ask before jumping into trying to implement it (not that I have any globus access ATM - I think all life signs of it were gone from dartmouth sites awhile back).
+
+[[!meta author=yoh]]

close as basis of this is wrong
diff --git a/doc/todo/inneficiency_on_slow_filesystems_opening_nonexistant_journal_files.mdwn b/doc/todo/inneficiency_on_slow_filesystems_opening_nonexistant_journal_files.mdwn
index dce5120e8..8ffae4e86 100644
--- a/doc/todo/inneficiency_on_slow_filesystems_opening_nonexistant_journal_files.mdwn
+++ b/doc/todo/inneficiency_on_slow_filesystems_opening_nonexistant_journal_files.mdwn
@@ -54,3 +54,7 @@ hard to plumb through to the git-annex branch reading code.
 An easier alternative would be an option that bypasses reading the journal.
 But maybe there's some other, better way to avoid this slow case?
 --[[Joey]]
+
+> yoh benchmarked the above patch on the slow NFS system, and it did not
+> result in a notable difference in speed, so it seems the basis of this
+> todo is false. [[done]] --[[Joey]]

comment
diff --git a/doc/forum/Checking_that_everything_is_committed/comment_1_875c22110d65c0d8e6ef6aebced87e95._comment b/doc/forum/Checking_that_everything_is_committed/comment_1_875c22110d65c0d8e6ef6aebced87e95._comment
new file mode 100644
index 000000000..eb0b6b0c6
--- /dev/null
+++ b/doc/forum/Checking_that_everything_is_committed/comment_1_875c22110d65c0d8e6ef6aebced87e95._comment
@@ -0,0 +1,23 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 1"""
+ date="2019-04-03T17:19:36Z"
+ content="""
+So specifically, this happens for unlocked files in a v7 repository, 
+but only when the files are empty.
+
+I suspect this is a bug in git. It might have something to do with
+the mention in git-diff-files(1) and git-diff(1) about empty files:
+
+       --ita-invisible-in-index
+           By default entries added by "git add -N" appear as an existing
+           empty file in "git diff" and a new file in "git diff --cached".
+
+And `git diff` similarly shows a diff for these empty unlocked files.
+
+Makes me suspect there's some hack going on in git WRT empty
+files and perhaps it bypasses the smudge/clean filters?
+
+I usually use `git diff --cached` for this kind of thing, and it doesn't have
+the problem, but I don't know if it meets your needs either.
+"""]]

comment
diff --git a/doc/todo/document_git-annex_dependencies/comment_1_bb9cbd703e57adb9ca45e2cea94308a0._comment b/doc/todo/document_git-annex_dependencies/comment_1_bb9cbd703e57adb9ca45e2cea94308a0._comment
new file mode 100644
index 000000000..9b0e30578
--- /dev/null
+++ b/doc/todo/document_git-annex_dependencies/comment_1_bb9cbd703e57adb9ca45e2cea94308a0._comment
@@ -0,0 +1,12 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 1"""
+ date="2019-04-03T17:12:38Z"
+ content="""
+There is a comprehensive list (AFAIK) in the debian/control file's
+Depends, Recommends, and Suggests.
+
+As far as exactly where each is used, that's pretty easy to grep the code
+for (search for `"$command"`) and would be a lot of documentation to write
+and keep up to date.
+"""]]

comment
diff --git a/doc/design/p2p_protocol/comment_5_08b190ff1c6d1e890311edf7cc7bfcd4._comment b/doc/design/p2p_protocol/comment_5_08b190ff1c6d1e890311edf7cc7bfcd4._comment
new file mode 100644
index 000000000..75b25ba49
--- /dev/null
+++ b/doc/design/p2p_protocol/comment_5_08b190ff1c6d1e890311edf7cc7bfcd4._comment
@@ -0,0 +1,20 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 5"""
+ date="2019-04-03T17:03:04Z"
+ content="""
+While it's true that most keys have a size field giving their size, in the
+context of this protocol, it's more relevant that the DATA message
+indicates the number of bytes of content that are going to be transmitted;
+once the receiver has sucessfully read that many bytes of content, it knows
+it has the whole content of the key.
+
+When resuming a previous transfer that has been interrupted, if the
+reciever happened to have all the content of the key, it would send GET
+with the number of bytes it already has, and the reply would be "DATA 0"
+which tells it that it already has all the content.
+
+If the whole content of the key has been received and a hash verification
+fails, git-annex throws away the corrupt data, since this protocol does not
+provide a way to recover from such a problem.
+"""]]

comment
diff --git a/doc/git-annex-lookupkey/comment_2_897eaca8174d5f568a19805f90d9e1c3._comment b/doc/git-annex-lookupkey/comment_2_897eaca8174d5f568a19805f90d9e1c3._comment
new file mode 100644
index 000000000..de1034d9f
--- /dev/null
+++ b/doc/git-annex-lookupkey/comment_2_897eaca8174d5f568a19805f90d9e1c3._comment
@@ -0,0 +1,8 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 2"""
+ date="2019-04-03T16:58:53Z"
+ content="""
+git-annex has several global options that are documented in the main
+git-annex man page.
+"""]]

fix name of --trust-glacier command in man page
diff --git a/doc/git-annex.mdwn b/doc/git-annex.mdwn
index 0ed08e184..6e11904e6 100644
--- a/doc/git-annex.mdwn
+++ b/doc/git-annex.mdwn
@@ -794,7 +794,7 @@ may not be explicitly listed on their individual man pages.
   The repository should be specified using the name of a configured remote,
   or the UUID or description of a repository.
 
-* `--trust-glacier-inventory`
+* `--trust-glacier`
 
   Amazon Glacier inventories take hours to retrieve, and may not represent
   the current state of a repository. So git-annex does not trust that

be more explicit about new hash format
diff --git a/doc/internals/hashing.mdwn b/doc/internals/hashing.mdwn
index bdc259b63..9895cad0e 100644
--- a/doc/internals/hashing.mdwn
+++ b/doc/internals/hashing.mdwn
@@ -19,7 +19,8 @@ below is only for completeness.
 
 This uses two directories, each with a three-letter name, such as "f87/4d5"
 
-The directory names come from the md5sum of the [[key|key_format]].
+The directory names come from the first 6 characters of the md5sum of the [[key|key_format]]
+when serialized as a hex string.
 
 For example:
 

Added a comment: re: key content size
diff --git a/doc/design/p2p_protocol/comment_4_94fff4c163de15cdad2030ac072b19ae._comment b/doc/design/p2p_protocol/comment_4_94fff4c163de15cdad2030ac072b19ae._comment
new file mode 100644
index 000000000..7b59e143c
--- /dev/null
+++ b/doc/design/p2p_protocol/comment_4_94fff4c163de15cdad2030ac072b19ae._comment
@@ -0,0 +1,8 @@
+[[!comment format=mdwn
+ username="Ilya_Shlyakhter"
+ avatar="http://cdn.libravatar.org/avatar/1647044369aa7747829c38b9dcc84df0"
+ subject="re: key content size"
+ date="2019-04-01T17:44:29Z"
+ content="""
+Most keys do include the size of the content as part of the key: see [[internals/key_format]], [[git-annex-examinekey]].
+"""]]

removed
diff --git a/doc/forum/git_annex_hanging_in_smudge_on_2k_file_on_rpi/comment_4_ec517dcc00fe1e08813ef046c2b82941._comment b/doc/forum/git_annex_hanging_in_smudge_on_2k_file_on_rpi/comment_4_ec517dcc00fe1e08813ef046c2b82941._comment
deleted file mode 100644
index f113fcd99..000000000
--- a/doc/forum/git_annex_hanging_in_smudge_on_2k_file_on_rpi/comment_4_ec517dcc00fe1e08813ef046c2b82941._comment
+++ /dev/null
@@ -1,9 +0,0 @@
-[[!comment format=mdwn
- username="maryjil2596"
- avatar="http://cdn.libravatar.org/avatar/2ce6b78d907f10b244c92330a4f0bd00"
- subject="aol account recovery"
- date="2019-04-01T06:52:11Z"
- content="""
-I am writing this post for the people who are facing a problem with their AOL mail account due to some technical error and are unable to send and receive important emails. Follow this guide <a href=\"=https://emailsupports.net/aol-account-recovery/\">aol account recovery</a> and recover your AOL mail within a short span of time.
-
-"""]]

Added a comment: aol account recovery
diff --git a/doc/forum/git_annex_hanging_in_smudge_on_2k_file_on_rpi/comment_4_ec517dcc00fe1e08813ef046c2b82941._comment b/doc/forum/git_annex_hanging_in_smudge_on_2k_file_on_rpi/comment_4_ec517dcc00fe1e08813ef046c2b82941._comment
new file mode 100644
index 000000000..f113fcd99
--- /dev/null
+++ b/doc/forum/git_annex_hanging_in_smudge_on_2k_file_on_rpi/comment_4_ec517dcc00fe1e08813ef046c2b82941._comment
@@ -0,0 +1,9 @@
+[[!comment format=mdwn
+ username="maryjil2596"
+ avatar="http://cdn.libravatar.org/avatar/2ce6b78d907f10b244c92330a4f0bd00"
+ subject="aol account recovery"
+ date="2019-04-01T06:52:11Z"
+ content="""
+I am writing this post for the people who are facing a problem with their AOL mail account due to some technical error and are unable to send and receive important emails. Follow this guide <a href=\"=https://emailsupports.net/aol-account-recovery/\">aol account recovery</a> and recover your AOL mail within a short span of time.
+
+"""]]

removed
diff --git a/doc/design/p2p_protocol/comment_3_72d9bd6eff2618b23e63a9422bf8c79b._comment b/doc/design/p2p_protocol/comment_3_72d9bd6eff2618b23e63a9422bf8c79b._comment
deleted file mode 100644
index a68ba23cc..000000000
--- a/doc/design/p2p_protocol/comment_3_72d9bd6eff2618b23e63a9422bf8c79b._comment
+++ /dev/null
@@ -1,9 +0,0 @@
-[[!comment format=mdwn
- username="driusan@4d47e7deeb2f5d3846792d049ed06f96a0c3ca98"
- nickname="driusan"
- avatar="http://cdn.libravatar.org/avatar/409b69c3ae7b431fc16129ccdadae9cd"
- subject="key content size"
- date="2019-03-31T16:31:09Z"
- content="""
-Is there a mechanism for a client to determine the size of the content pointed to by the key on the remote? How do you determine that all the content is received? If you rely on verifying sha256 (or whatever hash) of the key, I don't see any way you can tell if the object in a local annex is corrupted or just not fully received and should be updated with GET from a higher offset.
-"""]]

Added a comment: key content size
diff --git a/doc/design/p2p_protocol/comment_4_f48e73ea2b6f70597837d09d3c5d3849._comment b/doc/design/p2p_protocol/comment_4_f48e73ea2b6f70597837d09d3c5d3849._comment
new file mode 100644
index 000000000..9b89b8771
--- /dev/null
+++ b/doc/design/p2p_protocol/comment_4_f48e73ea2b6f70597837d09d3c5d3849._comment
@@ -0,0 +1,9 @@
+[[!comment format=mdwn
+ username="driusan@4d47e7deeb2f5d3846792d049ed06f96a0c3ca98"
+ nickname="driusan"
+ avatar="http://cdn.libravatar.org/avatar/409b69c3ae7b431fc16129ccdadae9cd"
+ subject="key content size"
+ date="2019-03-31T16:31:28Z"
+ content="""
+Is there a mechanism for a client to determine the size of the content pointed to by the key on the remote? How do you determine that all the content is received? If you rely on verifying sha256 (or whatever hash) of the key, I don't see any way you can tell if the object in a local annex is corrupted or just not fully received and should be updated with GET from a higher offset.
+"""]]

Added a comment: key content size
diff --git a/doc/design/p2p_protocol/comment_3_72d9bd6eff2618b23e63a9422bf8c79b._comment b/doc/design/p2p_protocol/comment_3_72d9bd6eff2618b23e63a9422bf8c79b._comment
new file mode 100644
index 000000000..a68ba23cc
--- /dev/null
+++ b/doc/design/p2p_protocol/comment_3_72d9bd6eff2618b23e63a9422bf8c79b._comment
@@ -0,0 +1,9 @@
+[[!comment format=mdwn
+ username="driusan@4d47e7deeb2f5d3846792d049ed06f96a0c3ca98"
+ nickname="driusan"
+ avatar="http://cdn.libravatar.org/avatar/409b69c3ae7b431fc16129ccdadae9cd"
+ subject="key content size"
+ date="2019-03-31T16:31:09Z"
+ content="""
+Is there a mechanism for a client to determine the size of the content pointed to by the key on the remote? How do you determine that all the content is received? If you rely on verifying sha256 (or whatever hash) of the key, I don't see any way you can tell if the object in a local annex is corrupted or just not fully received and should be updated with GET from a higher offset.
+"""]]

Added a comment: Options don't match git-annex lookupkey --help
diff --git a/doc/git-annex-lookupkey/comment_1_100fcc1559449ae99a2dc6eade61662c._comment b/doc/git-annex-lookupkey/comment_1_100fcc1559449ae99a2dc6eade61662c._comment
new file mode 100644
index 000000000..78c66e025
--- /dev/null
+++ b/doc/git-annex-lookupkey/comment_1_100fcc1559449ae99a2dc6eade61662c._comment
@@ -0,0 +1,49 @@
+[[!comment format=mdwn
+ username="driusan@4d47e7deeb2f5d3846792d049ed06f96a0c3ca98"
+ nickname="driusan"
+ avatar="http://cdn.libravatar.org/avatar/409b69c3ae7b431fc16129ccdadae9cd"
+ subject="Options don't match git-annex lookupkey --help"
+ date="2019-03-30T16:05:29Z"
+ content="""
+The options in this man page don't quite match what shows up with git-annex lookupkey --help. `--help` seems to include a lot of options that are non-sensicle in the context of lookup key.
+
+
+> % git-annex lookupkey --help
+> git-annex lookupkey - looks up key used for file
+>
+> Usage: git-annex lookupkey [--batch] [-z] [FILE ...]
+>
+>Available options:
+>  --batch                  enable batch mode
+>  -z                       null delimited batch input
+>  --force                  allow actions that may lose annexed data
+>  -F,--fast                avoid slow operations
+>  -q,--quiet               avoid verbose output
+>  -v,--verbose             allow verbose output (default)
+>  -d,--debug               show debug messages
+>  --no-debug               don't show debug messages
+>  -b,--backend NAME        specify key-value backend to use
+>  -N,--numcopies NUMBER    override default number of copies
+>  --trust REMOTE           override trust setting
+>  --semitrust REMOTE       override trust setting back to default
+>  --untrust REMOTE         override trust setting to untrusted
+>  -c,--config NAME=VALUE   override git configuration setting
+>  --user-agent NAME        override default User-Agent
+>  --trust-glacier          Trust Amazon Glacier inventory
+>  --notify-finish          show desktop notification after transfer finishes
+>  --notify-start           show desktop notification after transfer starts
+>  -h,--help                Show this help text
+>
+>For details, run: git-annex help lookupkey
+>% git-annex version
+>git-annex version: 7.20190322-gbc302b56a
+>build flags: S3(multipartupload)(storageclasses) TorrentParser Feeds Testsuite
+>dependency versions: aws-0.21.1 bloomfilter-2.0.1.0 cryptonite-0.25 feed-1.0.1.0 ghc-8.6.3 http-client-0.6.2 persistent-sqlite-2.9.2 torrent-10000.1.1 uuid-1.3.13
+>key/value backends: SHA256E SHA256 SHA512E SHA512 SHA224E SHA224 SHA384E SHA384 SHA3_256E SHA3_256 SHA3_512E SHA3_512 SHA3_224E SHA3_224 SHA3_384E SHA3_384 SKEIN256E SKEIN256 SKEIN512E SKEIN512 BLAKE2B256E BLAKE2B256 BLAKE2B512E BLAKE2B512 BLAKE2B160E BLAKE2B160 BLAKE2B224E BLAKE2B224 BLAKE2B384E BLAKE2B384 BLAKE2S256E BLAKE2S256 BLAKE2S160E BLAKE2S160 BLAKE2S224E BLAKE2S224 BLAKE2SP256E BLAKE2SP256 BLAKE2SP224E BLAKE2SP224 SHA1E SHA1 MD5E MD5 WORM URL
+>remote types: git gcrypt p2p S3 bup directory rsync web bittorrent adb tahoe glacier ddar hook external
+>operating system: dragonfly x86_64
+>supported repository versions: 5 7
+>upgrade supported from repository versions: 0 1 2 3 4 5 6
+>local repository version: 5
+
+"""]]

Added a comment: Warning building with cabal
diff --git a/doc/install/fromsource/comment_74_473d320a05f08ce3cbe24789dcb01200._comment b/doc/install/fromsource/comment_74_473d320a05f08ce3cbe24789dcb01200._comment
new file mode 100644
index 000000000..e02b0c53c
--- /dev/null
+++ b/doc/install/fromsource/comment_74_473d320a05f08ce3cbe24789dcb01200._comment
@@ -0,0 +1,22 @@
+[[!comment format=mdwn
+ username="driusan@4d47e7deeb2f5d3846792d049ed06f96a0c3ca98"
+ nickname="driusan"
+ avatar="http://cdn.libravatar.org/avatar/409b69c3ae7b431fc16129ccdadae9cd"
+ subject="Warning building with cabal"
+ date="2019-03-30T00:19:10Z"
+ content="""
+I had to build with cabal on DragonFlyBSD because stack isn't available (which is presumably the reason it's not in dports even though it builds cleanly.)
+
+Everything worked after, except all the cabal commands gave warnings of the type:
+
+> Warning: The install command is a part of the legacy v1 style of cabal usage.
+> 
+> Please switch to using either the new project style and the new-install
+command or the legacy v1-install alias as new-style projects will become the
+default in the next version of cabal-install. Please file a bug if you cannot
+replicate a working v1- use case with the new-style commands.
+>
+> For more information, see: https://wiki.haskell.org/Cabal/NewBuild
+
+I don't know much about \"new style\" and \"legacy\" commands in cabal, but instructions should probably be cleaned up to get around these warnings at some point.
+"""]]

test patch
diff --git a/doc/todo/inneficiency_on_slow_filesystems_opening_nonexistant_journal_files.mdwn b/doc/todo/inneficiency_on_slow_filesystems_opening_nonexistant_journal_files.mdwn
index 11b2e02e1..dce5120e8 100644
--- a/doc/todo/inneficiency_on_slow_filesystems_opening_nonexistant_journal_files.mdwn
+++ b/doc/todo/inneficiency_on_slow_filesystems_opening_nonexistant_journal_files.mdwn
@@ -10,6 +10,25 @@ either commit the journal to the branch once at startup, or check if the
 journal is empty, and once there's known to be nothing in the journal,
 avoid opening files from there.
 
+Minimum patch to test if this is a significant performance impact:
+
+	diff --git a/Annex/Branch.hs b/Annex/Branch.hs
+	index 0d8eb7944..686791a3a 100644
+	--- a/Annex/Branch.hs
+	+++ b/Annex/Branch.hs
+	@@ -222,7 +222,7 @@ get file = do
+	  - (Changing the value this returns, and then merging is always the
+	  - same as using get, and then changing its value.) -}
+	 getLocal :: FilePath -> Annex L.ByteString
+	-getLocal file = go =<< getJournalFileStale file
+	+getLocal file = go =<< pure Nothing -- getJournalFileStale file
+	   where
+	 	go (Just journalcontent) = return journalcontent
+	 	go Nothing = getRef fullname file
+
+I don't see any measuable speed gain with this on my laptop SSD, but maybe
+on a slower filesystem it will?
+
 But: Concurrency. Another process may be writing changes to the git-annex
 branch, via the journal, and so this would be a behavior change. Mostly
 that seems acceptible, because there's no defined ordering of events in

further thought
diff --git a/doc/todo/inneficiency_on_slow_filesystems_opening_nonexistant_journal_files.mdwn b/doc/todo/inneficiency_on_slow_filesystems_opening_nonexistant_journal_files.mdwn
index d87c374c8..11b2e02e1 100644
--- a/doc/todo/inneficiency_on_slow_filesystems_opening_nonexistant_journal_files.mdwn
+++ b/doc/todo/inneficiency_on_slow_filesystems_opening_nonexistant_journal_files.mdwn
@@ -26,6 +26,12 @@ So, this optimisation seems it would be limited to commands that
 are not in batch mode and do strictly read-only queries. Which seems a bit
 hard to plumb through to the git-annex branch reading code.
 
+> Unless, perhaps, we can rely on the process that modifies the git-annex
+> branch having cleanly exited, and so committed its changes to the branch,
+> before the next batch query. Can we rely on that, or might a batch
+> mode command expect to see changes made up to the point it started
+> by a concurrent command?
+
 An easier alternative would be an option that bypasses reading the journal.
 But maybe there's some other, better way to avoid this slow case?
 --[[Joey]]

todo item based on behavior yoh showed me
diff --git a/doc/todo/inneficiency_on_slow_filesystems_opening_nonexistant_journal_files.mdwn b/doc/todo/inneficiency_on_slow_filesystems_opening_nonexistant_journal_files.mdwn
new file mode 100644
index 000000000..d87c374c8
--- /dev/null
+++ b/doc/todo/inneficiency_on_slow_filesystems_opening_nonexistant_journal_files.mdwn
@@ -0,0 +1,31 @@
+`git-annex info uuid` was observed to be slow on a slow NFS, because
+it is opening lots of .git/annex/journal files that DNE. So does
+`git annex find --in remote`.
+
+Normally the journal is empty, but each query of a file from the git-annex
+branch still tries to open the corresponding journal file.
+
+It seems that this could be improved by making such query commands
+either commit the journal to the branch once at startup, or check if the
+journal is empty, and once there's known to be nothing in the journal,
+avoid opening files from there.
+
+But: Concurrency. Another process may be writing changes to the git-annex
+branch, via the journal, and so this would be a behavior change. Mostly
+that seems acceptible, because there's no defined ordering of events in
+such a situation, and this change only makes it so that the writes
+effectively always come after the reads.
+
+But: Batch jobs. When a git-annex command is run in a batch mode,
+its caller can currently safely expect that running some other command,
+that modifies the git-annex branch, followed by asking the batch
+mode command to query it will yield a result that takes the earlier write
+into account.
+
+So, this optimisation seems it would be limited to commands that
+are not in batch mode and do strictly read-only queries. Which seems a bit
+hard to plumb through to the git-annex branch reading code.
+
+An easier alternative would be an option that bypasses reading the journal.
+But maybe there's some other, better way to avoid this slow case?
+--[[Joey]]

improve wording
diff --git a/doc/git-annex-info.mdwn b/doc/git-annex-info.mdwn
index 455b67cad..646dd1b49 100644
--- a/doc/git-annex-info.mdwn
+++ b/doc/git-annex-info.mdwn
@@ -13,7 +13,7 @@ which can be a directory, or a file, or a treeish, or a remote,
 or the description or uuid of a repository.
   
 When no item is specified, displays statistics and information
-for the repository as a whole.
+for the local repository and all known annexed files.
 
 # OPTIONS
 

mention that repo decription can be used
diff --git a/doc/git-annex-info.mdwn b/doc/git-annex-info.mdwn
index c8ea473e5..455b67cad 100644
--- a/doc/git-annex-info.mdwn
+++ b/doc/git-annex-info.mdwn
@@ -4,13 +4,13 @@ git-annex info - information about an item or the repository
 
 # SYNOPSIS
 
-git annex info `[directory|file|treeish|remote|uuid ...]`
+git annex info `[directory|file|treeish|remote|description|uuid ...]`
 
 # DESCRIPTION
 
 Displays statistics and other information for the specified item,
 which can be a directory, or a file, or a treeish, or a remote,
-or the uuid of a repository.
+or the description or uuid of a repository.
   
 When no item is specified, displays statistics and information
 for the repository as a whole.

Added a comment: Re: Inconsistent idiom
diff --git a/doc/git-annex-addurl/comment_8_88aea3014245634d42f23a22ccf2fcc9._comment b/doc/git-annex-addurl/comment_8_88aea3014245634d42f23a22ccf2fcc9._comment
new file mode 100644
index 000000000..d8c832b25
--- /dev/null
+++ b/doc/git-annex-addurl/comment_8_88aea3014245634d42f23a22ccf2fcc9._comment
@@ -0,0 +1,17 @@
+[[!comment format=mdwn
+ username="pellman.john@e59e5c6d98d49cd9632d6fbe0c5026ddc71d52fd"
+ nickname="pellman.john"
+ avatar="http://cdn.libravatar.org/avatar/eaca2e5f6d5888d139129293c7293b1f"
+ subject="Re: Inconsistent idiom"
+ date="2019-03-28T03:59:04Z"
+ content="""
+Hi @joey,
+
+Thanks for your continued work on git-annex and for responding to my last comment.  I agree that consistency is not everything, but I do think that it's also important to balance functionality against the amount of cognitive load that an interface places on an end-user.  My perspective is no doubt influenced by my cognitive science background, but whenever I find an interface where it's easy to confuse two similar operations that use different syntaxes, I'm reminded of Don Norman's [rant about the early Unix UI](https://www.researchgate.net/publication/202165676_The_trouble_with_UNIX_The_user_interface_is_horrid).  I'm also reminded of common phenomena described in memory research such as [retroactive interference](https://en.wikipedia.org/wiki/Interference_theory#Proactive_interference), wherein a more recently learned memory interferes with something that was learned previously.  In this case, if I were to learn the syntax for addurl first, and then learned the syntax for rmurl much later, my internal representation of rmurl would to some degree \"overwrite\" my previous knowledge of addurl and compete with it.  Making the two syntaxes consistent with each other in this case would eliminate any competition between internal mental representations of how the two commands are structured.
+
+I'm also not entirely sure why a positional argument can't be optional.  If there's a good reason for this not to be so then I won't argue my point anymore, but something like the following syntax would make the most sense from my view:
+
+``git annex rmurl [url] [file]``
+
+``git annex addurl [url] [file; optional positional argument]``
+"""]]

minor typos
diff --git a/P2P/IO.hs b/P2P/IO.hs
index 134d54f1c..b079f8de8 100644
--- a/P2P/IO.hs
+++ b/P2P/IO.hs
@@ -369,7 +369,7 @@ relayReader v hout = loop
 				putMVar v $ RelayToPeer (L.fromChunks bs)
 				loop
 	
-	-- Waiit for the first available chunk. Then, without blocking,
+	-- Wait for the first available chunk. Then, without blocking,
 	-- try to get more chunks, in case a stream of chunks is being
 	-- written in close succession. 
 	--
diff --git a/doc/todo/annex.thin_without_hardlinks.mdwn b/doc/todo/annex.thin_without_hardlinks.mdwn
index 40e235089..dd3047c78 100644
--- a/doc/todo/annex.thin_without_hardlinks.mdwn
+++ b/doc/todo/annex.thin_without_hardlinks.mdwn
@@ -1,6 +1,6 @@
 Currently annex.thin needs hard link support to be efficient;
 it hard links the content from .git/annex/objects into the work tree.
-When hard links are not supported, two copie of checked out files exist on
+When hard links are not supported, two copies of checked out files exist on
 disk.
 
 Would it be possible to make it work w/o hard links? Note that direct mode

this is not all run as root
diff --git a/doc/walkthrough/adding_a_remote.mdwn b/doc/walkthrough/adding_a_remote.mdwn
index c02852544..0234e3ea1 100644
--- a/doc/walkthrough/adding_a_remote.mdwn
+++ b/doc/walkthrough/adding_a_remote.mdwn
@@ -1,14 +1,14 @@
 Like any other git repository, git-annex repositories have remotes.
 Let's start by adding a USB drive as a remote.
 
-	# sudo mount /media/usb
-	# cd /media/usb
-	# git clone ~/annex
-	# cd annex
-	# git annex init "portable USB drive"
-	# git remote add laptop ~/annex
-	# cd ~/annex
-	# git remote add usbdrive /media/usb/annex
+	$ sudo mount /media/usb
+	$ cd /media/usb
+	$ git clone ~/annex
+	$ cd annex
+	$ git annex init "portable USB drive"
+	$ git remote add laptop ~/annex
+	$ cd ~/annex
+	$ git remote add usbdrive /media/usb/annex
 
 This is all standard ad-hoc distributed git repository setup.
 
diff --git a/doc/walkthrough/adding_files.mdwn b/doc/walkthrough/adding_files.mdwn
index b014c3ee7..ada825a0b 100644
--- a/doc/walkthrough/adding_files.mdwn
+++ b/doc/walkthrough/adding_files.mdwn
@@ -1,10 +1,10 @@
-	# cd ~/annex
-	# cp /tmp/big_file .
-	# cp /tmp/debian.iso .
-	# git annex add .
+	$ cd ~/annex
+	$ cp /tmp/big_file .
+	$ cp /tmp/debian.iso .
+	$ git annex add .
 	add big_file (checksum...) ok
 	add debian.iso (checksum...) ok
-	# git commit -a -m added
+	$ git commit -a -m added
 
 When you add a file to the annex and commit it, only a symlink to
 the content is committed to git. The content itself is stored in
diff --git a/doc/walkthrough/automatically_managing_content.mdwn b/doc/walkthrough/automatically_managing_content.mdwn
index ec55c1cc8..1f29674dc 100644
--- a/doc/walkthrough/automatically_managing_content.mdwn
+++ b/doc/walkthrough/automatically_managing_content.mdwn
@@ -7,8 +7,8 @@ but then you have to decide what to get or drop. In this example, there
 are perhaps not enough copies of the first file, and too many of the second
 file.
 
-	# cd /media/usbdrive
-	# git annex whereis
+	$ cd /media/usbdrive
+	$ git annex whereis
 	whereis my_cool_big_file (1 copy)
 		0c443de8-e644-11df-acbf-f7cd7ca6210d  -- laptop
 	whereis other_file (3 copies)
@@ -20,15 +20,15 @@ What would be handy is some automated versions of get and drop, that only
 gets a file if there are not yet enough copies of it, or only drops a file
 if there are too many copies. Well, these exist, just use the --auto option.
 
-	# git annex get --auto --numcopies=2
+	$ git annex get --auto --numcopies=2
 	get my_cool_big_file (from laptop...) ok
-	# git annex drop --auto --numcopies=2
+	$ git annex drop --auto --numcopies=2
 	drop other_file ok
 
 With two quick commands, git-annex was able to decide for you how to
 work toward having two copies of your files.
 
-	# git annex whereis
+	$ git annex whereis
 	whereis my_cool_big_file (2 copies)
 		0c443de8-e644-11df-acbf-f7cd7ca6210d  -- laptop
 		62b39bbe-4149-11e0-af01-bb89245a1e61  -- usb drive [here]
diff --git a/doc/walkthrough/backups.mdwn b/doc/walkthrough/backups.mdwn
index 223e0b2ee..e346a6a57 100644
--- a/doc/walkthrough/backups.mdwn
+++ b/doc/walkthrough/backups.mdwn
@@ -4,8 +4,8 @@ numcopies setting, which defaults to 1 copy. Let's
 change that to require 2 copies, and send a copy of every file
 to a USB drive.
 
-	# git annex numcopies 2
-	# git annex copy . --to usbdrive
+	$ git annex numcopies 2
+	$ git annex copy . --to usbdrive
 
 Now when we try to `git annex drop` a file, it will verify that it
 knows of 2 other repositories that have a copy before removing its
@@ -15,13 +15,13 @@ The numcopies setting used above is the global default.
 You can also vary the number of copies needed, depending on the file name.
 So, if you want 3 copies of all your flac files, but only 1 copy of oggs:
 
-	# echo "*.ogg annex.numcopies=1" >> .gitattributes
-	# echo "*.flac annex.numcopies=3" >> .gitattributes
+	$ echo "*.ogg annex.numcopies=1" >> .gitattributes
+	$ echo "*.flac annex.numcopies=3" >> .gitattributes
 
 Or, you might want to make a directory for important stuff, and configure
 it so anything put in there is backed up more thoroughly:
 
-	# mkdir important_stuff
-	# echo "* annex.numcopies=3" > important_stuff/.gitattributes
+	$ mkdir important_stuff
+	$ echo "* annex.numcopies=3" > important_stuff/.gitattributes
 
 For more details about the numcopies setting, see [[copies]].
diff --git a/doc/walkthrough/creating_a_repository.mdwn b/doc/walkthrough/creating_a_repository.mdwn
index b5b3ab407..270d2e44e 100644
--- a/doc/walkthrough/creating_a_repository.mdwn
+++ b/doc/walkthrough/creating_a_repository.mdwn
@@ -1,6 +1,6 @@
 This is very straightforward.
 
-	# mkdir ~/annex
-	# cd ~/annex
-	# git init
-	# git annex init
+	$ mkdir ~/annex
+	$ cd ~/annex
+	$ git init
+	$ git annex init
diff --git a/doc/walkthrough/fsck__58___verifying_your_data.mdwn b/doc/walkthrough/fsck__58___verifying_your_data.mdwn
index 240014610..b4356e9ce 100644
--- a/doc/walkthrough/fsck__58___verifying_your_data.mdwn
+++ b/doc/walkthrough/fsck__58___verifying_your_data.mdwn
@@ -4,7 +4,7 @@ for the data. For example, when you use the SHA1 backend, fsck will verify
 that the checksums of your files are good. Fsck also checks that the
 [[numcopies|copies]] setting is satisfied for all files.
 
-	# git annex fsck
+	$ git annex fsck
 	fsck some_file (checksum...) ok
 	fsck my_cool_big_file (checksum...) ok
 	...
@@ -12,19 +12,19 @@ that the checksums of your files are good. Fsck also checks that the
 You can also specify the files to check.  This is particularly useful if 
 you're using sha1 and don't want to spend a long time checksumming everything.
 
-	# git annex fsck my_cool_big_file
+	$ git annex fsck my_cool_big_file
 	fsck my_cool_big_file (checksum...) ok
 
 If you have a large repo, you may want to check it in smaller steps. You may
 start and continue an aborted or time-limited check.
 
-	# git annex fsck -S <optional-directory> --time-limit=1m
+	$ git annex fsck -S <optional-directory> --time-limit=1m
 	fsck some_file (checksum...) ok
 	fsck my_cool_big_file (checksum...) ok
 	
 	  Time limit (1m) reached!
 
-	# git annex fsck -m <optional-directory>
+	$ git annex fsck -m <optional-directory>
 	fsck my_other_big_file (checksum...) ok
 	...
 
diff --git a/doc/walkthrough/fsck__58___when_things_go_wrong.mdwn b/doc/walkthrough/fsck__58___when_things_go_wrong.mdwn
index 85d9f20fe..348add570 100644
--- a/doc/walkthrough/fsck__58___when_things_go_wrong.mdwn
+++ b/doc/walkthrough/fsck__58___when_things_go_wrong.mdwn
@@ -2,7 +2,7 @@ Fsck never deletes possibly bad data; instead it will be moved to
 `.git/annex/bad/` for you to recover. Here is a sample of what fsck
 might say about a badly messed up annex:
 
-	# git annex fsck
+	$ git annex fsck
 	fsck my_cool_big_file (checksum...)
 	git-annex: Bad file content; moved to .git/annex/bad/SHA1:7da006579dd64330eb2456001fd01948430572f2
 	git-annex: ** No known copies exist of my_cool_big_file
diff --git a/doc/walkthrough/getting_file_content.mdwn b/doc/walkthrough/getting_file_content.mdwn
index f92704ff3..c95dca128 100644
--- a/doc/walkthrough/getting_file_content.mdwn
+++ b/doc/walkthrough/getting_file_content.mdwn
@@ -5,8 +5,8 @@ make it available.
 We can use this to copy everything in the laptop's annex to the
 USB drive.
 
-	# cd /media/usb/annex
-	# git annex sync laptop
-	# git annex get .
+	$ cd /media/usb/annex
+	$ git annex sync laptop
+	$ git annex get .
 	get my_cool_big_file (from laptop...) ok
 	get iso/debian.iso (from laptop...) ok
diff --git a/doc/walkthrough/modifying_annexed_files.mdwn b/doc/walkthrough/modifying_annexed_files.mdwn
index a35978d82..94dfe190f 100644
--- a/doc/walkthrough/modifying_annexed_files.mdwn
+++ b/doc/walkthrough/modifying_annexed_files.mdwn
@@ -4,12 +4,12 @@ Normally, the content of files in the annex is prevented from being modified.
 That's a good thing, because it might be the only copy, you wouldn't

(Diff truncated)
Added a comment
diff --git a/doc/todo/simpler__44___trusted_export_remotes/comment_5_aeefb4803340ff993a1d6673c8e5e97b._comment b/doc/todo/simpler__44___trusted_export_remotes/comment_5_aeefb4803340ff993a1d6673c8e5e97b._comment
new file mode 100644
index 000000000..254da7d79
--- /dev/null
+++ b/doc/todo/simpler__44___trusted_export_remotes/comment_5_aeefb4803340ff993a1d6673c8e5e97b._comment
@@ -0,0 +1,11 @@
+[[!comment format=mdwn
+ username="Ilya_Shlyakhter"
+ avatar="http://cdn.libravatar.org/avatar/1647044369aa7747829c38b9dcc84df0"
+ subject="comment 5"
+ date="2019-03-26T18:27:04Z"
+ content="""
+Another approach would be to let a key-value remote and an export remote be combined into one \"combo\" remote.  To the user, this would look like one trusted, versioned remote supporting both key-value and export operations.  Keys overwritten in the export remote would be stored in the key-value remote. Either keys or trees could be copied to the combo remote, keys going to the key-value remote and trees to the export remote.  The downside is that files could not be moved directly between the backing remotes.  But the inefficiency might not always matter. Also, TRANSFER and TRANSFEREXPORT could be extended to optionally accept URIs in lieu of content, and to do the transfer in the cloud.
+
+More generically, maybe repository groups could be treated as special remotes?  You'd configure the minimum number of copies of a key in a group.  You could then put a key-value remote and an export remote in a group.  When copying a tree to the group, if this would cause old keys to be overwritten, git-annex would first copy them to a key-value remote in the group, to preserve the per-group minimum number of copies constraint.
+
+"""]]

fixed a typo
diff --git a/doc/todo/simpler__44___trusted_export_remotes.mdwn b/doc/todo/simpler__44___trusted_export_remotes.mdwn
index 089721285..13acd1a7a 100644
--- a/doc/todo/simpler__44___trusted_export_remotes.mdwn
+++ b/doc/todo/simpler__44___trusted_export_remotes.mdwn
@@ -1,3 +1,3 @@
-Currently, some issues impede the use of export remotes: (1) they're untrusted, except for versioned ones -- and from  those keys cannot be dropped; (2) using them is different than using normal remotes: one can't just copy or move keys to them, one has to first make a tree-ish.   Maybe this could be fixed, as follows.   To copy a key to a external remote, if the key is not yet present in it, put it under .keys/aaa/bbb/keyname on the remote.  That is, take the tree-ish currently on the remote, merge .keys/aaa/bbb/keyname with it, and put that on the remote.   To drop a key from an external remote, take the tree-ish currently on the remote, drop all instances of the key from it, and push the changed tree-ish to the remote.  To git-annex-export add an option --add , which will add the tree-ish to the tree-ish currently on the remote, without losing any keys currently on the remote: take the tree-ish currently on the remote; overlay on it the treeish being exported; for any files that would be overwritten, if no copies of that key would be left, move it to .keys/aaa/bbb/keyname in the tree-ish that is then pushed to the remote.
+Currently, some issues impede the use of export remotes: (1) they're untrusted, except for versioned ones -- and from  those keys cannot be dropped; (2) using them is different than using normal remotes: one can't just copy or move keys to them, one has to first make a tree-ish.   Maybe this could be fixed, as follows.   To copy a key to an export remote, if the key is not yet present in it, put it under .keys/aaa/bbb/keyname on the remote.  That is, take the tree-ish currently on the remote, merge .keys/aaa/bbb/keyname with it, and put that on the remote.   To drop a key from an external remote, take the tree-ish currently on the remote, drop all instances of the key from it, and push the changed tree-ish to the remote.  To git-annex-export add an option --add , which will add the tree-ish to the tree-ish currently on the remote, without losing any keys currently on the remote: take the tree-ish currently on the remote; overlay on it the treeish being exported; for any files that would be overwritten, if no copies of that key would be left, move it to .keys/aaa/bbb/keyname in the tree-ish that is then pushed to the remote.
 
 This way, can always just copy any tree to the remote, without worrying about losing data.

Added a comment: simplifying the interface
diff --git a/doc/todo/simpler__44___trusted_export_remotes/comment_4_be525962211e8c4da681279aba132c71._comment b/doc/todo/simpler__44___trusted_export_remotes/comment_4_be525962211e8c4da681279aba132c71._comment
new file mode 100644
index 000000000..c011b98d1
--- /dev/null
+++ b/doc/todo/simpler__44___trusted_export_remotes/comment_4_be525962211e8c4da681279aba132c71._comment
@@ -0,0 +1,14 @@
+[[!comment format=mdwn
+ username="Ilya_Shlyakhter"
+ avatar="http://cdn.libravatar.org/avatar/1647044369aa7747829c38b9dcc84df0"
+ subject="simplifying the interface"
+ date="2019-03-26T17:40:32Z"
+ content="""
+\"I'm doubtful that this would actually let the interface be simplified\" -- I only meant that the minimum required interface would be simplified, in that git-annex could provide a default implementation of key-value remote methods in terms of the export remote interface; but any given remote could provide a more efficient implementation of these methods, overriding the default ones.
+
+But the main benefit would be to simplify the user-facing interface: as far as the user is concerned, all special remotes could be trusted, and accessed with the same basic commands, whether configured as export or not.
+
+\"if a S3 bucket is read-only, then an import can't re-upload.\" -- if the special remote is configured as read-only, then git-annex itself would not attempt to upload things there, no?
+
+\"not all users are going to want export remotes to store past versions of files\" -- maybe, there could be an option to store past versions encrypted, while storing current versions plain?
+"""]]

Added a comment: annex.thin without hardlinks would be useful for non-crippled systems as well
diff --git a/doc/tips/unlocked_files/comment_14_e3425d219001fc34470f0cd55fc7241e._comment b/doc/tips/unlocked_files/comment_14_e3425d219001fc34470f0cd55fc7241e._comment
new file mode 100644
index 000000000..2d935ed62
--- /dev/null
+++ b/doc/tips/unlocked_files/comment_14_e3425d219001fc34470f0cd55fc7241e._comment
@@ -0,0 +1,8 @@
+[[!comment format=mdwn
+ username="yarikoptic"
+ avatar="http://cdn.libravatar.org/avatar/f11e9c84cb18d26a1748c33b48c924b4"
+ subject="annex.thin without hardlinks  would be useful for non-crippled systems as well"
+ date="2019-03-25T18:57:36Z"
+ content="""
+One of the concerns with use of git-annex on HPC and other heavily loaded systems is the >3x consumption of inodes due to all the symlinks etc.  In some cases it could be completely avoided probably, if repository is instructed to be installed just for consumption (to access data) only.  In this way it would be nice if we could get the same \"annex.thin without hardlinks\" that there would not be even any `.git/annex/objects` (`superthin`?) and files just get installed in-place.
+"""]]

Added a comment
diff --git a/doc/forum/Getting__58___hGetChar__58___illegal_operation___40__handle_is_closed__41__/comment_3_976cb63e97774859023123536bdc9d99._comment b/doc/forum/Getting__58___hGetChar__58___illegal_operation___40__handle_is_closed__41__/comment_3_976cb63e97774859023123536bdc9d99._comment
new file mode 100644
index 000000000..80f192bb1
--- /dev/null
+++ b/doc/forum/Getting__58___hGetChar__58___illegal_operation___40__handle_is_closed__41__/comment_3_976cb63e97774859023123536bdc9d99._comment
@@ -0,0 +1,8 @@
+[[!comment format=mdwn
+ username="yarikoptic"
+ avatar="http://cdn.libravatar.org/avatar/f11e9c84cb18d26a1748c33b48c924b4"
+ subject="comment 3"
+ date="2019-03-24T23:49:48Z"
+ content="""
+actually not sure if that is a matter of multiple files with the same key since with a subsequent call to `datalad publish` 3 files did get published, so I guess it was something else.
+"""]]

Added a comment: The issue persists with recent git-annex
diff --git a/doc/forum/Getting__58___hGetChar__58___illegal_operation___40__handle_is_closed__41__/comment_2_7c88ebd9d7cdf4a009aa2580cc55787d._comment b/doc/forum/Getting__58___hGetChar__58___illegal_operation___40__handle_is_closed__41__/comment_2_7c88ebd9d7cdf4a009aa2580cc55787d._comment
new file mode 100644
index 000000000..e516fa5c0
--- /dev/null
+++ b/doc/forum/Getting__58___hGetChar__58___illegal_operation___40__handle_is_closed__41__/comment_2_7c88ebd9d7cdf4a009aa2580cc55787d._comment
@@ -0,0 +1,20 @@
+[[!comment format=mdwn
+ username="yarikoptic"
+ avatar="http://cdn.libravatar.org/avatar/f11e9c84cb18d26a1748c33b48c924b4"
+ subject="The issue persists with recent git-annex"
+ date="2019-03-24T23:00:30Z"
+ content="""
+The same with annex locally 7.20190219+git191-g2d6a364d4-1~ndall+1 and on remote  7.20190129+git78-g3fa6be1fe-1~ndall+1, while copying to the remote host a LOT (59k) of files, 3 \"failed\" and I get datalad print me a summary of those 3 error messages
+
+[[!format sh \"\"\"
+git-annex: <stdin>: hGetChar: illegal operation (handle is closed)git-annex-shell: p2pstdio: 1 failed  Lost connection (fd:20: hGetChar: end of file)
+  This could have failed because --fast is enabled.
+git-annex: <stdin>: hGetChar: illegal operation (handle is closed)git-annex-shell: p2pstdio: 1 failed  Lost connection (fd:19: hGetChar: end of file)
+  This could have failed because --fast is enabled.
+git-annex: <stdin>: hGetChar: illegal operation (handle is closed)git-annex-shell: p2pstdio: 1 failed  Lost connection (fd:19: hGetChar: end of file)
+  This could have failed because --fast is enabled.
+git-annex: copy: 3 failed
+
+\"\"\"]]
+I guess it is because the files are actually pointing to the same key(s), which get transferred in some other parallel batch.
+"""]]

re: documenting git-annex dependencies
diff --git a/doc/todo/document_git-annex_dependencies.mdwn b/doc/todo/document_git-annex_dependencies.mdwn
new file mode 100644
index 000000000..861421c5a
--- /dev/null
+++ b/doc/todo/document_git-annex_dependencies.mdwn
@@ -0,0 +1 @@
+It would help to document, in one place, the external programs and libraries on which git-annex depends for various functionalities, including optional ones.  Ones I know: curl, gpg, bup.  But there are also references in places to lsof, rsync, nocache.  For reliable packaging, it would be useful to have an authoritative list of dependencies and which functionality each supports.

poll vote (OpenStack SWIFT)
diff --git a/doc/design/assistant/polls/prioritizing_special_remotes.mdwn b/doc/design/assistant/polls/prioritizing_special_remotes.mdwn
index aeef0a490..620b0c772 100644
--- a/doc/design/assistant/polls/prioritizing_special_remotes.mdwn
+++ b/doc/design/assistant/polls/prioritizing_special_remotes.mdwn
@@ -6,7 +6,7 @@ locally paired systems, and remote servers with rsync.
 Help me prioritize my work: What special remote would you most like
 to use with the git-annex assistant?
 
-[[!poll open=yes 18 "Amazon S3 (done)" 13 "Amazon Glacier (done)" 10 "Box.com (done)" 79 "My phone (or MP3 player)" 29 "Tahoe-LAFS" 17 "OpenStack SWIFT" 37 "Google Drive"]]
+[[!poll open=yes 18 "Amazon S3 (done)" 13 "Amazon Glacier (done)" 10 "Box.com (done)" 79 "My phone (or MP3 player)" 29 "Tahoe-LAFS" 18 "OpenStack SWIFT" 37 "Google Drive"]]
 
 This poll is ordered with the options I consider easiest to build
 listed first. Mostly because git-annex already supports them and they

add news item for git-annex 7.20190322
diff --git a/doc/news/version_7.20181205.mdwn b/doc/news/version_7.20181205.mdwn
deleted file mode 100644
index 1cc1648aa..000000000
--- a/doc/news/version_7.20181205.mdwn
+++ /dev/null
@@ -1,19 +0,0 @@
-git-annex 7.20181205 released with [[!toggle text="these changes"]]
-[[!toggleable text="""
-   * Make bittorrent special remote work w/o btshowmetainfo installed
-     when it was build with torrentparser.
-     Thanks, Robert Schütz
-   * When running youtube-dl to get a filename, pass --no-playlist.
-   * Fix build without concurrent-output.
-   * init: When a crippled filesystem causes an adjusted unlocked branch to
-     be used, set repo version to 7, which it neglected to do before.
-   * init: When on a crippled filesystem, and the git version is too old
-     to use an adjusted unlocked branch, fall back to using direct mode.
-   * info: When used with an exporttree remote, includes an "exportedtree"
-     info, which is the tree last exported to the remote. During an export
-     conflict, multiple values will be listed.
-   * dropunused: When an unused object file has gotten modified, eg due to
-     annex.thin being set, don't silently skip it, but display a warning
-     and let --force drop it.
-   * annex.cachecreds: New config to allow disabling of credentials caching
-     for special remotes."""]]
\ No newline at end of file
diff --git a/doc/news/version_7.20190322.mdwn b/doc/news/version_7.20190322.mdwn
new file mode 100644
index 000000000..8f2748974
--- /dev/null
+++ b/doc/news/version_7.20190322.mdwn
@@ -0,0 +1,41 @@
+git-annex 7.20190322 released with [[!toggle text="these changes"]]
+[[!toggleable text="""
+   * New feature allows importing from special remotes, using
+     git annex import branch:subdir --from remote
+   * Directory special remote supports being configured with importree=yes,
+     to allow git-annex import of files from the directory. This can be
+     combined with exporttree=yes and git-annex export used to send changes
+     back to the same directory.
+   * Remote tracking branches are updated when importing and exporting to
+     special remotes, in ways analagous to how git fetch and git push do.
+   * export: Deprecated the --tracking option.
+     Instead, users can configure remote.&lt;name&gt;.annex-tracking-branch
+     themselves.
+   * sync --content: When remote.&lt;name&gt;.annex-tracking-branch is configured,
+     import from special remotes.
+   * sync, assistant: --no-push and remote.&lt;name&gt;.annex-push prevent exporting
+     trees to special remotes.
+   * Fix storage of metadata values containing newlines.
+     (Reversion introduced in version 7.20190122.)
+   * Sped up git-annex export in repositories with lots of keys.
+   * S3: Support enabling bucket versioning when built with aws-0.21.1.
+   * stack.yaml: Build with aws-0.21.1
+   * Fix cleanup of git-annex:export.log after git-annex forget --drop-dead.
+   * Makefile: Added install-home target which installs git-annex into
+     the HOME directory.
+   * addurl --file: Fix a bug that made youtube-dl be used unneccessarily
+     when adding an html url that does not contain any media.
+   * Add -- before %f in the smudge/clean filter configuration,
+     to support filenames starting with dashes.
+     (To update the config of existing repositories, you can
+     re-run git-annex init.)
+   * fsck: Detect situations where annex.thin has caused data loss
+     to the content of locked files.
+   * Removed bundled gpg from the Linux standalone build and OSX dmg,
+     because gpg now always wants to use gpg-agent, and shipping such a daemon
+     in those is not a good idea.
+   * import: Let --force overwrite symlinks, not only regular files.
+   * Android: Fix typo of name of armv7l in installation script.
+     Thanks, 4omecha.
+   * S3: Added protocol= initremote setting, to allow https to be used
+     on a non-standard port."""]]
\ No newline at end of file

back-compat warning for protocol=https
diff --git a/doc/special_remotes/S3.mdwn b/doc/special_remotes/S3.mdwn
index c286d4ba8..6fe9dc283 100644
--- a/doc/special_remotes/S3.mdwn
+++ b/doc/special_remotes/S3.mdwn
@@ -62,7 +62,11 @@ the S3 remote.
   service.
 
 * `protocol` - Either "http" (the default) or "https". Setting
-  protocol=https implies port=443.
+  protocol=https implies port=443. 
+  
+  This option was added in git-annex version 7.20190322; to make
+  a special remote that uses http with older versions of git-annex,
+  explicitly specify port=443.
 
 * `port` - Specify the port to connect to. Only needed when using a service
   on an unusual port. Setting port=443 implies protocol=https.

S3: Added protocol= initremote setting, to allow https to be used on a non-standard port
protocol=https implies port=443 and
port=443 implies protocol=https
-- this was necessary because the existing configs set port=443, but
with a protocol setting, users will naturally want to use it, and then
there's no need for them to supply the default https port. So we keep
back-compat, add a nicer way to enable https, and also add support for
non-standard https ports.
diff --git a/CHANGELOG b/CHANGELOG
index 93c97d729..80adc3e85 100644
--- a/CHANGELOG
+++ b/CHANGELOG
@@ -37,6 +37,8 @@ git-annex (7.20190220) UNRELEASED; urgency=medium
   * import: Let --force overwrite symlinks, not only regular files.
   * Android: Fix typo of name of armv7l in installation script.
     Thanks, 4omecha.
+  * S3: Added protocol= initremote setting, to allow https to be used
+    on a non-standard port.
 
  -- Joey Hess <id@joeyh.name>  Wed, 20 Feb 2019 14:20:59 -0400
 
diff --git a/Remote/S3.hs b/Remote/S3.hs
index 50f1255eb..9dfe46377 100644
--- a/Remote/S3.hs
+++ b/Remote/S3.hs
@@ -146,7 +146,6 @@ s3Setup' ss u mcreds c gc
 		[ ("datacenter", T.unpack $ AWS.defaultRegion AWS.S3)
 		, ("storageclass", "STANDARD")
 		, ("host", AWS.s3DefaultHost)
-		, ("port", "80")
 		, ("bucket", defbucket)
 		]
 		
@@ -571,9 +570,6 @@ s3Configuration c = cfg
 		Nothing -> S3.s3RequestStyle cfg
 	}
   where
-	proto
-		| port == 443 = AWS.HTTPS
-		| otherwise = AWS.HTTP
 	h = fromJust $ M.lookup "host" c
 	datacenter = fromJust $ M.lookup "datacenter" c
 	-- When the default S3 host is configured, connect directly to
@@ -582,10 +578,25 @@ s3Configuration c = cfg
 	endpoint
 		| h == AWS.s3DefaultHost = AWS.s3HostName $ T.pack datacenter
 		| otherwise = T.encodeUtf8 $ T.pack h
-	port = let s = fromJust $ M.lookup "port" c in
-		case reads s of
-		[(p, _)] -> p
-		_ -> giveup $ "bad S3 port value: " ++ s
+	port = case M.lookup "port" c of
+		Just s -> 
+			case reads s of
+				[(p, _)] -> p
+				_ -> giveup $ "bad S3 port value: " ++ s
+		Nothing -> case cfgproto of
+			Just AWS.HTTPS -> 443
+			Just AWS.HTTP -> 80
+			Nothing -> 80
+	cfgproto = case M.lookup "protocol" c of
+		Just "https" -> Just AWS.HTTPS
+		Just "http" -> Just AWS.HTTP
+		Just _ -> giveup $ "bad S3 protocol value"
+		Nothing -> Nothing
+	proto = case cfgproto of
+		Just v -> v
+		Nothing
+			| port == 443 -> AWS.HTTPS
+			| otherwise -> AWS.HTTP
 	cfg = S3.s3 proto endpoint False
 
 data S3Info = S3Info
@@ -735,6 +746,7 @@ s3Info c info = catMaybes
 	[ Just ("bucket", fromMaybe "unknown" (getBucketName c))
 	, Just ("endpoint", w82s (BS.unpack (S3.s3Endpoint s3c)))
 	, Just ("port", show (S3.s3Port s3c))
+	, Just ("protocol", map toLower (show (S3.s3Protocol s3c)))
 	, Just ("storage class", showstorageclass (getStorageClass c))
 	, if configIA c
 		then Just ("internet archive item", iaItemUrl $ fromMaybe "unknown" $ getBucketName c)
diff --git a/doc/bugs/The_S3_special_remote_limits_HTTPS_support_to_port_443.mdwn b/doc/bugs/The_S3_special_remote_limits_HTTPS_support_to_port_443.mdwn
index 3fc93c096..49704cd94 100644
--- a/doc/bugs/The_S3_special_remote_limits_HTTPS_support_to_port_443.mdwn
+++ b/doc/bugs/The_S3_special_remote_limits_HTTPS_support_to_port_443.mdwn
@@ -9,3 +9,5 @@ Version 7.20181121 on MacOS and 7.20190130-g024120065 on FreeBSD
 
 ### Have you had any luck using git-annex before? (Sometimes we get tired of reading bug reports all day and a lil' positive end note does wonders)
 Yes. I only encountered the problem because git-annex works well enough for me that I want to put a lot more data into it.
+
+> [[fixed|done]] --[[Joey]]
diff --git a/doc/bugs/The_S3_special_remote_limits_HTTPS_support_to_port_443/comment_1_f6de7a30714d6281a81ae218bb92dfd6._comment b/doc/bugs/The_S3_special_remote_limits_HTTPS_support_to_port_443/comment_1_f6de7a30714d6281a81ae218bb92dfd6._comment
new file mode 100644
index 000000000..ba24ec5d6
--- /dev/null
+++ b/doc/bugs/The_S3_special_remote_limits_HTTPS_support_to_port_443/comment_1_f6de7a30714d6281a81ae218bb92dfd6._comment
@@ -0,0 +1,7 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 1"""
+ date="2019-03-22T15:48:24Z"
+ content="""
+I've added a protocol= setting, so you can use port=N protocol=https
+"""]]
diff --git a/doc/special_remotes/S3.mdwn b/doc/special_remotes/S3.mdwn
index 73cfa4af0..c286d4ba8 100644
--- a/doc/special_remotes/S3.mdwn
+++ b/doc/special_remotes/S3.mdwn
@@ -58,9 +58,15 @@ the S3 remote.
   affect new objects sent to the remote, but not objects already
   stored there.
 
-* `host` and `port` - Specify in order to use a different, S3 compatable
+* `host` - Specify in order to use a different, S3 compatable
   service.
 
+* `protocol` - Either "http" (the default) or "https". Setting
+  protocol=https implies port=443.
+
+* `port` - Specify the port to connect to. Only needed when using a service
+  on an unusual port. Setting port=443 implies protocol=https.
+
 * `requeststyle` - Set to "path" to use path style requests, instead of the
   default DNS style requests. This is needed with some S3 services.
 

close old bug
diff --git a/doc/bugs/7.20181211+git29-gab4a1bed9_fails_tests_during_neurodebian_build.mdwn b/doc/bugs/7.20181211+git29-gab4a1bed9_fails_tests_during_neurodebian_build.mdwn
index 0cc7582b2..eea834280 100644
--- a/doc/bugs/7.20181211+git29-gab4a1bed9_fails_tests_during_neurodebian_build.mdwn
+++ b/doc/bugs/7.20181211+git29-gab4a1bed9_fails_tests_during_neurodebian_build.mdwn
@@ -24,3 +24,5 @@ FAIL
 """]]
 
 [[!meta author=yoh]]
+
+> [[done]] I think.. --[[Joey]]

comment
diff --git a/doc/todo/git-annex-test___58___skip_tests_if_external_utils_have_problems/comment_1_240c9c45a629124dc35f4ed0dddd7355._comment b/doc/todo/git-annex-test___58___skip_tests_if_external_utils_have_problems/comment_1_240c9c45a629124dc35f4ed0dddd7355._comment
new file mode 100644
index 000000000..42cfd40ee
--- /dev/null
+++ b/doc/todo/git-annex-test___58___skip_tests_if_external_utils_have_problems/comment_1_240c9c45a629124dc35f4ed0dddd7355._comment
@@ -0,0 +1,15 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 1"""
+ date="2019-03-22T14:18:48Z"
+ content="""
+I kind of like that the test suite will fail if git-annex is being used in
+some broken environment, because it gives an easy way to check if git-annex
+is able to fully work.
+
+Note that, the test suite does try a self-test of its ability to use gpg
+before proceeding with other gpg tests; if that self-test fails it does
+abort the other tests in that test block. That self-test does not currently
+test encryption or decrpryption, only that gpg can access the test key
+pair.
+"""]]

comment
diff --git a/doc/todo/simpler__44___trusted_export_remotes/comment_3_3e7be2ba92559a767ea09b764daef2db._comment b/doc/todo/simpler__44___trusted_export_remotes/comment_3_3e7be2ba92559a767ea09b764daef2db._comment
new file mode 100644
index 000000000..0506ae72a
--- /dev/null
+++ b/doc/todo/simpler__44___trusted_export_remotes/comment_3_3e7be2ba92559a767ea09b764daef2db._comment
@@ -0,0 +1,22 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 3"""
+ date="2019-03-22T14:10:41Z"
+ content="""
+I'm doubtful that this would actually let the interface be simplified,
+there are too many differences in the capabilities of different remotes.
+
+For example, if a S3 bucket has versioning disabled, and git-annex imports
+from it, then in this scheme it would need to re-upload the import to the
+key-value location. But, if a S3 bucket has versioning enabled, that upload
+would be redundant and should not be done. And, if a S3 bucket is
+read-only, then an import can't re-upload.
+
+Also, not all users are going to want export remotes to store past versions 
+of files; if they're used for some kind of publication, you may not want
+the exposure/cost of publishing old versions of files there. Of course, you
+could drop the old versions from the remote later, but this would be a
+workflow change from how export remotes work now.
+
+So it seems to me that this would need to be an optional thing.
+"""]]

despam
diff --git a/doc/forum/Problems_using_blake2_backend/comment_2_02e630afa29ebb0d54997f0e54fc70a6._comment b/doc/forum/Problems_using_blake2_backend/comment_2_02e630afa29ebb0d54997f0e54fc70a6._comment
deleted file mode 100644
index b394d7d90..000000000
--- a/doc/forum/Problems_using_blake2_backend/comment_2_02e630afa29ebb0d54997f0e54fc70a6._comment
+++ /dev/null
@@ -1,8 +0,0 @@
-[[!comment format=mdwn
- username="maryjil2596"
- avatar="http://cdn.libravatar.org/avatar/2ce6b78d907f10b244c92330a4f0bd00"
- subject="iTunes Error 0xe8000015"
- date="2019-03-18T06:42:20Z"
- content="""
-Nowadays, a lot of iPhone users are complaining about iTunes Error 0xe8000015. Therefore, I had shared a link <a href=\"https://itunessupport.org/blog/fix-itunes-error-0xe8000015/\">Advanced Solutions To Fix iTunes Error 0xe8000015</a> to fix all the technical issues related to iTunes. Click the link n get rid of the issue in no time.
-"""]]

improve docs
diff --git a/doc/forum/Special_remotes_description_misleading/comment_2_616cc2f7d729682c69a9379df785dda5._comment b/doc/forum/Special_remotes_description_misleading/comment_2_616cc2f7d729682c69a9379df785dda5._comment
new file mode 100644
index 000000000..70bb2bd6c
--- /dev/null
+++ b/doc/forum/Special_remotes_description_misleading/comment_2_616cc2f7d729682c69a9379df785dda5._comment
@@ -0,0 +1,12 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 2"""
+ date="2019-03-22T13:58:06Z"
+ content="""
+Thanks, I see how that could be confusing and have adjusted the
+description.
+
+annex-rsync-transport will work, but you have to put it in the
+configuration of the remote you want it to apply to. annex.rsync-transport
+sets it for all rsync remotes.
+"""]]
diff --git a/doc/special_remotes.mdwn b/doc/special_remotes.mdwn
index 6809c5e85..0ae4346ed 100644
--- a/doc/special_remotes.mdwn
+++ b/doc/special_remotes.mdwn
@@ -4,8 +4,9 @@ local and remote), that store the file contents in their own git-annex
 directory.
 
 But, git-annex also extends git's concept of remotes, with these special
-types of remotes. These can be used just like any normal remote by git-annex.
-They cannot be used by other git commands though.
+types of remotes. These can be used by git-annex to store and retrieve
+the content of files. They cannot be used by other git commands, and
+the git history is not stored in them.
 
 * [[adb]] (for Android devices)
 * [[Amazon_Glacier|glacier]]
diff --git a/doc/special_remotes/rsync.mdwn b/doc/special_remotes/rsync.mdwn
index 7d30b4092..96e452b10 100644
--- a/doc/special_remotes/rsync.mdwn
+++ b/doc/special_remotes/rsync.mdwn
@@ -38,27 +38,23 @@ These parameters can be passed to `git annex initremote` to configure rsync:
   This is typically not a win for rsync, so no need to enable it.
   But, it makes this interoperate with the [[directory]] special remote.
 
-The `annex-rsync-options` git configuration setting can be used to pass
-parameters to rsync.
+The `remote.name.annex-rsync-options` git configuration setting can be used
+to pass parameters to rsync. To pass parameters to rsync only when it's
+downloading and uploading, use `remote.name.annex-rsync-download-options`
+and `remote.name.annex-rsync-upload-options`
 
 ## annex-rsync-transport
 
-You can use the `annex-rsync-transport` git configuration setting to choose
-whether we run rsync over ssh or rsh.  This setting is also used to specify
-parameters that git annex will pass to ssh/rsh.
+You can use the `remote.name.annex-rsync-transport` git configuration
+setting to choose whether we run rsync over ssh or rsh.  This setting
+is also used to specify parameters that git annex will pass to ssh/rsh.
 
-ssh is the default transport; if you'd like to run rsync over rsh, modify your
-.git/config to include
+ssh is the default transport; if you'd like to run rsync over rsh:
 
-        annex-rsync-transport = rsh
-
-under the appropriate remote.
+	git config remote.name.annex-rsync-transport rsh
 
 To pass parameters to ssh/rsh, include the parameters after "rsh" or
 "ssh".  For example, to configure ssh to use the private key at
-`/path/to/private/key`, specify
-
-         annex-rsync-transport = ssh -i /path/to/private/key
+`/path/to/private/key`:
 
-Note that environment variables aren't expanded here, so for example, you
-cannot specify `-i $HOME/.ssh/private_key`.
+	git config renote.name.annex-rsync-transport "ssh -i /path/to/private/key"

fix wrong option, followup
diff --git a/doc/tips/hiding_missing_files.mdwn b/doc/tips/hiding_missing_files.mdwn
index 9fd8d1e8f..49f6c661a 100644
--- a/doc/tips/hiding_missing_files.mdwn
+++ b/doc/tips/hiding_missing_files.mdwn
@@ -95,7 +95,7 @@ operate on. (This might be improved later, but it's how things are currently.)
 What will work is to use `git annex sync`, which knows you're in an adjusted branch
 and can get hidden files.
 
-	git annex sync --content some_file some_directory --no-push --no-pull
+	git annex sync --content-of some_file --no-push --no-pull
 
 Unlike getting files that are hidden, dropping files is no problem, since
 the file you want to drop will be present. But, after dropping a file,
diff --git a/doc/tips/hiding_missing_files/comment_2_9bff461eb281f67d169d4be30129bc13._comment b/doc/tips/hiding_missing_files/comment_2_9bff461eb281f67d169d4be30129bc13._comment
new file mode 100644
index 000000000..108c2aa3c
--- /dev/null
+++ b/doc/tips/hiding_missing_files/comment_2_9bff461eb281f67d169d4be30129bc13._comment
@@ -0,0 +1,10 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 2"""
+ date="2019-03-22T13:50:10Z"
+ content="""
+I've fixed the two problems you spotted in the tip.
+
+git annex sync -C does work for me to get missing files.
+It would be good to file a bug report if you know how to make it not work.
+"""]]

remove unsupported option
diff --git a/doc/tips/hiding_missing_files.mdwn b/doc/tips/hiding_missing_files.mdwn
index 3ee2add76..9fd8d1e8f 100644
--- a/doc/tips/hiding_missing_files.mdwn
+++ b/doc/tips/hiding_missing_files.mdwn
@@ -11,7 +11,7 @@ but it needs some different workflows of using git-annex.
 To get started, your repository needs to be upgraded to v7, since the
 feature does not work in v5 repositories.
 
-	git annex upgrade --version=7
+	git annex upgrade
 
 The [[git-annex adjust|git-annex-adjust]] command sets up an adjusted form
 of a git branch, in this case we'll ask it to hide missing files.
@@ -124,7 +124,7 @@ I set up the repository like this:
 
 	git clone server:/path/to/podcasts
 	cd podcasts
-	git annex upgrade --version=7
+	git annex upgrade
 	git annex adjust --hide-missing
 	git annex group here client
 	git annex wanted here standard

reopen
diff --git a/doc/bugs/Android__44___unable_to_start_browser_.mdwn b/doc/bugs/Android__44___unable_to_start_browser_.mdwn
index 1c94cc1ca..a90741bb0 100644
--- a/doc/bugs/Android__44___unable_to_start_browser_.mdwn
+++ b/doc/bugs/Android__44___unable_to_start_browser_.mdwn
@@ -22,5 +22,3 @@ If I manually open the browser and I copy-paste the url to it, then it works.
 
 Not yet: I tried to use it some years ago to handle my photo collection but I think digikam didn't like the sim links and it was very slow; I also was not lucky with the external (NTFS) drive that I used for sync/backup.
 But I like this project so much that I frequently come back to check for updates and test myself with it.
-
-> closing as not a git-annex bug [[done]] --[[Joey]]
diff --git a/doc/bugs/Android__44___unable_to_start_browser_/comment_3_93e260d1cb9de25fe4e2a6a973f05da6._comment b/doc/bugs/Android__44___unable_to_start_browser_/comment_3_93e260d1cb9de25fe4e2a6a973f05da6._comment
new file mode 100644
index 000000000..332f68cf6
--- /dev/null
+++ b/doc/bugs/Android__44___unable_to_start_browser_/comment_3_93e260d1cb9de25fe4e2a6a973f05da6._comment
@@ -0,0 +1,10 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 3"""
+ date="2019-03-22T13:42:43Z"
+ content="""
+Reopened the bug since you confirmed xdg-open usually works.
+
+Why is it failing when git-annex runs it but not otherwise?
+Perhaps it has something to do with the environment set up by runshell.
+"""]]

Android: Fix typo of name of armv7l in installation script. Thanks, 4omecha.
diff --git a/CHANGELOG b/CHANGELOG
index 1c3f6d045..93c97d729 100644
--- a/CHANGELOG
+++ b/CHANGELOG
@@ -35,6 +35,8 @@ git-annex (7.20190220) UNRELEASED; urgency=medium
     because gpg now always wants to use gpg-agent, and shipping such a daemon
     in those is not a good idea.
   * import: Let --force overwrite symlinks, not only regular files.
+  * Android: Fix typo of name of armv7l in installation script.
+    Thanks, 4omecha.
 
  -- Joey Hess <id@joeyh.name>  Wed, 20 Feb 2019 14:20:59 -0400
 
diff --git a/doc/bugs/lineageOS_android_install_fail__58___incorrect_arch_test.mdwn b/doc/bugs/lineageOS_android_install_fail__58___incorrect_arch_test.mdwn
index 0b1209822..dc53b1546 100644
--- a/doc/bugs/lineageOS_android_install_fail__58___incorrect_arch_test.mdwn
+++ b/doc/bugs/lineageOS_android_install_fail__58___incorrect_arch_test.mdwn
@@ -27,3 +27,4 @@ Patch below:
 ### Have you had any luck using git-annex before? (Sometimes we get tired of reading bug reports all day and a lil' positive end note does wonders)
 Sure, love it! :)
 
+> Lo1! Thanks for the patch. [[done]] --[[Joey]]
diff --git a/doc/install/Android/git-annex-install b/doc/install/Android/git-annex-install
index 6e51afb43..cc85cd4fa 100755
--- a/doc/install/Android/git-annex-install
+++ b/doc/install/Android/git-annex-install
@@ -18,7 +18,7 @@ case $(uname -m) in
 	arm)
 		arch=armel
 		;;
-	armv71)
+	armv7l)
 		arch=armel
 		;;
 	x86_64)

comment
diff --git a/doc/tips/unlocked_files/comment_13_99f82c84aa9d886062aa3e3956e1acf8._comment b/doc/tips/unlocked_files/comment_13_99f82c84aa9d886062aa3e3956e1acf8._comment
new file mode 100644
index 000000000..c4e2d4a1c
--- /dev/null
+++ b/doc/tips/unlocked_files/comment_13_99f82c84aa9d886062aa3e3956e1acf8._comment
@@ -0,0 +1,8 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 13"""
+ date="2019-03-22T13:31:52Z"
+ content="""
+[[todo/annex.thin_without_hardlinks]] is a tracking bug for annex.thin not
+working on FAT etc.
+"""]]

comment
diff --git a/doc/bugs/weird_bug_with_annex_unlock_with_annex.thin_true_about_hard_links/comment_3_57924a0a08da3cafe78b95bf22ae89fd._comment b/doc/bugs/weird_bug_with_annex_unlock_with_annex.thin_true_about_hard_links/comment_3_57924a0a08da3cafe78b95bf22ae89fd._comment
new file mode 100644
index 000000000..88d0134c2
--- /dev/null
+++ b/doc/bugs/weird_bug_with_annex_unlock_with_annex.thin_true_about_hard_links/comment_3_57924a0a08da3cafe78b95bf22ae89fd._comment
@@ -0,0 +1,18 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 3"""
+ date="2019-03-22T13:25:22Z"
+ content="""
+annex.thin will only make one hard link to a given annex object file, so if
+the file that is not getting hard linked has the same content as another
+file in the repository that is getting hard linked, that explains why.
+
+It would be very susprising for two different files in the repo to end up
+hard linked together and then a modification to one change both files.
+
+You should really upgrade to git-annex 7.x when using v7 mode. You
+are both using versions that are missing quite a lot of the fixes needed to
+get v7 to release quality. 
+So please upgrade to a current version and see if your execute bit problems
+persist there.
+"""]]

comment and toddo
diff --git a/doc/bugs/__34__git_status__34___thread_blocked_indefinitely_in_an_MVar_operation/comment_4_df73b69e651c728943a404223f350ebf._comment b/doc/bugs/__34__git_status__34___thread_blocked_indefinitely_in_an_MVar_operation/comment_4_df73b69e651c728943a404223f350ebf._comment
new file mode 100644
index 000000000..92d5c7753
--- /dev/null
+++ b/doc/bugs/__34__git_status__34___thread_blocked_indefinitely_in_an_MVar_operation/comment_4_df73b69e651c728943a404223f350ebf._comment
@@ -0,0 +1,15 @@
+[[!comment format=mdwn
+ username="joey"
+ subject="""comment 4"""
+ date="2019-03-22T13:14:51Z"
+ content="""
+Ok, it makes sense that sqlite would crash creating a DB if the disk was
+full.
+
+I hope that the earlier Mvar error was the same problem, just a different
+handling of the exception in that version. Or something similar failing on
+full disk.
+
+annex.thin needing hard links is a limitation that may one day be lifted,
+see [[todo/annex.thin_without_hardlinks]]
+"""]]
diff --git a/doc/todo/annex.thin_without_hardlinks.mdwn b/doc/todo/annex.thin_without_hardlinks.mdwn
new file mode 100644
index 000000000..40e235089
--- /dev/null
+++ b/doc/todo/annex.thin_without_hardlinks.mdwn
@@ -0,0 +1,15 @@
+Currently annex.thin needs hard link support to be efficient;
+it hard links the content from .git/annex/objects into the work tree.
+When hard links are not supported, two copie of checked out files exist on
+disk.
+
+Would it be possible to make it work w/o hard links? Note that direct mode
+does avoid two copies of files.
+
+IIRC the main reason for the hard link is so, when git checkout deletes a
+work tree file, the only copy of the file is not lost. Seems this would
+need a git hook run before checkout to rescue such files.
+
+Also some parts of git-annex's code, including `withObjectLoc`, assume
+that the .annex/objects is present, and so it would need to be changed
+to look at the work tree file. --[[Joey]]