diff options
author | markster <markster@f38db490-d61c-443f-a65b-d21fe96a405b> | 2004-10-22 14:19:11 +0000 |
---|---|---|
committer | markster <markster@f38db490-d61c-443f-a65b-d21fe96a405b> | 2004-10-22 14:19:11 +0000 |
commit | 4ff08f5831bca1664a0dff071947498632161da0 (patch) | |
tree | 7bb4c4023f58141eff76d4832ace91a1df39c911 /pbx | |
parent | 624733ced21a3f476d5282284868c45533829aaa (diff) |
Work on precaching
git-svn-id: http://svn.digium.com/svn/asterisk/trunk@4045 f38db490-d61c-443f-a65b-d21fe96a405b
Diffstat (limited to 'pbx')
-rwxr-xr-x | pbx/pbx_dundi.c | 79 |
1 files changed, 77 insertions, 2 deletions
diff --git a/pbx/pbx_dundi.c b/pbx/pbx_dundi.c index f4847c598..b09c3dee0 100755 --- a/pbx/pbx_dundi.c +++ b/pbx/pbx_dundi.c @@ -203,6 +203,7 @@ static struct dundi_peer { int registerid; int qualifyid; int sentfullkey; + int canprecache; int order; unsigned char txenckey[256]; /* Transmitted encrypted key + sig */ unsigned char rxenckey[256]; /* Cache received encrypted key + sig */ @@ -1240,6 +1241,7 @@ static int handle_command_response(struct dundi_transaction *trans, struct dundi int x,y,z; int resp; int res; + int authpass=0; unsigned char *bufcpy; struct dundi_ie_data ied; struct dundi_ies ies; @@ -1349,10 +1351,82 @@ static int handle_command_response(struct dundi_transaction *trans, struct dundi } } break; + case DUNDI_COMMAND_PRECACHE: + /* Success of some sort */ + ast_log(LOG_DEBUG, "Looks like a precache with %d answers\n", ies.anscount); + /* A dialplan or entity discover -- qualify by highest level entity */ + peer = find_peer(ies.eids[0]); + if (peer && ies.called_number) { + struct dundi_request dr; + struct dundi_result dr2[1]; + memset(&dr, 0, sizeof(dr)); + memset(&dr2, 0, sizeof(dr2)); + /* Build placeholder Dundi Request */ + trans->us_eid = peer->us_eid; + if (!ies.called_context) + ies.called_context = "e164"; + strncpy(dr.dcontext, ies.called_context, sizeof(dr.dcontext) - 1); + strncpy(dr.number, ies.called_number, sizeof(dr.number) - 1); + dr.dr = dr2; + trans->parent = &dr; + + /* Make sure we have all the proper auths */ + if (strlen(peer->inkey)) { + authpass = encrypted; + } else + authpass = 1; + authpass &= has_permission(peer->include, ies.called_context); + authpass &= peer->canprecache; + if (authpass) { + /* Okay we're authentiated and all, now we check if they're authorized */ + for (x=0;x<ies.anscount;x++) { + /* Copy into parent responses */ + trans->parent->dr[0].flags = ntohs(ies.answers[x]->flags); + trans->parent->dr[0].techint = ies.answers[x]->protocol; + trans->parent->dr[0].weight = ntohs(ies.answers[x]->weight); + trans->parent->dr[0].eid = ies.answers[x]->eid; + if (ies.expiration > 0) + trans->parent->dr[0].expiration = ies.expiration; + else + trans->parent->dr[0].expiration = DUNDI_DEFAULT_CACHE_TIME; + dundi_eid_to_str(trans->parent->dr[0].eid_str, + sizeof(trans->parent->dr[0].eid_str), + &ies.answers[x]->eid); + strncpy(trans->parent->dr[0].dest, ies.answers[x]->data, + sizeof(trans->parent->dr[0].dest)); + strncpy(trans->parent->dr[0].tech, tech2str(ies.answers[x]->protocol), + sizeof(trans->parent->dr[0].tech)); + trans->parent->respcount=1; + /* Save all the results (if any) we had. Even if no results, still cache lookup. Let + the cache know if this request was unaffected by our entity list. */ + cache_save(&trans->them_eid, trans->parent, 0, + ies.hint ? ntohs(ies.hint->flags) & DUNDI_HINT_UNAFFECTED : 0, ies.expiration); + } + if (ies.hint) { + cache_save_hint(&trans->them_eid, trans->parent, ies.hint, ies.expiration); + if (ntohs(ies.hint->flags) & DUNDI_HINT_TTL_EXPIRED) + trans->parent->hmd->flags |= DUNDI_HINT_TTL_EXPIRED; + if (ntohs(ies.hint->flags) & DUNDI_HINT_DONT_ASK) { + if (strlen(ies.hint->data) > strlen(trans->parent->hmd->exten)) { + strncpy(trans->parent->hmd->exten, ies.hint->data, + sizeof(trans->parent->hmd->exten) - 1); + } + } else { + trans->parent->hmd->flags &= ~DUNDI_HINT_DONT_ASK; + } + } + } + } + if (!authpass && ies.eids[0]) + ast_log(LOG_NOTICE, "Peer '%s' does not have permission to pre-cache!\n", + dundi_eid_to_str(eid_str, sizeof(eid_str), ies.eids[0])); + /* Close connection if not final */ + if (!final) + dundi_send(trans, DUNDI_COMMAND_CANCEL, 0, 1, NULL); + break; case DUNDI_COMMAND_DPRESPONSE: /* A dialplan response, lets see what we got... */ if (ies.cause < 1) { - int authpass=0; /* Success of some sort */ ast_log(LOG_DEBUG, "Looks like success of some sort (%d), %d answers\n", ies.cause, ies.anscount); if (trans->flags & FLAG_ENCRYPT) { @@ -1437,7 +1511,6 @@ static int handle_command_response(struct dundi_transaction *trans, struct dundi case DUNDI_COMMAND_EIDRESPONSE: /* A dialplan response, lets see what we got... */ if (ies.cause < 1) { - int authpass=0; /* Success of some sort */ ast_log(LOG_DEBUG, "Looks like success of some sort (%d)\n", ies.cause); if (trans->flags & FLAG_ENCRYPT) { @@ -3381,6 +3454,8 @@ static void build_peer(dundi_eid *eid, struct ast_variable *v) strncpy(peer->inkey, v->value, sizeof(peer->inkey) - 1); } else if (!strcasecmp(v->name, "outkey")) { strncpy(peer->outkey, v->value, sizeof(peer->outkey) - 1); + } else if (!strcasecmp(v->name, "canprecache")) { + peer->canprecache = ast_true(v->value); } else if (!strcasecmp(v->name, "host")) { if (!strcasecmp(v->value, "dynamic")) { peer->dynamic = 1; |