Uso open()
en el archivo correcto en /dev
(por ejemplo. /dev/fb0
), a continuación, utilizar mmap()
hacer un mapa en la memoria. Las páginas de manual ayudarán con estos syscalls si no sabe cómo usarlos.
Luego hay algunas estructuras y constantes para algunos ioctl()
s en <linux/fb.h>
. Al igual que muchos encabezados de kernel, puede aprender mucho simplemente navegando por el archivo.
Particularmente interesante es el ioctl FBIOGET_VSCREENINFO
con struct fb_var_screeninfo
. Tenga en cuenta que esto tiene xres
, yres
(resolución) y bits_per_pixel
. Luego está FBIOGET_FSCREENINFO
y struct fb_fix_screeninfo
que cuenta con más información como type
y line_length
.
Así que un píxel en (x, y) podría estar en mmap_base_address + x * bits_per_pixel/8 + y * line_length
. El formato exacto de los píxeles dependerá de las estructuras que recupere mediante ioctl; es su trabajo decidir cómo leerlos/escribirlos.
Ha sido un tiempo desde que he trabajado con este así que estoy un poco confusa en más detalles ..
Aquí está un ejemplo de código rápido y sucio sólo para ilustrar cómo se hace ... No he t probado esto.
#include <sys/types.h>
#include <sys/ioctl.h>
#include <sys/mman.h>
#include <linux/fb.h>
#include <unistd.h>
#include <fcntl.h>
#include <stdio.h>
int main()
{
struct fb_var_screeninfo screen_info;
struct fb_fix_screeninfo fixed_info;
char *buffer = NULL;
size_t buflen;
int fd = -1;
int r = 1;
fd = open("/dev/fb0", O_RDWR);
if (fd >= 0)
{
if (!ioctl(fd, FBIOGET_VSCREENINFO, &screen_info) &&
!ioctl(fd, FBIOGET_FSCREENINFO, &fixed_info))
{
buflen = screen_info.yres_virtual * fixed_info.line_length;
buffer = mmap(NULL,
buflen,
PROT_READ|PROT_WRITE,
MAP_SHARED,
fd,
0);
if (buffer != MAP_FAILED)
{
/*
* TODO: something interesting here.
* "buffer" now points to screen pixels.
* Each individual pixel might be at:
* buffer + x * screen_info.bits_per_pixel/8
* + y * fixed_info.line_length
* Then you can write pixels at locations such as that.
*/
r = 0; /* Indicate success */
}
else
{
perror("mmap");
}
}
else
{
perror("ioctl");
}
}
else
{
perror("open");
}
/*
* Clean up
*/
if (buffer && buffer != MAP_FAILED)
munmap(buffer, buflen);
if (fd >= 0)
close(fd);
return r;
}
acabo de dar cuenta que me olvidé de line_length en el "finfo" estructura, por lo que la actualización .. – asveikau
cuando compilo que estoy recibiendo algunos errores como este, En el archivo incluído en GC: 4: /usr/include/sys/mman.h: 38: error: tipos conflictivos para 'mode_t' /usr/include/linux/types.h:15: error: la declaración anterior de 'mode_t' estaba aquí En el archivo incluido de gc: 5: /usr/include /unistd.h:203: error: tipos conflictivos para 'gid_t' /usr/include/linux/types.h:27: error: la declaración anterior de 'gid_t' estaba aquí /usr/include/unistd.h:208 : error: tipos conflictivos para 'uid_t' /usr/include/linux/types.h:26: error: la declaración anterior de 'uid_t' estaba aquí en el archivo incluido en /usr/include/bits/fcntl.h:25 , – Rahul
@Rahul - Debe ser el orden en el que puse los encabezados ... Tal vez intente sys/types.h primero? – asveikau