blob: f8c8093caf1652187e760505754cc523ea0635fc [file] [log] [blame]
Alex Stapletonc5fffd32014-03-18 15:29:00 +00001Submitting patches
Paul Kehrer0839aa82014-02-11 22:36:51 -06002==================
3
4* Always make a new branch for your work.
5* Patches should be small to facilitate easier review. `Studies have shown`_
6 that review quality falls off as patch size grows. Sometimes this will result
7 in many small PRs to land a single large feature.
8* Larger changes should be discussed on `our mailing list`_ before submission.
9* New features and significant bug fixes should be documented in the
10 :doc:`/changelog`.
11
12If you believe you've identified a security issue in ``cryptography``, please
13follow the directions on the :doc:`security page </security>`.
14
15Code
16----
17
Paul Kehrer5b6ce2a2014-02-24 20:16:10 -060018When in doubt, refer to :pep:`8` for Python code. You can check if your code
19meets our automated requirements by running ``flake8`` against it. If you've
20installed the development requirements this will automatically use our
21configuration. You can also run the ``tox`` job with ``tox -e pep8``.
Paul Kehrer0839aa82014-02-11 22:36:51 -060022
23`Write comments as complete sentences.`_
24
25Every code file must start with the boilerplate notice of the Apache License.
26Additionally, every Python code file must contain
27
28.. code-block:: python
29
30 from __future__ import absolute_import, division, print_function
31
Alex Stapletonc5fffd32014-03-18 15:29:00 +000032API considerations
Paul Kehrer0839aa82014-02-11 22:36:51 -060033~~~~~~~~~~~~~~~~~~
34
35Most projects' APIs are designed with a philosophy of "make easy things easy,
36and make hard things possible". One of the perils of writing cryptographic code
37is that secure code looks just like insecure code, and its results are almost
38always indistinguishable. As a result ``cryptography`` has, as a design
39philosophy: "make it hard to do insecure things". Here are a few strategies for
40API design that should be both followed, and should inspire other API choices:
41
42If it is necessary to compare a user provided value with a computed value (for
43example, verifying a signature), there should be an API provided that performs
44the verification in a secure way (for example, using a constant time
45comparison), rather than requiring the user to perform the comparison
46themselves.
47
48If it is incorrect to ignore the result of a method, it should raise an
49exception, and not return a boolean ``True``/``False`` flag. For example, a
50method to verify a signature should raise ``InvalidSignature``, and not return
51whether the signature was valid.
52
53.. code-block:: python
54
55 # This is bad.
56 def verify(sig):
57 # ...
58 return is_valid
59
60 # Good!
61 def verify(sig):
62 # ...
63 if not is_valid:
64 raise InvalidSignature
65
66Every recipe should include a version or algorithmic marker of some sort in its
67output in order to allow transparent upgrading of the algorithms in use, as
68the algorithms or parameters needed to achieve a given security margin evolve.
69
70APIs at the :doc:`/hazmat/primitives/index` layer should always take an
71explicit backend, APIs at the recipes layer should automatically use the
72:func:`~cryptography.hazmat.backends.default_backend`, but optionally allow
73specifying a different backend.
74
75C bindings
76~~~~~~~~~~
77
Laurens Van Houtven0a1d9e12014-06-23 14:06:16 +020078More information on C bindings can be found in :doc:`the dedicated
79section of the documentation <c-bindings>`.
80
Paul Kehrer0839aa82014-02-11 22:36:51 -060081When binding C code with ``cffi`` we have our own style guide, it's pretty
82simple.
83
84Don't name parameters:
85
86.. code-block:: c
87
Laurens Van Houtvened3d15b2014-06-23 13:50:35 +020088 /* Good */
Paul Kehrer0839aa82014-02-11 22:36:51 -060089 long f(long);
Laurens Van Houtvened3d15b2014-06-23 13:50:35 +020090 /* Bad */
Paul Kehrer0839aa82014-02-11 22:36:51 -060091 long f(long x);
92
93...unless they're inside a struct:
94
95.. code-block:: c
96
97 struct my_struct {
98 char *name;
99 int number;
100 ...;
101 };
102
103Include ``void`` if the function takes no arguments:
104
105.. code-block:: c
106
Laurens Van Houtvened3d15b2014-06-23 13:50:35 +0200107 /* Good */
Paul Kehrer0839aa82014-02-11 22:36:51 -0600108 long f(void);
Laurens Van Houtvened3d15b2014-06-23 13:50:35 +0200109 /* Bad */
Paul Kehrer0839aa82014-02-11 22:36:51 -0600110 long f();
111
112Wrap lines at 80 characters like so:
113
114.. code-block:: c
115
Laurens Van Houtvened3d15b2014-06-23 13:50:35 +0200116 /* Pretend this went to 80 characters */
Paul Kehrer0839aa82014-02-11 22:36:51 -0600117 long f(long, long,
118 int *)
119
120Include a space after commas between parameters:
121
122.. code-block:: c
123
Laurens Van Houtvened3d15b2014-06-23 13:50:35 +0200124 /* Good */
Paul Kehrer0839aa82014-02-11 22:36:51 -0600125 long f(int, char *)
Laurens Van Houtvened3d15b2014-06-23 13:50:35 +0200126 /* Bad */
Paul Kehrer0839aa82014-02-11 22:36:51 -0600127 long f(int,char *)
128
Laurens Van Houtven0d1122d2014-06-23 13:50:51 +0200129Use C-style ``/* */`` comments instead of C++-style ``//``:
130
131.. code-block:: c
132
133 // Bad
134 /* Good */
135
Paul Kehrer0839aa82014-02-11 22:36:51 -0600136Values set by ``#define`` should be assigned the appropriate type. If you see
137this:
138
139.. code-block:: c
140
141 #define SOME_INTEGER_LITERAL 0x0;
142 #define SOME_UNSIGNED_INTEGER_LITERAL 0x0001U;
143 #define SOME_STRING_LITERAL "hello";
144
145...it should be added to the bindings like so:
146
147.. code-block:: c
148
149 static const int SOME_INTEGER_LITERAL;
150 static const unsigned int SOME_UNSIGNED_INTEGER_LITERAL;
151 static const char *const SOME_STRING_LITERAL;
152
153Tests
154-----
155
156All code changes must be accompanied by unit tests with 100% code coverage (as
157measured by the combined metrics across our build matrix).
158
159When implementing a new primitive or recipe ``cryptography`` requires that you
Paul Kehrer1681a692014-02-11 23:43:51 -0600160provide a set of test vectors. See :doc:`/development/test-vectors` for more
161details.
Paul Kehrer0839aa82014-02-11 22:36:51 -0600162
163Documentation
164-------------
165
Paul Kehrer813b2942014-06-05 12:40:56 -0500166All features should be documented with prose in the ``docs`` section. To ensure
167it builds and passes `doc8`_ style checks you can run ``tox -e docs``.
Paul Kehrer0839aa82014-02-11 22:36:51 -0600168
169Because of the inherent challenges in implementing correct cryptographic
170systems, we want to make our documentation point people in the right directions
171as much as possible. To that end:
172
173* When documenting a generic interface, use a strong algorithm in examples.
174 (e.g. when showing a hashing example, don't use
175 :class:`~cryptography.hazmat.primitives.hashes.MD5`)
176* When giving prescriptive advice, always provide references and supporting
177 material.
178* When there is real disagreement between cryptographic experts, represent both
179 sides of the argument and describe the trade-offs clearly.
180
181When documenting a new module in the ``hazmat`` package, its documentation
182should begin with the "Hazardous Materials" warning:
183
184.. code-block:: rest
185
186 .. hazmat::
187
188When referring to a hypothetical individual (such as "a person receiving an
189encrypted message") use gender neutral pronouns (they/them/their).
190
191Docstrings are typically only used when writing abstract classes, but should
192be written like this if required:
193
194.. code-block:: python
195
196 def some_function(some_arg):
197 """
198 Does some things.
199
200 :param some_arg: Some argument.
201 """
202
203So, specifically:
204
205* Always use three double quotes.
206* Put the three double quotes on their own line.
207* No blank line at the end.
208* Use Sphinx parameter/attribute documentation `syntax`_.
209
210
211.. _`Write comments as complete sentences.`: http://nedbatchelder.com/blog/201401/comments_should_be_sentences.html
212.. _`syntax`: http://sphinx-doc.org/domains.html#info-field-lists
213.. _`Studies have shown`: http://www.ibm.com/developerworks/rational/library/11-proven-practices-for-peer-review/
214.. _`our mailing list`: https://mail.python.org/mailman/listinfo/cryptography-dev
Paul Kehrer813b2942014-06-05 12:40:56 -0500215.. _`doc8`: https://github.com/stackforge/doc8