modified to compile for me
Fork of USBHostXpad by
USBHostXpad.cpp@5:e0ed758abbdb, 2016-11-04 (annotated)
- Committer:
- Ownasaurus
- Date:
- Fri Nov 04 21:29:16 2016 +0000
- Revision:
- 5:e0ed758abbdb
- Parent:
- 4:4254192898a9
- Child:
- 6:954ecd99709c
support afterglow wired 360 controller
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
okini3939 | 0:bd0f6bf72a8b | 1 | /* |
okini3939 | 0:bd0f6bf72a8b | 2 | * Xbox 360 Wireless Controller for Windows library |
okini3939 | 0:bd0f6bf72a8b | 3 | * for mbed USBHost library |
okini3939 | 0:bd0f6bf72a8b | 4 | * Copyright (c) 2013 Hiroshi Suga |
okini3939 | 0:bd0f6bf72a8b | 5 | * |
okini3939 | 0:bd0f6bf72a8b | 6 | * VID=0x045e PID=0x0719 |
okini3939 | 0:bd0f6bf72a8b | 7 | * |
okini3939 | 1:5bb153989f33 | 8 | * Reference: |
okini3939 | 3:53ce7778a155 | 9 | * https://github.com/Grumbel/xboxdrv/blob/master/PROTOCOL |
okini3939 | 3:53ce7778a155 | 10 | * http://tattiebogle.net/index.php/ProjectRoot/Xbox360Controller |
okini3939 | 0:bd0f6bf72a8b | 11 | */ |
okini3939 | 0:bd0f6bf72a8b | 12 | |
okini3939 | 0:bd0f6bf72a8b | 13 | #include "USBHostXpad.h" |
okini3939 | 0:bd0f6bf72a8b | 14 | |
okini3939 | 0:bd0f6bf72a8b | 15 | #if 1 or USBHOST_XPAD |
okini3939 | 0:bd0f6bf72a8b | 16 | |
okini3939 | 0:bd0f6bf72a8b | 17 | #include "dbg.h" |
okini3939 | 0:bd0f6bf72a8b | 18 | |
okini3939 | 0:bd0f6bf72a8b | 19 | #define DEVICE_TO_HOST 0x80 |
okini3939 | 0:bd0f6bf72a8b | 20 | #define HOST_TO_DEVICE 0x00 |
okini3939 | 0:bd0f6bf72a8b | 21 | |
okini3939 | 0:bd0f6bf72a8b | 22 | USBHostXpad::USBHostXpad() |
okini3939 | 0:bd0f6bf72a8b | 23 | { |
okini3939 | 0:bd0f6bf72a8b | 24 | host = USBHost::getHostInst(); |
okini3939 | 0:bd0f6bf72a8b | 25 | init(); |
okini3939 | 0:bd0f6bf72a8b | 26 | } |
okini3939 | 0:bd0f6bf72a8b | 27 | |
okini3939 | 0:bd0f6bf72a8b | 28 | void USBHostXpad::init() { |
okini3939 | 0:bd0f6bf72a8b | 29 | dev_connected = false; |
okini3939 | 0:bd0f6bf72a8b | 30 | dev = NULL; |
okini3939 | 0:bd0f6bf72a8b | 31 | int_in = NULL; |
okini3939 | 0:bd0f6bf72a8b | 32 | int_out = NULL; |
okini3939 | 0:bd0f6bf72a8b | 33 | xpad_intf = -1; |
okini3939 | 0:bd0f6bf72a8b | 34 | xpad_device_found = false; |
okini3939 | 0:bd0f6bf72a8b | 35 | nb_ep = 0; |
okini3939 | 3:53ce7778a155 | 36 | dev_type = TYPE_UNKNOWN; |
okini3939 | 3:53ce7778a155 | 37 | dev_started = false; |
okini3939 | 0:bd0f6bf72a8b | 38 | } |
okini3939 | 0:bd0f6bf72a8b | 39 | |
okini3939 | 0:bd0f6bf72a8b | 40 | bool USBHostXpad::connected() |
okini3939 | 0:bd0f6bf72a8b | 41 | { |
okini3939 | 0:bd0f6bf72a8b | 42 | return dev_connected; |
okini3939 | 0:bd0f6bf72a8b | 43 | } |
okini3939 | 0:bd0f6bf72a8b | 44 | |
okini3939 | 0:bd0f6bf72a8b | 45 | bool USBHostXpad::connect() |
okini3939 | 0:bd0f6bf72a8b | 46 | { |
okini3939 | 0:bd0f6bf72a8b | 47 | |
okini3939 | 0:bd0f6bf72a8b | 48 | if (dev_connected) { |
okini3939 | 0:bd0f6bf72a8b | 49 | return true; |
okini3939 | 0:bd0f6bf72a8b | 50 | } |
okini3939 | 0:bd0f6bf72a8b | 51 | |
okini3939 | 3:53ce7778a155 | 52 | for (int i = 0; i < MAX_DEVICE_CONNECTED; i++) { |
okini3939 | 0:bd0f6bf72a8b | 53 | if ((dev = host->getDevice(i)) != NULL) { |
okini3939 | 0:bd0f6bf72a8b | 54 | |
okini3939 | 0:bd0f6bf72a8b | 55 | USB_DBG("Trying to connect MSD device\r\n"); |
okini3939 | 0:bd0f6bf72a8b | 56 | |
okini3939 | 3:53ce7778a155 | 57 | if(host->enumerate(dev, this)) break; |
okini3939 | 0:bd0f6bf72a8b | 58 | |
okini3939 | 0:bd0f6bf72a8b | 59 | if (xpad_device_found) { |
okini3939 | 0:bd0f6bf72a8b | 60 | int_in = dev->getEndpoint(xpad_intf, INTERRUPT_ENDPOINT, IN); |
okini3939 | 0:bd0f6bf72a8b | 61 | int_out = dev->getEndpoint(xpad_intf, INTERRUPT_ENDPOINT, OUT); |
okini3939 | 0:bd0f6bf72a8b | 62 | |
okini3939 | 3:53ce7778a155 | 63 | if (!int_in || !int_out) continue; |
okini3939 | 0:bd0f6bf72a8b | 64 | |
Ownasaurus | 5:e0ed758abbdb | 65 | USB_INFO("New Xpad device: VID:%04x PID:%04x [dev: %p - intf: %d]", dev->getVid(), dev->getPid(), dev, xpad_intf); |
okini3939 | 0:bd0f6bf72a8b | 66 | dev->setName("XPAD", xpad_intf); |
okini3939 | 0:bd0f6bf72a8b | 67 | host->registerDriver(dev, xpad_intf, this, &USBHostXpad::init); |
okini3939 | 1:5bb153989f33 | 68 | int_in->attach(this, &USBHostXpad::rxHandler); |
okini3939 | 1:5bb153989f33 | 69 | host->interruptRead(dev, int_in, report, int_in->getSize(), false); |
okini3939 | 0:bd0f6bf72a8b | 70 | |
Ownasaurus | 5:e0ed758abbdb | 71 | wait_ms(100); |
okini3939 | 2:2749f4e649db | 72 | led(LED_OFF); |
okini3939 | 0:bd0f6bf72a8b | 73 | dev_connected = true; |
okini3939 | 0:bd0f6bf72a8b | 74 | return true; |
okini3939 | 0:bd0f6bf72a8b | 75 | } |
okini3939 | 0:bd0f6bf72a8b | 76 | |
okini3939 | 1:5bb153989f33 | 77 | } |
okini3939 | 1:5bb153989f33 | 78 | } |
okini3939 | 0:bd0f6bf72a8b | 79 | init(); |
okini3939 | 0:bd0f6bf72a8b | 80 | return false; |
okini3939 | 0:bd0f6bf72a8b | 81 | } |
okini3939 | 0:bd0f6bf72a8b | 82 | |
okini3939 | 0:bd0f6bf72a8b | 83 | void USBHostXpad::rxHandler() { |
okini3939 | 0:bd0f6bf72a8b | 84 | int len_listen = int_in->getSize(); |
okini3939 | 0:bd0f6bf72a8b | 85 | int len = int_in->getLengthTransferred(); |
okini3939 | 0:bd0f6bf72a8b | 86 | |
Ownasaurus | 5:e0ed758abbdb | 87 | |
Ownasaurus | 5:e0ed758abbdb | 88 | /*for (int i = 0; i < len_listen; i ++) { |
okini3939 | 0:bd0f6bf72a8b | 89 | std::printf(" %02x", report[i]); |
okini3939 | 0:bd0f6bf72a8b | 90 | } |
Ownasaurus | 5:e0ed758abbdb | 91 | std::printf("\r\n");*/ |
Ownasaurus | 5:e0ed758abbdb | 92 | |
Ownasaurus | 5:e0ed758abbdb | 93 | |
okini3939 | 3:53ce7778a155 | 94 | if (dev_type == TYPE_XBOX) { |
okini3939 | 3:53ce7778a155 | 95 | parseMessage(); |
okini3939 | 3:53ce7778a155 | 96 | } else |
okini3939 | 3:53ce7778a155 | 97 | if (report[0] == 0x08) { |
Ownasaurus | 5:e0ed758abbdb | 98 | if (report[1] == 0x80 || /*x360 headset status*/report[1] == 0x80) { |
okini3939 | 3:53ce7778a155 | 99 | // Connection Status Messages |
okini3939 | 3:53ce7778a155 | 100 | start(); |
okini3939 | 3:53ce7778a155 | 101 | } else |
okini3939 | 3:53ce7778a155 | 102 | if (report[1] == 0x00) { |
okini3939 | 3:53ce7778a155 | 103 | // Disconnected Status Messages |
okini3939 | 3:53ce7778a155 | 104 | dev_started = false; |
okini3939 | 3:53ce7778a155 | 105 | } |
okini3939 | 0:bd0f6bf72a8b | 106 | } else |
Ownasaurus | 5:e0ed758abbdb | 107 | if (report[0] == 0x01) { // X360 led |
Ownasaurus | 5:e0ed758abbdb | 108 | ; // no need to do anything? |
Ownasaurus | 5:e0ed758abbdb | 109 | } else |
Ownasaurus | 5:e0ed758abbdb | 110 | if (report[0] == 0x02) { // X360 unknown |
Ownasaurus | 5:e0ed758abbdb | 111 | ; // no need to do anything? |
Ownasaurus | 5:e0ed758abbdb | 112 | } else |
Ownasaurus | 5:e0ed758abbdb | 113 | if (report[0] == 0x03) { // X360 rumble |
Ownasaurus | 5:e0ed758abbdb | 114 | ; // no need to do anything? |
Ownasaurus | 5:e0ed758abbdb | 115 | } else |
okini3939 | 3:53ce7778a155 | 116 | if (report[0] == 0x00) { |
okini3939 | 3:53ce7778a155 | 117 | if ((report[1] == 0x14) || |
okini3939 | 3:53ce7778a155 | 118 | (report[1] == 0x01 && report[2] == 0x00 && report[3] == 0xf0)) { |
okini3939 | 3:53ce7778a155 | 119 | // Event data |
okini3939 | 3:53ce7778a155 | 120 | parseMessage(); |
okini3939 | 3:53ce7778a155 | 121 | } else |
okini3939 | 3:53ce7778a155 | 122 | if (report[1] == 0x0f) { |
okini3939 | 3:53ce7778a155 | 123 | // On connection |
okini3939 | 3:53ce7778a155 | 124 | led(LED1_ON); |
okini3939 | 3:53ce7778a155 | 125 | start(); |
okini3939 | 3:53ce7778a155 | 126 | dev_started = true; |
okini3939 | 3:53ce7778a155 | 127 | } else |
okini3939 | 3:53ce7778a155 | 128 | if (report[1] == 0x00) { |
okini3939 | 3:53ce7778a155 | 129 | if (report[3] == 0x13) { |
okini3939 | 3:53ce7778a155 | 130 | // Battery charge level |
okini3939 | 3:53ce7778a155 | 131 | battery = report[4]; |
okini3939 | 3:53ce7778a155 | 132 | } else |
okini3939 | 3:53ce7778a155 | 133 | if (report[3] == 0xf0) { |
okini3939 | 3:53ce7778a155 | 134 | // Device low power mode (HID updates will stop until controller inputs change) |
okini3939 | 4:4254192898a9 | 135 | // restart(); |
okini3939 | 3:53ce7778a155 | 136 | } |
okini3939 | 3:53ce7778a155 | 137 | } else |
okini3939 | 3:53ce7778a155 | 138 | if (report[1] == 0xf8) { |
okini3939 | 3:53ce7778a155 | 139 | // Status Messages ? |
okini3939 | 3:53ce7778a155 | 140 | } |
okini3939 | 3:53ce7778a155 | 141 | } else { |
okini3939 | 1:5bb153989f33 | 142 | // Unknown |
okini3939 | 1:5bb153989f33 | 143 | USB_INFO("rxHandler len:%d data:%02x %02x %02x %02x", len, report[0], report[1], report[2], report[3]); |
okini3939 | 0:bd0f6bf72a8b | 144 | } |
okini3939 | 0:bd0f6bf72a8b | 145 | |
okini3939 | 3:53ce7778a155 | 146 | if (dev) { |
okini3939 | 3:53ce7778a155 | 147 | host->interruptRead(dev, int_in, report, len_listen, false); |
okini3939 | 0:bd0f6bf72a8b | 148 | } |
okini3939 | 0:bd0f6bf72a8b | 149 | } |
okini3939 | 0:bd0f6bf72a8b | 150 | |
okini3939 | 0:bd0f6bf72a8b | 151 | /*virtual*/ void USBHostXpad::setVidPid(uint16_t vid, uint16_t pid) |
okini3939 | 0:bd0f6bf72a8b | 152 | { |
okini3939 | 0:bd0f6bf72a8b | 153 | // we don't check VID/PID for MSD driver |
okini3939 | 3:53ce7778a155 | 154 | if (vid == 0x045e && (pid == 0x0202 || pid == 0x0285 || pid == 0x0287 || pid == 0x0289)) { |
okini3939 | 3:53ce7778a155 | 155 | dev_type = TYPE_XBOX; |
okini3939 | 3:53ce7778a155 | 156 | } else |
Ownasaurus | 5:e0ed758abbdb | 157 | if ((vid == 0x045e && pid == 0x028e) || /*my afterglow addition!*/(vid == 0x0e6f && pid == 0x0213)) { |
okini3939 | 3:53ce7778a155 | 158 | dev_type = TYPE_XBOX360; |
okini3939 | 3:53ce7778a155 | 159 | } else |
okini3939 | 3:53ce7778a155 | 160 | if (vid == 0x045e && pid == 0x0719) { |
okini3939 | 3:53ce7778a155 | 161 | dev_type = TYPE_XBOX360W; |
okini3939 | 3:53ce7778a155 | 162 | } |
okini3939 | 3:53ce7778a155 | 163 | USB_INFO("setVidPid vid:%04x pid:%04x xbox:%d", vid, pid, dev_type); |
okini3939 | 0:bd0f6bf72a8b | 164 | } |
okini3939 | 0:bd0f6bf72a8b | 165 | |
okini3939 | 0:bd0f6bf72a8b | 166 | /*virtual*/ bool USBHostXpad::parseInterface(uint8_t intf_nb, uint8_t intf_class, uint8_t intf_subclass, uint8_t intf_protocol) //Must return true if the interface should be parsed |
okini3939 | 0:bd0f6bf72a8b | 167 | { |
okini3939 | 0:bd0f6bf72a8b | 168 | USB_INFO("parseInterface class:%02x subclass:%02x protocol:%02x [nb: %d - intf: %d]", intf_class, intf_subclass, intf_protocol, intf_nb, xpad_intf); |
okini3939 | 3:53ce7778a155 | 169 | if ((xpad_intf == -1) && (intf_class == 0x58) && (intf_subclass == 0x42) && (intf_protocol == 0x00)) { |
okini3939 | 3:53ce7778a155 | 170 | xpad_intf = intf_nb; // XBOX ? |
okini3939 | 3:53ce7778a155 | 171 | return true; |
okini3939 | 3:53ce7778a155 | 172 | } |
okini3939 | 3:53ce7778a155 | 173 | if ((xpad_intf == -1) && (intf_class == 0xff) && (intf_subclass == 0x5d) && (intf_protocol == 0x81)) { |
okini3939 | 3:53ce7778a155 | 174 | xpad_intf = intf_nb; // XBOX360W |
okini3939 | 0:bd0f6bf72a8b | 175 | return true; |
okini3939 | 0:bd0f6bf72a8b | 176 | } |
Ownasaurus | 5:e0ed758abbdb | 177 | if ((xpad_intf == -1) && (intf_class == 0xff) && (intf_subclass == 0x5d) && (intf_protocol == 0x01)) { |
Ownasaurus | 5:e0ed758abbdb | 178 | xpad_intf = intf_nb; // XBOX360 WIRED AFTERGLOW |
Ownasaurus | 5:e0ed758abbdb | 179 | return true; |
Ownasaurus | 5:e0ed758abbdb | 180 | } |
okini3939 | 0:bd0f6bf72a8b | 181 | return false; |
okini3939 | 0:bd0f6bf72a8b | 182 | } |
okini3939 | 0:bd0f6bf72a8b | 183 | |
okini3939 | 0:bd0f6bf72a8b | 184 | /*virtual*/ bool USBHostXpad::useEndpoint(uint8_t intf_nb, ENDPOINT_TYPE type, ENDPOINT_DIRECTION dir) //Must return true if the endpoint will be used |
okini3939 | 0:bd0f6bf72a8b | 185 | { |
okini3939 | 0:bd0f6bf72a8b | 186 | USB_INFO("useEndpoint nb:%d type:%d dir:%d", intf_nb, type, dir); |
okini3939 | 0:bd0f6bf72a8b | 187 | if (intf_nb == xpad_intf) { |
okini3939 | 0:bd0f6bf72a8b | 188 | if (type == INTERRUPT_ENDPOINT) { |
okini3939 | 0:bd0f6bf72a8b | 189 | nb_ep ++; |
okini3939 | 3:53ce7778a155 | 190 | if (nb_ep == 2) { |
okini3939 | 0:bd0f6bf72a8b | 191 | xpad_device_found = true; |
okini3939 | 3:53ce7778a155 | 192 | } |
okini3939 | 0:bd0f6bf72a8b | 193 | return true; |
okini3939 | 0:bd0f6bf72a8b | 194 | } |
okini3939 | 0:bd0f6bf72a8b | 195 | } |
okini3939 | 0:bd0f6bf72a8b | 196 | return false; |
okini3939 | 0:bd0f6bf72a8b | 197 | } |
okini3939 | 0:bd0f6bf72a8b | 198 | |
okini3939 | 3:53ce7778a155 | 199 | |
okini3939 | 3:53ce7778a155 | 200 | void USBHostXpad::parseMessage() |
okini3939 | 0:bd0f6bf72a8b | 201 | { |
okini3939 | 3:53ce7778a155 | 202 | uint8_t *data = report; |
okini3939 | 3:53ce7778a155 | 203 | |
okini3939 | 3:53ce7778a155 | 204 | switch (dev_type) { |
okini3939 | 3:53ce7778a155 | 205 | case TYPE_XBOX: |
okini3939 | 3:53ce7778a155 | 206 | buttons = ((uint32_t)report[3] << 8) | report[2]; |
okini3939 | 3:53ce7778a155 | 207 | if (report[4]) buttons |= XPAD_PAD_A; |
okini3939 | 3:53ce7778a155 | 208 | if (report[5]) buttons |= XPAD_PAD_B; |
okini3939 | 3:53ce7778a155 | 209 | if (report[6]) buttons |= XPAD_PAD_X; |
okini3939 | 3:53ce7778a155 | 210 | if (report[7]) buttons |= XPAD_PAD_Y; |
okini3939 | 3:53ce7778a155 | 211 | trigger_l = data[10]; |
okini3939 | 3:53ce7778a155 | 212 | trigger_r = data[11]; |
okini3939 | 3:53ce7778a155 | 213 | |
okini3939 | 3:53ce7778a155 | 214 | stick_lx = ((int16_t)report[13] << 8) | report[12]; |
okini3939 | 3:53ce7778a155 | 215 | stick_ly = ((int16_t)report[15] << 8) | report[14]; |
okini3939 | 3:53ce7778a155 | 216 | stick_rx = ((int16_t)report[17] << 8) | report[16]; |
okini3939 | 3:53ce7778a155 | 217 | stick_ry = ((int16_t)report[19] << 8) | report[18]; |
okini3939 | 3:53ce7778a155 | 218 | break; |
okini3939 | 3:53ce7778a155 | 219 | case TYPE_XBOX360W: |
okini3939 | 3:53ce7778a155 | 220 | data += 4; |
okini3939 | 3:53ce7778a155 | 221 | case TYPE_XBOX360: |
okini3939 | 3:53ce7778a155 | 222 | buttons = ((uint32_t)data[3] << 8) | data[2]; |
okini3939 | 3:53ce7778a155 | 223 | trigger_l = data[4]; |
okini3939 | 3:53ce7778a155 | 224 | trigger_r = data[5]; |
okini3939 | 3:53ce7778a155 | 225 | |
okini3939 | 3:53ce7778a155 | 226 | stick_lx = ((int16_t)data[7] << 8) | data[6]; |
okini3939 | 3:53ce7778a155 | 227 | stick_ly = ((int16_t)data[9] << 8) | data[8]; |
okini3939 | 3:53ce7778a155 | 228 | stick_rx = ((int16_t)data[11] << 8) | data[10]; |
okini3939 | 3:53ce7778a155 | 229 | stick_ry = ((int16_t)data[13] << 8) | data[12]; |
okini3939 | 3:53ce7778a155 | 230 | break; |
okini3939 | 3:53ce7778a155 | 231 | default: |
okini3939 | 2:2749f4e649db | 232 | return; |
okini3939 | 2:2749f4e649db | 233 | } |
Ownasaurus | 5:e0ed758abbdb | 234 | |
okini3939 | 3:53ce7778a155 | 235 | if (onUpdate) { |
okini3939 | 3:53ce7778a155 | 236 | (*onUpdate)(buttons, stick_lx, stick_ly, stick_rx, stick_ry, trigger_l, trigger_r); |
okini3939 | 3:53ce7778a155 | 237 | } |
okini3939 | 0:bd0f6bf72a8b | 238 | } |
okini3939 | 0:bd0f6bf72a8b | 239 | |
okini3939 | 3:53ce7778a155 | 240 | bool USBHostXpad::restart () |
okini3939 | 0:bd0f6bf72a8b | 241 | { |
okini3939 | 1:5bb153989f33 | 242 | unsigned char odata[32]; |
okini3939 | 1:5bb153989f33 | 243 | memset(odata, 0, sizeof(odata)); |
okini3939 | 3:53ce7778a155 | 244 | odata[0] = 0x08; |
okini3939 | 3:53ce7778a155 | 245 | odata[2] = 0x0f; |
okini3939 | 3:53ce7778a155 | 246 | odata[3] = 0xc0; |
okini3939 | 3:53ce7778a155 | 247 | if (dev) { |
okini3939 | 3:53ce7778a155 | 248 | for (int i = 0; i < 4; i ++) { |
okini3939 | 3:53ce7778a155 | 249 | host->interruptWrite(dev, int_out, odata, 12); |
okini3939 | 1:5bb153989f33 | 250 | } |
okini3939 | 3:53ce7778a155 | 251 | } |
okini3939 | 0:bd0f6bf72a8b | 252 | return true; |
okini3939 | 0:bd0f6bf72a8b | 253 | } |
okini3939 | 0:bd0f6bf72a8b | 254 | |
okini3939 | 3:53ce7778a155 | 255 | int USBHostXpad::read (PAD pad) |
okini3939 | 3:53ce7778a155 | 256 | { |
okini3939 | 3:53ce7778a155 | 257 | switch (pad) { |
okini3939 | 3:53ce7778a155 | 258 | case XPAD_BUTTONS: |
okini3939 | 3:53ce7778a155 | 259 | return buttons; |
okini3939 | 2:2749f4e649db | 260 | case XPAD_STICK_LX: |
okini3939 | 2:2749f4e649db | 261 | return stick_lx; |
okini3939 | 2:2749f4e649db | 262 | case XPAD_STICK_LY: |
okini3939 | 2:2749f4e649db | 263 | return stick_ly; |
okini3939 | 2:2749f4e649db | 264 | case XPAD_STICK_RX: |
okini3939 | 2:2749f4e649db | 265 | return stick_rx; |
okini3939 | 2:2749f4e649db | 266 | case XPAD_STICK_RY: |
okini3939 | 2:2749f4e649db | 267 | return stick_ry; |
okini3939 | 2:2749f4e649db | 268 | case XPAD_TRIGGER_L: |
okini3939 | 2:2749f4e649db | 269 | return trigger_l; |
okini3939 | 2:2749f4e649db | 270 | case XPAD_TRIGGER_R: |
okini3939 | 2:2749f4e649db | 271 | return trigger_r; |
okini3939 | 3:53ce7778a155 | 272 | case XPAD_BATTERY: |
okini3939 | 3:53ce7778a155 | 273 | return battery; |
okini3939 | 2:2749f4e649db | 274 | default: |
okini3939 | 3:53ce7778a155 | 275 | return (buttons & pad) ? 1 : 0; |
okini3939 | 3:53ce7778a155 | 276 | } |
okini3939 | 3:53ce7778a155 | 277 | } |
okini3939 | 3:53ce7778a155 | 278 | |
okini3939 | 3:53ce7778a155 | 279 | bool USBHostXpad::start() |
okini3939 | 3:53ce7778a155 | 280 | { |
okini3939 | 3:53ce7778a155 | 281 | unsigned char odata[32]; |
okini3939 | 3:53ce7778a155 | 282 | memset(odata, 0, sizeof(odata)); |
okini3939 | 3:53ce7778a155 | 283 | odata[3] = 0x40; |
okini3939 | 3:53ce7778a155 | 284 | if (dev) { |
okini3939 | 3:53ce7778a155 | 285 | if (host->interruptWrite(dev, int_out, odata, 12) != USB_TYPE_OK) { |
okini3939 | 3:53ce7778a155 | 286 | return false; |
okini3939 | 3:53ce7778a155 | 287 | } |
okini3939 | 2:2749f4e649db | 288 | } |
okini3939 | 3:53ce7778a155 | 289 | return true; |
okini3939 | 3:53ce7778a155 | 290 | } |
okini3939 | 3:53ce7778a155 | 291 | |
okini3939 | 3:53ce7778a155 | 292 | bool USBHostXpad::stop() |
okini3939 | 3:53ce7778a155 | 293 | { |
okini3939 | 3:53ce7778a155 | 294 | unsigned char odata[32]; |
okini3939 | 3:53ce7778a155 | 295 | memset(odata, 0, sizeof(odata)); |
okini3939 | 3:53ce7778a155 | 296 | odata[2] = 0x08; |
okini3939 | 3:53ce7778a155 | 297 | odata[3] = 0xc0; |
okini3939 | 3:53ce7778a155 | 298 | if (dev) { |
okini3939 | 3:53ce7778a155 | 299 | if (host->interruptWrite(dev, int_out, odata, 12) != USB_TYPE_OK) { |
okini3939 | 3:53ce7778a155 | 300 | return false; |
okini3939 | 3:53ce7778a155 | 301 | } |
okini3939 | 3:53ce7778a155 | 302 | } |
okini3939 | 3:53ce7778a155 | 303 | return true; |
okini3939 | 2:2749f4e649db | 304 | } |
okini3939 | 2:2749f4e649db | 305 | |
okini3939 | 2:2749f4e649db | 306 | bool USBHostXpad::led(LED cmd) |
okini3939 | 0:bd0f6bf72a8b | 307 | { |
okini3939 | 0:bd0f6bf72a8b | 308 | unsigned char odata[32]; |
okini3939 | 1:5bb153989f33 | 309 | memset(odata, 0, sizeof(odata)); |
okini3939 | 3:53ce7778a155 | 310 | switch (dev_type) { |
okini3939 | 3:53ce7778a155 | 311 | case TYPE_XBOX: |
okini3939 | 3:53ce7778a155 | 312 | return true; |
okini3939 | 3:53ce7778a155 | 313 | case TYPE_XBOX360: |
okini3939 | 3:53ce7778a155 | 314 | odata[0] = 0x01; |
okini3939 | 3:53ce7778a155 | 315 | odata[1] = 0x03; |
okini3939 | 3:53ce7778a155 | 316 | odata[2] = cmd; |
okini3939 | 3:53ce7778a155 | 317 | break; |
okini3939 | 3:53ce7778a155 | 318 | case TYPE_XBOX360W: |
okini3939 | 3:53ce7778a155 | 319 | odata[2] = 0x08; |
okini3939 | 3:53ce7778a155 | 320 | odata[3] = 0x40 + (cmd % 0x0e); |
okini3939 | 3:53ce7778a155 | 321 | break; |
okini3939 | 3:53ce7778a155 | 322 | default: |
okini3939 | 3:53ce7778a155 | 323 | return false; |
okini3939 | 3:53ce7778a155 | 324 | } |
okini3939 | 3:53ce7778a155 | 325 | if (dev) { |
okini3939 | 3:53ce7778a155 | 326 | if (host->interruptWrite(dev, int_out, odata, 12) != USB_TYPE_OK) { |
okini3939 | 1:5bb153989f33 | 327 | return false; |
okini3939 | 3:53ce7778a155 | 328 | } |
okini3939 | 3:53ce7778a155 | 329 | } |
okini3939 | 1:5bb153989f33 | 330 | return true; |
okini3939 | 1:5bb153989f33 | 331 | } |
okini3939 | 0:bd0f6bf72a8b | 332 | |
okini3939 | 1:5bb153989f33 | 333 | bool USBHostXpad::rumble(uint8_t large, uint8_t small) |
okini3939 | 1:5bb153989f33 | 334 | { |
okini3939 | 1:5bb153989f33 | 335 | unsigned char odata[32]; |
okini3939 | 1:5bb153989f33 | 336 | memset(odata, 0, sizeof(odata)); |
okini3939 | 3:53ce7778a155 | 337 | switch (dev_type) { |
okini3939 | 3:53ce7778a155 | 338 | case TYPE_XBOX: |
okini3939 | 3:53ce7778a155 | 339 | odata[1] = 0x06; |
okini3939 | 3:53ce7778a155 | 340 | odata[3] = small; |
okini3939 | 3:53ce7778a155 | 341 | odata[5] = large; |
okini3939 | 3:53ce7778a155 | 342 | break; |
okini3939 | 3:53ce7778a155 | 343 | case TYPE_XBOX360: |
okini3939 | 3:53ce7778a155 | 344 | odata[1] = 0x08; |
okini3939 | 3:53ce7778a155 | 345 | odata[3] = large; |
okini3939 | 3:53ce7778a155 | 346 | odata[4] = small; |
okini3939 | 3:53ce7778a155 | 347 | break; |
okini3939 | 3:53ce7778a155 | 348 | case TYPE_XBOX360W: |
okini3939 | 3:53ce7778a155 | 349 | odata[1] = 0x01; |
okini3939 | 3:53ce7778a155 | 350 | odata[2] = 0x0f; |
okini3939 | 3:53ce7778a155 | 351 | odata[3] = 0xc0; |
okini3939 | 3:53ce7778a155 | 352 | odata[5] = large; |
okini3939 | 3:53ce7778a155 | 353 | odata[6] = small; |
okini3939 | 3:53ce7778a155 | 354 | break; |
okini3939 | 3:53ce7778a155 | 355 | default: |
okini3939 | 3:53ce7778a155 | 356 | return false; |
okini3939 | 3:53ce7778a155 | 357 | } |
okini3939 | 3:53ce7778a155 | 358 | if (dev) { |
okini3939 | 3:53ce7778a155 | 359 | if (host->interruptWrite(dev, int_out, odata, 12) != USB_TYPE_OK) { |
okini3939 | 1:5bb153989f33 | 360 | return false; |
okini3939 | 3:53ce7778a155 | 361 | } |
okini3939 | 3:53ce7778a155 | 362 | } |
okini3939 | 0:bd0f6bf72a8b | 363 | return true; |
okini3939 | 0:bd0f6bf72a8b | 364 | } |
okini3939 | 0:bd0f6bf72a8b | 365 | |
okini3939 | 0:bd0f6bf72a8b | 366 | #endif |
okini3939 | 0:bd0f6bf72a8b | 367 |