MemoryError when read wave frames

Hi,
when using openMV DAC to play wav file, MemoryError exception is raised in chunk.py when readframes function in wave.py module is called.
I got the chunk.py and wave.py and test wav file from below article:

https://docs.micropython.org/en/latest/pyboard/pyboard/tutorial/amp_skin.html

the tested wave file is near 9KB, 8-bit, 16KHZ.

def play(filename):
f = wave.open(filename, ‘r’)
total_frames = f.getnframes()
framerate = f.getframerate()

for position in range(0, total_frames, framerate):
f.setpos(position)
dac.write_timed(f.readframes(framerate), framerate)
delay(1000)

Is this MemoryError due to limited heap size? how to check how much heap available? the tested wav file is less than 9kB.
is there anyone succeed in play wav file with openMV?
Thanks,

Hi, I see no reason why this doesn’t work. However, we’ve never tested this.

Can you give use the exact line of code that error happened on?

Please see the attached screenshot.
Thanks,

import gc

print(“Free: %dKBs”%(gc.mem_free()//1024))

Note memory could be fragmented.

Please share the whole script(s)+wave file(s) in a .zip and I’ll test them.

Can you please leave me your mail address, I’ll mail you the script.
Also find when wav file is very small(tested with 1KB), it is ok.
Thanks,

OpenMV at OpenMV . io

This is just a fragmented memory issue, the scripts run fine on H7. I think most of memory is consumed by just loading/parsing/compiling the modules wave and chunk.

This seems to fix it:

            frames = f.readframes(frame_rate)
            self.dac.write_timed(frames, frame_rate)
            del frames
            delay(1000)
            gc.collect()

Are you on an M4?

Thanks!
It’s on M7.

Just tested, it seems not fix my issue on M7. do you have an estimate of memory cost of openmv itself excluding framebuffer?

Thanks

Hi,

Add a gc.collect at the end of detect_face_image:

        self.check_head_sideway(rotate_angle)
        gc.collect()

And gc.collect() before reading frames:

            gc.collect()
            frames = f.readframes(frame_rate)
            self.dac.write_timed(frames, frame_rate)
            del frames
            gc.collect()
            print("Free: %dKBs"%(gc.mem_free()/1024))

Unfortunately MicroPython’s GC doesn’t do very good defragmentation, reading bigger chunks if possible, will help.