modules_k/siputils/contact_ops.c

Go to the documentation of this file.
00001 /*
00002  * $Id$
00003  *
00004  * mangler module
00005  *
00006  * Copyright (C) 2001-2003 FhG Fokus
00007  *
00008  * This file is part of SIP-router, a free SIP server.
00009  *
00010  * SIP-router is free software; you can redistribute it and/or modify
00011  * it under the terms of the GNU General Public License as published by
00012  * the Free Software Foundation; either version 2 of the License, or
00013  * (at your option) any later version
00014  *
00015  * SIP-router is distributed in the hope that it will be useful,
00016  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00017  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00018  * GNU General Public License for more details.
00019  *
00020  * You should have received a copy of the GNU General Public License 
00021  * along with this program; if not, write to the Free Software 
00022  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
00023  *
00024  * History:
00025  * --------
00026  *  2003-04-07 first version.  
00027  */
00028 
00037 #define STRICT_CHECK 1
00038 
00039 #include "contact_ops.h"
00040 #include "utils.h"
00041 #include "../../mem/mem.h"
00042 #include "../../data_lump.h"
00043 #include "../../parser/hf.h"
00044 #include "../../parser/parse_uri.h"
00045 #include "../../parser/contact/parse_contact.h"
00046 #include "../../ut.h"
00047 
00048 #include <stdio.h>
00049 #include <string.h>
00050 
00051 
00052 //#define DEBUG
00053 int
00054 encode_contact (struct sip_msg *msg, char *encoding_prefix,char *public_ip)
00055 {
00056 
00057         contact_body_t *cb;
00058         contact_t *c;
00059         str uri;
00060         str newUri;
00061         int res;
00062         char separator;
00063 
00064 
00065 
00066         /*
00067          * I have a list of contacts in contact->parsed which is of type contact_body_t 
00068          * inside i have a contact->parsed->contact which is the head of the list of contacts
00069          * inside it is a 
00070          * str uri;
00071          * struct contact *next;
00072          * I just have to visit each uri and encode each uri according to a scheme
00073          */
00074         
00075         if ((msg->contact == NULL)&&((parse_headers(msg,HDR_CONTACT_F,0) == -1) ||
00076                                 (msg->contact == NULL) ))
00077                 {
00078                 LM_ERR("no Contact header present\n");
00079                 return -1;
00080                 }
00081 
00082 
00083         separator = DEFAULT_SEPARATOR[0];
00084         if (contact_flds_separator != NULL)
00085                 if (strlen(contact_flds_separator)>=1)
00086                         separator = contact_flds_separator[0];
00087 
00088         if (msg->contact->parsed == NULL)       parse_contact (msg->contact);
00089         if (msg->contact->parsed != NULL)
00090         {
00091                 cb = (contact_body_t *) msg->contact->parsed;
00092                 c = cb->contacts;
00093                 /* we visit each contact */
00094                 if (c != NULL)
00095                 {
00096                         uri = c->uri;
00097                         res = encode_uri (uri, encoding_prefix, public_ip,separator, &newUri);
00098                         
00099                         if (res != 0)
00100                                 {
00101                                 LM_ERR("failed encoding contact.Code %d\n", res);
00102 #ifdef STRICT_CHECK
00103                                 return res;
00104 #endif
00105                                 }
00106                         else
00107                                 if (patch (msg, uri.s, uri.len, newUri.s, newUri.len) < 0)
00108                                 {
00109                                         LM_ERR("lumping failed in mangling port \n");
00110                                         return -2;
00111                                 }
00112                         
00113                         /* encoding next contacts too?*/
00114 #ifdef ENCODE_ALL_CONTACTS
00115                         while (c->next != NULL)
00116                         {
00117                                 c = c->next;
00118                                 uri = c->uri;
00119                                 
00120                                 res = encode_uri (uri, encoding_prefix,public_ip,separator,&newUri);
00121                                 if (res != 0)
00122                                         {
00123                                         LM_ERR("failed encode_uri.Code %d\n",res);
00124 #ifdef STRICT_CHECK
00125                                 return res;
00126 #endif
00127                                         }
00128                                 else
00129                                 if (patch (msg, uri.s, uri.len, newUri.s, newUri.len)< 0)
00130                                 {
00131                                         LM_ERR("lumping failed in mangling port \n");
00132                                         return -3;
00133                                 }
00134                         } /* while */
00135 #endif /* ENCODE_ALL_CONTACTS */
00136                 } /* if c != NULL */
00137 
00138         } /* end if */
00139         else /* after parsing still NULL */
00140                 {
00141                         LM_ERR("unable to parse Contact header\n");
00142                         return -4;
00143                 }
00144         return 1;
00145 }
00146 
00147 int
00148 decode_contact (struct sip_msg *msg,char *unused1,char *unused2)
00149 {
00150 
00151         str uri;
00152         str newUri;
00153         char separator;
00154         int res;
00155 
00156         uri.s = 0;
00157         uri.len = 0;
00158 
00159 #ifdef DEBUG
00160         fprintf (stdout,"---START--------DECODE CONTACT-----------------\n");
00161         fprintf (stdout,"%.*s\n",50,msg->buf);
00162         fprintf (stdout, "INITIAL.s=[%.*s]\n", uri.len, uri.s);
00163 #endif
00164 
00165         separator = DEFAULT_SEPARATOR[0];
00166         if (contact_flds_separator != NULL)
00167                 if (strlen(contact_flds_separator)>=1)
00168                         separator = contact_flds_separator[0];
00169                 
00170         if ((msg->new_uri.s == NULL) || (msg->new_uri.len == 0))
00171         {
00172                 uri = msg->first_line.u.request.uri;
00173                 if (uri.s == NULL) 
00174                         return -1;
00175         }
00176         else
00177         {
00178                 uri = msg->new_uri;
00179         }
00180         
00181         res = decode_uri (uri, separator, &newUri);
00182         
00183 #ifdef DEBUG
00184         if (res == 0) 
00185                 fprintf (stdout, "newuri.s=[%.*s]\n", newUri.len, newUri.s);
00186 #endif
00187         if (res != 0)
00188         {
00189                 LM_ERR("failed decoding contact.Code %d\n", res);
00190 #ifdef STRICT_CHECK
00191                 return res;
00192 #endif
00193         }
00194         else
00195         {
00196                 /* we do not modify the original first line */
00197                 if ((msg->new_uri.s == NULL) || (msg->new_uri.len == 0)) 
00198                         msg->new_uri = newUri;
00199                 else
00200                 {
00201                         pkg_free(msg->new_uri.s);
00202                         msg->new_uri = newUri;
00203                 }               
00204         }
00205         return 1;
00206 }
00207 
00208 int
00209 decode_contact_header (struct sip_msg *msg,char *unused1,char *unused2)
00210 {
00211 
00212         contact_body_t *cb;
00213         contact_t *c;
00214         str uri;
00215         str newUri;
00216         char separator;
00217         int res;
00218         
00219         
00220 #ifdef DEBUG
00221         str* ruri;
00222         fprintf (stdout,"---START--------DECODE CONTACT HEADER-----------------\n");
00223 #endif
00224 
00225         if ((msg->contact == NULL)&&((parse_headers(msg,HDR_CONTACT_F,0) == -1) ||
00226                                 (msg->contact== NULL) ))
00227                 {
00228                 LM_ERR("no Contact header present\n");
00229                 return -1;
00230                 }
00231 
00232         separator = DEFAULT_SEPARATOR[0];
00233         if (contact_flds_separator != NULL)
00234                 if (strlen(contact_flds_separator)>=1)
00235                         separator = contact_flds_separator[0];
00236 
00237 #ifdef DEBUG
00238         fprintf (stdout,"Using separator %c\n",separator);
00239         ruri = GET_RURI(msg);
00240         fprintf (stdout,"[len = %d]New uri is->%.*s\n",
00241                         ruri->len,ruri->len,ruri->s);
00242         ruri = &msg->first_line.u.request.uri;
00243         fprintf (stdout, "INITIAL.s=[%.*s]\n", ruri->len, ruri->s);
00244 #endif
00245                 
00246         if (msg->contact->parsed == NULL) parse_contact (msg->contact);
00247         if (msg->contact->parsed != NULL)
00248         {
00249                 cb = (contact_body_t *) msg->contact->parsed;
00250                 c = cb->contacts;
00251                 // we visit each contact 
00252          if (c != NULL)
00253           {
00254                 uri = c->uri;
00255 
00256                 res = decode_uri (uri, separator, &newUri);
00257 #ifdef DEBUG
00258                 fprintf (stdout, "newuri.s=[%.*s]\n", newUri.len, newUri.s);
00259 #endif
00260                 if (res != 0)
00261                 {
00262                         LM_ERR("failed decoding contact.Code %d\n", res);
00263 #ifdef STRICT_CHECK
00264                                 return res;
00265 #endif
00266                 }
00267                 else
00268                 if (patch (msg, uri.s, uri.len, newUri.s, newUri.len) < 0)
00269                 {
00270                         LM_ERR("lumping failed in mangling port \n");
00271                         return -2;
00272                 }
00273 
00274 #ifdef DECODE_ALL_CONTACTS
00275                 while (c->next != NULL)
00276                 {
00277                         c = c->next;
00278                         uri = c->uri;
00279 
00280                         res = decode_uri (uri, separator, &newUri);
00281                         if (res != 0)
00282                                 {
00283                                 LM_ERR("failed decoding contact.Code %d\n",res);
00284 #ifdef STRICT_CHECK
00285                                 return res;
00286 #endif
00287                                 }
00288                         else
00289                         if (patch (msg, uri.s, uri.len, newUri.s, newUri.len) < 0)
00290                         {
00291                                 LM_ERR("lumping failed in mangling port \n");
00292                                 return -3;
00293                         }
00294                 } // end while 
00295 #endif
00296            } // if c!= NULL 
00297         } // end if 
00298         else // after parsing still NULL 
00299                 {
00300                         LM_ERR("unable to parse Contact header\n");
00301                         return -4;
00302                 }
00303 #ifdef DEBUG
00304         fprintf (stdout,"---END--------DECODE CONTACT HEADER-----------------\n");fflush(stdout);
00305 #endif
00306         return 1;
00307 }
00308 
00309 
00310 
00311 
00312 int
00313 encode2format (str uri, struct uri_format *format)
00314 {
00315         int foo;
00316         char *string, *pos, *start, *end;
00317         struct sip_uri sipUri;
00318 
00319 
00320         if (uri.s == NULL)
00321                 return -1;
00322         string = uri.s;
00323 
00324         pos = memchr (string, '<', uri.len);
00325         if (pos != NULL)        /* we are only interested of chars inside <> */
00326         {
00327                 /* KD: I think this can be removed as the parsed contact removed <> already */
00328                 start = memchr (string, ':', uri.len);
00329                 if (start == NULL)      return -2;
00330                 if (start - pos < 4) return -3;
00331                 start = start - 3;
00332                 end = strchr (start, '>');
00333                 if (end == NULL)
00334                         return -4;      /* must be a match to < */
00335         }
00336         else                    /* we do not have  <> */
00337         {
00338                 start = memchr (string, ':', uri.len);
00339                 if (start == NULL)
00340                         return -5;
00341                 if (start - string < 3)
00342                         return -6;
00343                 /* KD: FIXME: Looks like this code can not handle 'sips' URIs and discards all other URI parameters! */
00344                 start = start - 3;
00345                 end = string + uri.len;
00346         }
00347         memset(format,0,sizeof(struct uri_format));
00348         format->first = start - string + 4;     /*sip: */
00349         format->second = end - string;
00350         /* --------------------------testing ------------------------------- */
00351         /* sip:gva@pass@10.0.0.1;;transport=udp>;expires=2 INCORECT BEHAVIOR OF parse_uri,myfunction works good */
00352         foo = parse_uri (start, end - start, &sipUri);
00353         if (foo != 0)
00354         {
00355                 LM_ERR("parse_uri failed on [%.*s].Code %d \n",uri.len,uri.s,foo);
00356 #ifdef DEBUG
00357                 fprintf (stdout, "PARSING uri with parse uri not ok %d\n", foo);
00358 #endif
00359                 return foo-10;
00360         }
00361 
00362         
00363         format->username = sipUri.user;
00364         format->password = sipUri.passwd;
00365         format->ip = sipUri.host;
00366         format->port = sipUri.port;
00367         format->protocol = sipUri.transport_val;
00368         
00369 #ifdef DEBUG    
00370         fprintf (stdout, "transport=[%.*s] transportval=[%.*s]\n", sipUri.transport.len,sipUri.transport.s,sipUri.transport_val.len,sipUri.transport_val.s);
00371         fprintf(stdout,"First %d,second %d\n",format->first,format->second);
00372         #endif
00373         
00374         return 0;
00375 
00376 }
00377 
00378 
00379 int
00380 encode_uri (str uri, char *encoding_prefix, char *public_ip,char separator, str * result)
00381 {
00382         struct uri_format format;
00383         char *pos;
00384         int foo,res;
00385 
00386         
00387         result->s = NULL;
00388         result->len = 0;
00389         if (uri.len <= 1)
00390                 return -1;      /* no contact or an invalid one */
00391         if (public_ip == NULL) 
00392                 {
00393                         LM_ERR("invalid NULL value for public_ip parameter\n");
00394                         return -2;
00395                 }
00396 #ifdef DEBUG
00397         fprintf (stdout, "Primit cerere de encodare a [%.*s] cu %s-%s\n", uri.len,uri.s, encoding_prefix, public_ip);
00398 #endif
00399         fflush (stdout);
00400         foo = encode2format (uri, &format);
00401         if (foo < 0)
00402                 {
00403                 LM_ERR("unable to encode Contact URI [%.*s].Return code %d\n",uri.len,uri.s,foo);
00404                 return foo - 20;
00405                 }
00406 #ifdef DEBUG
00407         fprintf(stdout,"user=%.*s ip=%.*s port=%.*s protocol=%.*s\n",format.username.len,format.username.s,format.ip.len,format.ip.s,
00408              format.port.len,format.port.s,format.protocol.len,format.protocol.s);   
00409 #endif
00410 
00411         /* a complete uri would be sip:username@ip:port;transport=protocol goes to
00412          * sip:enc_pref*username*ip*port*protocol@public_ip
00413          */
00414 
00415         foo = 1;                /*strlen(separator); */
00416         result->len = format.first + uri.len - format.second +  //ar trebui sa sterg 1
00417                 strlen (encoding_prefix) + foo +
00418                 format.username.len + foo +
00419                 format.password.len + foo +
00420                 format.ip.len + foo + format.port.len + foo +
00421                 format.protocol.len + 1 + strlen (public_ip);
00422         /* adding one comes from @ */
00423         result->s = pkg_malloc (result->len);
00424         pos = result->s;
00425         if (pos == NULL)
00426                 {
00427 #ifdef DEBUG
00428                         fprintf (stdout, "Unable to alloc result [%d] end=%d\n",result->len, format.second);
00429 #endif
00430                         LM_ERR("unable to alloc pkg memory\n");
00431                         return -3;
00432                 }
00433 #ifdef DEBUG
00434         fprintf (stdout, "[pass=%d][Allocated %d bytes][first=%d][lengthsec=%d]\nAdding [%d] ->%.*s\n",format.password.len,result->len,format.first,uri.len-format.second,format.first, format.first,uri.s);fflush (stdout);
00435 #endif
00436                 
00437         res = snprintf(pos,result->len,"%.*s%s%c%.*s%c%.*s%c%.*s%c%.*s%c%.*s@",format.first,uri.s,encoding_prefix,separator,
00438         format.username.len,format.username.s,separator,format.password.len,format.password.s,
00439         separator,format.ip.len,format.ip.s,separator,format.port.len,format.port.s,separator,format.protocol.len,format.protocol.s);
00440 
00441         if ((res < 0 )||(res>result->len)) 
00442                 {
00443                         LM_ERR("unable to construct new uri.\n");
00444                         if (result->s != NULL) pkg_free(result->s);
00445                         return -4;
00446                 }
00447 #ifdef DEBUG
00448         fprintf(stdout,"res= %d\npos=%s\n",res,pos);
00449 #endif
00450         pos = pos + res ;/* overwriting the \0 from snprintf */
00451         memcpy (pos, public_ip, strlen (public_ip));
00452         pos = pos + strlen (public_ip);
00453         memcpy (pos, uri.s + format.second, uri.len - format.second);
00454 
00455 #ifdef DEBUG    
00456         fprintf (stdout, "Adding2 [%d] ->%.*s\n", uri.len - format.second,uri.len - format.second, uri.s + format.second);
00457         fprintf (stdout, "NEW NEW uri is->[%.*s]\n", result->len, result->s);
00458 #endif
00459 
00460         /* Because called parse_uri format contains pointers to the inside of msg,must not deallocate */
00461 
00462         return 0;
00463 }
00464 
00465 
00466 int
00467 decode2format (str uri, char separator, struct uri_format *format)
00468 {
00469         char *start, *end, *pos,*lastpos;
00470         str tmp;
00471         enum {EX_PREFIX=0,EX_USER,EX_PASS,EX_IP,EX_PORT,EX_PROT,EX_FINAL} state;
00472 
00473         //memset (format, 0, sizeof ((struct uri_format)));
00474 
00475         if (uri.s == NULL)
00476                 {
00477                 LM_ERR("invalid parameter uri.It is NULL\n");
00478                 return -1;
00479                 }
00480         /* sip:enc_pref*username*password*ip*port*protocol@public_ip */
00481         
00482         start = memchr (uri.s, ':', uri.len);
00483         if (start == NULL)
00484         {
00485                 LM_ERR("invalid SIP uri.Missing :\n");
00486                 return -2;
00487         }                       /* invalid uri */
00488         start = start + 1;      /* jumping over sip: ATENTIE LA BUFFER OVERFLOW DACA E DOAR sip: */
00489         format->first = start - uri.s;
00490         
00491         /* start */
00492 
00493         end = memchr(start,'@',uri.len-(start-uri.s));
00494         if (end == NULL) 
00495                 {
00496                 LM_ERR("invalid SIP uri.Missing @\n");
00497                 return -3;/* no host address found */
00498                 }
00499 
00500 #ifdef DEBUG
00501                 fprintf (stdout, "Decoding %.*s\n", (int)(long)(end-start), start);
00502 #endif
00503         
00504         state = EX_PREFIX;
00505         lastpos = start;
00506         
00507         for (pos = start;pos<end;pos++)
00508                 {
00509                         if (*pos == separator)
00510                                 {
00511                                         /* we copy between lastpos and pos */
00512                                         tmp.len = pos - lastpos;
00513                                         if (tmp.len>0) tmp.s = lastpos;
00514                                                 else tmp.s = NULL;
00515                                         switch (state)
00516                                                 {
00517                                                         case EX_PREFIX: state = EX_USER;break;
00518                                                         case EX_USER:format->username = tmp;state = EX_PASS;break;
00519                                                         case EX_PASS:format->password = tmp;state = EX_IP;break;
00520                                                         case EX_IP:format->ip = tmp;state = EX_PORT;break;
00521                                                         case EX_PORT:format->port = tmp;state = EX_PROT;break;
00522                                                         default:
00523                                                                 {
00524                                                                 /* this should not happen, we should find @ not separator */
00525                                                                 return -4;
00526                                                                 break;
00527                                                                 }
00528                                                 }
00529                                                 
00530                                         lastpos = pos+1;
00531                                 
00532                                 }
00533                         else
00534                         if (((*pos) == '>')||(*pos == ';'))
00535                                 {
00536                                 /* invalid chars inside username part */
00537                                 return -5;
00538                                 }
00539                 }
00540                 
00541                 
00542         /* we must be in state EX_PROT and protocol is between lastpos and end@ */
00543         if (state != EX_PROT) return -6;
00544         format->protocol.len = end - lastpos;
00545         if (format->protocol.len>0) format->protocol.s = lastpos;
00546                 else format->protocol.s = NULL;
00547         /* I should check perhaps that  after @ there is something */
00548                 
00549 #ifdef DEBUG
00550                 fprintf (stdout, "username=%.*s\n", format->username.len,format->username.s);
00551                 fprintf (stdout, "password=%.*s\n", format->password.len,format->password.s);
00552                 fprintf (stdout, "ip=%.*s\n", format->ip.len, format->ip.s);
00553                 fprintf (stdout, "port=%.*s\n", format->port.len,format->port.s);
00554                 fprintf (stdout, "protocol=%.*s\n", format->protocol.len,format->protocol.s);
00555 #endif
00556 
00557         /* looking for the end of public ip */
00558         start = end;/*we are now at @ */
00559         for(pos = start;pos<uri.s+uri.len;pos++)
00560                 {
00561                         if ((*pos == ';')||(*pos == '>'))
00562                                 {
00563                                 /* found end */
00564                                 format->second = pos - uri.s;
00565                                 return 0;
00566                                 }
00567                 }
00568         /* if we are here we did not find > or ; */
00569         format->second = uri.len;
00570         return 0;       
00571         
00572 }
00573 
00574 
00575 int
00576 decode_uri (str uri, char separator, str * result)
00577 {
00578         char *pos;
00579         struct uri_format format;
00580         int foo;
00581 
00582         result->s = NULL;
00583         result->len = 0;
00584 
00585         if ((uri.len <= 0) || (uri.s == NULL))
00586                 {
00587                 LM_ERR("invalid value for uri\n");
00588                 return -1;
00589                 }
00590 
00591         foo = decode2format (uri, separator, &format);
00592         if (foo < 0)
00593                 {
00594                 LM_ERR("failed to decode Contact uri .Error code %d\n",foo);
00595                 return foo - 20;
00596                 }
00597         /* sanity check */
00598         if (format.ip.len <= 0)
00599                 {
00600                         LM_ERR("unable to decode host address \n");
00601                         return -2;/* should I quit or ignore ? */
00602                 }                       
00603 
00604         if ((format.password.len > 0) && (format.username.len <= 0))
00605                 {
00606                         LM_ERR("password decoded but no username available\n");
00607                         return -3;
00608                 }
00609                 
00610         /* a complete uri would be sip:username:password@ip:port;transport=protocol goes to
00611          * sip:enc_pref#username#password#ip#port#protocol@public_ip
00612          */
00613         result->len = format.first + (uri.len - format.second); /* not NULL terminated */
00614         if (format.username.len > 0) result->len += format.username.len + 1;    //: or @
00615         if (format.password.len > 0) result->len += format.password.len + 1;    //@
00616                 
00617         /* if (format.ip.len > 0) */         result->len += format.ip.len;
00618                 
00619         if (format.port.len > 0)     result->len += 1 + format.port.len;        //:
00620         if (format.protocol.len > 0) result->len += 1 + 10 + format.protocol.len;       //;transport=
00621 #ifdef DEBUG
00622         fprintf (stdout, "Result size is %d.Original Uri size is %d\n",result->len, uri.len);
00623 #endif
00624         
00625         /* adding one comes from * */
00626         result->s = pkg_malloc (result->len);
00627         if (result->s == NULL)
00628                 {
00629                         LM_ERR("unable to allocate pkg memory\n");
00630                         return -4;
00631                 }
00632         pos = result->s;
00633 #ifdef DEBUG
00634         fprintf (stdout, "Adding [%d] ->%.*s\n", format.first, format.first,uri.s);fflush (stdout);
00635 #endif
00636         memcpy (pos, uri.s, format.first);      /* till sip: */
00637         pos = pos + format.first;
00638         
00639         if (format.username.len > 0)
00640         {
00641                 memcpy (pos, format.username.s, format.username.len);
00642                 pos = pos + format.username.len;
00643                 if (format.password.len > 0)
00644                         memcpy (pos, ":", 1);
00645                 else
00646                         memcpy (pos, "@", 1);
00647                 pos = pos + 1;
00648         }
00649         if (format.password.len > 0)
00650         {
00651                 memcpy (pos, format.password.s, format.password.len);
00652                 pos = pos + format.password.len;
00653                 memcpy (pos, "@", 1);
00654                 pos = pos + 1;
00655         }
00656         /* if (format.ip.len > 0) */
00657 
00658                 memcpy (pos, format.ip.s, format.ip.len);
00659                 pos = pos + format.ip.len;
00660         
00661         if (format.port.len > 0)
00662         {
00663                 memcpy (pos, ":", 1);
00664                 pos = pos + 1;
00665                 memcpy (pos, format.port.s, format.port.len);
00666                 pos = pos + format.port.len;
00667         }
00668         if (format.protocol.len > 0)
00669         {
00670                 memcpy (pos, ";transport=", 11);
00671                 pos = pos + 11;
00672                 memcpy (pos, format.protocol.s, format.protocol.len);
00673                 pos = pos + format.protocol.len;
00674         }
00675 
00676 #ifdef DEBUG
00677         fprintf (stdout, "Adding2 [%d] ->%.*s\n", uri.len - format.second,uri.len - format.second, uri.s + format.second);fflush (stdout);
00678 #endif
00679 
00680         memcpy (pos, uri.s + format.second, uri.len - format.second);   /* till end: */
00681 
00682 #ifdef DEBUG
00683         fprintf (stdout, "New decoded uri is->[%.*s]\n", result->len,result->s);
00684 #endif
00685 
00686         return 0;
00687 }
00688