xref: /utopia/UTPA2-700.0.x/modules/usb/drv/usbhost/source4/usb_host_p4/drvScsi_4.c (revision 53ee8cc121a030b8d368113ac3e966b4705770ef)
1 //<MStar Software>
2 //******************************************************************************
3 // MStar Software
4 // Copyright (c) 2010 - 2012 MStar Semiconductor, Inc. All rights reserved.
5 // All software, firmware and related documentation herein ("MStar Software") are
6 // intellectual property of MStar Semiconductor, Inc. ("MStar") and protected by
7 // law, including, but not limited to, copyright law and international treaties.
8 // Any use, modification, reproduction, retransmission, or republication of all
9 // or part of MStar Software is expressly prohibited, unless prior written
10 // permission has been granted by MStar.
11 //
12 // By accessing, browsing and/or using MStar Software, you acknowledge that you
13 // have read, understood, and agree, to be bound by below terms ("Terms") and to
14 // comply with all applicable laws and regulations:
15 //
16 // 1. MStar shall retain any and all right, ownership and interest to MStar
17 //    Software and any modification/derivatives thereof.
18 //    No right, ownership, or interest to MStar Software and any
19 //    modification/derivatives thereof is transferred to you under Terms.
20 //
21 // 2. You understand that MStar Software might include, incorporate or be
22 //    supplied together with third party`s software and the use of MStar
23 //    Software may require additional licenses from third parties.
24 //    Therefore, you hereby agree it is your sole responsibility to separately
25 //    obtain any and all third party right and license necessary for your use of
26 //    such third party`s software.
27 //
28 // 3. MStar Software and any modification/derivatives thereof shall be deemed as
29 //    MStar`s confidential information and you agree to keep MStar`s
30 //    confidential information in strictest confidence and not disclose to any
31 //    third party.
32 //
33 // 4. MStar Software is provided on an "AS IS" basis without warranties of any
34 //    kind. Any warranties are hereby expressly disclaimed by MStar, including
35 //    without limitation, any warranties of merchantability, non-infringement of
36 //    intellectual property rights, fitness for a particular purpose, error free
37 //    and in conformity with any international standard.  You agree to waive any
38 //    claim against MStar for any loss, damage, cost or expense that you may
39 //    incur related to your use of MStar Software.
40 //    In no event shall MStar be liable for any direct, indirect, incidental or
41 //    consequential damages, including without limitation, lost of profit or
42 //    revenues, lost or damage of data, and unauthorized system use.
43 //    You agree that this Section 4 shall still apply without being affected
44 //    even if MStar Software has been modified by MStar in accordance with your
45 //    request or instruction for your use, except otherwise agreed by both
46 //    parties in writing.
47 //
48 // 5. If requested, MStar may from time to time provide technical supports or
49 //    services in relation with MStar Software to you for your use of
50 //    MStar Software in conjunction with your or your customer`s product
51 //    ("Services").
52 //    You understand and agree that, except otherwise agreed by both parties in
53 //    writing, Services are provided on an "AS IS" basis and the warranty
54 //    disclaimer set forth in Section 4 above shall apply.
55 //
56 // 6. Nothing contained herein shall be construed as by implication, estoppels
57 //    or otherwise:
58 //    (a) conferring any license or right to use MStar name, trademark, service
59 //        mark, symbol or any other identification;
60 //    (b) obligating MStar or any of its affiliates to furnish any person,
61 //        including without limitation, you and your customers, any assistance
62 //        of any kind whatsoever, or any information; or
63 //    (c) conferring any license or right under any intellectual property right.
64 //
65 // 7. These terms shall be governed by and construed in accordance with the laws
66 //    of Taiwan, R.O.C., excluding its conflict of law rules.
67 //    Any and all dispute arising out hereof or related hereto shall be finally
68 //    settled by arbitration referred to the Chinese Arbitration Association,
69 //    Taipei in accordance with the ROC Arbitration Law and the Arbitration
70 //    Rules of the Association by three (3) arbitrators appointed in accordance
71 //    with the said Rules.
72 //    The place of arbitration shall be in Taipei, Taiwan and the language shall
73 //    be English.
74 //    The arbitration award shall be final and binding to both parties.
75 //
76 //******************************************************************************
77 //<MStar Software>
78 ////////////////////////////////////////////////////////////////////////////////
79 //
80 // Copyright (c) 2006-2008 MStar Semiconductor, Inc.
81 // All rights reserved.
82 //
83 // Unless otherwise stipulated in writing, any and all information contained
84 // herein regardless in any format shall remain the sole proprietary of
85 // MStar Semiconductor Inc. and be kept in strict confidence
86 // (��MStar Confidential Information��) by the recipient.
87 // Any unauthorized act including without limitation unauthorized disclosure,
88 // copying, use, reproduction, sale, distribution, modification, disassembling,
89 // reverse engineering and compiling of the contents of MStar Confidential
90 // Information is unlawful and strictly prohibited. MStar hereby reserves the
91 // rights to any and all damages, losses, costs and expenses resulting therefrom.
92 //
93 ////////////////////////////////////////////////////////////////////////////////
94 #if defined(MSOS_TYPE_NOS)
95 #include "../USBHostConfig_4.h"
96 #include <stdlib.h>
97 #ifndef ATV_SERISE_USE
98 #include <stdio.h>
99 #endif
100 #include <string.h>
101 #ifndef ATV_SERISE_USE
102 #include "../../include/datatype.h"
103 #else
104 #include "UsbHostDataDef.h"
105 #endif
106 #include "../drvHostLib_4.h"
107 #include "../drvHost200_4.h"
108 #include "../drvscsi_4.h"
109 #include "../drvMassStorage_4.h"
110 #ifdef ATV_SERISE_USE
111 #include "Board.h"
112 #include "common.h"
113 #include "uart.h"
114 #endif
115 #include "../drvUsbMain_4.h"
116 #include "../../include/_drvUSB.h"
117 
118 #include "MsCommon.h"
119 #include "MsIRQ.h"
120 #include "MsOS.h"
121 
122 extern void msAPI_Timer_ResetWDT(void);
123 
124 #define DRV_SCSI_DBG(x) // x;
125 
126 //struct us_data xdata *Mass_stor_us;
127 #define MAX_LUN_SUPPORT    5
128 
129 struct us_data Mass_stor_us1_port4;
130 #if 1
131 struct LUN_Device  Mass_stor_device_port4[MAX_LUN_SUPPORT];
132 #else
133 struct LUN_Device Mass_stor_device_1_port4; //support 4 LUN
134 struct LUN_Device Mass_stor_device_2_port4;
135 struct LUN_Device Mass_stor_device_3_port4;
136 struct LUN_Device Mass_stor_device_4_port4;
137 struct LUN_Device Mass_stor_device_5_port4;
138 #endif
139 
140 extern UINT8 pUsbData_Port4[1024];
141 Scsi_Cmnd  srb_data_port4;
142 
143 UINT8 u8Drive_port4 = 0;
144 extern U8 gUsbStatus_Port4;
145 extern U8 gSpeed_Port4;
146 
147 struct stForceModeSense1A
148 {
149     U16     VID;
150     U16     PID;
151 } stForceModeSense1A;
152 
153 struct stForceModeSense1A gForceModeSense1A_Port4[] =
154 {
155         {0x0DD8, 0x1448},
156         {0x1AA6, 0x0201},
157         {0x0DD8, 0x1414},
158         {0x0DD8, 0x1400},
159         {0x0DD8, 0xE203},
160         {0x8644, 0x800a},           //alan.yu add on 2010.08.13 (�Ϲ� ����)
161         {0x0DD8, 0xD202},           //alan.yu add on 2010.08.16 (�ʿ�Netac)
162         {0x18A5,0x302},             //alan.yu add on 2011.08.01
163         {0, 0}
164 };
165 
166 extern void MDrv_USBGetVIDPID_Port4(U16 *pVID, U16 *pPID);
167 
168 //BOOLEAN gDeviceFatalError=FALSE;
Init_Mass_Storage_Structure_Port4(void)169 void Init_Mass_Storage_Structure_Port4(void)
170 {
171   U16   uVID, uPID;
172 
173   //Mass_stor_us=&Mass_stor_us1;
174   Mass_stor_us1_port4.Mass_stor_device=&Mass_stor_device_port4[0];
175 #ifdef   ENABLE_CBI_HOST
176   if ( (psAttachDevice_Port4->saCD[0].sInterface[0].bInterfaceProtocol==0x00)||
177        (psAttachDevice_Port4->saCD[0].sInterface[0].bInterfaceProtocol==0x01) )
178     Mass_stor_us1_port4.max_lun=0;
179   else
180 #endif
181   {
182     MDrv_USBGetVIDPID_Port4(&uVID, &uPID);
183     //printf("MAXLUN VID: %x, PID: %x\n", uVID, uPID);
184     if ( ((uVID == 0x8564) && (uPID == 0x1000)) ||
185          ((uVID == 0xFCA) && (uPID == 0x8004)) ) //20130301, for blackberry phone
186           Mass_stor_us1_port4.max_lun = 0;
187     else
188           Mass_stor_us1_port4.max_lun=   Host20_MSCD_GetMaxLUN_Port4();
189   }
190   //printf("Max Lun:%02bx\n",Mass_stor_us1.max_lun);
191     if (Mass_stor_us1_port4.max_lun > (MAX_LUN_SUPPORT-1) )
192         Mass_stor_us1_port4.max_lun = MAX_LUN_SUPPORT-1;
193 }
194 //***************************************************************************************
195 // Function Name: vSCSICmd_READ_10
196 // Description:
197 // Input:
198 // Output:
199 // Status:S
200 //***************************************************************************************
vSCSICmd_READ_WRITE_10_Port4(BOOLEAN DoWrite,struct us_data * us,Scsi_Cmnd * srb,INT8U u8LunNum,INT32U u32BlockAddr,INT16U u16BlockNum,U32 u8Buffer)201 void vSCSICmd_READ_WRITE_10_Port4(BOOLEAN DoWrite,struct us_data *us, Scsi_Cmnd *srb, INT8U u8LunNum,
202 							  INT32U u32BlockAddr, INT16U u16BlockNum, U32 u8Buffer)
203 {
204 
205 
206   /* set the command and the LUN */
207   #if 0
208   memset(srb->cmnd, 0, MAX_COMMAND_SIZE);
209   srb->cmnd[0] = READ_10;
210 
211   srb->cmnd[2] = (INT8U)(u32BlockAddr >> 24);
212   srb->cmnd[3] = (INT8U)(u32BlockAddr >> 16);
213   srb->cmnd[4] = (INT8U)(u32BlockAddr >> 8);
214   srb->cmnd[5] = (INT8U)(u32BlockAddr);
215 
216   srb->cmnd[7] = (INT8U)(u16BlockNum >> 8);
217   srb->cmnd[8] = (INT8U)(u16BlockNum );
218   #endif
219   if (DoWrite)
220     pOTGH_PT_BLK_Port4->sCBW.u8CB[0]=WRITE_10;
221   else
222     pOTGH_PT_BLK_Port4->sCBW.u8CB[0]=READ_10;
223   pOTGH_PT_BLK_Port4->sCBW.u8CB[1]=0;
224 
225   pOTGH_PT_BLK_Port4->sCBW.u8CB[2]= (INT8U)(u32BlockAddr >> 24);
226   pOTGH_PT_BLK_Port4->sCBW.u8CB[3]= (INT8U)(u32BlockAddr >> 16);
227   pOTGH_PT_BLK_Port4->sCBW.u8CB[4]= (INT8U)(u32BlockAddr >> 8);
228   pOTGH_PT_BLK_Port4->sCBW.u8CB[5]= (INT8U)(u32BlockAddr);
229 
230   pOTGH_PT_BLK_Port4->sCBW.u8CB[7] = (INT8U)(u16BlockNum >> 8);
231   pOTGH_PT_BLK_Port4->sCBW.u8CB[8] = (INT8U)(u16BlockNum );
232 
233 
234   /* FIXME: we must do the protocol translation here */
235   /*
236   if (us->subclass == US_SC_RBC || us->subclass == US_SC_SCSI)
237     srb->cmd_len = 6;
238   else
239 	srb->cmd_len = 12;
240   */
241   srb->cmd_len = 10;
242 
243   /* set the transfer direction */
244   if (DoWrite)
245   	srb->sc_data_direction = SCSI_DATA_WRITE;
246   else
247 	srb->sc_data_direction = SCSI_DATA_READ;
248 
249   /* use the new buffer we have */
250   srb->request_buffer= u8Buffer;
251 
252   /* set the buffer length for transfer */
253   srb->request_bufflen = (us->Mass_stor_device[u8LunNum].u32BlockSize)*u16BlockNum;
254 
255   /* set up for no scatter-gather use */
256   //srb->use_sg = 0;
257 
258   /* change the serial number -- toggle the high bit*/
259   //srb->serial_number ^= 0x80000000;
260 
261   /* set Lun number*/
262   srb->lun= u8LunNum;
263 
264   //srb->scsi_done = vScsi_SendCmd_Done;
265 
266 
267 
268 }
269 #if 0
270 //***************************************************************************************
271 // Function Name:
272 // Description:
273 // Input:
274 // Output:
275 // Status:S
276 //***************************************************************************************
277 void vSCSICmd_WRITE_10(struct us_data *us, Scsi_Cmnd *srb,  INT8U u8LunNum,
278 							  INT32U u32BlockAddr, INT16U u16BlockNum, U32 u8Buffer)
279 {
280 
281 
282   /* set the command and the LUN */
283   #if 0
284   memset(srb->cmnd, 0, MAX_COMMAND_SIZE);
285   srb->cmnd[0] = WRITE_10;
286 
287   srb->cmnd[2] = (INT8U)(u32BlockAddr >> 24);
288   srb->cmnd[3] = (INT8U)(u32BlockAddr >> 16);
289   srb->cmnd[4] = (INT8U)(u32BlockAddr >> 8);
290   srb->cmnd[5] = (INT8U)(u32BlockAddr);
291 
292   srb->cmnd[7] = (INT8U)(u16BlockNum >> 8);
293   srb->cmnd[8] = (INT8U)(u16BlockNum );
294   #endif
295   pOTGH_PT_BLK_Port4->sCBW.u8CB[0]=WRITE_10;
296   pOTGH_PT_BLK_Port4->sCBW.u8CB[1]=0;
297 
298   pOTGH_PT_BLK_Port4->sCBW.u8CB[2]= (INT8U)(u32BlockAddr >> 24);
299   pOTGH_PT_BLK_Port4->sCBW.u8CB[3]= (INT8U)(u32BlockAddr >> 16);
300   pOTGH_PT_BLK_Port4->sCBW.u8CB[4]= (INT8U)(u32BlockAddr >> 8);
301   pOTGH_PT_BLK_Port4->sCBW.u8CB[5]= (INT8U)(u32BlockAddr);
302 
303   pOTGH_PT_BLK_Port4->sCBW.u8CB[7] = (INT8U)(u16BlockNum >> 8);
304   pOTGH_PT_BLK_Port4->sCBW.u8CB[8] = (INT8U)(u16BlockNum );
305 
306   /* FIXME: we must do the protocol translation here */
307   /*
308   if (us->subclass == US_SC_RBC || us->subclass == US_SC_SCSI)
309     srb->cmd_len = 6;
310   else
311 	srb->cmd_len = 12;
312   */
313   srb->cmd_len = CB_LENGTH_WRITE_10;
314 
315   /* set the transfer direction */
316   srb->sc_data_direction = SCSI_DATA_WRITE;
317 
318   /* use the new buffer we have */
319   srb->phy_buf_adr=u8Buffer;
320   srb->buffer_type=BUFFER_PHY;
321 
322   /* set the buffer length for transfer */
323   srb->request_bufflen = us->Mass_stor_device[u8LunNum].u32BlockSize*u16BlockNum;
324 
325   /* set up for no scatter-gather use */
326   //srb->use_sg = 0;
327 
328   /* change the serial number -- toggle the high bit*/
329   //srb->serial_number ^= 0x80000000;
330 
331   /* set Lun number*/
332   srb->lun= u8LunNum;
333 
334   //srb->scsi_done = vScsi_SendCmd_Done;
335 
336 
337 }
338 #endif
339 //***************************************************************************************
340 // Function Name:
341 // Description:
342 // Input:
343 // Output:
344 // Status:S
345 //***************************************************************************************
vSCSICmd_INQUIRY_Port4(Scsi_Cmnd * srb,INT8U * u8Buffer)346 void vSCSICmd_INQUIRY_Port4( Scsi_Cmnd *srb, INT8U *u8Buffer)
347 {
348 
349 
350   /* set the command and the LUN */
351   //memset(srb->cmnd, 0, MAX_COMMAND_SIZE);
352   //srb->cmnd[0] = INQUIRY;
353   //srb->cmnd[4] = DATA_LENGTH_INQUIRY;
354   memset(&pOTGH_PT_BLK_Port4->sCBW.u8CB[0], 0, 16);
355   pOTGH_PT_BLK_Port4->sCBW.u8CB[0]= INQUIRY;
356   pOTGH_PT_BLK_Port4->sCBW.u8CB[4]= DATA_LENGTH_INQUIRY;
357 
358   /* FIXME: we must do the protocol translation here */
359   /*
360   if (us->subclass == US_SC_RBC || us->subclass == US_SC_SCSI)
361     srb->cmd_len = 6;
362   else
363 	srb->cmd_len = 12;
364   */
365   srb->cmd_len = CB_LENGTH_INQUIRY;
366 
367   /* set the transfer direction */
368   srb->sc_data_direction = SCSI_DATA_READ;
369 
370   /* use the new buffer we have */
371     srb->request_buffer = (U32)u8Buffer;
372 
373   /* set the buffer length for transfer */
374   srb->request_bufflen = DATA_LENGTH_INQUIRY;
375 
376   /* set up for no scatter-gather use */
377   //srb->use_sg = 0;
378 
379   /* change the serial number -- toggle the high bit*/
380   //srb->serial_number ^= 0x80000000;
381 
382   /* set Lun number*/
383   //srb->lun= u8Drive;//0;
384 
385   //srb->scsi_done = vScsi_SendCmd_Done;
386 
387 
388 }
389 //***************************************************************************************
390 // Function Name:
391 // Description:
392 // Input:
393 // Output:
394 // Status:S
395 //***************************************************************************************
vSCSICmd_READ_CAPACITY_Port4(Scsi_Cmnd * srb,INT8U * u8Buffer)396 void vSCSICmd_READ_CAPACITY_Port4( Scsi_Cmnd *srb, INT8U *u8Buffer)
397 {
398 
399   /* set the command and the LUN */
400   //memset(srb->cmnd, 0, MAX_COMMAND_SIZE);
401   //srb->cmnd[0] = READ_CAPACITY;
402   memset(&pOTGH_PT_BLK_Port4->sCBW.u8CB[0], 0, 16);
403   pOTGH_PT_BLK_Port4->sCBW.u8CB[0]= READ_CAPACITY;
404 
405   /* FIXME: we must do the protocol translation here */
406   /*
407   if (us->subclass == US_SC_RBC || us->subclass == US_SC_SCSI)
408     srb->cmd_len = 6;
409   else
410 	srb->cmd_len = 12;
411   */
412   srb->cmd_len = CB_LENGTH_READ_CAPACITY;
413 
414   /* set the transfer direction */
415   srb->sc_data_direction = SCSI_DATA_READ;
416 
417   /* use the new buffer we have */
418     srb->request_buffer = (U32)u8Buffer;
419 
420   /* set the buffer length for transfer */
421   srb->request_bufflen = DATA_LENGTH_READ_CAPACITY;
422 
423   /* set up for no scatter-gather use */
424   //srb->use_sg = 0;
425 
426   /* change the serial number -- toggle the high bit*/
427   //srb->serial_number ^= 0x80000000;
428 
429   /* set Lun number*/
430   //srb->lun= u8Drive;
431 
432   //srb->scsi_done = vScsi_SendCmd_Done;
433 
434 
435 }
436 
vSCSICmd_READ_FORMAT_CAPACITY_Port4(Scsi_Cmnd * srb,INT8U * u8Buffer)437 void vSCSICmd_READ_FORMAT_CAPACITY_Port4( Scsi_Cmnd *srb, INT8U *u8Buffer)
438 {
439 
440   /* set the command and the LUN */
441   //memset(srb->cmnd, 0, MAX_COMMAND_SIZE);
442   //srb->cmnd[0] = READ_CAPACITY;
443   memset(&pOTGH_PT_BLK_Port4->sCBW.u8CB[0], 0, 16);
444   pOTGH_PT_BLK_Port4->sCBW.u8CB[0]= READ_FORMAT_CAPACITY;
445   pOTGH_PT_BLK_Port4->sCBW.u8CB[8]= 12; //Length
446 
447   /* FIXME: we must do the protocol translation here */
448   /*
449   if (us->subclass == US_SC_RBC || us->subclass == US_SC_SCSI)
450     srb->cmd_len = 6;
451   else
452 	srb->cmd_len = 12;
453   */
454   srb->cmd_len = CB_LENGTH_READ_CAPACITY;
455 
456   /* set the transfer direction */
457   srb->sc_data_direction = SCSI_DATA_READ;
458 
459   /* use the new buffer we have */
460   srb->request_buffer = (U32)u8Buffer;
461 
462   /* set the buffer length for transfer */
463   srb->request_bufflen = 12;
464 
465   /* set up for no scatter-gather use */
466   //srb->use_sg = 0;
467 
468   /* change the serial number -- toggle the high bit*/
469   //srb->serial_number ^= 0x80000000;
470 
471   /* set Lun number*/
472   //srb->lun= u8Drive;
473 
474   //srb->scsi_done = vScsi_SendCmd_Done;
475 
476 
477 }
478 
479 //***************************************************************************************
480 // Function Name:vSCSICmd_MODE_SENSE_Port4
481 // Description:
482 // Input:
483 // Output:
484 // Status:
485 //***************************************************************************************
vSCSICmd_MODE_SENSE_Port4(Scsi_Cmnd * srb,INT8U u8PageCode,INT8U * u8Buffer)486 void vSCSICmd_MODE_SENSE_Port4( Scsi_Cmnd *srb,INT8U u8PageCode,INT8U *u8Buffer)
487 {
488 
489   /* set the command and the LUN */
490   //memset(srb->cmnd, 0, MAX_COMMAND_SIZE);
491   //srb->cmnd[0] = MODE_SENSE;
492   //srb->cmnd[2] = u8PageCode;
493   //srb->cmnd[4] = DATA_LENGTH_MODE_SENSE;
494   memset(&pOTGH_PT_BLK_Port4->sCBW.u8CB[0], 0, 16);
495   pOTGH_PT_BLK_Port4->sCBW.u8CB[0]= MODE_SENSE;
496   pOTGH_PT_BLK_Port4->sCBW.u8CB[2]= u8PageCode;
497   pOTGH_PT_BLK_Port4->sCBW.u8CB[4]= DATA_LENGTH_MODE_SENSE;
498 
499   /* FIXME: we must do the protocol translation here */
500   /*
501   if (us->subclass == US_SC_RBC || us->subclass == US_SC_SCSI)
502     srb->cmd_len = 6;
503   else
504     srb->cmd_len = 12;
505   */
506   srb->cmd_len = CB_LENGTH_MODE_SENSE;
507 
508   /* set the transfer direction */
509   srb->sc_data_direction = SCSI_DATA_READ;
510 
511   /* use the new buffer we have */
512     srb->request_buffer = (U32)u8Buffer;
513   /* set the buffer length for transfer */
514   srb->request_bufflen = DATA_LENGTH_MODE_SENSE;
515 
516   /* set up for no scatter-gather use */
517   //srb->use_sg = 0;
518 
519   /* change the serial number -- toggle the high bit*/
520   //srb->serial_number ^= 0x80000000;
521 
522   /* set Lun number*/
523   //srb->lun= u8Drive;
524 
525   //srb->scsi_done = vScsi_SendCmd_Done;
526 
527 
528 }
529 
530 //***************************************************************************************
531 // Function Name:vSCSICmd_MODE_SENSE_OperCode5A_Port4
532 // Description:
533 // Input:
534 // Output:
535 // Status:
536 //***************************************************************************************
vSCSICmd_MODE_SENSE_OperCode5A_Port4(Scsi_Cmnd * srb,INT8U u8PageCode,INT8U * u8Buffer)537 void vSCSICmd_MODE_SENSE_OperCode5A_Port4( Scsi_Cmnd *srb,INT8U u8PageCode,INT8U *u8Buffer)
538 {
539 
540   /* set the command and the LUN */
541   //memset(srb->cmnd, 0, MAX_COMMAND_SIZE);
542   //srb->cmnd[0] = MODE_SENSE;
543   //srb->cmnd[2] = u8PageCode;
544   //srb->cmnd[4] = DATA_LENGTH_MODE_SENSE;
545   memset(&pOTGH_PT_BLK_Port4->sCBW.u8CB[0], 0, 16);
546   pOTGH_PT_BLK_Port4->sCBW.u8CB[0]= MODE_SENSE_5A;
547   pOTGH_PT_BLK_Port4->sCBW.u8CB[2]= u8PageCode;
548 
549 #if 0
550   pOTGH_PT_BLK_Port4->sCBW.u8CB[4]= DATA_LENGTH_MODE_SENSE_OperCode5A;		//RCC?
551 #else
552   pOTGH_PT_BLK_Port4->sCBW.u8CB[7] = (INT8U)(DATA_LENGTH_MODE_SENSE_OperCode5A >> 8);
553   pOTGH_PT_BLK_Port4->sCBW.u8CB[8] = (INT8U)(DATA_LENGTH_MODE_SENSE_OperCode5A );
554 #endif
555 
556   /* FIXME: we must do the protocol translation here */
557   /*
558   if (us->subclass == US_SC_RBC || us->subclass == US_SC_SCSI)
559     srb->cmd_len = 6;
560   else
561     srb->cmd_len = 12;
562   */
563   srb->cmd_len = CB_LENGTH_MODE_SENSE_5A;
564 
565   /* set the transfer direction */
566   srb->sc_data_direction = SCSI_DATA_READ;
567 
568   /* use the new buffer we have */
569     srb->request_buffer = (U32)u8Buffer;
570   /* set the buffer length for transfer */
571   srb->request_bufflen = DATA_LENGTH_MODE_SENSE_OperCode5A;
572 
573   /* set up for no scatter-gather use */
574   //srb->use_sg = 0;
575 
576   /* change the serial number -- toggle the high bit*/
577   //srb->serial_number ^= 0x80000000;
578 
579   /* set Lun number*/
580   //srb->lun= u8Drive;
581 
582   //srb->scsi_done = vScsi_SendCmd_Done;
583 
584 
585 }
586 
587 //***************************************************************************************
588 // Function Name:vSCSICmd_REQUEST_SENSE_Port4
589 // Description:
590 // Input:
591 // Output:
592 // Status:
593 //***************************************************************************************
vSCSICmd_REQUEST_SENSE_Port4(Scsi_Cmnd * srb,INT8U * u8Buffer)594 void vSCSICmd_REQUEST_SENSE_Port4(  Scsi_Cmnd *srb, INT8U *u8Buffer)
595 {
596 
597 
598   /* set the command and the LUN */
599   //memset(srb->cmnd, 0, MAX_COMMAND_SIZE);
600   //srb->cmnd[0] = REQUEST_SENSE;
601   //srb->cmnd[4] = 18;
602   memset(&pOTGH_PT_BLK_Port4->sCBW.u8CB[0], 0, 16);
603   pOTGH_PT_BLK_Port4->sCBW.u8CB[0]= REQUEST_SENSE;
604   pOTGH_PT_BLK_Port4->sCBW.u8CB[4]= 18;
605 
606   /* FIXME: we must do the protocol translation here */
607   /*
608   if (us->subclass == US_SC_RBC || us->subclass == US_SC_SCSI)
609     srb->cmd_len = 6;
610   else
611 	srb->cmd_len = 12;
612   */
613   srb->cmd_len = CB_LENGTH_REQUEST_SENSE;
614 
615   /* set the transfer direction */
616   srb->sc_data_direction = SCSI_DATA_READ;
617 
618   /* use the new buffer we have */
619     srb->request_buffer = (U32)u8Buffer;
620   /* set the buffer length for transfer */
621   srb->request_bufflen = 18;
622 
623   /* set up for no scatter-gather use */
624   //srb->use_sg = 0;
625 
626   /* change the serial number -- toggle the high bit*/
627   //srb->serial_number ^= 0x80000000;
628 
629   /* set Lun number*/
630   //srb->lun= u8Drive;
631 
632   //srb->scsi_done = vScsi_SendCmd_Done;
633 
634 
635 }
636 #if 0
637 //***************************************************************************************
638 // Function Name:vSCSICmd_TEST_UNIT_READY
639 // Description:
640 // Input:
641 // Output:
642 // Status:S
643 //***************************************************************************************
644 void vSCSICmd_TEST_UNIT_READY( Scsi_Cmnd *srb)
645 {
646 
647   memset(&pOTGH_PT_BLK_Port4->sCBW.u8CB[0], 0, 16);
648   pOTGH_PT_BLK_Port4->sCBW.u8CB[0]= TEST_UNIT_READY;
649 
650   srb->cmd_len = CB_LENGTH_TEST_UNIT_READY;
651 
652 
653   /* set the transfer direction */
654   srb->sc_data_direction = SCSI_DATA_READ;
655 
656   /* set the buffer length for transfer */
657   srb->request_bufflen = 0;
658 
659 }
660 #endif
661 
vSCSICmd_Prepare_Port4(Scsi_Cmnd * srb,U8 cmd)662 void vSCSICmd_Prepare_Port4(Scsi_Cmnd *srb, U8 cmd)
663 {
664   memset(&pOTGH_PT_BLK_Port4->sCBW.u8CB[0], 0, 16);
665   pOTGH_PT_BLK_Port4->sCBW.u8CB[0]= cmd;
666 
667   srb->cmd_len = 6;
668   /* set the transfer direction */
669   srb->sc_data_direction = SCSI_DATA_READ;
670   /* set the buffer length for transfer */
671   srb->request_bufflen = 0;
672 }
673 
674 
675 
676 
vSCSI_EJECT_DEVICE_Port4(U8 lun)677 BOOLEAN  vSCSI_EJECT_DEVICE_Port4(U8 lun)
678 {
679   BOOLEAN result;
680 
681   Mass_stor_us1_port4.srb =&srb_data_port4;
682   memset(Mass_stor_us1_port4.srb, 0, sizeof(struct scsi_cmnd ));
683 
684   vSCSICmd_Prepare_Port4(Mass_stor_us1_port4.srb,START_STOP);
685   Mass_stor_us1_port4.srb->lun=lun;
686   pOTGH_PT_BLK_Port4->sCBW.u8CB[4]= 2;                         //stop the device
687 
688   //result=Host20_MSCD_usb_stor_control_thread_Port4(&Mass_stor_us1);
689   //if (result==FALSE) return result;
690   //pOTGH_PT_BLK_Port4->sCBW.u8CB[0]= START_STOP;
691   //pOTGH_PT_BLK_Port4->sCBW.u8CB[4]= 2;                         //stop the device
692   //printf("lun:%02bx\n",lun);
693   result=Host20_MSCD_usb_stor_control_thread_Port4(&Mass_stor_us1_port4);
694   return result;
695 }
696 
697 
698 
699 
700 
701 //=======================================================================================
702 //=======================================================================================
703 //=======================================================================================
704 //=======================================================================================
705 //***************************************************************************************
706 // Function Name:vSCSI_REQUEST_SENSE_Port4
707 // Description: Reserved.
708 //              If Device do not support the command-A
709 //              ,Host should issue command "vSCSI_REQUEST_SENSE" to ask "why not support".
710 // Input:
711 // Output:
712 // Status:P-OK
713 //***************************************************************************************
vSCSI_REQUEST_SENSE_Port4(U8 lun)714 BOOLEAN vSCSI_REQUEST_SENSE_Port4(U8 lun)
715 {
716   INT8U *u8RequestSenseData;
717   //Scsi_Cmnd  srb_data;
718   BOOLEAN result;
719 
720   u8RequestSenseData=pUsbData_Port4;
721   Mass_stor_us1_port4.srb = &srb_data_port4;
722   memset(Mass_stor_us1_port4.srb, 0, sizeof(struct scsi_cmnd ));
723 
724   // Build SCSI command.
725   vSCSICmd_REQUEST_SENSE_Port4( Mass_stor_us1_port4.srb,u8RequestSenseData);
726 
727   Mass_stor_us1_port4.srb->lun=lun;
728 
729   //call mass storage function to send CBW
730   //and get REQUEST_SENSE Data. Return CSW to check status.
731   result=Host20_MSCD_usb_stor_control_thread_Port4(&Mass_stor_us1_port4);
732   return result;
733 
734 
735 
736 }
737 
738 //***************************************************************************************
739 // Function Name:bSCSI_INQUIRY_Port4
740 // Description:To ask the device u8DeviceType/u8ProductID/u8ProductVer... information
741 // Input:
742 // Output:
743 // Status:P-OK
744 //***************************************************************************************
745 ///////////////////////////////////////////////////////////////////////////////
746 //		bSCSI_INQUIRY_Port4()
747 //		Description:
748 //			1. scsi inquiry command.
749 //		input: none
750 //		output: TRUE or FALSE (BOOLEAN)
751 ///////////////////////////////////////////////////////////////////////////////
752 //INT8U xdata u8InquiryData[DATA_LENGTH_INQUIRY] _at_ Host20_TEMP_DATA;
bSCSI_INQUIRY_Port4(U8 lun)753 BOOLEAN bSCSI_INQUIRY_Port4(U8 lun)
754 {
755   INT8U u8i, u8j;
756   //Scsi_Cmnd  srb_data;
757   U8 *u8InquiryData;
758   BOOLEAN result;
759 
760   u8InquiryData=pUsbData_Port4;
761   //printf("INQUIRY\n");
762   for(u8j =0; u8j< ScsiCmd_Fail_Retry ;u8j++)
763   {
764 
765     Mass_stor_us1_port4.srb =&srb_data_port4;
766 	memset(Mass_stor_us1_port4.srb, 0, sizeof(struct scsi_cmnd ));
767 
768 	//Build SCSI command.
769 	vSCSICmd_INQUIRY_Port4( Mass_stor_us1_port4.srb, u8InquiryData);
770     Mass_stor_us1_port4.srb->lun=lun;
771 
772 	//call mass storage function to send CBW
773 	//and get INQUIRY Data. Return CSW to check status.
774 	result=Host20_MSCD_usb_stor_control_thread_Port4(&Mass_stor_us1_port4);
775 	if (result==FALSE) continue;
776 
777 	if(Mass_stor_us1_port4.srb->result == SAM_STAT_GOOD)
778 	{
779       //save all INQUIRY data
780 	  Mass_stor_us1_port4.device.u8DeviceType = (u8InquiryData[0] & 0x1F);
781 
782         Mass_stor_us1_port4.Mass_stor_device[lun].bRMB = (u8InquiryData[1] & 0x80) >> 7;
783         //printf("Removable: %d\n", Mass_stor_us1_port4.Mass_stor_device[lun].bRMB);
784 
785 	  for(u8i =0; u8i <8; u8i++)
786 	    Mass_stor_us1_port4.Mass_stor_device[lun].u8VendorID[u8i] = u8InquiryData[u8i+8];
787 	  for(u8i =0; u8i <16; u8i++)
788 		Mass_stor_us1_port4.Mass_stor_device[lun].u8ProductID[u8i] = u8InquiryData[u8i+16];
789 	  for(u8i =0; u8i <4; u8i++)
790 	    Mass_stor_us1_port4.Mass_stor_device[lun].u8ProductVer[u8i] = u8InquiryData[u8i+32];
791 
792 	  if(Mass_stor_us1_port4.device.u8DeviceType != TYPE_DISK)
793 	  {
794 	    DRV_SCSI_DBG(printf("Device type unsuport, it's not a scsi disk%s","\n"));
795 
796 		return FALSE;
797 	  }
798 	  else
799 	  {
800 
801 	    DRV_SCSI_DBG(SCSI_DbgPrint("SCSI INQUIRY : SCSI Device ID <%s>\n",&Mass_stor_us1_port4.Mass_stor_device[lun].u8VendorID));
802 		//SCSI_DbgPrint("SCSI INQUIRY : SCSI Product ID <%s>\n",&Mass_stor_us1.device.u8ProductID);
803 		//SCSI_DbgPrint("SCSI INQUIRY : SCSI Product ver <%s>\n",&Mass_stor_us1.device.u8ProductVer);
804         return TRUE;
805 	  }
806 
807 
808 	}
809 
810   }
811 	return FALSE;
812 }
813 //***************************************************************************************
814 // Function Name:bSCSI_MODE_SENSE_Port4
815 // Description:To know the mode of device <1>.Write Protect => Y/N
816 // Input:
817 // Output:
818 // Status:P-OK
819 //***************************************************************************************
820 ///////////////////////////////////////////////////////////////////////////////
821 //		bSCSI_MODE_SENSE()
822 //		Description:
823 //			1. scsi mode sense command.
824 //		input: none
825 //		output: TRUE or FALSE (BOOLEAN)
826 ///////////////////////////////////////////////////////////////////////////////
bSCSI_MODE_SENSE_Port4(U8 lun)827 BOOLEAN bSCSI_MODE_SENSE_Port4(U8 lun)
828 {
829   INT8U  u8j;
830   INT8U *u8ModeSenseData;
831   BOOLEAN result;
832   //Scsi_Cmnd  srb_data;
833 
834   u8ModeSenseData=pUsbData_Port4;
835 
836   Mass_stor_us1_port4.srb = &srb_data_port4;
837 
838   for(u8j =0; u8j< ScsiCmd_Fail_Retry ;u8j++)
839   {
840     memset(Mass_stor_us1_port4.srb, 0, sizeof(struct scsi_cmnd ));
841     //Build SCSI command.
842 	vSCSICmd_MODE_SENSE_Port4( Mass_stor_us1_port4.srb,0x3F, u8ModeSenseData);
843     Mass_stor_us1_port4.srb->lun=lun;
844 
845 	//call mass storage function to send CBW
846 	//and get Mode Sense Data. Return CSW to check status.
847 	result=Host20_MSCD_usb_stor_control_thread_Port4(&Mass_stor_us1_port4);
848 	if (result==FALSE) return FALSE;
849 
850 	if(Mass_stor_us1_port4.srb->result == SAM_STAT_GOOD)
851 	{
852       //save all Mode Sense(page code=0x3F) data
853 	  //Now we only use u8ModeSenseData[2], this byte save device
854 	  //write protection information
855 	  Mass_stor_us1_port4.Mass_stor_device[lun].bWriteProtect = (u8ModeSenseData[2]==0x80)?
856 												TRUE:FALSE;
857 
858 
859 	  return TRUE;
860 	}
861   }
862   Mass_stor_us1_port4.Mass_stor_device[lun].bWriteProtect=FALSE;      //not support this command
863   return FALSE;
864 }
865 
866 
867 //***************************************************************************************
868 // Function Name:bSCSI_MODE_SENSE_OperCode5A_Port4
869 // Description:To know the mode of device <1>.Write Protect => Y/N
870 // Input:
871 // Output:
872 // Status:P-OK
873 //***************************************************************************************
874 ///////////////////////////////////////////////////////////////////////////////
875 //		bSCSI_MODE_SENSE_OperCode5A_Port4()
876 //		Description:
877 //			1. scsi mode sense command.
878 //		input: none
879 //		output: TRUE or FALSE (BOOLEAN)
880 ///////////////////////////////////////////////////////////////////////////////
bSCSI_MODE_SENSE_OperCode5A_Port4(U8 lun)881 BOOLEAN bSCSI_MODE_SENSE_OperCode5A_Port4(U8 lun)
882 {
883   INT8U  u8j;
884   INT8U *u8ModeSenseData;
885   BOOLEAN result;
886   //Scsi_Cmnd  srb_data;
887 
888   u8ModeSenseData=pUsbData_Port4;
889 
890   Mass_stor_us1_port4.srb = &srb_data_port4;
891 
892   for(u8j =0; u8j< ScsiCmd_Fail_Retry ;u8j++)
893   {
894     memset(Mass_stor_us1_port4.srb, 0, sizeof(struct scsi_cmnd ));
895     //Build SCSI command.
896 		vSCSICmd_MODE_SENSE_OperCode5A_Port4( Mass_stor_us1_port4.srb,0x3F, u8ModeSenseData);
897     Mass_stor_us1_port4.srb->lun=lun;
898 
899 	//call mass storage function to send CBW
900 	//and get Mode Sense Data. Return CSW to check status.
901 	result=Host20_MSCD_usb_stor_control_thread_Port4(&Mass_stor_us1_port4);
902 	if (result==FALSE) return FALSE;
903 
904 	if(Mass_stor_us1_port4.srb->result == SAM_STAT_GOOD)
905 	{
906       //save all Mode Sense(page code=0x3F) data
907 	  //Now we only use u8ModeSenseData[2], this byte save device
908 	  //write protection information
909 	  Mass_stor_us1_port4.Mass_stor_device[lun].bWriteProtect = (u8ModeSenseData[3]==0x80)?
910 												TRUE:FALSE;
911 	  return TRUE;
912 	}
913   }
914   Mass_stor_us1_port4.Mass_stor_device[lun].bWriteProtect=FALSE;      //not support this command
915   return FALSE;
916 }
917 
918 
919 //***************************************************************************************
920 // Function Name:bSCSI_READ_CAPACITY_Port4
921 // Description:To get the CAPACITY
922 // Input:
923 // Output:
924 // Status:S
925 //***************************************************************************************
926 ///////////////////////////////////////////////////////////////////////////////
927 //		bSCSI_READ_CAPACITY_Port4()
928 //		Description:
929 //			1. scsi READ_CAPACITY command.
930 //		input: none
931 //		output: TRUE or FALSE (BOOLEAN)
932 ///////////////////////////////////////////////////////////////////////////////
bSCSI_READ_CAPACITY_Port4(U8 lun)933 BOOLEAN bSCSI_READ_CAPACITY_Port4(U8 lun)
934 {
935   //INT8U u8j;
936   INT8U *u8ReadCapacityData;
937   BOOLEAN result;
938   //Scsi_Cmnd  srb_data;
939 
940   u8ReadCapacityData=pUsbData_Port4;
941   //for(u8j =0; u8j< ScsiCmd_Fail_Retry ;u8j++)
942   {
943     Mass_stor_us1_port4.srb = &srb_data_port4;
944 	memset(Mass_stor_us1_port4.srb, 0, sizeof(struct scsi_cmnd ));
945 
946 	//Build SCSI command.
947 	vSCSICmd_READ_CAPACITY_Port4(Mass_stor_us1_port4.srb, u8ReadCapacityData);
948     Mass_stor_us1_port4.srb->lun=lun;
949 
950     //call mass storage function to send CBW
951 	//and get CAPACITY Data. Return CSW to check status.
952 	result=Host20_MSCD_usb_stor_control_thread_Port4(&Mass_stor_us1_port4);
953 	if (result==FALSE) return result;
954 
955 	if(Mass_stor_us1_port4.srb->result == SAM_STAT_GOOD)
956 	{
957 	  //save all CAPACITY data
958 	  Mass_stor_us1_port4.Mass_stor_device[lun].u32BlockTotalNum = ((INT32U)u8ReadCapacityData[0] << 24) |
959 										   ((INT32U)u8ReadCapacityData[1] << 16) |
960 										   ((INT32U)u8ReadCapacityData[2] << 8) |
961 										   ((INT32U)u8ReadCapacityData[3] ) ;
962 
963 	  Mass_stor_us1_port4.Mass_stor_device[lun].u32BlockSize = ((INT32U)u8ReadCapacityData[4] << 24) |
964 									   ((INT32U)u8ReadCapacityData[5] << 16) |
965 									   ((INT32U)u8ReadCapacityData[6] << 8) |
966 									   ((INT32U)u8ReadCapacityData[7] ) ;
967      //if ( Mass_stor_us1.Mass_stor_device[lun].u32BlockSize > 1024)
968      //{
969      //  printf("Block size over 1024, is %X\n",Mass_stor_us1.Mass_stor_device[lun].u32BlockSize);
970      //  while(1);
971      //}
972 
973 	 DRV_SCSI_DBG(SCSI_DbgPrint("SCSI CAPACITY : SCSI Device total block <0x%x%x>\n",
974 	                           (INT16U)(Mass_stor_us1_port4.Mass_stor_device[lun].u32BlockTotalNum >> 16),
975 					           (INT16U)Mass_stor_us1_port4.Mass_stor_device[lun].u32BlockTotalNum));
976 	 DRV_SCSI_DBG(SCSI_DbgPrint("SCSI CAPACITY : SCSI Product block size <0x%x bytes>\n",(INT16U)Mass_stor_us1_port4.Mass_stor_device[lun].u32BlockSize));
977 
978 	 return TRUE;
979    }
980    else
981    {
982         vSCSI_REQUEST_SENSE_Port4(lun);
983         return FALSE;
984    }
985  }
986  return FALSE;
987 
988 }
989 
bSCSI_READ_FORMAT_CAPACITY_Port4(U8 lun)990 BOOLEAN bSCSI_READ_FORMAT_CAPACITY_Port4(U8 lun)
991 {
992   INT8U u8j;
993   INT8U *u8ReadCapacityData;
994   BOOLEAN result;
995   //Scsi_Cmnd  srb_data;
996 
997   u8ReadCapacityData=pUsbData_Port4;
998   for(u8j =0; u8j< ScsiCmd_Fail_Retry ;u8j++)
999   {
1000       Mass_stor_us1_port4.srb = &srb_data_port4;
1001 	memset(Mass_stor_us1_port4.srb, 0, sizeof(struct scsi_cmnd ));
1002 
1003 	//Build SCSI command.
1004 	vSCSICmd_READ_FORMAT_CAPACITY_Port4(Mass_stor_us1_port4.srb, u8ReadCapacityData);
1005        Mass_stor_us1_port4.srb->lun=lun;
1006 
1007     //call mass storage function to send CBW
1008 	//and get CAPACITY Data. Return CSW to check status.
1009 	result=Host20_MSCD_usb_stor_control_thread_Port4(&Mass_stor_us1_port4);
1010 	if (result==FALSE) return result;
1011 
1012 	if(Mass_stor_us1_port4.srb->result == SAM_STAT_GOOD)
1013 	{
1014 	  //save all CAPACITY data
1015 	  Mass_stor_us1_port4.Mass_stor_device[lun].u32BlockTotalNum = ((INT32U)u8ReadCapacityData[4] << 24) |
1016 										   ((INT32U)u8ReadCapacityData[5] << 16) |
1017 										   ((INT32U)u8ReadCapacityData[6] << 8) |
1018 										   ((INT32U)u8ReadCapacityData[7] ) ;
1019 
1020 	  Mass_stor_us1_port4.Mass_stor_device[lun].u32BlockSize = ((INT32U)u8ReadCapacityData[9] << 16) |
1021 									   ((INT32U)u8ReadCapacityData[10] << 8) |
1022 									   ((INT32U)u8ReadCapacityData[11] ) ;
1023      //if ( Mass_stor_us1.Mass_stor_device[lun].u32BlockSize > 1024)
1024      //{
1025      //  printf("Block size over 1024, is %X\n",Mass_stor_us1.Mass_stor_device[lun].u32BlockSize);
1026      //  while(1);
1027      //}
1028 
1029 	 DRV_SCSI_DBG(SCSI_DbgPrint("SCSI CAPACITY : SCSI Device total block <0x%x%x>\n",
1030 	                           (INT16U)(Mass_stor_us1_port4.Mass_stor_device[lun].u32BlockTotalNum >> 16),
1031 					           (INT16U)Mass_stor_us1_port4.Mass_stor_device[lun].u32BlockTotalNum));
1032 	 DRV_SCSI_DBG(SCSI_DbgPrint("SCSI CAPACITY : SCSI Product block size <0x%x bytes>\n",(INT16U)Mass_stor_us1_port4.Mass_stor_device[lun].u32BlockSize));
1033 
1034 	 return TRUE;
1035    }
1036  }
1037  return FALSE;
1038 
1039 }
1040 
1041 
1042 extern void OTGH_PT_Bulk_Init_Port4(void);
1043 extern BOOLEAN MDrv_UsbHost_Init_Port4(void);
1044 //***************************************************************************************
1045 // Function Name:bSCSI_TEST_UNIT_READY_Port4
1046 // Description: To know that "device is ready ?"
1047 // Input:
1048 // Output:
1049 // Status:
1050 //***************************************************************************************
1051 ///////////////////////////////////////////////////////////////////////////////
1052 //		bSCSI_TEST_UNIT_READY_Port4()
1053 //		Description:
1054 //			1. scsi TEST_UNIT_READY command.
1055 //		input: none
1056 //		output: TRUE or FALSE (BOOLEAN)
1057 ///////////////////////////////////////////////////////////////////////////////
bSCSI_TEST_UNIT_READY_Port4(U8 lun)1058 BOOLEAN bSCSI_TEST_UNIT_READY_Port4(U8 lun)
1059 {
1060   INT8U u8j;
1061   BOOLEAN result;
1062   #ifdef ATV_SERISE_USE
1063   U32 i;
1064   #endif
1065   //Scsi_Cmnd  srb_data;
1066   //printf("TUR\n");
1067 
1068   for(u8j =0; u8j< TestUnitReady_Fail_Retry ;u8j++)
1069   {
1070     //printf("connect status:%02bx\n",mwHost20_PORTSC_ConnectStatus_Rd());
1071 	if (mwHost20_PORTSC_ConnectStatus_Rd()==0)
1072       return FALSE;               //device is not connected
1073 
1074 	Mass_stor_us1_port4.srb = &srb_data_port4;
1075 	memset((U8 xdata *)Mass_stor_us1_port4.srb, 0, sizeof(struct scsi_cmnd ));
1076 
1077 	// Build SCSI command.
1078 	vSCSICmd_Prepare_Port4(Mass_stor_us1_port4.srb,TEST_UNIT_READY);
1079 	//vSCSICmd_TEST_UNIT_READY(Mass_stor_us1.srb);
1080     Mass_stor_us1_port4.srb->lun=lun;
1081     //printf("Mass_stor_us1.srb:%02bx\n",Mass_stor_us1.srb->request_bufflen);
1082 	//call mass storage function to send CBW
1083 	//and get CAPACITY Data. Return CSW to check status.
1084 
1085 	result=Host20_MSCD_usb_stor_control_thread_Port4(&Mass_stor_us1_port4);
1086     //printf("result:%02bx\n",result);
1087 #if 1
1088         if (result == FALSE)
1089         {
1090             if (gUsbStatus_Port4== USB_TIMEOUT)
1091             {
1092                 DRV_SCSI_DBG(printf("resend TUR\n"));
1093                 if ( MDrv_UsbHost_Init_Port4() && (flib_Host20_Enumerate_Port4(1,3)!=0) )
1094                 {
1095                     OTGH_PT_Bulk_Init_Port4();
1096                     continue;
1097                 }
1098             }
1099             else
1100                 return result;
1101         }
1102 #else
1103         if (result==FALSE)
1104         {
1105             return result;
1106         }
1107 #endif
1108 
1109 	if(Mass_stor_us1_port4.srb->result == SAM_STAT_GOOD)
1110 	{
1111 	  Mass_stor_us1_port4.Mass_stor_device[lun].bDeviceReady = TRUE;
1112       //SCSI_DbgPrint("SCSI TEST UNIT READY : Succeed\n",u8Drive);
1113 
1114 	  return TRUE;
1115 	}
1116 	else
1117 	{
1118 	  #ifndef ATV_SERISE_USE
1119          MsOS_DelayTask(10);
1120          #else
1121          for(i=0;i<(0x100);i++);
1122          #endif
1123 
1124 
1125 	  result=vSCSI_REQUEST_SENSE_Port4(lun);
1126       if ((pUsbData_Port4[12]==0x3a)&&(pUsbData_Port4[13]==0)) return FALSE;  //no media
1127 	  if (result==FALSE) return result;
1128 	}
1129     #ifndef ATV_SERISE_USE
1130 	MsOS_DelayTask(10);
1131 	#else
1132 	for(i=0;i<0x100;i++);
1133 	#endif
1134   }
1135 	//SCSI_DbgPrint("SCSI TEST UNIT READY : Failed%s","\n");
1136   return FALSE;
1137 }
1138 extern BOOLEAN  MDrv_Usb_Device_Enum_Port4(void);
1139 #ifdef ATV_SERISE_USE
1140 extern void EnableINT(void);
1141 #endif
1142 
bSCSI_TEST_UNIT_READY2_Port4(U8 lun)1143 BOOLEAN bSCSI_TEST_UNIT_READY2_Port4(U8 lun)
1144 {
1145   INT8U u8j;
1146   BOOLEAN result;
1147   U8  RetryCnt=0;
1148 
1149   #ifdef ATV_SERISE_USE
1150   U32 i;
1151   #endif
1152   //Scsi_Cmnd  srb_data;
1153   //printf("TUR\n");
1154 
1155   for(u8j =0; u8j< TestUnitReady_Fail_Retry ;u8j++)
1156   {
1157     //printf("connect status:%02bx\n",mwHost20_PORTSC_ConnectStatus_Rd());
1158 	if (mwHost20_PORTSC_ConnectStatus_Rd()==0)
1159       return FALSE;               //device is not connected
1160 
1161 	Mass_stor_us1_port4.srb = &srb_data_port4;
1162 	memset((U8 xdata *)Mass_stor_us1_port4.srb, 0, sizeof(struct scsi_cmnd ));
1163 
1164 	// Build SCSI command.
1165 	vSCSICmd_Prepare_Port4(Mass_stor_us1_port4.srb,TEST_UNIT_READY);
1166 	//vSCSICmd_TEST_UNIT_READY(Mass_stor_us1.srb);
1167     Mass_stor_us1_port4.srb->lun=lun;
1168     //printf("Mass_stor_us1.srb:%02bx\n",Mass_stor_us1.srb->request_bufflen);
1169 	//call mass storage function to send CBW
1170 	//and get CAPACITY Data. Return CSW to check status.
1171 
1172 	result=Host20_MSCD_usb_stor_control_thread_Port4(&Mass_stor_us1_port4);
1173     //printf("result:%02bx\n",result);
1174 
1175     if (result==FALSE)
1176     {
1177       RetryCnt++;
1178       if (gUsbStatus_Port4==USB_TIMEOUT)
1179       {
1180         if (RetryCnt > 3) return FALSE;
1181         if ((RetryCnt==2)&&(mwOTG20_Control_HOST_SPD_TYP_Rd()==2) )           //make sure it is hi speed
1182         {
1183           DRV_SCSI_DBG( printf("Force FS\n"));
1184           UHC4_ORXBYTE(0x40,0x80);//force enter FSmode
1185         }
1186         #ifndef ATV_SERISE_USE
1187         msAPI_Timer_ResetWDT();
1188         #else
1189           #ifdef Enable_Close_INT
1190           //XBYTE[0x2B00]&=0xFD;
1191           EnableINT();
1192           #endif
1193         #endif
1194         #ifdef Enable_Low_Temperature_Patch
1195 	    if(gSpeed_Port4==0)
1196 	    {
1197 	      //printf("\r\n CDR toggle!!",0);
1198               UTMI4_SETXBYTE(0x0a,UTMI4_READXBYTE(0x0a)^0x10);    //invert CDR_CLOCK
1199               UTMI4_ORXBYTE(0x06,0x03);  //reset UTMI
1200               UTMI4_ANDXBYTE(0x06,0xfc);
1201 	    }
1202 		#endif
1203        // MDrv_Usb_Device_Enum();
1204         if (MDrv_Usb_Device_Enum_Port4()==FALSE) return FALSE;
1205 
1206         continue;
1207       }
1208       else
1209         return FALSE;
1210     }
1211 
1212 	if(Mass_stor_us1_port4.srb->result == SAM_STAT_GOOD)
1213 	{
1214 	  Mass_stor_us1_port4.Mass_stor_device[lun].bDeviceReady = TRUE;
1215       //SCSI_DbgPrint("SCSI TEST UNIT READY : Succeed\n",u8Drive);
1216 
1217 	  return TRUE;
1218 	}
1219 	else
1220 	{
1221 	  #ifndef ATV_SERISE_USE
1222          MsOS_DelayTask(10);
1223          #else
1224          for(i=0;i<(0x100);i++);
1225          #endif
1226 
1227 
1228 	  result=vSCSI_REQUEST_SENSE_Port4(lun);
1229       if ((pUsbData_Port4[12]==0x3a)&&(pUsbData_Port4[13]==0)) return FALSE;  //no media
1230       if ((pUsbData_Port4[12]==0x28)&&(pUsbData_Port4[13]==0)) return FALSE;  //media change
1231 	  if (result==FALSE) return result;
1232 	}
1233     #ifndef ATV_SERISE_USE
1234 	MsOS_DelayTask(10);
1235 	#else
1236 	for(i=0;i<0x100;i++);
1237 	#endif
1238   }
1239 	//SCSI_DbgPrint("SCSI TEST UNIT READY : Failed%s","\n");
1240   return FALSE;
1241 }
1242 //***************************************************************************************
1243 // Function Name:bSCSI_Initial_Port4
1244 // Description:
1245 // Input:
1246 // Output:
1247 // Status:P-OK
1248 //***************************************************************************************
1249 U8 ValidLunNum_Port4;
bSCSI_Initial_Port4(void)1250 BOOLEAN bSCSI_Initial_Port4(void)
1251 {
1252   //INT8U i=0;
1253   //iCardSuddenlyRemove = FALSE;
1254   //iCardReplace = FALSE;
1255   BOOLEAN		bFoundValidDev = FALSE;
1256   struct LUN_Device* LunDevice = Mass_stor_us1_port4.Mass_stor_device;
1257   U8		LunIdx;
1258 
1259  ValidLunNum_Port4=0;
1260  for (	LunIdx=0; LunIdx<=Mass_stor_us1_port4.max_lun; LunIdx++)
1261   {
1262     LunDevice[LunIdx].bDeviceValid=FALSE;
1263 	if (bSCSI_INQUIRY_Port4(LunIdx))
1264        {
1265             LunDevice[LunIdx].bDeviceValid=TRUE;
1266             ValidLunNum_Port4++;
1267        }
1268 	//break;
1269   }
1270  DRV_SCSI_DBG(printf("ValidLunNum_Port4:%02bx\n",ValidLunNum_Port4));
1271     // For some usb harddrive without enough power, may meet following case.
1272     if (!ValidLunNum_Port4)
1273     {
1274     	  if (mwHost20_PORTSC_ConnectChange_Rd()==0)
1275             MDrv_SetUsbDeviceStatus_Port4(BAD_DEVICE);
1276         return bFoundValidDev;
1277     }
1278 
1279     // Sometime device is failed to initial at first time, but success at last.
1280     // It set the device status as BAD_DEVICE at first time when it failed.
1281     // We need to set correct value to device status when successed.
1282     if (gSpeed_Port4==2)
1283     {
1284         MDrv_SetUsbDeviceStatus_Port4(USB20_DEVICE);
1285     }
1286     else
1287     {
1288         MDrv_SetUsbDeviceStatus_Port4(USB11_DEVICE);
1289     }
1290   #ifdef ATV_SERISE_USE
1291     #ifdef Enable_Close_INT
1292   EA=0;
1293   #endif
1294   #endif
1295   for (	LunIdx=0; LunIdx<=Mass_stor_us1_port4.max_lun; LunIdx++)
1296   {
1297     LunDevice[LunIdx].bDeviceReady = FALSE;
1298 	if (!bInit_USB_LUN_Port4(LunIdx))
1299 	  continue;
1300 	LunDevice[LunIdx].bDeviceReady = TRUE;
1301     bFoundValidDev = TRUE;
1302 
1303   }
1304   #ifdef ATV_SERISE_USE
1305     #ifdef Enable_Close_INT
1306   EA=1;
1307   #endif
1308   #endif
1309   return bFoundValidDev;
1310 
1311 }
GetValidLun_Port4(void)1312 void GetValidLun_Port4(void)
1313 {
1314   U8 LunIdx;
1315   struct LUN_Device* LunDevice = Mass_stor_us1_port4.Mass_stor_device;
1316 
1317   if (LunDevice == NULL)
1318   {
1319       DRV_SCSI_DBG(printf(" LUN structure not initialized!!\n"));
1320       return;
1321   }
1322 
1323   if ( (Mass_stor_us1_port4.max_lun == 0) && (!LunDevice[0].bRMB) && LunDevice[0].bDeviceReady)
1324   {
1325         //20120817, Don't do TUR on this special USB HDD.
1326         //It returns NOT READY after 30 minutes idle.
1327         return;
1328   }
1329 
1330   for (LunIdx=0; LunIdx<=Mass_stor_us1_port4.max_lun; LunIdx++)
1331   {
1332     if (LunDevice[LunIdx].bDeviceValid)
1333     {
1334       if(!bSCSI_TEST_UNIT_READY2_Port4(LunIdx))
1335       {
1336         LunDevice[LunIdx].bDeviceReady=FALSE;
1337         LunDevice[LunIdx].u32BlockSize = 0; // 20111110: resolve lun capacity zero if not the first lun
1338         LunDevice[LunIdx].u32BlockTotalNum = 0;
1339       }
1340       else
1341       {
1342         LunDevice[LunIdx].bDeviceReady = TRUE;
1343         if (LunDevice[LunIdx].u32BlockSize == 0) // 20111110: resolve lun capacity zero if not the first lun
1344         {
1345             if(!bSCSI_READ_CAPACITY_Port4(LunIdx))
1346             {
1347               if (!bSCSI_READ_FORMAT_CAPACITY_Port4(LunIdx))
1348               {
1349                   DRV_SCSI_DBG(SCSI_DbgPrint("Read CAPACITY failed.%s","\n"));
1350               }
1351             }
1352         }
1353       }
1354     }
1355     else
1356       LunDevice[LunIdx].bDeviceReady=FALSE;                   //not a valid device, so always not ready
1357   }
1358 }
bInit_USB_LUN_Port4(U8 Lun)1359 BOOLEAN bInit_USB_LUN_Port4(U8 Lun)
1360 {
1361   U16   uVID, uPID;
1362   U8     ii;
1363   BOOLEAN bIsForceMS1A = FALSE;
1364 
1365   MDrv_USBGetVIDPID_Port4(&uVID, &uPID);
1366   if ( (uVID == 0xFCA) && (uPID == 0x8004) ) //20130301, for blackberry phone
1367   {
1368       if (!bSCSI_INQUIRY_Port4(Lun))
1369       {
1370         DRV_SCSI_DBG(SCSI_DbgPrint("Scsi inquiry failed (Lun=%d).\n",u8Drive_port4));
1371     	return FALSE;
1372       }
1373   }
1374 
1375   if(!bSCSI_TEST_UNIT_READY_Port4(Lun))
1376   {
1377     DRV_SCSI_DBG(SCSI_DbgPrint("Scsi Device not ready (Lun=%d).\n",Lun));
1378 	return FALSE;
1379   }
1380   //bSCSI_INQUIRY();
1381   if (!bSCSI_INQUIRY_Port4(Lun))
1382   {
1383     DRV_SCSI_DBG(SCSI_DbgPrint("Scsi inquiry failed (Lun=%d).\n",u8Drive_port4));
1384 	return FALSE;
1385   }
1386   if(!bSCSI_READ_CAPACITY_Port4(Lun))
1387   {
1388     if (!bSCSI_READ_FORMAT_CAPACITY_Port4(Lun))
1389     {
1390         DRV_SCSI_DBG(SCSI_DbgPrint("Read CAPACITY failed.%s","\n"));
1391         return FALSE;
1392     }
1393   }
1394 
1395 #ifdef ENABLE_CBI_HOST
1396     if ((psAttachDevice_Port4->saCD[0].sInterface[0].bInterfaceProtocol==0x00)||(psAttachDevice_Port4->saCD[0].sInterface[0].bInterfaceProtocol==0x01))
1397     {
1398         //do nothing
1399     }
1400     else
1401 #endif
1402     {
1403     MDrv_USBGetVIDPID_Port4(&uVID, &uPID);
1404     DRV_SCSI_DBG(printf("VID: %x, PID: %x\n", uVID, uPID));
1405     ii = 0;
1406     while ( (gForceModeSense1A_Port4[ii].VID != 0) && (gForceModeSense1A_Port4[ii].PID != 0) )
1407     {
1408         if ( (uVID == gForceModeSense1A_Port4[ii].VID) && (uPID == gForceModeSense1A_Port4[ii].PID) )
1409         {
1410             DRV_SCSI_DBG(printf("Find a Force Mode Sense 1A device\n"));
1411             bIsForceMS1A = TRUE;
1412         }
1413 
1414         ii++;
1415         if (ii >= (sizeof(gForceModeSense1A_Port4) / sizeof(struct stForceModeSense1A)))
1416           break;
1417     }
1418 
1419     if (bIsForceMS1A)
1420         bSCSI_MODE_SENSE_Port4(Lun);
1421     else
1422         bSCSI_MODE_SENSE_OperCode5A_Port4(Lun);
1423 
1424     }
1425   //if (!bSCSI_MODE_SENSE(Lun))
1426   //{
1427   //  SCSI_DbgPrint("Mode sense failed!\n");
1428   //  return FALSE;
1429   //}
1430 
1431   if(!bSCSI_TEST_UNIT_READY_Port4(Lun))
1432   {
1433     DRV_SCSI_DBG(SCSI_DbgPrint("Scsi Device not ready (Lun=%d).\n",u8Drive_port4));
1434 	return FALSE;
1435   }
1436   return TRUE;
1437 
1438 }
1439 
1440 
1441 //***************************************************************************************
1442 // Function Name:
1443 // Description:
1444 // Input:
1445 // Output:
1446 // Status:
1447 //***************************************************************************************
1448 
1449 
1450 
bSCSI_Read_Write10_Port4(BOOLEAN DoWrite,U8 lun,INT32U u32BlockAddr,INT32U u32BlockNum,U32 u8Buffer)1451 BOOLEAN bSCSI_Read_Write10_Port4(BOOLEAN DoWrite, U8 lun,  INT32U u32BlockAddr, INT32U u32BlockNum,U32 u8Buffer)
1452 {
1453 
1454   //Scsi_Cmnd  srb_data;
1455   BOOLEAN result;
1456   Mass_stor_us1_port4.srb = &srb_data_port4;
1457   //memset(Mass_stor_us1.srb, 0, sizeof(struct scsi_cmnd ));
1458   //printf("read sector:%lx, sz:%lx\n",u32BlockAddr,u32BlockNum);
1459 
1460   if (DoWrite)
1461   {
1462     if(Mass_stor_us1_port4.Mass_stor_device[lun].bWriteProtect)
1463     {
1464 	  DRV_SCSI_DBG(printf("This device is write protect now\n"));
1465 	  return FALSE;
1466 	}
1467   }
1468 
1469   //Build SCSI command.
1470   vSCSICmd_READ_WRITE_10_Port4(DoWrite,&Mass_stor_us1_port4, Mass_stor_us1_port4.srb, lun,
1471 								u32BlockAddr, (INT16U)u32BlockNum, u8Buffer);
1472 
1473 
1474   //call mass storage function to send scsi command
1475   result=Host20_MSCD_usb_stor_control_thread_Port4(&Mass_stor_us1_port4);
1476   if (result==FALSE) return result;
1477 
1478   if(Mass_stor_us1_port4.srb->result != SAM_STAT_GOOD)
1479   {
1480     DRV_SCSI_DBG(SCSI_DbgPrint("Scsi ReadWrite_10 command failed.%s","\n"));
1481 
1482 	return FALSE;
1483   }
1484 
1485 
1486   //printf("#");
1487   return TRUE;
1488 
1489 
1490 
1491 }
1492 #endif //#if defined(MSOS_TYPE_NOS)
1493 
1494 
1495