We need to use the FBIO_WAITFORVSYNC ioctl on Linux using the i.MX28 EVK (with the lcd_43wvf1g.c LCD driver of the addon LCD) to reduce tearing in our application. We saw a couple of issues, and attached is a simple app which helps show these issues:
Issue 1 – Vertical refresh rate of the LCD panel
The ‘fbset’ command executed on the target gets us some basic parameters of the setup. This suggests a vertical refresh rate of ~92Hz.
root@freescale ~$ fbset
mode "800x480-92"
# D: 50.000 MHz, H: 50.403 kHz, V: 92.314 Hz
geometry 800 480 800 960 32
timings 20000 64 64 32 32 64 2
accel false
rgba 8/16,8/8,8/0,0/0
endmode
The attached vsync.c application simply waits for vsync and records the time between events. Execute it without command line arguments and you will see output like:
Frame time 23188 us
Frame time 23156 us
Frame time 23156 us
…
This suggests a refresh rate around 43.5Hz, as opposed to the “documented” 92Hz. What is the actual refresh rate of the panel?
Issue 2 – FBIO_WAITFORVSYNC not holding for next vsync
The expected behavior of FBIO_WAITFORVSYNC is for wait for the next vertical sync interrupt.
If you execute the attached test app with “vsync 1 30000” you will be simulating a 30ms load on each frame. This is more than the ~23ms budget, and should cause a frame skip, which means I would expect to see frame times of ~46ms (2 x 23ms). Instead I get:
Frame time 30313 us
Frame time 30281 us
Frame time 30281 us
…
This likely means that the vsync IRQ flag is already set when FBIO_WAITFORVSYNC is called, immediately unblocking the ioctl call. Instead the IRQ bit should be cleared when entering FBIO_WAITFORVSYNC and waiting for the next vsync interrupt. Otherwise you will tear if you exceed your frame budget.
The version of the SDK we use is L2.6.35_10.12.01. Does anyone know if the FBIO_WAITFORVSYNC is working properly, or if there is a fix available for it?
Original Attachment has been moved to: vsync.c.txt.zip