mirror of
https://github.com/sipeed/NanoKVM.git
synced 2026-09-11 00:22:56 -05:00
238 lines
4.7 KiB
C++
238 lines
4.7 KiB
C++
#include "hdmi.h"
|
|
|
|
using namespace maix;
|
|
using namespace maix::sys;
|
|
using namespace maix::peripheral;
|
|
i2c::I2C LT6911_i2c(4, i2c::Mode::MASTER);
|
|
|
|
void lt6911_enable()
|
|
{
|
|
uint8_t buf[2];
|
|
buf[0] = 0xff;
|
|
buf[1] = 0x80;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 2);
|
|
|
|
buf[0] = 0xee;
|
|
buf[1] = 0x01;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 2);
|
|
}
|
|
|
|
void lt6911_disable()
|
|
{
|
|
uint8_t buf[2];
|
|
buf[0] = 0xff;
|
|
buf[1] = 0x80;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 2);
|
|
|
|
buf[0] = 0xee;
|
|
buf[1] = 0x00;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 2);
|
|
}
|
|
|
|
void lt6911_start()
|
|
{
|
|
uint8_t buf[2];
|
|
|
|
buf[0] = 0xff;
|
|
buf[1] = 0x80;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 2);
|
|
|
|
buf[0] = 0x5A;
|
|
buf[1] = 0x80;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 2);
|
|
}
|
|
|
|
void lt6911_stop()
|
|
{
|
|
uint8_t buf[2];
|
|
|
|
buf[0] = 0xff;
|
|
buf[1] = 0x80;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 2);
|
|
|
|
buf[0] = 0x5A;
|
|
buf[1] = 0x88;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 2);
|
|
}
|
|
|
|
void lt6911_reset()
|
|
{
|
|
lt6911_stop();
|
|
time::sleep_ms(1);
|
|
lt6911_start();
|
|
}
|
|
|
|
void lt6911_get_hdmi_errer()
|
|
{
|
|
uint8_t buf[6];
|
|
|
|
buf[0] = 0xff;
|
|
buf[1] = 0xC0;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 2);
|
|
|
|
buf[0] = 0x20;
|
|
buf[1] = 0x01;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 2);
|
|
|
|
time::sleep_ms(100);
|
|
|
|
buf[0] = 0x24;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 1);
|
|
|
|
maix::Bytes *dat = LT6911_i2c.readfrom(LT6911_ADDR, 6);
|
|
|
|
buf[0] = 0x20;
|
|
buf[1] = 0x07;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 2);
|
|
|
|
for(int i = 0; i < 6; i++){
|
|
buf[i] = (uint8_t)dat->data[i];
|
|
}
|
|
delete dat;
|
|
|
|
printf("hdmi_errer_code = %x, %x, %x, %x, %x, %x\n", buf[0], buf[1], buf[2], buf[3], buf[4], buf[5]);
|
|
}
|
|
|
|
uint8_t lt6911_get_hdmi_res()
|
|
{
|
|
uint8_t buf[2];
|
|
uint8_t revbuf[4];
|
|
uint16_t Vactive;
|
|
uint16_t Hactive;
|
|
|
|
buf[0] = 0xff;
|
|
buf[1] = 0xd2;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 2);
|
|
|
|
buf[0] = 0x83;
|
|
buf[1] = 0x11;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 2);
|
|
|
|
time::sleep_ms(100);
|
|
|
|
// Vactive
|
|
buf[0] = 0x96;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 1);
|
|
maix::Bytes *dat0 = LT6911_i2c.readfrom(LT6911_ADDR, 2);
|
|
|
|
// Hactive
|
|
buf[0] = 0x8b;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 1);
|
|
maix::Bytes *dat1 = LT6911_i2c.readfrom(LT6911_ADDR, 2);
|
|
|
|
revbuf[0] = (uint8_t)dat0->data[0];
|
|
revbuf[1] = (uint8_t)dat0->data[1];
|
|
revbuf[2] = (uint8_t)dat1->data[0];
|
|
revbuf[3] = (uint8_t)dat1->data[1];
|
|
|
|
Vactive = (revbuf[0] << 8)|revbuf[1];
|
|
Hactive = (revbuf[2] << 8)|revbuf[3];
|
|
Hactive *= 2;
|
|
|
|
printf("HDMI res modification event\n");
|
|
printf("new res: %d * %d\n", Hactive, Vactive);
|
|
|
|
delete dat0;
|
|
delete dat1;
|
|
|
|
if (Vactive != 0 && Hactive != 0){
|
|
return 1;
|
|
} else {
|
|
return 0;
|
|
}
|
|
}
|
|
|
|
void lt6911_get_hdmi_clk()
|
|
{
|
|
uint8_t buf[2];
|
|
uint8_t revbuf[3];
|
|
uint32_t clk;
|
|
|
|
buf[0] = 0xff;
|
|
buf[1] = 0xa0;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 2);
|
|
|
|
buf[0] = 0x34;
|
|
buf[1] = 0x0b;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 2);
|
|
|
|
time::sleep_ms(50);
|
|
|
|
// clk
|
|
buf[0] = 0xff;
|
|
buf[1] = 0xb8;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 2);
|
|
|
|
buf[0] = 0xb1;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 1);
|
|
maix::Bytes *dat0 = LT6911_i2c.readfrom(LT6911_ADDR, 3);
|
|
|
|
revbuf[0] = (uint8_t)dat0->data[0];
|
|
revbuf[1] = (uint8_t)dat0->data[1];
|
|
revbuf[2] = (uint8_t)dat0->data[2];
|
|
revbuf[0] &= 0x07;
|
|
|
|
clk = revbuf[0];
|
|
clk <<= 8;
|
|
clk |= revbuf[1];
|
|
clk <<= 8;
|
|
clk |= revbuf[2];
|
|
|
|
printf("HDMI CLK = %d\n", clk);
|
|
|
|
delete dat0;
|
|
}
|
|
|
|
uint8_t lt6911_get_csi_res()
|
|
{
|
|
uint8_t ret = 0;
|
|
uint8_t buf[2];
|
|
uint8_t revbuf[4];
|
|
static uint16_t old_Vactive;
|
|
static uint16_t old_Hactive;
|
|
uint16_t Vactive;
|
|
uint16_t Hactive;
|
|
char Cmd[100]={0};
|
|
|
|
buf[0] = 0xff;
|
|
buf[1] = 0xc2;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 2);
|
|
|
|
// Vactive
|
|
buf[0] = 0x06;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 1);
|
|
maix::Bytes *dat0 = LT6911_i2c.readfrom(LT6911_ADDR, 2);
|
|
|
|
// Hactive
|
|
buf[0] = 0x38;
|
|
LT6911_i2c.writeto(LT6911_ADDR, buf, 1);
|
|
maix::Bytes *dat1 = LT6911_i2c.readfrom(LT6911_ADDR, 2);
|
|
|
|
revbuf[0] = (uint8_t)dat0->data[0];
|
|
revbuf[1] = (uint8_t)dat0->data[1];
|
|
revbuf[2] = (uint8_t)dat1->data[0];
|
|
revbuf[3] = (uint8_t)dat1->data[1];
|
|
|
|
Vactive = (revbuf[0] << 8)|revbuf[1];
|
|
Hactive = (revbuf[2] << 8)|revbuf[3];
|
|
|
|
if(old_Hactive != Hactive || old_Vactive != Vactive){
|
|
old_Hactive = Hactive;
|
|
old_Vactive = Vactive;
|
|
ret = 1;
|
|
}
|
|
|
|
printf("CSI res: %d * %d\n", Hactive, Vactive);
|
|
// setenv("KVM_CSI_HEIGHT", to_string(Hactive).c_str(), 1);
|
|
// setenv("KVM_CSI_WIDTH", to_string(Vactive).c_str(), 1);
|
|
|
|
sprintf(Cmd, "echo %d > /kvmapp/kvm/width", Hactive);
|
|
system(Cmd);
|
|
sprintf(Cmd, "echo %d > /kvmapp/kvm/height", Vactive);
|
|
system(Cmd);
|
|
|
|
delete dat0;
|
|
delete dat1;
|
|
|
|
return ret;
|
|
} |