#
9.3 Examples

Here is the example from section 9.1, rewritten so that the I/O buffer is allocated from the Python heap by using the first function set:

        PyObject *res;
        char *buf = (char *) PyMem_Malloc(BUFSIZ); /* for I/O */

        if (buf == NULL)
            return PyErr_NoMemory();
        /* ...Do some I/O operation involving buf... */
        res = PyString_FromString(buf);
        PyMem_Free(buf); /* allocated with PyMem_Malloc */
        return res;

The same code using the type-oriented function set:

        PyObject *res;
        char *buf = PyMem_New(char, BUFSIZ); /* for I/O */

        if (buf == NULL)
            return PyErr_NoMemory();
        /* ...Do some I/O operation involving buf... */
        res = PyString_FromString(buf);
        PyMem_Del(buf); /* allocated with PyMem_New */
        return res;

Note that in the two examples above, the buffer is always manipulated via functions belonging to the same set. Indeed, it is required to use the same memory API family for a given memory block, so that the risk of mixing different allocators is reduced to a minimum. The following code sequence contains two errors, one of which is labeled as fatal because it mixes two different allocators operating on different heaps.

    char *buf1 = PyMem_New(char, BUFSIZ);
    char *buf2 = (char *) malloc(BUFSIZ);
    char *buf3 = (char *) PyMem_Malloc(BUFSIZ);
    ...
    PyMem_Del(buf3);  /* Wrong -- should be PyMem_Free() */
    free(buf2);       /* Right -- allocated via malloc() */
    free(buf1);       /* Fatal -- should be PyMem_Del()  */

In addition to the functions aimed at handling raw memory blocks from the Python heap, objects in Python are allocated and released with `PyObject_New()`, `PyObject_NewVar()` and `PyObject_Del()`.

These will be explained in the next chapter on defining and implementing new object types in C.