Author Topic: nVIDIA ti4600 on 4k Monitor running FHD (EDID Simulator)  (Read 460 times)

Offline saturnu

  • Newcomer
  • *
  • Posts: 6
  • New Member
nVIDIA ti4600 on 4k Monitor running FHD (EDID Simulator)
« on: December 22, 2023, 07:57:38 AM »
Hi,

i recently flashed a "PC - PNY nVIDIA ti4600" with the help of the "GF Ti ROM Maker" into a MAC Card.
I'm not really sure but i thought i once flashed an asus v8460 with the arti rom and it worked with my monitors.
Maybe the pny card has an older firmware, but i wasn't keen enough to put the arti rom on it, in respect of different memory timings etc. (i don't know much about these cards).
Before this upgrade i was using an ati 9200 under os9 with no issues under a 1920x1080 resolution on my LG 4k Monitor.

I was goofing around with switchres2 without success, the monitor was recognized as 3840x2160 - without the possibility to select a lower resolution.
An old Samsung 24" fhd monitor was working out of the box and i was even able to "jumpstart" the 4k, by booting with it and hotplug the cable to the 4k monitor.

After this i bought a cheap edid feeder (16's bi -directional) with a rotary switch for different resolutions, but it only works on 720p for me.

I came across this project on hackaday, an edid inserter:
 https://hackaday.io/project/18634/instructions

The problem was, that i don't have the right i²c eeprom by hand, so why don't test it with an microcontroller first.
My starting point was this source, it uses the arduino wire library.
https://github.com/qbancoffee/edid_simulator

After editing the wire.h and twi.h buffer to 128 i edited the extension flag to 0 at the end of the first half of my dumped (Samsung) edid.
..and guess what, it didn't work.

The i2cdump command under linux just turncated the first 32 byte of the edid and i thought my arduino library changes didn't apply proberly, but it turned out that this was just an issue with the i2c-dev driver module, which is bound to a 32 byte smbus packet size.

The real problem was, that the extended edid was in fact needed in my case.
I tried to alter the wire lib buffer to 256 bytes, but the used variable seems to be signed, so i can't use all bits without other changes.
A quick and dirty fix was to split the 256 bytes edid in two 128 byte parts and to swap the outputed one to the extended part on the next readrequest.

Who knows, maybe this is a useful experience report for someone in the future.



Code: [Select]
#include <Wire.h>


/*
   In order for this program to work, the i2c transmit buffer length constants must be changed in
   two files. The Wire library has two buffers it uses for i2c transmissions

   "BUFFER_LENGTH" in
   "arduino_install_folder/hardware/arduino/avr/libraries/Wire/src/Wire.h" and

   "TWI_BUFFER_LENGTH" in
   "arduino_install_folder/hardware/arduino/avr/libraries/Wire/src/utility/twi.h"

   Both of these must be changed from 32 to 128 to be able to transmit the edid byte array in
   one shot.

   To test this program, you can directly wire SDA(pin 12),SCL(pin 15) and GND(pin 6) pins from your computers VGA port
   directly into the corresponding pins on the arduino.

*/


byte data = -1;
int counter = 0 ;
const int i2c_port = 0x50;
byte swap=0;

const byte edid[128] =
{ 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x4C, 0x2D, 0x45, 0x06, 0x34, 0x32, 0x55, 0x50,
  0x26, 0x14, 0x01, 0x03, 0x80, 0x34, 0x1D, 0x78, 0x2A, 0xEE, 0xD1, 0xA5, 0x55, 0x48, 0x9B, 0x26,
  0x12, 0x50, 0x54, 0xBF, 0xEF, 0x80, 0x81, 0x00, 0x81, 0x40, 0x81, 0x80, 0x95, 0x00, 0xA9, 0x40,
  0xB3, 0x00, 0x71, 0x4F, 0x95, 0x0F, 0x02, 0x3A, 0x80, 0x18, 0x71, 0x38, 0x2D, 0x40, 0x58, 0x2C,
  0x45, 0x00, 0x09, 0x25, 0x21, 0x00, 0x00, 0x1E, 0x00, 0x00, 0x00, 0xFD, 0x00, 0x38, 0x4B, 0x1E,
  0x51, 0x11, 0x00, 0x0A, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x00, 0x00, 0x00, 0xFC, 0x00, 0x53,
  0x4D, 0x42, 0x32, 0x34, 0x33, 0x30, 0x4C, 0x0A, 0x20, 0x20, 0x20, 0x20, 0x00, 0x00, 0x00, 0xFF,
  0x00, 0x48, 0x39, 0x58, 0x5A, 0x39, 0x30, 0x34, 0x36, 0x39, 0x38, 0x0A, 0x20, 0x20, 0x01, 0xE0
};

  const byte edid_ext[128] =
{ 0x02, 0x01, 0x04, 0x00, 0x02, 0x3A, 0x80, 0xD0, 0x72, 0x38, 0x2D, 0x40, 0x10, 0x2C, 0x45, 0x80,
  0x09, 0x25, 0x21, 0x00, 0x00, 0x1E, 0x01, 0x1D, 0x00, 0x72, 0x51, 0xD0, 0x1E, 0x20, 0x6E, 0x28,
  0x55, 0x00, 0x09, 0x25, 0x21, 0x00, 0x00, 0x1E, 0x01, 0x1D, 0x00, 0xBC, 0x52, 0xD0, 0x1E, 0x20,
  0xB8, 0x28, 0x55, 0x40, 0x09, 0x25, 0x21, 0x00, 0x00, 0x1E, 0x8C, 0x0A, 0xD0, 0x90, 0x20, 0x40,
  0x31, 0x20, 0x0C, 0x40, 0x55, 0x00, 0x09, 0x25, 0x21, 0x00, 0x00, 0x18, 0x8C, 0x0A, 0xD0, 0x8A,
  0x20, 0xE0, 0x2D, 0x10, 0x10, 0x3E, 0x96, 0x00, 0x09, 0x25, 0x21, 0x00, 0x00, 0x18, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
  0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x5E
};


void setup() {

  Wire.begin(i2c_port); // join i2c bus as slave
  Wire.onRequest(requestEvent); //event handler for requests from master
  Wire.onReceive(receiveData); // event handler when receiving from  master

}

void loop() {}

// function that executes whenever data is requested by master
// this function is registered as an event.
void requestEvent() {

  if(swap==0){
  Wire.write(edid, 128);
  swap=1;
  }else{
  Wire.write(edid_ext, 128);
  swap=0;
  }


}//end method
// function that executes whenever data is received by the slave


void receiveData(int byteCount) {


  while (Wire.available()) {
    data = Wire.read();
  }


}
« Last Edit: December 22, 2023, 08:48:19 AM by saturnu »