Issue #23501: Argumen Clinic now generates code into separate files by default.
diff --git a/Objects/bytearrayobject.c b/Objects/bytearrayobject.c
index 333f9c8..1dce4c7 100644
--- a/Objects/bytearrayobject.c
+++ b/Objects/bytearrayobject.c
@@ -90,6 +90,8 @@
     return 1;
 }
 
+#include "clinic/bytearrayobject.c.h"
+
 /* Direct API functions */
 
 PyObject *
@@ -1266,27 +1268,9 @@
 Remove all items from the bytearray.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_clear__doc__,
-"clear($self, /)\n"
-"--\n"
-"\n"
-"Remove all items from the bytearray.");
-
-#define BYTEARRAY_CLEAR_METHODDEF    \
-    {"clear", (PyCFunction)bytearray_clear, METH_NOARGS, bytearray_clear__doc__},
-
-static PyObject *
-bytearray_clear_impl(PyByteArrayObject *self);
-
-static PyObject *
-bytearray_clear(PyByteArrayObject *self, PyObject *Py_UNUSED(ignored))
-{
-    return bytearray_clear_impl(self);
-}
-
 static PyObject *
 bytearray_clear_impl(PyByteArrayObject *self)
-/*[clinic end generated code: output=5344093031e2f36c input=e524fd330abcdc18]*/
+/*[clinic end generated code: output=85c2fe6aede0956c input=e524fd330abcdc18]*/
 {
     if (PyByteArray_Resize((PyObject *)self, 0) < 0)
         return NULL;
@@ -1301,27 +1285,9 @@
 Return a copy of B.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_copy__doc__,
-"copy($self, /)\n"
-"--\n"
-"\n"
-"Return a copy of B.");
-
-#define BYTEARRAY_COPY_METHODDEF    \
-    {"copy", (PyCFunction)bytearray_copy, METH_NOARGS, bytearray_copy__doc__},
-
-static PyObject *
-bytearray_copy_impl(PyByteArrayObject *self);
-
-static PyObject *
-bytearray_copy(PyByteArrayObject *self, PyObject *Py_UNUSED(ignored))
-{
-    return bytearray_copy_impl(self);
-}
-
 static PyObject *
 bytearray_copy_impl(PyByteArrayObject *self)
-/*[clinic end generated code: output=8788ed299f7f2214 input=6d5d2975aa0f33f3]*/
+/*[clinic end generated code: output=68cfbcfed484c132 input=6d5d2975aa0f33f3]*/
 {
     return PyByteArray_FromStringAndSize(PyByteArray_AS_STRING((PyObject *)self),
                                          PyByteArray_GET_SIZE(self));
@@ -1557,53 +1523,9 @@
 The remaining characters are mapped through the given translation table.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_translate__doc__,
-"translate(table, [deletechars])\n"
-"Return a copy with each character mapped by the given translation table.\n"
-"\n"
-"  table\n"
-"    Translation table, which must be a bytes object of length 256.\n"
-"\n"
-"All characters occurring in the optional argument deletechars are removed.\n"
-"The remaining characters are mapped through the given translation table.");
-
-#define BYTEARRAY_TRANSLATE_METHODDEF    \
-    {"translate", (PyCFunction)bytearray_translate, METH_VARARGS, bytearray_translate__doc__},
-
-static PyObject *
-bytearray_translate_impl(PyByteArrayObject *self, PyObject *table, int group_right_1, PyObject *deletechars);
-
-static PyObject *
-bytearray_translate(PyByteArrayObject *self, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    PyObject *table;
-    int group_right_1 = 0;
-    PyObject *deletechars = NULL;
-
-    switch (PyTuple_GET_SIZE(args)) {
-        case 1:
-            if (!PyArg_ParseTuple(args, "O:translate", &table))
-                goto exit;
-            break;
-        case 2:
-            if (!PyArg_ParseTuple(args, "OO:translate", &table, &deletechars))
-                goto exit;
-            group_right_1 = 1;
-            break;
-        default:
-            PyErr_SetString(PyExc_TypeError, "bytearray.translate requires 1 to 2 arguments");
-            goto exit;
-    }
-    return_value = bytearray_translate_impl(self, table, group_right_1, deletechars);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytearray_translate_impl(PyByteArrayObject *self, PyObject *table, int group_right_1, PyObject *deletechars)
-/*[clinic end generated code: output=a709df81d41db4b7 input=b749ad85f4860824]*/
+/*[clinic end generated code: output=fa3ea4f9a8d58bc7 input=b749ad85f4860824]*/
 {
     char *input, *output;
     const char *table_chars;
@@ -1708,50 +1630,9 @@
 The bytes objects frm and to must be of the same length.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_maketrans__doc__,
-"maketrans(frm, to, /)\n"
-"--\n"
-"\n"
-"Return a translation table useable for the bytes or bytearray translate method.\n"
-"\n"
-"The returned table will be one where each byte in frm is mapped to the byte at\n"
-"the same position in to.\n"
-"\n"
-"The bytes objects frm and to must be of the same length.");
-
-#define BYTEARRAY_MAKETRANS_METHODDEF    \
-    {"maketrans", (PyCFunction)bytearray_maketrans, METH_VARARGS|METH_STATIC, bytearray_maketrans__doc__},
-
-static PyObject *
-bytearray_maketrans_impl(Py_buffer *frm, Py_buffer *to);
-
-static PyObject *
-bytearray_maketrans(void *null, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    Py_buffer frm = {NULL, NULL};
-    Py_buffer to = {NULL, NULL};
-
-    if (!PyArg_ParseTuple(args,
-        "y*y*:maketrans",
-        &frm, &to))
-        goto exit;
-    return_value = bytearray_maketrans_impl(&frm, &to);
-
-exit:
-    /* Cleanup for frm */
-    if (frm.obj)
-       PyBuffer_Release(&frm);
-    /* Cleanup for to */
-    if (to.obj)
-       PyBuffer_Release(&to);
-
-    return return_value;
-}
-
 static PyObject *
 bytearray_maketrans_impl(Py_buffer *frm, Py_buffer *to)
-/*[clinic end generated code: output=d332622814c26f4b input=5925a81d2fbbf151]*/
+/*[clinic end generated code: output=1df267d99f56b15e input=5925a81d2fbbf151]*/
 {
     return _Py_bytes_maketrans(frm, to);
 }
@@ -2260,53 +2141,9 @@
 replaced.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_replace__doc__,
-"replace($self, old, new, count=-1, /)\n"
-"--\n"
-"\n"
-"Return a copy with all occurrences of substring old replaced by new.\n"
-"\n"
-"  count\n"
-"    Maximum number of occurrences to replace.\n"
-"    -1 (the default value) means replace all occurrences.\n"
-"\n"
-"If the optional argument count is given, only the first count occurrences are\n"
-"replaced.");
-
-#define BYTEARRAY_REPLACE_METHODDEF    \
-    {"replace", (PyCFunction)bytearray_replace, METH_VARARGS, bytearray_replace__doc__},
-
-static PyObject *
-bytearray_replace_impl(PyByteArrayObject *self, Py_buffer *old, Py_buffer *new, Py_ssize_t count);
-
-static PyObject *
-bytearray_replace(PyByteArrayObject *self, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    Py_buffer old = {NULL, NULL};
-    Py_buffer new = {NULL, NULL};
-    Py_ssize_t count = -1;
-
-    if (!PyArg_ParseTuple(args,
-        "y*y*|n:replace",
-        &old, &new, &count))
-        goto exit;
-    return_value = bytearray_replace_impl(self, &old, &new, count);
-
-exit:
-    /* Cleanup for old */
-    if (old.obj)
-       PyBuffer_Release(&old);
-    /* Cleanup for new */
-    if (new.obj)
-       PyBuffer_Release(&new);
-
-    return return_value;
-}
-
 static PyObject *
 bytearray_replace_impl(PyByteArrayObject *self, Py_buffer *old, Py_buffer *new, Py_ssize_t count)
-/*[clinic end generated code: output=9997fbbd5bac4883 input=aa379d988637c7fb]*/
+/*[clinic end generated code: output=3fc105c8232d7b3f input=aa379d988637c7fb]*/
 {
     return (PyObject *)replace((PyByteArrayObject *) self,
                                old->buf, old->len,
@@ -2327,47 +2164,9 @@
 Return a list of the sections in the bytearray, using sep as the delimiter.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_split__doc__,
-"split($self, /, sep=None, maxsplit=-1)\n"
-"--\n"
-"\n"
-"Return a list of the sections in the bytearray, using sep as the delimiter.\n"
-"\n"
-"  sep\n"
-"    The delimiter according which to split the bytearray.\n"
-"    None (the default value) means split on ASCII whitespace characters\n"
-"    (space, tab, return, newline, formfeed, vertical tab).\n"
-"  maxsplit\n"
-"    Maximum number of splits to do.\n"
-"    -1 (the default value) means no limit.");
-
-#define BYTEARRAY_SPLIT_METHODDEF    \
-    {"split", (PyCFunction)bytearray_split, METH_VARARGS|METH_KEYWORDS, bytearray_split__doc__},
-
-static PyObject *
-bytearray_split_impl(PyByteArrayObject *self, PyObject *sep, Py_ssize_t maxsplit);
-
-static PyObject *
-bytearray_split(PyByteArrayObject *self, PyObject *args, PyObject *kwargs)
-{
-    PyObject *return_value = NULL;
-    static char *_keywords[] = {"sep", "maxsplit", NULL};
-    PyObject *sep = Py_None;
-    Py_ssize_t maxsplit = -1;
-
-    if (!PyArg_ParseTupleAndKeywords(args, kwargs,
-        "|On:split", _keywords,
-        &sep, &maxsplit))
-        goto exit;
-    return_value = bytearray_split_impl(self, sep, maxsplit);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytearray_split_impl(PyByteArrayObject *self, PyObject *sep, Py_ssize_t maxsplit)
-/*[clinic end generated code: output=062a3d87d6f918fa input=24f82669f41bf523]*/
+/*[clinic end generated code: output=cdccf5a29dbf7eb5 input=24f82669f41bf523]*/
 {
     Py_ssize_t len = PyByteArray_GET_SIZE(self), n;
     const char *s = PyByteArray_AS_STRING(self), *sub;
@@ -2409,25 +2208,9 @@
 bytearray object and two empty bytearray objects.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_partition__doc__,
-"partition($self, sep, /)\n"
-"--\n"
-"\n"
-"Partition the bytearray into three parts using the given separator.\n"
-"\n"
-"This will search for the separator sep in the bytearray. If the separator is\n"
-"found, returns a 3-tuple containing the part before the separator, the\n"
-"separator itself, and the part after it.\n"
-"\n"
-"If the separator is not found, returns a 3-tuple containing the original\n"
-"bytearray object and two empty bytearray objects.");
-
-#define BYTEARRAY_PARTITION_METHODDEF    \
-    {"partition", (PyCFunction)bytearray_partition, METH_O, bytearray_partition__doc__},
-
 static PyObject *
 bytearray_partition(PyByteArrayObject *self, PyObject *sep)
-/*[clinic end generated code: output=2645138221fe6f4d input=7d7fe37b1696d506]*/
+/*[clinic end generated code: output=45d2525ddd35f957 input=7d7fe37b1696d506]*/
 {
     PyObject *bytesep, *result;
 
@@ -2463,25 +2246,9 @@
 objects and the original bytearray object.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_rpartition__doc__,
-"rpartition($self, sep, /)\n"
-"--\n"
-"\n"
-"Partition the bytes into three parts using the given separator.\n"
-"\n"
-"This will search for the separator sep in the bytearray, starting and the end.\n"
-"If the separator is found, returns a 3-tuple containing the part before the\n"
-"separator, the separator itself, and the part after it.\n"
-"\n"
-"If the separator is not found, returns a 3-tuple containing two empty bytearray\n"
-"objects and the original bytearray object.");
-
-#define BYTEARRAY_RPARTITION_METHODDEF    \
-    {"rpartition", (PyCFunction)bytearray_rpartition, METH_O, bytearray_rpartition__doc__},
-
 static PyObject *
 bytearray_rpartition(PyByteArrayObject *self, PyObject *sep)
-/*[clinic end generated code: output=ed13e54605d007de input=9b8cd540c1b75853]*/
+/*[clinic end generated code: output=440de3c9426115e8 input=9b8cd540c1b75853]*/
 {
     PyObject *bytesep, *result;
 
@@ -2508,49 +2275,9 @@
 Splitting is done starting at the end of the bytearray and working to the front.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_rsplit__doc__,
-"rsplit($self, /, sep=None, maxsplit=-1)\n"
-"--\n"
-"\n"
-"Return a list of the sections in the bytearray, using sep as the delimiter.\n"
-"\n"
-"  sep\n"
-"    The delimiter according which to split the bytearray.\n"
-"    None (the default value) means split on ASCII whitespace characters\n"
-"    (space, tab, return, newline, formfeed, vertical tab).\n"
-"  maxsplit\n"
-"    Maximum number of splits to do.\n"
-"    -1 (the default value) means no limit.\n"
-"\n"
-"Splitting is done starting at the end of the bytearray and working to the front.");
-
-#define BYTEARRAY_RSPLIT_METHODDEF    \
-    {"rsplit", (PyCFunction)bytearray_rsplit, METH_VARARGS|METH_KEYWORDS, bytearray_rsplit__doc__},
-
-static PyObject *
-bytearray_rsplit_impl(PyByteArrayObject *self, PyObject *sep, Py_ssize_t maxsplit);
-
-static PyObject *
-bytearray_rsplit(PyByteArrayObject *self, PyObject *args, PyObject *kwargs)
-{
-    PyObject *return_value = NULL;
-    static char *_keywords[] = {"sep", "maxsplit", NULL};
-    PyObject *sep = Py_None;
-    Py_ssize_t maxsplit = -1;
-
-    if (!PyArg_ParseTupleAndKeywords(args, kwargs,
-        "|On:rsplit", _keywords,
-        &sep, &maxsplit))
-        goto exit;
-    return_value = bytearray_rsplit_impl(self, sep, maxsplit);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytearray_rsplit_impl(PyByteArrayObject *self, PyObject *sep, Py_ssize_t maxsplit)
-/*[clinic end generated code: output=affaf9fc2aae8d41 input=a68286e4dd692ffe]*/
+/*[clinic end generated code: output=4d648cf3ac65c9e9 input=a68286e4dd692ffe]*/
 {
     Py_ssize_t len = PyByteArray_GET_SIZE(self), n;
     const char *s = PyByteArray_AS_STRING(self), *sub;
@@ -2583,27 +2310,9 @@
 Reverse the order of the values in B in place.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_reverse__doc__,
-"reverse($self, /)\n"
-"--\n"
-"\n"
-"Reverse the order of the values in B in place.");
-
-#define BYTEARRAY_REVERSE_METHODDEF    \
-    {"reverse", (PyCFunction)bytearray_reverse, METH_NOARGS, bytearray_reverse__doc__},
-
-static PyObject *
-bytearray_reverse_impl(PyByteArrayObject *self);
-
-static PyObject *
-bytearray_reverse(PyByteArrayObject *self, PyObject *Py_UNUSED(ignored))
-{
-    return bytearray_reverse_impl(self);
-}
-
 static PyObject *
 bytearray_reverse_impl(PyByteArrayObject *self)
-/*[clinic end generated code: output=5d5e5f0bfc67f476 input=7933a499b8597bd1]*/
+/*[clinic end generated code: output=9f7616f29ab309d3 input=7933a499b8597bd1]*/
 {
     char swap, *head, *tail;
     Py_ssize_t i, j, n = Py_SIZE(self);
@@ -2642,43 +2351,9 @@
 Insert a single item into the bytearray before the given index.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_insert__doc__,
-"insert($self, index, item, /)\n"
-"--\n"
-"\n"
-"Insert a single item into the bytearray before the given index.\n"
-"\n"
-"  index\n"
-"    The index where the value is to be inserted.\n"
-"  item\n"
-"    The item to be inserted.");
-
-#define BYTEARRAY_INSERT_METHODDEF    \
-    {"insert", (PyCFunction)bytearray_insert, METH_VARARGS, bytearray_insert__doc__},
-
-static PyObject *
-bytearray_insert_impl(PyByteArrayObject *self, Py_ssize_t index, int item);
-
-static PyObject *
-bytearray_insert(PyByteArrayObject *self, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    Py_ssize_t index;
-    int item;
-
-    if (!PyArg_ParseTuple(args,
-        "nO&:insert",
-        &index, _getbytevalue, &item))
-        goto exit;
-    return_value = bytearray_insert_impl(self, index, item);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytearray_insert_impl(PyByteArrayObject *self, Py_ssize_t index, int item)
-/*[clinic end generated code: output=5ec9340d4ad19080 input=833766836ba30e1e]*/
+/*[clinic end generated code: output=76c775a70e7b07b7 input=833766836ba30e1e]*/
 {
     Py_ssize_t n = Py_SIZE(self);
     char *buf;
@@ -2716,40 +2391,9 @@
 Append a single item to the end of the bytearray.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_append__doc__,
-"append($self, item, /)\n"
-"--\n"
-"\n"
-"Append a single item to the end of the bytearray.\n"
-"\n"
-"  item\n"
-"    The item to be appended.");
-
-#define BYTEARRAY_APPEND_METHODDEF    \
-    {"append", (PyCFunction)bytearray_append, METH_VARARGS, bytearray_append__doc__},
-
-static PyObject *
-bytearray_append_impl(PyByteArrayObject *self, int item);
-
-static PyObject *
-bytearray_append(PyByteArrayObject *self, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    int item;
-
-    if (!PyArg_ParseTuple(args,
-        "O&:append",
-        _getbytevalue, &item))
-        goto exit;
-    return_value = bytearray_append_impl(self, item);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytearray_append_impl(PyByteArrayObject *self, int item)
-/*[clinic end generated code: output=b5b3325bb3bbaf85 input=ae56ea87380407cc]*/
+/*[clinic end generated code: output=a154e19ed1886cb6 input=ae56ea87380407cc]*/
 {
     Py_ssize_t n = Py_SIZE(self);
 
@@ -2777,21 +2421,9 @@
 Append all the items from the iterator or sequence to the end of the bytearray.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_extend__doc__,
-"extend($self, iterable_of_ints, /)\n"
-"--\n"
-"\n"
-"Append all the items from the iterator or sequence to the end of the bytearray.\n"
-"\n"
-"  iterable_of_ints\n"
-"    The iterable of items to append.");
-
-#define BYTEARRAY_EXTEND_METHODDEF    \
-    {"extend", (PyCFunction)bytearray_extend, METH_O, bytearray_extend__doc__},
-
 static PyObject *
 bytearray_extend(PyByteArrayObject *self, PyObject *iterable_of_ints)
-/*[clinic end generated code: output=13b0c13ad5110dfb input=ce83a5d75b70d850]*/
+/*[clinic end generated code: output=98155dbe249170b1 input=ce83a5d75b70d850]*/
 {
     PyObject *it, *item, *bytearray_obj;
     Py_ssize_t buf_size = 0, len = 0;
@@ -2877,43 +2509,9 @@
 If no index argument is given, will pop the last item.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_pop__doc__,
-"pop($self, index=-1, /)\n"
-"--\n"
-"\n"
-"Remove and return a single item from B.\n"
-"\n"
-"  index\n"
-"    The index from where to remove the item.\n"
-"    -1 (the default value) means remove the last item.\n"
-"\n"
-"If no index argument is given, will pop the last item.");
-
-#define BYTEARRAY_POP_METHODDEF    \
-    {"pop", (PyCFunction)bytearray_pop, METH_VARARGS, bytearray_pop__doc__},
-
-static PyObject *
-bytearray_pop_impl(PyByteArrayObject *self, Py_ssize_t index);
-
-static PyObject *
-bytearray_pop(PyByteArrayObject *self, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    Py_ssize_t index = -1;
-
-    if (!PyArg_ParseTuple(args,
-        "|n:pop",
-        &index))
-        goto exit;
-    return_value = bytearray_pop_impl(self, index);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytearray_pop_impl(PyByteArrayObject *self, Py_ssize_t index)
-/*[clinic end generated code: output=3b763e548e79af96 input=0797e6c0ca9d5a85]*/
+/*[clinic end generated code: output=e0ccd401f8021da8 input=0797e6c0ca9d5a85]*/
 {
     int value;
     Py_ssize_t n = Py_SIZE(self);
@@ -2953,40 +2551,9 @@
 Remove the first occurrence of a value in the bytearray.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_remove__doc__,
-"remove($self, value, /)\n"
-"--\n"
-"\n"
-"Remove the first occurrence of a value in the bytearray.\n"
-"\n"
-"  value\n"
-"    The value to remove.");
-
-#define BYTEARRAY_REMOVE_METHODDEF    \
-    {"remove", (PyCFunction)bytearray_remove, METH_VARARGS, bytearray_remove__doc__},
-
-static PyObject *
-bytearray_remove_impl(PyByteArrayObject *self, int value);
-
-static PyObject *
-bytearray_remove(PyByteArrayObject *self, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    int value;
-
-    if (!PyArg_ParseTuple(args,
-        "O&:remove",
-        _getbytevalue, &value))
-        goto exit;
-    return_value = bytearray_remove_impl(self, value);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytearray_remove_impl(PyByteArrayObject *self, int value)
-/*[clinic end generated code: output=c71c8bcf4703abfc input=47560b11fd856c24]*/
+/*[clinic end generated code: output=d659e37866709c13 input=47560b11fd856c24]*/
 {
     Py_ssize_t where, n = Py_SIZE(self);
     char *buf = PyByteArray_AS_STRING(self);
@@ -3042,39 +2609,9 @@
 If the argument is omitted or None, strip leading and trailing ASCII whitespace.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_strip__doc__,
-"strip($self, bytes=None, /)\n"
-"--\n"
-"\n"
-"Strip leading and trailing bytes contained in the argument.\n"
-"\n"
-"If the argument is omitted or None, strip leading and trailing ASCII whitespace.");
-
-#define BYTEARRAY_STRIP_METHODDEF    \
-    {"strip", (PyCFunction)bytearray_strip, METH_VARARGS, bytearray_strip__doc__},
-
-static PyObject *
-bytearray_strip_impl(PyByteArrayObject *self, PyObject *bytes);
-
-static PyObject *
-bytearray_strip(PyByteArrayObject *self, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    PyObject *bytes = Py_None;
-
-    if (!PyArg_UnpackTuple(args, "strip",
-        0, 1,
-        &bytes))
-        goto exit;
-    return_value = bytearray_strip_impl(self, bytes);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytearray_strip_impl(PyByteArrayObject *self, PyObject *bytes)
-/*[clinic end generated code: output=2e3d3358acc4c235 input=ef7bb59b09c21d62]*/
+/*[clinic end generated code: output=760412661a34ad5a input=ef7bb59b09c21d62]*/
 {
     Py_ssize_t left, right, mysize, byteslen;
     char *myptr, *bytesptr;
@@ -3113,39 +2650,9 @@
 If the argument is omitted or None, strip leading ASCII whitespace.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_lstrip__doc__,
-"lstrip($self, bytes=None, /)\n"
-"--\n"
-"\n"
-"Strip leading bytes contained in the argument.\n"
-"\n"
-"If the argument is omitted or None, strip leading ASCII whitespace.");
-
-#define BYTEARRAY_LSTRIP_METHODDEF    \
-    {"lstrip", (PyCFunction)bytearray_lstrip, METH_VARARGS, bytearray_lstrip__doc__},
-
-static PyObject *
-bytearray_lstrip_impl(PyByteArrayObject *self, PyObject *bytes);
-
-static PyObject *
-bytearray_lstrip(PyByteArrayObject *self, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    PyObject *bytes = Py_None;
-
-    if (!PyArg_UnpackTuple(args, "lstrip",
-        0, 1,
-        &bytes))
-        goto exit;
-    return_value = bytearray_lstrip_impl(self, bytes);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytearray_lstrip_impl(PyByteArrayObject *self, PyObject *bytes)
-/*[clinic end generated code: output=2599309808a9ec02 input=80843f975dd7c480]*/
+/*[clinic end generated code: output=d005c9d0ab909e66 input=80843f975dd7c480]*/
 {
     Py_ssize_t left, right, mysize, byteslen;
     char *myptr, *bytesptr;
@@ -3181,39 +2688,9 @@
 If the argument is omitted or None, strip trailing ASCII whitespace.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_rstrip__doc__,
-"rstrip($self, bytes=None, /)\n"
-"--\n"
-"\n"
-"Strip trailing bytes contained in the argument.\n"
-"\n"
-"If the argument is omitted or None, strip trailing ASCII whitespace.");
-
-#define BYTEARRAY_RSTRIP_METHODDEF    \
-    {"rstrip", (PyCFunction)bytearray_rstrip, METH_VARARGS, bytearray_rstrip__doc__},
-
-static PyObject *
-bytearray_rstrip_impl(PyByteArrayObject *self, PyObject *bytes);
-
-static PyObject *
-bytearray_rstrip(PyByteArrayObject *self, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    PyObject *bytes = Py_None;
-
-    if (!PyArg_UnpackTuple(args, "rstrip",
-        0, 1,
-        &bytes))
-        goto exit;
-    return_value = bytearray_rstrip_impl(self, bytes);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytearray_rstrip_impl(PyByteArrayObject *self, PyObject *bytes)
-/*[clinic end generated code: output=b5ca6259f4f4f2a3 input=e728b994954cfd91]*/
+/*[clinic end generated code: output=030e2fbd2f7276bd input=e728b994954cfd91]*/
 {
     Py_ssize_t right, mysize, byteslen;
     char *myptr, *bytesptr;
@@ -3252,48 +2729,9 @@
 Decode the bytearray using the codec registered for encoding.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_decode__doc__,
-"decode($self, /, encoding=\'utf-8\', errors=\'strict\')\n"
-"--\n"
-"\n"
-"Decode the bytearray using the codec registered for encoding.\n"
-"\n"
-"  encoding\n"
-"    The encoding with which to decode the bytearray.\n"
-"  errors\n"
-"    The error handling scheme to use for the handling of decoding errors.\n"
-"    The default is \'strict\' meaning that decoding errors raise a\n"
-"    UnicodeDecodeError. Other possible values are \'ignore\' and \'replace\'\n"
-"    as well as any other name registered with codecs.register_error that\n"
-"    can handle UnicodeDecodeErrors.");
-
-#define BYTEARRAY_DECODE_METHODDEF    \
-    {"decode", (PyCFunction)bytearray_decode, METH_VARARGS|METH_KEYWORDS, bytearray_decode__doc__},
-
-static PyObject *
-bytearray_decode_impl(PyByteArrayObject *self, const char *encoding, const char *errors);
-
-static PyObject *
-bytearray_decode(PyByteArrayObject *self, PyObject *args, PyObject *kwargs)
-{
-    PyObject *return_value = NULL;
-    static char *_keywords[] = {"encoding", "errors", NULL};
-    const char *encoding = NULL;
-    const char *errors = NULL;
-
-    if (!PyArg_ParseTupleAndKeywords(args, kwargs,
-        "|ss:decode", _keywords,
-        &encoding, &errors))
-        goto exit;
-    return_value = bytearray_decode_impl(self, encoding, errors);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytearray_decode_impl(PyByteArrayObject *self, const char *encoding, const char *errors)
-/*[clinic end generated code: output=38b83681f1e38a6c input=f28d8f903020257b]*/
+/*[clinic end generated code: output=7e64e2cc91573b26 input=f28d8f903020257b]*/
 {
     if (encoding == NULL)
         encoding = PyUnicode_GetDefaultEncoding();
@@ -3324,22 +2762,9 @@
 The result is returned as a new bytearray object.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_join__doc__,
-"join($self, iterable_of_bytes, /)\n"
-"--\n"
-"\n"
-"Concatenate any number of bytes/bytearray objects.\n"
-"\n"
-"The bytearray whose method is called is inserted in between each pair.\n"
-"\n"
-"The result is returned as a new bytearray object.");
-
-#define BYTEARRAY_JOIN_METHODDEF    \
-    {"join", (PyCFunction)bytearray_join, METH_O, bytearray_join__doc__},
-
 static PyObject *
 bytearray_join(PyByteArrayObject *self, PyObject *iterable_of_bytes)
-/*[clinic end generated code: output=544e7430032dfdf4 input=aba6b1f9b30fcb8e]*/
+/*[clinic end generated code: output=a8516370bf68ae08 input=aba6b1f9b30fcb8e]*/
 {
     return stringlib_bytes_join((PyObject*)self, iterable_of_bytes);
 }
@@ -3355,41 +2780,9 @@
 true.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_splitlines__doc__,
-"splitlines($self, /, keepends=False)\n"
-"--\n"
-"\n"
-"Return a list of the lines in the bytearray, breaking at line boundaries.\n"
-"\n"
-"Line breaks are not included in the resulting list unless keepends is given and\n"
-"true.");
-
-#define BYTEARRAY_SPLITLINES_METHODDEF    \
-    {"splitlines", (PyCFunction)bytearray_splitlines, METH_VARARGS|METH_KEYWORDS, bytearray_splitlines__doc__},
-
-static PyObject *
-bytearray_splitlines_impl(PyByteArrayObject *self, int keepends);
-
-static PyObject *
-bytearray_splitlines(PyByteArrayObject *self, PyObject *args, PyObject *kwargs)
-{
-    PyObject *return_value = NULL;
-    static char *_keywords[] = {"keepends", NULL};
-    int keepends = 0;
-
-    if (!PyArg_ParseTupleAndKeywords(args, kwargs,
-        "|i:splitlines", _keywords,
-        &keepends))
-        goto exit;
-    return_value = bytearray_splitlines_impl(self, keepends);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytearray_splitlines_impl(PyByteArrayObject *self, int keepends)
-/*[clinic end generated code: output=a837fd0512ad46ff input=36f0b25bc792f6c0]*/
+/*[clinic end generated code: output=4223c94b895f6ad9 input=36f0b25bc792f6c0]*/
 {
     return stringlib_splitlines(
         (PyObject*) self, PyByteArray_AS_STRING(self),
@@ -3427,40 +2820,9 @@
 Example: bytearray.fromhex('B9 01EF') -> bytearray(b'\\xb9\\x01\\xef')
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_fromhex__doc__,
-"fromhex($type, string, /)\n"
-"--\n"
-"\n"
-"Create a bytearray object from a string of hexadecimal numbers.\n"
-"\n"
-"Spaces between two numbers are accepted.\n"
-"Example: bytearray.fromhex(\'B9 01EF\') -> bytearray(b\'\\\\xb9\\\\x01\\\\xef\')");
-
-#define BYTEARRAY_FROMHEX_METHODDEF    \
-    {"fromhex", (PyCFunction)bytearray_fromhex, METH_VARARGS|METH_CLASS, bytearray_fromhex__doc__},
-
-static PyObject *
-bytearray_fromhex_impl(PyObject*cls, PyObject *string);
-
-static PyObject *
-bytearray_fromhex(PyTypeObject *cls, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    PyObject *string;
-
-    if (!PyArg_ParseTuple(args,
-        "U:fromhex",
-        &string))
-        goto exit;
-    return_value = bytearray_fromhex_impl((PyObject*)cls, string);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytearray_fromhex_impl(PyObject*cls, PyObject *string)
-/*[clinic end generated code: output=adc3c804a74e56d4 input=907bbd2d34d9367a]*/
+/*[clinic end generated code: output=df3da60129b3700c input=907bbd2d34d9367a]*/
 {
     PyObject *newbytes;
     char *buf;
@@ -3550,27 +2912,9 @@
 Return state information for pickling.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_reduce__doc__,
-"__reduce__($self, /)\n"
-"--\n"
-"\n"
-"Return state information for pickling.");
-
-#define BYTEARRAY_REDUCE_METHODDEF    \
-    {"__reduce__", (PyCFunction)bytearray_reduce, METH_NOARGS, bytearray_reduce__doc__},
-
-static PyObject *
-bytearray_reduce_impl(PyByteArrayObject *self);
-
-static PyObject *
-bytearray_reduce(PyByteArrayObject *self, PyObject *Py_UNUSED(ignored))
-{
-    return bytearray_reduce_impl(self);
-}
-
 static PyObject *
 bytearray_reduce_impl(PyByteArrayObject *self)
-/*[clinic end generated code: output=b1b56fe87bf30fb0 input=fbb07de4d102a03a]*/
+/*[clinic end generated code: output=52bf304086464cab input=fbb07de4d102a03a]*/
 {
     return _common_reduce(self, 2);
 }
@@ -3585,37 +2929,9 @@
 Return state information for pickling.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_reduce_ex__doc__,
-"__reduce_ex__($self, proto=0, /)\n"
-"--\n"
-"\n"
-"Return state information for pickling.");
-
-#define BYTEARRAY_REDUCE_EX_METHODDEF    \
-    {"__reduce_ex__", (PyCFunction)bytearray_reduce_ex, METH_VARARGS, bytearray_reduce_ex__doc__},
-
-static PyObject *
-bytearray_reduce_ex_impl(PyByteArrayObject *self, int proto);
-
-static PyObject *
-bytearray_reduce_ex(PyByteArrayObject *self, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    int proto = 0;
-
-    if (!PyArg_ParseTuple(args,
-        "|i:__reduce_ex__",
-        &proto))
-        goto exit;
-    return_value = bytearray_reduce_ex_impl(self, proto);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytearray_reduce_ex_impl(PyByteArrayObject *self, int proto)
-/*[clinic end generated code: output=bbd9afb2f5953dc1 input=0e091a42ca6dbd91]*/
+/*[clinic end generated code: output=52eac33377197520 input=0e091a42ca6dbd91]*/
 {
     return _common_reduce(self, proto);
 }
@@ -3628,27 +2944,9 @@
 Returns the size of the bytearray object in memory, in bytes.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytearray_sizeof__doc__,
-"__sizeof__($self, /)\n"
-"--\n"
-"\n"
-"Returns the size of the bytearray object in memory, in bytes.");
-
-#define BYTEARRAY_SIZEOF_METHODDEF    \
-    {"__sizeof__", (PyCFunction)bytearray_sizeof, METH_NOARGS, bytearray_sizeof__doc__},
-
-static PyObject *
-bytearray_sizeof_impl(PyByteArrayObject *self);
-
-static PyObject *
-bytearray_sizeof(PyByteArrayObject *self, PyObject *Py_UNUSED(ignored))
-{
-    return bytearray_sizeof_impl(self);
-}
-
 static PyObject *
 bytearray_sizeof_impl(PyByteArrayObject *self)
-/*[clinic end generated code: output=4a2254b0a85630c6 input=6b23d305362b462b]*/
+/*[clinic end generated code: output=738abdd17951c427 input=6b23d305362b462b]*/
 {
     Py_ssize_t res;
 
diff --git a/Objects/bytesobject.c b/Objects/bytesobject.c
index 27d6472..b6089dd 100644
--- a/Objects/bytesobject.c
+++ b/Objects/bytesobject.c
@@ -12,6 +12,8 @@
 [clinic start generated code]*/
 /*[clinic end generated code: output=da39a3ee5e6b4b0d input=1a1d9102afc1b00c]*/
 
+#include "clinic/bytesobject.c.h"
+
 #ifdef COUNT_ALLOCS
 Py_ssize_t null_strings, one_strings;
 #endif
@@ -1614,47 +1616,9 @@
 Return a list of the sections in the bytes, using sep as the delimiter.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytes_split__doc__,
-"split($self, /, sep=None, maxsplit=-1)\n"
-"--\n"
-"\n"
-"Return a list of the sections in the bytes, using sep as the delimiter.\n"
-"\n"
-"  sep\n"
-"    The delimiter according which to split the bytes.\n"
-"    None (the default value) means split on ASCII whitespace characters\n"
-"    (space, tab, return, newline, formfeed, vertical tab).\n"
-"  maxsplit\n"
-"    Maximum number of splits to do.\n"
-"    -1 (the default value) means no limit.");
-
-#define BYTES_SPLIT_METHODDEF    \
-    {"split", (PyCFunction)bytes_split, METH_VARARGS|METH_KEYWORDS, bytes_split__doc__},
-
-static PyObject *
-bytes_split_impl(PyBytesObject*self, PyObject *sep, Py_ssize_t maxsplit);
-
-static PyObject *
-bytes_split(PyBytesObject*self, PyObject *args, PyObject *kwargs)
-{
-    PyObject *return_value = NULL;
-    static char *_keywords[] = {"sep", "maxsplit", NULL};
-    PyObject *sep = Py_None;
-    Py_ssize_t maxsplit = -1;
-
-    if (!PyArg_ParseTupleAndKeywords(args, kwargs,
-        "|On:split", _keywords,
-        &sep, &maxsplit))
-        goto exit;
-    return_value = bytes_split_impl(self, sep, maxsplit);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytes_split_impl(PyBytesObject*self, PyObject *sep, Py_ssize_t maxsplit)
-/*[clinic end generated code: output=c80a47afdd505975 input=8b809b39074abbfa]*/
+/*[clinic end generated code: output=8bde44dacb36ef2e input=8b809b39074abbfa]*/
 {
     Py_ssize_t len = PyBytes_GET_SIZE(self), n;
     const char *s = PyBytes_AS_STRING(self), *sub;
@@ -1692,48 +1656,9 @@
 object and two empty bytes objects.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytes_partition__doc__,
-"partition($self, sep, /)\n"
-"--\n"
-"\n"
-"Partition the bytes into three parts using the given separator.\n"
-"\n"
-"This will search for the separator sep in the bytes. If the separator is found,\n"
-"returns a 3-tuple containing the part before the separator, the separator\n"
-"itself, and the part after it.\n"
-"\n"
-"If the separator is not found, returns a 3-tuple containing the original bytes\n"
-"object and two empty bytes objects.");
-
-#define BYTES_PARTITION_METHODDEF    \
-    {"partition", (PyCFunction)bytes_partition, METH_VARARGS, bytes_partition__doc__},
-
-static PyObject *
-bytes_partition_impl(PyBytesObject *self, Py_buffer *sep);
-
-static PyObject *
-bytes_partition(PyBytesObject *self, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    Py_buffer sep = {NULL, NULL};
-
-    if (!PyArg_ParseTuple(args,
-        "y*:partition",
-        &sep))
-        goto exit;
-    return_value = bytes_partition_impl(self, &sep);
-
-exit:
-    /* Cleanup for sep */
-    if (sep.obj)
-       PyBuffer_Release(&sep);
-
-    return return_value;
-}
-
 static PyObject *
 bytes_partition_impl(PyBytesObject *self, Py_buffer *sep)
-/*[clinic end generated code: output=3006727cfbf83aa4 input=bc855dc63ca949de]*/
+/*[clinic end generated code: output=f532b392a17ff695 input=bc855dc63ca949de]*/
 {
     return stringlib_partition(
         (PyObject*) self,
@@ -1759,48 +1684,9 @@
 objects and the original bytes object.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytes_rpartition__doc__,
-"rpartition($self, sep, /)\n"
-"--\n"
-"\n"
-"Partition the bytes into three parts using the given separator.\n"
-"\n"
-"This will search for the separator sep in the bytes, starting and the end. If\n"
-"the separator is found, returns a 3-tuple containing the part before the\n"
-"separator, the separator itself, and the part after it.\n"
-"\n"
-"If the separator is not found, returns a 3-tuple containing two empty bytes\n"
-"objects and the original bytes object.");
-
-#define BYTES_RPARTITION_METHODDEF    \
-    {"rpartition", (PyCFunction)bytes_rpartition, METH_VARARGS, bytes_rpartition__doc__},
-
-static PyObject *
-bytes_rpartition_impl(PyBytesObject *self, Py_buffer *sep);
-
-static PyObject *
-bytes_rpartition(PyBytesObject *self, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    Py_buffer sep = {NULL, NULL};
-
-    if (!PyArg_ParseTuple(args,
-        "y*:rpartition",
-        &sep))
-        goto exit;
-    return_value = bytes_rpartition_impl(self, &sep);
-
-exit:
-    /* Cleanup for sep */
-    if (sep.obj)
-       PyBuffer_Release(&sep);
-
-    return return_value;
-}
-
 static PyObject *
 bytes_rpartition_impl(PyBytesObject *self, Py_buffer *sep)
-/*[clinic end generated code: output=57b169dc47fa90e8 input=6588fff262a9170e]*/
+/*[clinic end generated code: output=191b114cbb028e50 input=6588fff262a9170e]*/
 {
     return stringlib_rpartition(
         (PyObject*) self,
@@ -1817,49 +1703,9 @@
 Splitting is done starting at the end of the bytes and working to the front.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytes_rsplit__doc__,
-"rsplit($self, /, sep=None, maxsplit=-1)\n"
-"--\n"
-"\n"
-"Return a list of the sections in the bytes, using sep as the delimiter.\n"
-"\n"
-"  sep\n"
-"    The delimiter according which to split the bytes.\n"
-"    None (the default value) means split on ASCII whitespace characters\n"
-"    (space, tab, return, newline, formfeed, vertical tab).\n"
-"  maxsplit\n"
-"    Maximum number of splits to do.\n"
-"    -1 (the default value) means no limit.\n"
-"\n"
-"Splitting is done starting at the end of the bytes and working to the front.");
-
-#define BYTES_RSPLIT_METHODDEF    \
-    {"rsplit", (PyCFunction)bytes_rsplit, METH_VARARGS|METH_KEYWORDS, bytes_rsplit__doc__},
-
-static PyObject *
-bytes_rsplit_impl(PyBytesObject*self, PyObject *sep, Py_ssize_t maxsplit);
-
-static PyObject *
-bytes_rsplit(PyBytesObject*self, PyObject *args, PyObject *kwargs)
-{
-    PyObject *return_value = NULL;
-    static char *_keywords[] = {"sep", "maxsplit", NULL};
-    PyObject *sep = Py_None;
-    Py_ssize_t maxsplit = -1;
-
-    if (!PyArg_ParseTupleAndKeywords(args, kwargs,
-        "|On:rsplit", _keywords,
-        &sep, &maxsplit))
-        goto exit;
-    return_value = bytes_rsplit_impl(self, sep, maxsplit);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytes_rsplit_impl(PyBytesObject*self, PyObject *sep, Py_ssize_t maxsplit)
-/*[clinic end generated code: output=f86feddedbd7b26d input=0f86c9f28f7d7b7b]*/
+/*[clinic end generated code: output=0b6570b977911d88 input=0f86c9f28f7d7b7b]*/
 {
     Py_ssize_t len = PyBytes_GET_SIZE(self), n;
     const char *s = PyBytes_AS_STRING(self), *sub;
@@ -1896,24 +1742,9 @@
 Example: b'.'.join([b'ab', b'pq', b'rs']) -> b'ab.pq.rs'.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytes_join__doc__,
-"join($self, iterable_of_bytes, /)\n"
-"--\n"
-"\n"
-"Concatenate any number of bytes objects.\n"
-"\n"
-"The bytes whose method is called is inserted in between each pair.\n"
-"\n"
-"The result is returned as a new bytes object.\n"
-"\n"
-"Example: b\'.\'.join([b\'ab\', b\'pq\', b\'rs\']) -> b\'ab.pq.rs\'.");
-
-#define BYTES_JOIN_METHODDEF    \
-    {"join", (PyCFunction)bytes_join, METH_O, bytes_join__doc__},
-
 static PyObject *
 bytes_join(PyBytesObject*self, PyObject *iterable_of_bytes)
-/*[clinic end generated code: output=e541a14a8da97908 input=7fe377b95bd549d2]*/
+/*[clinic end generated code: output=634aff14764ff997 input=7fe377b95bd549d2]*/
 {
     return stringlib_bytes_join((PyObject*)self, iterable_of_bytes);
 }
@@ -2170,39 +2001,9 @@
 If the argument is omitted or None, strip leading and trailing ASCII whitespace.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytes_strip__doc__,
-"strip($self, bytes=None, /)\n"
-"--\n"
-"\n"
-"Strip leading and trailing bytes contained in the argument.\n"
-"\n"
-"If the argument is omitted or None, strip leading and trailing ASCII whitespace.");
-
-#define BYTES_STRIP_METHODDEF    \
-    {"strip", (PyCFunction)bytes_strip, METH_VARARGS, bytes_strip__doc__},
-
-static PyObject *
-bytes_strip_impl(PyBytesObject *self, PyObject *bytes);
-
-static PyObject *
-bytes_strip(PyBytesObject *self, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    PyObject *bytes = Py_None;
-
-    if (!PyArg_UnpackTuple(args, "strip",
-        0, 1,
-        &bytes))
-        goto exit;
-    return_value = bytes_strip_impl(self, bytes);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytes_strip_impl(PyBytesObject *self, PyObject *bytes)
-/*[clinic end generated code: output=c8234a599ba5ec35 input=37daa5fad1395d95]*/
+/*[clinic end generated code: output=c7c228d3bd104a1b input=37daa5fad1395d95]*/
 {
     return do_argstrip(self, BOTHSTRIP, bytes);
 }
@@ -2219,39 +2020,9 @@
 If the argument is omitted or None, strip leading  ASCII whitespace.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytes_lstrip__doc__,
-"lstrip($self, bytes=None, /)\n"
-"--\n"
-"\n"
-"Strip leading bytes contained in the argument.\n"
-"\n"
-"If the argument is omitted or None, strip leading  ASCII whitespace.");
-
-#define BYTES_LSTRIP_METHODDEF    \
-    {"lstrip", (PyCFunction)bytes_lstrip, METH_VARARGS, bytes_lstrip__doc__},
-
-static PyObject *
-bytes_lstrip_impl(PyBytesObject *self, PyObject *bytes);
-
-static PyObject *
-bytes_lstrip(PyBytesObject *self, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    PyObject *bytes = Py_None;
-
-    if (!PyArg_UnpackTuple(args, "lstrip",
-        0, 1,
-        &bytes))
-        goto exit;
-    return_value = bytes_lstrip_impl(self, bytes);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytes_lstrip_impl(PyBytesObject *self, PyObject *bytes)
-/*[clinic end generated code: output=529e8511ab6f1115 input=88811b09dfbc2988]*/
+/*[clinic end generated code: output=28602e586f524e82 input=88811b09dfbc2988]*/
 {
     return do_argstrip(self, LEFTSTRIP, bytes);
 }
@@ -2268,39 +2039,9 @@
 If the argument is omitted or None, strip trailing ASCII whitespace.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytes_rstrip__doc__,
-"rstrip($self, bytes=None, /)\n"
-"--\n"
-"\n"
-"Strip trailing bytes contained in the argument.\n"
-"\n"
-"If the argument is omitted or None, strip trailing ASCII whitespace.");
-
-#define BYTES_RSTRIP_METHODDEF    \
-    {"rstrip", (PyCFunction)bytes_rstrip, METH_VARARGS, bytes_rstrip__doc__},
-
-static PyObject *
-bytes_rstrip_impl(PyBytesObject *self, PyObject *bytes);
-
-static PyObject *
-bytes_rstrip(PyBytesObject *self, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    PyObject *bytes = Py_None;
-
-    if (!PyArg_UnpackTuple(args, "rstrip",
-        0, 1,
-        &bytes))
-        goto exit;
-    return_value = bytes_rstrip_impl(self, bytes);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytes_rstrip_impl(PyBytesObject *self, PyObject *bytes)
-/*[clinic end generated code: output=e98730bd133e6593 input=8f93c9cd361f0140]*/
+/*[clinic end generated code: output=547e3815c95447da input=8f93c9cd361f0140]*/
 {
     return do_argstrip(self, RIGHTSTRIP, bytes);
 }
@@ -2371,53 +2112,9 @@
 The remaining characters are mapped through the given translation table.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytes_translate__doc__,
-"translate(table, [deletechars])\n"
-"Return a copy with each character mapped by the given translation table.\n"
-"\n"
-"  table\n"
-"    Translation table, which must be a bytes object of length 256.\n"
-"\n"
-"All characters occurring in the optional argument deletechars are removed.\n"
-"The remaining characters are mapped through the given translation table.");
-
-#define BYTES_TRANSLATE_METHODDEF    \
-    {"translate", (PyCFunction)bytes_translate, METH_VARARGS, bytes_translate__doc__},
-
-static PyObject *
-bytes_translate_impl(PyBytesObject *self, PyObject *table, int group_right_1, PyObject *deletechars);
-
-static PyObject *
-bytes_translate(PyBytesObject *self, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    PyObject *table;
-    int group_right_1 = 0;
-    PyObject *deletechars = NULL;
-
-    switch (PyTuple_GET_SIZE(args)) {
-        case 1:
-            if (!PyArg_ParseTuple(args, "O:translate", &table))
-                goto exit;
-            break;
-        case 2:
-            if (!PyArg_ParseTuple(args, "OO:translate", &table, &deletechars))
-                goto exit;
-            group_right_1 = 1;
-            break;
-        default:
-            PyErr_SetString(PyExc_TypeError, "bytes.translate requires 1 to 2 arguments");
-            goto exit;
-    }
-    return_value = bytes_translate_impl(self, table, group_right_1, deletechars);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytes_translate_impl(PyBytesObject *self, PyObject *table, int group_right_1, PyObject *deletechars)
-/*[clinic end generated code: output=f0f29a57f41df5d8 input=d8fa5519d7cc4be7]*/
+/*[clinic end generated code: output=0ddd2cef4f4918f2 input=d8fa5519d7cc4be7]*/
 {
     char *input, *output;
     Py_buffer table_view = {NULL, NULL};
@@ -2547,50 +2244,9 @@
 The bytes objects frm and to must be of the same length.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytes_maketrans__doc__,
-"maketrans(frm, to, /)\n"
-"--\n"
-"\n"
-"Return a translation table useable for the bytes or bytearray translate method.\n"
-"\n"
-"The returned table will be one where each byte in frm is mapped to the byte at\n"
-"the same position in to.\n"
-"\n"
-"The bytes objects frm and to must be of the same length.");
-
-#define BYTES_MAKETRANS_METHODDEF    \
-    {"maketrans", (PyCFunction)bytes_maketrans, METH_VARARGS|METH_STATIC, bytes_maketrans__doc__},
-
-static PyObject *
-bytes_maketrans_impl(Py_buffer *frm, Py_buffer *to);
-
-static PyObject *
-bytes_maketrans(void *null, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    Py_buffer frm = {NULL, NULL};
-    Py_buffer to = {NULL, NULL};
-
-    if (!PyArg_ParseTuple(args,
-        "y*y*:maketrans",
-        &frm, &to))
-        goto exit;
-    return_value = bytes_maketrans_impl(&frm, &to);
-
-exit:
-    /* Cleanup for frm */
-    if (frm.obj)
-       PyBuffer_Release(&frm);
-    /* Cleanup for to */
-    if (to.obj)
-       PyBuffer_Release(&to);
-
-    return return_value;
-}
-
 static PyObject *
 bytes_maketrans_impl(Py_buffer *frm, Py_buffer *to)
-/*[clinic end generated code: output=7df47390c476ac60 input=de7a8fc5632bb8f1]*/
+/*[clinic end generated code: output=a36f6399d4b77f6f input=de7a8fc5632bb8f1]*/
 {
     return _Py_bytes_maketrans(frm, to);
 }
@@ -3104,53 +2760,9 @@
 replaced.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytes_replace__doc__,
-"replace($self, old, new, count=-1, /)\n"
-"--\n"
-"\n"
-"Return a copy with all occurrences of substring old replaced by new.\n"
-"\n"
-"  count\n"
-"    Maximum number of occurrences to replace.\n"
-"    -1 (the default value) means replace all occurrences.\n"
-"\n"
-"If the optional argument count is given, only the first count occurrences are\n"
-"replaced.");
-
-#define BYTES_REPLACE_METHODDEF    \
-    {"replace", (PyCFunction)bytes_replace, METH_VARARGS, bytes_replace__doc__},
-
-static PyObject *
-bytes_replace_impl(PyBytesObject*self, Py_buffer *old, Py_buffer *new, Py_ssize_t count);
-
-static PyObject *
-bytes_replace(PyBytesObject*self, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    Py_buffer old = {NULL, NULL};
-    Py_buffer new = {NULL, NULL};
-    Py_ssize_t count = -1;
-
-    if (!PyArg_ParseTuple(args,
-        "y*y*|n:replace",
-        &old, &new, &count))
-        goto exit;
-    return_value = bytes_replace_impl(self, &old, &new, count);
-
-exit:
-    /* Cleanup for old */
-    if (old.obj)
-       PyBuffer_Release(&old);
-    /* Cleanup for new */
-    if (new.obj)
-       PyBuffer_Release(&new);
-
-    return return_value;
-}
-
 static PyObject *
 bytes_replace_impl(PyBytesObject*self, Py_buffer *old, Py_buffer *new, Py_ssize_t count)
-/*[clinic end generated code: output=f07bd9ecf29ee8d8 input=b2fbbf0bf04de8e5]*/
+/*[clinic end generated code: output=3fe052c3c60cffc2 input=b2fbbf0bf04de8e5]*/
 {
     return (PyObject *)replace((PyBytesObject *) self,
                                (const char *)old->buf, old->len,
@@ -3316,48 +2928,9 @@
 Decode the bytes using the codec registered for encoding.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytes_decode__doc__,
-"decode($self, /, encoding=\'utf-8\', errors=\'strict\')\n"
-"--\n"
-"\n"
-"Decode the bytes using the codec registered for encoding.\n"
-"\n"
-"  encoding\n"
-"    The encoding with which to decode the bytes.\n"
-"  errors\n"
-"    The error handling scheme to use for the handling of decoding errors.\n"
-"    The default is \'strict\' meaning that decoding errors raise a\n"
-"    UnicodeDecodeError. Other possible values are \'ignore\' and \'replace\'\n"
-"    as well as any other name registered with codecs.register_error that\n"
-"    can handle UnicodeDecodeErrors.");
-
-#define BYTES_DECODE_METHODDEF    \
-    {"decode", (PyCFunction)bytes_decode, METH_VARARGS|METH_KEYWORDS, bytes_decode__doc__},
-
-static PyObject *
-bytes_decode_impl(PyBytesObject*self, const char *encoding, const char *errors);
-
-static PyObject *
-bytes_decode(PyBytesObject*self, PyObject *args, PyObject *kwargs)
-{
-    PyObject *return_value = NULL;
-    static char *_keywords[] = {"encoding", "errors", NULL};
-    const char *encoding = NULL;
-    const char *errors = NULL;
-
-    if (!PyArg_ParseTupleAndKeywords(args, kwargs,
-        "|ss:decode", _keywords,
-        &encoding, &errors))
-        goto exit;
-    return_value = bytes_decode_impl(self, encoding, errors);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytes_decode_impl(PyBytesObject*self, const char *encoding, const char *errors)
-/*[clinic end generated code: output=61a80290bbfce696 input=958174769d2a40ca]*/
+/*[clinic end generated code: output=8038751c823b9038 input=958174769d2a40ca]*/
 {
     return PyUnicode_FromEncodedObject((PyObject*)self, encoding, errors);
 }
@@ -3374,41 +2947,9 @@
 true.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytes_splitlines__doc__,
-"splitlines($self, /, keepends=False)\n"
-"--\n"
-"\n"
-"Return a list of the lines in the bytes, breaking at line boundaries.\n"
-"\n"
-"Line breaks are not included in the resulting list unless keepends is given and\n"
-"true.");
-
-#define BYTES_SPLITLINES_METHODDEF    \
-    {"splitlines", (PyCFunction)bytes_splitlines, METH_VARARGS|METH_KEYWORDS, bytes_splitlines__doc__},
-
-static PyObject *
-bytes_splitlines_impl(PyBytesObject*self, int keepends);
-
-static PyObject *
-bytes_splitlines(PyBytesObject*self, PyObject *args, PyObject *kwargs)
-{
-    PyObject *return_value = NULL;
-    static char *_keywords[] = {"keepends", NULL};
-    int keepends = 0;
-
-    if (!PyArg_ParseTupleAndKeywords(args, kwargs,
-        "|i:splitlines", _keywords,
-        &keepends))
-        goto exit;
-    return_value = bytes_splitlines_impl(self, keepends);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytes_splitlines_impl(PyBytesObject*self, int keepends)
-/*[clinic end generated code: output=79da057d05d126de input=ddb93e3351080c8c]*/
+/*[clinic end generated code: output=995c3598f7833cad input=ddb93e3351080c8c]*/
 {
     return stringlib_splitlines(
         (PyObject*) self, PyBytes_AS_STRING(self),
@@ -3445,40 +2986,9 @@
 Example: bytes.fromhex('B9 01EF') -> b'\\xb9\\x01\\xef'.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(bytes_fromhex__doc__,
-"fromhex($type, string, /)\n"
-"--\n"
-"\n"
-"Create a bytes object from a string of hexadecimal numbers.\n"
-"\n"
-"Spaces between two numbers are accepted.\n"
-"Example: bytes.fromhex(\'B9 01EF\') -> b\'\\\\xb9\\\\x01\\\\xef\'.");
-
-#define BYTES_FROMHEX_METHODDEF    \
-    {"fromhex", (PyCFunction)bytes_fromhex, METH_VARARGS|METH_CLASS, bytes_fromhex__doc__},
-
-static PyObject *
-bytes_fromhex_impl(PyTypeObject *type, PyObject *string);
-
-static PyObject *
-bytes_fromhex(PyTypeObject *type, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    PyObject *string;
-
-    if (!PyArg_ParseTuple(args,
-        "U:fromhex",
-        &string))
-        goto exit;
-    return_value = bytes_fromhex_impl(type, string);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 bytes_fromhex_impl(PyTypeObject *type, PyObject *string)
-/*[clinic end generated code: output=09e6cbef56cbbb65 input=bf4d1c361670acd3]*/
+/*[clinic end generated code: output=0973acc63661bb2e input=bf4d1c361670acd3]*/
 {
     PyObject *newstring;
     char *buf;
diff --git a/Objects/clinic/bytearrayobject.c.h b/Objects/clinic/bytearrayobject.c.h
new file mode 100644
index 0000000..f0c0af1
--- /dev/null
+++ b/Objects/clinic/bytearrayobject.c.h
@@ -0,0 +1,708 @@
+/*[clinic input]
+preserve
+[clinic start generated code]*/
+
+PyDoc_STRVAR(bytearray_clear__doc__,
+"clear($self, /)\n"
+"--\n"
+"\n"
+"Remove all items from the bytearray.");
+
+#define BYTEARRAY_CLEAR_METHODDEF    \
+    {"clear", (PyCFunction)bytearray_clear, METH_NOARGS, bytearray_clear__doc__},
+
+static PyObject *
+bytearray_clear_impl(PyByteArrayObject *self);
+
+static PyObject *
+bytearray_clear(PyByteArrayObject *self, PyObject *Py_UNUSED(ignored))
+{
+    return bytearray_clear_impl(self);
+}
+
+PyDoc_STRVAR(bytearray_copy__doc__,
+"copy($self, /)\n"
+"--\n"
+"\n"
+"Return a copy of B.");
+
+#define BYTEARRAY_COPY_METHODDEF    \
+    {"copy", (PyCFunction)bytearray_copy, METH_NOARGS, bytearray_copy__doc__},
+
+static PyObject *
+bytearray_copy_impl(PyByteArrayObject *self);
+
+static PyObject *
+bytearray_copy(PyByteArrayObject *self, PyObject *Py_UNUSED(ignored))
+{
+    return bytearray_copy_impl(self);
+}
+
+PyDoc_STRVAR(bytearray_translate__doc__,
+"translate(table, [deletechars])\n"
+"Return a copy with each character mapped by the given translation table.\n"
+"\n"
+"  table\n"
+"    Translation table, which must be a bytes object of length 256.\n"
+"\n"
+"All characters occurring in the optional argument deletechars are removed.\n"
+"The remaining characters are mapped through the given translation table.");
+
+#define BYTEARRAY_TRANSLATE_METHODDEF    \
+    {"translate", (PyCFunction)bytearray_translate, METH_VARARGS, bytearray_translate__doc__},
+
+static PyObject *
+bytearray_translate_impl(PyByteArrayObject *self, PyObject *table, int group_right_1, PyObject *deletechars);
+
+static PyObject *
+bytearray_translate(PyByteArrayObject *self, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    PyObject *table;
+    int group_right_1 = 0;
+    PyObject *deletechars = NULL;
+
+    switch (PyTuple_GET_SIZE(args)) {
+        case 1:
+            if (!PyArg_ParseTuple(args, "O:translate", &table))
+                goto exit;
+            break;
+        case 2:
+            if (!PyArg_ParseTuple(args, "OO:translate", &table, &deletechars))
+                goto exit;
+            group_right_1 = 1;
+            break;
+        default:
+            PyErr_SetString(PyExc_TypeError, "bytearray.translate requires 1 to 2 arguments");
+            goto exit;
+    }
+    return_value = bytearray_translate_impl(self, table, group_right_1, deletechars);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytearray_maketrans__doc__,
+"maketrans(frm, to, /)\n"
+"--\n"
+"\n"
+"Return a translation table useable for the bytes or bytearray translate method.\n"
+"\n"
+"The returned table will be one where each byte in frm is mapped to the byte at\n"
+"the same position in to.\n"
+"\n"
+"The bytes objects frm and to must be of the same length.");
+
+#define BYTEARRAY_MAKETRANS_METHODDEF    \
+    {"maketrans", (PyCFunction)bytearray_maketrans, METH_VARARGS|METH_STATIC, bytearray_maketrans__doc__},
+
+static PyObject *
+bytearray_maketrans_impl(Py_buffer *frm, Py_buffer *to);
+
+static PyObject *
+bytearray_maketrans(void *null, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    Py_buffer frm = {NULL, NULL};
+    Py_buffer to = {NULL, NULL};
+
+    if (!PyArg_ParseTuple(args,
+        "y*y*:maketrans",
+        &frm, &to))
+        goto exit;
+    return_value = bytearray_maketrans_impl(&frm, &to);
+
+exit:
+    /* Cleanup for frm */
+    if (frm.obj)
+       PyBuffer_Release(&frm);
+    /* Cleanup for to */
+    if (to.obj)
+       PyBuffer_Release(&to);
+
+    return return_value;
+}
+
+PyDoc_STRVAR(bytearray_replace__doc__,
+"replace($self, old, new, count=-1, /)\n"
+"--\n"
+"\n"
+"Return a copy with all occurrences of substring old replaced by new.\n"
+"\n"
+"  count\n"
+"    Maximum number of occurrences to replace.\n"
+"    -1 (the default value) means replace all occurrences.\n"
+"\n"
+"If the optional argument count is given, only the first count occurrences are\n"
+"replaced.");
+
+#define BYTEARRAY_REPLACE_METHODDEF    \
+    {"replace", (PyCFunction)bytearray_replace, METH_VARARGS, bytearray_replace__doc__},
+
+static PyObject *
+bytearray_replace_impl(PyByteArrayObject *self, Py_buffer *old, Py_buffer *new, Py_ssize_t count);
+
+static PyObject *
+bytearray_replace(PyByteArrayObject *self, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    Py_buffer old = {NULL, NULL};
+    Py_buffer new = {NULL, NULL};
+    Py_ssize_t count = -1;
+
+    if (!PyArg_ParseTuple(args,
+        "y*y*|n:replace",
+        &old, &new, &count))
+        goto exit;
+    return_value = bytearray_replace_impl(self, &old, &new, count);
+
+exit:
+    /* Cleanup for old */
+    if (old.obj)
+       PyBuffer_Release(&old);
+    /* Cleanup for new */
+    if (new.obj)
+       PyBuffer_Release(&new);
+
+    return return_value;
+}
+
+PyDoc_STRVAR(bytearray_split__doc__,
+"split($self, /, sep=None, maxsplit=-1)\n"
+"--\n"
+"\n"
+"Return a list of the sections in the bytearray, using sep as the delimiter.\n"
+"\n"
+"  sep\n"
+"    The delimiter according which to split the bytearray.\n"
+"    None (the default value) means split on ASCII whitespace characters\n"
+"    (space, tab, return, newline, formfeed, vertical tab).\n"
+"  maxsplit\n"
+"    Maximum number of splits to do.\n"
+"    -1 (the default value) means no limit.");
+
+#define BYTEARRAY_SPLIT_METHODDEF    \
+    {"split", (PyCFunction)bytearray_split, METH_VARARGS|METH_KEYWORDS, bytearray_split__doc__},
+
+static PyObject *
+bytearray_split_impl(PyByteArrayObject *self, PyObject *sep, Py_ssize_t maxsplit);
+
+static PyObject *
+bytearray_split(PyByteArrayObject *self, PyObject *args, PyObject *kwargs)
+{
+    PyObject *return_value = NULL;
+    static char *_keywords[] = {"sep", "maxsplit", NULL};
+    PyObject *sep = Py_None;
+    Py_ssize_t maxsplit = -1;
+
+    if (!PyArg_ParseTupleAndKeywords(args, kwargs,
+        "|On:split", _keywords,
+        &sep, &maxsplit))
+        goto exit;
+    return_value = bytearray_split_impl(self, sep, maxsplit);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytearray_partition__doc__,
+"partition($self, sep, /)\n"
+"--\n"
+"\n"
+"Partition the bytearray into three parts using the given separator.\n"
+"\n"
+"This will search for the separator sep in the bytearray. If the separator is\n"
+"found, returns a 3-tuple containing the part before the separator, the\n"
+"separator itself, and the part after it.\n"
+"\n"
+"If the separator is not found, returns a 3-tuple containing the original\n"
+"bytearray object and two empty bytearray objects.");
+
+#define BYTEARRAY_PARTITION_METHODDEF    \
+    {"partition", (PyCFunction)bytearray_partition, METH_O, bytearray_partition__doc__},
+
+PyDoc_STRVAR(bytearray_rpartition__doc__,
+"rpartition($self, sep, /)\n"
+"--\n"
+"\n"
+"Partition the bytes into three parts using the given separator.\n"
+"\n"
+"This will search for the separator sep in the bytearray, starting and the end.\n"
+"If the separator is found, returns a 3-tuple containing the part before the\n"
+"separator, the separator itself, and the part after it.\n"
+"\n"
+"If the separator is not found, returns a 3-tuple containing two empty bytearray\n"
+"objects and the original bytearray object.");
+
+#define BYTEARRAY_RPARTITION_METHODDEF    \
+    {"rpartition", (PyCFunction)bytearray_rpartition, METH_O, bytearray_rpartition__doc__},
+
+PyDoc_STRVAR(bytearray_rsplit__doc__,
+"rsplit($self, /, sep=None, maxsplit=-1)\n"
+"--\n"
+"\n"
+"Return a list of the sections in the bytearray, using sep as the delimiter.\n"
+"\n"
+"  sep\n"
+"    The delimiter according which to split the bytearray.\n"
+"    None (the default value) means split on ASCII whitespace characters\n"
+"    (space, tab, return, newline, formfeed, vertical tab).\n"
+"  maxsplit\n"
+"    Maximum number of splits to do.\n"
+"    -1 (the default value) means no limit.\n"
+"\n"
+"Splitting is done starting at the end of the bytearray and working to the front.");
+
+#define BYTEARRAY_RSPLIT_METHODDEF    \
+    {"rsplit", (PyCFunction)bytearray_rsplit, METH_VARARGS|METH_KEYWORDS, bytearray_rsplit__doc__},
+
+static PyObject *
+bytearray_rsplit_impl(PyByteArrayObject *self, PyObject *sep, Py_ssize_t maxsplit);
+
+static PyObject *
+bytearray_rsplit(PyByteArrayObject *self, PyObject *args, PyObject *kwargs)
+{
+    PyObject *return_value = NULL;
+    static char *_keywords[] = {"sep", "maxsplit", NULL};
+    PyObject *sep = Py_None;
+    Py_ssize_t maxsplit = -1;
+
+    if (!PyArg_ParseTupleAndKeywords(args, kwargs,
+        "|On:rsplit", _keywords,
+        &sep, &maxsplit))
+        goto exit;
+    return_value = bytearray_rsplit_impl(self, sep, maxsplit);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytearray_reverse__doc__,
+"reverse($self, /)\n"
+"--\n"
+"\n"
+"Reverse the order of the values in B in place.");
+
+#define BYTEARRAY_REVERSE_METHODDEF    \
+    {"reverse", (PyCFunction)bytearray_reverse, METH_NOARGS, bytearray_reverse__doc__},
+
+static PyObject *
+bytearray_reverse_impl(PyByteArrayObject *self);
+
+static PyObject *
+bytearray_reverse(PyByteArrayObject *self, PyObject *Py_UNUSED(ignored))
+{
+    return bytearray_reverse_impl(self);
+}
+
+PyDoc_STRVAR(bytearray_insert__doc__,
+"insert($self, index, item, /)\n"
+"--\n"
+"\n"
+"Insert a single item into the bytearray before the given index.\n"
+"\n"
+"  index\n"
+"    The index where the value is to be inserted.\n"
+"  item\n"
+"    The item to be inserted.");
+
+#define BYTEARRAY_INSERT_METHODDEF    \
+    {"insert", (PyCFunction)bytearray_insert, METH_VARARGS, bytearray_insert__doc__},
+
+static PyObject *
+bytearray_insert_impl(PyByteArrayObject *self, Py_ssize_t index, int item);
+
+static PyObject *
+bytearray_insert(PyByteArrayObject *self, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    Py_ssize_t index;
+    int item;
+
+    if (!PyArg_ParseTuple(args,
+        "nO&:insert",
+        &index, _getbytevalue, &item))
+        goto exit;
+    return_value = bytearray_insert_impl(self, index, item);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytearray_append__doc__,
+"append($self, item, /)\n"
+"--\n"
+"\n"
+"Append a single item to the end of the bytearray.\n"
+"\n"
+"  item\n"
+"    The item to be appended.");
+
+#define BYTEARRAY_APPEND_METHODDEF    \
+    {"append", (PyCFunction)bytearray_append, METH_VARARGS, bytearray_append__doc__},
+
+static PyObject *
+bytearray_append_impl(PyByteArrayObject *self, int item);
+
+static PyObject *
+bytearray_append(PyByteArrayObject *self, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    int item;
+
+    if (!PyArg_ParseTuple(args,
+        "O&:append",
+        _getbytevalue, &item))
+        goto exit;
+    return_value = bytearray_append_impl(self, item);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytearray_extend__doc__,
+"extend($self, iterable_of_ints, /)\n"
+"--\n"
+"\n"
+"Append all the items from the iterator or sequence to the end of the bytearray.\n"
+"\n"
+"  iterable_of_ints\n"
+"    The iterable of items to append.");
+
+#define BYTEARRAY_EXTEND_METHODDEF    \
+    {"extend", (PyCFunction)bytearray_extend, METH_O, bytearray_extend__doc__},
+
+PyDoc_STRVAR(bytearray_pop__doc__,
+"pop($self, index=-1, /)\n"
+"--\n"
+"\n"
+"Remove and return a single item from B.\n"
+"\n"
+"  index\n"
+"    The index from where to remove the item.\n"
+"    -1 (the default value) means remove the last item.\n"
+"\n"
+"If no index argument is given, will pop the last item.");
+
+#define BYTEARRAY_POP_METHODDEF    \
+    {"pop", (PyCFunction)bytearray_pop, METH_VARARGS, bytearray_pop__doc__},
+
+static PyObject *
+bytearray_pop_impl(PyByteArrayObject *self, Py_ssize_t index);
+
+static PyObject *
+bytearray_pop(PyByteArrayObject *self, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    Py_ssize_t index = -1;
+
+    if (!PyArg_ParseTuple(args,
+        "|n:pop",
+        &index))
+        goto exit;
+    return_value = bytearray_pop_impl(self, index);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytearray_remove__doc__,
+"remove($self, value, /)\n"
+"--\n"
+"\n"
+"Remove the first occurrence of a value in the bytearray.\n"
+"\n"
+"  value\n"
+"    The value to remove.");
+
+#define BYTEARRAY_REMOVE_METHODDEF    \
+    {"remove", (PyCFunction)bytearray_remove, METH_VARARGS, bytearray_remove__doc__},
+
+static PyObject *
+bytearray_remove_impl(PyByteArrayObject *self, int value);
+
+static PyObject *
+bytearray_remove(PyByteArrayObject *self, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    int value;
+
+    if (!PyArg_ParseTuple(args,
+        "O&:remove",
+        _getbytevalue, &value))
+        goto exit;
+    return_value = bytearray_remove_impl(self, value);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytearray_strip__doc__,
+"strip($self, bytes=None, /)\n"
+"--\n"
+"\n"
+"Strip leading and trailing bytes contained in the argument.\n"
+"\n"
+"If the argument is omitted or None, strip leading and trailing ASCII whitespace.");
+
+#define BYTEARRAY_STRIP_METHODDEF    \
+    {"strip", (PyCFunction)bytearray_strip, METH_VARARGS, bytearray_strip__doc__},
+
+static PyObject *
+bytearray_strip_impl(PyByteArrayObject *self, PyObject *bytes);
+
+static PyObject *
+bytearray_strip(PyByteArrayObject *self, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    PyObject *bytes = Py_None;
+
+    if (!PyArg_UnpackTuple(args, "strip",
+        0, 1,
+        &bytes))
+        goto exit;
+    return_value = bytearray_strip_impl(self, bytes);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytearray_lstrip__doc__,
+"lstrip($self, bytes=None, /)\n"
+"--\n"
+"\n"
+"Strip leading bytes contained in the argument.\n"
+"\n"
+"If the argument is omitted or None, strip leading ASCII whitespace.");
+
+#define BYTEARRAY_LSTRIP_METHODDEF    \
+    {"lstrip", (PyCFunction)bytearray_lstrip, METH_VARARGS, bytearray_lstrip__doc__},
+
+static PyObject *
+bytearray_lstrip_impl(PyByteArrayObject *self, PyObject *bytes);
+
+static PyObject *
+bytearray_lstrip(PyByteArrayObject *self, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    PyObject *bytes = Py_None;
+
+    if (!PyArg_UnpackTuple(args, "lstrip",
+        0, 1,
+        &bytes))
+        goto exit;
+    return_value = bytearray_lstrip_impl(self, bytes);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytearray_rstrip__doc__,
+"rstrip($self, bytes=None, /)\n"
+"--\n"
+"\n"
+"Strip trailing bytes contained in the argument.\n"
+"\n"
+"If the argument is omitted or None, strip trailing ASCII whitespace.");
+
+#define BYTEARRAY_RSTRIP_METHODDEF    \
+    {"rstrip", (PyCFunction)bytearray_rstrip, METH_VARARGS, bytearray_rstrip__doc__},
+
+static PyObject *
+bytearray_rstrip_impl(PyByteArrayObject *self, PyObject *bytes);
+
+static PyObject *
+bytearray_rstrip(PyByteArrayObject *self, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    PyObject *bytes = Py_None;
+
+    if (!PyArg_UnpackTuple(args, "rstrip",
+        0, 1,
+        &bytes))
+        goto exit;
+    return_value = bytearray_rstrip_impl(self, bytes);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytearray_decode__doc__,
+"decode($self, /, encoding=\'utf-8\', errors=\'strict\')\n"
+"--\n"
+"\n"
+"Decode the bytearray using the codec registered for encoding.\n"
+"\n"
+"  encoding\n"
+"    The encoding with which to decode the bytearray.\n"
+"  errors\n"
+"    The error handling scheme to use for the handling of decoding errors.\n"
+"    The default is \'strict\' meaning that decoding errors raise a\n"
+"    UnicodeDecodeError. Other possible values are \'ignore\' and \'replace\'\n"
+"    as well as any other name registered with codecs.register_error that\n"
+"    can handle UnicodeDecodeErrors.");
+
+#define BYTEARRAY_DECODE_METHODDEF    \
+    {"decode", (PyCFunction)bytearray_decode, METH_VARARGS|METH_KEYWORDS, bytearray_decode__doc__},
+
+static PyObject *
+bytearray_decode_impl(PyByteArrayObject *self, const char *encoding, const char *errors);
+
+static PyObject *
+bytearray_decode(PyByteArrayObject *self, PyObject *args, PyObject *kwargs)
+{
+    PyObject *return_value = NULL;
+    static char *_keywords[] = {"encoding", "errors", NULL};
+    const char *encoding = NULL;
+    const char *errors = NULL;
+
+    if (!PyArg_ParseTupleAndKeywords(args, kwargs,
+        "|ss:decode", _keywords,
+        &encoding, &errors))
+        goto exit;
+    return_value = bytearray_decode_impl(self, encoding, errors);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytearray_join__doc__,
+"join($self, iterable_of_bytes, /)\n"
+"--\n"
+"\n"
+"Concatenate any number of bytes/bytearray objects.\n"
+"\n"
+"The bytearray whose method is called is inserted in between each pair.\n"
+"\n"
+"The result is returned as a new bytearray object.");
+
+#define BYTEARRAY_JOIN_METHODDEF    \
+    {"join", (PyCFunction)bytearray_join, METH_O, bytearray_join__doc__},
+
+PyDoc_STRVAR(bytearray_splitlines__doc__,
+"splitlines($self, /, keepends=False)\n"
+"--\n"
+"\n"
+"Return a list of the lines in the bytearray, breaking at line boundaries.\n"
+"\n"
+"Line breaks are not included in the resulting list unless keepends is given and\n"
+"true.");
+
+#define BYTEARRAY_SPLITLINES_METHODDEF    \
+    {"splitlines", (PyCFunction)bytearray_splitlines, METH_VARARGS|METH_KEYWORDS, bytearray_splitlines__doc__},
+
+static PyObject *
+bytearray_splitlines_impl(PyByteArrayObject *self, int keepends);
+
+static PyObject *
+bytearray_splitlines(PyByteArrayObject *self, PyObject *args, PyObject *kwargs)
+{
+    PyObject *return_value = NULL;
+    static char *_keywords[] = {"keepends", NULL};
+    int keepends = 0;
+
+    if (!PyArg_ParseTupleAndKeywords(args, kwargs,
+        "|i:splitlines", _keywords,
+        &keepends))
+        goto exit;
+    return_value = bytearray_splitlines_impl(self, keepends);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytearray_fromhex__doc__,
+"fromhex($type, string, /)\n"
+"--\n"
+"\n"
+"Create a bytearray object from a string of hexadecimal numbers.\n"
+"\n"
+"Spaces between two numbers are accepted.\n"
+"Example: bytearray.fromhex(\'B9 01EF\') -> bytearray(b\'\\\\xb9\\\\x01\\\\xef\')");
+
+#define BYTEARRAY_FROMHEX_METHODDEF    \
+    {"fromhex", (PyCFunction)bytearray_fromhex, METH_VARARGS|METH_CLASS, bytearray_fromhex__doc__},
+
+static PyObject *
+bytearray_fromhex_impl(PyObject*cls, PyObject *string);
+
+static PyObject *
+bytearray_fromhex(PyTypeObject *cls, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    PyObject *string;
+
+    if (!PyArg_ParseTuple(args,
+        "U:fromhex",
+        &string))
+        goto exit;
+    return_value = bytearray_fromhex_impl((PyObject*)cls, string);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytearray_reduce__doc__,
+"__reduce__($self, /)\n"
+"--\n"
+"\n"
+"Return state information for pickling.");
+
+#define BYTEARRAY_REDUCE_METHODDEF    \
+    {"__reduce__", (PyCFunction)bytearray_reduce, METH_NOARGS, bytearray_reduce__doc__},
+
+static PyObject *
+bytearray_reduce_impl(PyByteArrayObject *self);
+
+static PyObject *
+bytearray_reduce(PyByteArrayObject *self, PyObject *Py_UNUSED(ignored))
+{
+    return bytearray_reduce_impl(self);
+}
+
+PyDoc_STRVAR(bytearray_reduce_ex__doc__,
+"__reduce_ex__($self, proto=0, /)\n"
+"--\n"
+"\n"
+"Return state information for pickling.");
+
+#define BYTEARRAY_REDUCE_EX_METHODDEF    \
+    {"__reduce_ex__", (PyCFunction)bytearray_reduce_ex, METH_VARARGS, bytearray_reduce_ex__doc__},
+
+static PyObject *
+bytearray_reduce_ex_impl(PyByteArrayObject *self, int proto);
+
+static PyObject *
+bytearray_reduce_ex(PyByteArrayObject *self, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    int proto = 0;
+
+    if (!PyArg_ParseTuple(args,
+        "|i:__reduce_ex__",
+        &proto))
+        goto exit;
+    return_value = bytearray_reduce_ex_impl(self, proto);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytearray_sizeof__doc__,
+"__sizeof__($self, /)\n"
+"--\n"
+"\n"
+"Returns the size of the bytearray object in memory, in bytes.");
+
+#define BYTEARRAY_SIZEOF_METHODDEF    \
+    {"__sizeof__", (PyCFunction)bytearray_sizeof, METH_NOARGS, bytearray_sizeof__doc__},
+
+static PyObject *
+bytearray_sizeof_impl(PyByteArrayObject *self);
+
+static PyObject *
+bytearray_sizeof(PyByteArrayObject *self, PyObject *Py_UNUSED(ignored))
+{
+    return bytearray_sizeof_impl(self);
+}
+/*[clinic end generated code: output=70ea384faeca8d16 input=a9049054013a1b77]*/
diff --git a/Objects/clinic/bytesobject.c.h b/Objects/clinic/bytesobject.c.h
new file mode 100644
index 0000000..642a08c
--- /dev/null
+++ b/Objects/clinic/bytesobject.c.h
@@ -0,0 +1,496 @@
+/*[clinic input]
+preserve
+[clinic start generated code]*/
+
+PyDoc_STRVAR(bytes_split__doc__,
+"split($self, /, sep=None, maxsplit=-1)\n"
+"--\n"
+"\n"
+"Return a list of the sections in the bytes, using sep as the delimiter.\n"
+"\n"
+"  sep\n"
+"    The delimiter according which to split the bytes.\n"
+"    None (the default value) means split on ASCII whitespace characters\n"
+"    (space, tab, return, newline, formfeed, vertical tab).\n"
+"  maxsplit\n"
+"    Maximum number of splits to do.\n"
+"    -1 (the default value) means no limit.");
+
+#define BYTES_SPLIT_METHODDEF    \
+    {"split", (PyCFunction)bytes_split, METH_VARARGS|METH_KEYWORDS, bytes_split__doc__},
+
+static PyObject *
+bytes_split_impl(PyBytesObject*self, PyObject *sep, Py_ssize_t maxsplit);
+
+static PyObject *
+bytes_split(PyBytesObject*self, PyObject *args, PyObject *kwargs)
+{
+    PyObject *return_value = NULL;
+    static char *_keywords[] = {"sep", "maxsplit", NULL};
+    PyObject *sep = Py_None;
+    Py_ssize_t maxsplit = -1;
+
+    if (!PyArg_ParseTupleAndKeywords(args, kwargs,
+        "|On:split", _keywords,
+        &sep, &maxsplit))
+        goto exit;
+    return_value = bytes_split_impl(self, sep, maxsplit);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytes_partition__doc__,
+"partition($self, sep, /)\n"
+"--\n"
+"\n"
+"Partition the bytes into three parts using the given separator.\n"
+"\n"
+"This will search for the separator sep in the bytes. If the separator is found,\n"
+"returns a 3-tuple containing the part before the separator, the separator\n"
+"itself, and the part after it.\n"
+"\n"
+"If the separator is not found, returns a 3-tuple containing the original bytes\n"
+"object and two empty bytes objects.");
+
+#define BYTES_PARTITION_METHODDEF    \
+    {"partition", (PyCFunction)bytes_partition, METH_VARARGS, bytes_partition__doc__},
+
+static PyObject *
+bytes_partition_impl(PyBytesObject *self, Py_buffer *sep);
+
+static PyObject *
+bytes_partition(PyBytesObject *self, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    Py_buffer sep = {NULL, NULL};
+
+    if (!PyArg_ParseTuple(args,
+        "y*:partition",
+        &sep))
+        goto exit;
+    return_value = bytes_partition_impl(self, &sep);
+
+exit:
+    /* Cleanup for sep */
+    if (sep.obj)
+       PyBuffer_Release(&sep);
+
+    return return_value;
+}
+
+PyDoc_STRVAR(bytes_rpartition__doc__,
+"rpartition($self, sep, /)\n"
+"--\n"
+"\n"
+"Partition the bytes into three parts using the given separator.\n"
+"\n"
+"This will search for the separator sep in the bytes, starting and the end. If\n"
+"the separator is found, returns a 3-tuple containing the part before the\n"
+"separator, the separator itself, and the part after it.\n"
+"\n"
+"If the separator is not found, returns a 3-tuple containing two empty bytes\n"
+"objects and the original bytes object.");
+
+#define BYTES_RPARTITION_METHODDEF    \
+    {"rpartition", (PyCFunction)bytes_rpartition, METH_VARARGS, bytes_rpartition__doc__},
+
+static PyObject *
+bytes_rpartition_impl(PyBytesObject *self, Py_buffer *sep);
+
+static PyObject *
+bytes_rpartition(PyBytesObject *self, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    Py_buffer sep = {NULL, NULL};
+
+    if (!PyArg_ParseTuple(args,
+        "y*:rpartition",
+        &sep))
+        goto exit;
+    return_value = bytes_rpartition_impl(self, &sep);
+
+exit:
+    /* Cleanup for sep */
+    if (sep.obj)
+       PyBuffer_Release(&sep);
+
+    return return_value;
+}
+
+PyDoc_STRVAR(bytes_rsplit__doc__,
+"rsplit($self, /, sep=None, maxsplit=-1)\n"
+"--\n"
+"\n"
+"Return a list of the sections in the bytes, using sep as the delimiter.\n"
+"\n"
+"  sep\n"
+"    The delimiter according which to split the bytes.\n"
+"    None (the default value) means split on ASCII whitespace characters\n"
+"    (space, tab, return, newline, formfeed, vertical tab).\n"
+"  maxsplit\n"
+"    Maximum number of splits to do.\n"
+"    -1 (the default value) means no limit.\n"
+"\n"
+"Splitting is done starting at the end of the bytes and working to the front.");
+
+#define BYTES_RSPLIT_METHODDEF    \
+    {"rsplit", (PyCFunction)bytes_rsplit, METH_VARARGS|METH_KEYWORDS, bytes_rsplit__doc__},
+
+static PyObject *
+bytes_rsplit_impl(PyBytesObject*self, PyObject *sep, Py_ssize_t maxsplit);
+
+static PyObject *
+bytes_rsplit(PyBytesObject*self, PyObject *args, PyObject *kwargs)
+{
+    PyObject *return_value = NULL;
+    static char *_keywords[] = {"sep", "maxsplit", NULL};
+    PyObject *sep = Py_None;
+    Py_ssize_t maxsplit = -1;
+
+    if (!PyArg_ParseTupleAndKeywords(args, kwargs,
+        "|On:rsplit", _keywords,
+        &sep, &maxsplit))
+        goto exit;
+    return_value = bytes_rsplit_impl(self, sep, maxsplit);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytes_join__doc__,
+"join($self, iterable_of_bytes, /)\n"
+"--\n"
+"\n"
+"Concatenate any number of bytes objects.\n"
+"\n"
+"The bytes whose method is called is inserted in between each pair.\n"
+"\n"
+"The result is returned as a new bytes object.\n"
+"\n"
+"Example: b\'.\'.join([b\'ab\', b\'pq\', b\'rs\']) -> b\'ab.pq.rs\'.");
+
+#define BYTES_JOIN_METHODDEF    \
+    {"join", (PyCFunction)bytes_join, METH_O, bytes_join__doc__},
+
+PyDoc_STRVAR(bytes_strip__doc__,
+"strip($self, bytes=None, /)\n"
+"--\n"
+"\n"
+"Strip leading and trailing bytes contained in the argument.\n"
+"\n"
+"If the argument is omitted or None, strip leading and trailing ASCII whitespace.");
+
+#define BYTES_STRIP_METHODDEF    \
+    {"strip", (PyCFunction)bytes_strip, METH_VARARGS, bytes_strip__doc__},
+
+static PyObject *
+bytes_strip_impl(PyBytesObject *self, PyObject *bytes);
+
+static PyObject *
+bytes_strip(PyBytesObject *self, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    PyObject *bytes = Py_None;
+
+    if (!PyArg_UnpackTuple(args, "strip",
+        0, 1,
+        &bytes))
+        goto exit;
+    return_value = bytes_strip_impl(self, bytes);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytes_lstrip__doc__,
+"lstrip($self, bytes=None, /)\n"
+"--\n"
+"\n"
+"Strip leading bytes contained in the argument.\n"
+"\n"
+"If the argument is omitted or None, strip leading  ASCII whitespace.");
+
+#define BYTES_LSTRIP_METHODDEF    \
+    {"lstrip", (PyCFunction)bytes_lstrip, METH_VARARGS, bytes_lstrip__doc__},
+
+static PyObject *
+bytes_lstrip_impl(PyBytesObject *self, PyObject *bytes);
+
+static PyObject *
+bytes_lstrip(PyBytesObject *self, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    PyObject *bytes = Py_None;
+
+    if (!PyArg_UnpackTuple(args, "lstrip",
+        0, 1,
+        &bytes))
+        goto exit;
+    return_value = bytes_lstrip_impl(self, bytes);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytes_rstrip__doc__,
+"rstrip($self, bytes=None, /)\n"
+"--\n"
+"\n"
+"Strip trailing bytes contained in the argument.\n"
+"\n"
+"If the argument is omitted or None, strip trailing ASCII whitespace.");
+
+#define BYTES_RSTRIP_METHODDEF    \
+    {"rstrip", (PyCFunction)bytes_rstrip, METH_VARARGS, bytes_rstrip__doc__},
+
+static PyObject *
+bytes_rstrip_impl(PyBytesObject *self, PyObject *bytes);
+
+static PyObject *
+bytes_rstrip(PyBytesObject *self, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    PyObject *bytes = Py_None;
+
+    if (!PyArg_UnpackTuple(args, "rstrip",
+        0, 1,
+        &bytes))
+        goto exit;
+    return_value = bytes_rstrip_impl(self, bytes);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytes_translate__doc__,
+"translate(table, [deletechars])\n"
+"Return a copy with each character mapped by the given translation table.\n"
+"\n"
+"  table\n"
+"    Translation table, which must be a bytes object of length 256.\n"
+"\n"
+"All characters occurring in the optional argument deletechars are removed.\n"
+"The remaining characters are mapped through the given translation table.");
+
+#define BYTES_TRANSLATE_METHODDEF    \
+    {"translate", (PyCFunction)bytes_translate, METH_VARARGS, bytes_translate__doc__},
+
+static PyObject *
+bytes_translate_impl(PyBytesObject *self, PyObject *table, int group_right_1, PyObject *deletechars);
+
+static PyObject *
+bytes_translate(PyBytesObject *self, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    PyObject *table;
+    int group_right_1 = 0;
+    PyObject *deletechars = NULL;
+
+    switch (PyTuple_GET_SIZE(args)) {
+        case 1:
+            if (!PyArg_ParseTuple(args, "O:translate", &table))
+                goto exit;
+            break;
+        case 2:
+            if (!PyArg_ParseTuple(args, "OO:translate", &table, &deletechars))
+                goto exit;
+            group_right_1 = 1;
+            break;
+        default:
+            PyErr_SetString(PyExc_TypeError, "bytes.translate requires 1 to 2 arguments");
+            goto exit;
+    }
+    return_value = bytes_translate_impl(self, table, group_right_1, deletechars);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytes_maketrans__doc__,
+"maketrans(frm, to, /)\n"
+"--\n"
+"\n"
+"Return a translation table useable for the bytes or bytearray translate method.\n"
+"\n"
+"The returned table will be one where each byte in frm is mapped to the byte at\n"
+"the same position in to.\n"
+"\n"
+"The bytes objects frm and to must be of the same length.");
+
+#define BYTES_MAKETRANS_METHODDEF    \
+    {"maketrans", (PyCFunction)bytes_maketrans, METH_VARARGS|METH_STATIC, bytes_maketrans__doc__},
+
+static PyObject *
+bytes_maketrans_impl(Py_buffer *frm, Py_buffer *to);
+
+static PyObject *
+bytes_maketrans(void *null, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    Py_buffer frm = {NULL, NULL};
+    Py_buffer to = {NULL, NULL};
+
+    if (!PyArg_ParseTuple(args,
+        "y*y*:maketrans",
+        &frm, &to))
+        goto exit;
+    return_value = bytes_maketrans_impl(&frm, &to);
+
+exit:
+    /* Cleanup for frm */
+    if (frm.obj)
+       PyBuffer_Release(&frm);
+    /* Cleanup for to */
+    if (to.obj)
+       PyBuffer_Release(&to);
+
+    return return_value;
+}
+
+PyDoc_STRVAR(bytes_replace__doc__,
+"replace($self, old, new, count=-1, /)\n"
+"--\n"
+"\n"
+"Return a copy with all occurrences of substring old replaced by new.\n"
+"\n"
+"  count\n"
+"    Maximum number of occurrences to replace.\n"
+"    -1 (the default value) means replace all occurrences.\n"
+"\n"
+"If the optional argument count is given, only the first count occurrences are\n"
+"replaced.");
+
+#define BYTES_REPLACE_METHODDEF    \
+    {"replace", (PyCFunction)bytes_replace, METH_VARARGS, bytes_replace__doc__},
+
+static PyObject *
+bytes_replace_impl(PyBytesObject*self, Py_buffer *old, Py_buffer *new, Py_ssize_t count);
+
+static PyObject *
+bytes_replace(PyBytesObject*self, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    Py_buffer old = {NULL, NULL};
+    Py_buffer new = {NULL, NULL};
+    Py_ssize_t count = -1;
+
+    if (!PyArg_ParseTuple(args,
+        "y*y*|n:replace",
+        &old, &new, &count))
+        goto exit;
+    return_value = bytes_replace_impl(self, &old, &new, count);
+
+exit:
+    /* Cleanup for old */
+    if (old.obj)
+       PyBuffer_Release(&old);
+    /* Cleanup for new */
+    if (new.obj)
+       PyBuffer_Release(&new);
+
+    return return_value;
+}
+
+PyDoc_STRVAR(bytes_decode__doc__,
+"decode($self, /, encoding=\'utf-8\', errors=\'strict\')\n"
+"--\n"
+"\n"
+"Decode the bytes using the codec registered for encoding.\n"
+"\n"
+"  encoding\n"
+"    The encoding with which to decode the bytes.\n"
+"  errors\n"
+"    The error handling scheme to use for the handling of decoding errors.\n"
+"    The default is \'strict\' meaning that decoding errors raise a\n"
+"    UnicodeDecodeError. Other possible values are \'ignore\' and \'replace\'\n"
+"    as well as any other name registered with codecs.register_error that\n"
+"    can handle UnicodeDecodeErrors.");
+
+#define BYTES_DECODE_METHODDEF    \
+    {"decode", (PyCFunction)bytes_decode, METH_VARARGS|METH_KEYWORDS, bytes_decode__doc__},
+
+static PyObject *
+bytes_decode_impl(PyBytesObject*self, const char *encoding, const char *errors);
+
+static PyObject *
+bytes_decode(PyBytesObject*self, PyObject *args, PyObject *kwargs)
+{
+    PyObject *return_value = NULL;
+    static char *_keywords[] = {"encoding", "errors", NULL};
+    const char *encoding = NULL;
+    const char *errors = NULL;
+
+    if (!PyArg_ParseTupleAndKeywords(args, kwargs,
+        "|ss:decode", _keywords,
+        &encoding, &errors))
+        goto exit;
+    return_value = bytes_decode_impl(self, encoding, errors);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytes_splitlines__doc__,
+"splitlines($self, /, keepends=False)\n"
+"--\n"
+"\n"
+"Return a list of the lines in the bytes, breaking at line boundaries.\n"
+"\n"
+"Line breaks are not included in the resulting list unless keepends is given and\n"
+"true.");
+
+#define BYTES_SPLITLINES_METHODDEF    \
+    {"splitlines", (PyCFunction)bytes_splitlines, METH_VARARGS|METH_KEYWORDS, bytes_splitlines__doc__},
+
+static PyObject *
+bytes_splitlines_impl(PyBytesObject*self, int keepends);
+
+static PyObject *
+bytes_splitlines(PyBytesObject*self, PyObject *args, PyObject *kwargs)
+{
+    PyObject *return_value = NULL;
+    static char *_keywords[] = {"keepends", NULL};
+    int keepends = 0;
+
+    if (!PyArg_ParseTupleAndKeywords(args, kwargs,
+        "|i:splitlines", _keywords,
+        &keepends))
+        goto exit;
+    return_value = bytes_splitlines_impl(self, keepends);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(bytes_fromhex__doc__,
+"fromhex($type, string, /)\n"
+"--\n"
+"\n"
+"Create a bytes object from a string of hexadecimal numbers.\n"
+"\n"
+"Spaces between two numbers are accepted.\n"
+"Example: bytes.fromhex(\'B9 01EF\') -> b\'\\\\xb9\\\\x01\\\\xef\'.");
+
+#define BYTES_FROMHEX_METHODDEF    \
+    {"fromhex", (PyCFunction)bytes_fromhex, METH_VARARGS|METH_CLASS, bytes_fromhex__doc__},
+
+static PyObject *
+bytes_fromhex_impl(PyTypeObject *type, PyObject *string);
+
+static PyObject *
+bytes_fromhex(PyTypeObject *type, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    PyObject *string;
+
+    if (!PyArg_ParseTuple(args,
+        "U:fromhex",
+        &string))
+        goto exit;
+    return_value = bytes_fromhex_impl(type, string);
+
+exit:
+    return return_value;
+}
+/*[clinic end generated code: output=dfe5c9a317b99f49 input=a9049054013a1b77]*/
diff --git a/Objects/clinic/dictobject.c.h b/Objects/clinic/dictobject.c.h
new file mode 100644
index 0000000..5288b9a
--- /dev/null
+++ b/Objects/clinic/dictobject.c.h
@@ -0,0 +1,42 @@
+/*[clinic input]
+preserve
+[clinic start generated code]*/
+
+PyDoc_STRVAR(dict_fromkeys__doc__,
+"fromkeys($type, iterable, value=None, /)\n"
+"--\n"
+"\n"
+"Returns a new dict with keys from iterable and values equal to value.");
+
+#define DICT_FROMKEYS_METHODDEF    \
+    {"fromkeys", (PyCFunction)dict_fromkeys, METH_VARARGS|METH_CLASS, dict_fromkeys__doc__},
+
+static PyObject *
+dict_fromkeys_impl(PyTypeObject *type, PyObject *iterable, PyObject *value);
+
+static PyObject *
+dict_fromkeys(PyTypeObject *type, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    PyObject *iterable;
+    PyObject *value = Py_None;
+
+    if (!PyArg_UnpackTuple(args, "fromkeys",
+        1, 2,
+        &iterable, &value))
+        goto exit;
+    return_value = dict_fromkeys_impl(type, iterable, value);
+
+exit:
+    return return_value;
+}
+
+PyDoc_STRVAR(dict___contains____doc__,
+"__contains__($self, key, /)\n"
+"--\n"
+"\n"
+"True if D has a key k, else False.");
+
+#define DICT___CONTAINS___METHODDEF    \
+    {"__contains__", (PyCFunction)dict___contains__, METH_O|METH_COEXIST, dict___contains____doc__},
+/*[clinic end generated code: output=fe74d676332fdba6 input=a9049054013a1b77]*/
diff --git a/Objects/clinic/unicodeobject.c.h b/Objects/clinic/unicodeobject.c.h
new file mode 100644
index 0000000..053a471
--- /dev/null
+++ b/Objects/clinic/unicodeobject.c.h
@@ -0,0 +1,42 @@
+/*[clinic input]
+preserve
+[clinic start generated code]*/
+
+PyDoc_STRVAR(unicode_maketrans__doc__,
+"maketrans(x, y=None, z=None, /)\n"
+"--\n"
+"\n"
+"Return a translation table usable for str.translate().\n"
+"\n"
+"If there is only one argument, it must be a dictionary mapping Unicode\n"
+"ordinals (integers) or characters to Unicode ordinals, strings or None.\n"
+"Character keys will be then converted to ordinals.\n"
+"If there are two arguments, they must be strings of equal length, and\n"
+"in the resulting dictionary, each character in x will be mapped to the\n"
+"character at the same position in y. If there is a third argument, it\n"
+"must be a string, whose characters will be mapped to None in the result.");
+
+#define UNICODE_MAKETRANS_METHODDEF    \
+    {"maketrans", (PyCFunction)unicode_maketrans, METH_VARARGS|METH_STATIC, unicode_maketrans__doc__},
+
+static PyObject *
+unicode_maketrans_impl(PyObject *x, PyObject *y, PyObject *z);
+
+static PyObject *
+unicode_maketrans(void *null, PyObject *args)
+{
+    PyObject *return_value = NULL;
+    PyObject *x;
+    PyObject *y = NULL;
+    PyObject *z = NULL;
+
+    if (!PyArg_ParseTuple(args,
+        "O|UU:maketrans",
+        &x, &y, &z))
+        goto exit;
+    return_value = unicode_maketrans_impl(x, y, z);
+
+exit:
+    return return_value;
+}
+/*[clinic end generated code: output=4670413843c53055 input=a9049054013a1b77]*/
diff --git a/Objects/dictobject.c b/Objects/dictobject.c
index a3219f7..cb0d2a7 100644
--- a/Objects/dictobject.c
+++ b/Objects/dictobject.c
@@ -233,6 +233,8 @@
 static PyDictObject *free_list[PyDict_MAXFREELIST];
 static int numfree = 0;
 
+#include "clinic/dictobject.c.h"
+
 int
 PyDict_ClearFreeList(void)
 {
@@ -1757,38 +1759,9 @@
 Returns a new dict with keys from iterable and values equal to value.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(dict_fromkeys__doc__,
-"fromkeys($type, iterable, value=None, /)\n"
-"--\n"
-"\n"
-"Returns a new dict with keys from iterable and values equal to value.");
-
-#define DICT_FROMKEYS_METHODDEF    \
-    {"fromkeys", (PyCFunction)dict_fromkeys, METH_VARARGS|METH_CLASS, dict_fromkeys__doc__},
-
-static PyObject *
-dict_fromkeys_impl(PyTypeObject *type, PyObject *iterable, PyObject *value);
-
-static PyObject *
-dict_fromkeys(PyTypeObject *type, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    PyObject *iterable;
-    PyObject *value = Py_None;
-
-    if (!PyArg_UnpackTuple(args, "fromkeys",
-        1, 2,
-        &iterable, &value))
-        goto exit;
-    return_value = dict_fromkeys_impl(type, iterable, value);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 dict_fromkeys_impl(PyTypeObject *type, PyObject *iterable, PyObject *value)
-/*[clinic end generated code: output=55f8dc0ffa87406f input=b85a667f9bf4669d]*/
+/*[clinic end generated code: output=8fb98e4b10384999 input=b85a667f9bf4669d]*/
 {
     PyObject *it;       /* iter(seq) */
     PyObject *key;
@@ -2266,18 +2239,9 @@
 True if D has a key k, else False.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(dict___contains____doc__,
-"__contains__($self, key, /)\n"
-"--\n"
-"\n"
-"True if D has a key k, else False.");
-
-#define DICT___CONTAINS___METHODDEF    \
-    {"__contains__", (PyCFunction)dict___contains__, METH_O|METH_COEXIST, dict___contains____doc__},
-
 static PyObject *
 dict___contains__(PyDictObject *self, PyObject *key)
-/*[clinic end generated code: output=3cf3f8aaf2cc5cc3 input=b852b2a19b51ab24]*/
+/*[clinic end generated code: output=a3d03db709ed6e6b input=b852b2a19b51ab24]*/
 {
     register PyDictObject *mp = self;
     Py_hash_t hash;
diff --git a/Objects/unicodeobject.c b/Objects/unicodeobject.c
index e494e4a..9611ed4 100644
--- a/Objects/unicodeobject.c
+++ b/Objects/unicodeobject.c
@@ -290,6 +290,8 @@
     0, 0, 0, 0, 0, 0, 0, 0
 };
 
+#include "clinic/unicodeobject.c.h"
+
 /* The max unicode value is always 0x10FFFF while using the PEP-393 API.
    This function is kept for backward compatibility with the old API. */
 Py_UNICODE
@@ -12955,47 +12957,9 @@
 must be a string, whose characters will be mapped to None in the result.
 [clinic start generated code]*/
 
-PyDoc_STRVAR(unicode_maketrans__doc__,
-"maketrans(x, y=None, z=None, /)\n"
-"--\n"
-"\n"
-"Return a translation table usable for str.translate().\n"
-"\n"
-"If there is only one argument, it must be a dictionary mapping Unicode\n"
-"ordinals (integers) or characters to Unicode ordinals, strings or None.\n"
-"Character keys will be then converted to ordinals.\n"
-"If there are two arguments, they must be strings of equal length, and\n"
-"in the resulting dictionary, each character in x will be mapped to the\n"
-"character at the same position in y. If there is a third argument, it\n"
-"must be a string, whose characters will be mapped to None in the result.");
-
-#define UNICODE_MAKETRANS_METHODDEF    \
-    {"maketrans", (PyCFunction)unicode_maketrans, METH_VARARGS|METH_STATIC, unicode_maketrans__doc__},
-
-static PyObject *
-unicode_maketrans_impl(PyObject *x, PyObject *y, PyObject *z);
-
-static PyObject *
-unicode_maketrans(void *null, PyObject *args)
-{
-    PyObject *return_value = NULL;
-    PyObject *x;
-    PyObject *y = NULL;
-    PyObject *z = NULL;
-
-    if (!PyArg_ParseTuple(args,
-        "O|UU:maketrans",
-        &x, &y, &z))
-        goto exit;
-    return_value = unicode_maketrans_impl(x, y, z);
-
-exit:
-    return return_value;
-}
-
 static PyObject *
 unicode_maketrans_impl(PyObject *x, PyObject *y, PyObject *z)
-/*[clinic end generated code: output=566edf630f77436a input=7bfbf529a293c6c5]*/
+/*[clinic end generated code: output=a925c89452bd5881 input=7bfbf529a293c6c5]*/
 {
     PyObject *new = NULL, *key, *value;
     Py_ssize_t i = 0;