### Description

It is impossible to create a follower index with a `$` character in its name (please note, it is possible to create a regular index with `$` in its name).

This could be reproduced by rest request:
```
PUT /my-index/_ccr/follow
{
    "remote_cluster": "my-remote-cluster",
    "leader_index": "my-index$follower"
}
```

or `CcrIntegTestCase`:

```
    public void testFollowIndex() throws Exception {
        assertAcked(leaderClient().admin().indices().prepareCreate("my$index"));
        setupRemoteCluster();
        final PutFollowAction.Request followRequest = putFollow("my$index", "my$index");
        followerClient().execute(PutFollowAction.INSTANCE, followRequest).get();
    }
```

This is happening as during initial follow phase we restore the leader cluster from the remote using a snapshot restore.
Corresponding request is created with index name added to `RestoreSnapshotRequest#renamePattern` (regexp) without escaping `$`.

x-pack/plugin/ccr/src/internalClusterTest/java/org/elasticsearch/xpack/ccr/IndexFollowingIT.java
final String leaderIndexSettings = getIndexSettings(between(1, 2), between(0, 1));
        assertAcked(leaderClient().admin().indices().prepareCreate("leader").setSource(leaderIndexSettings, XContentType.JSON));
        followerClient().execute(PutFollowAction.INSTANCE, putFollow("leader", "follower")).get();
        pauseFollow("follower");
        followerClient().admin().indices().close(new CloseIndexRequest("follower").masterNodeTimeout(TimeValue.MAX_VALUE)).actionGet();
        assertAcked(followerClient().execute(UnfollowAction.INSTANCE, new UnfollowAction.Request("follower")).actionGet());
        followerClient().admin().indices().open(new OpenIndexRequest("follower").masterNodeTimeout(TimeValue.MAX_VALUE)).actionGet();
        final IndicesAliasesRequest request = new IndicesAliasesRequest().masterNodeTimeout(TimeValue.MAX_VALUE)
            .addAliasAction(IndicesAliasesRequest.AliasActions.add().index("follower").alias("follower_alias"));
        assertAcked(followerClient().admin().indices().aliases(request).actionGet());
        final GetAliasesResponse response = followerClient().admin()
            .indices()
            .getAliases(new GetAliasesRequest("follower_alias"))
            .actionGet();
        assertThat(response.getAliases().keySet().size(), equalTo(1));
        assertThat(response.getAliases().keySet().iterator().next(), equalTo("follower"));
        final List<AliasMetadata> aliasMetadata = response.getAliases().get("follower");
        assertThat(aliasMetadata, hasSize(1));
        assertThat(aliasMetadata.get(0).alias(), equalTo("follower_alias"));
    }
    public void testFollowIndex_backlog() throws Exception {
        int numberOfShards = between(1, 5);
        String leaderIndexSettings = getIndexSettings(numberOfShards, between(0, 1));
        assertAcked(leaderClient().admin().indices().prepareCreate("index1").setSource(leaderIndexSettings, XContentType.JSON));
        BulkProcessor2.Listener listener = new BulkProcessor2.Listener() {
            @Override
            public void beforeBulk(long executionId, BulkRequest request) {}
            @Override
            public void afterBulk(long executionId, BulkRequest request, BulkResponse response) {}
            @Override