Hi!
I have not followed the whole discussion. I just had an idea which might be useful: Why not hook up dialog module with tm module? Tm module already knows the state of forked INVITE transaction, which ones are in early states, and which branch is the winner.
regards klaus
Am 15.03.2010 14:00, schrieb Iñaki Baz Castillo:
2010/3/12 Timo Reimanntimo.reimann@1und1.de:
If so, my major concern with this approach is that it will break dialog callback functionality. If a dialog user, upon creation of an unconfirmed dialog (initial request received), registers for further callbacks associated with that dialog (for instance, DLGCB_CONFIRMED), it won't get any further callbacks in the scenario outlined above. The reason for this is that when the dialog is terminated due to the 5xx response, all associated callbacks will be swept out too, and the re-created dialog's structure will not contain any callbacks yet.
A suggestion to cover all the cases:
There could be two kinds of dialog entries in the module:
- dialog-in: It's a *single* dialog entry generated upon receipt of
the INVITE. No info about To-tag is stored with it. It has a status field (none, early, confirmed, terminated), but this status is handled carefully (see below). This entry exists until the dialog or early-dialog is terminated. Callbacks are inserted *here*.
- dialog-out: It's a single or multiple entries pointing to a single
dialog-in entry. It contains a To-tag and status fields. A dialog-out is generated when a response for same Call-ID and From-tag is received and contains a new To-tag. Status for each dialog-out is updated according to the status of the response (early, confirmed, terminated). No callbacks are inserted here.
When a dialog-out is generated (provisional response received) it updates the dialog-in status to "early" (so callback is raised), but just in case the dialog-in status was "none".
When a dialog-out receives a (200 it also updates the dialog-in status to "confirmed" (so callback is raised), just in case it was in "none" or "early" status.
When a dialog-out is terminated ([3456]XX response received) it *just* updates the dialog-in status to "terminated" in case there are no more alive dialog-outs (for parallel forking cases) and *also* in case the INVITE transaction has terminated (for serial forking cases in which still there is no new branches).
I think that with this approach all the cases are covered. Opinions?
2010/3/17 Klaus Darilion klaus.mailinglists@pernau.at:
Hi!
I have not followed the whole discussion. I just had an idea which might be useful: Why not hook up dialog module with tm module? Tm module already knows the state of forked INVITE transaction, which ones are in early states, and which branch is the winner.
This is not valid for the case in which a dialog is forked by a proxy behind our proxy. From the point of view of TM it's a single transaction.
Hi
2010/3/17 Klaus Darilion klaus.mailinglists@pernau.at:
Hi!
I have not followed the whole discussion. I just had an idea which might be useful: Why not hook up dialog module with tm module? Tm module already knows the state of forked INVITE transaction, which
ones are
in early states, and which branch is the winner.
This is not valid for the case in which a dialog is forked by a proxy behind our proxy. From the point of view of TM it's a single transaction.
In tm/dlg.c there is:
new_dlg_uac/new_dlg_uas
The dialog-in/dialog-out model seems to be similar to this b2b uac/uas?
Any one can explain the difference between tm/dlg and dialog module, and in which case should they be used?
Kind Regards
Min Wang
-- Iñaki Baz Castillo ibc@aliax.net
sr-dev mailing list sr-dev@lists.sip-router.org http://lists.sip-router.org/cgi-bin/mailman/listinfo/sr-dev
No virus found in this incoming message. Checked by AVG - www.avg.com Version: 9.0.790 / Virus Database: 271.1.1/2752 - Release Date: 03/17/10 03:33:00
Am 17.03.2010 13:44, schrieb Iñaki Baz Castillo:
2010/3/17 Klaus Darilionklaus.mailinglists@pernau.at:
Hi!
I have not followed the whole discussion. I just had an idea which might be useful: Why not hook up dialog module with tm module? Tm module already knows the state of forked INVITE transaction, which ones are in early states, and which branch is the winner.
This is not valid for the case in which a dialog is forked by a proxy behind our proxy. From the point of view of TM it's a single transaction.
That's true. It probably depends on what you actually want to track with the dialog module. E.g. if you just want to track the number of established dialogs then you do not care about multiple early dialogs.
Btw: how are dialogs in dialog module and transactions in tm module are exactly identified? For example a response with proper callid and fromtag but faked Via branch, will it be accepted by dialog module but ignored (drop or stateless forwarding) by tm?
Or the other way round - e.g. a spoofed 200 reply with proper Via branchid and false fromtag. Will it terminate the transaction but keep the dialog in early state (RFC 3261 says transaction matching does not care about callid/tags)? Then the real 200 OK will be forwarded stateless by tm module and may bypass dialog module (if callback is only triggered is there is a matching transaction)?
Note: This is just speculation as I do not know details about callbacks and dialog/transaction matching.
regards klaus
2010/3/17 Klaus Darilion klaus.mailinglists@pernau.at:
This is not valid for the case in which a dialog is forked by a proxy behind our proxy. From the point of view of TM it's a single transaction.
That's true. It probably depends on what you actually want to track with the dialog module. E.g. if you just want to track the number of established dialogs then you do not care about multiple early dialogs.
But it's also true that more and more modules want to depend on dialog module (take a look to OpenSIPS loadbalancer or mediaproxy modules). And they fail when handling forking calls.
Btw: how are dialogs in dialog module and transactions in tm module are exactly identified? For example a response with proper callid and fromtag but faked Via branch, will it be accepted by dialog module but ignored (drop or stateless forwarding) by tm?
Good question. IMHO it should be discarded as TM and dialog level (and not relayed stateless).
Or the other way round - e.g. a spoofed 200 reply with proper Via branchid and false fromtag. Will it terminate the transaction but keep the dialog in early state
But that is not a spoofed reply, instead it's just a 100% valid reply with a different To-tag. It could occur if the called is a proxy which performs serial forking (so after some seconds our proxy receives responses with a new To-tag, i.e. the remote voicemail server).
Then the real 200 OK will be forwarded stateless by tm module
No, it would be a valid response according to TM.
and may bypass dialog module (if callback is only triggered is there is a matching transaction)?
But there is matching transaction so no problem :)
Iñaki Baz Castillo wrote:
2010/3/17 Klaus Darilion klaus.mailinglists@pernau.at:
Btw: how are dialogs in dialog module and transactions in tm module are exactly identified? For example a response with proper callid and fromtag but faked Via branch, will it be accepted by dialog module but ignored (drop or stateless forwarding) by tm?
Good question. IMHO it should be discarded as TM and dialog level (and not relayed stateless).
The dialog module handles responses in the dlg_onreply() function which is called by the tm module when the TMCB_RESPONSE_PRE_OUT (named TMCB_RESPONSE_READY in 3.x) tm callback is triggered. If the Via branch is faked, the tm module should not be able to match the response to a request because the branch parameter must constitute the transaction identifier. Subsequently, tm will not execute any TMCB_RESPONSE_PRE_OUT callbacks, and the dialog module won't ever have to look at the faked response.
Paraphrasing: If something's wrong on the transaction level and tm is doing its job right, dialog won't care.
Cheers,
--Timo
Am 17.03.2010 18:10, schrieb Timo Reimann:
Iñaki Baz Castillo wrote:
2010/3/17 Klaus Darilionklaus.mailinglists@pernau.at:
Btw: how are dialogs in dialog module and transactions in tm module are exactly identified? For example a response with proper callid and fromtag but faked Via branch, will it be accepted by dialog module but ignored (drop or stateless forwarding) by tm?
Good question. IMHO it should be discarded as TM and dialog level (and not relayed stateless).
The dialog module handles responses in the dlg_onreply() function which is called by the tm module when the TMCB_RESPONSE_PRE_OUT (named TMCB_RESPONSE_READY in 3.x) tm callback is triggered.
If dialog module receives this callback - will it check fromtag/callid or is the dialog already identified by the callback?
regards klaus
If the Via branch
is faked, the tm module should not be able to match the response to a request because the branch parameter must constitute the transaction identifier. Subsequently, tm will not execute any TMCB_RESPONSE_PRE_OUT callbacks, and the dialog module won't ever have to look at the faked response.
Paraphrasing: If something's wrong on the transaction level and tm is doing its job right, dialog won't care.
Cheers,
--Timo
Klaus Darilion wrote:
Btw: how are dialogs in dialog module and transactions in tm module are exactly identified? For example a response with proper callid and fromtag but faked Via branch, will it be accepted by dialog module but ignored (drop or stateless forwarding) by tm?
Good question. IMHO it should be discarded as TM and dialog level (and not relayed stateless).
The dialog module handles responses in the dlg_onreply() function which is called by the tm module when the TMCB_RESPONSE_PRE_OUT (named TMCB_RESPONSE_READY in 3.x) tm callback is triggered.
If dialog module receives this callback - will it check fromtag/callid or is the dialog already identified by the callback?
The latter is true: The dialog module does not need to check the dialog identifier (From-tag, To-Tag, Call-ID) because the dialog that the response is associated with will be given as one of the callback parameters. When the dlg_onreq() function initially established the dialog, it passed a pointer to the dialog data-structure (dlg_cell *) to the callback registration function for TMCB_RESPONSE_PRE_OUT.
The whole effort of matching dialogs (including the dialog identifier) is only done in dlg_onroute() which is called for every loose_route'ed message, i.e., in-dialog request.
Cheers,
--Timo
Hi, please help me with the dialog module in scenarios with spiral. IMHO there are two approachs for this case (dialog module working on P1):
UAC ---------------> P1 -----------> P2 --------------> P1 ----------------> UAS
Approach 1) - When the INVITE arrives form UAC a dialog entry is generated. - When the INVITE does spiral and arrives to P1 from P2 a new dialog entry is created. - The difference between both entries is the caller route-set which would be null for the first entry and "sip:P2, sip:P1" for the second entry, right?
Approach 2) - When the INVITE arrives form UAC a dialog entry is generated. - When the INVITE does spiral and arrives to P1 from P2 a new dialog entry is NOT created as there is already an entry with same callid and fromtag (even if the caller route-set is different).
*** Now imagine UAS replies 200 and the response arrives from UAS to P1:
In the first approach TM would invoke the callback for the second dialog entry (OK).
In the second approach TM would invoke NO callback as no dialog entry was generated for this INVITE transaction (OK).
so it changes its state. *** Now the 200 does the spiral through P2 and arrives again to P1:
In the first approach TM would invoke the callback for the first dialog entry (OK).
In the second approach TM would invoke the callback for the first (an unique) dialog entry (OK).
*** Now UAC sends a re-INVITE and arrives to P1:
In the first approach the dialog module tries to match the dialog and finds two entries with same callid and fromtag (opsss), which one to choose? the ONLY solution is matching the request route-set which is difficult as involves SIP URI comparisons (not just a string match). PROBLEM: what to do here?
In the second approach the dialog module tries to match the dialog and finds the unique entry with same callid and fromtag.
*** Now UAS sends BYE and arrives to P1:
In the first approach same as above occurs, in order to determine which dialog entry to update it's required to inspect and match the request route-set (ugly!).
In the second approach the unique dialog entry would be matched.
So the main question is: when a spiral occurs, should it involve an unique dialog entry or two (different route-set)?
I don't see the benefict of creating two dialog entries. From SIP perspective it's still the same and unique dialog, but there is a possible vulnerability: Imagine the above case when UAS sends the BYE: - UAS sends BYE to P1. - P1 matches the unique dialog and marks it as terminated. - P1 relays the BYE to P2 following the loose routing mechanism. - P2 and UAS are "hackers". P2 ignores the BYE and doesn't relay it. - UAC never receives it but the dialog is marked as terminated.
Opinions? Thanks.
Am 17.03.2010 19:34, schrieb Iñaki Baz Castillo:
Hi, please help me with the dialog module in scenarios with spiral. IMHO there are two approachs for this case (dialog module working on P1):
UAC ---------------> P1 -----------> P2 --------------> P1 ----------------> UAS
Dialog creation in dialog module is based on tm's transactions. Thus I guess a second dialog is created. Interesting would be how the in-dialog requests are mapped to the dialog - here a RR-cookie would be needed to find the proper dialog structure.
regards klaus
Approach 1)
- When the INVITE arrives form UAC a dialog entry is generated.
- When the INVITE does spiral and arrives to P1 from P2 a new dialog
entry is created.
- The difference between both entries is the caller route-set which
would be null for the first entry and "sip:P2, sip:P1" for the second entry, right?
Approach 2)
- When the INVITE arrives form UAC a dialog entry is generated.
- When the INVITE does spiral and arrives to P1 from P2 a new dialog
entry is NOT created as there is already an entry with same callid and fromtag (even if the caller route-set is different).
*** Now imagine UAS replies 200 and the response arrives from UAS to P1:
In the first approach TM would invoke the callback for the second dialog entry (OK).
In the second approach TM would invoke NO callback as no dialog entry was generated for this INVITE transaction (OK).
so it changes its state. *** Now the 200 does the spiral through P2 and arrives again to P1:
In the first approach TM would invoke the callback for the first dialog entry (OK).
In the second approach TM would invoke the callback for the first (an unique) dialog entry (OK).
*** Now UAC sends a re-INVITE and arrives to P1:
In the first approach the dialog module tries to match the dialog and finds two entries with same callid and fromtag (opsss), which one to choose? the ONLY solution is matching the request route-set which is difficult as involves SIP URI comparisons (not just a string match). PROBLEM: what to do here?
In the second approach the dialog module tries to match the dialog and finds the unique entry with same callid and fromtag.
*** Now UAS sends BYE and arrives to P1:
In the first approach same as above occurs, in order to determine which dialog entry to update it's required to inspect and match the request route-set (ugly!).
In the second approach the unique dialog entry would be matched.
So the main question is: when a spiral occurs, should it involve an unique dialog entry or two (different route-set)?
I don't see the benefict of creating two dialog entries. From SIP perspective it's still the same and unique dialog, but there is a possible vulnerability: Imagine the above case when UAS sends the BYE:
- UAS sends BYE to P1.
- P1 matches the unique dialog and marks it as terminated.
- P1 relays the BYE to P2 following the loose routing mechanism.
- P2 and UAS are "hackers". P2 ignores the BYE and doesn't relay it.
- UAC never receives it but the dialog is marked as terminated.
Opinions? Thanks.
2010/3/18 Klaus Darilion klaus.mailinglists@pernau.at:
UAC ---------------> P1 -----------> P2 --------------> P1 ----------------> UAS
Dialog creation in dialog module is based on tm's transactions. Thus I guess a second dialog is created.
Well, I'm trying to figure a new design for dialog module [*] so I don't care too much how the dialog module is implemented right now :)
Interesting would be how the in-dialog requests are mapped to the dialog - here a RR-cookie would be needed to find the proper dialog structure.
Yes, that's the point, the in-dialog requests. The only way is by inspecting the route-set of the request but this involver ugly SIP URI comparisons. But this can be really simpliffied using RR-cookies as RR module already uses, right? If not, the dialog hash_id could be added to the Record-Route during loose_route().
Thanks.
[*] http://www.kamailio.org/dokuwiki/doku.php/dialog-stateful:new-dialog-module-... (work in progress...)
Am 18.03.2010 10:31, schrieb Iñaki Baz Castillo:
If not, the dialog hash_id could be added to the Record-Route during loose_route().
Yes. But then an manipulated Route header may cause that the request is not handled by the dialog module. So, design of a dialog module heavily depends on what you want to use it for.
regards klaus
2010/3/18 Klaus Darilion klaus.mailinglists@pernau.at:
Am 18.03.2010 10:31, schrieb Iñaki Baz Castillo:
If not, the dialog hash_id could be added to the Record-Route during loose_route().
Yes. But then an manipulated Route header may cause that the request is not handled by the dialog module. So, design of a dialog module heavily depends on what you want to use it for.
Right. Then the other approach is just inspecting the From-tag, To-tag and Call-ID, but with this is not possible to differentiate spirals through the proxy.
Iñaki Baz Castillo wrote:
Interesting would be how the in-dialog requests are mapped to the dialog - here a RR-cookie would be needed to find the proper dialog structure.
Yes, that's the point, the in-dialog requests. The only way is by inspecting the route-set of the request but this involver ugly SIP URI comparisons. But this can be really simpliffied using RR-cookies as RR module already uses, right? If not, the dialog hash_id could be added to the Record-Route during loose_route().
The dialog module currently supports three modes of matching dialogs (actually, it's just two because the third mode is a combination of both were one is used as fallback). See here for a short description:
http://kamailio.org/docs/modules/1.5.x/dialog.html#id2491878
(The modes haven't changed for 3.x.)
Matching on SIP elements only employs the Call-ID, From-tag, and To-tag currently. Record set is stored but its usage apparently limited to displaying purposes (i.e., MI interface): dlg_hash.h's match_dialog() function doesn't show any sign of record set parsing.
For DID-(cookie-)based matching, a reference to the hashed dialog data-structure is attached to the record set by the time the dialog is created, and later fetched when on-route processing in dlg_onroute() (called from loose_route()) is performed.
Cheers,
--Timo
2010/3/18 Timo Reimann timo.reimann@1und1.de:
Yes, that's the point, the in-dialog requests. The only way is by inspecting the route-set of the request but this involver ugly SIP URI comparisons. But this can be really simpliffied using RR-cookies as RR module already uses, right? If not, the dialog hash_id could be added to the Record-Route during loose_route().
The dialog module currently supports three modes of matching dialogs (actually, it's just two because the third mode is a combination of both were one is used as fallback). See here for a short description:
http://kamailio.org/docs/modules/1.5.x/dialog.html#id2491878
(The modes haven't changed for 3.x.)
Thanks for clarification. More inline:
Matching on SIP elements only employs the Call-ID, From-tag, and To-tag currently. Record set is stored but its usage apparently limited to displaying purposes (i.e., MI interface): dlg_hash.h's match_dialog() function doesn't show any sign of record set parsing.
Yes sure, note that matching a route-set involves complex SIP URI comparisons, which would be not very "efficient".
For DID-(cookie-)based matching, a reference to the hashed dialog data-structure is attached to the record set by the time the dialog is created, and later fetched when on-route processing in dlg_onroute() (called from loose_route()) is performed.
Ok, then this way (using cookie) is the *only* way to properly match dialogs when an spiral occurs. Do you agree?
Of course, a malicious user could modify such cookie value so kamailio couldn't match the dialog, or it could match it according to From/To-tags and Call-ID, but then it's not possible to differentiate between two dialogs originated due to a spiral (the in-dialog request matches both if route-set is not inspected).
So the next question would be: do we need two dialog entries to be created when an INVITE does a spiral? As I understand this is fully possible as the INVITE after the spiral is a new transaction and future in-dialog requests would be matched against the appropriate dialog based on the dialog cookie, right?
Regards.
Iñaki Baz Castillo wrote:
Hi, please help me with the dialog module in scenarios with spiral. IMHO there are two approachs for this case (dialog module working on P1):
UAC ---------------> P1 -----------> P2 --------------> P1 ----------------> UAS
Approach 1)
- When the INVITE arrives form UAC a dialog entry is generated.
- When the INVITE does spiral and arrives to P1 from P2 a new dialog
entry is created.
- The difference between both entries is the caller route-set which
would be null for the first entry and "sip:P2, sip:P1" for the second entry, right?
At this time of routing, wouldn't it just be the record-route set? Of course, it'd yield a record set once signaling is complete. (Sorry if I'm being too picky here.)
[snap]
Agreeing with the rest of the description you provided.
So the main question is: when a spiral occurs, should it involve an unique dialog entry or two (different route-set)?
I don't see the benefict of creating two dialog entries. From SIP perspective it's still the same and unique dialog, but there is a possible vulnerability: Imagine the above case when UAS sends the BYE:
- UAS sends BYE to P1.
- P1 matches the unique dialog and marks it as terminated.
- P1 relays the BYE to P2 following the loose routing mechanism.
- P2 and UAS are "hackers". P2 ignores the BYE and doesn't relay it.
- UAC never receives it but the dialog is marked as terminated.
I am not sure if this really needs to be handled. Generally, is Kamailio designed to deal with misbehaving on-route proxies? There's probably a whole bunch of problems one can think of if you try to break operations intentionally.
The UAC should implement some way of detecting disconnected sessions and act accordingly anyway, like observing the RTP stream and indicate an error if there's no more data flowing.
Cheers,
--Timo
Am 17.03.2010 17:55, schrieb Iñaki Baz Castillo:
2010/3/17 Klaus Darilionklaus.mailinglists@pernau.at:
This is not valid for the case in which a dialog is forked by a proxy behind our proxy. From the point of view of TM it's a single transaction.
That's true. It probably depends on what you actually want to track
with the
dialog module. E.g. if you just want to track the number of established dialogs then you do not care about multiple early dialogs.
But it's also true that more and more modules want to depend on dialog module (take a look to OpenSIPS loadbalancer or mediaproxy modules). And they fail when handling forking calls.
Btw: how are dialogs in dialog module and transactions in tm module are exactly identified? For example a response with proper callid and
fromtag
but faked Via branch, will it be accepted by dialog module but
ignored (drop
or stateless forwarding) by tm?
Good question. IMHO it should be discarded as TM and dialog level (and not relayed stateless).
Or the other way round - e.g. a spoofed 200 reply with proper Via
branchid
and false fromtag. Will it terminate the transaction but keep the
dialog in
early state
But that is not a spoofed reply, instead it's just a 100% valid reply with a different To-tag. It could occur if the called is a proxy which performs serial forking (so after some seconds our proxy receives responses with a new To-tag, i.e. the remote voicemail server).
Let's call it a malicious reply. I was talking about a false from-tag, not to-tag. Thus, tm will accept the 200 ok and terminate the transaction (if it is implemented RFC conform). If dialog module checks from-tag it probably will ignore the reply.
Anyway, I guess dialog module is only good as helper module but shouldn't be used as a reliable module (e.g. for security, accounting ...)
regards klaus
Then the real 200 OK will be forwarded stateless by tm module
No, it would be a valid response according to TM.
and may bypass dialog module (if callback is only triggered is there
is a
matching transaction)?
But there is matching transaction so no problem :)
2010/3/17 Klaus Darilion klaus.mailinglists@pernau.at:
But that is not a spoofed reply, instead it's just a 100% valid reply with a different To-tag. It could occur if the called is a proxy which performs serial forking (so after some seconds our proxy receives responses with a new To-tag, i.e. the remote voicemail server).
Let's call it a malicious reply. I was talking about a false from-tag, not to-tag. Thus, tm will accept the 200 ok and terminate the transaction (if it is implemented RFC conform). If dialog module checks from-tag it probably will ignore the reply.
You are rigth, sorry, I understood "To-tag". Well, from the proxy point of view the transaction must end (even if
From tag doesn't match the dialog data), as the transaction layer is
not dialog aware.
But of course the dialog module would ignore the response as From-tag doesn't match, and that's the expected behavior (the UAC wouuld also ignore such response).
Anyway, I guess dialog module is only good as helper module but shouldn't be used as a reliable module (e.g. for security, accounting ...)
That's the question. Theorically dialog module is just a helper, but looking at OpenSIPS there are several modules offering functionality based on dialog module... so... It's like "it's not a secure/robust module but I don't care".
Am 17.03.2010 18:18, schrieb Iñaki Baz Castillo:
2010/3/17 Klaus Darilionklaus.mailinglists@pernau.at:
But that is not a spoofed reply, instead it's just a 100% valid reply with a different To-tag. It could occur if the called is a proxy which performs serial forking (so after some seconds our proxy receives responses with a new To-tag, i.e. the remote voicemail server).
Let's call it a malicious reply. I was talking about a false from-tag, not to-tag. Thus, tm will accept the 200 ok and terminate the transaction (if it is implemented RFC conform). If dialog module checks from-tag it probably will ignore the reply.
You are rigth, sorry, I understood "To-tag". Well, from the proxy point of view the transaction must end (even if From tag doesn't match the dialog data), as the transaction layer is not dialog aware.
But of course the dialog module would ignore the response as From-tag doesn't match, and that's the expected behavior (the UAC wouuld also ignore such response).
I checked dialog code: it is safe. Dialog does not have to check callid/tags as the dialog is already identified via the tm-callback (at least of out-of-dialog transactions).
Thus, a malicious response can not be used to bring tm/dialog out of synchronization.
Anyway, I guess dialog module is only good as helper module but shouldn't be used as a reliable module (e.g. for security, accounting ...)
That's the question. Theorically dialog module is just a helper, but looking at OpenSIPS there are several modules offering functionality based on dialog module... so... It's like "it's not a secure/robust module but I don't care".
I think it is OK for things like NAT traversal as an attacker can just stop its NAT traversal.
But for example it is unreliable for accounting. E.g. a malicious BYE request with manipulated RURI (sip:foo.bar instead of sip:00431234@ip.address.of.gw) will stop the dialog, but never reach the gateway.
regards klaus