tuesday wip

Change-Id: I8eae6c985dbe60e05bd8898e0e11db6879e1626e
diff --git a/system/dev/ethernet/usb-cdc-function/cdc-eth-function.c b/system/dev/ethernet/usb-cdc-function/cdc-eth-function.c
index 1528f7c..5f093f8 100644
--- a/system/dev/ethernet/usb-cdc-function/cdc-eth-function.c
+++ b/system/dev/ethernet/usb-cdc-function/cdc-eth-function.c
@@ -454,9 +454,6 @@
 
     // TODO(voydanoff) fullspeed and superspeed support
     if (alt_setting) {
-        // send status notifications on interrupt endpoint
-        status = cdc_send_notifications(cdc);
-
         if ((status = usb_function_config_ep(&cdc->function, &descriptors.bulk_out_ep, NULL))
                 != ZX_OK ||
             (status = usb_function_config_ep(&cdc->function, &descriptors.bulk_in_ep, NULL))
@@ -481,6 +478,9 @@
             usb_function_queue(&cdc->function, req);
         }
         mtx_unlock(&cdc->rx_mutex);
+
+        // send status notifications on interrupt endpoint
+        status = cdc_send_notifications(cdc);
     }
 
     mtx_lock(&cdc->ethmac_mutex);
diff --git a/system/dev/usb/dwc2-device/dwc2-endpoints.c b/system/dev/usb/dwc2-device/dwc2-endpoints.c
index ac680ae..b98bd40 100644
--- a/system/dev/usb/dwc2-device/dwc2-endpoints.c
+++ b/system/dev/usb/dwc2-device/dwc2-endpoints.c
@@ -174,6 +174,7 @@
             req = list_remove_head_type(&ep->queued_reqs, usb_request_t, node);
         }
     }
+printf("dwc_ep_queue_next_locked current_req %p req %p\n", ep->current_req, req);
 
     if (req) {
         ep->current_req = req;
@@ -280,7 +281,8 @@
 
     if (!ep->enabled) {
         mtx_unlock(&ep->lock);
-        usb_request_complete(req, ZX_ERR_BAD_STATE, 0);
+        zxlogf(ERROR, "dwc_ep_queue ep not enabled!\n");    
+       usb_request_complete(req, ZX_ERR_BAD_STATE, 0);
         return;
     }
 
@@ -288,6 +290,8 @@
 
     if (dwc->configured) {
         dwc_ep_queue_next_locked(dwc, ep);
+    } else {
+            zxlogf(ERROR, "dwc_ep_queue not configured!\n");    
     }
 
     mtx_unlock(&ep->lock);
diff --git a/system/dev/usb/dwc2-device/dwc2-interrupts.c b/system/dev/usb/dwc2-device/dwc2-interrupts.c
index d8526df..d89d7b3 100644
--- a/system/dev/usb/dwc2-device/dwc2-interrupts.c
+++ b/system/dev/usb/dwc2-device/dwc2-interrupts.c
@@ -138,11 +138,12 @@
         case USB_REQ_SET_CONFIGURATION:
             zxlogf(INFO, "SET_CONFIGURATION %d\n", setup->wValue);
             dwc_reset_configuration(dwc);
-            dwc->configured = false;
+                dwc->configured = true;
             status = usb_dci_control(&dwc->dci_intf, setup, buffer, length, out_actual);
             if (status == ZX_OK && setup->wValue) {
-                dwc->configured = true;
                 dwc_start_eps(dwc);
+            } else {
+                dwc->configured = false;
             }
             return status;
         default:
@@ -153,11 +154,12 @@
                setup->bRequest == USB_REQ_SET_INTERFACE) {
         zxlogf(INFO, "SET_INTERFACE %d\n", setup->wValue);
         dwc_reset_configuration(dwc);
-        dwc->configured = false;
+        dwc->configured = true;
         status = usb_dci_control(&dwc->dci_intf, setup, buffer, length, out_actual);
         if (status == ZX_OK) {
-            dwc->configured = true;
             dwc_start_eps(dwc);
+        } else {
+            dwc->configured = false;
         }
         return status;
     }
@@ -456,9 +458,11 @@
 static void dwc_handle_inepintr_irq(dwc_usb_t* dwc) {
     dwc_regs_t* regs = dwc->regs;
 
+printf("dwc_handle_inepintr_irq\n");
 	for (uint32_t ep_num = 0; ep_num < MAX_EPS_CHANNELS; ep_num++) {
         uint32_t bit = 1 << ep_num;
-        if ((regs->daint & bit) == 0) {
+        uint32_t daint = regs->daint;
+        if ((daint & bit) == 0) {
             continue;
         }
         regs->daint |= bit;
@@ -476,6 +480,7 @@
 			} else {
 				dwc_complete_ep(dwc, ep_num);
 				if (diepint.nak) {
+printf("diepint.nak ep_num %u\n", ep_num);
 					CLEAR_IN_EP_INTR(ep_num, nak);
 			    }
 			}
@@ -506,6 +511,7 @@
 		}
 		/** IN Endpoint NAK Effective */
 		if (diepint.inepnakeff) {
+printf("diepint.inepnakeff ep_num %u\n", ep_num);
 			CLEAR_IN_EP_INTR(ep_num, inepnakeff);
 		}
 	}
@@ -615,7 +621,6 @@
             // acknowledge
             regs->gintsts = interrupts;
 
-/*
             zxlogf(LINFO, "dwc_handle_irq:");
             if (interrupts.modemismatch) zxlogf(LINFO, " modemismatch");
             if (interrupts.otgintr) zxlogf(LINFO, " otgintr");
@@ -649,7 +654,6 @@
             if (interrupts.sessreqintr) zxlogf(LINFO, " sessreqintr");
             if (interrupts.wkupintr) zxlogf(LINFO, " wkupintr");
             zxlogf(LINFO, "\n");
-*/
 
             if (interrupts.usbreset) {
                 dwc_handle_reset_irq(dwc);
diff --git a/system/dev/usb/dwc2-device/dwc2.c b/system/dev/usb/dwc2-device/dwc2.c
index b11781b..88804ec 100644
--- a/system/dev/usb/dwc2-device/dwc2.c
+++ b/system/dev/usb/dwc2-device/dwc2.c
@@ -46,7 +46,7 @@
 
     regs->grxfsiz = 256;    //???
 
-	regs->gnptxfsiz.depth = 512;
+	regs->gnptxfsiz.depth = 256;
 	regs->gnptxfsiz.startaddr = 256;
 
 	dwc_flush_fifo(dwc, 0x10);
@@ -76,6 +76,11 @@
 //    gintmsk.sof_intr = 1;
     gintmsk.usbsuspend = 1;
 
+
+    gintmsk.ginnakeff = 1;
+    gintmsk.goutnakeff = 1;
+
+
 /*
 	gintmsk.modemismatch = 1;
 	gintmsk.otgintr = 1;
@@ -85,6 +90,8 @@
 	gintmsk.sessreqintr = 1;
 */
 
+printf("ghwcfg1 %08x ghwcfg2 %08x ghwcfg3 %08x\n", regs->ghwcfg1, regs->ghwcfg2, regs->ghwcfg3);
+
 	regs->gotgint = 0xFFFFFFF;
 	regs->gintsts.val = 0xFFFFFFF;
 
@@ -100,7 +107,7 @@
 static void dwc_request_queue(void* ctx, usb_request_t* req) {
     dwc_usb_t* dwc = ctx;
 
-//    zxlogf(INFO, "XXXXXXX dwc_request_queue ep: 0x%02x\n", req->header.ep_address);
+    zxlogf(INFO, "XXXXXXX dwc_request_queue ep: 0x%02x length %zu\n", req->header.ep_address, req->header.length);
     unsigned ep_num = DWC_ADDR_TO_INDEX(req->header.ep_address);
     if (ep_num == 0 || ep_num >= countof(dwc->eps)) {
         zxlogf(ERROR, "dwc_request_queue: bad ep address 0x%02X\n", req->header.ep_address);
diff --git a/system/dev/usb/dwc2-device/dwc2.h b/system/dev/usb/dwc2-device/dwc2.h
index a66bb39..a20faf9 100644
--- a/system/dev/usb/dwc2-device/dwc2.h
+++ b/system/dev/usb/dwc2-device/dwc2.h
@@ -36,7 +36,7 @@
 #define MMIO_INDEX  0
 #define IRQ_INDEX   0
 
-#define SINGLE_EP_IN_QUEUE 1
+//#define SINGLE_EP_IN_QUEUE 1
 
 typedef enum dwc_ep0_state {
     EP0_STATE_DISCONNECTED,
diff --git a/system/dev/usb/dwc2-device/usb_dwc_regs.h b/system/dev/usb/dwc2-device/usb_dwc_regs.h
index 9442cc8..f1ef694 100644
--- a/system/dev/usb/dwc2-device/usb_dwc_regs.h
+++ b/system/dev/usb/dwc2-device/usb_dwc_regs.h
@@ -469,6 +469,8 @@
     dwc_fifosiz_t gnptxfsiz;
 	// Non Periodic Transmit FIFO/Queue Status Register
     dwc_gnptxsts_t gnptxsts;
+    // I2C Access Register
+    uint32_t gi2cctl;
 	// PHY Vendor Control Register
 	uint32_t gpvndctl;
 	// General Purpose Input/Output Register
@@ -481,8 +483,12 @@
 	uint32_t ghwcfg1;
 	// User HW Config2 Register (Read Only)
 	uint32_t ghwcfg2;
+	// User HW Config3 Register (Read Only)
+	uint32_t ghwcfg3;
+	// User HW Config4 Register (Read Only)
+	uint32_t ghwcfg4;
 
-    uint32_t reserved_030[(0x800 - 0x048) / sizeof(uint32_t)];
+    uint32_t reserved_030[(0x800 - 0x054) / sizeof(uint32_t)];
 
     // Device Configuration Register
     dwc_dcfg_t dcfg;