Line 762:
Line 762:
== Device 5 & 6 ==
== Device 5 & 6 ==
−
LCD controllers for main/sub displays, most likely.
+
These are the chip-on-glass display controllers, also known as I2CLCD.
+
+
=== Shared registers ===
+
These registers are the same across all known I2CLCD controllers (except Controller ID 0x00).
{| class="wikitable" border="1"
{| class="wikitable" border="1"
! Register
! Register
−
! Width
! Name
! Name
+
! Valid bits
! Description
! Description
|-
|-
−
| 0x1
+
| 0x01
−
| 8
+
| Display enable
−
| ?
+
| 0x11
+
| Values:
+
+
- 0x00 - screen off, slow burn-in
+
- 0x01 - screen off, fast burn-in
+
- 0x10 - screen on, color input used
+
- 0x11 - screen on, color input not used, High-Z (display turns black or white depending on interface config)
+
|-
+
| 0x40
+
| Read address
|
|
+
| Write to this register to set the read address.
+
+
Reading from I2CLCD is non-standard. When you read, it returns pairs of the currently read address, and then the data byte at that address. The read address auto-increments.
+
|-
+
| 0x54
+
| Checksum? trigger
+
| 0x01
+
| When transitioning bit0 from 0 to 1, it seems to trigger some sort of checksum calcuation. Broken on controller 0x01, where it's oneshot.
+
|-
+
| 0x55
+
| ???
+
| 0x03 (all) /
+
0x07 (2DS)
+
| Unknown. When toggling 0x54 bit0 from 0 to 1, this register gets changed to 0x01 (all) / 0x05 (2DS).
+
+
This register is sometimes seen with a value of 0x02 at initialization time on the top screen.
+
|-
+
| 0x56
+
| Checksum?
+
|
+
| Unknown. Read-writable with no effect (old3DS) / read-only (all).
+
+
A random value is written here when 0x54 bit0 is changed from 0 to 1. Constantly updates with a seemingly random value, except on Controller ID 0x01, where it's oneshot/bugged.
+
|-
+
| 0x60
+
| ???
+
| 0x01
+
| Unknown. 0x00 is written here during init. Seems to have no effect.
+
|-
+
| 0x61
+
| Register checksum
+
|
+
| Some - but not all - register values are combined using an unknown algorithm into this register.
+
It's unknown which registers influence this value, as some registers which influence this value are read-only.
+
|-
+
| 0x62
+
| ???
+
| 0x01
+
| Unknown, does nothing on known controllers. During init, gsp waits for this to become 0x01.
+
|-
+
| 0xFE
+
| ???
+
|
+
| Unknown, does nothing. 0xAA is written here during init.
+
|-
+
| 0xFF
+
| Controller ID
+
|
+
| Upper 4bits is manufacturer. Lower 4bits is unknown, most likely revision, possibly encoded as a Johnson counter.
+
+
Known IDs:
+
- 0xC7 - new3DS, new3DSXL, new2DSXL, and some select newer old3DSXL
+
- 0xC3 - older old3DSXL
+
- 0xE1 - 2DS
+
- 0x10 - some select new3DS and new3DSXL with IPS screens
+
- 0x01 - old3DS
+
- 0x00 - unknown, gsp compares for this exact Controller ID for an alternate initialization path
+
+
Manufacturers:
+
- 0xC - SHARP (TN)
+
- 0x1 - JDI (LTPS IPS), found in select new3DS and new3DSXL consoles
+
- 0xE - unknown, found in 2DS only
+
- 0x0 - unknown, found in old3DS (non-XL) only
+
|}
+
+
=== Custom registers for controller 0x00 ===
+
This Controller ID is fully unknown, and the only reason we know about its existance is due to gsp having special handling code for it.
+
+
{| class="wikitable" border="1"
+
! Register
+
! Name
+
! Valid bits
+
! Description
|-
|-
| 0x11
| 0x11
−
| 8
+
| ???
−
| ?
+
|
+
| Unknown. Write 0x10 to initialize.
+
|-
+
| 0x50
+
| ???
|
|
+
| Unknown. Write 0x01 to initialize.
+
|}
+
+
=== Custom registers for controller 0x01 ===
+
+
{| class="wikitable" border="1"
+
! Register
+
! Name
+
! Valid bits
+
! Description
|-
|-
−
| 0x40
+
| 0x10
−
| 8
+
| Interface config
−
| CMD_IN/CMD_RESULT1
+
| 0xF7
−
| Write to trigger a command? Seen commands: 0xFF=Reset?, 0x62=IsFinished?. Result is stored in CMD_RESULT1:CMD_RESULT0.
+
| Regonfigures the input pins and pin behavior of the controller.
|-
|-
−
| 0x41
+
| 0x11
−
| 8
+
| Image config
−
| CMD_RESULT0
+
| 0x7F
−
| Read result
+
| Image filters and pixel clock control.
|-
|-
| 0x50
| 0x50
−
| 8
+
| ???
−
| ?
+
| 0x11
+
| Unknown. Has no effect on bottom screen. On the top screen, bit4 blanks out the display (LVDS disable?).
+
|-
+
| 0x53
+
| ???
+
| 0x73
+
| Unknown. While other bits seem to have no effect, bit0 kills the controller until a power cycle.
+
|}
+
+
=== Custom registers for controller 0xC3 ===
+
Basically the same as Controller ID 0xC7.
+
+
=== Custom registers for controller 0xC7 ===
+
This is the most common non-old3DS display controller. Quite overclockable.
+
+
{| class="wikitable" border="1"
+
! Register
+
! Name
+
! Valid bits
+
! Description
+
|-
+
| 0xAF
+
| Factory key
|
|
+
| Write 0xAA here to unlock factory controls.
+
|}
+
+
=== Custom registers for controller 0xE1 ===
+
This controller is designed to drive a split panel. As such, the factory controls have been slightly altered to accomodate this.
+
+
This is the only I2CLCD which responds on both I2CLCD addresses. The dominant screen is the bottom one.
+
+
{| class="wikitable" border="1"
+
! Register
+
! Name
+
! Valid bits
+
! Description
|-
|-
−
| 0x60
+
| 0xAF
−
| 8
+
| Factory key
−
| ?
+
|
+
| Write 0xAA here to unlock factory controls.
+
|}
+
+
=== Custom registers for controller 0x10 ===
+
JDI IPS controller. It's currently unknown how to unlock factory registers.
+
+
Factory mode registers:
+
{| class="wikitable" border="1"
+
! Register
+
! Name
+
! Valid bits
+
! Description
+
|-
+
| 0x70-0x7F
+
| Driving curve 1-1
+
|
+
|
+
|-
+
| 0x80-0x8F
+
| Driving curve 1-2
+
|
+
|
+
|-
+
| 0x90-0x9F
+
| Driving curve 2-1
+
|
+
|
+
|-
+
| 0xA0-0xAF
+
| Driving curve 2-2
+
|
+
|
+
|-
+
| 0xB0-0xBF
+
| Driving curve 3-1
+
|
|
|
|-
|-
−
| 0xFE
+
| 0xC0-0xCF
−
| 8
+
| Driving curve 3-2
−
| ?
+
|
|
|
|}
|}