Upon reading that chan_pjsip supports multiple AOR’s such that several devices can act as one endpoint you may think that’s a neat feature. All you need to do is use the PJSIP_DIAL_CONTACTS dialplan function to create the Dial application’s dial string to call each device. Fairly simple and it works. You start to run into problems if you think that since I only need to register three devices (e.g., home, office, and mobile) for the endpoint then any other registrations should be rejected by using “max_contacts” for added security. The “max_contacts” option is not intended as a security feature. The “max_contacts”, “remove_existing”, and “rewrite_contact” chan_pjsip options interact with each other. If “max_contacts” is configured too low for the interactions with the other two options then it can cause loss of registrations.
max_contacts – Maximum number of REGISTER request contacts that can associate with an AOR object to reach an endpoint. The value does not affect the number of contacts added by the “contact” option.
remove_existing – On receiving a new REGISTER request for an AOR object, should Asterisk remove enough existing contacts not added or updated by the registration to satisfy “max_contacts”? Any removed contacts will expire the soonest. Before v13.18.0, v14.7.0, and v15.1.0 the “remove_existing” option simply removed all contacts not added or updated by a registration. See ASTERISK-27192.
rewrite_contact – On inbound SIP messages from the associated endpoint, the Contact header or an appropriate Record-Route header is changed to have the source IP address and port. The option does not affect outbound messages sent to the endpoint. The option helps servers communicate with endpoints behind NATs. The option also helps reuse reliable transport connections such as TCP and TLS.
Enabling “rewrite_contact” can increase the number of contacts you need to allow on the server side. The “rewrite_contact” option registers the source address as the contact address to help with NAT and reusing connection oriented transports such as TCP and TLS. However, a device refreshing a registration may register a different contact address and exceed “max_contacts”. The device could then give up attempting to register. A couple recent changes help mitigate the stale contacts caused by “rewrite_contact” registration addresses.
Since ASTERISK-27147, connection oriented transports such as TCP and TLS are monitored for when the transport gets disconnected or Asterisk is restarted.
On the server side (res_pjsip_registrar.so), registered contacts associated with connection oriented transports immediately remove themselves when the transport disconnects or Asterisk restarts. Those contacts became invalid. There are a few benefits to immediately removing these invalid contacts. The first is that the server cannot use the invalid contact to send requests. The second is that the endpoint status can become unavailable immediately. The third is that the client may not be able to register if the invalid contact is still present.
On the client side (res_pjsip_outbound_registration.so), the transport disconnection or Asterisk restart causes the client to immediately re-register with the server. The immediate re-registration minimizes the time that the client is unreachable.
Removing connection oriented contacts when the transport is disconnected or Asterisk restarts is great but UDP needs a little more help. Since ASTERISK-27192, the “remove_existing” option can help by removing the soonest to expire contact(s) over “max_contacts”. The removed contact is likely the old “rewrite_contact” contact source address being refreshed.
The “max_contacts” setting has three types of values that are useful.
- Setting to zero disables incoming registrations.
- Setting to one with “remove_existing” set to yes reproduces the chan_sip behavior of registration contacts.
- Setting to at least twice the number of devices desired for the endpoint should give enough headroom to avoid unexpected registration loss.