?login_element?

Subversion Repositories NedoOS

Rev

Rev 203 | Go to most recent revision | Blame | Compare with Previous | Last modification | View Log | Download | RSS feed

  1.  
  2. SL811
  3. .EP0Control=0
  4. .EP0Address=1
  5. .EP0Status=3
  6. .EP0Counter=4
  7. .CtrlReg=5
  8. .IntEna=6
  9. .IntStatus=13
  10. .cDATASet=14
  11. .cSOFcnt=15
  12. .INT_CLEAR=0xff
  13.         MACRO WRITE_REG _r,_v
  14.         IF _r == 0x00
  15.                 xor a
  16.         ELSE
  17.                 ld a,_r
  18.         ENDIF
  19.         out (c),a              
  20.         IF _r != _v
  21.                 IF _v == 0x00
  22.                         xor a
  23.                 ELSE
  24.                         ld a,_v
  25.                 ENDIF
  26.         ENDIF
  27.         IF _v & 0x80
  28.                 dec b
  29.                 out (c),a
  30.                 inc b
  31.         ELSE
  32.                 out (0xab),a
  33.         ENDIF
  34.         ENDM
  35. .init  
  36. ; 32.       SL11HardReset();
  37.        
  38.         CALL    .SL11HardReset
  39. ; 33.       USBReset();
  40.         CALL    .USBReset
  41. ; 34.           temp=sl811_init_my();
  42.         CALL    .sl811_init_my
  43.         or a
  44.         ld a,1
  45.         ret z
  46. ; 35.           temp=EnumUsbDev();                              // enumerate USB device, assign USB address = #1
  47.         CALL    .EnumUsbDev
  48.         or a
  49.         ld a,1
  50.         ret z
  51. ; 36.           temp=EnumMassDev();
  52.         CALL    .EnumMassDev
  53.         or a
  54.         ret z
  55.         ld a,1
  56.         ret
  57.  
  58. .DBUF=0x8000-1024
  59. ; 17.   void USBReset(void)  
  60. ; 18.   {
  61. .USBReset:
  62.         PUSH    BC
  63.         PUSH    DE
  64.         PUSH    AF
  65. ; 19.           BYTE tmp;
  66. ; 20.           tmp =  SL811Read(CtrlReg);
  67.         LD      A,.CtrlReg      ;0x05
  68.         LD      BC,0x80ab
  69.         OUT     (C),A
  70.         in a,(0xab)
  71.         LD      HL,0
  72.         ADD     HL,SP
  73.         LD      (HL),a
  74. ; 21.           SL811Write(CtrlReg,0x08);
  75.         WRITE_REG .CtrlReg,0x08
  76. ; 22.           .delayms(100);
  77.         LD      E,6
  78.         CALL    .delayms
  79. ; 23.           SL811Write(CtrlReg,0x18);
  80.         WRITE_REG .CtrlReg, 0x18
  81. ; 24.           .delayms(100);
  82.         LD      E,6
  83.         CALL    .delayms
  84. ; 25.           SL811Write(CtrlReg,0x08);
  85.         WRITE_REG .CtrlReg, 0x08
  86. ; 26.           .delayms(500);
  87.         LD      E,26
  88.         CALL    .delayms
  89. ; 27.           SL811Write(CtrlReg,tmp);
  90.         LD      A,.CtrlReg      ;0x05
  91.         OUT     (C),A
  92.         LD      HL,0
  93.         ADD     HL,SP
  94.         LD      A,(HL)
  95.         dec B
  96.         OUT     (C),A
  97. ; 28.   }  
  98.         POP     HL
  99.         POP     DE
  100.         POP     BC
  101.         RET
  102. ; 29.   BYTE sl811_init_my(void)
  103. ; 30.   {      
  104. .sl811_init_my:
  105.         PUSH    BC
  106.         PUSH    DE
  107. ; 31.                   SL811Write(cSOFcnt, 0xae);  // Set SOF high counter, no change D+/D-SL11Write(CtrlReg, 0x48); // Setup Normal Operation
  108.         LD      A,.cSOFcnt
  109.         LD      BC,0x80ab
  110.         OUT     (C),A
  111.         LD      A,174
  112.         dec     B       ;LD     B,0x7f
  113.         OUT     (C),A
  114.         inc b
  115. ; 32.                   SL811Write(IntEna, 0x63); // USBA/B, Insert/Remove,USBRest/Resume.
  116.         WRITE_REG .IntEna, 0x63
  117. ; 33.                   SL811Write(cSOFcnt, 0xae);  // Set SOF high counter, no change D+/D-SL11Write(CtrlReg, 0x48); // Setup Normal Operation
  118.         WRITE_REG .cSOFcnt, 0xae
  119. ; 34.                   SL811Write(CtrlReg, 0);         // Disable USB transfer operation and SOF
  120.         WRITE_REG .CtrlReg, 0x00
  121. ; 35.                   SL811Write(cSOFcnt, 0xae);      // Set SOF high counter, no change D+/D-SL11Write(CtrlReg, 0x48);
  122.         WRITE_REG .cSOFcnt, 0xae
  123. ; 36.                                                                           // Clear SL811H mode and setup normal operation
  124. ; 37.                   .delayms(20);     // Delay for HW stablize
  125.         LD      E,2
  126.         CALL    .delayms
  127. ; 38.                   SL811Write(CtrlReg, 0);         // Disable USB transfer operation and SOF
  128.         WRITE_REG .CtrlReg, 0
  129. ; 39.                   if(SL811Read(IntStatus)==0x05) return FALSE;
  130.         LD      A,13
  131.         OUT     (C),A
  132.         IN      A,(0xab)
  133.         CP      5
  134.         JR      Z,.lo183
  135. .lo010:
  136. .lo011:
  137. ; 40.                  
  138. ; 41.                   SL811Write(cSOFcnt,0xae);
  139.         WRITE_REG .cSOFcnt,0xae
  140.         call .USBReset
  141. ; 42.                   SL811Write(IntEna,0x00);
  142.         WRITE_REG .IntEna,0x00
  143. ; 43.                   SL811Write(IntStatus,INT_CLEAR);
  144.         WRITE_REG .IntStatus, 0xFF
  145. ; 44.                   .delayms(100);
  146.         LD      E,6
  147.         CALL    .delayms
  148. ; 45.                   if((SL811Read(IntStatus)&0xc0)!=0x80) return FALSE;
  149.         LD      A,13
  150.         OUT     (C),A
  151.         IN      a,(0xab)
  152.         AND     0xc0
  153.         cp 0x80
  154.         jr z,.lo013
  155. .lo012:
  156. .lo183:
  157.         XOR     A
  158. ; 46.                   puts("'Full' Speed is detected!");      // ** Full Speed is detected ** //  
  159.         JR      .lo014
  160. .lo013:
  161. ; 47.                   SL811Write(cSOFcnt,0xae);       // Set up Master & low speed direct and SOF cnt high=0x2e  
  162.         WRITE_REG .cSOFcnt,0xae
  163. ; 48.                   SL811Write(cDATASet,0xe0);      // SOF Counter Low = 0xE0; 1ms interval  
  164.         WRITE_REG .cDATASet,0xe0
  165. ; 49.                   SL811Write(CtrlReg,0x05);       // Setup 48MHz and SOF enable
  166.         WRITE_REG .CtrlReg,0x05
  167. ; 50.                   SL811Write(EP0Status,0x50);     //90);
  168.         WRITE_REG .EP0Status,0x50
  169. ; 51.                   SL811Write(EP0Counter,0x00);
  170.         WRITE_REG .EP0Counter,0x00
  171. ; 52.                   SL811Write(EP0Control,1);       //sDATA0_RD);   //0x23
  172.         WRITE_REG .EP0Control,1
  173. ; 53.                   .delayms(15);
  174.         LD      E,A
  175.         CALL    .delayms
  176. ; 54.                   SL811Write(IntEna,0x61);
  177.         WRITE_REG .IntEna,0x61
  178. ; 55.                   SL811Write(IntStatus,INT_CLEAR);        //0xff
  179.         WRITE_REG .IntStatus, 0xFF
  180. ; 56.                   return TRUE;
  181.         LD      A,1
  182. ; 57.   }
  183. .lo014:
  184.         POP     DE
  185.         POP     BC
  186.         RET
  187. ; 58.   //*****************************************************************************************  
  188. ; 59.   // .usbXfer:  
  189. ; 60.   // successful transfer = return TRUE  
  190. ; 61.   // fail transfer = return FALSE  
  191. ; 62.   //*****************************************************************************************  
  192. ; 63.   unsigned char .usbXfer(void)  
  193. ; 64.   {    
  194. .usbXfer:
  195.         PUSH    BC
  196.         PUSH    DE
  197.         PUSH    IY
  198.         PUSH    IX
  199.         PUSH    AF
  200. ; 65.       unsigned char xferLen, cmd;  
  201. ; 66.       unsigned char result,remainder,dataX=0x10,bufLen,timeout;  
  202. ; 67.       timeout=TIMEOUT_RETRY;
  203. ; 68.           #define data0 EP0_Buf                    // DATA0 buffer address  
  204. ; 69.       #define data1 (EP0_Buf + 64)                        // DATA1 buffer address  
  205. ; 70.       //------------------------------------------------  
  206. ; 71.       // Define data transfer payload  
  207. ; 72.       //------------------------------------------------  
  208. ; 73.       if (.usbstack.wLen >= 64)          // select proper data payload  
  209.         LD      E,16
  210.         LD      HL,0
  211.         ADD     HL,SP
  212.         LD      (HL),6
  213.         LD      HL,(.usbstack+3)
  214.         LD      BC,64
  215.         AND     A
  216.         SBC     HL,BC
  217.         JR      C,.lo016
  218. .lo015:
  219. ; 74.           xferLen = 64;            // limit to wPayload size    
  220.         LD      IXL,64
  221. ; 75.       else                            // else take < payload len  
  222.         JR      .lo017
  223. .lo016:
  224. ; 76.           xferLen = .usbstack.wLen;            //    
  225.         LD      A,(.usbstack+3)
  226.         LD      IXL,A
  227. .lo017:
  228. ; 77.          
  229. ; 78.       // For IN token  
  230. ; 79.       if (.usbstack.pid==PID_IN)               // for current IN tokens  
  231.         LD      A,(.usbstack+2)
  232.         CP      144
  233.         JR      NZ,.lo019
  234. .lo018:
  235. ; 80.           {
  236. ; 81.                   cmd = sDATA0_RD;            // FS/FS on Hub, sync to sof  
  237.         LD      D,35
  238.         JR      .lo025
  239. .lo019:
  240. ; 82.           }  
  241. ; 83.       // For OUT token  
  242. ; 84.       else if(.usbstack.pid==PID_OUT)              // for OUT tokens  
  243.         CP      16
  244.         LD      B,IXL
  245.         JR      NZ,.lo022
  246. .lo021:
  247. ; 85.       {      
  248. ; 86.           if(xferLen)                                 // only when there are    
  249.         INC     B
  250.         DEC     B
  251.         JR      Z,.lo024
  252. .lo023:
  253. ; 87.                   {
  254. ; 88.               SL811BufWrite(data0,.usbstack.buffer,xferLen);   // data to transfer on USB  
  255.         PUSH    DE
  256.         LD      HL,.usbstack+5
  257.         LD      C,(HL)
  258.         INC     HL
  259.         LD      B,(HL)
  260.         PUSH    BC
  261.         LD      C,IXL
  262.         LD      E,16
  263.         CALL    SL811BUFWRITE
  264.         POP     HL
  265.         POP     DE
  266. .lo024:
  267. ; 89.                   }
  268. ; 90.                   cmd = sDATA0_WR;                        // FS/FS on Hub, sync to sof
  269. ; 91.                   .uDev.bData1[.usbstack.endpoint]=(cmd |= .uDev.bData1[.usbstack.endpoint])^0x40;
  270.         LD      BC,(.usbstack+1)
  271.         LD      B,0
  272.         LD      HL,.uDev+1
  273.         ADD     HL,BC
  274.         LD      A,(HL)
  275.         OR      39
  276.         LD      D,A
  277.         XOR     64
  278.         LD      BC,(.usbstack+1)
  279.         LD      B,0
  280.         LD      HL,.uDev+1
  281.         ADD     HL,BC
  282.         LD      (HL),A
  283. ; 92.       }  
  284. ; 93.       //------------------------------------------------  
  285. ; 94.       // For SETUP/OUT token  
  286. ; 95.       //------------------------------------------------  
  287. ; 96.       else                                            // for current SETUP/OUT tokens  
  288.         JR      .lo025
  289. .lo022:
  290. ; 97.       {      
  291. ; 98.           if(xferLen)                                 // only when there are    
  292.         INC     B
  293.         DEC     B
  294.         JR      Z,.lo027
  295. .lo026:
  296. ; 99.           {                                       // data to transfer on USB
  297. ; 100.              SL811BufWrite(data0,&.usbstack.setup.bmRequest,xferLen);
  298.         PUSH    DE
  299.         LD      HL,.usbstack+7
  300.         PUSH    HL
  301.         LD      C,IXL
  302.         LD      E,16
  303.         CALL    SL811BUFWRITE
  304.         POP     HL
  305.         POP     DE
  306. .lo027:
  307. ; 101.          }  
  308. ; 102.                  cmd = sDATA0_WR;                            // FS/FS on Hub, sync to sof  
  309.         LD      D,39
  310. .lo025:
  311. .lo020:
  312. ; 103.      }  
  313. ; 104.      //------------------------------------------------  
  314. ; 105.      // For EP0's IN/OUT token data, start with DATA1  
  315. ; 106.      // Control Endpoint0's status stage.  
  316. ; 107.      // For data endpoint, IN/OUT data, start ????  
  317. ; 108.      //------------------------------------------------  
  318. ; 109.      if (.usbstack.endpoint == 0 && .usbstack.pid != PID_SETUP)    // for Ep0's IN/OUT token  
  319.         LD      A,(.usbstack+1)
  320.         OR      A
  321.         JR      NZ,.lo029
  322.         LD      A,(.usbstack+2)
  323.         CP      208
  324.         JR      Z,.lo029
  325. .lo031:
  326. .lo030:
  327. .lo028:
  328. ; 110.          cmd |= 0x40;                    // always set DATA1  
  329.         SET     6,D
  330. .lo029:
  331. ; 111.      //------------------------------------------------  
  332. ; 112.      // Arming of USB data transfer for the first pkt  
  333. ; 113.      //------------------------------------------------  
  334. ; 114.      SL811Write(EP0Status,((.usbstack.endpoint&0x0F)|.usbstack.pid));  // PID + EP address  
  335.         LD      A,3
  336.         LD      BC,0x80ab
  337.         OUT     (C),A
  338.         ld hl,(.usbstack+1)
  339.         LD      A,l
  340.         AND     15
  341.         OR      H
  342.         dec B
  343.         OUT     (C),A
  344.         inc B
  345. ; 115.      SL811Write(EP0Counter,.usbstack.usbaddr);                    // USB address  
  346.         LD      A,4
  347.         OUT     (C),A
  348.         LD      A,(.usbstack)
  349.         dec B
  350.         OUT     (C),A
  351.         inc B
  352. ; 116.      SL811Write(EP0Address,data0);                   // buffer address, start with "data0"  
  353.         WRITE_REG .EP0Address,16
  354. ; 117.      SL811Write(.ep0XferLen,xferLen);                 // data transfer length  
  355.         LD      A,2
  356.         OUT     (C),A
  357.         LD      A,IXL
  358.         dec B
  359.         OUT     (C),A
  360.         inc B
  361. ; 118.      SL811Write(IntStatus,INT_CLEAR);                // clear interrupt status
  362.         WRITE_REG .IntStatus,.INT_CLEAR
  363. ; 119.      SL811Write(EP0Control,cmd);                     // Enable ARM and USB transfer start here  
  364.         XOR     A
  365.         OUT     (C),A
  366.         dec B
  367.         OUT     (C),D
  368. .lo033:
  369. ; 120.      //------------------------------------------------  
  370. ; 121.      // Main loop for completing a wLen data trasnfer  
  371. ; 122.      //------------------------------------------------  
  372. ; 123.      while(TRUE)  
  373. .lo034:
  374. .lo036:
  375. ; 124.      {      
  376. ; 125.          //---------------Wait for done interrupt------------------  
  377. ; 126.          while(TRUE)                                             // always ensure requested device is  
  378. .lo037:
  379. ; 127.          {                                                       // inserted at all time, then you will  
  380. ; 128.              result = SL811Read(IntStatus);      
  381.         LD      A,13
  382.         LD      BC,0x80ab
  383.         OUT     (C),A
  384.         dec B
  385.         IN      H,(C)
  386.         LD      B,H
  387. ; 129.                                      // wait for interrupt to be done, and    
  388. ; 130.              if(result & (USB_RESET|INSERT_REMOVE))    // proceed to parse result from slave    
  389.         LD      A,H
  390.         AND     96
  391.         JR      Z,.lo039
  392. .lo038:
  393. ; 131.              {                                                   // device.
  394. ; 132.                  return FALSE;                                   // flag true, so that main loop will    
  395.         XOR     A
  396.         JP      .lo079
  397. .lo039:
  398. ; 133.              }else if(result & USB_A_DONE)                                           // know this condition and exit gracefully  
  399.         BIT     0,B
  400.         JR      Z,.lo033
  401. .lo040:
  402. ; 134.                  break;                          // interrupt done !!!  
  403. .lo041:
  404. .lo035:
  405. ; 135.          }  
  406. ; 136.     
  407. ; 137.          SL811Write(IntStatus,INT_CLEAR); // clear interrupt status  
  408.         LD      B,0x80
  409.         WRITE_REG .IntStatus,.INT_CLEAR
  410. ; 138.          result    = SL811Read(EP0Status);                       // read EP0status register  
  411.         LD      A,3
  412.         LD      B,0x80
  413.         OUT     (C),A
  414.         IN      a,(0xab)
  415.         LD      h,a
  416.         LD      IYH,a
  417. ; 139.          remainder = SL811Read(EP0Counter);                      // remainder value in last pkt xfer  
  418.         LD      A,4
  419.         OUT     (C),A
  420.         IN      a,(0xab)
  421.         LD      L,A
  422.         LD      IYL,A
  423. ; 140.     
  424. ; 141.          //-------------------------ACK----------------------------  
  425. ; 142.          if (result & EP0_ACK)                                   // Transmission ACK  
  426.         BIT     0,H
  427.         JP      Z,.lo063
  428. .lo042:
  429. ; 143.          {      
  430. ; 144.     
  431. ; 145.              // SETUP TOKEN  
  432. ; 146.              if(.usbstack.pid == PID_SETUP)                               // do nothing for SETUP/OUT token    
  433.         LD      A,(.usbstack+2)
  434.         CP      208
  435.         JP      Z,.lo032
  436. .lo044:
  437. ; 147.                  break;                                          // exit while(1) immediately    
  438. .lo045:
  439. ; 148.              // OUT TOKEN                  
  440. ; 149.              else if(.usbstack.pid == PID_OUT)  
  441.         CP      16
  442.         JP      Z,.lo032
  443. .lo046:
  444. ; 150.                  break;    
  445. .lo047:
  446. ; 151.              // IN TOKEN  
  447. ; 152.              else if(.usbstack.pid == PID_IN)  
  448.         CP      144
  449.         JP      NZ,.lo063
  450. .lo048:
  451. ; 153.              {                                                   // for IN token only  
  452. ; 154.                  .usbstack.wLen  -= (WORD)xferLen;    // update remainding wLen value  
  453.         LD      HL,.usbstack+3
  454.         LD      C,IXL
  455.         LD      B,0
  456.         LD      A,(HL)
  457.         SUB     C
  458.         LD      (HL),A
  459.         INC     HL
  460.         LD      A,(HL)
  461.         SBC     A,B
  462.         LD      (HL),A
  463. ; 155.                  cmd   ^= 0x40;              // toggle DATA0/DATA1  
  464.         LD      A,D
  465.         XOR     64
  466.         LD      D,A
  467. ; 156.                  dataX ^= 0x40;                // point to next dataX    
  468.         LD      A,E
  469.         XOR     64
  470.         LD      E,A
  471. ; 157.                  //------------------------------------------------    
  472. ; 158.                  // If host requested for more data than the slave    
  473. ; 159.                  // have, and if the slave's data len is a multiple  
  474. ; 160.                  // of its endpoint payload size/last xferLen. Do    
  475. ; 161.                  // not overwrite data in previous buffer.  
  476. ; 162.                  //------------------------------------------------    
  477. ; 163.                  if(remainder==xferLen)          // empty data detected  
  478.         LD      A,IYL
  479.         CP      C
  480.         JR      NZ,.lo051
  481. .lo050:
  482. ; 164.                      bufLen = 0;         // do not overwriten previous data  
  483.         LD      IXH,0
  484. ; 165.                  else                    // reset bufLen to zero  
  485.         JR      .lo052
  486. .lo051:
  487. ; 166.                      bufLen = xferLen;       // update previous buffer length  
  488.         LD      IXH,IXL
  489. .lo052:
  490. ; 167.                     
  491. ; 168.                  //------------------------------------------------    
  492. ; 169.                  // Arm for next data transfer when requested data    
  493. ; 170.                  // length have not reach zero, i.e. wLen!=0, and  
  494. ; 171.                  // last xferlen of data was completed, i.e.  
  495. ; 172.                  // remainder is equal to zero, not a short pkt  
  496. ; 173.                  //------------------------------------------------    
  497. ; 174.                  if(!remainder && .usbstack.wLen)                         // remainder==0 when last xferLen  
  498.         LD      B,IYL
  499.         INC     B
  500.         DEC     B
  501.         JR      NZ,.lo054
  502.         LD      HL,(.usbstack+3)
  503.         LD      A,L
  504.         OR      H
  505.         JR      Z,.lo054
  506. .lo056:
  507. .lo055:
  508. .lo053:
  509. ; 175.                  {                                               // was all completed or wLen!=0  
  510. ; 176.                      xferLen = (BYTE)(.usbstack.wLen>=64) ? 64:.usbstack.wLen;    // get data length required  
  511.         LD      C,64
  512.         SBC     HL,BC
  513.         JR      C,.lo058
  514.         LD      A,C
  515.         JR      .lo059
  516. .lo058:
  517.         LD      A,(.usbstack+3)
  518. .lo059:
  519.         LD      IXL,A
  520. ; 177.                                     
  521. ; 178.                      SL811Write(.ep0XferLen, xferLen);            // select next xfer length  
  522.         LD      A,2
  523.         LD      BC,0x80ab
  524.         OUT     (C),A
  525.         LD      A,IXL
  526.         dec B   ;LD     B,0x7f
  527.         OUT     (C),A
  528.         inc B
  529. ; 179.                      SL811Write(EP0Address, dataX); //addr);               // data buffer addr    
  530.         LD      A,1
  531.         OUT     (C),A
  532.         dec B
  533.         OUT     (C),E
  534.         inc B
  535. ; 180.                      SL811Write(IntStatus,INT_CLEAR);            // is a LS is on Hub.  
  536.         LD      A,13
  537.         OUT     (C),A
  538.         LD      A,255
  539.         dec B
  540.         OUT     (C),A
  541.         inc B
  542. ; 181.                      SL811Write(EP0Control,cmd);                 // Enable USB transfer and re-arm  
  543.         XOR     A
  544.         LD      B,0x80
  545.         OUT     (C),A
  546.         dec B
  547.         LD      B,0x7f
  548.         OUT     (C),D
  549. .lo054:
  550. ; 182.                                  }                    
  551. ; 183.                  //------------------------------------------------  
  552. ; 184.                  // Copy last IN token data pkt from prev transfer  
  553. ; 185.                  // Check if there was data available during the  
  554. ; 186.                  // last data transfer  
  555. ; 187.                  //------------------------------------------------  
  556. ; 188.                  if(bufLen)                                        
  557.         LD      B,IXH
  558.         INC     B
  559.         DEC     B
  560.         JR      Z,.lo061
  561. .lo060:
  562. ; 189.                  {      
  563. ; 190.                      SL811BufRead(dataX^0x40, .usbstack.buffer, bufLen);  
  564.         PUSH    DE
  565.         LD      HL,.usbstack+5
  566.         LD      C,(HL)
  567.         INC     HL
  568.         LD      B,(HL)
  569.         PUSH    BC
  570.         LD      C,IXH
  571.         LD      A,E
  572.         XOR     64
  573.         LD      E,A
  574.         CALL    SL811BUFREAD
  575.         POP     HL
  576.         POP     DE
  577. ; 191.                      .usbstack.buffer += bufLen;                                
  578.         LD      HL,.usbstack+5
  579.         LD      C,IXH
  580.         LD      B,0
  581.         LD      A,(HL)
  582.         ADD     A,C
  583.         LD      (HL),A
  584.         INC     HL
  585.         LD      A,(HL)
  586.         ADC     A,B
  587.         LD      (HL),A
  588. .lo061:
  589. ; 192.                  }  
  590. ; 193.                  //------------------------------------------------  
  591. ; 194.                  // Terminate on short packets, i.e. remainder!=0  
  592. ; 195.                  // a short packet or empty data packet OR when    
  593. ; 196.                  // requested data len have completed, i.e.wLen=0  
  594. ; 197.                  // For a LOWSPEED device, the 1st device descp,  
  595. ; 198.                  // wPayload is default to 64-byte, LS device will  
  596. ; 199.                  // only send back a max of 8-byte device descp,  
  597. ; 200.                  // and host detect this as a short packet, and    
  598. ; 201.                  // terminate with OUT status stage  
  599. ; 202.                  //------------------------------------------------  
  600. ; 203.                  if(remainder || !.usbstack.wLen)  
  601.         LD      B,IYL
  602.         INC     B
  603.         DEC     B
  604.         JR      NZ,.lo032
  605.         LD      HL,(.usbstack+3)
  606.         LD      A,L
  607.         OR      H
  608.         JR      Z,.lo032
  609. .lo064:
  610. .lo065:
  611. .lo062:
  612. ; 204.                      break;  
  613. .lo063:
  614. .lo049:
  615. .lo043:
  616. ; 205.              }// PID IN                            
  617. ; 206.          }  
  618. ; 207.                 
  619. ; 208.          //-------------------------NAK----------------------------  
  620. ; 209.          if (result & EP0_NAK)                                   // NAK Detected  
  621.         LD      B,IYH
  622.         BIT     6,B
  623.         JR      Z,.lo067
  624. .lo066:
  625. ; 210.          {                                                          
  626. ; 211.                  SL811Write(IntStatus,INT_CLEAR);                // clear interrupt status, need to  
  627.         LD      BC,0x80ab
  628.         WRITE_REG .IntStatus,.INT_CLEAR
  629. ; 212.                  SL811Write(EP0Control,cmd);                     // re-arm and request for last cmd, IN token  
  630.         XOR     A
  631.         OUT     (C),A
  632.         dec B
  633.         OUT     (C),D
  634. ; 213.                                  result = 0;                                     // respond to NAK status only  
  635.         LD      IYH,0
  636. .lo067:
  637. ; 214.          }        
  638. ; 215.          //-----------------------TIMEOUT--------------------------  
  639. ; 216.          if (result & EP0_TIMEOUT)                               // TIMEOUT Detected  
  640.         LD      B,IYH
  641.         BIT     2,B
  642.         JR      Z,.lo074
  643. .lo068:
  644. ; 217.          {                                                          
  645. ; 218.              if(.usbstack.endpoint==0)                                        // happens when hub enumeration  
  646.         LD      A,(.usbstack+1)
  647.         OR      A
  648.         JR      NZ,.lo032
  649. .lo070:
  650. ; 219.              {  
  651. ; 220.                  if((--timeout)==0)  
  652.         LD      L,A
  653.         LD      H,A
  654.         ADD     HL,SP
  655.         DEC     (HL)
  656.         OR      (HL)
  657.         JR      Z,.lo032
  658. .lo072:
  659. ; 221.                  {      
  660. ; 222.                      break;                                      // exit on the timeout detected    
  661. .lo073:
  662. ; 223.                  }  
  663. ; 224.                  SL811Write(IntStatus,INT_CLEAR);                // clear interrupt status, need to  
  664.         LD      BC,0x80ab
  665.         WRITE_REG .IntStatus,.INT_CLEAR
  666. ; 225.                  SL811Write(EP0Control,cmd);                     // re-arm and request for last cmd again  
  667.         XOR     A
  668.         OUT     (C),A
  669.         dec B
  670.         OUT     (C),D
  671. ; 226.                          }  
  672. ; 227.              else                                                  
  673. .lo071:
  674. ; 228.              {                                                   // all other data endpoint, data transfer    
  675. ; 229.                  break;                                          // happens when data transfer on a device  
  676. .lo074:
  677. .lo069:
  678. ; 230.              }                                                   // through the hub  
  679. ; 231.          }    
  680. ; 232.          //-----------------------STALL----------------------------  
  681. ; 233.          if (result & EP0_STALL)                                 // STALL detected  
  682.         LD      B,IYH
  683.         BIT     7,B
  684.         JR      Z,.lo076
  685. .lo075:
  686. ; 234.              return TRUE;                                        // for unsupported request.                                                                            
  687.         LD      A,1
  688.         JR      .lo079
  689. .lo076:
  690. ; 235.          //----------------------OVEFLOW---------------------------  
  691. ; 236.          if (result & (EP0_OVERFLOW|EP0_ERROR))                              // OVERFLOW detected  
  692.         LD      A,IYH
  693.         AND     34
  694.         JP      Z,.lo033
  695. .lo077:
  696. ; 237.              break;  
  697. .lo078:
  698. .lo032:
  699. ; 238.          //-----------------------ERROR----------------------------  
  700. ; 239.      }   // end of While(1)  
  701. ; 240.      return result & EP0_ACK;
  702.         LD      A,IYH
  703.         AND     1
  704. ; 241.  }  
  705. .lo079:
  706.         POP     HL
  707.         POP     IX
  708.         POP     IY
  709.         POP     DE
  710.         POP     BC
  711.         RET
  712. ; 242.  //*****************************************************************************************  
  713. ; 243.  // Control Endpoint 0's USB Data Xfer  
  714. ; 244.  // .ep0Xfer, endpoint 0 data transfer  
  715. ; 245.  //*****************************************************************************************  
  716. ; 246.  unsigned char .ep0Xfer(void)  
  717. ; 247.  {  
  718. .ep0Xfer:
  719.         PUSH    DE
  720. ; 248.      .usbstack.endpoint=0;  
  721.         XOR     A
  722.         LD      (.usbstack+1),A
  723. ; 249.      //----------------------------------------------------  
  724. ; 250.      // SETUP token with 8-byte request on endpoint 0  
  725. ; 251.      //----------------------------------------------------  
  726. ; 252.      .usbstack.pid=PID_SETUP;  
  727.         LD      A,208
  728.         LD      (.usbstack+2),A
  729. ; 253.      .usbstack.wLen=8;  
  730.         LD      HL,8
  731.         LD      (.usbstack+3),HL
  732. ; 254.      if (!.usbXfer())
  733.         CALL    .usbXfer
  734.         OR      A
  735.         JR      Z,.lo191
  736. .lo080:
  737. ; 255.          {      
  738. ; 256.                  return FALSE;
  739. ; 257.          }
  740. .lo081:
  741. ; 258.      .usbstack.pid  = PID_IN;  
  742.         LD      A,144
  743.         LD      (.usbstack+2),A
  744. ; 259.      //----------------------------------------------------  
  745. ; 260.      // IN or OUT data stage on endpoint 0      
  746. ; 261.      //----------------------------------------------------  
  747. ; 262.      .usbstack.wLen=.usbstack.setup.wLength;  
  748.         LD      HL,(.usbstack+13)
  749.         LD      (.usbstack+3),HL
  750. ; 263.      if (.usbstack.wLen)                                          // if there are data for transfer  
  751.         LD      A,L
  752.         OR      H
  753.         JR      Z,.lo088
  754. .lo082:
  755. ; 264.      {  
  756. ; 265.          if (.usbstack.setup.bmRequest & 0x80)        // host-to-device : IN token  
  757.         LD      A,(.usbstack+7)
  758.         OR      A
  759.         JP      P,.lo085
  760. .lo084:
  761. ; 266.          {  
  762. ; 267.              .usbstack.pid  = PID_IN;    
  763.         LD      A,144
  764.         LD      (.usbstack+2),A
  765. ; 268.                 
  766. ; 269.              if(!.usbXfer())
  767.         CALL    .usbXfer
  768.         OR      A
  769.         JR      Z,.lo191
  770. .lo086:
  771. ; 270.                          {      
  772. ; 271.                                  return FALSE;
  773. ; 272.                          }
  774. .lo087:
  775. ; 273.              .usbstack.pid  = PID_OUT;  
  776.         LD      A,16
  777.         JR      .lo188
  778. ; 274.          }  
  779. ; 275.          else                                            // device-to-host : OUT token  
  780. .lo085:
  781. ; 276.          {
  782. ; 277.              .usbstack.pid  = PID_OUT;  
  783.         LD      A,16
  784.         LD      (.usbstack+2),A
  785. ; 278.                     
  786. ; 279.              if(!.usbXfer())
  787.         CALL    .usbXfer
  788.         OR      A
  789.         JR      Z,.lo191
  790. .lo089:
  791. ; 280.                          {      
  792. ; 281.                                  return FALSE;
  793. ; 282.                          }
  794. .lo090:
  795. ; 283.              .usbstack.pid  = PID_IN;  
  796.         LD      A,144
  797. .lo188:
  798.         LD      (.usbstack+2),A
  799. .lo088:
  800. .lo083:
  801. ; 284.          }  
  802. ; 285.      }  
  803. ; 286.      .delayms(10);  
  804.         LD      E,1
  805.         CALL    .delayms
  806. ; 287.      //----------------------------------------------------  
  807. ; 288.      // Status stage IN or OUT zero-length data packet  
  808. ; 289.      //----------------------------------------------------  
  809. ; 290.      .usbstack.wLen=0;  
  810.         LD      HL,0
  811.         LD      (.usbstack+3),HL
  812. ; 291.      if(!.usbXfer())
  813.         CALL    .usbXfer
  814.         OR      A
  815.         JR      NZ,.lo092
  816. .lo091:
  817. ; 292.          {      
  818. ; 293.                  return FALSE;
  819. .lo191:
  820.         XOR     A
  821. ; 294.          }
  822.         JR      .lo093
  823. .lo092:
  824. ; 295.      return TRUE;                                              
  825.         LD      A,1
  826. ; 296.  }  
  827. .lo093:
  828.         POP     DE
  829.         RET
  830. ; 297. 
  831. ; 298.  unsigned char .epBulkSend(unsigned char *pBuffer,unsigned int len)  
  832. ; 299.  {
  833. .epBulkSend:
  834.         PUSH    IX
  835.         PUSH    DE
  836.         PUSH    BC
  837.         POP     IX
  838. ; 300.      .usbstack.usbaddr=myusbaddr;  
  839.         LD      A,1
  840.         LD      (.usbstack),A
  841. ; 301.      .usbstack.endpoint=.usbstack.epbulkout;  
  842.         LD      A,(.usbstack+16)
  843.         LD      (.usbstack+1),A
  844. ; 302.      .usbstack.pid=PID_OUT;    
  845.         LD      A,16
  846.         LD      (.usbstack+2),A
  847. ; 303.      .usbstack.wLen=len;  
  848.         LD      (.usbstack+3),BC
  849. ; 304.      .usbstack.buffer=pBuffer;  
  850.         LD      L,E
  851.         LD      H,D
  852.         LD      (.usbstack+5),HL
  853. .lo095:
  854. ; 305.      while(len>0)  
  855.         LD      A,IXL
  856.         OR      IXH
  857.         JR      Z,.lo094
  858. .lo096:
  859. ; 306.      {  
  860. ; 307.          if (len >= 64)  
  861.         LD      BC,64
  862.         PUSH    IX
  863.         POP     HL
  864.         SBC     HL,BC
  865.         JR      C,.lo098
  866. .lo097:
  867. ; 308.              .usbstack.wLen = 64;  
  868.         LD      L,C
  869.         LD      H,B
  870.         JR      .lo193
  871. ; 309.          else                  
  872. .lo098:
  873. ; 310.              .usbstack.wLen = len;
  874.         PUSH    IX
  875.         POP     HL
  876. .lo193:
  877.         LD      (.usbstack+3),HL
  878. .lo099:
  879. ; 311.          disable_interrupt();
  880.         DI
  881. .lo101:
  882. ; 312.          while(!.usbXfer()){
  883.         CALL    .usbXfer
  884.         OR      A
  885.         EI
  886.         JR      Z,.lo103
  887. .lo102:
  888. ; 313.                  enable_interrupt();
  889. ; 314.                  puts(".epBulkSend ERROR");
  890. ; 315.              return FALSE;
  891. ; 316.          }
  892. .lo100:
  893. ; 317.          enable_interrupt();
  894. ; 318.          len-=.usbstack.wLen;  
  895.         LD      BC,(.usbstack+3)
  896.         PUSH    IX
  897.         POP     HL
  898.         AND     A
  899.         SBC     HL,BC
  900.         PUSH    HL
  901.         POP     IX
  902. ; 319.          .usbstack.buffer=.usbstack.buffer+.usbstack.wLen;  
  903.         LD      HL,.usbstack+5
  904.         LD      A,(HL)
  905.         ADD     A,C
  906.         LD      (HL),A
  907.         INC     HL
  908.         LD      A,(HL)
  909.         ADC     A,B
  910.         LD      (HL),A
  911.         JR      .lo095
  912. .lo094:
  913. ; 320.      }  
  914. ; 321.      return TRUE;      
  915.         LD      A,1
  916. ; 322.  }  
  917. .lo103:
  918.         POP     HL
  919.         POP     IX
  920.         RET
  921. ; 323.     
  922. ; 324.  unsigned char .epBulkRcv(unsigned char *pBuffer,unsigned int len)  
  923. ; 325.  {  
  924. .epBulkRcv:
  925.         PUSH    IX
  926.         LD      IX,0
  927.         ADD     IX,SP
  928.         PUSH    BC
  929.         PUSH    DE
  930. ; 326.      .usbstack.usbaddr=myusbaddr;  
  931.         LD      A,1
  932.         LD      (.usbstack),A
  933. ; 327.      .usbstack.endpoint=.usbstack.epbulkin;  
  934.         LD      A,(.usbstack+15)
  935.         LD      (.usbstack+1),A
  936. ; 328.      .usbstack.pid=PID_IN;    
  937.         LD      A,144
  938.         LD      (.usbstack+2),A
  939. ; 329.      .usbstack.wLen=len;  
  940.         LD      (.usbstack+3),BC
  941. ; 330.      .usbstack.buffer=pBuffer;
  942.         LD      (.usbstack+5),DE
  943. ; 331.      if(.usbstack.wLen)  
  944.         LD      A,C
  945.         LD      H,B
  946.         OR      H
  947.         JR      Z,.lo106
  948. .lo104:
  949. ; 332.      {    
  950. ; 333.          disable_interrupt();  
  951.         DI
  952. .lo107:
  953. ; 334.          while(!.usbXfer()){
  954.         CALL    .usbXfer
  955.         OR      A
  956.         EI
  957.         JR      Z,.lo109
  958. .lo108:
  959. ; 335.                  enable_interrupt();
  960. ; 336.              return FALSE;
  961. ; 337.          }
  962. .lo106:
  963. ; 338.          enable_interrupt();    
  964. .lo105:
  965. ; 339.      }  
  966. ; 340.      return TRUE;  
  967.         LD      A,1
  968. ; 341.  }  
  969. .lo109:
  970.         LD      SP,IX
  971.         POP     IX
  972.         RET
  973. ; 342.     
  974. ; 343.  //*****************************************************************************************  
  975. ; 344.  // Set Device Address :    
  976. ; 345.  //*****************************************************************************************  
  977. ; 346.  unsigned char SetAddress(unsigned char addr)  
  978. ; 347.  {  
  979. .SetAddress:
  980.         PUSH    BC
  981.         PUSH    DE
  982. ; 348.      .usbstack.usbaddr=0;  
  983.         XOR     A
  984.         LD      (.usbstack),A
  985. ; 349.      .usbstack.setup.bmRequest=0;  
  986.         LD      (.usbstack+7),A
  987. ; 350.      .usbstack.setup.bRequest=SET_ADDRESS;  
  988.         LD      A,5
  989.         LD      (.usbstack+8),A
  990. ; 351.      .usbstack.setup.wValue=addr;  
  991.         LD      C,E
  992.         LD      B,0
  993.         LD      (.usbstack+9),BC
  994. ; 352.      .usbstack.setup.wIndex=0;  
  995.         LD      L,B
  996.         LD      H,B
  997.         LD      (.usbstack+11),HL
  998. ; 353.      .usbstack.setup.wLength=0;  
  999.         LD      (.usbstack+13),HL
  1000. ; 354.      return .ep0Xfer();  
  1001.         CALL    .ep0Xfer
  1002. ; 355.  }  
  1003.         POP     HL
  1004.         POP     BC
  1005.         RET
  1006. ; 356..
  1007. ; 357.  //*****************************************************************************************  
  1008. ; 358.  // Set Device Configuration :    
  1009. ; 359.  //*****************************************************************************************  
  1010. ; 360.  unsigned char Set_Configuration(void)  
  1011. ; 361.  {  
  1012. .Set_Configuration:
  1013. ; 362.      .usbstack.setup.bmRequest=0;  
  1014.         XOR     A
  1015.         LD      (.usbstack+7),A
  1016. ; 363.      .usbstack.setup.bRequest=SET_CONFIG;  
  1017.         LD      A,9
  1018.         LD      (.usbstack+8),A
  1019. ; 364.      .usbstack.setup.wIndex=0;  
  1020.         LD      HL,0
  1021.         LD      (.usbstack+11),HL
  1022. ; 365.      .usbstack.setup.wLength=0;  
  1023.         LD      (.usbstack+13),HL
  1024. ; 366.      .usbstack.buffer=NULL;  
  1025.         LD      (.usbstack+5),HL
  1026. ; 367.      return .ep0Xfer();  
  1027.         JP      .ep0Xfer
  1028. ; 368.  }
  1029. ; 369. 
  1030. ; 370.  //*****************************************************************************************  
  1031. ; 371.  // Get Device Descriptor : Device, Configuration, String  
  1032. ; 372.  //*****************************************************************************************  
  1033. ; 373.  unsigned char GetDesc(void)  
  1034. ; 374.  {    
  1035. .GetDesc:
  1036.         PUSH    BC
  1037. ; 375.      .usbstack.setup.bmRequest=0x80;  
  1038.         LD      A,0x80
  1039.         LD      (.usbstack+7),A
  1040. ; 376.      .usbstack.setup.bRequest=GET_DESCRIPTOR;  
  1041.         LD      A,6
  1042.         LD      (.usbstack+8),A
  1043. ; 377.      .usbstack.setup.wValue=.usbstack.setup.wValue<<8;
  1044.         LD      HL,.usbstack+9
  1045.         LD      B,(HL)
  1046.         LD      (HL),0
  1047.         INC     HL
  1048.         LD      (HL),B
  1049. ; 378.      return .ep0Xfer();  
  1050.         CALL    .ep0Xfer
  1051. ; 379.  }  
  1052.         POP     BC
  1053.         RET
  1054. ; 380.     
  1055. ; 381.  //*****************************************************************************************  
  1056. ; 382.  // USB Device Enumeration Process  
  1057. ; 383.  // Support 1 confguration and interface #0 and alternate setting #0 only  
  1058. ; 384.  // Support up to 1 control endpoint + 4 data endpoint only  
  1059. ; 385.  //*****************************************************************************************  
  1060. ; 386.  unsigned char EnumUsbDev(void)  
  1061. ; 387.  {
  1062. .EnumUsbDev:
  1063.         PUSH    BC
  1064.         PUSH    DE
  1065.         PUSH    IX
  1066.         PUSH    AF
  1067.         PUSH    AF
  1068. ; 388.      unsigned char i;                                    // always reset USB transfer address    
  1069. ; 389.      unsigned char uAddr = 0;                            // for enumeration to Address #0  
  1070. ; 390.      unsigned char epLen;
  1071. ; 391. 
  1072. ; 392.      //------------------------------------------------  
  1073. ; 393.      // Reset only Slave device attached directly  
  1074. ; 394.      //------------------------------------------------  
  1075. ; 395.      //.uDev.wPayLoad[0] = 64;  // default 64-byte payload of Endpoint 0, address #0  
  1076. ; 396.      if(myusbaddr == 1)        // bus reset for the device attached to SL811HS only  
  1077. .lo110:
  1078. ; 397.          USBReset();     // that will always have the USB address = 0x01 (for a hub)
  1079.         CALL    .USBReset
  1080. .lo111:
  1081. ; 398.      //------------------------------------------------  
  1082. ; 399.      // Set Slave USB Device Address  
  1083. ; 400.      //------------------------------------------------
  1084. ; 401.      if (!SetAddress(myusbaddr))                       // set to specific USB address  
  1085.         LD      E,1
  1086.         CALL    .SetAddress
  1087.         OR      A
  1088.         JR      Z,.lo198
  1089. .lo112:
  1090. ; 402.          return FALSE;                               //  
  1091. .lo113:
  1092. ; 403.      uAddr = myusbaddr;                                // transfer using this new address  
  1093. ; 404. 
  1094. ; 405.      //------------------------------------------------  
  1095. ; 406.      // Get Slave USB Configuration Descriptors  
  1096. ; 407.      //------------------------------------------------  
  1097. ; 408.      .usbstack.usbaddr=uAddr;  
  1098.         LD      A,1
  1099.         LD      (.usbstack),A
  1100. ; 409.      .usbstack.setup.wValue=CONFIGURATION;  
  1101.         LD      HL,2
  1102.         LD      (.usbstack+9),HL
  1103. ; 410.      .usbstack.setup.wIndex=0;  
  1104.         DEC     HL
  1105.         DEC     HL
  1106.         LD      (.usbstack+11),HL
  1107. ; 411.      .usbstack.setup.wLength=64;  
  1108.         LD      L,64
  1109.         LD      (.usbstack+13),HL
  1110. ; 412.      .usbstack.buffer=.DBUF;      
  1111.         LD      HL,.DBUF
  1112.         LD      (.usbstack+5),HL
  1113. ; 413.      if (!GetDesc())
  1114.         LD      IXH,1
  1115.         CALL    .GetDesc
  1116.         OR      A
  1117.         JR      Z,.lo198
  1118. .lo114:
  1119. ; 414.          return FALSE;        
  1120. .lo115:
  1121. ; 415.      .uDev.bNumOfEPs = (.DBUF[9+4] <= MAX_EP) ? .DBUF[9+4] : MAX_EP;  
  1122.         LD      A,(.DBUF+13)
  1123.         LD      B,A
  1124.         LD      A,5
  1125.         CP      B
  1126.         JR      C,.lo117
  1127.         LD      A,(.DBUF+13)
  1128. .lo117:
  1129.         LD      (.uDev),A
  1130. ; 416.      if(.DBUF[9+5]==8) //mass storage device  
  1131.         LD      A,(.DBUF+14)
  1132.         CP      8
  1133.         JR      NZ,.lo120
  1134. .lo119:
  1135. ; 417.          .bFlags.bits.bMassDevice=TRUE;  
  1136.         LD      A,1
  1137.         LD      (.bFlags),A
  1138. .lo120:
  1139. ; 418.      //------------------------------------------------  
  1140. ; 419.      // Set configuration (except for HUB device)  
  1141. ; 420.      //------------------------------------------------  
  1142. ; 421.      .usbstack.usbaddr=uAddr;  
  1143.         LD      A,IXH
  1144.         LD      (.usbstack),A
  1145. ; 422.      .usbstack.setup.wValue=DEVICE;  
  1146.         LD      HL,1
  1147.         LD      (.usbstack+9),HL
  1148. ; 423.                                          // enumerating a FS/LS non-hub device  
  1149. ; 424.          if (!Set_Configuration())       // connected directly to SL811HS  
  1150.         CALL    .Set_Configuration
  1151.         OR      A
  1152.         JR      NZ,.lo122
  1153. .lo121:
  1154. ; 425.                  return FALSE;  
  1155. .lo198:
  1156.         XOR     A
  1157.         JR      .lo132
  1158. .lo122:
  1159. ; 426. 
  1160. ; 427.      //------------------------------------------------  
  1161. ; 428.      // For each slave endpoints, get its attributes  
  1162. ; 429.      // Excluding endpoint0, only data endpoints  
  1163. ; 430.      //------------------------------------------------  
  1164. ; 431. 
  1165. ; 432.      epLen = 0;  
  1166. ; 433.      for (i=1; i<=.uDev.bNumOfEPs; i++)                // For each data endpoint  
  1167.         LD      E,0
  1168.         LD      IXL,1
  1169. .lo124:
  1170.         LD      A,(.uDev)
  1171.         CP      IXL
  1172.         JR      C,.lo123
  1173. .lo125:
  1174. ; 434.      {
  1175. ; 435.          unsigned char bEPAddr  = .DBUF[9 + 9 + epLen+2];    // Ep address and direction  
  1176.         LD      HL,.DBUF+20
  1177.         LD      C,E
  1178.         LD      B,0
  1179.         ADD     HL,BC
  1180.         LD      D,(HL)
  1181. ; 436.          if(.DBUF[9 + 9 + epLen+3]==0x2)     //bulk transfer  
  1182.         LD      HL,.DBUF+21
  1183.         ADD     HL,BC
  1184.         LD      B,(HL)
  1185.         DEC     B
  1186.         DEC     B
  1187.         JR      NZ,.lo131
  1188. .lo127:
  1189. ; 437.          {
  1190. ; 438.              if(bEPAddr&0x80)
  1191.         BIT     7,D
  1192.         LD      A,D
  1193.         JR      Z,.lo130
  1194. .lo129:
  1195. ; 439.                  .usbstack.epbulkin=bEPAddr;
  1196.         LD      (.usbstack+15),A
  1197. ; 440.              else  
  1198.         JR      .lo131
  1199. .lo130:
  1200. ; 441.                  .usbstack.epbulkout=bEPAddr;
  1201.         LD      (.usbstack+16),A
  1202. .lo131:
  1203. .lo128:
  1204. ; 442.          }          
  1205. ; 443.          .uDev.bData1[i] = 0;                     // init data toggle  
  1206.         LD      HL,.uDev+1
  1207.         LD      C,IXL
  1208.         LD      B,0
  1209.         ADD     HL,BC
  1210.         LD      (HL),B
  1211. ; 444.          epLen += 7;  
  1212.         LD      A,E
  1213.         ADD     A,7
  1214.         LD      E,A
  1215.         INC     IXL
  1216.         JR      .lo124
  1217. .lo123:
  1218. ; 445.          //////////////////////////////  
  1219. ; 446.          //////////////////////////////  
  1220. ; 447.      }
  1221. ; 448.      return TRUE;  
  1222.         LD      A,1
  1223. ; 449.  }
  1224. .lo132:
  1225.         POP     HL
  1226.         POP     HL
  1227.         POP     IX
  1228.         POP     DE
  1229.         POP     BC
  1230.         RET
  1231. ; 450.  unsigned char .outbuf[0x20];  
  1232. ; 451.  ///////////////////////////////////////////////////////////////////////////  
  1233. ; 452.  unsigned char EnumMassDev(void)  
  1234. ; 453.  {  
  1235. .EnumMassDev:
  1236. ; 454.      if(!.SPC_Inquiry())
  1237.         CALL    .SPC_Inquiry
  1238.         OR      A
  1239.         JR      NZ,.lo134
  1240. .lo133:
  1241. ; 455.          return 0x81;//FALSE;  
  1242.         LD      A,1
  1243.         RET
  1244. .lo134:
  1245. ; 456.      if(!SPC_TestUnit())  
  1246.         CALL    .SPC_TestUnit
  1247.         OR      A
  1248.         JR      NZ,.lo136
  1249. .lo135:
  1250. ; 457.          return 0x82;//FALSE;  
  1251.         LD      A,1
  1252.         RET
  1253. .lo136:
  1254. ; 458.      if(!SPC_LockMedia())  
  1255.         CALL    .SPC_LockMedia
  1256.         OR      A
  1257.         JR      NZ,.lo138
  1258. .lo137:
  1259. ; 459.          return 0x83;//FALSE;  
  1260.         LD      A,1
  1261.         RET
  1262. .lo138:
  1263. ; 460.      if(!SPC_RequestSense())  
  1264.         CALL    .SPC_RequestSense
  1265.         OR      A
  1266.         JR      NZ,.lo140
  1267. .lo139:
  1268. ; 461.          return 0x84;//FALSE;  
  1269.         LD      A,1
  1270.         RET
  1271. .lo140:
  1272. ; 462.      if(!SPC_TestUnit())  
  1273.         CALL    .SPC_TestUnit
  1274.         OR      A
  1275.         JR      NZ,.lo142
  1276. .lo141:
  1277. ; 463.          return 0x85;//FALSE;  
  1278.         LD      A,1
  1279.         RET
  1280. .lo142:
  1281. ; 464.      if(!.RBC_ReadCapacity())  
  1282.         CALL    .RBC_ReadCapacity
  1283.         OR      A
  1284.         JR      NZ,.lo144
  1285. .lo143:
  1286. ; 465.          return 0x86;//FALSE;  
  1287.         LD      A,1
  1288.         RET
  1289. .lo144:
  1290. ; 466.     
  1291. ; 467.      ////////////////////////////////////////////////////  
  1292. ; 468.      //DeviceInfo.BPB_BytesPerSec=512; //SectorSize 512  
  1293. ; 469.         
  1294. ; 470.      if(!SPC_RequestSense())  
  1295.         CALL    .SPC_RequestSense
  1296.         OR      A
  1297.         JR      NZ,.lo146
  1298. .lo145:
  1299. ; 471.          return 0x87;//FALSE;  
  1300.         LD      A,1
  1301.         RET
  1302. .lo146:
  1303. ; 472.      if(!SPC_TestUnit())  
  1304.         CALL    .SPC_TestUnit
  1305.         OR      A
  1306.         JR      NZ,.lo148
  1307. .lo147:
  1308. ; 473.          return 0x88;//FALSE;  
  1309.         LD      A,1
  1310.         RET
  1311. .lo148:
  1312. ; 474.      if(!.RBC_ReadCapacity())  
  1313.         CALL    .RBC_ReadCapacity
  1314.         OR      A
  1315.         JR      NZ,.lo150
  1316. .lo149:
  1317. ; 475.          return 0x89;//FALSE;  
  1318.         LD      A,1
  1319.         RET
  1320. .lo150:
  1321. ; 476.      ////////////////////////////////////////////////////  
  1322. ; 477.      //if(!.RBC_Read(0x0,1,.DBUF))  
  1323. ; 478.      //   return 0x8a;//FALSE;  
  1324. ; 479.      //////////////////////////////////
  1325. ; 480. 
  1326. ; 481.      return TRUE;  
  1327.         LD      A,0
  1328. ; 482.  }  
  1329. .lo151:
  1330.         RET
  1331. ; 483. 
  1332. ; 484.  const unsigned char .data00[25]={
  1333. ; 485.          0x55,0x53,0x42,0x43,0x60,0xa6,0x24,0xde,  
  1334. ; 486.          0x24,0x00,0x00,0x00,0x80,0x00,0x06,SPC_CMD_INQUIRY,
  1335. ; 487.          0x00,0x00,0x00,0x24,};
  1336. ; 488.               
  1337. ; 489.  unsigned char .SPC_Inquiry(void)  
  1338. ; 490.  {  
  1339. .SPC_Inquiry:
  1340.         PUSH    BC
  1341.         PUSH    DE
  1342. ; 491.      memcpy(.outbuf,.data00,21);
  1343.         LD      BC,21
  1344.         LD      DE,.outbuf
  1345.         LD      HL,.data00
  1346.         LDIR
  1347. ; 492.      if(!.epBulkSend(.outbuf,0x1f))      
  1348.         CALL    .lo208
  1349.         OR      A
  1350.         JR      Z,.lo201
  1351. .lo152:
  1352. ; 493.          return FALSE;  
  1353. .lo153:
  1354. ; 494.      .delayms(150);  
  1355.         LD      E,8
  1356.         CALL    .delayms
  1357. ; 495.      if(!.epBulkRcv(.DBUF,36))  
  1358.         LD      BC,36
  1359.         LD      DE,.DBUF
  1360.         CALL    .epBulkRcv
  1361.         OR      A
  1362.         JR      Z,.lo201
  1363. .lo154:
  1364. ; 496.          return FALSE;      
  1365. .lo155:
  1366. ; 497.      if(!.epBulkRcv(.outbuf,13))  
  1367.         CALL    .lo210
  1368.         OR      A
  1369.         JR      NZ,.lo157
  1370. .lo156:
  1371. ; 498.          return FALSE;    
  1372. .lo201:
  1373.         XOR     A
  1374.         JR      .lo158
  1375. .lo157:
  1376. ; 499.      return TRUE;      
  1377.         LD      A,1
  1378. ; 500.  }  
  1379. .lo158:
  1380.         POP     DE
  1381.         POP     BC
  1382.         RET
  1383. .lo209:
  1384.         LD      (.outbuf+19),A
  1385. .lo208:
  1386.         LD      C,31
  1387.         LD      DE,.outbuf
  1388.         JP      .epBulkSend
  1389. .lo212:
  1390.         LD      E,1
  1391.         CALL    .delayms
  1392. .lo210:
  1393.         LD      BC,13
  1394. .lo211:
  1395.         LD      DE,.outbuf
  1396.         JP      .epBulkRcv
  1397. ; 501.     
  1398. ; 502.  unsigned char SPC_RequestSense(void)  
  1399. ; 503.  {  
  1400. .SPC_RequestSense:
  1401.         PUSH    BC
  1402.         PUSH    DE
  1403. ; 504.      memcpy(.outbuf,.data00,21);  
  1404.         LD      BC,21
  1405.         LD      DE,.outbuf
  1406.         LD      HL,.data00
  1407.         LDIR
  1408. ; 505.      .outbuf[8]=0x0e;  
  1409.         LD      A,14
  1410.         LD      (.outbuf+8),A
  1411. ; 506.      .outbuf[15]=SPC_CMD_REQUESTSENSE;
  1412.         LD      A,3
  1413.         LD      (.outbuf+15),A
  1414. ; 507.      .outbuf[19]=0x0e;        
  1415.         LD      A,14
  1416. ; 508.      if(!.epBulkSend(.outbuf,0x1f))      
  1417.         CALL    .lo209
  1418.         OR      A
  1419.         JR      Z,.lo203
  1420. .lo159:
  1421. ; 509.          return FALSE;  
  1422. .lo160:
  1423. ; 510.      .delayms(5);  
  1424.         LD      E,1
  1425.         CALL    .delayms
  1426. ; 511.      if(!.epBulkRcv(.outbuf,18))  
  1427.         LD      BC,18
  1428.         CALL    .lo211
  1429.         OR      A
  1430.         JR      Z,.lo203
  1431. .lo161:
  1432. ; 512.          return FALSE;
  1433. .lo162:
  1434. ; 513.      if(!.epBulkRcv(.outbuf,13))  
  1435.         CALL    .lo210
  1436.         OR      A
  1437.         JR      NZ,.lo164
  1438. .lo163:
  1439. ; 514.          return FALSE;    
  1440. .lo203:
  1441.         XOR     A
  1442.         JR      .lo165
  1443. .lo164:
  1444. ; 515.      return TRUE;  
  1445.         LD      A,1
  1446. ; 516.  }  
  1447. .lo165:
  1448.         POP     DE
  1449.         POP     BC
  1450.         RET
  1451. ; 517.     
  1452. ; 518.  unsigned char SPC_TestUnit(void)  
  1453. ; 519.  {  
  1454. .SPC_TestUnit:
  1455.         PUSH    BC
  1456.         PUSH    DE
  1457. ; 520.      memcpy(.outbuf,.data00,21);  
  1458.         LD      BC,21
  1459.         LD      DE,.outbuf
  1460.         LD      HL,.data00
  1461.         LDIR
  1462. ; 521.      ////////////////////////////////      
  1463. ; 522.      .outbuf[8]=0x00;  
  1464.         XOR     A
  1465.         LD      (.outbuf+8),A
  1466. ; 523.      .outbuf[12]=0x00;
  1467.         LD      (.outbuf+12),A
  1468. ; 524.      /////////////////////////////////////      
  1469. ; 525.      .outbuf[15]=SPC_CMD_TESTUNITREADY;  
  1470.         LD      (.outbuf+15),A
  1471. ; 526.      .outbuf[19]=0;  
  1472. ; 527.      //////////////////////////////////////  
  1473. ; 528.      if(!.epBulkSend(.outbuf,0x1f))
  1474.         CALL    .lo209
  1475.         OR      A
  1476.         JR      Z,.lo204
  1477. .lo166:
  1478. ; 529.          return FALSE;
  1479. .lo167:
  1480. ; 530.      .delayms(5);  
  1481. ; 531.      if(!.epBulkRcv(.outbuf,13))
  1482.         CALL    .lo212
  1483.         OR      A
  1484.         JR      NZ,.lo169
  1485. .lo168:
  1486. ; 532.          return FALSE;
  1487. .lo204:
  1488.         XOR     A
  1489.         JR      .lo170
  1490. .lo169:
  1491. ; 533.      return TRUE;  
  1492.         LD      A,1
  1493. ; 534.  }  
  1494. .lo170:
  1495.         POP     DE
  1496.         POP     BC
  1497.         RET
  1498. ; 535.     
  1499. ; 536.  unsigned char SPC_LockMedia(void)  
  1500. ; 537.  {  
  1501. .SPC_LockMedia:
  1502.         PUSH    BC
  1503.         PUSH    DE
  1504. ; 538.      memcpy(.outbuf,.data00,21);      
  1505.         LD      BC,21
  1506.         LD      DE,.outbuf
  1507.         LD      HL,.data00
  1508.         LDIR
  1509. ; 539.      .outbuf[8]=0x00;  
  1510.         XOR     A
  1511.         LD      (.outbuf+8),A
  1512. ; 540.      .outbuf[12]=0x00;
  1513.         LD      (.outbuf+12),A
  1514. ; 541.      .outbuf[14]=5;  
  1515.         LD      A,5
  1516.         LD      (.outbuf+14),A
  1517. ; 542.      ///////////////////////////////////////////  
  1518. ; 543.      .outbuf[15]=SPC_CMD_PRVENTALLOWMEDIUMREMOVAL;  
  1519.         LD      A,30
  1520.         LD      (.outbuf+15),A
  1521. ; 544.      .outbuf[19]=1;  
  1522.         LD      A,1
  1523. ; 545.      ///////////////////////////////////////////  
  1524. ; 546.      if(!.epBulkSend(.outbuf,0x1f))      
  1525.         CALL    .lo209
  1526.         OR      A
  1527.         JR      Z,.lo205
  1528. .lo171:
  1529. ; 547.          return FALSE;  
  1530. .lo172:
  1531. ; 548.      .delayms(5);  
  1532. ; 549.     
  1533. ; 550.      if(!.epBulkRcv(.outbuf,13))  
  1534.         CALL    .lo212
  1535.         OR      A
  1536.         JR      NZ,.lo174
  1537. .lo173:
  1538. ; 551.          return FALSE;  
  1539. .lo205:
  1540.         XOR     A
  1541.         JR      .lo175
  1542. .lo174:
  1543. ; 552.     
  1544. ; 553.  /////////////////////////////  
  1545. ; 554.      return TRUE;  
  1546.         LD      A,1
  1547. ; 555.  }  
  1548. .lo175:
  1549.         POP     DE
  1550.         POP     BC
  1551.         RET
  1552. ; 556.     
  1553. ; 557.  unsigned char .RBC_ReadCapacity(void)  
  1554. ; 558.  {  
  1555. .RBC_ReadCapacity:
  1556.         PUSH    BC
  1557.         PUSH    DE
  1558. ; 559.      memcpy(.outbuf,.data00,25);    
  1559.         LD      BC,25
  1560.         LD      DE,.outbuf
  1561.         LD      HL,.data00
  1562.         LDIR
  1563. ; 560.      .outbuf[8]=0x08;    
  1564.         LD      A,8
  1565.         LD      (.outbuf+8),A
  1566. ; 561.      .outbuf[14]=10;  
  1567.         LD      A,10
  1568.         LD      (.outbuf+14),A
  1569. ; 562.      /////////////////////////////////////  
  1570. ; 563.      .outbuf[15]=RBC_CMD_READCAPACITY;
  1571.         LD      A,37
  1572.         LD      (.outbuf+15),A
  1573. ; 564.      .outbuf[19]=0;
  1574.         XOR     A
  1575. ; 565.      /////////////////////////////////////  
  1576. ; 566.      if(!.epBulkSend(.outbuf,0x1f))      
  1577.         CALL    .lo209
  1578.         OR      A
  1579.         JR      Z,.lo207
  1580. .lo176:
  1581. ; 567.          return FALSE;  
  1582. .lo177:
  1583. ; 568.      .delayms(10);  
  1584.         LD      E,1
  1585.         CALL    .delayms
  1586. ; 569.      if(!.epBulkRcv(.DBUF,8))  
  1587.         LD      BC,8
  1588.         LD      DE,.DBUF
  1589.         CALL    .epBulkRcv
  1590.         OR      A
  1591.         JR      Z,.lo207
  1592. .lo178:
  1593. ; 570.          return FALSE;  
  1594. .lo179:
  1595. ; 571.      if(!.epBulkRcv(.outbuf,13))  
  1596.         CALL    .lo210
  1597.         OR      A
  1598.         JR      NZ,.lo181
  1599. .lo180:
  1600. ; 572.          return FALSE;  
  1601. .lo207:
  1602.         XOR     A
  1603.         JR      .lo182
  1604. .lo181:
  1605. ; 573.      /////////////////////////////  
  1606. ; 574.      return TRUE;  
  1607.         LD      A,1
  1608. ; 575.  }  
  1609. .lo182:
  1610.         POP     DE
  1611.         POP     BC
  1612.         RET
  1613.         ;RSEG   CONST
  1614. .data00:
  1615.         DEFB    'U'
  1616.         DEFB    'S'
  1617.         DEFB    'B'
  1618.         DEFB    'C'
  1619.         DEFB    '`'
  1620.         DEFB    166
  1621.         DEFB    '$'
  1622.         DEFB    222
  1623.         DEFB    '$'
  1624.         DEFB    0
  1625.         DEFB    0
  1626.         DEFB    0
  1627.         DEFB    128
  1628.         DEFB    0
  1629.         DEFB    6
  1630.         DEFB    18
  1631.         DEFB    0
  1632.         DEFB    0
  1633.         DEFB    0
  1634.         DEFB    '$'
  1635.         DEFB    0,0,0,0,0
  1636.         ;RSEG   NO_INIT
  1637. .bFlags:
  1638.         DEFS    1
  1639. .usbstack:
  1640.         DEFS    17
  1641. ;.DBUF:
  1642. ;       DEFS    1024
  1643. .uDev:
  1644.         DEFS    6
  1645.         ;RSEG   UDATA0
  1646. .outbuf:
  1647.         DEFS    32
  1648.        
  1649.        
  1650. .delayms
  1651.         halt
  1652.         dec e
  1653.         jr nz,.delayms
  1654.         ret
  1655.        
  1656.         ;bcde=lba,hl=buf,a'=count
  1657. .RBC_Read
  1658.         push hl
  1659.         ld hl,0xa660
  1660.         ld (.outbuf+4),hl
  1661.         ld hl,0xde24
  1662.         ld (.outbuf+6),hl
  1663.         ld hl,0x0080
  1664.         ld (.outbuf+12),hl
  1665.         ld hl,0x2810    ;RBC_CMD_READ10
  1666.         ld (.outbuf+14),hl
  1667.         call .send_cmd
  1668.         pop de ;buffer
  1669.         ret z
  1670.         call .epBulkRcv
  1671.         jr .RBC_rw_end
  1672. .RBC_Write
  1673.         push hl
  1674.         ld hl,0xd9b4
  1675.         ld (.outbuf+4),hl
  1676.         ld hl,0xc177
  1677.         ld (.outbuf+6),hl
  1678.         ld hl,0x0000
  1679.         ld (.outbuf+12),hl
  1680.         ld hl,0x2a10    ;RBC_CMD_WRITE10
  1681.         ld (.outbuf+14),hl
  1682.         call .send_cmd
  1683.         pop de ;buffer
  1684.         ret z
  1685.         call .epBulkSend
  1686. .RBC_rw_end
  1687.         or a
  1688.         ret z
  1689.         ld de,.outbuf
  1690.         ld bc,13
  1691.         call .epBulkRcv
  1692.         or a
  1693.         ld a,0
  1694.         ret nz
  1695.         ld de,.outbuf
  1696.         ld bc,13
  1697.         call .epBulkRcv
  1698.         xor a
  1699.         ret
  1700.        
  1701. .send_cmd       ;out bc=length
  1702.         ld hl,0x5355
  1703.         ld (.outbuf+0),hl
  1704.         ld hl,0x4342
  1705.         ld (.outbuf+2),hl
  1706.         ld hl,.outbuf+16
  1707.         ld (hl),0
  1708.         inc hl
  1709.         ld (hl),b       ;LBA
  1710.         inc hl
  1711.         ld (hl),c
  1712.         inc hl
  1713.         ld (hl),d
  1714.         inc hl
  1715.         ld (hl),e
  1716.         ex af,af'
  1717.         ld l,a
  1718.         ld h,0
  1719.         ld (.outbuf+23),hl
  1720.         ld b,l          ;count*512
  1721.         sla b
  1722.         ld c,h
  1723.         ld (.outbuf+8),bc       ;(long)bytes length
  1724.         ld l,h
  1725.         ld (.outbuf+10),hl
  1726.         ld (.outbuf+21),hl
  1727.         push bc
  1728.         ld bc,0x82ab
  1729.         in a,(c)
  1730.         and 0xaf                ;хост-мод и сл811 в портах
  1731.         out (c),a      
  1732.         ld de,.outbuf
  1733.         ld bc,31
  1734.         call .epBulkSend
  1735.         pop bc
  1736.         or a
  1737.         ret
  1738.  
  1739.        
  1740. .SL11HardReset
  1741.         push bc
  1742.         ld bc,0x83ab    ;ресет sl811
  1743.         in a,(c)
  1744.         and 0xdf
  1745.         out (c),a
  1746.         ld b,0x82               ;сняли питание с разъёма
  1747.         in a,(c)
  1748.         or 0x40
  1749.         out (c),a
  1750.         ;ld e,2;0xff&(2000+20)/20               ;пару секунд чтоп девайс сдох совсем
  1751.         ;call .delayms
  1752.         ld bc,0x82ab
  1753.         in a,(c)
  1754.         and 0xaf                ;хост-мод и сл811 в портах
  1755.         out (c),a      
  1756.         ld e,2;0xff&(50+20)/20
  1757.         call .delayms
  1758.         ld bc,0x83ab
  1759.         in a,(c)
  1760.         or 0x20
  1761.         out (c),a               ;убрали ресет  
  1762.         pop bc
  1763.         ret
  1764.                
  1765.        
  1766. SL811BUFWRITE  
  1767.         pop af
  1768.         pop hl
  1769.         push hl
  1770.         push af
  1771.         ;HL-buf,E-reg, C-count
  1772.         ld a,c
  1773. .wrloop
  1774.         ld bc,0x80ab
  1775.         out (c),e
  1776.         inc e
  1777.         ld b,a
  1778.         outi
  1779.         ld a,b
  1780.         jp nz,.wrloop
  1781.         ret
  1782.        
  1783. SL811BUFREAD   
  1784.         pop af
  1785.         pop hl
  1786.         push hl
  1787.         push af
  1788.         ;HL-buf,E-reg, C-count
  1789.         ld a,c
  1790. .rdloop
  1791.         ld bc,0x80ab
  1792.         out (c),e
  1793.         inc e
  1794.         ld b,a
  1795.         ini
  1796.         ld a,b
  1797.         jp nz,.rdloop
  1798.         ret