Hi,
Is there any good solution for the scenario of an auth_challenge() with two separate transaction suspensions?
To clarify (simplified):
request_route { ...
t_newtran();
if(!is_present_hf("Authorization") && !is_present_hf("Proxy-Authorization")) { auth_challenge("$fd", "1"); exit; }
# TM suspend/continue t_newtran();
async credentials query("RESUME_AUTH"); }
route[RESUME_AUTH] { # Credentials received into PVs.
if(!pv_auth_check("...")) { auth_challenge("$fd", "1"); exit; }
# Create transaction shell if not exists already from auth query. if(!t_lookup_request()) t_newtran();
# TM suspend/continue async route query("RESUME_ROUTING"); }
route[RESUME_ROUTING] { # Unmarshal etc.
t_relay(); # etc. }
What happens here is that the first auth_challenge() results in a retransmission of its 407 challenge without absorbing the negative ACK. This is despite the ostensibly stateful behaviour of auth_challenge() without "force_stateless_reply" enabled.
In this case, it eclipses the second, unrelated 407 challenge from the subsequent routing query (407 challenge with +1 CSeq):

-- Alex
To be clear, the two t_newtran() calls in the main request_route were naturally a typo. :-) Only the first one was intended.
On Dec 12, 2022, at 3:45 PM, Alex Balashov abalashov@evaristesys.com wrote:
Hi,
Is there any good solution for the scenario of an auth_challenge() with two separate transaction suspensions?
To clarify (simplified):
request_route { ... t_newtran(); if(!is_present_hf("Authorization") && !is_present_hf("Proxy-Authorization")) { auth_challenge("$fd", "1"); exit; } # TM suspend/continue t_newtran(); async credentials query("RESUME_AUTH"); } route[RESUME_AUTH] { # Credentials received into PVs. if(!pv_auth_check("...")) { auth_challenge("$fd", "1"); exit; } # Create transaction shell if not exists already from auth query. if(!t_lookup_request()) t_newtran(); # TM suspend/continue async route query("RESUME_ROUTING"); } route[RESUME_ROUTING] { # Unmarshal etc. t_relay(); # etc. }
What happens here is that the first auth_challenge() results in a retransmission of its 407 challenge without absorbing the negative ACK. This is despite the ostensibly stateful behaviour of auth_challenge() without "force_stateless_reply" enabled.
In this case, it eclipses the second, unrelated 407 challenge from the subsequent routing query (407 challenge with +1 CSeq):
<Screenshot 2022-12-12 at 3.44.15 PM.jpeg> -- Alex
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
Hello,
change of cseq results in a different transaction, there should be two at the same time for a short interval. Try to see if debug=3 offers any hints.
For clarification: do you need to do authentication two times? Second time with pv function?
Cheers, Daniel
On 12.12.22 21:53, Alex Balashov wrote:
To be clear, the two t_newtran() calls in the main request_route were naturally a typo. :-) Only the first one was intended.
On Dec 12, 2022, at 3:45 PM, Alex Balashov abalashov@evaristesys.com wrote:
Hi,
Is there any good solution for the scenario of an auth_challenge() with two separate transaction suspensions?
To clarify (simplified):
request_route { ... t_newtran(); if(!is_present_hf("Authorization") && !is_present_hf("Proxy-Authorization")) { auth_challenge("$fd", "1"); exit; } # TM suspend/continue t_newtran(); async credentials query("RESUME_AUTH"); } route[RESUME_AUTH] { # Credentials received into PVs. if(!pv_auth_check("...")) { auth_challenge("$fd", "1"); exit; } # Create transaction shell if not exists already from auth query. if(!t_lookup_request()) t_newtran(); # TM suspend/continue async route query("RESUME_ROUTING"); } route[RESUME_ROUTING] { # Unmarshal etc. t_relay(); # etc. }
What happens here is that the first auth_challenge() results in a retransmission of its 407 challenge without absorbing the negative ACK. This is despite the ostensibly stateful behaviour of auth_challenge() without "force_stateless_reply" enabled.
In this case, it eclipses the second, unrelated 407 challenge from the subsequent routing query (407 challenge with +1 CSeq):
<Screenshot 2022-12-12 at 3.44.15 PM.jpeg> -- Alex
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
Kamailio - Users Mailing List - Non Commercial Discussions sr-users@lists.kamailio.org Important: keep the mailing list in the recipients, do not reply only to the sender! Edit mailing list options or unsubscribe: https://lists.kamailio.org/cgi-bin/mailman/listinfo/sr-users
On Dec 13, 2022, at 3:14 AM, Daniel-Constantin Mierla miconda@gmail.com wrote:
change of cseq results in a different transaction, there should be two at the same time for a short interval. Try to see if debug=3 offers any hints.
Makes sense. What I'm wondering is why the ACK for the negative reply (407) isn't processed and doesn't seem to result in immediate termination of the first transaction.
This doesn't happen if I only suspend once. There is no problem in that scenario.
For clarification: do you need to do authentication two times? Second time with pv function?
No, the process is basically that I don't know whether I need to do digest authentication until a preliminary routing query happens (async) first, and if I do, then I return a 407 challenge from that transaction. I then receive a new INVITE with digest credentials, and I (async) query for the credentials-info (HA1 of password), and then I auth_check() the received digest credentials against the info. If not valid, I issue another auth challenge, and if valid, I continue with route processing (again async).
This sounds like a mess that Kamailio's async stuff wasn't really intended to support, maybe. I'm wondering if the simplest thing to seed the credentials-info into Kamailio somehow, e.g. via JSONRPC+htable, so that an async query is not required in order to obtain it dynamically. I was hoping to avoid that, but maybe there's not another way to do it?
-- Alex
Just as an update, still haven't been able to solve this. I have tried a number of different permutations, but it seems that whenever a new INVITE (CSeq+1) comes in response to an auth challenge sent from a async resume route, the 407 challenge for the old INVITE keeps being retransmitted.
It does not appear to matter if the auth challenge is failed:
│IN 172.24.0.9:60921 172.24.0.7:5060 │VI ──────────┬───────── ──────────┬───────── │TE 16:30:56.392948 │ INVITE (SDP) │ │ s +0.000355 │ ──────────────────────────> │ │ip 16:30:56.393303 │ 100 trying -- your call is │ │:1 +0.002757 │ <────────────────────────── │ │00 16:30:56.396060 │ 407 Proxy Authentication R │ │@s +0.000213 │ <────────────────────────── │ │ip 16:30:56.396273 │ ACK │ │-p +0.201427 │ ──────────────────────────> │ │ro 16:30:56.597700 │ INVITE (SDP) │ │xy +0.000432 │ ──────────────────────────> │ │-d 16:30:56.598132 │ 100 trying -- your call is │ │ig +0.001420 │ <────────────────────────── │ │es 16:30:56.599552 │ 407 Proxy Authentication R │ │t- +0.000227 │ <────────────────────────── │ │au 16:30:56.599779 │ ACK │ │th +0.237534 │ ──────────────────────────> │ │:5 16:30:56.837313 │ 407 Proxy Authentication R │ │06 +1.000347 │ <────────────────────────── │ │0 16:30:57.837660 │ 407 Proxy Authentication R │ │SI +1.999542 │ <<<──────────────────────── │ │P/ 16:30:59.837202 │ 407 Proxy Authentication R │ │2. +0.000090 │ <<<──────────────────────── │ │0 16:30:59.837292 │ 407 Proxy Authentication R │ │Vi │ <<<──────────────────────── │ │a: │ │ │ S
Or successful:
│IN 172.24.0.9:49685 172.24.0.7:5060 172.24.0.8:│VI0 ──────────┬───────── ──────────┬───────── ──────────┬───│TE─ 16:30:56.835874 │ INVITE (SDP) │ │ │ s +0.001246 │ ──────────────────────────> │ │ │ip 16:30:56.837120 │ 100 trying -- your call is │ │ │:1 +0.003917 │ <────────────────────────── │ │ │00 16:30:56.841037 │ 407 Proxy Authentication R │ │ │@s +0.000577 │ <────────────────────────── │ │ │ip 16:30:56.841614 │ ACK │ │ │-p +0.200484 │ ──────────────────────────> │ │ │ro 16:30:57.042098 │ INVITE (SDP) │ │ │xy +0.000823 │ ──────────────────────────> │ │ │-d 16:30:57.042921 │ 100 trying -- your call is │ │ │ig +0.009837 │ <────────────────────────── │ │ │es 16:30:57.052758 │ │ INVITE (SDP) │ │t- +0.001506 │ │ ──────────────────────────> │ │au 16:30:57.054264 │ │ 100 Trying │ │th +0.001558 │ │ <────────────────────────── │ │:5 16:30:57.055822 │ │ 200 OK (SDP) │ │06 +0.000664 │ │ <────────────────────────── │ │0 16:30:57.056486 │ 200 OK (SDP) │ │ │SI +0.000854 │ <────────────────────────── │ │ │P/ 16:30:57.057340 │ ACK │ │ │2. +0.000447 │ ──────────────────────────> │ │ │0 16:30:57.057787 │ │ ACK │ │Vi +0.279666 │ │ ──────────────────────────> │ │a: 16:30:57.337453 │ 407 Proxy Authentication R │ │ │ S +0.224273 │ <────────────────────────── │ │ │IP 16:30:57.561726 │ │ BYE │ │/2 +0.001295 │ │ <────────────────────────── │ │.0 16:30:57.563021 │ BYE │ │ │/U +0.002180 │ <────────────────────────── │ │ │DP 16:30:57.565201 │ 200 OK Now │ │ │ 1 +0.000327 │ ──────────────────────────> │ │ │72 16:30:57.565528 │ │ 200 OK Now │ │.2 +0.771759 │ │ ──────────────────────────> │ │4. 16:30:58.337287 │ 407 Proxy Authentication R │ │ │0. +2.000408 │ <────────────────────────── │ │ │9: 16:31:00.337695 │ 407 Proxy Authentication R │ │ │49 +0.000158 │ <<<──────────────────────── │ │ │68 16:31:00.337853 │ 407 Proxy Authentication R │ │ │5; │ <<<──────────────────────── │ │ │rp │ │ │ │or │ │ │ │t;
What does matter is if there is a subsequent INVITE at all. If there's not, no problem, no retransmission:
│IN 172.24.0.9:33672 172.24.0.7:5060 │VI ──────────┬───────── ──────────┬───────── │TE 16:34:56.823495 │ INVITE (SDP) │ │ s +0.001047 │ ──────────────────────────> │ │ip 16:34:56.824542 │ 100 trying -- your call is │ │:1 +0.002516 │ <────────────────────────── │ │00 16:34:56.827058 │ 407 Proxy Authentication R │ │@s +0.000351 │ <────────────────────────── │ │ip 16:34:56.827409 │ ACK │ │-p │ ──────────────────────────> │ │ro │ │ │xy
If the negative ACK were not being matched, I would think the retransmission would happen here too. It seems to happen because the subsequent INVITE keeps the old transaction alive and in its previous state somehow.
Any suggestions welcome!
-- Alex
On Dec 13, 2022, at 8:54 AM, Alex Balashov abalashov@evaristesys.com wrote:
On Dec 13, 2022, at 3:14 AM, Daniel-Constantin Mierla miconda@gmail.com wrote:
change of cseq results in a different transaction, there should be two at the same time for a short interval. Try to see if debug=3 offers any hints.
Makes sense. What I'm wondering is why the ACK for the negative reply (407) isn't processed and doesn't seem to result in immediate termination of the first transaction.
This doesn't happen if I only suspend once. There is no problem in that scenario.
For clarification: do you need to do authentication two times? Second time with pv function?
No, the process is basically that I don't know whether I need to do digest authentication until a preliminary routing query happens (async) first, and if I do, then I return a 407 challenge from that transaction. I then receive a new INVITE with digest credentials, and I (async) query for the credentials-info (HA1 of password), and then I auth_check() the received digest credentials against the info. If not valid, I issue another auth challenge, and if valid, I continue with route processing (again async).
This sounds like a mess that Kamailio's async stuff wasn't really intended to support, maybe. I'm wondering if the simplest thing to seed the credentials-info into Kamailio somehow, e.g. via JSONRPC+htable, so that an async query is not required in order to obtain it dynamically. I was hoping to avoid that, but maybe there's not another way to do it?
-- Alex
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
Hi Alex,
it might not help you much, but recently I was implementing a similar structure in one larger migration project, and it seems to work fine. I am not using any special flags for the challenge etc..
It’s basically like this (pseudo-code)
route{ if no auth user -> auth_challenge() else -> http_async_query(API, AUTH) }
route[AUTH] { get API result for password if API failure -> auth_challenge() else -> pv_auth_check(..)
route(next steps) }
Cheers,
Henning
-- Henning Westerholt – https://skalatan.de/blog/ Kamailio services – https://gilawa.comhttps://gilawa.com/
From: Alex Balashov abalashov@evaristesys.com Sent: Thursday, December 15, 2022 5:36 PM To: Kamailio (SER) - Users Mailing List sr-users@lists.kamailio.org Subject: [SR-Users] Re: auth_challenge() and async
Just as an update, still haven't been able to solve this. I have tried a number of different permutations, but it seems that whenever a new INVITE (CSeq+1) comes in response to an auth challenge sent from a async resume route, the 407 challenge for the old INVITE keeps being retransmitted.
It does not appear to matter if the auth challenge is failed:
│IN 172.24.0.9:60921 172.24.0.7:5060 │VI ──────────┬───────── ──────────┬───────── │TE 16:30:56.392948 │ INVITE (SDP) │ │ s +0.000355 │ ──────────────────────────> │ │ip 16:30:56.393303 │ 100 trying -- your call is │ │:1 +0.002757 │ <────────────────────────── │ │00 16:30:56.396060 │ 407 Proxy Authentication R │ │@s +0.000213 │ <────────────────────────── │ │ip 16:30:56.396273 │ ACK │ │-p +0.201427 │ ──────────────────────────> │ │ro 16:30:56.597700 │ INVITE (SDP) │ │xy +0.000432 │ ──────────────────────────> │ │-d 16:30:56.598132 │ 100 trying -- your call is │ │ig +0.001420 │ <────────────────────────── │ │es 16:30:56.599552 │ 407 Proxy Authentication R │ │t- +0.000227 │ <────────────────────────── │ │au 16:30:56.599779 │ ACK │ │th +0.237534 │ ──────────────────────────> │ │:5 16:30:56.837313 │ 407 Proxy Authentication R │ │06 +1.000347 │ <────────────────────────── │ │0 16:30:57.837660 │ 407 Proxy Authentication R │ │SI +1.999542 │ <<<──────────────────────── │ │P/ 16:30:59.837202 │ 407 Proxy Authentication R │ │2. +0.000090 │ <<<──────────────────────── │ │0 16:30:59.837292 │ 407 Proxy Authentication R │ │Vi │ <<<──────────────────────── │ │a: │ │ │ S
Or successful:
│IN 172.24.0.9:49685 172.24.0.7:5060 172.24.0.8:│VI0 ──────────┬───────── ──────────┬───────── ──────────┬───│TE─ 16:30:56.835874 │ INVITE (SDP) │ │ │ s +0.001246 │ ──────────────────────────> │ │ │ip 16:30:56.837120 │ 100 trying -- your call is │ │ │:1 +0.003917 │ <────────────────────────── │ │ │00 16:30:56.841037 │ 407 Proxy Authentication R │ │ │@s +0.000577 │ <────────────────────────── │ │ │ip 16:30:56.841614 │ ACK │ │ │-p +0.200484 │ ──────────────────────────> │ │ │ro 16:30:57.042098 │ INVITE (SDP) │ │ │xy +0.000823 │ ──────────────────────────> │ │ │-d 16:30:57.042921 │ 100 trying -- your call is │ │ │ig +0.009837 │ <────────────────────────── │ │ │es 16:30:57.052758 │ │ INVITE (SDP) │ │t- +0.001506 │ │ ──────────────────────────> │ │au 16:30:57.054264 │ │ 100 Trying │ │th +0.001558 │ │ <────────────────────────── │ │:5 16:30:57.055822 │ │ 200 OK (SDP) │ │06 +0.000664 │ │ <────────────────────────── │ │0 16:30:57.056486 │ 200 OK (SDP) │ │ │SI +0.000854 │ <────────────────────────── │ │ │P/ 16:30:57.057340 │ ACK │ │ │2. +0.000447 │ ──────────────────────────> │ │ │0 16:30:57.057787 │ │ ACK │ │Vi +0.279666 │ │ ──────────────────────────> │ │a: 16:30:57.337453 │ 407 Proxy Authentication R │ │ │ S +0.224273 │ <────────────────────────── │ │ │IP 16:30:57.561726 │ │ BYE │ │/2 +0.001295 │ │ <────────────────────────── │ │.0 16:30:57.563021 │ BYE │ │ │/U +0.002180 │ <────────────────────────── │ │ │DP 16:30:57.565201 │ 200 OK Now │ │ │ 1 +0.000327 │ ──────────────────────────> │ │ │72 16:30:57.565528 │ │ 200 OK Now │ │.2 +0.771759 │ │ ──────────────────────────> │ │4. 16:30:58.337287 │ 407 Proxy Authentication R │ │ │0. +2.000408 │ <────────────────────────── │ │ │9: 16:31:00.337695 │ 407 Proxy Authentication R │ │ │49 +0.000158 │ <<<──────────────────────── │ │ │68 16:31:00.337853 │ 407 Proxy Authentication R │ │ │5; │ <<<──────────────────────── │ │ │rp │ │ │ │or │ │ │ │t;
What does matter is if there is a subsequent INVITE at all. If there's not, no problem, no retransmission:
│IN 172.24.0.9:33672 172.24.0.7:5060 │VI ──────────┬───────── ──────────┬───────── │TE 16:34:56.823495 │ INVITE (SDP) │ │ s +0.001047 │ ──────────────────────────> │ │ip 16:34:56.824542 │ 100 trying -- your call is │ │:1 +0.002516 │ <────────────────────────── │ │00 16:34:56.827058 │ 407 Proxy Authentication R │ │@s +0.000351 │ <────────────────────────── │ │ip 16:34:56.827409 │ ACK │ │-p │ ──────────────────────────> │ │ro │ │ │xy
If the negative ACK were not being matched, I would think the retransmission would happen here too. It seems to happen because the subsequent INVITE keeps the old transaction alive and in its previous state somehow.
Any suggestions welcome!
-- Alex
On Dec 13, 2022, at 8:54 AM, Alex Balashov <abalashov@evaristesys.commailto:abalashov@evaristesys.com> wrote:
On Dec 13, 2022, at 3:14 AM, Daniel-Constantin Mierla <miconda@gmail.commailto:miconda@gmail.com> wrote:
change of cseq results in a different transaction, there should be two at the same time for a short interval. Try to see if debug=3 offers any hints.
Makes sense. What I'm wondering is why the ACK for the negative reply (407) isn't processed and doesn't seem to result in immediate termination of the first transaction.
This doesn't happen if I only suspend once. There is no problem in that scenario.
For clarification: do you need to do authentication two times? Second time with pv function?
No, the process is basically that I don't know whether I need to do digest authentication until a preliminary routing query happens (async) first, and if I do, then I return a 407 challenge from that transaction. I then receive a new INVITE with digest credentials, and I (async) query for the credentials-info (HA1 of password), and then I auth_check() the received digest credentials against the info. If not valid, I issue another auth challenge, and if valid, I continue with route processing (again async).
This sounds like a mess that Kamailio's async stuff wasn't really intended to support, maybe. I'm wondering if the simplest thing to seed the credentials-info into Kamailio somehow, e.g. via JSONRPC+htable, so that an async query is not required in order to obtain it dynamically. I was hoping to avoid that, but maybe there's not another way to do it?
-- Alex
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
Hi Henning,
On Dec 15, 2022, at 11:51 AM, Henning Westerholt hw@gilawa.com wrote:
Hi Alex, it might not help you much, but recently I was implementing a similar structure in one larger migration project, and it seems to work fine. I am not using any special flags for the challenge etc.. It’s basically like this (pseudo-code) route{ if no auth user -> auth_challenge() else -> http_async_query(API, AUTH) } route[AUTH] { get API result for password if API failure -> auth_challenge() else -> pv_auth_check(..) route(next steps) }
Yeah, that's more or less what I've got, except the first part.
I don't auth_challenge() every request because some requests are allowed by static IP, and I don't know whether to auth_challenge() them unless I am already in the async resume context.
I have eliminated the independent credentials query. At this point my process is more:
request_route { ...
http_async_query(API, RESUME) }
route[RESUME] { if(method == "INVITE") { if(has_auth_attrib()) { if(!pv_auth_check(...)) { auth_challenge("realm", "1"); exit; } }
# Get more routing info. http_async_query(API, RESUME2) return; } }
route[RESUME2} { t_relay() etc }
-- Alex
Well, the difference seems pretty clear. In a scenario with an auth challenge and no subsequent INVITE+credentials, the negative ACK is matched:
4(54) DEBUG: <core> [core/receive.c:389]: receive_msg(): --- received sip message - request - call-id: [01eed151-4234-4518-9a0e-9b9168f21a3f] - cseq: [288439 ACK] 4(54) DEBUG: <core> [core/receive.c:261]: ksr_evrt_pre_routing(): event route core:pre-routing not defined 4(54) DEBUG: <core> [core/receive.c:471]: receive_msg(): preparing to run routing scripts... 4(54) DEBUG: sl [sl_funcs.c:447]: sl_filter_ACK(): too late to be a local ACK! 4(54) DEBUG: <core> [core/parser/parse_hname2.c:301]: parse_sip_header_name(): parsed header name [Content-Length] type 12 4(54) DEBUG: <core> [core/parser/msg_parser.c:187]: get_hdr_field(): content_length=0 4(54) DEBUG: <core> [core/parser/msg_parser.c:91]: get_hdr_field(): found end of header 4(54) DEBUG: maxfwd [mf_funcs.c:55]: is_maxfwd_present(): max_forwards header not found! 4(54) DEBUG: siputils [checks.c:123]: has_totag(): totag found 4(54) DEBUG: rr [loose.c:108]: find_first_route(): No Route headers found 4(54) DEBUG: rr [loose.c:1006]: loose_route_mode(): There is no Route HF 4(54) DEBUG: tm [t_lookup.c:1053]: t_check_msg(): msg (0xffffa72f7088) id=14/54 global id=13/54 T start=0 4(54) DEBUG: tm [t_lookup.c:497]: t_lookup_request(): start searching: hash=42311, isACK=1 4(54) DEBUG: tm [t_lookup.c:439]: matching_3261(): RFC3261 transaction matched, tid=SG.ceb57d44-7388-4739-9a86-d44ea04d974d 4(54) DEBUG: tm [t_lookup.c:692]: t_lookup_request(): transaction found (T=0xffffa2f428a8) 4(54) DEBUG: tm [t_lookup.c:1122]: t_check_msg(): msg (0xffffa72f7088) id=14/54 global id=14/54 T end=0xffffa2f428a8 4(54) DEBUG: tm [t_reply.c:1763]: cleanup_uac_timers(): RETR/FR timers reset 4(54) DEBUG: tm [t_funcs.c:120]: put_on_wait(): put T [0xffffa2f428a8] on wait 4(54) DEBUG: <core> [core/timer.c:557]: timer_add_safe(): timer_add called on an active timer 0xffffa2f42930 (0xffffa2d05d08, 0xffffa2d05d08), flags 201 4(54) DEBUG: tm [t_funcs.c:143]: put_on_wait(): transaction 0xffffa2f428a8 already on wait
However, in a scenario with an auth challenge with subsequent INVITE+credentials, the same negative ACK is not matched to a known transaction.
2(52) DEBUG: <core> [core/receive.c:389]: receive_msg(): --- received sip message - request - call-id: [895a7051-3e0c-410a-88ea-4bad7a1c21b6] - cseq: [939189 ACK] 2(52) DEBUG: <core> [core/receive.c:261]: ksr_evrt_pre_routing(): event route core:pre-routing not defined 2(52) DEBUG: <core> [core/receive.c:471]: receive_msg(): preparing to run routing scripts... 2(52) DEBUG: sl [sl_funcs.c:447]: sl_filter_ACK(): too late to be a local ACK! 2(52) DEBUG: <core> [core/parser/parse_hname2.c:301]: parse_sip_header_name(): parsed header name [Content-Length] type 12 2(52) DEBUG: <core> [core/parser/msg_parser.c:187]: get_hdr_field(): content_length=0 2(52) DEBUG: <core> [core/parser/msg_parser.c:91]: get_hdr_field(): found end of header 2(52) DEBUG: maxfwd [mf_funcs.c:55]: is_maxfwd_present(): max_forwards header not found! 2(52) DEBUG: siputils [checks.c:123]: has_totag(): totag found 2(52) DEBUG: rr [loose.c:108]: find_first_route(): No Route headers found 2(52) DEBUG: rr [loose.c:1006]: loose_route_mode(): There is no Route HF 2(52) DEBUG: tm [t_lookup.c:1053]: t_check_msg(): msg (0xffffa72f7088) id=19/52 global id=18/52 T start=0 2(52) DEBUG: tm [t_lookup.c:497]: t_lookup_request(): start searching: hash=21251, isACK=1 2(52) DEBUG: tm [t_lookup.c:455]: matching_3261(): RFC3261 transaction matching failed - via branch [z9hG4bKSG.c52861b7-2535-4080-84f5-2819c4169843] 2(52) DEBUG: tm [t_lookup.c:675]: t_lookup_request(): no transaction found
This makes sense intuitively; the auth_challenge(), and resulting 407 challenge, should have ended the old transaction, so the negative ACK should just be absorbed.
But in that case, why does the 407 keep being retransmitted?
-- Alex
On Dec 15, 2022, at 12:00 PM, Alex Balashov abalashov@evaristesys.com wrote:
Hi Henning,
On Dec 15, 2022, at 11:51 AM, Henning Westerholt hw@gilawa.com wrote:
Hi Alex, it might not help you much, but recently I was implementing a similar structure in one larger migration project, and it seems to work fine. I am not using any special flags for the challenge etc.. It’s basically like this (pseudo-code) route{ if no auth user -> auth_challenge() else -> http_async_query(API, AUTH) } route[AUTH] { get API result for password if API failure -> auth_challenge() else -> pv_auth_check(..) route(next steps) }
Yeah, that's more or less what I've got, except the first part.
I don't auth_challenge() every request because some requests are allowed by static IP, and I don't know whether to auth_challenge() them unless I am already in the async resume context.
I have eliminated the independent credentials query. At this point my process is more:
request_route { ...
http_async_query(API, RESUME)
}
route[RESUME] { if(method == "INVITE") { if(has_auth_attrib()) { if(!pv_auth_check(...)) { auth_challenge("realm", "1"); exit; } }
# Get more routing info. http_async_query(API, RESUME2) return; }
}
route[RESUME2} { t_relay() etc }
-- Alex
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
As a test, I tried to put the auth_challenge() in the request_route before any async suspension, and in that case works fine.
The issue is definitely with the way auth_challenge() issued from _within_ an async resume route (failure_route context) bears upon transaction state.
-- Alex
On Dec 15, 2022, at 12:23 PM, Alex Balashov abalashov@evaristesys.com wrote:
Well, the difference seems pretty clear. In a scenario with an auth challenge and no subsequent INVITE+credentials, the negative ACK is matched:
4(54) DEBUG: <core> [core/receive.c:389]: receive_msg(): --- received sip message - request - call-id: [01eed151-4234-4518-9a0e-9b9168f21a3f] - cseq: [288439 ACK] 4(54) DEBUG: <core> [core/receive.c:261]: ksr_evrt_pre_routing(): event route core:pre-routing not defined 4(54) DEBUG: <core> [core/receive.c:471]: receive_msg(): preparing to run routing scripts... 4(54) DEBUG: sl [sl_funcs.c:447]: sl_filter_ACK(): too late to be a local ACK! 4(54) DEBUG: <core> [core/parser/parse_hname2.c:301]: parse_sip_header_name(): parsed header name [Content-Length] type 12 4(54) DEBUG: <core> [core/parser/msg_parser.c:187]: get_hdr_field(): content_length=0 4(54) DEBUG: <core> [core/parser/msg_parser.c:91]: get_hdr_field(): found end of header 4(54) DEBUG: maxfwd [mf_funcs.c:55]: is_maxfwd_present(): max_forwards header not found! 4(54) DEBUG: siputils [checks.c:123]: has_totag(): totag found 4(54) DEBUG: rr [loose.c:108]: find_first_route(): No Route headers found 4(54) DEBUG: rr [loose.c:1006]: loose_route_mode(): There is no Route HF 4(54) DEBUG: tm [t_lookup.c:1053]: t_check_msg(): msg (0xffffa72f7088) id=14/54 global id=13/54 T start=0 4(54) DEBUG: tm [t_lookup.c:497]: t_lookup_request(): start searching: hash=42311, isACK=1 4(54) DEBUG: tm [t_lookup.c:439]: matching_3261(): RFC3261 transaction matched, tid=SG.ceb57d44-7388-4739-9a86-d44ea04d974d 4(54) DEBUG: tm [t_lookup.c:692]: t_lookup_request(): transaction found (T=0xffffa2f428a8) 4(54) DEBUG: tm [t_lookup.c:1122]: t_check_msg(): msg (0xffffa72f7088) id=14/54 global id=14/54 T end=0xffffa2f428a8 4(54) DEBUG: tm [t_reply.c:1763]: cleanup_uac_timers(): RETR/FR timers reset 4(54) DEBUG: tm [t_funcs.c:120]: put_on_wait(): put T [0xffffa2f428a8] on wait 4(54) DEBUG: <core> [core/timer.c:557]: timer_add_safe(): timer_add called on an active timer 0xffffa2f42930 (0xffffa2d05d08, 0xffffa2d05d08), flags 201 4(54) DEBUG: tm [t_funcs.c:143]: put_on_wait(): transaction 0xffffa2f428a8 already on wait
However, in a scenario with an auth challenge with subsequent INVITE+credentials, the same negative ACK is not matched to a known transaction.
2(52) DEBUG: <core> [core/receive.c:389]: receive_msg(): --- received sip message - request - call-id: [895a7051-3e0c-410a-88ea-4bad7a1c21b6] - cseq: [939189 ACK] 2(52) DEBUG: <core> [core/receive.c:261]: ksr_evrt_pre_routing(): event route core:pre-routing not defined 2(52) DEBUG: <core> [core/receive.c:471]: receive_msg(): preparing to run routing scripts... 2(52) DEBUG: sl [sl_funcs.c:447]: sl_filter_ACK(): too late to be a local ACK! 2(52) DEBUG: <core> [core/parser/parse_hname2.c:301]: parse_sip_header_name(): parsed header name [Content-Length] type 12 2(52) DEBUG: <core> [core/parser/msg_parser.c:187]: get_hdr_field(): content_length=0 2(52) DEBUG: <core> [core/parser/msg_parser.c:91]: get_hdr_field(): found end of header 2(52) DEBUG: maxfwd [mf_funcs.c:55]: is_maxfwd_present(): max_forwards header not found! 2(52) DEBUG: siputils [checks.c:123]: has_totag(): totag found 2(52) DEBUG: rr [loose.c:108]: find_first_route(): No Route headers found 2(52) DEBUG: rr [loose.c:1006]: loose_route_mode(): There is no Route HF 2(52) DEBUG: tm [t_lookup.c:1053]: t_check_msg(): msg (0xffffa72f7088) id=19/52 global id=18/52 T start=0 2(52) DEBUG: tm [t_lookup.c:497]: t_lookup_request(): start searching: hash=21251, isACK=1 2(52) DEBUG: tm [t_lookup.c:455]: matching_3261(): RFC3261 transaction matching failed - via branch [z9hG4bKSG.c52861b7-2535-4080-84f5-2819c4169843] 2(52) DEBUG: tm [t_lookup.c:675]: t_lookup_request(): no transaction found
This makes sense intuitively; the auth_challenge(), and resulting 407 challenge, should have ended the old transaction, so the negative ACK should just be absorbed.
But in that case, why does the 407 keep being retransmitted?
-- Alex
On Dec 15, 2022, at 12:00 PM, Alex Balashov abalashov@evaristesys.com wrote:
Hi Henning,
On Dec 15, 2022, at 11:51 AM, Henning Westerholt hw@gilawa.com wrote:
Hi Alex, it might not help you much, but recently I was implementing a similar structure in one larger migration project, and it seems to work fine. I am not using any special flags for the challenge etc.. It’s basically like this (pseudo-code) route{ if no auth user -> auth_challenge() else -> http_async_query(API, AUTH) } route[AUTH] { get API result for password if API failure -> auth_challenge() else -> pv_auth_check(..) route(next steps) }
Yeah, that's more or less what I've got, except the first part.
I don't auth_challenge() every request because some requests are allowed by static IP, and I don't know whether to auth_challenge() them unless I am already in the async resume context.
I have eliminated the independent credentials query. At this point my process is more:
request_route { ...
http_async_query(API, RESUME)
}
route[RESUME] { if(method == "INVITE") { if(has_auth_attrib()) { if(!pv_auth_check(...)) { auth_challenge("realm", "1"); exit; } }
# Get more routing info. http_async_query(API, RESUME2) return; }
}
route[RESUME2} { t_relay() etc }
-- Alex
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
Adding further to this, it seems to me the real problem is that I can't use t_release() in an async resume route, because it's internally structured to take place inside a failure_route context. If I could, I think that would rid me of the first transaction after I send the challenge and call 'exit'.
On Dec 15, 2022, at 12:42 PM, Alex Balashov abalashov@evaristesys.com wrote:
As a test, I tried to put the auth_challenge() in the request_route before any async suspension, and in that case works fine.
The issue is definitely with the way auth_challenge() issued from _within_ an async resume route (failure_route context) bears upon transaction state.
-- Alex
On Dec 15, 2022, at 12:23 PM, Alex Balashov abalashov@evaristesys.com wrote:
Well, the difference seems pretty clear. In a scenario with an auth challenge and no subsequent INVITE+credentials, the negative ACK is matched:
4(54) DEBUG: <core> [core/receive.c:389]: receive_msg(): --- received sip message - request - call-id: [01eed151-4234-4518-9a0e-9b9168f21a3f] - cseq: [288439 ACK] 4(54) DEBUG: <core> [core/receive.c:261]: ksr_evrt_pre_routing(): event route core:pre-routing not defined 4(54) DEBUG: <core> [core/receive.c:471]: receive_msg(): preparing to run routing scripts... 4(54) DEBUG: sl [sl_funcs.c:447]: sl_filter_ACK(): too late to be a local ACK! 4(54) DEBUG: <core> [core/parser/parse_hname2.c:301]: parse_sip_header_name(): parsed header name [Content-Length] type 12 4(54) DEBUG: <core> [core/parser/msg_parser.c:187]: get_hdr_field(): content_length=0 4(54) DEBUG: <core> [core/parser/msg_parser.c:91]: get_hdr_field(): found end of header 4(54) DEBUG: maxfwd [mf_funcs.c:55]: is_maxfwd_present(): max_forwards header not found! 4(54) DEBUG: siputils [checks.c:123]: has_totag(): totag found 4(54) DEBUG: rr [loose.c:108]: find_first_route(): No Route headers found 4(54) DEBUG: rr [loose.c:1006]: loose_route_mode(): There is no Route HF 4(54) DEBUG: tm [t_lookup.c:1053]: t_check_msg(): msg (0xffffa72f7088) id=14/54 global id=13/54 T start=0 4(54) DEBUG: tm [t_lookup.c:497]: t_lookup_request(): start searching: hash=42311, isACK=1 4(54) DEBUG: tm [t_lookup.c:439]: matching_3261(): RFC3261 transaction matched, tid=SG.ceb57d44-7388-4739-9a86-d44ea04d974d 4(54) DEBUG: tm [t_lookup.c:692]: t_lookup_request(): transaction found (T=0xffffa2f428a8) 4(54) DEBUG: tm [t_lookup.c:1122]: t_check_msg(): msg (0xffffa72f7088) id=14/54 global id=14/54 T end=0xffffa2f428a8 4(54) DEBUG: tm [t_reply.c:1763]: cleanup_uac_timers(): RETR/FR timers reset 4(54) DEBUG: tm [t_funcs.c:120]: put_on_wait(): put T [0xffffa2f428a8] on wait 4(54) DEBUG: <core> [core/timer.c:557]: timer_add_safe(): timer_add called on an active timer 0xffffa2f42930 (0xffffa2d05d08, 0xffffa2d05d08), flags 201 4(54) DEBUG: tm [t_funcs.c:143]: put_on_wait(): transaction 0xffffa2f428a8 already on wait
However, in a scenario with an auth challenge with subsequent INVITE+credentials, the same negative ACK is not matched to a known transaction.
2(52) DEBUG: <core> [core/receive.c:389]: receive_msg(): --- received sip message - request - call-id: [895a7051-3e0c-410a-88ea-4bad7a1c21b6] - cseq: [939189 ACK] 2(52) DEBUG: <core> [core/receive.c:261]: ksr_evrt_pre_routing(): event route core:pre-routing not defined 2(52) DEBUG: <core> [core/receive.c:471]: receive_msg(): preparing to run routing scripts... 2(52) DEBUG: sl [sl_funcs.c:447]: sl_filter_ACK(): too late to be a local ACK! 2(52) DEBUG: <core> [core/parser/parse_hname2.c:301]: parse_sip_header_name(): parsed header name [Content-Length] type 12 2(52) DEBUG: <core> [core/parser/msg_parser.c:187]: get_hdr_field(): content_length=0 2(52) DEBUG: <core> [core/parser/msg_parser.c:91]: get_hdr_field(): found end of header 2(52) DEBUG: maxfwd [mf_funcs.c:55]: is_maxfwd_present(): max_forwards header not found! 2(52) DEBUG: siputils [checks.c:123]: has_totag(): totag found 2(52) DEBUG: rr [loose.c:108]: find_first_route(): No Route headers found 2(52) DEBUG: rr [loose.c:1006]: loose_route_mode(): There is no Route HF 2(52) DEBUG: tm [t_lookup.c:1053]: t_check_msg(): msg (0xffffa72f7088) id=19/52 global id=18/52 T start=0 2(52) DEBUG: tm [t_lookup.c:497]: t_lookup_request(): start searching: hash=21251, isACK=1 2(52) DEBUG: tm [t_lookup.c:455]: matching_3261(): RFC3261 transaction matching failed - via branch [z9hG4bKSG.c52861b7-2535-4080-84f5-2819c4169843] 2(52) DEBUG: tm [t_lookup.c:675]: t_lookup_request(): no transaction found
This makes sense intuitively; the auth_challenge(), and resulting 407 challenge, should have ended the old transaction, so the negative ACK should just be absorbed.
But in that case, why does the 407 keep being retransmitted?
-- Alex
On Dec 15, 2022, at 12:00 PM, Alex Balashov abalashov@evaristesys.com wrote:
Hi Henning,
On Dec 15, 2022, at 11:51 AM, Henning Westerholt hw@gilawa.com wrote:
Hi Alex, it might not help you much, but recently I was implementing a similar structure in one larger migration project, and it seems to work fine. I am not using any special flags for the challenge etc.. It’s basically like this (pseudo-code) route{ if no auth user -> auth_challenge() else -> http_async_query(API, AUTH) } route[AUTH] { get API result for password if API failure -> auth_challenge() else -> pv_auth_check(..) route(next steps) }
Yeah, that's more or less what I've got, except the first part.
I don't auth_challenge() every request because some requests are allowed by static IP, and I don't know whether to auth_challenge() them unless I am already in the async resume context.
I have eliminated the independent credentials query. At this point my process is more:
request_route { ...
http_async_query(API, RESUME) }
route[RESUME] { if(method == "INVITE") { if(has_auth_attrib()) { if(!pv_auth_check(...)) { auth_challenge("realm", "1"); exit; } }
# Get more routing info. http_async_query(API, RESUME2) return;
} }
route[RESUME2} { t_relay() etc }
-- Alex
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
Setting tm.wt_timer to a very low value (e.g. 200 ms) does provide a hack around this behaviour, but it doesn't seem to me that this is the correct solution.
│AC 172.24.0.9:39777 172.24.0.7:5060 │K ──────────┬───────── ──────────┬───────── │si 19:38:44.386913 │ INVITE (SDP) │ │p: +0.001550 │ ──────────────────────────> │ │10 19:38:44.388463 │ 100 trying -- your call is │ │0@ +0.003336 │ <────────────────────────── │ │si 19:38:44.391799 │ 407 Proxy Authentication R │ │p- +0.000234 │ <────────────────────────── │ │pr 19:38:44.392033 │ ACK │ │ox +0.201070 │ ──────────────────────────> │ │y- 19:38:44.593103 │ INVITE (SDP) │ │di +0.004226 │ ──────────────────────────> │ │ge 19:38:44.597329 │ 100 trying -- your call is │ │st +0.003063 │ <────────────────────────── │ │-a 19:38:44.600392 │ 407 Proxy Authentication R │ │ut +0.000489 │ <────────────────────────── │ │h: 19:38:44.600881 │ ACK │ │50 │ ──────────────────────────> │ │60 │ │ │ S
The real question is why the negative ACK for the first transaction doesn't seem to be having the intended effect in this scenario.
-- Alex
On Dec 15, 2022, at 2:21 PM, Alex Balashov abalashov@evaristesys.com wrote:
Adding further to this, it seems to me the real problem is that I can't use t_release() in an async resume route, because it's internally structured to take place inside a failure_route context. If I could, I think that would rid me of the first transaction after I send the challenge and call 'exit'.
On Dec 15, 2022, at 12:42 PM, Alex Balashov abalashov@evaristesys.com wrote:
As a test, I tried to put the auth_challenge() in the request_route before any async suspension, and in that case works fine.
The issue is definitely with the way auth_challenge() issued from _within_ an async resume route (failure_route context) bears upon transaction state.
-- Alex
On Dec 15, 2022, at 12:23 PM, Alex Balashov abalashov@evaristesys.com wrote:
Well, the difference seems pretty clear. In a scenario with an auth challenge and no subsequent INVITE+credentials, the negative ACK is matched:
4(54) DEBUG: <core> [core/receive.c:389]: receive_msg(): --- received sip message - request - call-id: [01eed151-4234-4518-9a0e-9b9168f21a3f] - cseq: [288439 ACK] 4(54) DEBUG: <core> [core/receive.c:261]: ksr_evrt_pre_routing(): event route core:pre-routing not defined 4(54) DEBUG: <core> [core/receive.c:471]: receive_msg(): preparing to run routing scripts... 4(54) DEBUG: sl [sl_funcs.c:447]: sl_filter_ACK(): too late to be a local ACK! 4(54) DEBUG: <core> [core/parser/parse_hname2.c:301]: parse_sip_header_name(): parsed header name [Content-Length] type 12 4(54) DEBUG: <core> [core/parser/msg_parser.c:187]: get_hdr_field(): content_length=0 4(54) DEBUG: <core> [core/parser/msg_parser.c:91]: get_hdr_field(): found end of header 4(54) DEBUG: maxfwd [mf_funcs.c:55]: is_maxfwd_present(): max_forwards header not found! 4(54) DEBUG: siputils [checks.c:123]: has_totag(): totag found 4(54) DEBUG: rr [loose.c:108]: find_first_route(): No Route headers found 4(54) DEBUG: rr [loose.c:1006]: loose_route_mode(): There is no Route HF 4(54) DEBUG: tm [t_lookup.c:1053]: t_check_msg(): msg (0xffffa72f7088) id=14/54 global id=13/54 T start=0 4(54) DEBUG: tm [t_lookup.c:497]: t_lookup_request(): start searching: hash=42311, isACK=1 4(54) DEBUG: tm [t_lookup.c:439]: matching_3261(): RFC3261 transaction matched, tid=SG.ceb57d44-7388-4739-9a86-d44ea04d974d 4(54) DEBUG: tm [t_lookup.c:692]: t_lookup_request(): transaction found (T=0xffffa2f428a8) 4(54) DEBUG: tm [t_lookup.c:1122]: t_check_msg(): msg (0xffffa72f7088) id=14/54 global id=14/54 T end=0xffffa2f428a8 4(54) DEBUG: tm [t_reply.c:1763]: cleanup_uac_timers(): RETR/FR timers reset 4(54) DEBUG: tm [t_funcs.c:120]: put_on_wait(): put T [0xffffa2f428a8] on wait 4(54) DEBUG: <core> [core/timer.c:557]: timer_add_safe(): timer_add called on an active timer 0xffffa2f42930 (0xffffa2d05d08, 0xffffa2d05d08), flags 201 4(54) DEBUG: tm [t_funcs.c:143]: put_on_wait(): transaction 0xffffa2f428a8 already on wait
However, in a scenario with an auth challenge with subsequent INVITE+credentials, the same negative ACK is not matched to a known transaction.
2(52) DEBUG: <core> [core/receive.c:389]: receive_msg(): --- received sip message - request - call-id: [895a7051-3e0c-410a-88ea-4bad7a1c21b6] - cseq: [939189 ACK] 2(52) DEBUG: <core> [core/receive.c:261]: ksr_evrt_pre_routing(): event route core:pre-routing not defined 2(52) DEBUG: <core> [core/receive.c:471]: receive_msg(): preparing to run routing scripts... 2(52) DEBUG: sl [sl_funcs.c:447]: sl_filter_ACK(): too late to be a local ACK! 2(52) DEBUG: <core> [core/parser/parse_hname2.c:301]: parse_sip_header_name(): parsed header name [Content-Length] type 12 2(52) DEBUG: <core> [core/parser/msg_parser.c:187]: get_hdr_field(): content_length=0 2(52) DEBUG: <core> [core/parser/msg_parser.c:91]: get_hdr_field(): found end of header 2(52) DEBUG: maxfwd [mf_funcs.c:55]: is_maxfwd_present(): max_forwards header not found! 2(52) DEBUG: siputils [checks.c:123]: has_totag(): totag found 2(52) DEBUG: rr [loose.c:108]: find_first_route(): No Route headers found 2(52) DEBUG: rr [loose.c:1006]: loose_route_mode(): There is no Route HF 2(52) DEBUG: tm [t_lookup.c:1053]: t_check_msg(): msg (0xffffa72f7088) id=19/52 global id=18/52 T start=0 2(52) DEBUG: tm [t_lookup.c:497]: t_lookup_request(): start searching: hash=21251, isACK=1 2(52) DEBUG: tm [t_lookup.c:455]: matching_3261(): RFC3261 transaction matching failed - via branch [z9hG4bKSG.c52861b7-2535-4080-84f5-2819c4169843] 2(52) DEBUG: tm [t_lookup.c:675]: t_lookup_request(): no transaction found
This makes sense intuitively; the auth_challenge(), and resulting 407 challenge, should have ended the old transaction, so the negative ACK should just be absorbed.
But in that case, why does the 407 keep being retransmitted?
-- Alex
On Dec 15, 2022, at 12:00 PM, Alex Balashov abalashov@evaristesys.com wrote:
Hi Henning,
On Dec 15, 2022, at 11:51 AM, Henning Westerholt hw@gilawa.com wrote:
Hi Alex, it might not help you much, but recently I was implementing a similar structure in one larger migration project, and it seems to work fine. I am not using any special flags for the challenge etc.. It’s basically like this (pseudo-code) route{ if no auth user -> auth_challenge() else -> http_async_query(API, AUTH) } route[AUTH] { get API result for password if API failure -> auth_challenge() else -> pv_auth_check(..) route(next steps) }
Yeah, that's more or less what I've got, except the first part.
I don't auth_challenge() every request because some requests are allowed by static IP, and I don't know whether to auth_challenge() them unless I am already in the async resume context.
I have eliminated the independent credentials query. At this point my process is more:
request_route { ...
http_async_query(API, RESUME) }
route[RESUME] { if(method == "INVITE") { if(has_auth_attrib()) { if(!pv_auth_check(...)) { auth_challenge("realm", "1"); exit; } }
# Get more routing info. http_async_query(API, RESUME2) return;
} }
route[RESUME2} { t_relay() etc }
-- Alex
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
One more thing, and I apologise profusely for the spam:
This is not caused by immediate re-suspension of the transaction upon successful authorisation of new INVITE+credentials. Even if I attempt to complete the onward routing in the same route which does the authentication, without any further TM suspend/continue, I get the 407 retransmissions from the previous transaction, e.g.
route[RESUME] { pv_auth_check() and the rest
$ru = "sip:asterisk-receiver:5060"; t_on_reply("MAIN_REPLY");
if(!t_relay()) t_reply("500", "Internal server error");
exit; }
I can't say for sure what's going on, not knowing TM internals.
-- Alex
On Dec 15, 2022, at 2:40 PM, Alex Balashov abalashov@evaristesys.com wrote:
Setting tm.wt_timer to a very low value (e.g. 200 ms) does provide a hack around this behaviour, but it doesn't seem to me that this is the correct solution.
│AC 172.24.0.9:39777 172.24.0.7:5060 │K ──────────┬───────── ──────────┬───────── │si
19:38:44.386913 │ INVITE (SDP) │ │p: +0.001550 │ ──────────────────────────> │ │10 19:38:44.388463 │ 100 trying -- your call is │ │0@ +0.003336 │ <────────────────────────── │ │si 19:38:44.391799 │ 407 Proxy Authentication R │ │p- +0.000234 │ <────────────────────────── │ │pr 19:38:44.392033 │ ACK │ │ox +0.201070 │ ──────────────────────────> │ │y- 19:38:44.593103 │ INVITE (SDP) │ │di +0.004226 │ ──────────────────────────> │ │ge 19:38:44.597329 │ 100 trying -- your call is │ │st +0.003063 │ <────────────────────────── │ │-a 19:38:44.600392 │ 407 Proxy Authentication R │ │ut +0.000489 │ <────────────────────────── │ │h: 19:38:44.600881 │ ACK │ │50 │ ──────────────────────────> │ │60 │ │ │ S
The real question is why the negative ACK for the first transaction doesn't seem to be having the intended effect in this scenario.
-- Alex
On Dec 15, 2022, at 2:21 PM, Alex Balashov abalashov@evaristesys.com wrote:
Adding further to this, it seems to me the real problem is that I can't use t_release() in an async resume route, because it's internally structured to take place inside a failure_route context. If I could, I think that would rid me of the first transaction after I send the challenge and call 'exit'.
On Dec 15, 2022, at 12:42 PM, Alex Balashov abalashov@evaristesys.com wrote:
As a test, I tried to put the auth_challenge() in the request_route before any async suspension, and in that case works fine.
The issue is definitely with the way auth_challenge() issued from _within_ an async resume route (failure_route context) bears upon transaction state.
-- Alex
On Dec 15, 2022, at 12:23 PM, Alex Balashov abalashov@evaristesys.com wrote:
Well, the difference seems pretty clear. In a scenario with an auth challenge and no subsequent INVITE+credentials, the negative ACK is matched:
4(54) DEBUG: <core> [core/receive.c:389]: receive_msg(): --- received sip message - request - call-id: [01eed151-4234-4518-9a0e-9b9168f21a3f] - cseq: [288439 ACK] 4(54) DEBUG: <core> [core/receive.c:261]: ksr_evrt_pre_routing(): event route core:pre-routing not defined 4(54) DEBUG: <core> [core/receive.c:471]: receive_msg(): preparing to run routing scripts... 4(54) DEBUG: sl [sl_funcs.c:447]: sl_filter_ACK(): too late to be a local ACK! 4(54) DEBUG: <core> [core/parser/parse_hname2.c:301]: parse_sip_header_name(): parsed header name [Content-Length] type 12 4(54) DEBUG: <core> [core/parser/msg_parser.c:187]: get_hdr_field(): content_length=0 4(54) DEBUG: <core> [core/parser/msg_parser.c:91]: get_hdr_field(): found end of header 4(54) DEBUG: maxfwd [mf_funcs.c:55]: is_maxfwd_present(): max_forwards header not found! 4(54) DEBUG: siputils [checks.c:123]: has_totag(): totag found 4(54) DEBUG: rr [loose.c:108]: find_first_route(): No Route headers found 4(54) DEBUG: rr [loose.c:1006]: loose_route_mode(): There is no Route HF 4(54) DEBUG: tm [t_lookup.c:1053]: t_check_msg(): msg (0xffffa72f7088) id=14/54 global id=13/54 T start=0 4(54) DEBUG: tm [t_lookup.c:497]: t_lookup_request(): start searching: hash=42311, isACK=1 4(54) DEBUG: tm [t_lookup.c:439]: matching_3261(): RFC3261 transaction matched, tid=SG.ceb57d44-7388-4739-9a86-d44ea04d974d 4(54) DEBUG: tm [t_lookup.c:692]: t_lookup_request(): transaction found (T=0xffffa2f428a8) 4(54) DEBUG: tm [t_lookup.c:1122]: t_check_msg(): msg (0xffffa72f7088) id=14/54 global id=14/54 T end=0xffffa2f428a8 4(54) DEBUG: tm [t_reply.c:1763]: cleanup_uac_timers(): RETR/FR timers reset 4(54) DEBUG: tm [t_funcs.c:120]: put_on_wait(): put T [0xffffa2f428a8] on wait 4(54) DEBUG: <core> [core/timer.c:557]: timer_add_safe(): timer_add called on an active timer 0xffffa2f42930 (0xffffa2d05d08, 0xffffa2d05d08), flags 201 4(54) DEBUG: tm [t_funcs.c:143]: put_on_wait(): transaction 0xffffa2f428a8 already on wait
However, in a scenario with an auth challenge with subsequent INVITE+credentials, the same negative ACK is not matched to a known transaction.
2(52) DEBUG: <core> [core/receive.c:389]: receive_msg(): --- received sip message - request - call-id: [895a7051-3e0c-410a-88ea-4bad7a1c21b6] - cseq: [939189 ACK] 2(52) DEBUG: <core> [core/receive.c:261]: ksr_evrt_pre_routing(): event route core:pre-routing not defined 2(52) DEBUG: <core> [core/receive.c:471]: receive_msg(): preparing to run routing scripts... 2(52) DEBUG: sl [sl_funcs.c:447]: sl_filter_ACK(): too late to be a local ACK! 2(52) DEBUG: <core> [core/parser/parse_hname2.c:301]: parse_sip_header_name(): parsed header name [Content-Length] type 12 2(52) DEBUG: <core> [core/parser/msg_parser.c:187]: get_hdr_field(): content_length=0 2(52) DEBUG: <core> [core/parser/msg_parser.c:91]: get_hdr_field(): found end of header 2(52) DEBUG: maxfwd [mf_funcs.c:55]: is_maxfwd_present(): max_forwards header not found! 2(52) DEBUG: siputils [checks.c:123]: has_totag(): totag found 2(52) DEBUG: rr [loose.c:108]: find_first_route(): No Route headers found 2(52) DEBUG: rr [loose.c:1006]: loose_route_mode(): There is no Route HF 2(52) DEBUG: tm [t_lookup.c:1053]: t_check_msg(): msg (0xffffa72f7088) id=19/52 global id=18/52 T start=0 2(52) DEBUG: tm [t_lookup.c:497]: t_lookup_request(): start searching: hash=21251, isACK=1 2(52) DEBUG: tm [t_lookup.c:455]: matching_3261(): RFC3261 transaction matching failed - via branch [z9hG4bKSG.c52861b7-2535-4080-84f5-2819c4169843] 2(52) DEBUG: tm [t_lookup.c:675]: t_lookup_request(): no transaction found
This makes sense intuitively; the auth_challenge(), and resulting 407 challenge, should have ended the old transaction, so the negative ACK should just be absorbed.
But in that case, why does the 407 keep being retransmitted?
-- Alex
On Dec 15, 2022, at 12:00 PM, Alex Balashov abalashov@evaristesys.com wrote:
Hi Henning,
On Dec 15, 2022, at 11:51 AM, Henning Westerholt hw@gilawa.com wrote:
Hi Alex, it might not help you much, but recently I was implementing a similar structure in one larger migration project, and it seems to work fine. I am not using any special flags for the challenge etc.. It’s basically like this (pseudo-code) route{ if no auth user -> auth_challenge() else -> http_async_query(API, AUTH) } route[AUTH] { get API result for password if API failure -> auth_challenge() else -> pv_auth_check(..) route(next steps) }
Yeah, that's more or less what I've got, except the first part.
I don't auth_challenge() every request because some requests are allowed by static IP, and I don't know whether to auth_challenge() them unless I am already in the async resume context.
I have eliminated the independent credentials query. At this point my process is more:
request_route { ...
http_async_query(API, RESUME) }
route[RESUME] { if(method == "INVITE") { if(has_auth_attrib()) { if(!pv_auth_check(...)) { auth_challenge("realm", "1"); exit; } }
# Get more routing info. http_async_query(API, RESUME2) return;
} }
route[RESUME2} { t_relay() etc }
-- Alex
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
Hi Alex,
Thanks for sharing more insights about that. Yes, indeed hard to say why its happens without digging into TM internals.
Does this also happens e.g. if you just create a reply with send_reply/t_reply, and not with the auth_challenge()? If it’s a generic issue, it might be sensible to create an issue about it to at least document it in a structure way.
Cheers,
Henning
From: Alex Balashov abalashov@evaristesys.com Sent: Thursday, December 15, 2022 9:03 PM To: Kamailio (SER) - Users Mailing List sr-users@lists.kamailio.org Subject: [SR-Users] Re: auth_challenge() and async
One more thing, and I apologise profusely for the spam:
This is not caused by immediate re-suspension of the transaction upon successful authorisation of new INVITE+credentials. Even if I attempt to complete the onward routing in the same route which does the authentication, without any further TM suspend/continue, I get the 407 retransmissions from the previous transaction, e.g.
route[RESUME] { pv_auth_check() and the rest
$ru = "sip:asterisk-receiver:5060"; t_on_reply("MAIN_REPLY");
if(!t_relay()) t_reply("500", "Internal server error");
exit; }
I can't say for sure what's going on, not knowing TM internals.
-- Alex
On Dec 15, 2022, at 2:40 PM, Alex Balashov <abalashov@evaristesys.commailto:abalashov@evaristesys.com> wrote:
Setting tm.wt_timer to a very low value (e.g. 200 ms) does provide a hack around this behaviour, but it doesn't seem to me that this is the correct solution.
│AC 172.24.0.9:39777 172.24.0.7:5060 │K ──────────┬───────── ──────────┬───────── │si 19:38:44.386913 │ INVITE (SDP) │ │p: +0.001550 │ ──────────────────────────> │ │10 19:38:44.388463 │ 100 trying -- your call is │ │0@ +0.003336 │ <────────────────────────── │ │si 19:38:44.391799 │ 407 Proxy Authentication R │ │p- +0.000234 │ <────────────────────────── │ │pr 19:38:44.392033 │ ACK │ │ox +0.201070 │ ──────────────────────────> │ │y- 19:38:44.593103 │ INVITE (SDP) │ │di +0.004226 │ ──────────────────────────> │ │ge 19:38:44.597329 │ 100 trying -- your call is │ │st +0.003063 │ <────────────────────────── │ │-a 19:38:44.600392 │ 407 Proxy Authentication R │ │ut +0.000489 │ <────────────────────────── │ │h: 19:38:44.600881 │ ACK │ │50 │ ──────────────────────────> │ │60 │ │ │ S
The real question is why the negative ACK for the first transaction doesn't seem to be having the intended effect in this scenario.
-- Alex
On Dec 15, 2022, at 2:21 PM, Alex Balashov <abalashov@evaristesys.commailto:abalashov@evaristesys.com> wrote:
Adding further to this, it seems to me the real problem is that I can't use t_release() in an async resume route, because it's internally structured to take place inside a failure_route context. If I could, I think that would rid me of the first transaction after I send the challenge and call 'exit'.
On Dec 15, 2022, at 12:42 PM, Alex Balashov <abalashov@evaristesys.commailto:abalashov@evaristesys.com> wrote:
As a test, I tried to put the auth_challenge() in the request_route before any async suspension, and in that case works fine.
The issue is definitely with the way auth_challenge() issued from _within_ an async resume route (failure_route context) bears upon transaction state.
-- Alex
On Dec 15, 2022, at 12:23 PM, Alex Balashov <abalashov@evaristesys.commailto:abalashov@evaristesys.com> wrote:
Well, the difference seems pretty clear. In a scenario with an auth challenge and no subsequent INVITE+credentials, the negative ACK is matched:
4(54) DEBUG: <core> [core/receive.c:389]: receive_msg(): --- received sip message - request - call-id: [01eed151-4234-4518-9a0e-9b9168f21a3f] - cseq: [288439 ACK] 4(54) DEBUG: <core> [core/receive.c:261]: ksr_evrt_pre_routing(): event route core:pre-routing not defined 4(54) DEBUG: <core> [core/receive.c:471]: receive_msg(): preparing to run routing scripts... 4(54) DEBUG: sl [sl_funcs.c:447]: sl_filter_ACK(): too late to be a local ACK! 4(54) DEBUG: <core> [core/parser/parse_hname2.c:301]: parse_sip_header_name(): parsed header name [Content-Length] type 12 4(54) DEBUG: <core> [core/parser/msg_parser.c:187]: get_hdr_field(): content_length=0 4(54) DEBUG: <core> [core/parser/msg_parser.c:91]: get_hdr_field(): found end of header 4(54) DEBUG: maxfwd [mf_funcs.c:55]: is_maxfwd_present(): max_forwards header not found! 4(54) DEBUG: siputils [checks.c:123]: has_totag(): totag found 4(54) DEBUG: rr [loose.c:108]: find_first_route(): No Route headers found 4(54) DEBUG: rr [loose.c:1006]: loose_route_mode(): There is no Route HF 4(54) DEBUG: tm [t_lookup.c:1053]: t_check_msg(): msg (0xffffa72f7088) id=14/54 global id=13/54 T start=0 4(54) DEBUG: tm [t_lookup.c:497]: t_lookup_request(): start searching: hash=42311, isACK=1 4(54) DEBUG: tm [t_lookup.c:439]: matching_3261(): RFC3261 transaction matched, tid=SG.ceb57d44-7388-4739-9a86-d44ea04d974d 4(54) DEBUG: tm [t_lookup.c:692]: t_lookup_request(): transaction found (T=0xffffa2f428a8) 4(54) DEBUG: tm [t_lookup.c:1122]: t_check_msg(): msg (0xffffa72f7088) id=14/54 global id=14/54 T end=0xffffa2f428a8 4(54) DEBUG: tm [t_reply.c:1763]: cleanup_uac_timers(): RETR/FR timers reset 4(54) DEBUG: tm [t_funcs.c:120]: put_on_wait(): put T [0xffffa2f428a8] on wait 4(54) DEBUG: <core> [core/timer.c:557]: timer_add_safe(): timer_add called on an active timer 0xffffa2f42930 (0xffffa2d05d08, 0xffffa2d05d08), flags 201 4(54) DEBUG: tm [t_funcs.c:143]: put_on_wait(): transaction 0xffffa2f428a8 already on wait
However, in a scenario with an auth challenge with subsequent INVITE+credentials, the same negative ACK is not matched to a known transaction.
2(52) DEBUG: <core> [core/receive.c:389]: receive_msg(): --- received sip message - request - call-id: [895a7051-3e0c-410a-88ea-4bad7a1c21b6] - cseq: [939189 ACK] 2(52) DEBUG: <core> [core/receive.c:261]: ksr_evrt_pre_routing(): event route core:pre-routing not defined 2(52) DEBUG: <core> [core/receive.c:471]: receive_msg(): preparing to run routing scripts... 2(52) DEBUG: sl [sl_funcs.c:447]: sl_filter_ACK(): too late to be a local ACK! 2(52) DEBUG: <core> [core/parser/parse_hname2.c:301]: parse_sip_header_name(): parsed header name [Content-Length] type 12 2(52) DEBUG: <core> [core/parser/msg_parser.c:187]: get_hdr_field(): content_length=0 2(52) DEBUG: <core> [core/parser/msg_parser.c:91]: get_hdr_field(): found end of header 2(52) DEBUG: maxfwd [mf_funcs.c:55]: is_maxfwd_present(): max_forwards header not found! 2(52) DEBUG: siputils [checks.c:123]: has_totag(): totag found 2(52) DEBUG: rr [loose.c:108]: find_first_route(): No Route headers found 2(52) DEBUG: rr [loose.c:1006]: loose_route_mode(): There is no Route HF 2(52) DEBUG: tm [t_lookup.c:1053]: t_check_msg(): msg (0xffffa72f7088) id=19/52 global id=18/52 T start=0 2(52) DEBUG: tm [t_lookup.c:497]: t_lookup_request(): start searching: hash=21251, isACK=1 2(52) DEBUG: tm [t_lookup.c:455]: matching_3261(): RFC3261 transaction matching failed - via branch [z9hG4bKSG.c52861b7-2535-4080-84f5-2819c4169843] 2(52) DEBUG: tm [t_lookup.c:675]: t_lookup_request(): no transaction found
This makes sense intuitively; the auth_challenge(), and resulting 407 challenge, should have ended the old transaction, so the negative ACK should just be absorbed.
But in that case, why does the 407 keep being retransmitted?
-- Alex
On Dec 15, 2022, at 12:00 PM, Alex Balashov <abalashov@evaristesys.commailto:abalashov@evaristesys.com> wrote:
Hi Henning,
On Dec 15, 2022, at 11:51 AM, Henning Westerholt <hw@gilawa.commailto:hw@gilawa.com> wrote:
Hi Alex, it might not help you much, but recently I was implementing a similar structure in one larger migration project, and it seems to work fine. I am not using any special flags for the challenge etc.. It’s basically like this (pseudo-code) route{ if no auth user -> auth_challenge() else -> http_async_query(API, AUTH) } route[AUTH] { get API result for password if API failure -> auth_challenge() else -> pv_auth_check(..) route(next steps) }
Yeah, that's more or less what I've got, except the first part.
I don't auth_challenge() every request because some requests are allowed by static IP, and I don't know whether to auth_challenge() them unless I am already in the async resume context.
I have eliminated the independent credentials query. At this point my process is more:
request_route { ...
http_async_query(API, RESUME) }
route[RESUME] { if(method == "INVITE") { if(has_auth_attrib()) { if(!pv_auth_check(...)) { auth_challenge("realm", "1"); exit; } }
# Get more routing info. http_async_query(API, RESUME2) return; } }
route[RESUME2} { t_relay() etc }
-- Alex
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
On Dec 16, 2022, at 3:40 AM, Henning Westerholt hw@gilawa.com wrote:
Does this also happens e.g. if you just create a reply with send_reply/t_reply, and not with the auth_challenge()?
Yes, I did think to try that, and the problem still happens.
Sorry, I just didn't want to add more spam to the thread. :-)
-- Alex
One other data point I can add is that the problem is independent of any particular module's way of suspending the transaction, though of course in hindsight this is obvious.
That is to say, just a manual t_suspend() will trigger the issue, no need to use `http_async_client` or any other module offering async operation ...
Hi Alex,
Thanks. As said, maybe it makes sense to create an issue about to document it e.g., in the tm docs.
Cheers,
Henning
But what exactly shall we document?
"Don't suspend a transaction and do an auth challenge + exit from the resume route unless you want the first transaction to be drawn out of wait state by a rapid subsequent INVITE, despite prior receipt of a negative ACK for the challenge?" :-)
-- Alex
On Dec 16, 2022, at 6:36 AM, Henning Westerholt hw@gilawa.com wrote:
Hi Alex,
Thanks. As said, maybe it makes sense to create an issue about to document it e.g., in the tm docs.
Cheers,
Henning
-- Henning Westerholt - https://skalatan.de/blog/ Kamailio services - https://gilawa.com
-----Original Message----- From: Alex Balashov abalashov@evaristesys.com Sent: Friday, December 16, 2022 11:38 AM To: Kamailio (SER) - Users Mailing List sr-users@lists.kamailio.org Subject: [SR-Users] Re: auth_challenge() and async
One other data point I can add is that the problem is independent of any particular module's way of suspending the transaction, though of course in hindsight this is obvious.
That is to say, just a manual t_suspend() will trigger the issue, no need to use `http_async_client` or any other module offering async operation ...
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
Kamailio - Users Mailing List - Non Commercial Discussions To unsubscribe send an email to sr-users-leave@lists.kamailio.org Important: keep the mailing list in the recipients, do not reply only to the sender! Edit mailing list options or unsubscribe: __________________________________________________________ Kamailio - Users Mailing List - Non Commercial Discussions To unsubscribe send an email to sr-users-leave@lists.kamailio.org Important: keep the mailing list in the recipients, do not reply only to the sender! Edit mailing list options or unsubscribe:
Just to conclude this, I have worked around it by setting tm.wt_timer to about ~300 ms, which is low enough to shuffle the old transaction off before the retransmissions ad nauseum can start.
But I don't think this is the ideal solution to this problem.
-- Alex
On Dec 16, 2022, at 9:09 AM, Alex Balashov abalashov@evaristesys.com wrote:
But what exactly shall we document?
"Don't suspend a transaction and do an auth challenge + exit from the resume route unless you want the first transaction to be drawn out of wait state by a rapid subsequent INVITE, despite prior receipt of a negative ACK for the challenge?" :-)
-- Alex
On Dec 16, 2022, at 6:36 AM, Henning Westerholt hw@gilawa.com wrote:
Hi Alex,
Thanks. As said, maybe it makes sense to create an issue about to document it e.g., in the tm docs.
Cheers,
Henning
-- Henning Westerholt - https://skalatan.de/blog/ Kamailio services - https://gilawa.com
-----Original Message----- From: Alex Balashov abalashov@evaristesys.com Sent: Friday, December 16, 2022 11:38 AM To: Kamailio (SER) - Users Mailing List sr-users@lists.kamailio.org Subject: [SR-Users] Re: auth_challenge() and async
One other data point I can add is that the problem is independent of any particular module's way of suspending the transaction, though of course in hindsight this is obvious.
That is to say, just a manual t_suspend() will trigger the issue, no need to use `http_async_client` or any other module offering async operation ...
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/
Kamailio - Users Mailing List - Non Commercial Discussions To unsubscribe send an email to sr-users-leave@lists.kamailio.org Important: keep the mailing list in the recipients, do not reply only to the sender! Edit mailing list options or unsubscribe: __________________________________________________________ Kamailio - Users Mailing List - Non Commercial Discussions To unsubscribe send an email to sr-users-leave@lists.kamailio.org Important: keep the mailing list in the recipients, do not reply only to the sender! Edit mailing list options or unsubscribe:
-- Alex Balashov | Principal | Evariste Systems LLC
Tel: +1-706-510-6800 / +1-800-250-5920 (toll-free) Web: http://www.evaristesys.com/, http://www.csrpswitch.com/