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

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

Parent Directory Parent Directory | Revision Log Revision Log


Revision 2578 - (show annotations) (download)
Sun Apr 11 01:34:34 2004 UTC (15 years, 8 months ago) by jason
Original Path: main/sip/resiprocate/dum/Dialog.cxx
File size: 9361 byte(s)
*** empty log message ***

1 #include "resiprocate/Contents.hxx"
2 //#include "resiprocate/OctetContents.hxx"
3 //#include "resiprocate/HeaderFieldValueList.hxx"
4 #include "resiprocate/sam/Dialog.hxx"
5 #include "resiprocate/sam/ClientInviteSession.hxx"
6
7 using namespace resip;
8 using namespace std;
9
10 class ServerInviteSession;
11
12 Dialog::Dialog(DialogUsageManager& dum, const SipMessage& msg)
13 : mId(msg),
14 mDum(dum),
15 mLocalCSeq(0),
16 mRemoteCSeq(0),
17 mCallId(msg.header(h_CallID))
18 {
19 assert(msg.isFromWire());
20
21 if (msg.isRequest()) // UAS
22 {
23 const SipMessage& request = msg;
24 mRouteSet = request.header(h_RecordRoutes);
25
26 switch (request.header(h_CSeq).method())
27 {
28 case INVITE:
29 case SUBSRIBE:
30 if (request.exists(h_Contacts) && request.header(h_Contacts).size() == 1)
31 {
32 NameAddr& contact = request.header(h_Contacts).front();
33 if (isEqualNoCase(contact.uri().scheme(), Symbols::Sips) ||
34 isEqualNoCase(contact.uri().scheme(), Symbols::Sip))
35 {
36 mRemoteTarget = contact;
37 }
38 else
39 {
40 InfoLog (<< "Got an INVITE or SUBSCRIBE with invalid scheme");
41 DebugLog (<< request);
42 throw Exception("Invalid dialog", __FILE__, __LINE__);
43 }
44 }
45 else
46 {
47 InfoLog (<< "Got an INVITE or SUBSCRIBE that doesn't have exactly one contact");
48 DebugLog (<< request);
49 throw Exception("Invalid dialog", __FILE__, __LINE__);
50 }
51 break;
52 }
53
54 mRemoteCSeq = request.header(h_CSeq).sequence();
55 mLocalCSeq = 0;
56
57 if ( response.header(h_From).exists(p_tag) ) // 2543 compat
58 {
59 mRemoteTag = response.header(h_From).param(p_tag);
60 }
61 if ( response.header(h_To).exists(p_tag) ) // 2543 compat
62 {
63 mLocalTag = response.header(h_To).param(p_tag);
64 }
65 mMe = response.header(h_To);
66
67 //mDialogId = mCallId;
68 //mDialogId.param(p_toTag) = mLocalTag;
69 //mDialogId.param(p_fromTag) = mRemoteTag;
70 }
71 else if (msg.isResponse())
72 {
73 const SipMessage& response = msg;
74 if (response.exists(h_RecordRoutes))
75 {
76 mRouteSet = response.header(h_RecordRoutes).reverse();
77 }
78
79 switch (response.header(h_CSeq).method())
80 {
81 case INVITE:
82 case SUBSRIBE:
83 if (response.exists(h_Contacts) && response.header(h_Contacts).size() == 1)
84 {
85 NameAddr& contact = response.header(h_Contacts).front();
86 if (isEqualNoCase(contact.uri().scheme(), Symbols::Sips) ||
87 isEqualNoCase(contact.uri().scheme(), Symbols::Sip))
88 {
89 mRemoteTarget = contact;
90 }
91 else
92 {
93 InfoLog (<< "Got an INVITE or SUBSCRIBE with invalid scheme");
94 DebugLog (<< response);
95 throw Exception("Invalid dialog", __FILE__, __LINE__);
96 }
97 }
98 else
99 {
100 InfoLog (<< "Got an INVITE or SUBSCRIBE that doesn't have exactly one contact");
101 DebugLog (<< response);
102 throw Exception("Invalid dialog", __FILE__, __LINE__);
103 }
104 break;
105 }
106
107 mLocalCSeq = response.header(h_CSeq).sequence();
108
109 if ( response.header(h_From).exists(p_tag) ) // 2543 compat
110 {
111 mLocalTag = response.header(h_From).param(p_tag);
112 }
113 if ( response.header(h_To).exists(p_tag) ) // 2543 compat
114 {
115 mRemoteTag = response.header(h_To).param(p_tag);
116 }
117 mMe = response.header(h_From);
118
119 //mDialogId = mCallId;
120 //mDialogId.param(p_toTag) = mLocalTag;
121 //mDialogId.param(p_fromTag) = mRemoteTag;
122
123 BaseUsage* usage = mCreator->makeUsage(response);
124 assert(usage);
125 mUsages.push_back(usage);
126 }
127 }
128
129 void
130 Dialog::dispatch(const SipMessage& msg)
131 {
132 BaseUsage* usage = mCreator->makeUsage(response);
133 assert(usage);
134 mUsages.push_back(usage);
135 }
136
137 DialogId Dialog::getId() const
138 {
139 return mId;
140 }
141
142 BaseUsage&
143 Dialog::findInvSession()
144 {
145 std::list<BaseUsage*>::iterator it = mUsages.begin();
146 BaseUsage *usage;
147 while (it != mUsages.end())
148 {
149 usage = it->next();
150 if ((dynamic_cast<ClientInviteSession*>(usage) != NULL) ||
151 (dynamic_cast<ServerInviteSession*>(usage) != NULL))
152 {
153 return *usage;
154 }
155 }
156 return BaseUsage::empty();
157 }
158
159 UsageSet
160 Dialog::findSubscriptions()
161 {
162 std::list<BaseUsage*>::iterator it = mUsages.begin();
163 BaseUsage *usage;
164 UsageSet usageSet;
165 while (it != mUsages.end())
166 {
167 usage = it.next();
168 if ((dynamic_cast<ClientSubscription*>(usage) != null) ||
169 (dynamic_cast<ServerSubscription*>(usage) != null))
170 {
171 usageSet.push_back(*usage);
172 }
173 }
174 return usageSet:
175 }
176
177 BaseUsage&
178 Dialog::findRegistration()
179 {
180 std::list<BaseUsage*>::iterator it = mUsages.begin();
181 BaseUsage *usage;
182 while (it != mUsages.end())
183 {
184 usage = it.next();
185 if ((dynamic_cast<CientRegistration*>(usage) != null) ||
186 (dynamic_cast<ServerRegistration*>(usage) != null))
187 {
188 return *usage;
189 }
190 }
191 return BaseUsage::empty();
192 }
193
194
195 BaseUsage&
196 Dialog::findPublication()
197 {
198 std::list<BaseUsage*>::iterator it = mUsages.begin();
199 BaseUsage *usage;
200 while (it != mUsages.end())
201 {
202 usage = it.next();
203 if ((dynamic_cast<CientPublication*>(usage) != null) ||
204 (dynamic_cast<ServerPublication*>(usage) != null))
205 {
206 return *usage;
207 }
208 }
209 return BaseUsage::empty();
210 }
211
212 UsageSet
213 Dialog::findOutOfDialogs()
214 {
215 std::list<BaseUsage*>::iterator it = mUsages.begin();
216 BaseUsage *usage;
217 UsageSet usageSet;
218 while (it != mUsages.end())
219 {
220 usage = it.next();
221 if ((dynamic_cast<ClientOutOfDialogReq*>(usage) != null) ||
222 (dynamic_cast<ServerOutOfDialogReq*>(usage) != null))
223 {
224 usageSet.push_back(*usage);
225 }
226 }
227 return usageSet:
228 }
229
230 void
231 Dialog::dispatch(const SipMessage& msg)
232 {
233 if (msg.isRequest())
234 {
235 switch (request.header(h_RequestLine).getMethod())
236 {
237 // a NOTIFY is the only request that can
238 // create a full dialog (when the 2xx from the
239 // SUBSCRIBE arrives *after* the NOTIFY
240 case NOTIFY :
241 processNotify(msg);
242 break;
243
244 case REFER:
245 // !jf! wierdo
246 // affects an InvSession and a ServerSubscription
247 break;
248
249 case SUBSCRIBE:
250 processSubscribe(msg);
251 break;
252
253 case CANCEL:
254 // should only occur when canceling a re-INVITE
255 case INVITE:
256 // should only occur for a re-INVITE
257 case ACK:
258 case PRACK:
259 case BYE:
260 case UPDATE:
261 case INFO:
262 processInviteRelated(msg);
263 break;
264
265 case REGISTER:
266 {
267 assert(0); // already handled
268 break;
269 }
270
271 case PUBLISH:
272 assert(0);
273 break;
274
275 case MESSAGE:
276 case OPTIONS:
277 assert(0);
278 break;
279
280 default:
281 assert(0);
282 break;
283 }
284 }
285 else if (msg.isResponse())
286 {
287
288 }
289 else
290 {
291 assert(0);
292 }
293 }
294
295 void
296 Dialog::processNotify(const SipMessage& notify)
297 {
298 if (notify.isRequest())
299 {
300 if (findSubscriptions().empty())
301 {
302 SubscriptionCreator* creator = dynamic_cast<SubscriptionCreator*>(DialogSetId(notify).getCreator());
303 if (creator)
304 {
305 creator->makeNewSubscription(notify);
306 }
307 }
308 else
309 {
310 for (std::list<BaseUsage*>::iterator i=mUsages.begin(); i!=mUsages.end(); i++)
311 {
312 ClientSubscription* sub = dynamic_cast<ClientSubscription*>(*i);
313 if (sub && sub->matches(notify))
314 {
315 sub->process(notify);
316 break;
317 }
318 }
319 }
320 }
321 }
322
323 void
324 Dialog::processSubscribe(const SipMessage& subscribe)
325 {
326 for (std::list<BaseUsage*>::iterator i=mUsages.begin(); i!=mUsages.end(); i++)
327 {
328 ServerSubscription* sub = dynamic_cast<ServerSubscription*>(*i);
329 if (sub && sub->matches(subscribe))
330 {
331 sub->process(subscribe); // a resubscribe or unsubscribe
332 return;
333 }
334 }
335
336 // a subscribe on an existing dialog with a different BaseUsage
337 ServerSubscription* sub = new ServerSubscription(mDum, subscribe);
338 }
339
340 void
341 Dialog::processInviteRelated(const SipMessage& msg)
342 {
343 for (std::list<BaseUsage*>::iterator i=mUsages.begin(); i!=mUsages.end(); i++)
344 {
345 ServerInvSession* server = dynamic_cast<ServerInvSession*>(*i);
346 ClientInvSession* client = dynamic_cast<ClientInvSession*>(*i);
347 if (server)
348 {
349 server->process(msg);
350 break;
351 }
352 else if (client)
353 {
354 client->process(msg);
355 break;
356 }
357 }
358 }

webmaster AT resiprocate DOT org
ViewVC Help
Powered by ViewVC 1.1.27