[usb][xhci] Compile the USB XHCI driver as C++

Change-Id: Iec3171f4764a0c6c6e795e150435e91c999678b3
diff --git a/system/dev/usb/xhci/bind.c b/system/dev/usb/xhci/bind.c
new file mode 100644
index 0000000..a177e89
--- /dev/null
+++ b/system/dev/usb/xhci/bind.c
@@ -0,0 +1,31 @@
+// Copyright 2018 The Fuchsia Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include <ddk/binding.h>
+#include <ddk/driver.h>
+#include <ddk/platform-defs.h>
+
+extern zx_status_t usb_xhci_bind(void* ctx, zx_device_t* parent);
+
+static zx_driver_ops_t xhci_driver_ops = {
+    .version = DRIVER_OPS_VERSION,
+    .bind = usb_xhci_bind,
+};
+
+// clang-format off
+ZIRCON_DRIVER_BEGIN(usb_xhci, xhci_driver_ops, "zircon", "0.1", 9)
+    // PCI binding support
+    BI_GOTO_IF(NE, BIND_PROTOCOL, ZX_PROTOCOL_PCI, 0),
+    BI_ABORT_IF(NE, BIND_PCI_CLASS, 0x0C),
+    BI_ABORT_IF(NE, BIND_PCI_SUBCLASS, 0x03),
+    BI_MATCH_IF(EQ, BIND_PCI_INTERFACE, 0x30),
+
+    // platform bus binding support
+    BI_LABEL(0),
+    BI_ABORT_IF(NE, BIND_PLATFORM_DEV_VID, PDEV_VID_GENERIC),
+    BI_ABORT_IF(NE, BIND_PLATFORM_DEV_PID, PDEV_PID_GENERIC),
+    BI_MATCH_IF(EQ, BIND_PLATFORM_DEV_DID, PDEV_DID_USB_XHCI),
+
+    BI_ABORT(),
+ZIRCON_DRIVER_END(usb_xhci)
diff --git a/system/dev/usb/xhci/rules.mk b/system/dev/usb/xhci/rules.mk
index ec3b71f..22cc1e6 100644
--- a/system/dev/usb/xhci/rules.mk
+++ b/system/dev/usb/xhci/rules.mk
@@ -9,23 +9,31 @@
 MODULE_TYPE := driver
 
 MODULE_SRCS := \
-    $(LOCAL_DIR)/usb-xhci.c \
-    $(LOCAL_DIR)/xdc.c \
-    $(LOCAL_DIR)/xdc-transfer.c \
-    $(LOCAL_DIR)/xhci.c \
-    $(LOCAL_DIR)/xhci-device-manager.c \
-    $(LOCAL_DIR)/xhci-root-hub.c \
-    $(LOCAL_DIR)/xhci-transfer.c \
-    $(LOCAL_DIR)/xhci-transfer-common.c \
-    $(LOCAL_DIR)/xhci-trb.c \
-    $(LOCAL_DIR)/xhci-util.c \
+    $(LOCAL_DIR)/bind.c \
+    $(LOCAL_DIR)/usb-xhci.cpp \
+    $(LOCAL_DIR)/xdc.cpp \
+    $(LOCAL_DIR)/xdc-transfer.cpp \
+    $(LOCAL_DIR)/xhci.cpp \
+    $(LOCAL_DIR)/xhci-device-manager.cpp \
+    $(LOCAL_DIR)/xhci-root-hub.cpp \
+    $(LOCAL_DIR)/xhci-transfer.cpp \
+    $(LOCAL_DIR)/xhci-transfer-common.cpp \
+    $(LOCAL_DIR)/xhci-trb.cpp \
+    $(LOCAL_DIR)/xhci-util.cpp \
 
 MODULE_STATIC_LIBS := \
     system/ulib/ddk \
+    system/ulib/ddktl \
+    system/ulib/fbl \
+    system/ulib/hwreg \
     system/ulib/sync \
     system/ulib/xdc-server-utils \
+    system/ulib/zx \
     system/dev/lib/usb \
 
-MODULE_LIBS := system/ulib/driver system/ulib/zircon system/ulib/c
+MODULE_LIBS := \
+    system/ulib/driver \
+    system/ulib/zircon \
+    system/ulib/c \
 
 include make/module.mk
diff --git a/system/dev/usb/xhci/usb-xhci.c b/system/dev/usb/xhci/usb-xhci.cpp
similarity index 92%
rename from system/dev/usb/xhci/usb-xhci.c
rename to system/dev/usb/xhci/usb-xhci.cpp
index b9a8d6f..26303db 100644
--- a/system/dev/usb/xhci/usb-xhci.c
+++ b/system/dev/usb/xhci/usb-xhci.cpp
@@ -58,11 +58,12 @@
 }
 
 static void xhci_hci_request_queue(void* ctx, usb_request_t* req) {
-    xhci_request_queue(ctx, req);
+    auto* xhci = static_cast<xhci_t*>(ctx);
+    xhci_request_queue(xhci, req);
 }
 
 static void xhci_set_bus_interface(void* ctx, usb_bus_interface_t* bus) {
-    xhci_t* xhci = ctx;
+    auto* xhci = static_cast<xhci_t*>(ctx);
 
     if (bus) {
         memcpy(&xhci->bus, bus, sizeof(xhci->bus));
@@ -74,7 +75,7 @@
 }
 
 static size_t xhci_get_max_device_count(void* ctx) {
-    xhci_t* xhci = ctx;
+    auto* xhci = static_cast<xhci_t*>(ctx);
     // add one to allow device IDs to be 1-based
     return xhci->max_slots + XHCI_RH_COUNT + 1;
 }
@@ -82,35 +83,35 @@
 static zx_status_t xhci_enable_ep(void* ctx, uint32_t device_id,
                                   usb_endpoint_descriptor_t* ep_desc,
                                   usb_ss_ep_comp_descriptor_t* ss_comp_desc, bool enable) {
-    xhci_t* xhci = ctx;
+    auto* xhci = static_cast<xhci_t*>(ctx);
     return xhci_enable_endpoint(xhci, device_id, ep_desc, ss_comp_desc, enable);
 }
 
 static uint64_t xhci_get_frame(void* ctx) {
-    xhci_t* xhci = ctx;
+    auto* xhci = static_cast<xhci_t*>(ctx);
     return xhci_get_current_frame(xhci);
 }
 
 static zx_status_t xhci_config_hub(void* ctx, uint32_t device_id, usb_speed_t speed,
                             usb_hub_descriptor_t* descriptor) {
-    xhci_t* xhci = ctx;
+    auto* xhci = static_cast<xhci_t*>(ctx);
     return xhci_configure_hub(xhci, device_id, speed, descriptor);
 }
 
 static zx_status_t xhci_hub_device_added(void* ctx, uint32_t hub_address, int port,
                                   usb_speed_t speed) {
-    xhci_t* xhci = ctx;
+    auto* xhci = static_cast<xhci_t*>(ctx);
     return xhci_enumerate_device(xhci, hub_address, port, speed);
 }
 
 static zx_status_t xhci_hub_device_removed(void* ctx, uint32_t hub_address, int port) {
-    xhci_t* xhci = ctx;
+    auto* xhci = static_cast<xhci_t*>(ctx);
     xhci_device_disconnected(xhci, hub_address, port);
     return ZX_OK;
 }
 
 static zx_status_t xhci_reset_ep(void* ctx, uint32_t device_id, uint8_t ep_address) {
-    xhci_t* xhci = ctx;
+    auto* xhci = static_cast<xhci_t*>(ctx);
     return xhci_reset_endpoint(xhci, device_id, ep_address);
 }
 
@@ -128,12 +129,12 @@
 }
 
 static zx_status_t xhci_cancel_all(void* ctx, uint32_t device_id, uint8_t ep_address) {
-    xhci_t* xhci = ctx;
+    auto* xhci = static_cast<xhci_t*>(ctx);
     return xhci_cancel_transfers(xhci, device_id, xhci_endpoint_index(ep_address));
 }
 
 static zx_status_t xhci_get_bti(void* ctx, zx_handle_t* out_handle) {
-    xhci_t* xhci = ctx;
+    auto* xhci = static_cast<xhci_t*>(ctx);
     *out_handle = xhci->bti_handle;
     return ZX_OK;
 }
@@ -182,7 +183,7 @@
 
 static zx_status_t xhci_suspend(void* ctx, uint32_t flags) {
     zxlogf(TRACE, "xhci_suspend %u\n", flags);
-    xhci_t* xhci = ctx;
+    auto* xhci = static_cast<xhci_t*>(ctx);
 
     // TODO(voydanoff) do different things based on the flags.
     // for now we shutdown the driver in preparation for mexec
@@ -193,7 +194,7 @@
 
 static void xhci_unbind(void* ctx) {
     zxlogf(INFO, "xhci_unbind\n");
-    xhci_t* xhci = ctx;
+    auto* xhci = static_cast<xhci_t*>(ctx);
 
     xhci_shutdown(xhci);
     device_remove(xhci->zxdev);
@@ -201,18 +202,19 @@
 
 static void xhci_release(void* ctx) {
     zxlogf(INFO, "xhci_release\n");
-    xhci_t* xhci = ctx;
+    auto* xhci = static_cast<xhci_t*>(ctx);
     mmio_buffer_release(&xhci->mmio);
     zx_handle_close(xhci->cfg_handle);
     xhci_free(xhci);
 }
-
-static zx_protocol_device_t xhci_device_proto = {
-    .version = DEVICE_OPS_VERSION,
-    .suspend = xhci_suspend,
-    .unbind = xhci_unbind,
-    .release = xhci_release,
-};
+static zx_protocol_device_t xhci_device_ops = []() {
+    zx_protocol_device_t device;
+    device.version = DEVICE_OPS_VERSION;
+    device.suspend = xhci_suspend,
+    device.unbind = xhci_unbind,
+    device.release = xhci_release;
+    return device;
+}();
 
 typedef struct completer {
     xhci_t *xhci;
@@ -305,7 +307,7 @@
         .version = DEVICE_ADD_ARGS_VERSION,
         .name = "xhci",
         .ctx = xhci,
-        .ops = &xhci_device_proto,
+        .ops = &xhci_device_ops,
         .proto_id = ZX_PROTOCOL_USB_HCI,
         .proto_ops = &xhci_hci_protocol,
         .flags = DEVICE_ADD_INVISIBLE
@@ -357,7 +359,8 @@
         goto error_return;
     }
 
-    uint32_t irq_cnt = 0;
+    uint32_t irq_cnt;
+    irq_cnt = 0;
     status = pci_query_irq_mode(pci, ZX_PCIE_IRQ_MODE_MSI, &irq_cnt);
     if (status != ZX_OK) {
         zxlogf(ERROR, "pci_query_irq_mode failed %d\n", status);
@@ -370,7 +373,8 @@
     irq_cnt = MIN(irq_cnt, xhci_get_max_interrupters(xhci));
 
     // select our IRQ mode
-    xhci_mode_t mode = XHCI_PCI_MSI;
+    xhci_mode_t mode;
+    mode = XHCI_PCI_MSI;
     status = pci_set_irq_mode(pci, ZX_PCIE_IRQ_MODE_MSI, irq_cnt);
     if (status < 0) {
         zxlogf(ERROR, "MSI interrupts not available, irq_cnt: %d, err: %d\n",
@@ -495,19 +499,3 @@
     .bind = usb_xhci_bind,
 };
 
-// clang-format off
-ZIRCON_DRIVER_BEGIN(usb_xhci, xhci_driver_ops, "zircon", "0.1", 9)
-    // PCI binding support
-    BI_GOTO_IF(NE, BIND_PROTOCOL, ZX_PROTOCOL_PCI, 0),
-    BI_ABORT_IF(NE, BIND_PCI_CLASS, 0x0C),
-    BI_ABORT_IF(NE, BIND_PCI_SUBCLASS, 0x03),
-    BI_MATCH_IF(EQ, BIND_PCI_INTERFACE, 0x30),
-
-    // platform bus binding support
-    BI_LABEL(0),
-    BI_ABORT_IF(NE, BIND_PLATFORM_DEV_VID, PDEV_VID_GENERIC),
-    BI_ABORT_IF(NE, BIND_PLATFORM_DEV_PID, PDEV_PID_GENERIC),
-    BI_MATCH_IF(EQ, BIND_PLATFORM_DEV_DID, PDEV_DID_USB_XHCI),
-
-    BI_ABORT(),
-ZIRCON_DRIVER_END(usb_xhci)
diff --git a/system/dev/usb/xhci/xdc-transfer.c b/system/dev/usb/xhci/xdc-transfer.cpp
similarity index 98%
rename from system/dev/usb/xhci/xdc-transfer.c
rename to system/dev/usb/xhci/xdc-transfer.cpp
index 79d77bd..8c67e5c 100644
--- a/system/dev/usb/xhci/xdc-transfer.c
+++ b/system/dev/usb/xhci/xdc-transfer.cpp
@@ -25,7 +25,7 @@
         return ZX_ERR_BAD_STATE;
     }
     xdc_context_data_t* ctx = xdc->context_data;
-    xhci_endpoint_context_t* epc = ep->direction == USB_DIR_OUT ? &ctx->out_epc : &ctx->in_epc;
+    volatile xhci_endpoint_context_t* epc = ep->direction == USB_DIR_OUT ? &ctx->out_epc : &ctx->in_epc;
 
     uint64_t dequeue_ptr_hi = XHCI_READ32(&epc->tr_dequeue_hi);
     uint32_t dequeue_ptr_lo = XHCI_READ32(&epc->epc2) & EP_CTX_TR_DEQUEUE_LO_MASK;
diff --git a/system/dev/usb/xhci/xdc.c b/system/dev/usb/xhci/xdc.cpp
similarity index 95%
rename from system/dev/usb/xhci/xdc.c
rename to system/dev/usb/xhci/xdc.cpp
index 5f03fd9..92e1f3b 100644
--- a/system/dev/usb/xhci/xdc.c
+++ b/system/dev/usb/xhci/xdc.cpp
@@ -258,7 +258,7 @@
 
 static zx_status_t xdc_write_instance(void* ctx, const void* buf, size_t count,
                                       zx_off_t off, size_t* actual) {
-    xdc_instance_t* inst = ctx;
+    auto* inst = static_cast<xdc_instance_t*>(ctx);
 
     mtx_lock(&inst->lock);
 
@@ -397,7 +397,7 @@
 
 static zx_status_t xdc_read_instance(void* ctx, void* buf, size_t count,
                                      zx_off_t off, size_t* actual) {
-    xdc_instance_t* inst = ctx;
+    auto* inst = static_cast<xdc_instance_t*>(ctx);
 
     mtx_lock(&inst->lock);
 
@@ -478,14 +478,15 @@
 
 static zx_status_t xdc_ioctl_instance(void* ctx, uint32_t op, const void* in_buf, size_t in_len,
                                       void* out_buf, size_t out_len, size_t* out_actual) {
-    xdc_instance_t* inst = ctx;
+    auto* inst = static_cast<xdc_instance_t*>(ctx);
 
     switch (op) {
     case IOCTL_DEBUG_SET_STREAM:
         if (in_len != sizeof(uint32_t)) {
             return ZX_ERR_INVALID_ARGS;
         }
-        uint32_t stream_id = *((int *)in_buf);
+        uint32_t stream_id;
+        stream_id = *((int *)in_buf);
         return xdc_register_stream(inst, stream_id);
     default:
         return ZX_ERR_NOT_SUPPORTED;
@@ -493,7 +494,7 @@
 }
 
 static zx_status_t xdc_close_instance(void* ctx, uint32_t flags) {
-    xdc_instance_t* inst = ctx;
+    auto* inst = static_cast<xdc_instance_t*>(ctx);
 
     list_node_t free_reqs = LIST_INITIAL_VALUE(free_reqs);
 
@@ -526,21 +527,23 @@
 }
 
 static void xdc_release_instance(void* ctx) {
-    xdc_instance_t* inst = ctx;
+    auto* inst = static_cast<xdc_instance_t*>(ctx);
     free(inst);
 }
 
-zx_protocol_device_t xdc_instance_proto = {
-    .version = DEVICE_OPS_VERSION,
-    .write = xdc_write_instance,
-    .read = xdc_read_instance,
-    .ioctl = xdc_ioctl_instance,
-    .close = xdc_close_instance,
-    .release = xdc_release_instance,
-};
+static zx_protocol_device_t xdc_instance_ops = []() {
+    zx_protocol_device_t device;
+    device.version = DEVICE_OPS_VERSION;
+    device.write = xdc_write_instance;
+    device.read = xdc_read_instance;
+    device.ioctl = xdc_ioctl_instance;
+    device.close = xdc_close_instance;
+    device.release = xdc_release_instance;
+    return device;
+}();
 
 static zx_status_t xdc_open(void* ctx, zx_device_t** dev_out, uint32_t flags) {
-    xdc_t* xdc = ctx;
+    auto* xdc = static_cast<xdc_t*>(ctx);
 
     xdc_instance_t* inst = calloc(1, sizeof(xdc_instance_t));
     if (inst == NULL) {
@@ -551,7 +554,7 @@
         .version = DEVICE_ADD_ARGS_VERSION,
         .name = "xdc",
         .ctx = inst,
-        .ops = &xdc_instance_proto,
+        .ops = &xdc_instance_ops,
         .proto_id = ZX_PROTOCOL_USB_DBC,
         .flags = DEVICE_ADD_INSTANCE,
     };
@@ -639,7 +642,7 @@
 
 static zx_status_t xdc_suspend(void* ctx, uint32_t flags) {
     zxlogf(TRACE, "xdc_suspend %u\n", flags);
-    xdc_t* xdc = ctx;
+    auto* xdc = static_cast<xdc_t*>(ctx);
 
     // TODO(jocelyndang) do different things based on the flags.
     // For now we shutdown the driver in preparation for mexec.
@@ -650,7 +653,7 @@
 
 static void xdc_unbind(void* ctx) {
     zxlogf(INFO, "xdc_unbind\n");
-    xdc_t* xdc = ctx;
+    auto* xdc = static_cast<xdc_t*>(ctx);
     xdc_shutdown(xdc);
 
     mtx_lock(&xdc->instance_list_lock);
@@ -671,7 +674,7 @@
 
 static void xdc_release(void* ctx) {
     zxlogf(INFO, "xdc_release\n");
-    xdc_t* xdc = ctx;
+    auto* xdc = static_cast<xdc_t*>(ctx);
     xdc_free(xdc);
 }
 
@@ -831,7 +834,8 @@
     }
 
     void* data;
-    zx_status_t status = usb_request_mmap(req, &data);
+    zx_status_t status;
+    status = usb_request_mmap(req, &data);
     if (status != ZX_OK) {
         zxlogf(ERROR, "usb_request_mmap failed, err: %d\n", status);
         xdc_queue_read_locked(xdc, req);
@@ -867,7 +871,8 @@
     // Find the instance that is registered for the stream id of the message.
     mtx_lock(&xdc->instance_list_lock);
 
-    bool found = false;
+    bool found;
+    found = false;
     xdc_instance_t* inst;
     list_for_every_entry(&xdc->instance_list, inst, xdc_instance_t, node) {
         mtx_lock(&inst->lock);
@@ -894,13 +899,14 @@
     mtx_unlock(&xdc->read_lock);
 }
 
-static zx_protocol_device_t xdc_proto = {
-    .version = DEVICE_OPS_VERSION,
-    .open = xdc_open,
-    .suspend = xdc_suspend,
-    .unbind = xdc_unbind,
-    .release = xdc_release,
-};
+static zx_protocol_device_t xdc_device_ops = []() {
+    zx_protocol_device_t device;
+    device.version = DEVICE_OPS_VERSION;
+    device.suspend = xhci_suspend,
+    device.unbind = xhci_unbind,
+    device.release = xhci_release;
+    return device;
+}();
 
 static void xdc_handle_port_status_change(xdc_t* xdc, xdc_poll_state_t* poll_state) {
     uint32_t dcportsc = XHCI_READ32(&xdc->debug_cap_regs->dcportsc);
@@ -1168,7 +1174,7 @@
 }
 
 static int xdc_start_thread(void* arg) {
-    xdc_t* xdc = arg;
+    auto* xdc = static_cast<xdc_t*>(arg);
 
     zxlogf(TRACE, "about to enable XHCI DBC\n");
     XHCI_WRITE32(&xdc->debug_cap_regs->dcctrl, DCCTRL_LSE | DCCTRL_DCE);
@@ -1245,21 +1251,22 @@
         goto error_return;
     }
 
-    device_add_args_t args = {
-        .version = DEVICE_ADD_ARGS_VERSION,
-        .name = "xdc",
-        .ctx = xdc,
-        .ops = &xdc_proto,
-        .proto_id = ZX_PROTOCOL_USB_DBC,
-        .flags = DEVICE_ADD_NON_BINDABLE,
-    };
+    device_add_args_t args;
+    args = {};
+    args.version = DEVICE_ADD_ARGS_VERSION;
+    args.name = "xdc";
+    args.ctx = xdc;
+    args.ops = &xdc_device_ops;
+    args.proto_id = ZX_PROTOCOL_USB_DBC;
+    args.flags = DEVICE_ADD_NON_BINDABLE;
 
     status = device_add(parent, &args, &xdc->zxdev);
     if (status != ZX_OK) {
         goto error_return;
     }
 
-    int ret = thrd_create_with_name(&xdc->start_thread, xdc_start_thread, xdc, "xdc_start_thread");
+    int ret;
+    ret = thrd_create_with_name(&xdc->start_thread, xdc_start_thread, xdc, "xdc_start_thread");
     if (ret != thrd_success) {
         device_remove(xdc->zxdev);
         return ZX_ERR_BAD_STATE;
diff --git a/system/dev/usb/xhci/xdc.h b/system/dev/usb/xhci/xdc.h
index 360460a..3f4b246 100644
--- a/system/dev/usb/xhci/xdc.h
+++ b/system/dev/usb/xhci/xdc.h
@@ -7,6 +7,7 @@
 #include <ddk/device.h>
 #include <ddk/protocol/usb.h>
 #include <usb/usb-request.h>
+#include <fbl/atomic.h>
 #include <lib/sync/completion.h>
 #include <xdc-server-utils/packet.h>
 
@@ -107,7 +108,7 @@
     thrd_t start_thread;
 
     // Whether to suspend all activity.
-    atomic_bool suspended;
+    fbl::atomic<bool> suspended;
 
     xdc_endpoint_t eps[NUM_EPS];
     // Whether the Debug Device is in the Configured state.
@@ -131,7 +132,7 @@
 
     // At least one xdc instance has been opened.
     sync_completion_t has_instance_completion;
-    atomic_int num_instances;
+    fbl::atomic<int> num_instances;
 } xdc_t;
 
 // TODO(jocelyndang): we should get our own handles rather than borrowing them from XHCI.
diff --git a/system/dev/usb/xhci/xhci-device-manager.c b/system/dev/usb/xhci/xhci-device-manager.cpp
similarity index 98%
rename from system/dev/usb/xhci/xhci-device-manager.c
rename to system/dev/usb/xhci/xhci-device-manager.cpp
index 078f7ea..2507570 100644
--- a/system/dev/usb/xhci/xhci-device-manager.c
+++ b/system/dev/usb/xhci/xhci-device-manager.cpp
@@ -329,7 +329,8 @@
         goto disable_slot_exit;
     }
 
-    int mps = device_descriptor.bMaxPacketSize0;
+    int mps;
+    mps = device_descriptor.bMaxPacketSize0;
     // enforce correct max packet size for ep0
     switch (speed) {
         case USB_SPEED_LOW:
@@ -353,10 +354,12 @@
 
     // update the max packet size in our device context
     mtx_lock(&xhci->input_context_lock);
-    xhci_input_control_context_t* icc = (xhci_input_control_context_t*)xhci->input_context;
-    zx_paddr_t icc_phys = xhci->input_context_phys;
-    xhci_endpoint_context_t* ep0c = (xhci_endpoint_context_t*)
-                                            &xhci->input_context[2 * xhci->context_size];
+    xhci_input_control_context_t* icc;
+    icc = (xhci_input_control_context_t*)xhci->input_context;
+    zx_paddr_t icc_phys;
+    icc_phys = xhci->input_context_phys;
+    xhci_endpoint_context_t* ep0c;
+    ep0c = (xhci_endpoint_context_t*)&xhci->input_context[2 * xhci->context_size];
     memset((void*)icc, 0, xhci->context_size);
     memset((void*)ep0c, 0, xhci->context_size);
 
diff --git a/system/dev/usb/xhci/xhci-hw.h b/system/dev/usb/xhci/xhci-hw.h
index 545fe24..4a08153 100644
--- a/system/dev/usb/xhci/xhci-hw.h
+++ b/system/dev/usb/xhci/xhci-hw.h
@@ -42,7 +42,7 @@
 } __PACKED xhci_cap_regs_t;
 
 // XHCI Port Register Set
-typedef volatile struct {
+typedef /* volatile */ struct {
     uint32_t portsc;        // Port Status and Control
     uint32_t portpmsc;      // Port Power Management Status and Control
     uint32_t portli;        // Port Link Info
@@ -50,7 +50,7 @@
 } __PACKED xhci_port_regs_t;
 
 // XHCI Operational Registers
-typedef volatile struct {
+typedef /* volatile */ struct {
     uint32_t usbcmd;        // USB Command
     uint32_t usbsts;        // USB Status
     uint32_t pagesize;      // Page Size
@@ -65,7 +65,7 @@
 } __PACKED xhci_op_regs_t;
 
 // XHCI Interrupter Registers
-typedef volatile struct {
+typedef /* volatile */ struct {
     uint32_t    iman;       // Interrupter Management
     uint32_t    imod;       // Interrupter Moderation
     uint32_t    erstsz;     // Event Ring Segment Table Size
@@ -75,7 +75,7 @@
 } __PACKED xhci_intr_regs_t;
 
 // XHCI Runtime Registers
-typedef volatile struct {
+typedef /* volatile */ struct {
     uint32_t    mfindex;    // Microframe Index Register
     uint32_t    reserved[7];
     xhci_intr_regs_t intr_regs[1024];
@@ -83,7 +83,7 @@
 #define XHCI_MFINDEX_BITS   14
 
 // Slot Context
-typedef volatile struct {
+typedef /* volatile */ struct {
     uint32_t sc0;
     uint32_t sc1;
     uint32_t sc2;
@@ -92,7 +92,7 @@
 } __PACKED xhci_slot_context_t;
 
 // Endpoint Context
-typedef volatile struct {
+typedef /* volatile */ struct {
     uint32_t epc0;
     uint32_t epc1;
     uint32_t epc2;
@@ -102,7 +102,7 @@
 } __PACKED xhci_endpoint_context_t;
 
 // Stream Context
-typedef volatile struct {
+typedef /* volatile */ struct {
     uint32_t sc0;
     uint32_t sc1;
     uint32_t sc2;
@@ -110,7 +110,7 @@
 } __PACKED xhci_stream_context_t;
 
 // Input Control Context
-typedef volatile struct {
+typedef /* volatile */ struct {
     uint32_t drop_context_flags;
     uint32_t add_context_flags;
     uint32_t reserved[5];
@@ -118,7 +118,7 @@
 } __PACKED xhci_input_control_context_t;
 
 // Transfer Request Block
-typedef volatile struct {
+typedef /* volatile */ struct {
     union {
     uint64_t ptr;
         struct {
@@ -131,14 +131,14 @@
 } __PACKED xhci_trb_t;
 
 // Event Ring Segment Table Entry
-typedef volatile struct {
+typedef /* volatile */ struct {
     uint64_t ptr;
     uint32_t size;
     uint32_t reserved;
 } __PACKED erst_entry_t;
 
 // XHCI USB Legacy Support Extended Cap
-typedef volatile struct {
+typedef /* volatile */ struct {
     uint8_t cap_id;
     uint8_t next_cap_ptr;
     uint8_t bios_owned_sem;
diff --git a/system/dev/usb/xhci/xhci-root-hub.c b/system/dev/usb/xhci/xhci-root-hub.cpp
similarity index 100%
rename from system/dev/usb/xhci/xhci-root-hub.c
rename to system/dev/usb/xhci/xhci-root-hub.cpp
diff --git a/system/dev/usb/xhci/xhci-transfer-common.c b/system/dev/usb/xhci/xhci-transfer-common.cpp
similarity index 98%
rename from system/dev/usb/xhci/xhci-transfer-common.c
rename to system/dev/usb/xhci/xhci-transfer-common.cpp
index fbd5716..8358e60 100644
--- a/system/dev/usb/xhci/xhci-transfer-common.c
+++ b/system/dev/usb/xhci/xhci-transfer-common.cpp
@@ -8,7 +8,7 @@
 #include "xhci-transfer-common.h"
 
 void xhci_print_trb(xhci_transfer_ring_t* ring, xhci_trb_t* trb) {
-    int index = trb - ring->start;
+    size_t index = trb - ring->start;
     uint32_t* ptr = (uint32_t *)trb;
     uint64_t paddr = io_buffer_phys(&ring->buffer) + index * sizeof(xhci_trb_t);
 
diff --git a/system/dev/usb/xhci/xhci-transfer.c b/system/dev/usb/xhci/xhci-transfer.cpp
similarity index 99%
rename from system/dev/usb/xhci/xhci-transfer.c
rename to system/dev/usb/xhci/xhci-transfer.cpp
index 8cec767..594e8d8 100644
--- a/system/dev/usb/xhci/xhci-transfer.c
+++ b/system/dev/usb/xhci/xhci-transfer.cpp
@@ -612,7 +612,8 @@
             break;
         case TRB_CC_TRB_ERROR:
             zxlogf(TRACE, "xhci_handle_transfer_event: TRB_CC_TRB_ERROR\n");
-            int ep_ctx_state = xhci_get_ep_ctx_state(slot, ep);
+            int ep_ctx_state;
+            ep_ctx_state = xhci_get_ep_ctx_state(slot, ep);
             /*
              * For usb-c ethernet adapters on Intel xhci controller, we receive this error
              * when a packet fails with NRDY token on the bus.see NET:97 for more details.
diff --git a/system/dev/usb/xhci/xhci-trb.c b/system/dev/usb/xhci/xhci-trb.cpp
similarity index 97%
rename from system/dev/usb/xhci/xhci-trb.c
rename to system/dev/usb/xhci/xhci-trb.cpp
index 631096b..d4eea90 100644
--- a/system/dev/usb/xhci/xhci-trb.c
+++ b/system/dev/usb/xhci/xhci-trb.cpp
@@ -90,11 +90,11 @@
     trb_set_control(trb, TRB_TRANSFER_NOOP, control & TRB_C);
 }
 
-void* xhci_read_trb_ptr(xhci_transfer_ring_t* ring, xhci_trb_t* trb) {
+xhci_trb_t* xhci_read_trb_ptr(xhci_transfer_ring_t* ring, xhci_trb_t* trb) {
     // convert physical address to virtual
     uint8_t* ptr = trb_get_ptr(trb);
     ptr += ((uint8_t *)io_buffer_virt(&ring->buffer) - (uint8_t *)io_buffer_phys(&ring->buffer));
-    return ptr;
+    return static_cast<xhci_trb_t*>(ptr);
 }
 
 xhci_trb_t* xhci_get_next_trb(xhci_transfer_ring_t* ring, xhci_trb_t* trb) {
diff --git a/system/dev/usb/xhci/xhci-trb.h b/system/dev/usb/xhci/xhci-trb.h
index 17dcf76..6c09bee 100644
--- a/system/dev/usb/xhci/xhci-trb.h
+++ b/system/dev/usb/xhci/xhci-trb.h
@@ -42,7 +42,7 @@
 void xhci_clear_trb(xhci_trb_t* trb);
 // Converts a transfer trb into a NO-OP transfer TRB, does nothing if it is the LINK TRB.
 void xhci_set_transfer_noop_trb(xhci_trb_t* trb);
-void* xhci_read_trb_ptr(xhci_transfer_ring_t* ring, xhci_trb_t* trb);
+xhci_trb_t* xhci_read_trb_ptr(xhci_transfer_ring_t* ring, xhci_trb_t* trb);
 xhci_trb_t* xhci_get_next_trb(xhci_transfer_ring_t* ring, xhci_trb_t* trb);
 void xhci_increment_ring(xhci_transfer_ring_t* ring);
 void xhci_set_dequeue_ptr(xhci_transfer_ring_t* ring, xhci_trb_t* new_ptr);
diff --git a/system/dev/usb/xhci/xhci-util.c b/system/dev/usb/xhci/xhci-util.cpp
similarity index 100%
rename from system/dev/usb/xhci/xhci-util.c
rename to system/dev/usb/xhci/xhci-util.cpp
diff --git a/system/dev/usb/xhci/xhci.c b/system/dev/usb/xhci/xhci.cpp
similarity index 98%
rename from system/dev/usb/xhci/xhci.c
rename to system/dev/usb/xhci/xhci.cpp
index b676d1a..d13ac16 100644
--- a/system/dev/usb/xhci/xhci.c
+++ b/system/dev/usb/xhci/xhci.cpp
@@ -221,7 +221,8 @@
         goto fail;
     }
 
-    bool scratch_pad_is_contig = false;
+    bool scratch_pad_is_contig;
+    scratch_pad_is_contig = false;
     if (scratch_pad_bufs > 0) {
         // map scratchpad buffers read-only
         uint32_t flags = IO_BUFFER_RO;
@@ -260,9 +261,11 @@
     xhci->input_context_phys = io_buffer_phys(&xhci->input_context_buffer);
 
     // DCBAA can only be 256 * sizeof(uint64_t) = 2048 bytes, so we have room for ERST array after DCBAA
-    zx_off_t erst_offset = 256 * sizeof(uint64_t);
+    zx_off_t erst_offset;
+    erst_offset = 256 * sizeof(uint64_t);
 
-    size_t array_bytes = ERST_ARRAY_SIZE * sizeof(erst_entry_t);
+    size_t array_bytes;
+    array_bytes = ERST_ARRAY_SIZE * sizeof(erst_entry_t);
     // MSI only supports up to 32 interupts, so the required ERST arrays will fit
     // within the page. Potentially more pages will need to be allocated for MSI-X.
     for (uint32_t i = 0; i < xhci->num_interrupts; i++) {
diff --git a/system/dev/usb/xhci/xhci.h b/system/dev/usb/xhci/xhci.h
index 2526da1..98c33c9 100644
--- a/system/dev/usb/xhci/xhci.h
+++ b/system/dev/usb/xhci/xhci.h
@@ -18,6 +18,7 @@
 #include <ddk/protocol/platform-device.h>
 #include <ddk/protocol/usb-bus.h>
 #include <ddk/protocol/usb.h>
+#include <fbl/atomic.h>
 #include <usb/usb-request.h>
 
 #include "xhci-hw.h"
@@ -103,7 +104,7 @@
     usb_bus_interface_t bus;
 
     xhci_mode_t mode;
-    atomic_bool suspended;
+    fbl::atomic<bool> suspended;
 
     // Desired number of interrupters. This may be greater than what is
     // supported by hardware. The actual number of interrupts configured
@@ -235,3 +236,7 @@
 void xhci_remove_device(xhci_t* xhci, int slot_id);
 
 void xhci_request_queue(xhci_t* xhci, usb_request_t* req);
+
+__BEGIN_CDECLS
+zx_status_t dwc3_bind(void* ctx, zx_device_t* parent);
+__END_CDECLS