31 iUsb.Close(); |
39 iUsb.Close(); |
32 } |
40 } |
33 |
41 |
34 void CUsbConsole::ConstructL(const TDesC& aTitle) |
42 void CUsbConsole::ConstructL(const TDesC& aTitle) |
35 { |
43 { |
|
44 TUsbPortConfig portConfig; |
|
45 User::LeaveIfError(ReadConfig(aTitle, portConfig)); |
|
46 |
36 User::LeaveIfError(iUsb.Connect()); |
47 User::LeaveIfError(iUsb.Connect()); |
37 |
48 |
38 TRequestStatus stat; |
49 TRequestStatus stat; |
39 // assume USB device already started |
50 if (portConfig.iPersonality >= 0) |
40 /*iUsb.Start(stat); |
|
41 User::WaitForRequest(stat); |
|
42 // KErrAccessDenied returned if already started; |
|
43 if (stat.Int()!=KErrAccessDenied) |
|
44 { |
51 { |
45 Message(EError, KUsbError, stat.Int(), 1); |
52 iUsb.TryStart(portConfig.iPersonality, stat); |
46 User::LeaveIfError(stat.Int()); |
53 User::WaitForRequest(stat); |
47 }*/ |
54 Message(ErrOrDebug(stat.Int()), _L("Starting USB personality %d returned %d"), portConfig.iPersonality, stat.Int()); |
|
55 } |
48 |
56 |
49 // Wait for an enumeration that supports ACM (this is so that if the device defaulted to say mass storage and was then reconfigured to a personality with ACM, we wait for the ACM reconfiguration |
57 // Wait for an enumeration that supports ACM (this is so that if the device defaulted to say mass storage and was then reconfigured to a personality with ACM, we wait for the ACM reconfiguration |
50 TBool gotAcm = EFalse; |
58 TBool gotAcm = EFalse; |
51 while (!gotAcm) |
59 while (!gotAcm) |
52 { |
60 { |
53 TUsbDeviceState usbState; |
61 TUsbDeviceState usbState; |
54 User::LeaveIfError(iUsb.GetDeviceState(usbState)); |
62 User::LeaveIfError(iUsb.GetDeviceState(usbState)); |
55 if (usbState & EUsbDeviceStateConfigured) |
63 if (usbState & (EUsbDeviceStateConfigured|EUsbDeviceStatePowered)) // We should only need to check for EUsbDeviceStateConfigured, but some HW doesn't go to configured state if the cable is inserted before USB is started |
56 { |
64 { |
57 // Check if we have ACM |
65 // Check if we have ACM |
58 TInt currentPersonality; |
66 TInt currentPersonality; |
59 User::LeaveIfError(iUsb.GetCurrentPersonalityId(currentPersonality)); |
67 TInt err = iUsb.GetCurrentPersonalityId(currentPersonality); |
60 User::LeaveIfError(iUsb.ClassSupported(currentPersonality, KECACMUid, gotAcm)); |
68 if (!err) |
|
69 { |
|
70 err = iUsb.ClassSupported(currentPersonality, KECACMUid, gotAcm); |
|
71 } |
61 _LIT(KGotIt, "Current USB personality has ACM, proceeding"); |
72 _LIT(KGotIt, "Current USB personality has ACM, proceeding"); |
62 _LIT(KNotGotIt, "Current USB personality doesn't have ACM, waiting for re-enumeration"); |
73 _LIT(KNotGotIt, "Current USB personality doesn't have ACM, waiting for re-enumeration"); |
63 if (gotAcm) Message(EInformation, KGotIt); |
74 if (gotAcm) Message(EInformation, KGotIt); |
64 else Message(EInformation, KNotGotIt); |
75 else Message(EInformation, KNotGotIt); |
65 } |
76 } |
67 if (!gotAcm) |
78 if (!gotAcm) |
68 { |
79 { |
69 // We're not enumerated, or we are but don't have ACM. So wait for a (re-)enumeration |
80 // We're not enumerated, or we are but don't have ACM. So wait for a (re-)enumeration |
70 _LIT(KWaitingForEnumeration, "Waiting for USB enumeration (please connect USB cable)"); |
81 _LIT(KWaitingForEnumeration, "Waiting for USB enumeration (please connect USB cable)"); |
71 Message(EInformation, KWaitingForEnumeration); |
82 Message(EInformation, KWaitingForEnumeration); |
72 iUsb.DeviceStateNotification(EUsbDeviceStateConfigured, usbState, stat); |
83 iUsb.DeviceStateNotification(EUsbDeviceStateConfigured|EUsbDeviceStatePowered, usbState, stat); |
73 User::WaitForRequest(stat); |
84 User::WaitForRequest(stat); |
74 if (stat.Int() != KErrNone) |
85 if (stat.Int() != KErrNone) |
75 { |
86 { |
76 _LIT(KUsbError, "Error configuring USB: %d"); |
87 _LIT(KUsbError, "Error configuring USB: %d"); |
77 Message(EError, KUsbError, stat.Int()); |
88 Message(EError, KUsbError, stat.Int()); |
78 User::Leave(stat.Int()); |
89 User::Leave(stat.Int()); |
79 } |
90 } |
80 _LIT(KUsbEnumerated, "USB cable connected."); |
91 _LIT(KUsbEnumerated, "USB state changed to %d."); |
81 Message(EInformation, KUsbEnumerated); |
92 Message(EInformation, KUsbEnumerated, usbState); |
82 } |
93 } |
83 } |
94 } |
84 |
95 |
85 // Run the preamble script, if we have one. Because iosrv is multithreaded this shouldn't cause a deadlock so long as we use a different console (in this case, nullcons) |
96 // Run the preamble script, if we have one. Because iosrv is multithreaded this shouldn't cause a deadlock so long as we use a different console (in this case, nullcons) |
86 _LIT(KPreamble, "--console nullcons vt100usbcons_preamble"); |
97 _LIT(KPreamble, "--console nullcons vt100usbcons_preamble"); |
105 else if (err != KErrNotFound) |
116 else if (err != KErrNotFound) |
106 { |
117 { |
107 Message(EInformation, _L("Preamble script failed with %d"), err); |
118 Message(EInformation, _L("Preamble script failed with %d"), err); |
108 } |
119 } |
109 |
120 |
110 //TODO should we ensure that the port passed in here is an ACM::%s port? |
121 Message(EInformation, _L("Opening %S"), &portConfig.iPort); |
111 Message(EInformation, _L("Opening %S"), &aTitle); |
122 CVtcSerialConsole::ConstructL(portConfig.iPort); |
112 CVtcSerialConsole::ConstructL(aTitle); |
|
113 } |
123 } |
|
124 |
|
125 TInt CUsbConsole::ReadConfig(const TDesC& aConfigDes, TUsbPortConfig& aConfig) |
|
126 { |
|
127 _LIT(KKeywordPort, "port"); |
|
128 _LIT(KKeywordPersonality, "personality"); |
|
129 |
|
130 TBool keywordFound(EFalse); |
|
131 TLex lex(aConfigDes); |
|
132 while (!lex.Eos()) |
|
133 { |
|
134 TPtrC keyword; |
|
135 TPtrC value; |
|
136 TInt err = ReadKeywordValuePair(lex, keyword, value); |
|
137 if (err != KErrNone) |
|
138 { |
|
139 break; |
|
140 } |
|
141 |
|
142 if (keyword == KKeywordPort) |
|
143 { |
|
144 aConfig.iPort.Set(value); |
|
145 keywordFound = ETrue; |
|
146 } |
|
147 else if (keyword == KKeywordPersonality) |
|
148 { |
|
149 TLex lex(value); |
|
150 TInt err = lex.Val(aConfig.iPersonality); |
|
151 if (err) return err; |
|
152 keywordFound = ETrue; |
|
153 } |
|
154 } |
|
155 |
|
156 if (!keywordFound) |
|
157 { |
|
158 // Treat unrecognised string as a port (to preserve backwards compatibility with earlier releases). |
|
159 aConfig.iPort.Set(aConfigDes); |
|
160 } |
|
161 |
|
162 return KErrNone; |
|
163 } |