Line 474:
Line 474:
These are two blocks of calibration data (for redundancy), where the last byte of each is a checksum (all prior bytes plus 0x55). Nintendo's libraries will only use a calibration block if its checksum is correct, falling back to the second one if the first one is incorrect, and falling back to default values otherwise.
These are two blocks of calibration data (for redundancy), where the last byte of each is a checksum (all prior bytes plus 0x55). Nintendo's libraries will only use a calibration block if its checksum is correct, falling back to the second one if the first one is incorrect, and falling back to default values otherwise.
−
The first block contains calibration data related to the IR camera. The format of this data and its significance has not been investigated yet.
+
The first block contains calibration data related to the IR camera: the position of 4 reference values. Nintendo's code uses this to compute a center offset, scale, and possibly an angle offset. It also looks like the values could appear in any order; code exists to check for values in each quadrant (below and above x=512 and y=384).
+
+
{| style="border-collapse: collapse; padding: 0.2em 0.2em 0.2em 0.2em; text-align: center;"
+
|- style="background-color: #ddd;"
+
| style="background-color: #fff;" colspan="2" |
+
| style="border: 1px solid #ccc; padding: 0.2em; text-align: center;" colspan="8"| '''Bit'''
+
|- style="background-color: #cdc;"
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #ddd;" colspan="2" | '''Byte'''
+
| style="border: 1px solid #ccc; padding: 0.2em; width:3.3em;" | '''7'''
+
| style="border: 1px solid #ccc; padding: 0.2em; width:3.3em;" | '''6'''
+
| style="border: 1px solid #ccc; padding: 0.2em; width:3.3em;" | '''5'''
+
| style="border: 1px solid #ccc; padding: 0.2em; width:3.3em;" | '''4'''
+
| style="border: 1px solid #ccc; padding: 0.2em; width:3.3em;" | '''3'''
+
| style="border: 1px solid #ccc; padding: 0.2em; width:3.3em;" | '''2'''
+
| style="border: 1px solid #ccc; padding: 0.2em; width:3.3em;" | '''1'''
+
| style="border: 1px solid #ccc; padding: 0.2em; width:3.3em;" | '''0'''
+
|- style="background-color: #ded;"
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x00
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x0B
+
| style="border: 1px solid #ccc; padding: 0.2em;" colspan="8" | '''X 1'''<span style="color: #777;"><<span style="color: #c00;">7:0</span>></span>
+
|- style="background-color: #ded;"
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x01
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x0C
+
| style="border: 1px solid #ccc; padding: 0.2em;" colspan="8" | '''Y 1'''<span style="color: #777;"><<span style="color: #c00;">7:0</span>></span>
+
|- style="background-color: #ded;"
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x02
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x0D
+
| style="border: 1px solid #ccc; padding: 0.2em;" colspan="2" | '''Y 1'''<span style="color: #777;"><<span style="color: #c00;">9:8</span>></span>
+
| style="border: 1px solid #ccc; padding: 0.2em;" colspan="2" | '''X 1'''<span style="color: #777;"><<span style="color: #c00;">9:8</span>></span>
+
| style="border: 1px solid #ccc; padding: 0.2em;" colspan="2" | '''Y 2'''<span style="color: #777;"><<span style="color: #c00;">9:8</span>></span>
+
| style="border: 1px solid #ccc; padding: 0.2em;" colspan="2" | '''X 2'''<span style="color: #777;"><<span style="color: #c00;">9:8</span>></span>
+
|- style="background-color: #ded;"
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x03
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x0E
+
| style="border: 1px solid #ccc; padding: 0.2em;" colspan="8" | '''X 2'''<span style="color: #777;"><<span style="color: #c00;">7:0</span>></span>
+
|- style="background-color: #ded;"
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x04
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x0F
+
| style="border: 1px solid #ccc; padding: 0.2em;" colspan="8" | '''Y 2'''<span style="color: #777;"><<span style="color: #c00;">7:0</span>></span>
+
|- style="background-color: #ded;"
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x05
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x10
+
| style="border: 1px solid #ccc; padding: 0.2em;" colspan="8" | '''X 3'''<span style="color: #777;"><<span style="color: #c00;">7:0</span>></span>
+
|- style="background-color: #ded;"
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x06
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x11
+
| style="border: 1px solid #ccc; padding: 0.2em;" colspan="8" | '''Y 3'''<span style="color: #777;"><<span style="color: #c00;">7:0</span>></span>
+
|- style="background-color: #ded;"
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x07
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x12
+
| style="border: 1px solid #ccc; padding: 0.2em;" colspan="2" | '''Y 3'''<span style="color: #777;"><<span style="color: #c00;">9:8</span>></span>
+
| style="border: 1px solid #ccc; padding: 0.2em;" colspan="2" | '''X 3'''<span style="color: #777;"><<span style="color: #c00;">9:8</span>></span>
+
| style="border: 1px solid #ccc; padding: 0.2em;" colspan="2" | '''Y 4'''<span style="color: #777;"><<span style="color: #c00;">9:8</span>></span>
+
| style="border: 1px solid #ccc; padding: 0.2em;" colspan="2" | '''X 4'''<span style="color: #777;"><<span style="color: #c00;">9:8</span>></span>
+
|- style="background-color: #ded;"
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x08
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x13
+
| style="border: 1px solid #ccc; padding: 0.2em;" colspan="8" | '''X 4'''<span style="color: #777;"><<span style="color: #c00;">7:0</span>></span>
+
|- style="background-color: #ded;"
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x09
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x14
+
| style="border: 1px solid #ccc; padding: 0.2em;" colspan="8" | '''Y 4'''<span style="color: #777;"><<span style="color: #c00;">7:0</span>></span>
+
|- style="background-color: #ded;"
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x0A
+
| style="border: 1px solid #ccc; padding: 0.2em; background-color: #eee;" | 0x15
+
| style="border: 1px solid #ccc; padding: 0.2em;" colspan="8" | '''Checksum'''
+
|}
The four bytes starting at 0x0016 and 0x0020 store the calibrated zero offsets for the accelerometer (high 8 bits of X,Y,Z in the first three bytes, low 2 bits packed in the fourth byte as --XXYYZZ). The four bytes at 0x001A and 0x24 store the force of gravity on those axes. The byte at 0x1e and 0x28 seems to be unused, but apparently used to contain flags related to the speaker volume and the rumble motor (Nintendo games will print a debug message related to it but do not seem to use the value elsewhere). On all checked remotes, that byte has been 0x40.
The four bytes starting at 0x0016 and 0x0020 store the calibrated zero offsets for the accelerometer (high 8 bits of X,Y,Z in the first three bytes, low 2 bits packed in the fourth byte as --XXYYZZ). The four bytes at 0x001A and 0x24 store the force of gravity on those axes. The byte at 0x1e and 0x28 seems to be unused, but apparently used to contain flags related to the speaker volume and the rumble motor (Nintendo games will print a debug message related to it but do not seem to use the value elsewhere). On all checked remotes, that byte has been 0x40.