/[resiprocate]/main/resip/dum/Dialog.cxx
ViewVC logotype

Annotation of /main/resip/dum/Dialog.cxx

Parent Directory Parent Directory | Revision Log Revision Log


Revision 3082 - (hide annotations) (download)
Fri Jul 9 01:23:36 2004 UTC (15 years, 5 months ago) by derek
Original Path: main/sip/resiprocate/dum/Dialog.cxx
File size: 28378 byte(s)
subscribe/notify fixes
1 davidb 2603 #include "resiprocate/Contents.hxx"
2 jason 2614 #include "resiprocate/Helper.hxx"
3 jason 2885 #include "resiprocate/SipMessage.hxx"
4 derek 2943 #include "resiprocate/dum/AppDialog.hxx"
5 jason 2885 #include "resiprocate/dum/BaseCreator.hxx"
6 derek 2991 #include "resiprocate/dum/ClientAuthManager.hxx"
7 jason 2941 #include "resiprocate/dum/ClientInviteSession.hxx"
8 jason 2885 #include "resiprocate/dum/ClientOutOfDialogReq.hxx"
9 jason 2941 #include "resiprocate/dum/ClientRegistration.hxx"
10     #include "resiprocate/dum/ClientSubscription.hxx"
11 jason 2885 #include "resiprocate/dum/Dialog.hxx"
12     #include "resiprocate/dum/DialogUsageManager.hxx"
13     #include "resiprocate/dum/InviteSessionCreator.hxx"
14 derek 3058 #include "resiprocate/dum/InviteSessionHandler.hxx"
15 jason 2941 #include "resiprocate/dum/ServerInviteSession.hxx"
16     #include "resiprocate/dum/ServerOutOfDialogReq.hxx"
17     #include "resiprocate/dum/ServerRegistration.hxx"
18     #include "resiprocate/dum/ServerSubscription.hxx"
19 derek 3082 #include "resiprocate/dum/SubscriptionHandler.hxx"
20 jason 2941 #include "resiprocate/dum/ClientPublication.hxx"
21     #include "resiprocate/dum/ServerPublication.hxx"
22 davidb 2603 #include "resiprocate/os/Logger.hxx"
23    
24     #define RESIPROCATE_SUBSYSTEM Subsystem::DUM
25    
26 ken 2520 using namespace resip;
27     using namespace std;
28    
29 derek 2867 Dialog::Dialog(DialogUsageManager& dum, const SipMessage& msg, DialogSet& ds)
30 derek 2995 : mDum(dum),
31 derek 2867 mDialogSet(ds),
32 jason 2588 mClientSubscriptions(),
33 derek 3041 mServerSubscriptions(),
34 jason 2588 mInviteSession(0),
35     mClientRegistration(0),
36     mServerRegistration(0),
37     mClientPublication(0),
38     mServerPublication(0),
39 jason 2614 mClientOutOfDialogRequests(),
40     mServerOutOfDialogRequest(0),
41 jason 2588 mType(Fake),
42     mRouteSet(),
43 jason 2611 mLocalContact(),
44 jason 2577 mLocalCSeq(0),
45     mRemoteCSeq(0),
46 derek 2995 mId("INVALID", "INVALID", "INVALID"),
47 derek 2981 mRemoteTarget(),
48 derek 2995 mLocalNameAddr(),
49     mRemoteNameAddr(),
50     mCallId(msg.header(h_CallID)),
51 derek 2981 mDestroying(false)
52 jason 2577 {
53 davidb 2603 assert(msg.isExternal());
54 jason 2577
55 derek 2936
56 jason 2577 if (msg.isRequest()) // UAS
57     {
58     const SipMessage& request = msg;
59    
60     switch (request.header(h_CSeq).method())
61     {
62     case INVITE:
63 jason 2611 mType = Invitation;
64     break;
65    
66 davidb 2603 case SUBSCRIBE:
67 jason 2611 case REFER:
68     case NOTIFY:
69 derek 3041 //!dcm! -- event header check
70 jason 2611 mType = Subscription;
71     break;
72    
73     default:
74     mType = Fake;
75     }
76 derek 3024 if (request.exists(h_RecordRoutes))
77     {
78     mRouteSet = request.header(h_RecordRoutes); // !jf! is this right order
79     }
80 jason 2611
81     switch (request.header(h_CSeq).method())
82     {
83     case INVITE:
84     case SUBSCRIBE:
85     case REFER:
86 derek 2995 InfoLog ( << "UAS dialog ID creation, DS: " << ds.getId());
87     mId = DialogId(ds.getId(), request.header(h_From).param(p_tag));
88     mRemoteNameAddr = request.header(h_From);
89     mLocalNameAddr = request.header(h_To);
90     mLocalNameAddr.param(p_tag) = mId.getLocalTag();
91 jason 2577 if (request.exists(h_Contacts) && request.header(h_Contacts).size() == 1)
92     {
93 davidb 2603 const NameAddr& contact = request.header(h_Contacts).front();
94 jason 2577 if (isEqualNoCase(contact.uri().scheme(), Symbols::Sips) ||
95     isEqualNoCase(contact.uri().scheme(), Symbols::Sip))
96     {
97 jason 2611 mLocalContact = NameAddr(request.header(h_RequestLine).uri()); // update later when send a request
98 jason 2577 mRemoteTarget = contact;
99     }
100     else
101     {
102 davidb 2603 InfoLog(<< "Got an INVITE or SUBSCRIBE with invalid scheme");
103     DebugLog(<< request);
104 jason 2611 throw Exception("Invalid scheme in request", __FILE__, __LINE__);
105 jason 2577 }
106     }
107     else
108     {
109     InfoLog (<< "Got an INVITE or SUBSCRIBE that doesn't have exactly one contact");
110     DebugLog (<< request);
111 jason 2611 throw Exception("Too many (or no contact) contacts in request", __FILE__, __LINE__);
112 jason 2577 }
113     break;
114 davidb 2603 default:
115     break;
116 jason 2577 }
117    
118     mRemoteCSeq = request.header(h_CSeq).sequence();
119 jason 2611 mLocalCSeq = 1;
120 derek 2995
121     InfoLog ( << "************** Created Dialog as UAS **************" );
122     InfoLog ( << "mRemoteNameAddr: " << mRemoteNameAddr );
123     InfoLog ( << "mLocalNameAddr: " << mLocalNameAddr );
124     InfoLog ( << "mLocalContact: " << mLocalContact );
125     InfoLog ( << "mRemoteTarget: " << mRemoteTarget );
126 jason 2577 }
127     else if (msg.isResponse())
128     {
129 derek 2995 mId = DialogId(msg);
130 jason 2577 const SipMessage& response = msg;
131 derek 2995 mRemoteNameAddr = response.header(h_To);
132     mLocalNameAddr = response.header(h_From);
133 jason 2611
134     switch (msg.header(h_CSeq).method())
135     {
136     case INVITE:
137     mType = Invitation;
138     break;
139    
140     case SUBSCRIBE:
141     case REFER:
142     mType = Subscription;
143     break;
144    
145     default:
146     mType = Fake;
147     }
148    
149 jason 2577 if (response.exists(h_RecordRoutes))
150     {
151     mRouteSet = response.header(h_RecordRoutes).reverse();
152     }
153    
154     switch (response.header(h_CSeq).method())
155     {
156     case INVITE:
157 davidb 2603 case SUBSCRIBE:
158 jason 2611 case REFER:
159 derek 2983 if (response.header(h_StatusLine).statusCode() > 100 &&
160     response.header(h_StatusLine).statusCode() < 300)
161 jason 2577 {
162 derek 2983
163     if (response.exists(h_Contacts) && response.header(h_Contacts).size() == 1)
164 jason 2577 {
165 derek 2983 const NameAddr& contact = response.header(h_Contacts).front();
166     if (isEqualNoCase(contact.uri().scheme(), Symbols::Sips) ||
167     isEqualNoCase(contact.uri().scheme(), Symbols::Sip))
168     {
169     BaseCreator* creator = mDum.findCreator(mId);
170     assert(creator);// !jf! throw or something here
171 jason 2612
172 derek 2983 mLocalContact = creator->getLastRequest().header(h_Contacts).front();
173     mRemoteTarget = contact;
174     }
175     else
176     {
177     InfoLog (<< "Got an INVITE or SUBSCRIBE with invalid scheme");
178     DebugLog (<< response);
179     throw Exception("Bad scheme in contact in response", __FILE__, __LINE__);
180     }
181 jason 2577 }
182     else
183     {
184 derek 2983 InfoLog (<< "Got an INVITE or SUBSCRIBE that doesn't have exactly one contact");
185 jason 2577 DebugLog (<< response);
186 derek 2983 throw Exception("Too many contacts (or no contact) in response", __FILE__, __LINE__);
187 jason 2577 }
188 derek 2983 break;
189     default:
190     break;
191 jason 2577 }
192     }
193 derek 2983
194 jason 2577 mLocalCSeq = response.header(h_CSeq).sequence();
195 jason 2611 mRemoteCSeq = 0;
196 derek 2995 InfoLog ( << "************** Created Dialog as UAC **************" );
197     InfoLog ( << "mRemoteNameAddr: " << mRemoteNameAddr );
198     InfoLog ( << "mLocalNameAddr: " << mLocalNameAddr );
199     InfoLog ( << "mLocalContact: " << mLocalContact );
200     InfoLog ( << "mRemoteTarget: " << mRemoteTarget );
201    
202 jason 2611
203 jason 2577 }
204 derek 2867 mDialogSet.addDialog(this);
205 derek 3081 DebugLog ( <<"Dialog::Dialog " << mId);
206 jason 2577 }
207    
208 jason 2868 Dialog::~Dialog()
209     {
210 derek 3081 DebugLog ( <<"Dialog::~Dialog() ");
211    
212 derek 2981 mDestroying = true;
213     //does removing an elemnt from a list invalidate iterators?
214     for(std::list<ClientSubscription*>::iterator it = mClientSubscriptions.begin();
215     it != mClientSubscriptions.end(); it++)
216     {
217     delete *it;
218     }
219 derek 3041 for(std::list<ServerSubscription*>::iterator it = mServerSubscriptions.begin();
220     it != mServerSubscriptions.end(); it++)
221     {
222     delete *it;
223     }
224 derek 2981 for(std::list<ClientOutOfDialogReq*>::iterator it = mClientOutOfDialogRequests.begin();
225     it != mClientOutOfDialogRequests.end(); it++)
226     {
227     delete *it;
228     }
229     delete mInviteSession;
230     delete mClientRegistration;
231     delete mServerRegistration;
232     delete mClientPublication;
233     delete mServerPublication;
234     delete mServerOutOfDialogRequest;
235    
236 jason 2884 mDialogSet.mDialogs.erase(this->getId());
237 derek 2976 delete mAppDialog;
238     mDialogSet.possiblyDie();
239 jason 2868 }
240    
241 jason 2588 DialogId
242     Dialog::getId() const
243     {
244     return mId;
245     }
246    
247 davidb 2604 void
248 jason 2891 Dialog::cancel()
249     {
250 derek 3006 if (mInviteSession)
251     {
252     mInviteSession->end();
253     }
254     else
255     {
256     if (mDialogSet.getCreator())
257     {
258     makeRequest(mDialogSet.getCreator()->getLastRequest(), CANCEL);
259     mDum.send(mDialogSet.getCreator()->getLastRequest());
260     delete this;
261     }
262     }
263 jason 2891 }
264    
265     void
266 davidb 2604 Dialog::dispatch(const SipMessage& msg)
267     {
268 derek 2990 InfoLog ( << "Dialog::dispatch: " << msg.brief());
269 jason 2614 if (msg.isRequest())
270 jason 2583 {
271 jason 2614 const SipMessage& request = msg;
272     switch (request.header(h_CSeq).method())
273 jason 2583 {
274 jason 2614 case INVITE: // new INVITE
275     if (mInviteSession == 0)
276     {
277 derek 2992 InfoLog ( << "Dialog::dispatch -- Created new server invite session" << msg.brief());
278 jason 2885 mInviteSession = makeServerInviteSession(request);
279 jason 2614 }
280     mInviteSession->dispatch(request);
281     break;
282 derek 2997 case BYE:
283     if (mInviteSession == 0)
284     {
285     InfoLog ( << "Spurious BYE" );
286     return;
287     }
288     else
289     {
290     mInviteSession->dispatch(request);
291     }
292     break;
293 jason 2614 case ACK:
294     case CANCEL:
295     if (mInviteSession == 0)
296     {
297     InfoLog (<< "Drop stray ACK or CANCEL in dialog on the floor");
298     DebugLog (<< request);
299     }
300     else
301     {
302     mInviteSession->dispatch(request);
303     }
304     break;
305    
306     case SUBSCRIBE:
307     case REFER: //!jf! does this create a server subs?
308 derek 3041 {
309     ServerSubscription* server = findMatchingServerSub(request);
310     if (server)
311 jason 2614 {
312 derek 3041 server->dispatch(request);
313 jason 2614 }
314 derek 3041 else
315     {
316     server = makeServerSubscription(request);
317     mServerSubscriptions.push_back(server);
318     server->dispatch(request);
319     }
320     }
321     break;
322 jason 2614 case NOTIFY:
323     if (request.header(h_To).exists(p_tag))
324     {
325     ClientSubscription* client = findMatchingClientSub(request);
326     if (client)
327 jason 2612 {
328 jason 2614 client->dispatch(request);
329 jason 2612 }
330     else
331     {
332 jason 2614 BaseCreator* creator = mDum.findCreator(mId);
333     if (creator)
334 jason 2612 {
335 jason 2885 ClientSubscription* sub = makeClientSubscription(request);
336 jason 2614 mClientSubscriptions.push_back(sub);
337     sub->dispatch(request);
338 jason 2612 }
339     else
340     {
341 jason 2887 SipMessage failure;
342     makeResponse(failure, request, 481);
343     mDum.sendResponse(failure);
344 jason 2614 return;
345 jason 2612 }
346     }
347 jason 2614 }
348     else // no to tag - unsolicited notify
349     {
350     assert(mServerOutOfDialogRequest == 0);
351 jason 2885 mServerOutOfDialogRequest = makeServerOutOfDialog(request);
352 jason 2614 mServerOutOfDialogRequest->dispatch(request);
353     }
354     break;
355 jason 2583
356 jason 2614 case PUBLISH:
357     if (mServerPublication == 0)
358     {
359 jason 2885 mServerPublication = makeServerPublication(request);
360 jason 2614 }
361     mServerPublication->dispatch(request);
362     break;
363 jason 2612
364 jason 2614 case REGISTER:
365     if (mServerRegistration == 0)
366     {
367 jason 2885 mServerRegistration = makeServerRegistration(request);
368 jason 2614 }
369     mServerRegistration->dispatch(request);
370     break;
371 jason 2584
372 jason 2614 default:
373 derek 2997 InfoLog ( << "In Dialog::dispatch, default(ServerOutOfDialogRequest), msg: " << msg );
374 jason 2614 // only can be one ServerOutOfDialogReq at a time
375     assert(mServerOutOfDialogRequest == 0);
376 jason 2885 mServerOutOfDialogRequest = makeServerOutOfDialog(request);
377 jason 2614 mServerOutOfDialogRequest->dispatch(request);
378     break;
379 jason 2583 }
380 jason 2614 }
381     else if (msg.isResponse())
382     {
383 derek 3026 #if 0
384 derek 3058 // //Auth related
385     // if (mDum.mClientAuthManager && !mDialogSet.mCancelled)
386     // {
387     // if (mDialogSet.getCreator())
388     // {
389     // if ( mDum.mClientAuthManager->handle( mDialogSet.getCreator()->getLastRequest(), msg))
390     // {
391     // InfoLog( << "about to retransmit request with digest credentials" );
392     // InfoLog( << mDialogSet.getCreator()->getLastRequest() );
393 derek 2991
394 derek 3058 // mDum.send(mDialogSet.getCreator()->getLastRequest());
395     // return;
396     // }
397     // }
398     // else
399     // {
400     // SipMessage* lastRequest = 0;
401     // switch (msg.header(h_CSeq).method())
402     // {
403     // case INVITE:
404     // case CANCEL:
405     // case REFER:
406     // if (mInviteSession == 0)
407     // {
408     // return;
409     // }
410     // else
411     // {
412     // lastRequest = &mInviteSession->mLastRequest;
413     // }
414     // break;
415     // case REGISTER:
416     // if (mClientRegistration == 0)
417     // {
418     // return;
419     // }
420     // else
421     // {
422     // lastRequest = &mClientRegistration->mLastRequest;
423     // }
424     // break;
425     // default:
426     // break;
427     // }
428     // if ( lastRequest && mDum.mClientAuthManager->handle( *lastRequest, msg ) )
429     // {
430     // InfoLog( << "about to retransmit request with digest credentials" );
431     // InfoLog( << *lastRequest );
432 derek 2991
433 derek 3058 // mDum.send(*lastRequest);
434     // return;
435     // }
436     // }
437     // }
438 derek 3026 #endif
439 jason 2614 const SipMessage& response = msg;
440 jason 2885 // !jf! should this only be for 2xx responses? !jf! Propose no as an
441     // answer !dcm! what is he on?
442 jason 2614 switch (response.header(h_CSeq).method())
443 jason 2583 {
444 jason 2614 case INVITE:
445     if (mInviteSession == 0)
446     {
447 jason 2885 // #if!jf! don't think creator needs a dispatch
448     //BaseCreator* creator = mDum.findCreator(mId);
449     //assert (creator); // stray responses have been rejected already
450     //creator->dispatch(response);
451     // #endif!jf!
452 derek 2992 InfoLog ( << "Dialog::dispatch -- Created new client invite session" << msg.brief());
453    
454 jason 2885 mInviteSession = makeClientInviteSession(response);
455     mInviteSession->dispatch(response);
456 jason 2614 }
457     else
458     {
459     mInviteSession->dispatch(response);
460     }
461     break;
462 derek 2997 case BYE:
463 jason 2614 case ACK:
464     case CANCEL:
465     if (mInviteSession != 0)
466     {
467     mInviteSession->dispatch(response);
468     }
469     // else drop on the floor
470 derek 3058 break;
471 jason 2614 case REFER:
472     {
473 derek 3058 int code = response.header(h_StatusLine).statusCode();
474     if (code < 300)
475 jason 2612 {
476 derek 3058 // throw it away
477     return;
478     }
479 jason 2614 else
480     {
481 derek 3058 if (mInviteSession && mDum.mInviteSessionHandler)
482     {
483     mDum.mInviteSessionHandler->onReferRejected(mInviteSession->getSessionHandle(), response);
484     }
485     }
486     }
487     break;
488     case SUBSCRIBE:
489     {
490     int code = response.header(h_StatusLine).statusCode();
491     if (code < 300)
492     {
493     // throw it away
494     return;
495     }
496     else
497     {
498     ClientSubscription* client = findMatchingClientSub(response);
499     if (client)
500     {
501     client->dispatch(response);
502     }
503 derek 3082 else
504     {
505     //!dcm! -- can't subscribe in an existing Dialog, this is all
506     //a bit of a hack.
507     BaseCreator* creator = mDialogSet.getCreator();
508     assert(creator);
509     assert(creator->getLastRequest().exists(h_Event));
510     ClientSubscriptionHandler* handler =
511     mDum.getClientSubscriptionHandler(creator->getLastRequest().header(h_Event).value());
512     assert(handler);
513     handler->onTerminated(ClientSubscriptionHandle::NotValid(), response);
514     possiblyDie();
515     }
516 jason 2614 }
517     }
518 derek 3058 break;
519 jason 2614 case PUBLISH:
520 jason 2887 // !jf! could assert that no other usages exist
521 jason 2614 if (mClientPublication == 0)
522     {
523 jason 2885 mClientPublication = makeClientPublication(response);
524 jason 2614 }
525     mClientPublication->dispatch(response);
526     break;
527 jason 2584
528 jason 2614 case REGISTER:
529 jason 2887 // !jf! could assert that no other usages exist
530 jason 2614 if (mClientRegistration == 0)
531     {
532 jason 2885 mClientRegistration = makeClientRegistration(response);
533 jason 2614 }
534     mClientRegistration->dispatch(response);
535     break;
536 jason 2584
537 jason 2614 // unsolicited - not allowed but commonly implemented
538     // by large companies with a bridge as their logo
539     case NOTIFY:
540     case INFO:
541 jason 2612
542 jason 2614 default:
543     {
544     ClientOutOfDialogReq* req = findMatchingClientOutOfDialogReq(response);
545     if (req == 0)
546 jason 2612 {
547 jason 2885 req = makeClientOutOfDialogReq(response);
548 jason 2614 mClientOutOfDialogRequests.push_back(req);
549     }
550     req->dispatch(response);
551     break;
552 jason 2584 }
553 jason 2583 }
554     }
555 jason 2578 }
556    
557 derek 3041 ServerSubscription*
558     Dialog::findMatchingServerSub(const SipMessage& msg)
559     {
560     for (std::list<ServerSubscription*>::iterator i=mServerSubscriptions.begin();
561     i != mServerSubscriptions.end(); ++i)
562     {
563     if ((*i)->matches(msg))
564     {
565     return *i;
566     }
567     }
568     return 0;
569     }
570 jason 2612
571     ClientSubscription*
572     Dialog::findMatchingClientSub(const SipMessage& msg)
573 jason 2583 {
574 derek 2858 for (std::list<ClientSubscription*>::iterator i=mClientSubscriptions.begin();
575 jason 2612 i != mClientSubscriptions.end(); ++i)
576 jason 2583 {
577 jason 2614 if ((*i)->matches(msg))
578 jason 2612 {
579 jason 2614 return *i;
580 jason 2612 }
581     }
582 jason 2614 return 0;
583 jason 2612 }
584 jason 2585
585 jason 2614 ClientOutOfDialogReq*
586 jason 2612 Dialog::findMatchingClientOutOfDialogReq(const SipMessage& msg)
587     {
588 derek 2858 for (std::list<ClientOutOfDialogReq*>::iterator i=mClientOutOfDialogRequests.begin();
589 jason 2612 i != mClientOutOfDialogRequests.end(); ++i)
590     {
591 jason 2614 if ((*i)->matches(msg))
592 jason 2612 {
593 jason 2614 return *i;
594 jason 2612 }
595 jason 2583 }
596 jason 2614 return 0;
597 jason 2583 }
598    
599 jason 2612
600 jason 2941 InviteSessionHandle
601 derek 3041 Dialog::getInviteSession()
602 ken 2520 {
603 davidb 2603 if (mInviteSession)
604     {
605     return mInviteSession->getSessionHandle();
606     }
607     else
608     {
609 derek 3041 return InviteSessionHandle::NotValid();
610 davidb 2603 }
611 ken 2520 }
612    
613 jason 2941 std::vector<ClientSubscriptionHandle>
614 derek 3041 Dialog::findClientSubscriptions(const Data& event)
615 ken 2520 {
616 jason 2941 std::vector<ClientSubscriptionHandle> handles;
617 davidb 2603
618 derek 2858 for (std::list<ClientSubscription*>::const_iterator i = mClientSubscriptions.begin();
619 davidb 2603 i != mClientSubscriptions.end(); ++i)
620     {
621 derek 3041 if ( (*i)->getEventType() == event)
622     {
623     handles.push_back((*i)->getHandle());
624     }
625     }
626     return handles;
627     }
628    
629     std::vector<ServerSubscriptionHandle>
630     Dialog::findServerSubscriptions(const Data& event)
631     {
632     std::vector<ServerSubscriptionHandle> handles;
633    
634     for (std::list<ServerSubscription*>::const_iterator i = mServerSubscriptions.begin();
635     i != mServerSubscriptions.end(); ++i)
636     {
637     if ( (*i)->getEventType() == event)
638     {
639     handles.push_back((*i)->getHandle());
640     }
641     }
642     return handles;
643     }
644    
645    
646     std::vector<ClientSubscriptionHandle>
647     Dialog::getClientSubscriptions()
648     {
649     std::vector<ClientSubscriptionHandle> handles;
650    
651     for (std::list<ClientSubscription*>::const_iterator i = mClientSubscriptions.begin();
652     i != mClientSubscriptions.end(); ++i)
653     {
654 davidb 2603 handles.push_back((*i)->getHandle());
655     }
656    
657     return handles;
658 ken 2520 }
659    
660 derek 3041 std::vector<ServerSubscriptionHandle>
661     Dialog::getServerSubscriptions()
662     {
663     std::vector<ServerSubscriptionHandle> handles;
664    
665     for (std::list<ServerSubscription*>::const_iterator i = mServerSubscriptions.begin();
666     i != mServerSubscriptions.end(); ++i)
667     {
668     handles.push_back((*i)->getHandle());
669     }
670    
671     return handles;
672     }
673    
674 jason 2941 ClientRegistrationHandle
675 derek 3041 Dialog::getClientRegistration()
676 ken 2520 {
677 davidb 2603 if (mClientRegistration)
678     {
679     return mClientRegistration->getHandle();
680     }
681     else
682     {
683 derek 3041 return ClientRegistrationHandle::NotValid();
684 davidb 2603 }
685 ken 2520 }
686    
687 jason 2941 ServerRegistrationHandle
688 derek 3041 Dialog::getServerRegistration()
689 ken 2520 {
690 davidb 2603 if (mServerRegistration)
691     {
692     return mServerRegistration->getHandle();
693     }
694     else
695     {
696 derek 3041 return ServerRegistrationHandle::NotValid();
697 davidb 2603 }
698 ken 2520 }
699    
700 jason 2941 ClientPublicationHandle
701 derek 3041 Dialog::getClientPublication()
702 davidb 2604 {
703     if (mClientPublication)
704     {
705     return mClientPublication->getHandle();
706     }
707     else
708     {
709 derek 3041 return ClientPublicationHandle::NotValid();
710 davidb 2604 }
711     }
712 ken 2520
713 jason 2941 ServerPublicationHandle
714 derek 3041 Dialog::getServerPublication()
715 ken 2520 {
716 davidb 2604 if (mServerPublication)
717     {
718     return mServerPublication->getHandle();
719     }
720     else
721     {
722 derek 3041 return ServerPublicationHandle::NotValid();
723 davidb 2604 }
724 ken 2520 }
725 jason 2535
726 jason 2614 #if 0
727 jason 2941 ClientOutOfDialogReqHandle
728 davidb 2604 Dialog::findClientOutOfDialog()
729 jason 2539 {
730 jason 2614 if (mClientOutOfDialogRequests)
731 jason 2539 {
732 davidb 2604 return mClientOutOfDialogReq->getHandle();
733 jason 2577 }
734 davidb 2604 else
735 jason 2577 {
736 davidb 2604 throw BaseUsage::Exception("no such client out of dialog",
737     __FILE__, __LINE__);
738 jason 2577 }
739 davidb 2604 }
740 jason 2614 #endif
741 davidb 2604
742 jason 2941 ServerOutOfDialogReqHandle
743 derek 3041 Dialog::getServerOutOfDialog()
744 davidb 2604 {
745 jason 2614 if (mServerOutOfDialogRequest)
746 davidb 2604 {
747 jason 2614 return mServerOutOfDialogRequest->getHandle();
748 davidb 2604 }
749 jason 2577 else
750     {
751 derek 3041 return ServerOutOfDialogReqHandle::NotValid();
752 jason 2577 }
753 jason 2539 }
754    
755 davidb 2604 #if 0
756 jason 2539 void
757 jason 2535 Dialog::processNotify(const SipMessage& notify)
758     {
759     if (notify.isRequest())
760     {
761     if (findSubscriptions().empty())
762     {
763     SubscriptionCreator* creator = dynamic_cast<SubscriptionCreator*>(DialogSetId(notify).getCreator());
764     if (creator)
765     {
766     creator->makeNewSubscription(notify);
767     }
768     }
769     else
770     {
771     for (std::list<BaseUsage*>::iterator i=mUsages.begin(); i!=mUsages.end(); i++)
772     {
773     ClientSubscription* sub = dynamic_cast<ClientSubscription*>(*i);
774     if (sub && sub->matches(notify))
775     {
776     sub->process(notify);
777     break;
778     }
779     }
780     }
781     }
782     }
783 jason 2612 #endif
784 jason 2539
785    
786 derek 2813 void
787     Dialog::makeRequest(SipMessage& request, MethodTypes method)
788     {
789     RequestLine rLine(method);
790    
791 derek 2817 rLine.uri() = mRemoteTarget.uri();
792 derek 2813
793     request.header(h_RequestLine) = rLine;
794 derek 2995 request.header(h_To) = mRemoteNameAddr;
795     // request.header(h_To).param(p_tag) = mId.getRemoteTag();
796     request.header(h_From) = mLocalNameAddr;
797     // request.header(h_From).param(p_tag) = mId.getLocalTag();
798 derek 2813
799     request.header(h_CallId) = mCallId;
800 derek 2997
801     request.remove(h_RecordRoutes); //!dcm! -- all of this is rather messy
802    
803 derek 2995 request.remove(h_Contacts);
804     request.header(h_Contacts).push_front(mLocalContact);
805 derek 2813 request.header(h_CSeq).method() = method;
806     request.header(h_MaxForwards).value() = 70;
807    
808 derek 2961 //must keep old via for cancel
809     if (method != CANCEL)
810     {
811 derek 3024 request.header(h_Routes) = mRouteSet;
812 derek 2992 request.remove(h_Vias);
813 derek 2961 Via via;
814     via.param(p_branch); // will create the branch
815     request.header(h_Vias).push_front(via);
816     }
817     else
818     {
819     assert(request.exists(h_Vias));
820     }
821 derek 3024 //don't increment CSeq for ACK or CANCEL
822     if (method != ACK && method != CANCEL)
823 derek 2965 {
824     request.header(h_CSeq).sequence() = ++mLocalCSeq;
825     }
826 derek 2995 InfoLog ( << "Dialog::makeRequest: " << request );
827 derek 2813 }
828    
829 derek 2961 void
830     Dialog::makeCancel(SipMessage& request)
831     {
832     makeRequest(request, CANCEL);
833 derek 2813
834 derek 2961 //not allowed in a CANCEL
835     request.remove(h_Requires);
836     request.remove(h_ProxyRequires);
837 derek 3058 request.header(h_To).remove(p_tag);
838 derek 2961 }
839    
840 derek 2813 void
841 jason 2887 Dialog::makeResponse(SipMessage& response, const SipMessage& request, int code)
842 derek 2813 {
843     assert( code >= 100 );
844 derek 2992 if (code < 300 && code > 100)
845 derek 2813 {
846     assert(request.isRequest());
847     assert(request.header(h_RequestLine).getMethod() == INVITE ||
848 derek 2997 request.header(h_RequestLine).getMethod() == SUBSCRIBE ||
849 derek 3024 request.header(h_RequestLine).getMethod() == BYE ||
850 derek 3082 request.header(h_RequestLine).getMethod() == CANCEL ||
851     request.header(h_RequestLine).getMethod() == NOTIFY
852     );
853 derek 2813
854 sgodin 3068 assert (request.header(h_RequestLine).getMethod() == CANCEL || // Contact header is not required for Requests that do not form a dialog
855     request.header(h_RequestLine).getMethod() == BYE ||
856     request.header(h_Contacts).size() == 1);
857 derek 2992 Helper::makeResponse(response, request, code, mLocalContact);
858 derek 2936 response.header(h_To).param(p_tag) = mId.getLocalTag();
859 derek 2813 }
860     else
861     {
862 derek 2817 Helper::makeResponse(response, request, code, mLocalContact);
863 derek 3006 response.header(h_To).param(p_tag) = mId.getLocalTag();
864    
865 derek 2813 }
866 derek 2992 InfoLog ( << "Dialog::makeResponse: " << response);
867 derek 2813 }
868    
869 jason 2885
870     ClientInviteSession*
871     Dialog::makeClientInviteSession(const SipMessage& response)
872     {
873     InviteSessionCreator* creator = dynamic_cast<InviteSessionCreator*>(mDialogSet.getCreator());
874     assert(creator); // !jf! this maybe can assert by evil UAS
875 jason 2941 //return mDum.createAppClientInviteSession(*this, *creator);
876     return new ClientInviteSession(mDum, *this, creator->getLastRequest(), creator->getInitialOffer());
877 jason 2885 }
878    
879     ClientRegistration*
880     Dialog::makeClientRegistration(const SipMessage& response)
881     {
882     BaseCreator* creator = mDialogSet.getCreator();
883     assert(creator);
884 jason 2941 return new ClientRegistration(mDum, *this, creator->getLastRequest());
885 jason 2885 }
886    
887     ClientPublication*
888     Dialog::makeClientPublication(const SipMessage& response)
889     {
890     BaseCreator* creator = mDialogSet.getCreator();
891     assert(creator);
892 jason 2941 return new ClientPublication(mDum, *this, creator->getLastRequest());
893 jason 2885 }
894    
895     ClientSubscription*
896 derek 3058 Dialog::makeClientSubscription(const SipMessage& request)
897 jason 2885 {
898 derek 3058 return new ClientSubscription(mDum, *this, request);
899 jason 2885 }
900    
901     ClientOutOfDialogReq*
902     Dialog::makeClientOutOfDialogReq(const SipMessage& response)
903     {
904     BaseCreator* creator = mDialogSet.getCreator();
905     assert(creator);
906 jason 2941 return new ClientOutOfDialogReq(mDum, *this, creator->getLastRequest());
907 jason 2885 }
908    
909     ServerInviteSession*
910     Dialog::makeServerInviteSession(const SipMessage& request)
911     {
912 jason 2941 return new ServerInviteSession(mDum, *this, request);
913 jason 2885 }
914    
915     ServerSubscription*
916     Dialog::makeServerSubscription(const SipMessage& request)
917     {
918 jason 2941 return new ServerSubscription(mDum, *this, request);
919 jason 2885 }
920    
921     ServerRegistration*
922     Dialog::makeServerRegistration(const SipMessage& request)
923     {
924 jason 2941 return new ServerRegistration(mDum, *this, request);
925 jason 2885 }
926    
927     ServerPublication*
928     Dialog::makeServerPublication(const SipMessage& request)
929     {
930 jason 2941 return new ServerPublication(mDum, *this, request);
931 jason 2885 }
932    
933     ServerOutOfDialogReq*
934     Dialog::makeServerOutOfDialog(const SipMessage& request)
935     {
936 jason 2941 return new ServerOutOfDialogReq(mDum, *this, request);
937 jason 2885 }
938    
939 davidb 2603 Dialog::Exception::Exception(const Data& msg, const Data& file, int line)
940     : BaseException(msg, file, line)
941 jason 2885 {
942     }
943 davidb 2603
944 jason 2853 void
945     Dialog::update(const SipMessage& msg)
946     {
947     }
948    
949     #if 0
950 derek 2839 void
951     Dialog::setLocalContact(const NameAddr& localContact)
952     {
953     mLocalContact = localContact;
954     }
955    
956     void
957     Dialog::setRemoteTarget(const NameAddr& remoteTarget)
958     {
959     mRemoteTarget = remoteTarget;
960     }
961 jason 2853 #endif
962 derek 2839
963 derek 2858 void Dialog::possiblyDie()
964     {
965 derek 2981 if (!mDestroying)
966 derek 2858 {
967 derek 2981 if (mClientSubscriptions.empty() &&
968 derek 3041 mServerSubscriptions.empty() &&
969 derek 2981 mClientOutOfDialogRequests.empty() &&
970 derek 3041 !(mInviteSession ||
971 derek 2981 mClientRegistration ||
972     mServerRegistration ||
973     mClientPublication ||
974     mServerPublication ||
975     mServerOutOfDialogRequest))
976     {
977     delete this;
978     }
979     }
980 derek 2858 }
981 derek 2862
982 jason 2884 ostream&
983     resip::operator<<(ostream& strm, const Dialog& dialog)
984     {
985    
986     return strm;
987     }
988    

webmaster AT resiprocate DOT org
ViewVC Help
Powered by ViewVC 1.1.27