mirror of
https://github.com/ivoszbg/uniLoader.git
synced 2024-11-10 06:00:07 +00:00
lib: Implement simplefb driver for framebuffer management
Signed-off-by: Ivaylo Ivanov <ivo.ivanov.ivanov1@gmail.com>
This commit is contained in:
parent
94b2cf0c4a
commit
e364dfbc1b
1
.gitignore
vendored
1
.gitignore
vendored
@ -4,3 +4,4 @@ asm/*.o
|
|||||||
asm/linker.lds
|
asm/linker.lds
|
||||||
board/*/*.o
|
board/*/*.o
|
||||||
soc/*/*.o
|
soc/*/*.o
|
||||||
|
lib/*/*.o
|
||||||
|
9
Makefile
9
Makefile
@ -43,8 +43,8 @@ OBJ = main.o \
|
|||||||
uniLoader: uniLoader.o
|
uniLoader: uniLoader.o
|
||||||
$(OBJCPY) -O binary $< $@
|
$(OBJCPY) -O binary $< $@
|
||||||
|
|
||||||
uniLoader.o: copy-board-config $(OBJ) asm/linker.lds build-board build-soc
|
uniLoader.o: copy-board-config $(OBJ) asm/linker.lds build-board build-soc build-lib
|
||||||
$(LD) $(OBJ) board.o soc.o -o $@ --script=asm/linker.lds
|
$(LD) $(OBJ) board.o soc.o lib/simplefb/simplefb.o -o $@ --script=asm/linker.lds
|
||||||
|
|
||||||
asm/linker.lds: asm/linker.lds.S $(KERNEL_PATH)
|
asm/linker.lds: asm/linker.lds.S $(KERNEL_PATH)
|
||||||
$(CPP) $< -DKERNEL_PATH=$(KERNEL_PATH) -DDTB_PATH=$(DTB_PATH) -P -o $@
|
$(CPP) $< -DKERNEL_PATH=$(KERNEL_PATH) -DDTB_PATH=$(DTB_PATH) -P -o $@
|
||||||
@ -55,8 +55,11 @@ build-board:
|
|||||||
build-soc:
|
build-soc:
|
||||||
cd soc && make
|
cd soc && make
|
||||||
|
|
||||||
|
build-lib:
|
||||||
|
cd lib && make
|
||||||
|
|
||||||
copy-board-config:
|
copy-board-config:
|
||||||
cp include/board/board-$(board_codename).h include/board-config.h
|
cp include/board/board-$(board_codename).h include/board-config.h
|
||||||
|
|
||||||
clean:
|
clean:
|
||||||
-rm *.o asm/linker.lds asm/Start.o uniLoader board/*/*.o include/board-config.h soc/*/*.o
|
-rm *.o asm/linker.lds asm/Start.o uniLoader board/*/*.o include/board-config.h soc/*/*.o lib/*/*.o
|
||||||
|
@ -9,4 +9,9 @@
|
|||||||
#define PAYLOAD_ENTRY 0x90000000
|
#define PAYLOAD_ENTRY 0x90000000
|
||||||
#define PAYLOAD_SIZE 0x2000000
|
#define PAYLOAD_SIZE 0x2000000
|
||||||
|
|
||||||
|
#define FRAMEBUFFER_BASE 0xcc000000
|
||||||
|
#define FRAMEBUFFER_WIDTH 1440
|
||||||
|
#define FRAMEBUFFER_HEIGHT 2960
|
||||||
|
#define FRAMEBUFFER_STRIDE 4
|
||||||
|
|
||||||
#endif // BOARD_DREAMLTE_H_
|
#endif // BOARD_DREAMLTE_H_
|
||||||
|
@ -10,4 +10,10 @@
|
|||||||
#define PAYLOAD_ENTRY 0x830000000
|
#define PAYLOAD_ENTRY 0x830000000
|
||||||
#define PAYLOAD_SIZE 0x2000000
|
#define PAYLOAD_SIZE 0x2000000
|
||||||
|
|
||||||
|
#define FRAMEBUFFER_BASE 0x83e900000
|
||||||
|
/* Width is offsetted by 2 */
|
||||||
|
#define FRAMEBUFFER_WIDTH 752
|
||||||
|
#define FRAMEBUFFER_HEIGHT 1334
|
||||||
|
#define FRAMEBUFFER_STRIDE 4
|
||||||
|
|
||||||
#endif // BOARD_N61AP_H_
|
#endif // BOARD_N61AP_H_
|
||||||
|
1830
include/lib/font.h
Normal file
1830
include/lib/font.h
Normal file
File diff suppressed because it is too large
Load Diff
35
include/lib/simplefb.h
Normal file
35
include/lib/simplefb.h
Normal file
@ -0,0 +1,35 @@
|
|||||||
|
/* SPDX-License-Identifier: GPL-2.0 */
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2022, Ivaylo Ivanov <ivo.ivanov.ivanov1@gmail.com>
|
||||||
|
* Copyright (c) 2022, Markuss Broks <markuss.broks@gmail.com>
|
||||||
|
* Copyright (c) 2022, Michael Srba <Michael.Srba@seznam.cz>
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef SIMPLEFB_H_ /* Include guard */
|
||||||
|
#define SIMPLEFB_H_
|
||||||
|
|
||||||
|
typedef struct _color {
|
||||||
|
int r;
|
||||||
|
int g;
|
||||||
|
int b;
|
||||||
|
} color;
|
||||||
|
|
||||||
|
typedef struct _font_params {
|
||||||
|
int width;
|
||||||
|
int height;
|
||||||
|
} font_params;
|
||||||
|
|
||||||
|
font_params get_font_params(void);
|
||||||
|
|
||||||
|
long unsigned int strlen(const char *p) {
|
||||||
|
unsigned int i = 0;
|
||||||
|
|
||||||
|
while(*p != '\0') {
|
||||||
|
i++;
|
||||||
|
p++;
|
||||||
|
}
|
||||||
|
|
||||||
|
return i;
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif
|
@ -10,6 +10,9 @@ extern void load_kernel(void* dtb, void* x1, void* x2, void* x3, void* kernel);
|
|||||||
extern void soc_init(void);
|
extern void soc_init(void);
|
||||||
extern void board_init(void);
|
extern void board_init(void);
|
||||||
|
|
||||||
|
extern void draw_text(volatile char *fb, char *text, int textX, int textY);
|
||||||
|
extern void debug_printfb(volatile char *fb, char *text, int textX, int width, int stride);
|
||||||
|
|
||||||
/* Define our own 128 bit memcpy */
|
/* Define our own 128 bit memcpy */
|
||||||
void memcpy(void *dest, void *src, int size)
|
void memcpy(void *dest, void *src, int size)
|
||||||
{
|
{
|
||||||
|
27
lib/Makefile
Normal file
27
lib/Makefile
Normal file
@ -0,0 +1,27 @@
|
|||||||
|
# SPDX-License-Identifier: GPL-2.0
|
||||||
|
|
||||||
|
#
|
||||||
|
# Compiler defines
|
||||||
|
#
|
||||||
|
CCPREFIX?=aarch64-linux-gnu-
|
||||||
|
CC=$(CCPREFIX)gcc
|
||||||
|
CPP=$(CCPREFIX)cpp
|
||||||
|
LD=$(CCPREFIX)ld
|
||||||
|
OBJCPY=$(CCPREFIX)objcopy
|
||||||
|
|
||||||
|
#
|
||||||
|
# Compiler flags
|
||||||
|
#
|
||||||
|
CFLAGS = -march=armv8-a -Wall -nodefaultlibs \
|
||||||
|
-nostdlib -nostartfiles -fno-builtin \
|
||||||
|
-nostdinc -Wstrict-prototypes -std=gnu11 \
|
||||||
|
-Wno-main -I'../include'
|
||||||
|
|
||||||
|
#
|
||||||
|
# Split BOARD definition into 2 parts - manufacturer and codename
|
||||||
|
#
|
||||||
|
split_board := $(subst -, ,$(BOARD:%=%))
|
||||||
|
board_manu := $(word 1,$(split_board))
|
||||||
|
board_codename := $(word 2,$(split_board))
|
||||||
|
|
||||||
|
all: simplefb/simplefb.o
|
80
lib/simplefb/simplefb.c
Normal file
80
lib/simplefb/simplefb.c
Normal file
@ -0,0 +1,80 @@
|
|||||||
|
/* SPDX-License-Identifier: GPL-2.0 */
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2022, Ivaylo Ivanov <ivo.ivanov.ivanov1@gmail.com>
|
||||||
|
* Copyright (c) 2022, Markuss Broks <markuss.broks@gmail.com>
|
||||||
|
* Copyright (c) 2022, Michael Srba <Michael.Srba@seznam.cz>
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <lib/simplefb.h>
|
||||||
|
#include <lib/font.h>
|
||||||
|
|
||||||
|
int debug_linecount = 0;
|
||||||
|
|
||||||
|
void clean_fb(volatile char *fb, char *text, int width, int height, int stride) {
|
||||||
|
for (volatile char *addr = fb; addr < fb + (width * height * stride); addr += stride)
|
||||||
|
*(int*) (addr) = 0x0;
|
||||||
|
}
|
||||||
|
|
||||||
|
void draw_pixel(volatile char *fb, int x, int y, int width, int stride) {
|
||||||
|
long int location = (x * stride) + (y * width * stride);
|
||||||
|
|
||||||
|
*(fb + location) = 255; // Blue
|
||||||
|
*(fb + location + 1) = 255; // Green
|
||||||
|
*(fb + location + 2) = 255; // Red
|
||||||
|
*(fb + location + 3) = 255; // Full opacity
|
||||||
|
}
|
||||||
|
|
||||||
|
void draw_horizontal_line(volatile char *fb, int x1, int x2, int y, color c, int width, int stride) {
|
||||||
|
for (int i = x1; i < x2; i++)
|
||||||
|
draw_pixel(fb, i, y, width, stride);
|
||||||
|
}
|
||||||
|
|
||||||
|
void draw_vertical_line(volatile char *fb, int x, int y1, int y2, color c, int width, int stride) {
|
||||||
|
for (int i = y1; i < y2; i++)
|
||||||
|
draw_pixel(fb, x, i, width, stride);
|
||||||
|
}
|
||||||
|
|
||||||
|
void draw_filled_rectangle(volatile char *fb, int x1, int y1, int w, int h, color c, int width, int stride) {
|
||||||
|
for (int i = y1; i < (y1 + h); i++)
|
||||||
|
draw_horizontal_line(fb, x1, (x1 + w), i, c, width, stride);
|
||||||
|
}
|
||||||
|
|
||||||
|
void draw_text(volatile char *fb, char *text, int textX, int textY, int width, int stride) {
|
||||||
|
// loop through all characters in the text string
|
||||||
|
int l = strlen(text);
|
||||||
|
|
||||||
|
for (int i = 0; i < l; i++) {
|
||||||
|
if(text[i] < 32)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
int ix = font_index(text[i]);
|
||||||
|
unsigned char *img = letters[ix];
|
||||||
|
|
||||||
|
for (int y = 0; y < FONTH; y++) {
|
||||||
|
unsigned char b = img[y];
|
||||||
|
|
||||||
|
for (int x = 0; x < FONTW; x++) {
|
||||||
|
if (((b << x) & 0b10000000) > 0)
|
||||||
|
draw_pixel(fb, textX + i * FONTW + x, textY + y, width, stride);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void debug_printfb(volatile char *fb, char *text, int textX, int width, int stride) {
|
||||||
|
/* IMPORTANT: Limit the linecount */
|
||||||
|
if(debug_linecount > 100 || debug_linecount < 0)
|
||||||
|
debug_linecount = 0;
|
||||||
|
|
||||||
|
draw_text(fb, "[uniLoader] ", textX, (20 + (debug_linecount * 30)), width, stride);
|
||||||
|
draw_text(fb, text, textX + 96, (20 + (debug_linecount * 30)), width, stride);
|
||||||
|
|
||||||
|
debug_linecount++;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Helper functions */
|
||||||
|
font_params get_font_params() {
|
||||||
|
font_params params = {.width=FONTW, .height=FONTH};
|
||||||
|
|
||||||
|
return params;
|
||||||
|
}
|
6
main.c
6
main.c
@ -8,11 +8,17 @@
|
|||||||
#include <board-config.h>
|
#include <board-config.h>
|
||||||
|
|
||||||
void main(void* dt, void* kernel) {
|
void main(void* dt, void* kernel) {
|
||||||
|
/* C entry */
|
||||||
|
|
||||||
/* Initialize SoC and Board specific peripherals/quirks */
|
/* Initialize SoC and Board specific peripherals/quirks */
|
||||||
soc_init();
|
soc_init();
|
||||||
|
debug_printfb((char*)FRAMEBUFFER_BASE, "soc_init() passed!", 0, FRAMEBUFFER_WIDTH, FRAMEBUFFER_STRIDE);
|
||||||
|
|
||||||
board_init();
|
board_init();
|
||||||
|
debug_printfb((char*)FRAMEBUFFER_BASE, "board_init() passed!", 0, FRAMEBUFFER_WIDTH, FRAMEBUFFER_STRIDE);
|
||||||
|
|
||||||
/* Copy kernel to memory and boot */
|
/* Copy kernel to memory and boot */
|
||||||
|
debug_printfb((char*)FRAMEBUFFER_BASE, "Booting linux...", 0, FRAMEBUFFER_WIDTH, FRAMEBUFFER_STRIDE);
|
||||||
memcpy((void*)PAYLOAD_ENTRY, kernel, PAYLOAD_SIZE);
|
memcpy((void*)PAYLOAD_ENTRY, kernel, PAYLOAD_SIZE);
|
||||||
load_kernel(dt, 0, 0, 0, (void*)PAYLOAD_ENTRY);
|
load_kernel(dt, 0, 0, 0, (void*)PAYLOAD_ENTRY);
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user