Hello,
I'm running the latest pull of Kamailio 4.1 (last commit be187e135b0b9b28136817c3569ab5c0abcc5b3f) and am using rtpproxy-ng with a recent mediaproxy-ng master (commit cb6990e43864b077dd6a24acfbdf5ef76c1a427e).
For no apparent reason, Kamailio has stopped sending 'offer' commands to it when I use rtpproxy_manage(). My use of it is in this setting:
if(isflagset(PROXY_MEDIA) && !isflagset(PROXY_MEDIA_SET) && has_body("application/sdp")) { set_rtp_proxy_set("1"); rtpproxy_manage("o");
add_rr_param(";proxy_media=yes");
setflag(PROXY_MEDIA_SET); }
I put in a log message to confirm that this block is being run. It is.
But, there's no offer command going to the mediaproxy-ng on the other box, as confirmed by packet captures and logs. However, the mediaproxy-ng is getting lots of 'answer' and 'delete' commands that it doesn't know what to do with, since the call was never initialised with 'offer'.
When I change rtpproxy_manage() to rtpproxy_offer(), it works perfectly.
I've been using rtpproxy_manage() forever, almost as long as it's existed. Does it not work with rtpproxy-ng, despite what the documentation says?
If it helps, here are my rtpproxy-ng modparams:
modparam("rtpproxy-ng", "rtpproxy_sock", "1 == udp:xxx.xxx.xxx.xxx:5050") modparam("rtpproxy-ng", "rtpproxy_disable_tout", 120) modparam("rtpproxy-ng", "rtpproxy_tout", 1) modparam("rtpproxy-ng", "rtpproxy_retr", 2)
On 04/23/14 11:53, Alex Balashov wrote:
Hello,
I'm running the latest pull of Kamailio 4.1 (last commit be187e135b0b9b28136817c3569ab5c0abcc5b3f) and am using rtpproxy-ng with a recent mediaproxy-ng master (commit cb6990e43864b077dd6a24acfbdf5ef76c1a427e).
For no apparent reason, Kamailio has stopped sending 'offer' commands to it when I use rtpproxy_manage(). My use of it is in this setting:
if(isflagset(PROXY_MEDIA) && !isflagset(PROXY_MEDIA_SET) && has_body("application/sdp")) { set_rtp_proxy_set("1"); rtpproxy_manage("o"); add_rr_param(";proxy_media=yes"); setflag(PROXY_MEDIA_SET); }
I put in a log message to confirm that this block is being run. It is.
But, there's no offer command going to the mediaproxy-ng on the other box, as confirmed by packet captures and logs. However, the mediaproxy-ng is getting lots of 'answer' and 'delete' commands that it doesn't know what to do with, since the call was never initialised with 'offer'.
Can you please clarify: does it not send anything at all, or does it send an answer instead of an offer?
cheers
On 04/23/2014 12:08 PM, Richard Fuchs wrote:
Can you please clarify: does it not send anything at all, or does it send an answer instead of an offer?
Well, I suppose I can't say for sure, but it looks like it's not sending anything at all. When I grep a particular Call-ID, the first thing I get is:
Apr 23 15:28:37 sd-rtp01 mediaproxy-ng[7910]: Got valid command from xxx.xxx.xxx.xxx:43733: answer - { "sdp": "v=0#015#012o=- 1398266077 1398266077 IN IP4 xxx.xxx.xxx.xxx#015#012s=VOS2009#015#012c=IN IP4 yyy.yyy.yyy.yyy#015#012t=0 0#015#012m=audio 33576 RTP/AVP 18 101#015#012a=rtpmap:18 G729/8000#015#012a=fmtp:18 annexb=no#015#012a=rtpmap:101 telephone-event/8000#015#012a=fmtp:101 0-16#015#012", "replace": [ "origin" ], "call-id": "15109646-3607255707-160030@xxx", "received-from": [ "IP4", "xxx.xxx.xxx.xxx" ], "from-tag": "3607255707-160035", "to-tag": "Fa1Fe4ZSvBQSF", "command": "answer" }
If my understanding of the control protocol is correct, this is actually an answer, not a mislabeled offer, since the offer would contain some other attributes.
But maybe not?
I expect an answer because I have an rtpproxy_manage() in an onreply_route for 18x/2xx+SDP responses to this INVITE, of course.
Maybe it's not a bug. I think I've got a theory about what may be happening. Admittedly, it's not trivial to follow, but bear with me.
The invocation of rtpproxy_manage() is happening in a REQUEST_ROUTE that is actually being triggered out of a FAILURE_ROUTE, because we are pulling routing info from a redirect server. So, it looks like this (obviously, greatly simplified):
# Main request route.
route { ...
t_on_failure("FAIL"); t_relay(); }
route[PROCESS_CALL] { rtpproxy_manage("o"); }
failure_route[FAIL] { if($T_rpl($rs) == 302) { ...
route(PROCESS_CALL); } }
Now, "PROCESS_CALL" is a request route and the things that are done inside it are all safe to do inside a FAILURE_ROUTE, e.g. no stateless replies. However, because it's being called from a FAILURE_ROUTE, I'll bet what's happening is that the evaluative context tells rtpproxy_manage() that it's dealing with a _reply_ (the 302 redirect), not a _request_, so it should be sending an 'answer' on that basis.
Does that sound reasonable? I don't have an easy way of testing this thesis right now since it's production.
The reason I had not previously considered this possibility is because the documentation says--or, at least to my lackadaisical interpretation--that rtpproxy_manage() will only call rtpproxy_answer() if it is operating on a 1xx/2xx reply with SDP, otherwise it'll send rtpproxy_offer(), or send a delete command if it's a >= 300 reply.
On 04/23/2014 12:51 PM, Alex Balashov wrote:
Maybe it's not a bug. I think I've got a theory about what may be happening. Admittedly, it's not trivial to follow, but bear with me.
The invocation of rtpproxy_manage() is happening in a REQUEST_ROUTE that is actually being triggered out of a FAILURE_ROUTE, because we are pulling routing info from a redirect server. So, it looks like this (obviously, greatly simplified):
# Main request route. route { ... t_on_failure("FAIL"); t_relay(); } route[PROCESS_CALL] { rtpproxy_manage("o"); } failure_route[FAIL] { if($T_rpl($rs) == 302) { ... route(PROCESS_CALL); } }
Now, "PROCESS_CALL" is a request route and the things that are done inside it are all safe to do inside a FAILURE_ROUTE, e.g. no stateless replies. However, because it's being called from a FAILURE_ROUTE, I'll bet what's happening is that the evaluative context tells rtpproxy_manage() that it's dealing with a _reply_ (the 302 redirect), not a _request_, so it should be sending an 'answer' on that basis.
Does that sound reasonable? I don't have an easy way of testing this thesis right now since it's production.
On 04/23/14 12:59, Alex Balashov wrote:
The reason I had not previously considered this possibility is because the documentation says--or, at least to my lackadaisical interpretation--that rtpproxy_manage() will only call rtpproxy_answer() if it is operating on a 1xx/2xx reply with SDP, otherwise it'll send rtpproxy_offer(), or send a delete command if it's a >= 300 reply.
Actually the logic is a bit more complicated than that. You can look at rtpproxy_manage() in rtpproxy.c for the full details. Main selection criterion is whether the message is a request or a reply, second criterion is the SIP method (taken from the CSeq) and/or the response code in case of a reply. The route type is only marginally relevant. So it really depends on what kind of SIP message you're acting upon.
You should actually see the same behaviour with rtpproxy module as well, as this part of the code hasn't been changed.
cheerse
On 04/23/2014 01:22 PM, Richard Fuchs wrote:
Main selection criterion is whether the message is a request or a reply, second criterion is the SIP method (taken from the CSeq) and/or the response code in case of a reply. The route type is only marginally relevant.
Yeah, so the key question is: what is the message we are acting upon?
It it is my theory that in a request route that is called from a failure_route that is triggered by a 302 reply, the message being operated on is actually the 302 reply, and not an initial INVITE. And that's why it doesn't produce the offer command as expected.
The legacy rtpproxy module may well behave the same way. I hadn't tried to use rtpproxy_manage() in this scope before, which is why I was imagining it to have "always worked".
On 04/23/14 13:24, Alex Balashov wrote:
On 04/23/2014 01:22 PM, Richard Fuchs wrote:
Main selection criterion is whether the message is a request or a reply, second criterion is the SIP method (taken from the CSeq) and/or the response code in case of a reply. The route type is only marginally relevant.
Yeah, so the key question is: what is the message we are acting upon?
It it is my theory that in a request route that is called from a failure_route that is triggered by a 302 reply, the message being operated on is actually the 302 reply, and not an initial INVITE. And that's why it doesn't produce the offer command as expected.
Correct, it would be sending a delete to the proxy. I'm not certain that instead sending an offer is indeed the expected behaviour.
cheers