Wiimote
This is an old revision of this page, as edited by Hallowizer (talk | contribs) at 18:50, 2 December 2021. It may differ significantly from the current revision. |
This may require cleanup to meet WiiBrew's quality standards.
Reason: Make sections collapsable. Add a See Also section |
Please wikify this article or section. Help improve this article by adding relevant internal links. |
- This article is a technical guide to the Wii Remote. For a high-level overview of the Wii Remote, see the Wikipedia entry.
The Wii Remote (informally known as the Wiimote) is the Wii's main input device. It is a wireless device, using standard Bluetooth technology to communicate with the Wii. It is built around a Broadcom BCM2042 bluetooth System-on-a-chip, and contains multiple peripherals that provide data to it, as well as an expansion port for external add-ons. The Wii Remote uses (and, at times, abuses) the standard Bluetooth HID protocol to communicate with the host, which is directly based upon the USB HID standard. As such, it will appear as a standard input device to any Bluetooth host. However, the Wii Remote does not make use of the standard data types and HID descriptor, and only describes its report format length, leaving the actual contents undefined, which makes it useless with standard HID drivers (but some Wiimote Drivers exist). The Wii Remote actually uses a fairly complex set of operations, transmitted through HID Output reports, and returns a number of different data packets through its Input reports, which contain the data from its peripherals.
Summary
Reverse engineering and documenting all of the Wii Remote's features is a work in progress. Here are the known features and their status:
Bluetooth Communication | ![]() |
Connecting to the Wii Remote and listening for connections works. | ||||
Core Buttons | ![]() |
All working. | ||||
Accelerometer | ![]() |
All working. | ||||
IR Camera | ![]() |
All working. | ||||
Power Button | ![]() |
All working. | ||||
Speaker | ![]() |
All working. | ||||
Player LEDs | ![]() |
All working. | ||||
Status Information | ![]() |
Battery and extension info in Status Report | ||||
Extension Controllers | ![]() |
Official extensions are supported, however many 3rd party extensions are not understood. See Extension Controllers page | ||||
|
Protocol
See /Protocol
EEPROM Memory
There is a 128kbit (= 16kB) EEPROM chip (Data Sheet / Full EEPROM dump from a sample Wii Remote) in the Wii Remote. Part of its contents include code for the built-in microcontroller, and a generic section which can be freely read and written by the host. This section is 0x1700 bytes long, and part of this memory is used to store the Mii Data. It can be accessed by reading from/writing to addresses 0x0000-0x16FF in the Wii Remote's virtual memory space; in the actual EEPROM chip, the data is located at 0x0070-0x176F.
The firmware stored in the Wiimote has been disassembled.
The BCM2042 microcontroller built into the Wii Remote includes a large 108kb on-chip ROM section for storing firmware. If the EEPROM chip really contains code for the BCM2042 then this was probably done to make firmware updates possible, so there might be a way of accessing the other parts of the EEPROM via Bluetooth as well. From the BCM2042 Product Brief: "ROM-based design eliminates external flash memories; Flash option offered to support feature development".
On a virgin Wii Remote, acquired separately (not bundled with a Wii), that has never communicated with any device (except the PC used to dump the memory contents), most of the memory is blank (0x00). However, the first few bytes contain some information:
0000: A1 AA 8B 99 AE 9E 78 30 A7 74 D3 A1 AA 8B 99 AE 0010: 9E 78 30 A7 74 D3 82 82 82 15 9C 9C 9E 38 40 3E 0020: 82 82 82 15 9C 9C 9E 38 40 3E 00 00 00 00 00 00 0030: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
This can be better visualized as two sequences, each one repeated twice:
0000: A1 AA 8B 99 AE 9E 78 30 A7 74 D3 000B: A1 AA 8B 99 AE 9E 78 30 A7 74 D3 0016: 82 82 82 15 9C 9C 9E 38 40 3E 0020: 82 82 82 15 9C 9C 9E 38 40 3E
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 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).
Bit | |||||||||
Byte | 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 | |
0x00 | 0x0B | X 1<7:0> | |||||||
0x01 | 0x0C | Y 1<7:0> | |||||||
0x02 | 0x0D | Y 1<9:8> | X 1<9:8> | Y 2<9:8> | X 2<9:8> | ||||
0x03 | 0x0E | X 2<7:0> | |||||||
0x04 | 0x0F | Y 2<7:0> | |||||||
0x05 | 0x10 | X 3<7:0> | |||||||
0x06 | 0x11 | Y 3<7:0> | |||||||
0x07 | 0x12 | Y 3<9:8> | X 3<9:8> | Y 4<9:8> | X 4<9:8> | ||||
0x08 | 0x13 | X 4<7:0> | |||||||
0x09 | 0x14 | Y 4<7:0> | |||||||
0x0A | 0x15 | Checksum |
The data given above decodes to (0A1, 2AA), (399, 28B), (39E, 078), (0A7, 030).
ExpandAdditional examples |
---|
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.
Bit | |||||||||
Byte | 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 | |
0x16 | 0x20 | 0G X Acceleration<9:2> | |||||||
0x17 | 0x21 | 0G Y Acceleration<9:2> | |||||||
0x18 | 0x22 | 0G Z Acceleration<9:2> | |||||||
0x19 | 0x23 | 0 | 0G X Acc<1:0> | 0G Y Acc<1:0> | 0G Z Acc<1:0> | ||||
0x1A | 0x24 | 1G X Acceleration<9:2> | |||||||
0x1B | 0x25 | 1G Y Acceleration<9:2> | |||||||
0x1C | 0x26 | 1G Z Acceleration<9:2> | |||||||
0x1D | 0x27 | 0 | 1G X Acc<1:0> | 1G Y Acc<1:0> | 1G Z Acc<1:0> | ||||
0x1E | 0x28 | Motor | Volume | ||||||
0x1F | 0x29 | Checksum |
At 0x16D0, there is some more unknown data:
16D0: 00 00 00 FF 11 EE 00 00 33 CC 44 BB 00 00 66 99 16E0: 77 88 00 00 2B 01 E8 13 00 00 00 00 00 00 00 00 16F0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
In contrast to the data at 0x0000, this data seems to differ in only a few bytes between different Wii Remotes.
The "User Data" section appears to start with a 0x38-byte header, repeated twice (so 0x70 bytes total). The header starts with an 8-byte timestamp (from TBL and TBU; 1/60750000ths of a second since January 1 2000). That is followed by a 34-byte (17 characters, or 16 excluding the null terminator) Unicode name (which does not necessarily match the game's name), followed by the 4-byte game ID, then the application type (the value at 0x80003184). Then there is a checksum (at 0x2f), which is the sum of bytes 0 through 0x2e plus 0x55. Bytes 0x30 through 0x37 do not seem to be used and were all 0.
Known memory ranges are listed below.
Start | End | Length | Initial Value | Use |
0x0000 | 0x0029 | 0x002A | See above | Calibration values / pre-set data |
0x002A | 0x0FC9 | 0x0FA0 | Zeroed | User data / Unknown uses |
0x0FCA | 0x12B9 | 0x02f0 | Zeroed | Mii Data block 1 |
0x12BA | 0x15A9 | 0x02f0 | Zeroed | Mii Data block 2 |
0x15AA | 0x16CF | 0x0126 | Zeroed | Unknown / Unused |
0x16D0 | 0x16FF | 0x0030 | See above | Unknown data |
The top byte of the address is unused, which means memory is mirrored every 0x10000 bytes. Reading from unused addresses where the low 16 bits are >= 0x1700 will result in error returns.
Control Registers
The Wii Remote has several memory mapped register spaces corresponding to different peripherals in it. These include the Speaker, Extension Controllers, and the IR Camera.
Remember to set bit 2 (0x04) on the first byte of the Output Report, otherwise you'll overwrite EEPROM memory!
The peripheral to access is selected by the first byte of the address, and the lower 16 bits specify the register to access within that peripheral. The lowest bit of the high byte is ignored, which means every peripheral is mirrored at its address + 0x10000. Known peripherals are listed below:
Start | End | Use |
0xA20000 | 0xA20009 | Speaker settings |
0xA40000 | 0xA400FF | Extension Controller settings and data |
0xA60000 | 0xA600FF | Wii Motion Plus settings and data |
0xB00000 | 0xB00033 | IR Camera settings |
Most of these are also mirrored across the high bits of the individual peripheral. For example, the second byte of the address is ignored in the Extension controller address, which means any address of the form 0xA4xx00 will work (as will 0xA5xx00).
Input features
See /Input features.
Feedback Features
The Wii Remote sports three feedback features: Player LEDs, Rumble, and the Speaker.
Player LEDs
There are four blue LEDs on the front face of the Wii Remote. During discovery and before initialization, these LEDs blink at a fixed rate. The number of blinking LEDs is proportional to the battery voltage, indicating battery charge (all four are lit for newly charged batteries, and only the first is lit if the batteries are low and should be replaced).
During gameplay with the Wii, one LED is lit to indicate the player number assigned to the Wii Remote. However, the LEDs are independently controllable by the host, and can be set to display any pattern. They can also be modulated at a moderately high speed, enabling some brightness control at the cost of a lot of Bluetooth bandwidth. Sigma-delta modulation works reasonably well for this.
The LEDs can be controlled by sending a report with ID 0x11:
(a2) 11 LL
The high nybble of LL controls the four LEDs. Bit 4 of LL controls the first LED, and bit 7 controls the last:
Bit | Mask | LEDs | ||||
4 | 0x10 |
| ||||
5 | 0x20 |
| ||||
6 | 0x40 |
| ||||
7 | 0x80 |
|
Turning off all LEDs for an extended period of time is discouraged, as it might lead the user to believe the Wii Remote is turned off and disconnected, when in fact it is active.
The LEDs are surface mount parts, driven at 2.66 VDC.
Rumble
The Wii Remote includes a rumble feature, which is implemented as a small motor attached to an off-center weight. It will cause the controller to vibrate when activated.
The rumble motor is primarilly controlled via the report with ID 0x10:
(a2) 10 RR
Setting RR to 1 enables rumble, and setting it to 0 disables rumble. However, note that the rumble motor can be turned on or off through any of the Output Reports, not just 0x10. Setting the LSB (bit 0) of the first byte of any output report will activate the rumble motor, and unsetting it will deactivate it. For example, the following report will turn the rumble motor on:
(a2) 11 01
However, this will also have the side-effect of turning off all LEDs. The rumble bit needs to be set properly with every single report sent, to avoid inadvertently turning the rumble motor off.
Different photos of the rumble motor hardware show different markings. One example is SEM 8728DA. The Wii Remote drives it at 3.3 VDC and it draws 35 mA. It would be reasonable to think that the rumble motor could be removed and the motor replaced with another device with equal voltage and equal or less current draw.
Speaker
The Wii Remote has a small low-quality 21mm piezo-electric speaker, used for short sound effects during gameplay. The sound is streamed directly from the host, and the speaker has some adjustable parameters.
The speaker is controlled by using three output reports, together with a section of the register address space of the Wii Remote.
Report 0x14 is used to enable or disable the speaker. Setting bit 2 will enable the speaker, and clearing it will disable it. For example, to enable the speaker, send:
(a2) 14 04
Report 0x19 is used to mute or unmute the speaker, and works identically to report 0x14. 0x04 will mute the speaker, and 0x00 will unmute it.
Report 0x18 is used to send speaker data. 1-20 bytes may be sent at once:
(a2) 18 LL DD DD DD DD DD DD DD DD DD DD DD DD DD DD DD DD DD DD DD DD
LL specifies the data length, shifted left by three bits. The DD bytes are the speaker data. To fullfill the report length requirements, the data must be padded if it is less than 20 bytes long. Sound data must be sent at the proper rate.
Initialization Sequence
Remember to set bit 2 (0x04) on the first byte of the Output Reports to write to registers!
The following sequence will initialize the speaker:
- Enable speaker (Send 0x04 to Output Report 0x14)
- Mute speaker (Send 0x04 to Output Report 0x19)
- Write 0x01 to register 0xa20009
- Write 0x08 to register 0xa20001
- Write 7-byte configuration to registers 0xa20001-0xa20008
- Write 0x01 to register 0xa20008
- Unmute speaker (Send 0x00 to Output Report 0x19)
Speaker Configuration
7 bytes control the speaker settings, including volume. The full purpose of these bytes is not known, but the following values seem to produce some sound:
00 FF RR RR VV 00 00
RR RR specify the sample rate (little-endian format), using the following formulae:
pcm_sample_rate = 12000000 / rate_value adpcm_sample_rate = 6000000 / rate_value
The standard value is 0x7d0, for 3000Hz 4-bit PCM
FF configures the data format. Setting it to 0x40 configures the speaker to use signed 8-bit PCM, while setting it to 0x00 configures it to use 4-bit Yamaha ADPCM. VV specifies the volume, which has a range of 0x00-0xFF for 8-bit mode, and 0x00-0x40 for 4-bit mode.
This configuration can be used to play 4-bit ADPCM sound at 3000Hz:
00 00 D0 07 40 00 00
This configuration can be used to play 8-bit PCM sound at 1500Hz sample rate:
00 40 40 1f 40 00 00
It looks like the best compromise between sample rate and slow bluetooth chipsets / drivers is playing 8-bit PCM at 2000Hz, so a new 20-byte chunk of audio data is sent every 10 milliseconds.
00 40 70 17 60 00 00
Sound Data Format
The Wii Remote can use multiple sound formats at multiple sampling rates. PC drivers currently seem unable to keep up with the higher rates.
The 4-bit ADPCM is Yamaha ADPCM (for example, as implemented in ffmpeg).
8-bit signed PCM mode works, but when in 8-bit mode the sampling frequency must be made so low that the audio quality is pretty bad.
Extension Controllers
Notes
See Also
- Disassembled Firmware shows raw firmware dumps from several wiimotes.
- Extension Controllers explains the protocol used by the wiimote extensions.
- Motion analysis gives hints how to implement accelerometer parsers.
- Pointing shows how to create a pointing device with IR data.
- Library lists several wiimote library implementations.
- Mii Data shows raw wiimote data dumps.
Acknowledgements
Some of the information here is based on the documentation at Wiili