126 lines
4.7 KiB
C
126 lines
4.7 KiB
C
#include <am.h>
|
|
#include <klib.h>
|
|
#include <klib-macros.h>
|
|
|
|
#define VGALCD_BASE_ADDR 0x10004000
|
|
#define VGALCD_REG_CTRL *((volatile uint32_t *)(VGALCD_BASE_ADDR + 0))
|
|
#define VGALCD_REG_HVVL *((volatile uint32_t *)(VGALCD_BASE_ADDR + 4))
|
|
#define VGALCD_REG_HTIM *((volatile uint32_t *)(VGALCD_BASE_ADDR + 8))
|
|
#define VGALCD_REG_VTIM *((volatile uint32_t *)(VGALCD_BASE_ADDR + 12))
|
|
#define VGALCD_REG_FBBA1 *((volatile uint32_t *)(VGALCD_BASE_ADDR + 16))
|
|
#define VGALCD_REG_FBBA2 *((volatile uint32_t *)(VGALCD_BASE_ADDR + 20))
|
|
#define VGALCD_REG_THOLD *((volatile uint32_t *)(VGALCD_BASE_ADDR + 24))
|
|
#define VGALCD_REG_STAT *((volatile uint32_t *)(VGALCD_BASE_ADDR + 28))
|
|
|
|
#define VGALCD_FB1_ADDR 0x80110000
|
|
#define VGALCD_FB2_ADDR 0x80120000
|
|
#define VGALCD_FB_TEST_SIZE (4 * 1024)
|
|
#define VGALCD_FB_TEST_STEP 256
|
|
|
|
#define VGALCD_HVSIZE 640
|
|
#define VGALCD_VVSIZE 480
|
|
|
|
void vgalcd_init() {
|
|
VGALCD_REG_CTRL = (uint32_t)0;
|
|
VGALCD_REG_HVVL = (uint32_t)0x01DF027F;
|
|
VGALCD_REG_HTIM = (uint32_t)0x02F17C0F;
|
|
VGALCD_REG_VTIM = (uint32_t)0x02000409;
|
|
VGALCD_REG_FBBA1 = VGALCD_FB1_ADDR;
|
|
VGALCD_REG_FBBA2 = VGALCD_FB2_ADDR;
|
|
printf("HVLEN: %d VVLEN: %d\n", (VGALCD_REG_HVVL & 0xFFFF) + 1, ((VGALCD_REG_HVVL >> 16) & 0xFFFF) + 1);
|
|
printf("HFPSIZE: %d HSNSIZE: %d HBPSIZE: %d\n", (VGALCD_REG_HTIM & 0x3FF) + 1, ((VGALCD_REG_HTIM >> 10) & 0x3FF) + 1, ((VGALCD_REG_HTIM >> 20) & 0x3FF) + 1);
|
|
printf("VFPSIZE: %d VSNSIZE: %d VBPSIZE: %d\n", (VGALCD_REG_VTIM & 0x3FF) + 1, ((VGALCD_REG_VTIM >> 10) & 0x3FF) + 1, ((VGALCD_REG_VTIM >> 20) & 0x3FF) + 1);
|
|
printf("FB1: %x FB2: %x CTRL: %x\n", VGALCD_REG_FBBA1, VGALCD_REG_FBBA2, VGALCD_REG_CTRL);
|
|
}
|
|
|
|
void vgalcd_test_mode() {
|
|
VGALCD_REG_CTRL = (uint32_t)0x110101; // div 2, test, en, rgb444
|
|
printf("FB1: %x FB2: %x CTRL: %x\n", VGALCD_REG_FBBA1, VGALCD_REG_FBBA2, VGALCD_REG_CTRL);
|
|
}
|
|
|
|
void vgalcd_single_frame_mode(uint32_t addr) {
|
|
VGALCD_REG_STAT = (uint32_t)0;
|
|
VGALCD_REG_THOLD = (uint32_t)256;
|
|
|
|
// R[11:8] G[7:4] B[3:0]
|
|
uint16_t *mem_data = (void *)(uint64_t)addr;
|
|
for(int i = 0; i < VGALCD_HVSIZE * VGALCD_VVSIZE; ++i) {
|
|
if(i < VGALCD_HVSIZE * VGALCD_VVSIZE / 2) mem_data[i] = 0x0F;
|
|
else mem_data[i] = 0xF0;
|
|
}
|
|
|
|
VGALCD_REG_CTRL = (uint32_t)0x1FA0101; // burlen 64, div 2, single frame, en, rgb444
|
|
printf("FB1: %x FB2: %x CTRL: %x\n", VGALCD_REG_FBBA1, VGALCD_REG_FBBA2, VGALCD_REG_CTRL);
|
|
}
|
|
|
|
void vgalcd_two_frame_sw_mode(uint32_t addr1, uint32_t addr2) {
|
|
VGALCD_REG_STAT = (uint32_t)0;
|
|
VGALCD_REG_THOLD = (uint32_t)256;
|
|
|
|
// R[11:8] G[7:4] B[3:0]
|
|
uint16_t *mem_data1 = (void *)(uint64_t)addr1;
|
|
uint16_t tmp_val;
|
|
for(int i = 0; i < VGALCD_HVSIZE * VGALCD_VVSIZE; ++i) mem_data1[i] = 0x0F;
|
|
for(int i = 0; i < VGALCD_HVSIZE * VGALCD_VVSIZE; ++i) {
|
|
tmp_val = mem_data1[i];
|
|
if(tmp_val != (uint16_t)0x0F) putstr("error\n");
|
|
}
|
|
|
|
uint16_t *mem_data2 = (void *)(uint64_t)addr2;
|
|
for(int i = 0; i < VGALCD_HVSIZE * VGALCD_VVSIZE; ++i) mem_data2[i] = 0xF0;
|
|
for(int i = 0; i < VGALCD_HVSIZE * VGALCD_VVSIZE; ++i) {
|
|
tmp_val = mem_data2[i];
|
|
if(tmp_val != (uint16_t)0xF0) putstr("error\n");
|
|
}
|
|
|
|
VGALCD_REG_CTRL = (uint32_t)0x1FA0111; // burlen 64, div 2, two frame sw, en, rgb444
|
|
printf("FB1: %x FB2: %x CTRL: %x\n", VGALCD_REG_FBBA1, VGALCD_REG_FBBA2, VGALCD_REG_CTRL);
|
|
}
|
|
|
|
void vgalcd_fb_test(uint32_t addr) {
|
|
uint64_t *mem_data = (void *)(uint64_t)addr;
|
|
uint64_t len = VGALCD_FB_TEST_SIZE / sizeof(uint64_t);
|
|
for (int i = 0; i < len; ++i) {
|
|
if (i % VGALCD_FB_TEST_STEP == 0) {
|
|
printf("[mem data][1] cnt: %d(%x), addr: %p\n", i, i, (mem_data + i));
|
|
}
|
|
mem_data[i] = i;
|
|
}
|
|
putstr("mem tests prepared\n");
|
|
|
|
for(int i = 0; i < len; ++i) {
|
|
if (i % VGALCD_FB_TEST_STEP == 0) {
|
|
printf("[mem data][2] cnt: %d(%x), addr: %p\n", i, i, (mem_data + i));
|
|
}
|
|
if (mem_data[i] != i) {
|
|
printf("[error] i: %lx mem_data[i]: %lx xor: %lx addr: %p\n", i, mem_data[i], i ^ mem_data[i], (mem_data + i));
|
|
}
|
|
}
|
|
}
|
|
|
|
int main()
|
|
{
|
|
putstr("vgalcd test\n");
|
|
putstr("vgalcd init\n");
|
|
vgalcd_init();
|
|
// vgalcd_test_mode();
|
|
vgalcd_single_frame_mode(VGALCD_FB1_ADDR);
|
|
// vgalcd_two_frame_sw_mode(VGALCD_FB1_ADDR, VGALCD_FB2_ADDR);
|
|
// vgalcd_fb_test(VGALCD_FB1_ADDR);
|
|
// vgalcd_fb_test(VGALCD_FB2_ADDR);
|
|
|
|
|
|
// putstr("[write fb]\n");
|
|
// uint64_t *fb = (void *)FB_ADDR;
|
|
// for(int i = 0; i < VGA_H * VGA_W; ++i) {
|
|
// fb[i] = 0x123456;
|
|
// }
|
|
|
|
// mem_data = (void *)(VGA_FB_ADDR);
|
|
// for(int i = 0; i < VGA_H * VGA_W; ++i){
|
|
// printf("[mem data] addr: %p val: %lx\n", mem_data + i, mem_data[i]);
|
|
// }
|
|
|
|
return 0;
|
|
}
|