It looks like PyOpenCL obsoleted the enqueue_read_buffer method, and enqueue_copy should be used instead. Even though enqueue_copy already exists with the earliest version of PyOpenCL I looked at, I wrote it in a backwards-compatible way so that it doesn't break in case I missed something. Tested on OSX in frozen mode, but it should be platform-independent.