<p>Friendly Automation <strong>submitted</strong> this change.</p><p><a href="https://gerrit.asterisk.org/c/asterisk/+/16527">View Change</a></p><div style="white-space:pre-wrap">Approvals:
  Kevin Harwell: Looks good to me, but someone else must approve
  George Joseph: Looks good to me, approved
  Friendly Automation: Approved for Submit

</div><pre style="font-family: monospace,monospace; white-space: pre-wrap;">app_queue: Fix hint updates for included contexts<br><br>Previously, if custom hints were used with the hint:<br>format in app_queue, when device state changes occured,<br>app_queue would only do a literal string comparison of<br>the context used for the hint in app_queue and the context<br>of the hint which just changed state. This caused hints<br>to not update and become stale if the context associated<br>with the agent included the context which actually changes<br>state, essentially completely breaking device state for<br>any such agents defined in this manner.<br><br>This fix adds an additional check to ensure that included<br>contexts are also compared against the context which changed<br>state, so that the behavior is correct no matter whether the<br>context is specified to app_queue directly or indirectly.<br><br>ASTERISK-29578 #close<br><br>Change-Id: I8caf2f8da8157ef3d9ea71a8568c1eec95592b78<br>---<br>M apps/app_queue.c<br>1 file changed, 47 insertions(+), 2 deletions(-)<br><br></pre><pre style="font-family: monospace,monospace; white-space: pre-wrap;"><span>diff --git a/apps/app_queue.c b/apps/app_queue.c</span><br><span>index 4d908a5..a4f6dce 100644</span><br><span>--- a/apps/app_queue.c</span><br><span>+++ b/apps/app_queue.c</span><br><span>@@ -2633,6 +2633,46 @@</span><br><span>       return state;</span><br><span> }</span><br><span> </span><br><span style="color: hsl(120, 100%, 40%);">+/*!</span><br><span style="color: hsl(120, 100%, 40%);">+ * \brief Returns if one context includes another context</span><br><span style="color: hsl(120, 100%, 40%);">+ *</span><br><span style="color: hsl(120, 100%, 40%);">+ * \param parent Parent context to search for child</span><br><span style="color: hsl(120, 100%, 40%);">+ * \param child Context to check for inclusion in parent</span><br><span style="color: hsl(120, 100%, 40%);">+ *</span><br><span style="color: hsl(120, 100%, 40%);">+ * This function recrusively checks if the context child is included in the context parent.</span><br><span style="color: hsl(120, 100%, 40%);">+ *</span><br><span style="color: hsl(120, 100%, 40%);">+ * \return 1 if child is included in parent, 0 if not</span><br><span style="color: hsl(120, 100%, 40%);">+ */</span><br><span style="color: hsl(120, 100%, 40%);">+static int context_included(const char *parent, const char *child);</span><br><span style="color: hsl(120, 100%, 40%);">+static int context_included(const char *parent, const char *child)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+        struct ast_context *c = NULL;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+       c = ast_context_find(parent);</span><br><span style="color: hsl(120, 100%, 40%);">+ if (!c) {</span><br><span style="color: hsl(120, 100%, 40%);">+             /* well, if parent doesn't exist, how can the child be included in it? */</span><br><span style="color: hsl(120, 100%, 40%);">+         return 0;</span><br><span style="color: hsl(120, 100%, 40%);">+     }</span><br><span style="color: hsl(120, 100%, 40%);">+     if (!strcmp(ast_get_context_name(c), parent)) {</span><br><span style="color: hsl(120, 100%, 40%);">+               /* found the context of the hint app_queue is using. Now, see</span><br><span style="color: hsl(120, 100%, 40%);">+                 if that context includes the one that just changed state */</span><br><span style="color: hsl(120, 100%, 40%);">+           struct ast_include *inc = NULL;</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+             while ((inc = (struct ast_include*) ast_walk_context_includes(c, inc))) {</span><br><span style="color: hsl(120, 100%, 40%);">+                     const char *includename = ast_get_include_name(inc);</span><br><span style="color: hsl(120, 100%, 40%);">+                  if (!strcasecmp(child, includename)) {</span><br><span style="color: hsl(120, 100%, 40%);">+                                return 1;</span><br><span style="color: hsl(120, 100%, 40%);">+                     }</span><br><span style="color: hsl(120, 100%, 40%);">+                     /* recurse on this context, for nested includes. The</span><br><span style="color: hsl(120, 100%, 40%);">+                          PBX extension parser will prevent infinite recursion. */</span><br><span style="color: hsl(120, 100%, 40%);">+                      if (context_included(includename, child)) {</span><br><span style="color: hsl(120, 100%, 40%);">+                           return 1;</span><br><span style="color: hsl(120, 100%, 40%);">+                     }</span><br><span style="color: hsl(120, 100%, 40%);">+             }</span><br><span style="color: hsl(120, 100%, 40%);">+     }</span><br><span style="color: hsl(120, 100%, 40%);">+     return 0;</span><br><span style="color: hsl(120, 100%, 40%);">+}</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span> static int extension_state_cb(const char *context, const char *exten, struct ast_state_cb_info *info, void *data)</span><br><span> {</span><br><span>     struct ao2_iterator miter, qiter;</span><br><span>@@ -2653,9 +2693,14 @@</span><br><span>           miter = ao2_iterator_init(q->members, 0);</span><br><span>                 for (; (m = ao2_iterator_next(&miter)); ao2_ref(m, -1)) {</span><br><span>                        if (!strcmp(m->state_context, context) && !strcmp(m->state_exten, exten)) {</span><br><span style="color: hsl(120, 100%, 40%);">+                             found = 1;</span><br><span style="color: hsl(120, 100%, 40%);">+                    } else if (!strcmp(m->state_exten, exten) && context_included(m->state_context, context)) {</span><br><span style="color: hsl(120, 100%, 40%);">+                             /* context could be included in m->state_context. We need to check. */</span><br><span style="color: hsl(120, 100%, 40%);">+                             found = 1;</span><br><span style="color: hsl(120, 100%, 40%);">+                    }</span><br><span style="color: hsl(120, 100%, 40%);">+                     if (found) {</span><br><span>                                 update_status(q, m, device_state);</span><br><span>                           ao2_ref(m, -1);</span><br><span style="color: hsl(0, 100%, 40%);">-                         found = 1;</span><br><span>                           break;</span><br><span>                       }</span><br><span>            }</span><br><span>@@ -2666,7 +2711,7 @@</span><br><span>    }</span><br><span>    ao2_iterator_destroy(&qiter);</span><br><span> </span><br><span style="color: hsl(0, 100%, 40%);">-        if (found) {</span><br><span style="color: hsl(120, 100%, 40%);">+     if (found) {</span><br><span>                 ast_debug(1, "Extension '%s@%s' changed to state '%d' (%s)\n", exten, context, device_state, ast_devstate2str(device_state));</span><br><span>      } else {</span><br><span>             ast_debug(3, "Extension '%s@%s' changed to state '%d' (%s) but we don't care because they're not a member of any queue.\n",</span><br><span></span><br></pre><div style="white-space:pre-wrap"></div><p>To view, visit <a href="https://gerrit.asterisk.org/c/asterisk/+/16527">change 16527</a>. To unsubscribe, or for help writing mail filters, visit <a href="https://gerrit.asterisk.org/settings">settings</a>.</p><div itemscope itemtype="http://schema.org/EmailMessage"><div itemscope itemprop="action" itemtype="http://schema.org/ViewAction"><link itemprop="url" href="https://gerrit.asterisk.org/c/asterisk/+/16527"/><meta itemprop="name" content="View Change"/></div></div>

<div style="display:none"> Gerrit-Project: asterisk </div>
<div style="display:none"> Gerrit-Branch: 16 </div>
<div style="display:none"> Gerrit-Change-Id: I8caf2f8da8157ef3d9ea71a8568c1eec95592b78 </div>
<div style="display:none"> Gerrit-Change-Number: 16527 </div>
<div style="display:none"> Gerrit-PatchSet: 2 </div>
<div style="display:none"> Gerrit-Owner: N A <mail@interlinked.x10host.com> </div>
<div style="display:none"> Gerrit-Reviewer: Friendly Automation </div>
<div style="display:none"> Gerrit-Reviewer: George Joseph <gjoseph@digium.com> </div>
<div style="display:none"> Gerrit-Reviewer: Kevin Harwell <kharwell@digium.com> </div>
<div style="display:none"> Gerrit-MessageType: merged </div>