<p>N A has uploaded this change for <strong>review</strong>.</p><p><a href="https://gerrit.asterisk.org/c/asterisk/+/16075">View Change</a></p><pre style="font-family: monospace,monospace; white-space: pre-wrap;">func_lookup: Fork of HINT function<br><br>This is a generic key-value lookup function<br>that is similar to HINT, except it references<br>priorities that are not used for device state,<br>allowing for access to these extension values<br>without adding overhead for device state.<br><br>This provides a fast, efficient, and convenient<br>mechanism in certain circumstances for accessing<br>key-values in the dialplan while being able to<br>use native extension pattern matching on the keys.<br><br>ASTERISK-29486<br><br>Change-Id: Iad81019689674c9f4ac77d235f5d7234adbb1432<br>---<br>A doc/CHANGES-staging/func_lookup.txt<br>A funcs/func_lookup.c<br>M pbx/pbx_config.c<br>3 files changed, 151 insertions(+), 2 deletions(-)<br><br></pre><pre style="font-family: monospace,monospace; white-space: pre-wrap;">git pull ssh://gerrit.asterisk.org:29418/asterisk refs/changes/75/16075/1</pre><pre style="font-family: monospace,monospace; white-space: pre-wrap;"><span>diff --git a/doc/CHANGES-staging/func_lookup.txt b/doc/CHANGES-staging/func_lookup.txt</span><br><span>new file mode 100644</span><br><span>index 0000000..2e3d948</span><br><span>--- /dev/null</span><br><span>+++ b/doc/CHANGES-staging/func_lookup.txt</span><br><span>@@ -0,0 +1,7 @@</span><br><span style="color: hsl(120, 100%, 40%);">+Subject: func_lookup</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+This is a new function that works like</span><br><span style="color: hsl(120, 100%, 40%);">+HINT, except the referenced priorities</span><br><span style="color: hsl(120, 100%, 40%);">+are not used for device state, ditching</span><br><span style="color: hsl(120, 100%, 40%);">+unneeded overhead while allowing for</span><br><span style="color: hsl(120, 100%, 40%);">+key value lookups using pattern matching.</span><br><span>diff --git a/funcs/func_lookup.c b/funcs/func_lookup.c</span><br><span>new file mode 100644</span><br><span>index 0000000..97377c7</span><br><span>--- /dev/null</span><br><span>+++ b/funcs/func_lookup.c</span><br><span>@@ -0,0 +1,128 @@</span><br><span style="color: hsl(120, 100%, 40%);">+/*</span><br><span style="color: hsl(120, 100%, 40%);">+ * Asterisk -- An open source telephony toolkit.</span><br><span style="color: hsl(120, 100%, 40%);">+ *</span><br><span style="color: hsl(120, 100%, 40%);">+ * Copyright (C) 2021, Naveen Albert</span><br><span style="color: hsl(120, 100%, 40%);">+ *</span><br><span style="color: hsl(120, 100%, 40%);">+ * See http://www.asterisk.org for more information about</span><br><span style="color: hsl(120, 100%, 40%);">+ * the Asterisk project. Please do not directly contact</span><br><span style="color: hsl(120, 100%, 40%);">+ * any of the maintainers of this project for assistance;</span><br><span style="color: hsl(120, 100%, 40%);">+ * the project provides a web site, mailing lists and IRC</span><br><span style="color: hsl(120, 100%, 40%);">+ * channels for your use.</span><br><span style="color: hsl(120, 100%, 40%);">+ *</span><br><span style="color: hsl(120, 100%, 40%);">+ * This program is free software, distributed under the terms of</span><br><span style="color: hsl(120, 100%, 40%);">+ * the GNU General Public License Version 2. See the LICENSE file</span><br><span style="color: hsl(120, 100%, 40%);">+ * at the top of the source tree.</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%);">+/*! \file</span><br><span style="color: hsl(120, 100%, 40%);">+ *</span><br><span style="color: hsl(120, 100%, 40%);">+ * \brief Dialplan lookup function</span><br><span style="color: hsl(120, 100%, 40%);">+ *</span><br><span style="color: hsl(120, 100%, 40%);">+ * \author Naveen Albert <asterisk@phreaknet.org></span><br><span style="color: hsl(120, 100%, 40%);">+ *</span><br><span style="color: hsl(120, 100%, 40%);">+ * \ingroup functions</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%);">+/*** MODULEINFO</span><br><span style="color: hsl(120, 100%, 40%);">+ <support_level>extended</support_level></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%);">+#include "asterisk.h"</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+#include "asterisk/module.h"</span><br><span style="color: hsl(120, 100%, 40%);">+#include "asterisk/channel.h"</span><br><span style="color: hsl(120, 100%, 40%);">+#include "asterisk/pbx.h"</span><br><span style="color: hsl(120, 100%, 40%);">+#include "asterisk/utils.h"</span><br><span style="color: hsl(120, 100%, 40%);">+#include "asterisk/app.h"</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+/*** DOCUMENTATION</span><br><span style="color: hsl(120, 100%, 40%);">+ <function name="LOOKUP" language="en_US"></span><br><span style="color: hsl(120, 100%, 40%);">+ <synopsis></span><br><span style="color: hsl(120, 100%, 40%);">+ Get the value set for a static dialplan lookup extension.</span><br><span style="color: hsl(120, 100%, 40%);">+ </synopsis></span><br><span style="color: hsl(120, 100%, 40%);">+ <syntax></span><br><span style="color: hsl(120, 100%, 40%);">+ <parameter name="extension" required="true" argsep="@"></span><br><span style="color: hsl(120, 100%, 40%);">+ <argument name="extension" required="true" /></span><br><span style="color: hsl(120, 100%, 40%);">+ <argument name="context" /></span><br><span style="color: hsl(120, 100%, 40%);">+ </parameter></span><br><span style="color: hsl(120, 100%, 40%);">+ </syntax></span><br><span style="color: hsl(120, 100%, 40%);">+ <description></span><br><span style="color: hsl(120, 100%, 40%);">+ <para>The LOOKUP function can be used to retrieve arbitrary values</span><br><span style="color: hsl(120, 100%, 40%);">+ from a static dialplan lookup, similar to using a hint. For example:</para></span><br><span style="color: hsl(120, 100%, 40%);">+ <para>NoOp(Bill calls from 1234 to ${LOOKUP(1234@billing-tel-num)})</para></span><br><span style="color: hsl(120, 100%, 40%);">+ <para>LOOKUP is like the HINT function without device state, providing</span><br><span style="color: hsl(120, 100%, 40%);">+ an easy and efficient way to access static values in the dialplan and</span><br><span style="color: hsl(120, 100%, 40%);">+ enables key-value lookups to be performed with pattern matching.</para></span><br><span style="color: hsl(120, 100%, 40%);">+ </description></span><br><span style="color: hsl(120, 100%, 40%);">+ </function></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%);">+#define PRIORITY_LOOKUP -2 /*!< Special Priority for a lookup */</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+static struct ast_exten *ast_lookup_extension(struct ast_channel *c, const char *context, const char *exten)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+ struct ast_exten *e;</span><br><span style="color: hsl(120, 100%, 40%);">+ struct pbx_find_info q = { .stacklen = 0 }; /* the rest is set in pbx_find_context */</span><br><span style="color: hsl(120, 100%, 40%);">+ ast_rdlock_contexts();</span><br><span style="color: hsl(120, 100%, 40%);">+ e = pbx_find_extension(c, NULL, &q, context, exten, PRIORITY_LOOKUP, NULL, "", E_MATCH);</span><br><span style="color: hsl(120, 100%, 40%);">+ ast_unlock_contexts();</span><br><span style="color: hsl(120, 100%, 40%);">+ return e;</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%);">+static int ast_get_lookup(char *lookup, int lookupsize, char *name, int namesize, struct ast_channel *c, const char *context, const char *exten)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+ struct ast_exten *e = ast_lookup_extension(c, context, exten);</span><br><span style="color: hsl(120, 100%, 40%);">+ if (e) {</span><br><span style="color: hsl(120, 100%, 40%);">+ if (name) {</span><br><span style="color: hsl(120, 100%, 40%);">+ const char *tmp = ast_get_extension_app(e);</span><br><span style="color: hsl(120, 100%, 40%);">+ if (tmp)</span><br><span style="color: hsl(120, 100%, 40%);">+ ast_copy_string(name, tmp, namesize);</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%);">+ 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%);">+static int lookup_read(struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t len)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+ char *exten, *context;</span><br><span style="color: hsl(120, 100%, 40%);">+ AST_DECLARE_APP_ARGS(args,</span><br><span style="color: hsl(120, 100%, 40%);">+ AST_APP_ARG(exten);</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%);">+ if (ast_strlen_zero(data)) {</span><br><span style="color: hsl(120, 100%, 40%);">+ ast_log(LOG_WARNING, "The LOOKUP function requires an extension\n");</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%);">+ AST_STANDARD_APP_ARGS(args, data);</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ if (ast_strlen_zero(args.exten)) {</span><br><span style="color: hsl(120, 100%, 40%);">+ ast_log(LOG_WARNING, "The LOOKUP function requires an extension\n");</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%);">+ context = exten = args.exten;</span><br><span style="color: hsl(120, 100%, 40%);">+ strsep(&context, "@");</span><br><span style="color: hsl(120, 100%, 40%);">+ if (ast_strlen_zero(context))</span><br><span style="color: hsl(120, 100%, 40%);">+ context = "default";</span><br><span style="color: hsl(120, 100%, 40%);">+</span><br><span style="color: hsl(120, 100%, 40%);">+ return ast_get_lookup(NULL, 0, buf, len, chan, context, exten);</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%);">+static struct ast_custom_function lookup_function = {</span><br><span style="color: hsl(120, 100%, 40%);">+ .name = "LOOKUP",</span><br><span style="color: hsl(120, 100%, 40%);">+ .read = lookup_read,</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%);">+static int unload_module(void)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+ return ast_custom_function_unregister(&lookup_function);</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%);">+static int load_module(void)</span><br><span style="color: hsl(120, 100%, 40%);">+{</span><br><span style="color: hsl(120, 100%, 40%);">+ return ast_custom_function_register(&lookup_function);</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%);">+AST_MODULE_INFO_STANDARD(ASTERISK_GPL_KEY, "Arbitrary static dialplan lookup function");</span><br><span>diff --git a/pbx/pbx_config.c b/pbx/pbx_config.c</span><br><span>index f6af7bf..39aa6ea 100644</span><br><span>--- a/pbx/pbx_config.c</span><br><span>+++ b/pbx/pbx_config.c</span><br><span>@@ -446,6 +446,8 @@</span><br><span> */</span><br><span> if (!strcmp("hint", c))</span><br><span> removing_priority = PRIORITY_HINT;</span><br><span style="color: hsl(120, 100%, 40%);">+ else if (!strcmp("lookup", c))</span><br><span style="color: hsl(120, 100%, 40%);">+ removing_priority = PRIORITY_LOOKUP;</span><br><span> else {</span><br><span> while (*c && isdigit(*c))</span><br><span> c++;</span><br><span>@@ -526,6 +528,8 @@</span><br><span> ipriority = 0;</span><br><span> } else if (!strcmp("hint", priority)) {</span><br><span> ipriority = PRIORITY_HINT;</span><br><span style="color: hsl(120, 100%, 40%);">+ } else if (!strcmp("lookup", priority)) {</span><br><span style="color: hsl(120, 100%, 40%);">+ ipriority = PRIORITY_LOOKUP;</span><br><span> } else if ((sscanf(priority, "%30d", &ipriority) != 1) || ipriority <= 0) {</span><br><span> astman_send_error(s, m, "The priority specified was invalid.");</span><br><span> return 0;</span><br><span>@@ -963,7 +967,11 @@</span><br><span> fprintf(output, "exten => %s,hint,%s\n",</span><br><span> ast_get_extension_name(p),</span><br><span> ast_get_extension_app(p));</span><br><span style="color: hsl(0, 100%, 40%);">- } else {</span><br><span style="color: hsl(120, 100%, 40%);">+ } else if (ast_get_extension_priority(p) == PRIORITY_LOOKUP) { /* easy */</span><br><span style="color: hsl(120, 100%, 40%);">+ fprintf(output, "exten => %s,lookup,%s\n",</span><br><span style="color: hsl(120, 100%, 40%);">+ ast_get_extension_name(p),</span><br><span style="color: hsl(120, 100%, 40%);">+ ast_get_extension_app(p));</span><br><span style="color: hsl(120, 100%, 40%);">+ } else {</span><br><span> const char *sep, *cid;</span><br><span> const char *el = ast_get_extension_label(p);</span><br><span> char label[128] = "";</span><br><span>@@ -1112,6 +1120,8 @@</span><br><span> if (prior) {</span><br><span> if (!strcmp(prior, "hint")) {</span><br><span> iprior = PRIORITY_HINT;</span><br><span style="color: hsl(120, 100%, 40%);">+ } else if (!strcmp(prior, "lookup")) {</span><br><span style="color: hsl(120, 100%, 40%);">+ iprior = PRIORITY_LOOKUP;</span><br><span> } else {</span><br><span> if (sscanf(prior, "%30d", &iprior) != 1) {</span><br><span> ast_cli(a->fd, "'%s' is not a valid priority\n", prior);</span><br><span>@@ -1215,7 +1225,9 @@</span><br><span> /* Priority conversion/validation */</span><br><span> if (!strcmp(priority, "hint")) {</span><br><span> ipriority = PRIORITY_HINT;</span><br><span style="color: hsl(0, 100%, 40%);">- } else if ((sscanf(priority, "%30d", &ipriority) != 1) || (ipriority < 0)) {</span><br><span style="color: hsl(120, 100%, 40%);">+ } else if (!strcmp(priority, "lookup")) {</span><br><span style="color: hsl(120, 100%, 40%);">+ ipriority = PRIORITY_LOOKUP;</span><br><span style="color: hsl(120, 100%, 40%);">+ } else if ((sscanf(priority, "%30d", &ipriority) != 1) || (ipriority < 0)) {</span><br><span> astman_send_error(s, m, "The priority specified was invalid.");</span><br><span> return 0;</span><br><span> }</span><br><span>@@ -1799,6 +1811,8 @@</span><br><span> }</span><br><span> if (!strcmp(pri,"hint")) {</span><br><span> ipri = PRIORITY_HINT;</span><br><span style="color: hsl(120, 100%, 40%);">+ } else if (!strcmp(pri,"lookup")) {</span><br><span style="color: hsl(120, 100%, 40%);">+ ipri = PRIORITY_LOOKUP;</span><br><span> } else if (!strcmp(pri, "next") || !strcmp(pri, "n")) {</span><br><span> if (lastpri > -2) {</span><br><span> ipri = lastpri + 1;</span><br><span></span><br></pre><p>To view, visit <a href="https://gerrit.asterisk.org/c/asterisk/+/16075">change 16075</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/+/16075"/><meta itemprop="name" content="View Change"/></div></div>
<div style="display:none"> Gerrit-Project: asterisk </div>
<div style="display:none"> Gerrit-Branch: master </div>
<div style="display:none"> Gerrit-Change-Id: Iad81019689674c9f4ac77d235f5d7234adbb1432 </div>
<div style="display:none"> Gerrit-Change-Number: 16075 </div>
<div style="display:none"> Gerrit-PatchSet: 1 </div>
<div style="display:none"> Gerrit-Owner: N A <mail@interlinked.x10host.com> </div>
<div style="display:none"> Gerrit-MessageType: newchange </div>