Is there a way to, for example, mmap the fsb files and then tell FMOD to "use this region of ram for this FSB file"?
Using setFilesystem won’t work since it requires the data to be copied into a buffer, which would defeat the point of using mmap().
- BananaRaffle asked 8 years ago
Streaming requires nearly constant file reading and scales unpredictably on the iPhone. Using mmap means that file reads only happen when absolutely necessary. Most sounds that are used in a particular area of the game are used constantly. I also have a hunch that streaming would end up using much more RAM inside FMOD.
Also, we are also using streaming for sounds that are very large or are rarely used (e.g. cinematics, music, ambience). Memory mapping is used for fsbs that mainly contain a relatively large number of small waves (e.g. monsters, weapons, effects).
Oh! That’s exactly what I mean. I forgot about that – thanks I’ll report back for the record when I have a chance to try it out and see what the effect is. The goal is to reduce iPhone crashing due to low memory conditions by mmapping as much data as possible. If it’s hitchy or starts thrashing, then letting the OS fault the data is obviously not going to work out well for a game. We already try to be smart about loading/unloading only the necessary sounds, so it should be an interesting stress test.
We’re still testing, but it seems to work fine provided you jump through a couple of hoops:
1) You can’t "Decompress on load" any of your sounds. And since decompressing during playback eats a lot of CPU on the iPhone, this means you have to store your FSBs as PCM. But if it means lower risk of running out of RAM, it’s worth it IMO.
2) You have to use "PROT_READ | PROT_WRITE" and "MAP_PRIVATE" with mmap. There are a few place where FMOD will actually write to the OPENMEMORY_POINT data (loop points or something?). If you don’t use PROT_WRITE, you get invalid memory access. If you don’t MAP_PRIVATE, then writing to the memory mapped region will result in trying to write to the backing file. I’m not sure what would happen in that case.
3) You have to call "madvise( mappedFile, fileSize, POSIX_MADV_SEQUENTIAL )". Doing this tells the kernel to read ahead on fault by default. If you don’t do this, you get stuttering and lagging during faults. If you make this call, it’s completely transparent. Amazing.
And that’s about it.
Please login first to submit.