Module: sip-router
Branch: master
Commit: bfa4d86a7a18b321a14b65c90d32c5aed32c10d3
URL:
http://git.sip-router.org/cgi-bin/gitweb.cgi/sip-router/?a=commit;h=bfa4d86…
Author: Elena-Ramona Modroiu <ramona(a)asipto.com>
Committer: Elena-Ramona Modroiu <ramona(a)asipto.com>
Date: Sat Dec 8 14:20:43 2012 +0100
pdt(k): added pdt.list command to dump memory structure via rpc
---
modules_k/pdt/pdt.c | 174 +++++++++++++++++++++++++++++++++++++++++++++++++++
1 files changed, 174 insertions(+), 0 deletions(-)
diff --git a/modules_k/pdt/pdt.c b/modules_k/pdt/pdt.c
index 085c7bf..f5f3bdc 100644
--- a/modules_k/pdt/pdt.c
+++ b/modules_k/pdt/pdt.c
@@ -735,9 +735,183 @@ static void pdt_rpc_reload(rpc_t* rpc, void* ctx)
}
+static const char* pdt_rpc_list_doc[2] = {
+ "List PDT memory records",
+ 0
+};
+
+
+int pdt_rpc_print_node(rpc_t* rpc, void* ctx, void *ih, pdt_node_t *pt, char *code,
+ int len, str *sdomain, str *tdomain, str *tprefix)
+{
+ int i;
+ str *cl;
+ str prefix;
+ void* vh;
+
+ if(pt==NULL || len>=PDT_MAX_DEPTH)
+ return 0;
+
+ cl = pdt_get_char_list();
+
+ for(i=0; i<cl->len; i++)
+ {
+ code[len]=cl->s[i];
+ if(pt[i].domain.s!=NULL)
+ {
+ if((tprefix->s==NULL && tdomain->s==NULL)
+ || (tprefix->s==NULL && (tdomain->s!=NULL &&
pt[i].domain.len==tdomain->len
+ && strncasecmp(pt[i].domain.s, tdomain->s, tdomain->len)==0))
+ || (tdomain->s==NULL && (len+1>=tprefix->len
+ && strncmp(code, tprefix->s, tprefix->len)==0))
+ || ((tprefix->s!=NULL && len+1>=tprefix->len
+ && strncmp(code, tprefix->s, tprefix->len)==0)
+ && (tdomain->s!=NULL && pt[i].domain.len>=tdomain->len
+ && strncasecmp(pt[i].domain.s, tdomain->s, tdomain->len)==0)))
+ {
+ if(rpc->struct_add(ih, "{",
+ "ENTRY", &vh)<0)
+ {
+ LM_ERR("Internal error creating entry\n");
+ return -1;
+ }
+ prefix.s = code;
+ prefix.len = len + 1;
+ if(rpc->struct_add(vh, "SS",
+ "DOMAIN", &pt[i].domain,
+ "PREFIX", &prefix)<0)
+ {
+ LM_ERR("Internal error filling entry struct\n");
+ return -1;
+ }
+ }
+ }
+ if(pdt_rpc_print_node(rpc, ctx, ih, pt[i].child, code, len+1, sdomain,
+ tdomain, tprefix)<0)
+ goto error;
+ }
+ return 0;
+error:
+ return -1;
+}
+
+/*
+ * RPC command to list pdt memory records
+ */
+/**
+ * "pdt.list" parameters:
+ * sdomain
+ * prefix
+ * domain
+ *
+ * - '.' (dot) means NULL value and will match anything
+ * - the comparison operation is 'START WITH' -- if domain is 'a' then
+ * all domains starting with 'a' are listed
+ *
+ * Examples
+ * pdt_list o 2 . - lists the entries where sdomain is starting with 'o',
+ * prefix is starting with '2' and domain is anything
+ *
+ * pdt_list . 2 open - lists the entries where sdomain is anything, prefix
+ * starts with '2' and domain starts with 'open'
+ */
+static void pdt_rpc_list(rpc_t* rpc, void* ctx)
+{
+ str sdomain = {0};
+ str tprefix = {0};
+ str tdomain = {0};
+ pdt_tree_t *pt;
+ unsigned int i;
+ static char code_buf[PDT_MAX_DEPTH+1];
+ int len;
+ str *cl;
+ pdt_tree_t **ptree;
+ void* th;
+ void* ih;
+
+ ptree = pdt_get_ptree();
+
+ if(ptree==NULL || *ptree==NULL)
+ {
+ LM_ERR("empty domain list\n");
+ rpc->fault(ctx, 404, "No records");
+ return;
+ }
+
+ len = rpc->scan(ctx, "*S.SS", &sdomain, &tprefix, &tdomain);
+ if(len<0)
+ {
+ rpc->fault(ctx, 500, "Error Reading Parameters");
+ return;
+ }
+ if(len<1 || sdomain.len==0 || (sdomain.len==1 && sdomain.s[0]=='.'))
{
+ sdomain.len = 0;
+ sdomain.s = 0;
+ }
+ cl = pdt_get_char_list();
+ if(len<2 || tprefix.len==0 || (tprefix.len==1 && tprefix.s[0]=='.'))
{
+ tprefix.len = 0;
+ tprefix.s = 0;
+ } else if(tprefix.len>0) {
+ /* validate prefix */
+ i = 0;
+ while(tprefix.s!=NULL && i!=tprefix.len)
+ {
+ if(strpos(cl->s, tprefix.s[i]) < 0)
+ {
+ LM_ERR("bad prefix [%.*s]\n", tprefix.len, tprefix.s);
+ rpc->fault(ctx, 400, "Bad Prefix");
+ return;
+ }
+ i++;
+ }
+ }
+ if(len<3 || tdomain.len==0 || (tdomain.len==1 && tdomain.s[0]=='.'))
{
+ tdomain.len = 0;
+ tdomain.s = 0;
+ }
+
+ pt = *ptree;
+
+ if (rpc->add(ctx, "{", &th) < 0)
+ {
+ rpc->fault(ctx, 500, "Internal error root reply");
+ return;
+ }
+ while(pt!=NULL)
+ {
+ LM_ERR("---- 1 (%d [%.*s])\n", sdomain.len, sdomain.len, sdomain.s);
+ if(sdomain.s==NULL ||
+ (sdomain.s!=NULL && pt->sdomain.len>=sdomain.len &&
+ strncmp(pt->sdomain.s, sdomain.s, sdomain.len)==0))
+ {
+ LM_ERR("---- 2\n");
+ len = 0;
+ if(rpc->struct_add(th, "S{",
+ "SDOMAIN", &pt->sdomain,
+ "RECORDS", &ih)<0)
+ {
+ rpc->fault(ctx, 500, "Internal error creating sdomain structure");
+ return;
+ }
+ if(pdt_rpc_print_node(rpc, ctx, ih, pt->head, code_buf, len, &pt->sdomain,
+ &tdomain, &tprefix)<0)
+ goto error;
+ }
+ pt = pt->next;
+ }
+ return;
+error:
+ rpc->fault(ctx, 500, "Internal error printing records");
+ return;
+}
+
+
rpc_export_t pdt_rpc_cmds[] = {
{"pdt.reload", pdt_rpc_reload,
pdt_rpc_reload_doc, 0},
+ {"pdt.list", pdt_rpc_list,
+ pdt_rpc_list_doc, 0},
{0, 0, 0, 0}
};