t_var.c
Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023 #include "../../mem/mem.h"
00024
00025 #include "t_lookup.h"
00026 #include "t_var.h"
00027
00028 static struct cell *_pv_T_req = NULL;
00029 static struct cell *_pv_T_rpl = NULL;
00030 static struct sip_msg _pv_treq;
00031 static struct sip_msg _pv_trpl;
00032 static struct sip_msg *_pv_treq_p = NULL;
00033 static struct sip_msg *_pv_trpl_p = NULL;
00034 static unsigned int _pv_treq_id = 0;
00035 static unsigned int _pv_trpl_id = 0;
00036 static char *_pv_treq_buf = NULL;
00037 static char *_pv_trpl_buf = NULL;
00038 static unsigned int _pv_treq_size = 0;
00039 static unsigned int _pv_trpl_size = 0;
00040
00041 int pv_t_copy_msg(struct sip_msg *src, struct sip_msg *dst)
00042 {
00043 dst->id = src->id;
00044 dst->rcv = src->rcv;
00045 dst->set_global_address=src->set_global_address;
00046 dst->set_global_port=src->set_global_port;
00047 dst->flags = src->flags;
00048 dst->force_send_socket = src->force_send_socket;
00049
00050 if (parse_msg(dst->buf, dst->len, dst)!=0)
00051 {
00052 LM_ERR("parse msg failed\n");
00053 return -1;
00054 }
00055 return 0;
00056 }
00057
00058 int pv_t_update_req(struct sip_msg *msg)
00059 {
00060 struct cell * t;
00061 int branch;
00062
00063 if(msg==NULL)
00064 return 1;
00065
00066 if(msg!=FAKED_REPLY && msg->first_line.type!=SIP_REPLY)
00067 return 1;
00068
00069 t = get_t();
00070
00071 if(t==NULL || t==T_UNDEFINED)
00072 {
00073 if(msg==FAKED_REPLY)
00074 return 1;
00075 branch=-1;
00076 if (t_check(msg, &branch ) == -1)
00077 return 1;
00078 t = get_t();
00079 if ((t == 0) || (t == T_UNDEFINED))
00080 return 1;
00081
00082 }
00083
00084 if(t->uas.request==NULL)
00085 return 1;
00086
00087 if(_pv_T_req==t && t->uas.request==_pv_treq_p
00088 && t->uas.request->id==_pv_treq_id)
00089 return 0;
00090
00091
00092 if(_pv_treq_buf==NULL || _pv_treq_size<t->uas.request->len+1)
00093 {
00094 if(_pv_treq_buf!=NULL)
00095 pkg_free(_pv_treq_buf);
00096 if(_pv_treq_p)
00097 free_sip_msg(&_pv_treq);
00098 _pv_treq_p = NULL;
00099 _pv_treq_id = 0;
00100 _pv_T_req = NULL;
00101 _pv_treq_size = t->uas.request->len+1;
00102 _pv_treq_buf = (char*)pkg_malloc(_pv_treq_size*sizeof(char));
00103 if(_pv_treq_buf==NULL)
00104 {
00105 LM_ERR("no more pkg\n");
00106 _pv_treq_size = 0;
00107 return -1;
00108 }
00109 }
00110 if(_pv_treq_p)
00111 free_sip_msg(&_pv_treq);
00112 memset(&_pv_treq, 0, sizeof(struct sip_msg));
00113 memcpy(_pv_treq_buf, t->uas.request->buf, t->uas.request->len);
00114 _pv_treq_buf[t->uas.request->len] = '\0';
00115 _pv_treq.len = t->uas.request->len;
00116 _pv_treq.buf = _pv_treq_buf;
00117 _pv_treq_p = t->uas.request;
00118 _pv_treq_id = t->uas.request->id;
00119 _pv_T_req = t;
00120
00121
00122 if(pv_t_copy_msg(t->uas.request, &_pv_treq)!=0)
00123 {
00124 pkg_free(_pv_treq_buf);
00125 _pv_treq_size = 0;
00126 _pv_treq_buf = NULL;
00127 _pv_T_req = NULL;
00128 return -1;
00129 }
00130
00131 return 0;
00132 }
00133
00134 int pv_t_update_rpl(struct sip_msg *msg)
00135 {
00136 struct cell * t;
00137 int branch;
00138
00139 if(msg==NULL)
00140 return 1;
00141
00142 if(msg==FAKED_REPLY || msg->first_line.type!=SIP_REQUEST)
00143 return 1;
00144
00145 t = get_t();
00146
00147 if(t==NULL || t==T_UNDEFINED)
00148 {
00149 if(t_lookup_request(msg, 0)<=0)
00150 return 1;
00151 t = get_t();
00152
00153 if(t==NULL || t==T_UNDEFINED)
00154 return 1;
00155 }
00156 if ( (branch=t_get_picked_branch())<0 )
00157 return 1;
00158 if(t->uac[branch].reply==NULL || t->uac[branch].reply==FAKED_REPLY)
00159 return 1;
00160
00161 if(_pv_T_rpl==t && t->uac[branch].reply==_pv_trpl_p
00162 && t->uac[branch].reply->id==_pv_trpl_id)
00163 return 0;
00164
00165
00166 if(_pv_trpl_buf==NULL || _pv_trpl_size<t->uac[branch].reply->len+1)
00167 {
00168 if(_pv_trpl_buf!=NULL)
00169 pkg_free(_pv_trpl_buf);
00170 if(_pv_trpl_p)
00171 free_sip_msg(&_pv_trpl);
00172 _pv_trpl_p = NULL;
00173 _pv_trpl_id = 0;
00174 _pv_T_rpl = NULL;
00175 _pv_trpl_size = t->uac[branch].reply->len+1;
00176 _pv_trpl_buf = (char*)pkg_malloc(_pv_trpl_size*sizeof(char));
00177 if(_pv_trpl_buf==NULL)
00178 {
00179 LM_ERR("no more pkg\n");
00180 _pv_trpl_size = 0;
00181 return -1;
00182 }
00183 }
00184 if(_pv_trpl_p)
00185 free_sip_msg(&_pv_trpl);
00186 memset(&_pv_trpl, 0, sizeof(struct sip_msg));
00187 memcpy(_pv_trpl_buf, t->uac[branch].reply->buf, t->uac[branch].reply->len);
00188 _pv_trpl_buf[t->uac[branch].reply->len] = '\0';
00189 _pv_trpl.len = t->uac[branch].reply->len;
00190 _pv_trpl.buf = _pv_trpl_buf;
00191 _pv_trpl_p = t->uac[branch].reply;
00192 _pv_trpl_id = t->uac[branch].reply->id;
00193 _pv_T_rpl = t;
00194
00195 if(pv_t_copy_msg(t->uac[branch].reply, &_pv_trpl)!=0)
00196 {
00197 pkg_free(_pv_trpl_buf);
00198 _pv_trpl_buf = NULL;
00199 _pv_trpl_size = 0;
00200 _pv_T_rpl = 0;
00201 return -1;
00202 }
00203
00204 return 0;
00205 }
00206
00207 int pv_get_t_var_req(struct sip_msg *msg, pv_param_t *param,
00208 pv_value_t *res)
00209 {
00210 pv_spec_t *pv=NULL;
00211
00212 if(pv_t_update_req(msg))
00213 return pv_get_null(msg, param, res);
00214
00215 pv = (pv_spec_t*)param->pvn.u.dname;
00216 if(pv==NULL || pv_alter_context(pv))
00217 return pv_get_null(msg, param, res);
00218
00219 return pv_get_spec_value(&_pv_treq, pv, res);
00220 }
00221
00222 int pv_get_t_var_rpl(struct sip_msg *msg, pv_param_t *param,
00223 pv_value_t *res)
00224 {
00225 pv_spec_t *pv=NULL;
00226
00227 if(pv_t_update_rpl(msg))
00228 return pv_get_null(msg, param, res);
00229
00230 pv = (pv_spec_t*)param->pvn.u.dname;
00231 if(pv==NULL || pv_alter_context(pv))
00232 return pv_get_null(msg, param, res);
00233
00234 return pv_get_spec_value(&_pv_trpl, pv, res);
00235 }
00236
00237 int pv_parse_t_var_name(pv_spec_p sp, str *in)
00238 {
00239 pv_spec_t *pv=NULL;
00240
00241 if(in->s==NULL || in->len<=0)
00242 return -1;
00243
00244 pv = (pv_spec_t*)pkg_malloc(sizeof(pv_spec_t));
00245 if(pv==NULL)
00246 return -1;
00247
00248 memset(pv, 0, sizeof(pv_spec_t));
00249
00250 if(pv_parse_spec(in, pv)==NULL)
00251 goto error;
00252
00253 sp->pvp.pvn.u.dname = (void*)pv;
00254 sp->pvp.pvn.type = PV_NAME_PVAR;
00255 return 0;
00256
00257 error:
00258 LM_ERR("invalid pv name [%.*s]\n", in->len, in->s);
00259 if(pv!=NULL)
00260 pkg_free(pv);
00261 return -1;
00262 }
00263