diff --git a/mercurial/bundle2.py b/mercurial/bundle2.py
index 8c74b3ce5b7059d8acdfd24175e29f77730457df_bWVyY3VyaWFsL2J1bmRsZTIucHk=..8532f5e1b9df0fd970c446047e76a56cfcf9a6a1_bWVyY3VyaWFsL2J1bmRsZTIucHk= 100644
--- a/mercurial/bundle2.py
+++ b/mercurial/bundle2.py
@@ -47,6 +47,10 @@
 
   Empty name are obviously forbidden.
 
+  Name MUST start with a letter. This first character has to be capitalizable.
+  The capitalisation of the first letter will be used to know if an option is
+  advisory or mandatory. This is not implemented yet.
+
   Stream parameters use a simple textual format for two main reasons:
 
   - Stream level parameters should remains simple and we want to discourage any
@@ -72,6 +76,7 @@
 import util
 import struct
 import urllib
+import string
 
 import changegroup
 from i18n import _
@@ -100,6 +105,8 @@
         """add a stream level parameter"""
         if not name:
             raise ValueError('empty parameter name')
+        if name[0] not in string.letters:
+            raise ValueError('non letter first character: %r' % name)
         self._params.append((name, value))
 
     def getchunks(self):
diff --git a/tests/test-bundle2.t b/tests/test-bundle2.t
index 8c74b3ce5b7059d8acdfd24175e29f77730457df_dGVzdHMvdGVzdC1idW5kbGUyLnQ=..8532f5e1b9df0fd970c446047e76a56cfcf9a6a1_dGVzdHMvdGVzdC1idW5kbGUyLnQ= 100644
--- a/tests/test-bundle2.t
+++ b/tests/test-bundle2.t
@@ -162,3 +162,9 @@
   $ hg bundle2 --param '' --quiet
   abort: empty parameter name
   [255]
+
+bad parameter name
+
+  $ hg bundle2 --param 42babar
+  abort: non letter first character: '42babar'
+  [255]