00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025 #include <es_sock.h>
00026 #include <bt_sock.h>
00027
00028 #include "bluetoothcommunicator.h"
00029 #include "btdiscoverer.h"
00030 #include "cobainserver.h"
00031 #include "serversession.h"
00032 #include "Log.h"
00033
00034 CBTDiscoverer * CBTDiscoverer::NewL(RMessage &aMessage, CServerSession &aSession)
00035 {
00036 CBTDiscoverer *d = new (ELeave) CBTDiscoverer(aMessage, aSession);
00037 CleanupStack::PushL(d);
00038 d->ConstructL();
00039 CleanupStack::Pop();
00040
00041 return d;
00042 }
00043
00044 void CBTDiscoverer::ConstructL()
00045 {
00046
00047 iSdpPattern = CSdpSearchPattern::NewL();
00048
00049
00050
00051
00052 TUint aServiceClassID = iMessage.Int2();
00053 iSdpPattern->AddL(aServiceClassID);
00054
00055
00056
00057
00058
00059
00060
00061 }
00062
00063 CBTDiscoverer::CBTDiscoverer(RMessage &aMessage, CServerSession &aSession)
00064 : CActive(CActive::EPriorityStandard),
00065 iMessage(aMessage),
00066 iSession(aSession),
00067 iCurrentDeviceIndex(-1)
00068 {
00069 }
00070
00071 CBTDiscoverer::~CBTDiscoverer()
00072 {
00073 iDeviceAddresses.ResetAndDestroy();
00074 delete iSdpPattern;
00075 delete iAgent;
00076 }
00077
00078 void CBTDiscoverer::DoCancel()
00079 {
00080
00081 iHr.Close();
00082
00083 delete iPeerList;
00084 iPeerList = NULL;
00085 }
00086
00087 void CBTDiscoverer::StartL(RSocketServ &aSocketServ)
00088 {
00089
00090
00091 iPeerList = new (ELeave) TPeerDataList();
00092
00093 TProtocolDesc pInfo;
00094 User::LeaveIfError(aSocketServ.FindProtocol(_L("BTLinkManager"), pInfo));
00095
00096
00097 User::LeaveIfError(iHr.Open(aSocketServ, pInfo.iAddrFamily, pInfo.iProtocol));
00098
00099
00100 TInquirySockAddr addr;
00101 TNameEntry name;
00102 addr.SetIAC(KGIAC);
00103 addr.SetAction(KHostResName | KHostResInquiry);
00104
00105
00106 CActiveScheduler::Add(this);
00107
00108
00109 TRequestStatus status;
00110 iHr.GetByAddress(addr, iNameEntry, iStatus);
00111
00112
00113 SetActive();
00114 }
00115
00116 void CBTDiscoverer::DiscoverServices(TNameRecord &aNameRecord)
00117 {
00118 delete iAgent;
00119 iAgent = NULL;
00120
00121
00122
00123
00124 TBTDevAddr btaddr = static_cast<TBTSockAddr>(aNameRecord.iAddr).BTAddr();
00125
00126 TRAPD(err, (iAgent = CSdpAgent::NewL(*this, btaddr)));
00127 if( err != KErrNone ) {
00128 User::Panic(KBTDiscovererPanic, KErrBtdiscovererAllocFailed);
00129 }
00130
00131 iAgent->SetRecordFilterL(*iSdpPattern);
00132 iAgent->NextRecordRequestL();
00133 }
00134
00135
00136 void CBTDiscoverer::FinishDiscovery()
00137 {
00138
00139
00140 iCurrentDeviceIndex = -1;
00141
00142
00143 iSession.SetPeerList(iPeerList);
00144 iPeerList = NULL;
00145
00146
00147 TBuf8<sizeof(TInt)> buf;
00148 buf.Copy((const TUint8 *)(&iNumPeers), sizeof(TInt));
00149 iMessage.WriteL(iMessage.Ptr1(), buf);
00150
00151 iMessage.Complete(KErrNone);
00152
00153
00154 iDeviceAddresses.ResetAndDestroy();
00155 }
00156
00157 void CBTDiscoverer::DeviceDiscovered()
00158 {
00159 if( iStatus == KErrNone ) {
00160 TNameRecord record = iNameEntry();
00161
00162
00163
00164
00165 TNameRecord *new_record = NULL;
00166 TRAPD(err, (new_record = new (ELeave) TNameRecord()));
00167 if( err != KErrNone ) {
00168 User::Panic(KBTDiscovererPanic, KErrBtdiscovererAllocFailed);
00169 }
00170
00171
00172 Mem::Copy(new_record, &record, sizeof(TNameRecord));
00173
00174
00175 iDeviceAddresses.Append(new_record);
00176
00177
00178 iHr.Next(iNameEntry, iStatus);
00179 SetActive();
00180 } else {
00181
00182
00183
00184 iHr.Close();
00185
00186
00187 if( iDeviceAddresses.Count() > 0 ) {
00188
00189 iCurrentDeviceIndex = 0;
00190 DiscoverServices(*iDeviceAddresses[iCurrentDeviceIndex]);
00191 } else {
00192
00193 FinishDiscovery();
00194 }
00195 }
00196 }
00197
00198 void CBTDiscoverer::RunL()
00199 {
00200
00201
00202 DeviceDiscovered();
00203 }
00204
00205 TInt CBTDiscoverer::RunError(TInt aError)
00206 {
00207
00208
00209 return aError;
00210 }
00211
00213
00215
00216 void CBTDiscoverer::AttributeRequestComplete(TSdpServRecordHandle ,
00217 TInt aError)
00218 {
00219
00220
00221 if( aError != KErrNone ) {
00222
00223
00224 } else {
00225
00226 TRAPD(err, iAgent->NextRecordRequestL());
00227 if( err != KErrNone ) {
00228
00229
00230 }
00231 }
00232 }
00233
00234 void CBTDiscoverer::AttributeRequestResult(TSdpServRecordHandle ,
00235 TSdpAttributeID ,
00236 CSdpAttrValue* aAttrValue)
00237 {
00238
00239 iAttrNum = 0;
00240 iPeerOk = ETrue;
00241
00242
00243
00244
00245
00246 TRAPD(err, aAttrValue->AcceptVisitorL(*this));
00247 if( err != KErrNone )
00248 {
00249
00250
00251 }
00252 }
00253
00254
00255 void CBTDiscoverer::NextRecordRequestComplete(TInt aError,
00256 TSdpServRecordHandle aHandle,
00257 TInt aTotalRecordsCount)
00258 {
00259
00260
00261
00262 if( (aError == KErrNone) && (aTotalRecordsCount > 0) ) {
00263
00264
00265
00266
00267
00268 TRAPD(err, iAgent->AttributeRequestL(aHandle, KSdpAttrIdProtocolDescriptorList));
00269 if( err != KErrNone ) {
00270
00271
00272 }
00273 } else {
00274
00275
00276 iCurrentDeviceIndex++;
00277
00278 if( iCurrentDeviceIndex < iDeviceAddresses.Count() ) {
00279 DiscoverServices(*iDeviceAddresses[iCurrentDeviceIndex]);
00280 } else {
00281
00282 FinishDiscovery();
00283 }
00284 }
00285 }
00286
00288
00290
00291
00292
00293
00294
00295
00296
00297
00298 const TInt KCobainProtocolStackSize = 4;
00299
00300 static const TSdpElementType KCtalkStack[KCobainProtocolStackSize] =
00301 { ETypeDES, ETypeDES, ETypeUUID, ETypeUint };
00302
00303 void CBTDiscoverer::VisitAttributeValueL(CSdpAttrValue &aValue,
00304 TSdpElementType aType)
00305 {
00306
00307 if( !iPeerOk ||
00308 (iAttrNum >= KCobainProtocolStackSize) ||
00309 (KCtalkStack[iAttrNum++] != aType) ) {
00310 iPeerOk = EFalse;
00311
00312
00313 return;
00314 }
00315
00316 TBuf<64> buf;
00317
00318 TBuf8<16> uuid;
00319 TUint *val;
00320
00321 switch( aType ) {
00322 case ETypeUUID:
00323
00324 uuid = aValue.UUID().ShortestForm();
00325 val = (TUint*)uuid.Ptr();
00326
00327 break;
00328 case ETypeUint:
00329
00330
00331
00332
00333 if( iAttrNum == KCobainProtocolStackSize ) {
00334
00335 TNameRecord *record = iDeviceAddresses[iCurrentDeviceIndex];
00336 TBTDevAddr btaddr = static_cast<TBTSockAddr>(record->iAddr).BTAddr();
00337 TPeerData *data = new (ELeave) TPeerData();
00338 data->iDeviceName = record->iName;
00339 data->iDeviceAddress = btaddr.Des();
00340
00341
00342
00343 data->iPort = aValue.Uint();
00344
00345
00346
00347
00348 iPeerList->Append(data);
00349 iNumPeers++;
00350 } else {
00351
00352 }
00353 break;
00354 case ETypeDES:
00355
00356 break;
00357 case ETypeNil:
00358
00359 break;
00360 case ETypeInt:
00361
00362 break;
00363 case ETypeString:
00364
00365 break;
00366 case ETypeBoolean:
00367
00368 break;
00369 case ETypeDEA:
00370
00371 break;
00372 case ETypeURL:
00373
00374 break;
00375 case ETypeEncoded:
00376
00377 break;
00378 default:
00379
00380 break;
00381 }
00382 }
00383
00384 void CBTDiscoverer::StartListL(CSdpAttrValueList& )
00385 {
00386
00387 }
00388
00389 void CBTDiscoverer::EndListL()
00390 {
00391
00392 }
00393