Почему не отображается в FrameBuffer Linux?

Решил попробовать написать графику без библиотек (своё всегда понятнее), но после запуска ничего не обнаружил, решил сделать фигуру больше - всё равно не помогло. Никаких ошибок не выводится, просто запускается программа и всё. Путь к FrameBuffer вроде указал правильно. (Не обращайте внимания на незаканчиваемый цикл while, это временная заглушка)

Код:

#include <iostream>
#include <string>
#include <vector>
#include <unistd.h>
#include <sys/ioctl.h>
#include <linux/fb.h>
#include <fcntl.h>
#include <sys/mman.h>

const int SCREEN_WIDTH = 800;
const int SCREEN_HEIGHT = 600;

const std::vector<float> vertices = {
    -0.5f, -0.5f, 0.0f,
     0.5f, -0.5f, 0.0f,
     0.0f,  0.5f, 0.0f
};

const std::vector<float> colors = {
    1.0f, 0.5f, 0.75f,
    1.0f, 0.5f, 0.75f,
    1.0f, 0.5f, 0.75f
};

int main() {
    int fb_fd = open("/dev/fb0", O_RDWR);
    if (fb_fd < 0) {
        std::cerr << "Failed to open framebuffer" << std::endl;
        return 1;
    }

    struct fb_var_screeninfo vinfo;
    ioctl(fb_fd, FBIOGET_HWCINFO, &vinfo);

    unsigned char* fbp = (unsigned char*)mmap(0, vinfo.xres * vinfo.yres * (vinfo.bits_per_pixel / 8), PROT_READ | PROT_WRITE, MAP_SHARED, fb_fd, 0);
    if (fbp == MAP_FAILED) {
        std::cerr << "Failed to map framebuffer" << std::endl;
        close(fb_fd);
        return 1;
    }
    while (true) {

        for (int y = 0; y < SCREEN_HEIGHT; y++) {
            for (int x = 0; x < SCREEN_WIDTH; x++) {
                bool inside = false;
                for (int i = 0; i < vertices.size(); i += 3) {
                    float x1 = vertices[i] * SCREEN_WIDTH / 2 + SCREEN_WIDTH / 2;
                    float y1 = vertices[i+1] * SCREEN_HEIGHT / 2 + SCREEN_HEIGHT / 2;
                    float x2 = vertices[i+3] * SCREEN_WIDTH / 2 + SCREEN_WIDTH / 2;
                    float y2 = vertices[i+4] * SCREEN_HEIGHT / 2 + SCREEN_HEIGHT / 2;
                    float x3 = vertices[i+6] * SCREEN_WIDTH / 2 + SCREEN_WIDTH / 2;
                    float y3 = vertices[i+7] * SCREEN_HEIGHT / 2 + SCREEN_HEIGHT / 2;

                    if ((x - x1) * (y2 - y1) - (y - y1) * (x2 - x1) >= 0 &&
                        (x - x2) * (y3 - y2) - (y - y2) * (x3 - x2) >= 0 &&
                        (x - x3) * (y1 - y3) - (y - y3) * (x1 - x3) >= 0) {
                        inside = true;
                        break;
                    }
                }

                if (inside) {
                    int pixel_offset = (y * vinfo.xres + x) * (vinfo.bits_per_pixel / 8);
                    fbp[pixel_offset + 0] = static_cast<unsigned char>(colors[2] * 255);
                    fbp[pixel_offset + 1] = static_cast<unsigned char>(colors[1] * 255);
                    fbp[pixel_offset + 2] = static_cast<unsigned char>(colors[0] * 255);
                }
            }
        }

        munmap(fbp, vinfo.xres * vinfo.yres * (vinfo.bits_per_pixel / 8));
    }
    close(fb_fd);
    return 0;
}

Система:

[rost@archlinux ~]$ neofetch
                   -`                    rost@archlinux 
                  .o+`                   -------------- 
                 `ooo/                   OS: Arch Linux x86_64 
                `+oooo:                  Host: 81HN Lenovo V130-15IKB 
               `+oooooo:                 Kernel: 6.9.7-arch1-1 
               -+oooooo+:                Uptime: 1 day, 1 hour, 15 mins 
             `/:-:++oooo+:               Packages: 1258 (pacman) 
            `/++++/+++++++:              Shell: bash 5.2.26 
           `/++++++++++++++:             Resolution: 1920x1080 
          `/+++ooooooooooooo/`           DE: Plasma 6.1.1 
         ./ooosssso++osssssso+`          WM: kwin 
        .oossssso-````/ossssss+`         Theme: Breeze-Dark [GTK2], Breeze [GTK3] 
       -osssssso.      :ssssssso.        Icons: breeze-dark [GTK2/3] 
      :osssssss/        osssso+++.       Terminal: konsole 
     /ossssssss/        +ssssooo/-       CPU: Intel i5-7200U (4) @ 3.100GHz 
   `/ossssso+/:-        -:/+osssso+-     GPU: Intel HD Graphics 620 
  `+sso+:-`                 `.-/+oso:    Memory: 5700MiB / 7107MiB 
 `++:.                           `-/+/
 .`                                 `/                           
                                                                 

Ответы (1 шт):

Автор решения: leb

Судя по отображению WM в neofetch, вы запускаете программу из графической оболочки. Скорее всего, из Xorg. Запустите арч без Xorg'а -- фреймбуфер сейчас не используется в Иксах.

В пакмане, кажется, есть пакет драйверов Xorg'а для фреймбуфера. Уверен, можно их поставить и сейчас в конфигах Xorg'а, но я где-то читал, что они медленные.

→ Ссылка