[OpenSIPS-Users] Possible memory leak related to AVPs

Mickael Marrache mickaelmarrache at gmail.com
Sun Aug 2 12:12:15 CEST 2015


Hi Razvan,

I have some news.

It happens for the following scenario:

1. For first branch, the branch route is executed therefore I can see the
branch AVPs are created by our module.
2. The first branch fails and we do a second attempt to a different
destination. So a second branch is created, the branch route is executed
and new branch AVPs are created. However, unlike the first branch, we
decide to discard the branch by calling the drop() command (after the
branch AVPs have been created).
3. Then, I see the following errors in the log:

opensips[30292]: ERROR:tm:t_forward_nonack: failure to add branches
opensips[30292]: ERROR:tm:w_t_relay: t_forward_nonack failed

4. After that, I can see that the branch AVPs of the first branch are
destroyed. However, the branch AVPs of the second branch are never
destroyed.

I guess that creating the branch AVPs after the block that may call drop()
will solve the problem but it is a workaround. It looks like a bug in
OpenSIPS.

Thanks,
Mickael

On Thu, Jul 16, 2015 at 5:47 PM, Răzvan Crainea <razvan at opensips.org> wrote:

> Hi, Mickael!
>
> Can you check if there are also any transactions hanged? Also, What is the
> scenario you are using? When are you populating these variables?
>
> Best regards,
>
> Răzvan Crainea
> OpenSIPS Solutionswww.opensips-solutions.com
>
> On 07/09/2015 12:17 PM, Mickael Marrache wrote:
>
> Hi Razvan,
>
> I have some news.
>
> The suspects are not regular AVPs but branch AVPs that I set in a module.
>
> Is there a specific handling for those AVPs?
>
> Here is how I use it:
>
> static str bavp_msgops_flags = str_init("$bavp(_msgops_bflags)");
> pv_spec_t bavp_msgops_flags_spec;
>
> In mod_init:
>
> if (parse_store_bavp(&bavp_msgops_flags, &bavp_msgops_flags_spec)) {
>                 LM_ERR("Fail to parse branch AVPs.\n");
>                 return -1;
> }
>
> In a command called from branch_route:
>
> b_flags.flags = PV_VAL_INT|PV_TYPE_INT;
> b_flags.ri = 0;
> if(pv_set_value(msg, &bavp_msgops_flags_spec, (int)EQ_T, &b_flags) != 0) {
>             LM_ERR("Fail to set branch flags AVP.\n");
>             return -1;
> }
>
> Sometimes, I do the following to get the branch AVP value:
>
> if (pv_get_spec_value(rpl, &bavp_msgops_flags_spec, &b_flags_val) != 0) {
>            LM_ERR("Branch AVP not found!\n");
>            return;
> }
>
>
> Thanks,
> Mickael
>
> On Thu, Jul 2, 2015 at 2:34 PM, Răzvan Crainea <razvan at opensips.org>
> wrote:
>
>> Hi, Mickael!
>>
>> Not sure why the signal is triggered. But what you could do is to
>> replicate the behavior of the function until you find the proper id.
>>
>> Best regards,
>>
>> Răzvan Crainea
>> OpenSIPS Solutionswww.opensips-solutions.com
>>
>> On 06/23/2015 05:37 PM, Mickael Marrache wrote:
>>
>> Hi Razvan,
>>
>> I'm using GDB as follows:
>>
>> (gdb) p get_avp_name_id(((struct usr_avp*)0x2ba445441948)->id)
>>
>> Program received signal SIGUSR2, User defined signal 2.
>> get_avp_name_id (id=139) at usr_avp.c:263
>> 263     {
>> The program being debugged was signaled while in a function called from
>> GDB.
>> GDB remains in the frame where the signal was received.
>> To change this behavior use "set unwindonsignal on"
>> Evaluation of the expression containing the function (get_avp_name_id)
>> will be abandoned.
>>
>> where ((struct usr_avp*)0x2ba445441948)->id gives me the AVP id.
>>
>> I expect the result to be of type str* (representing the AVP name) but it
>> looks like some signal is received while executing the function.
>>
>> Any idea?
>>
>> Thanks,
>> Mickael
>>
>> On Tue, Jun 23, 2015 at 12:08 PM, Răzvan Crainea < <razvan at opensips.org>
>> razvan at opensips.org> wrote:
>>
>>> Hi, Mickael!
>>>
>>> That's the correct usage, and the AVP is attached to the transaction,
>>> and destroyed when the transaction is destroyed. However, it depends on the
>>> context when the AVP is populated. Is it done for each message? Timer based?
>>> If I were you, I'd continue tracing the name of the AVPs and checking
>>> where they are populated.
>>>
>>> Best regards,
>>>
>>> Răzvan Crainea
>>> OpenSIPS Solutionswww.opensips-solutions.com
>>>
>>> On 06/22/2015 07:28 PM, Mickael Marrache wrote:
>>>
>>> Looking for example at the DIALPLAN module, it looks like the same
>>> procedure is followed, so I don't see anything special I'm doing here.
>>>
>>> On Mon, Jun 22, 2015 at 7:22 PM, Mickael Marrache <
>>> <mickaelmarrache at gmail.com>mickaelmarrache at gmail.com> wrote:
>>>
>>>> Hi Razvan,
>>>>
>>>> I do the following:
>>>>
>>>> static str my_avp_name = {NULL, 0};
>>>> static pv_spec_t my_avp;
>>>>
>>>> static param_export_t params[] = {
>>>> .....
>>>> { "my_avp", STR_PARAM, &my_avp_name.s}
>>>> };
>>>>
>>>> static int mod_init(void) {
>>>>         ....
>>>> my_avp_name.len = strlen(my_avp_name.s);
>>>>         ....
>>>>         if(my_avp_name.s == NULL || my_avp_name.len == 0) {
>>>> return -1;
>>>> }
>>>> if (pv_parse_spec(&my_avp_name, &my_avp) == 0 || my_avp.type !=
>>>> PVT_AVP) {
>>>> return -1;
>>>> }
>>>> }
>>>>
>>>> Then, when I want to set a value to my AVP (for example, for setting an
>>>> integer):
>>>>
>>>> pv_value_t pvar_value;
>>>> pvar_value.flags = PV_VAL_INT|PV_TYPE_INT;
>>>> pvar_value.ri = some_integer;
>>>> if(pv_set_value(msg, &my_avp, (int)EQ_T, &pvar_value) < 0) {
>>>> goto error;
>>>> }
>>>>
>>>> And, that's all. I don't detroy the AVP after use because the module
>>>> can't know the AVP is not used anymore. I can destroy the AVP in the script
>>>> after use but I thought it was handled automatically.
>>>>
>>>> In the example I gave here, is the AVP attached to a transaction? What
>>>> are the conditions for an AVP to be attached to a transaction?
>>>>
>>>> Thanks,
>>>> Mickael
>>>>
>>>> On Mon, Jun 22, 2015 at 10:33 AM, Răzvan Crainea <
>>>> <razvan at opensips.org>razvan at opensips.org> wrote:
>>>>
>>>>> Hi, Mickael!
>>>>>
>>>>> Both maps are relevant, because both of them contain id2name mappings.
>>>>> So you should definitely look into the avp_map too. Note that those
>>>>> mappings do not store AVPs, they only store the real name of the AVP, as
>>>>> you use in script, and they can be populated at startup (in this case they
>>>>> are stored in PKG) and runtime (stored in SHM).
>>>>> It depends when the AVP should be destroyed: if they are attached to
>>>>> the transaction (and they usually are), they are automatically destroyed by
>>>>> the tm module. Otherwise the module that uses them, should take care of
>>>>> that.
>>>>>
>>>>> Best regards,
>>>>>
>>>>> Răzvan Crainea
>>>>> OpenSIPS Solutionswww.opensips-solutions.com
>>>>>
>>>>> On 06/18/2015 09:56 PM, Mickael Marrache wrote:
>>>>>
>>>>> Hi Razvan,
>>>>>
>>>>> I looked at both avp_map and avp_map_shm. In our case, only
>>>>> avp_map_shm is relevant since the leak appears in shared memory. I only see
>>>>> 4 elements in this map while I can see a lot of remaining AVPs when looking
>>>>> at the memory dump created at shutdown using QM debug. Therefore, it looks
>>>>> like these AVPs are not in the map. Looking at the new_avp function in
>>>>> usr_avp.c, I don't see at any moment that an entry is added to the map for
>>>>> the new AVP.
>>>>>
>>>>> (gdb) print avp_map_shm->avl_count
>>>>> $5 = 4
>>>>> (gdb) print avp_map->avl_count
>>>>> $6 = 140
>>>>>
>>>>> Any idea?
>>>>>
>>>>> At which moment during execution an AVP is destroyed? Is it required
>>>>> for modules returning values to script through AVPs to destroy these AVPs?
>>>>> or are they automatically destroyed?
>>>>>
>>>>> Thanks,
>>>>> Mickael
>>>>>
>>>>> On Thu, Jun 18, 2015 at 7:33 PM, Răzvan Crainea <
>>>>> <razvan at opensips.org>razvan at opensips.org> wrote:
>>>>>
>>>>>> Hi, Mickael!
>>>>>>
>>>>>> This is not entirely true - you can define AVPs with the integer
>>>>>> value 0. Those will have avp->flags == 0 and avp->data == 0.
>>>>>> What I'd do, is to note down the avp->id value of those AVPs and then
>>>>>> try to see their names. To do that, you'd have to look into the avp_map and
>>>>>> avp_map_shm maps to see the corresponding name for that id. Alternatively
>>>>>> you can call in your script the avp_print() method, which prints all the
>>>>>> AVPs for a specific transaction along with their id and names. Let me know
>>>>>> how this goes.
>>>>>>
>>>>>> Best regards,
>>>>>>
>>>>>> Răzvan Crainea
>>>>>> OpenSIPS Solutionswww.opensips-solutions.com
>>>>>>
>>>>>>
>>> _______________________________________________
>>> Users mailing list
>>> Users at lists.opensips.org
>>> http://lists.opensips.org/cgi-bin/mailman/listinfo/users
>>>
>>>
>>
>>
>> _______________________________________________
>> Users mailing listUsers at lists.opensips.orghttp://lists.opensips.org/cgi-bin/mailman/listinfo/users
>>
>>
>>
>> _______________________________________________
>> Users mailing list
>> Users at lists.opensips.org
>> http://lists.opensips.org/cgi-bin/mailman/listinfo/users
>>
>>
>
>
> _______________________________________________
> Users mailing listUsers at lists.opensips.orghttp://lists.opensips.org/cgi-bin/mailman/listinfo/users
>
>
>
> _______________________________________________
> Users mailing list
> Users at lists.opensips.org
> http://lists.opensips.org/cgi-bin/mailman/listinfo/users
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.opensips.org/pipermail/users/attachments/20150802/c15740c7/attachment-0001.htm>


More information about the Users mailing list