00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050 #include <stdlib.h>
00051 #include <string.h>
00052 #include "../dprint.h"
00053 #include "../ut.h"
00054 #include "../mem/mem.h"
00055 #include "../ip_addr.h"
00056 #include "parse_via.h"
00057 #include "parse_def.h"
00058
00059
00060
00061
00062 enum {
00063 F_HOST, P_HOST,
00064 L_PORT, F_PORT, P_PORT,
00065 L_PARAM, F_PARAM, P_PARAM,
00066 L_VIA, F_VIA,
00067 F_COMMENT, P_COMMENT,
00068 F_IP6HOST, P_IP6HOST,
00069 F_CRLF,
00070 F_LF,
00071 F_CR,
00072 END_OF_HEADER
00073 };
00074
00075
00076
00077 enum {
00078 F_SIP = 100,
00079 SIP1, SIP2, FIN_SIP,
00080 L_VER, F_VER,
00081 VER1, VER2, FIN_VER,
00082 UDP1, UDP2, FIN_UDP,
00083 TCP_TLS1, TCP2, FIN_TCP,
00084 TLS2, FIN_TLS,
00085 SCTP1, SCTP2, SCTP3, FIN_SCTP,
00086 L_PROTO, F_PROTO
00087 };
00088
00089
00090
00091
00092
00093 enum {
00094 L_VALUE = 200, F_VALUE, P_VALUE, P_STRING,
00095 HIDDEN1, HIDDEN2, HIDDEN3, HIDDEN4, HIDDEN5,
00096 TTL1, TTL2,
00097 BRANCH1, BRANCH2, BRANCH3, BRANCH4, BRANCH5,
00098 MADDR1, MADDR2, MADDR3, MADDR4,
00099 RECEIVED1, RECEIVED2, RECEIVED3, RECEIVED4, RECEIVED5, RECEIVED6,
00100 RECEIVED7,
00101 RPORT1, RPORT2, RPORT3,
00102 ALIAS1, ALIAS2, ALIAS3, ALIAS4,
00103
00104 FIN_HIDDEN = 230, FIN_TTL, FIN_BRANCH,
00105 FIN_MADDR, FIN_RECEIVED, FIN_RPORT, FIN_I, FIN_ALIAS
00106
00107
00108 };
00109
00110
00111
00112
00113
00114
00115
00116
00117 static char* parse_via_param(char* p, char* end,
00118 unsigned char* pstate,
00119 unsigned char* psaved_state,
00120 struct via_param* param)
00121 {
00122 char* tmp;
00123 register unsigned char state;
00124 unsigned char saved_state;
00125
00126 state=*pstate;
00127
00128 saved_state=*psaved_state;
00129 param->type=PARAM_ERROR;
00130
00131 for (tmp=p;tmp<end;tmp++){
00132 switch(*tmp){
00133 case ' ':
00134 case '\t':
00135 switch(state){
00136 case FIN_HIDDEN:
00137 case FIN_ALIAS:
00138 param->type=state;
00139 param->name.len=tmp-param->name.s;
00140 state=L_PARAM;
00141 goto endofparam;
00142 case FIN_BRANCH:
00143 case FIN_TTL:
00144 case FIN_MADDR:
00145 case FIN_RECEIVED:
00146 case FIN_RPORT:
00147 case FIN_I:
00148 param->type=state;
00149 param->name.len=tmp-param->name.s;
00150 state=L_VALUE;
00151 goto find_value;
00152 case F_PARAM:
00153 break;
00154 case F_LF:
00155 case F_CR:
00156 case F_CRLF:
00157 state=saved_state;
00158 break;
00159 case GEN_PARAM:
00160 default:
00161 param->type=GEN_PARAM;
00162 param->name.len=tmp-param->name.s;
00163 state=L_VALUE;
00164 goto find_value;
00165 }
00166 break;
00167
00168 case '\n':
00169 switch(state){
00170 case FIN_HIDDEN:
00171 case FIN_ALIAS:
00172 param->type=state;
00173 param->name.len=tmp-param->name.s;
00174 param->size=tmp-param->start;
00175 saved_state=L_PARAM;
00176 state=F_LF;
00177 goto endofparam;
00178 case FIN_BRANCH:
00179 case FIN_TTL:
00180 case FIN_MADDR:
00181 case FIN_RECEIVED:
00182 case FIN_I:
00183 case FIN_RPORT:
00184 param->type=state;
00185 param->name.len=tmp-param->name.s;
00186 param->size=tmp-param->start;
00187 saved_state=L_VALUE;
00188 state=F_LF;
00189 goto find_value;
00190 case F_PARAM:
00191 saved_state=state;
00192 state=F_LF;
00193 break;
00194 case F_LF:
00195 case F_CRLF:
00196 state=END_OF_HEADER;
00197 goto end_via;
00198 case F_CR:
00199 state=F_CRLF;
00200 break;
00201 case GEN_PARAM:
00202 default:
00203 param->type=GEN_PARAM;
00204 saved_state=L_VALUE;
00205 param->name.len=tmp-param->name.s;
00206 param->size=tmp-param->start;
00207 state=F_LF;
00208 goto find_value;
00209 }
00210 break;
00211 case '\r':
00212 switch(state){
00213 case FIN_HIDDEN:
00214 case FIN_ALIAS:
00215 param->type=state;
00216 param->name.len=tmp-param->name.s;
00217 param->size=tmp-param->start;
00218 saved_state=L_PARAM;
00219 state=F_CR;
00220 goto endofparam;
00221 case FIN_BRANCH:
00222 case FIN_TTL:
00223 case FIN_MADDR:
00224 case FIN_RECEIVED:
00225 case FIN_I:
00226 case FIN_RPORT:
00227 param->type=state;
00228 param->name.len=tmp-param->name.s;
00229 param->size=tmp-param->start;
00230 saved_state=L_VALUE;
00231 state=F_CR;
00232 goto find_value;
00233 case F_PARAM:
00234 saved_state=state;
00235 state=F_CR;
00236 break;
00237 case F_CR:
00238 case F_CRLF:
00239 state=END_OF_HEADER;
00240 goto end_via;
00241 case GEN_PARAM:
00242 default:
00243 param->type=GEN_PARAM;
00244 param->name.len=tmp-param->name.s;
00245 param->size=tmp-param->start;
00246 saved_state=L_VALUE;
00247 state=F_CR;
00248 goto find_value;
00249 }
00250 break;
00251
00252 case '=':
00253 switch(state){
00254 case FIN_BRANCH:
00255 case FIN_TTL:
00256 case FIN_MADDR:
00257 case FIN_RECEIVED:
00258 case FIN_RPORT:
00259 case FIN_I:
00260 param->type=state;
00261 param->name.len=tmp-param->name.s;
00262 state=F_VALUE;
00263 goto find_value;
00264 case F_PARAM:
00265 case FIN_HIDDEN:
00266 case FIN_ALIAS:
00267 LM_ERR("invalid char <%c> in state %d\n", *tmp, state);
00268 goto error;
00269 case F_CR:
00270 case F_LF:
00271 case F_CRLF:
00272 state=END_OF_HEADER;
00273 goto end_via;
00274 case GEN_PARAM:
00275 default:
00276 param->type=GEN_PARAM;
00277 param->name.len=tmp-param->name.s;
00278 state=F_VALUE;
00279 goto find_value;
00280 }
00281 break;
00282 case ';':
00283 switch(state){
00284 case FIN_HIDDEN:
00285 case FIN_RPORT:
00286 case FIN_ALIAS:
00287 param->type=state;
00288 param->name.len=tmp-param->name.s;
00289 state=F_PARAM;
00290 goto endofparam;
00291 case FIN_BRANCH:
00292 case FIN_MADDR:
00293 case FIN_TTL:
00294 case FIN_RECEIVED:
00295 case FIN_I:
00296 LM_ERR("invalid char <%c> in state %d\n", *tmp, state);
00297 goto error;
00298 case F_CR:
00299 case F_LF:
00300 case F_CRLF:
00301 state=END_OF_HEADER;
00302 goto end_via;
00303 case GEN_PARAM:
00304 default:
00305 param->type=GEN_PARAM;
00306 param->name.len=tmp-param->name.s;
00307 state=F_PARAM;
00308 goto endofparam;
00309 }
00310 break;
00311 case ',':
00312 switch(state){
00313 case FIN_HIDDEN:
00314 case FIN_RPORT:
00315 case FIN_ALIAS:
00316 param->type=state;
00317 param->name.len=tmp-param->name.s;
00318 state=F_VIA;
00319 goto endofvalue;
00320 case FIN_BRANCH:
00321 case FIN_MADDR:
00322 case FIN_TTL:
00323 case FIN_RECEIVED:
00324 case FIN_I:
00325 LM_ERR("new via found (',') when '=' expected"
00326 "(state %d=)\n", state);
00327 goto error;
00328 case F_CR:
00329 case F_LF:
00330 case F_CRLF:
00331 state=END_OF_HEADER;
00332 goto end_via;
00333 case GEN_PARAM:
00334 default:
00335 param->type=GEN_PARAM;
00336 param->name.len=tmp-param->name.s;
00337 state=F_VIA;
00338 goto endofvalue;
00339 }
00340 break;
00341
00342
00343 case 'h':
00344 case 'H':
00345 switch(state){
00346 case F_PARAM:
00347 state=HIDDEN1;
00348 param->name.s=tmp;
00349 break;
00350 case BRANCH5:
00351 state=FIN_BRANCH;
00352 break;
00353 case GEN_PARAM:
00354 break;
00355 case F_CR:
00356 case F_LF:
00357 case F_CRLF:
00358 state=END_OF_HEADER;
00359 goto end_via;
00360 default:
00361 state=GEN_PARAM;
00362 }
00363 break;
00364 case 'i':
00365 case 'I':
00366 switch(state){
00367 case F_PARAM:
00368 state=FIN_I;
00369 param->name.s=tmp;
00370 break;
00371 case HIDDEN1:
00372 state=HIDDEN2;
00373 break;
00374 case RECEIVED4:
00375 state=RECEIVED5;
00376 break;
00377 case ALIAS2:
00378 state=ALIAS3;
00379 break;
00380 case GEN_PARAM:
00381 break;
00382 case F_CR:
00383 case F_LF:
00384 case F_CRLF:
00385 state=END_OF_HEADER;
00386 goto end_via;
00387 default:
00388 state=GEN_PARAM;
00389 }
00390 break;
00391 case 'd':
00392 case 'D':
00393 switch(state){
00394 case F_PARAM:
00395 state=GEN_PARAM;
00396 param->name.s=tmp;
00397 break;
00398 case HIDDEN2:
00399 state=HIDDEN3;
00400 break;
00401 case HIDDEN3:
00402 state=HIDDEN4;
00403 break;
00404 case MADDR2:
00405 state=MADDR3;
00406 break;
00407 case MADDR3:
00408 state=MADDR4;
00409 break;
00410 case RECEIVED7:
00411 state=FIN_RECEIVED;
00412 break;
00413 case GEN_PARAM:
00414 break;
00415 case F_CR:
00416 case F_LF:
00417 case F_CRLF:
00418 state=END_OF_HEADER;
00419 goto end_via;
00420 default:
00421 state=GEN_PARAM;
00422 }
00423 break;
00424 case 'e':
00425 case 'E':
00426 switch(state){
00427 case F_PARAM:
00428 state=GEN_PARAM;
00429 param->name.s=tmp;
00430 break;
00431 case HIDDEN4:
00432 state=HIDDEN5;
00433 break;
00434 case RECEIVED1:
00435 state=RECEIVED2;
00436 break;
00437 case RECEIVED3:
00438 state=RECEIVED4;
00439 break;
00440 case RECEIVED6:
00441 state=RECEIVED7;
00442 break;
00443 case GEN_PARAM:
00444 break;
00445 case F_CR:
00446 case F_LF:
00447 case F_CRLF:
00448 state=END_OF_HEADER;
00449 goto end_via;
00450 default:
00451 state=GEN_PARAM;
00452 }
00453 break;
00454 case 'n':
00455 case 'N':
00456 switch(state){
00457 case F_PARAM:
00458 state=GEN_PARAM;
00459 param->name.s=tmp;
00460 break;
00461 case HIDDEN5:
00462 state=FIN_HIDDEN;
00463 break;
00464 case BRANCH3:
00465 state=BRANCH4;
00466 break;
00467 case GEN_PARAM:
00468 break;
00469 case F_CR:
00470 case F_LF:
00471 case F_CRLF:
00472 state=END_OF_HEADER;
00473 goto end_via;
00474 default:
00475 state=GEN_PARAM;
00476 }
00477 break;
00478 case 't':
00479 case 'T':
00480 switch(state){
00481 case F_PARAM:
00482 state=TTL1;
00483 param->name.s=tmp;
00484 break;
00485 case TTL1:
00486 state=TTL2;
00487 break;
00488 case RPORT3:
00489 state=FIN_RPORT;
00490 break;
00491 case GEN_PARAM:
00492 break;
00493 case F_CR:
00494 case F_LF:
00495 case F_CRLF:
00496 state=END_OF_HEADER;
00497 goto end_via;
00498 default:
00499 state=GEN_PARAM;
00500 }
00501 break;
00502 case 'l':
00503 case 'L':
00504 switch(state){
00505 case F_PARAM:
00506 state=GEN_PARAM;
00507 param->name.s=tmp;
00508 break;
00509 case TTL2:
00510 state=FIN_TTL;
00511 break;
00512 case ALIAS1:
00513 state=ALIAS2;
00514 break;
00515 case GEN_PARAM:
00516 break;
00517 case F_CR:
00518 case F_LF:
00519 case F_CRLF:
00520 state=END_OF_HEADER;
00521 goto end_via;
00522 default:
00523 state=GEN_PARAM;
00524 }
00525 break;
00526 case 'm':
00527 case 'M':
00528 switch(state){
00529 case F_PARAM:
00530 state=MADDR1;
00531 param->name.s=tmp;
00532 break;
00533 case GEN_PARAM:
00534 break;
00535 case F_CR:
00536 case F_LF:
00537 case F_CRLF:
00538 state=END_OF_HEADER;
00539 goto end_via;
00540 default:
00541 state=GEN_PARAM;
00542 }
00543 break;
00544 case 'a':
00545 case 'A':
00546 switch(state){
00547 case F_PARAM:
00548 state=ALIAS1;
00549 param->name.s=tmp;
00550 break;
00551 case MADDR1:
00552 state=MADDR2;
00553 break;
00554 case BRANCH2:
00555 state=BRANCH3;
00556 break;
00557 case ALIAS3:
00558 state=ALIAS4;
00559 break;
00560 case GEN_PARAM:
00561 break;
00562 case F_CR:
00563 case F_LF:
00564 case F_CRLF:
00565 state=END_OF_HEADER;
00566 goto end_via;
00567 default:
00568 state=GEN_PARAM;
00569 }
00570 break;
00571 case 'r':
00572 case 'R':
00573 switch(state){
00574 case MADDR4:
00575 state=FIN_MADDR;
00576 break;
00577 case F_PARAM:
00578 state=RECEIVED1;
00579 param->name.s=tmp;
00580 break;
00581 case BRANCH1:
00582 state=BRANCH2;
00583 break;
00584 case RPORT2:
00585 state=RPORT3;
00586 break;
00587 case GEN_PARAM:
00588 break;
00589 case F_CR:
00590 case F_LF:
00591 case F_CRLF:
00592 state=END_OF_HEADER;
00593 goto end_via;
00594 default:
00595 state=GEN_PARAM;
00596 }
00597 break;
00598 case 'c':
00599 case 'C':
00600 switch(state){
00601 case F_PARAM:
00602 state=GEN_PARAM;
00603 param->name.s=tmp;
00604 break;
00605 case RECEIVED2:
00606 state=RECEIVED3;
00607 break;
00608 case BRANCH4:
00609 state=BRANCH5;
00610 break;
00611 case GEN_PARAM:
00612 break;
00613 case F_CR:
00614 case F_LF:
00615 case F_CRLF:
00616 state=END_OF_HEADER;
00617 goto end_via;
00618 default:
00619 state=GEN_PARAM;
00620 }
00621 break;
00622 case 'v':
00623 case 'V':
00624 switch(state){
00625 case F_PARAM:
00626 state=GEN_PARAM;
00627 param->name.s=tmp;
00628 break;
00629 case RECEIVED5:
00630 state=RECEIVED6;
00631 break;
00632 case GEN_PARAM:
00633 break;
00634 case F_CR:
00635 case F_LF:
00636 case F_CRLF:
00637 state=END_OF_HEADER;
00638 goto end_via;
00639 default:
00640 state=GEN_PARAM;
00641 }
00642 break;
00643 case 'b':
00644 case 'B':
00645 switch(state){
00646 case F_PARAM:
00647 state=BRANCH1;
00648 param->name.s=tmp;
00649 break;
00650 case GEN_PARAM:
00651 break;
00652 case F_CR:
00653 case F_LF:
00654 case F_CRLF:
00655 state=END_OF_HEADER;
00656 goto end_via;
00657 default:
00658 state=GEN_PARAM;
00659 }
00660 break;
00661 case 'p':
00662 case 'P':
00663 switch(state){
00664 case F_PARAM:
00665 state=GEN_PARAM;
00666 param->name.s=tmp;
00667 break;
00668 case RECEIVED1:
00669 state=RPORT1;
00670 break;
00671 case F_CR:
00672 case F_LF:
00673 case F_CRLF:
00674 state=END_OF_HEADER;
00675 goto end_via;
00676 default:
00677 state=GEN_PARAM;
00678 }
00679 break;
00680 case 'o':
00681 case 'O':
00682 switch(state){
00683 case F_PARAM:
00684 state=GEN_PARAM;
00685 param->name.s=tmp;
00686 break;
00687 case RPORT1:
00688 state=RPORT2;
00689 break;
00690 case F_CR:
00691 case F_LF:
00692 case F_CRLF:
00693 state=END_OF_HEADER;
00694 goto end_via;
00695 default:
00696 state=GEN_PARAM;
00697 }
00698 break;
00699 case 's':
00700 case 'S':
00701 switch(state){
00702 case F_PARAM:
00703 state=GEN_PARAM;
00704 param->name.s=tmp;
00705 break;
00706 case ALIAS4:
00707 state=FIN_ALIAS;
00708 break;
00709 case F_CR:
00710 case F_LF:
00711 case F_CRLF:
00712 state=END_OF_HEADER;
00713 goto end_via;
00714 default:
00715 state=GEN_PARAM;
00716 }
00717 break;
00718 default:
00719 switch(state){
00720 case F_PARAM:
00721 state=GEN_PARAM;
00722 param->name.s=tmp;
00723 break;
00724 case GEN_PARAM:
00725 break;
00726 case F_CR:
00727 case F_LF:
00728 case F_CRLF:
00729 state=END_OF_HEADER;
00730 goto end_via;
00731 default:
00732 state=GEN_PARAM;
00733 }
00734 }
00735 }
00736
00737
00738 saved_state=state;
00739 state=END_OF_HEADER;
00740 goto error;
00741
00742 find_value:
00743 tmp++;
00744 for(;*tmp;tmp++){
00745 switch(*tmp){
00746 case ' ':
00747 case '\t':
00748 switch(state){
00749 case L_VALUE:
00750 case F_VALUE:
00751 break;
00752 case P_VALUE:
00753 state=L_PARAM;
00754 param->value.len=tmp-param->value.s;
00755 goto endofvalue;
00756 case P_STRING:
00757 break;
00758 case F_CR:
00759 case F_LF:
00760 case F_CRLF:
00761 state=saved_state;
00762 break;
00763 default:
00764 LM_ERR("invalid char <%c> in state %d\n", *tmp, state);
00765 goto error;
00766 }
00767 break;
00768 case '\n':
00769 switch(state){
00770 case L_VALUE:
00771 case F_VALUE:
00772 case P_STRING:
00773 saved_state=state;
00774 param->size=tmp-param->start;
00775 state=F_LF;
00776 break;
00777 case P_VALUE:
00778 saved_state=L_PARAM;
00779 state=F_LF;
00780 param->value.len=tmp-param->value.s;
00781 goto endofvalue;
00782 case F_LF:
00783 case F_CRLF:
00784 state=END_OF_HEADER;
00785 goto end_via;
00786 case F_CR:
00787 state=F_CRLF;
00788 break;
00789 default:
00790 LM_ERR("invalid char <%c> in state %d\n", *tmp, state);
00791 goto error;
00792 }
00793 break;
00794 case '\r':
00795 switch(state){
00796 case L_VALUE:
00797 case F_VALUE:
00798 case P_STRING:
00799 saved_state=state;
00800 param->size=tmp-param->start;
00801 state=F_CR;
00802 break;
00803 case P_VALUE:
00804 param->value.len=tmp-param->value.s;
00805 saved_state=L_PARAM;
00806 state=F_CR;
00807 goto endofvalue;
00808 case F_LF:
00809 case F_CR:
00810 case F_CRLF:
00811 state=END_OF_HEADER;
00812 goto end_via;
00813 default:
00814 LM_ERR("invalid char <%c> in state %d\n", *tmp, state);
00815 goto error;
00816 }
00817 break;
00818
00819 case '=':
00820 switch(state){
00821 case L_VALUE:
00822 state=F_VALUE;
00823 break;
00824 case P_STRING:
00825 break;
00826 case F_LF:
00827 case F_CR:
00828 case F_CRLF:
00829 state=END_OF_HEADER;
00830 goto end_via;
00831 default:
00832 LM_ERR("invalid char <%c> in state %d\n", *tmp, state);
00833 goto error;
00834 }
00835 break;
00836 case ';':
00837 switch(state){
00838 case P_VALUE:
00839 param->value.len=tmp-param->value.s;
00840 state=F_PARAM;
00841 goto endofvalue;
00842 case F_VALUE:
00843 param->value.len=0;
00844 state=F_PARAM;
00845 goto endofvalue;
00846 case P_STRING:
00847 break;
00848 case F_LF:
00849 case F_CR:
00850 case F_CRLF:
00851 state=END_OF_HEADER;
00852 goto end_via;
00853 case L_VALUE:
00854 if (param->type==FIN_RPORT){
00855 param->value.len=0;
00856 param->value.s=0;
00857 state=F_PARAM;
00858 goto endofvalue;
00859 };
00860
00861 default:
00862 LM_ERR("invalid char <%c> in state %d\n", *tmp, state);
00863 goto error;
00864 }
00865 break;
00866 case ',':
00867 switch(state){
00868 case P_VALUE:
00869 param->value.len=tmp-param->value.s;
00870 state=F_VIA;
00871 goto endofvalue;
00872 case P_STRING:
00873 case F_LF:
00874 case F_CR:
00875 case F_CRLF:
00876 state=END_OF_HEADER;
00877 goto end_via;
00878 case L_VALUE:
00879 if (param->type==FIN_RPORT){
00880 param->value.len=0;
00881 param->value.s=0;
00882 state=F_VIA;
00883 goto endofvalue;
00884 };
00885
00886 default:
00887 LM_ERR("invalid char <%c> in state %d\n", *tmp, state);
00888 goto error;
00889 }
00890 break;
00891 case '"':
00892 switch(state){
00893 case F_VALUE:
00894 state=P_STRING;
00895 param->value.s=tmp+1;
00896 break;
00897 case P_STRING:
00898 state=L_PARAM;
00899 param->value.len=tmp-param->value.s;
00900 goto endofvalue;
00901 case F_LF:
00902 case F_CR:
00903 case F_CRLF:
00904 state=END_OF_HEADER;
00905 goto end_via;
00906 default:
00907 LM_ERR("invalid char <%c> in state %d\n", *tmp, state);
00908 goto error;
00909 }
00910 break;
00911 default:
00912 switch(state){
00913 case F_VALUE:
00914 state=P_VALUE;
00915 param->value.s=tmp;
00916 break;
00917 case P_VALUE:
00918 case P_STRING:
00919 break;
00920 case F_LF:
00921 case F_CR:
00922 case F_CRLF:
00923 state=END_OF_HEADER;
00924 goto end_via;
00925 default:
00926 LM_ERR("invalid char <%c> in state %d\n", *tmp, state);
00927 goto error;
00928 }
00929 }
00930 }
00931
00932
00933 saved_state=state;
00934 state=END_OF_HEADER;
00935 goto error;
00936
00937 endofparam:
00938 endofvalue:
00939 param->size=tmp-param->start;
00940 normal_exit:
00941 *pstate=state;
00942 *psaved_state=saved_state;
00943 LM_DBG("found param type %d, <%.*s> = <%.*s>; state=%d\n", param->type,
00944 param->name.len, ZSW(param->name.s),
00945 (param->value.len?param->value.len:3),
00946 (param->value.len?param->value.s:"n/a"), state);
00947 return tmp;
00948
00949 end_via:
00950
00951
00952
00953
00954 if ((param->type==GEN_PARAM)||(param->type==PARAM_RPORT)){
00955 saved_state=L_PARAM;
00956
00957
00958 goto normal_exit;
00959 }
00960 *pstate=state;
00961 *psaved_state=saved_state;
00962 LM_DBG("error on param type %d, <%.*s>, state=%d, saved_state=%d\n",
00963 param->type, param->name.len, ZSW(param->name.s), state, saved_state);
00964
00965 error:
00966 LM_ERR("parse_via_param\n");
00967 param->type=PARAM_ERROR;
00968 *pstate=PARAM_ERROR;
00969 *psaved_state=state;
00970 return tmp;
00971 }
00972
00973
00974
00975
00976
00977
00978
00979
00980 char* parse_via(char* buffer, char* end, struct via_body *vbody)
00981 {
00982 char* tmp;
00983 char* param_start;
00984 unsigned char state;
00985 unsigned char saved_state;
00986 int c_nest;
00987 int err;
00988 struct via_body* vb;
00989 struct via_param* param;
00990
00991 vb=vbody;
00992
00993 parse_again:
00994 vb->error=PARSE_ERROR;
00995
00996 state=F_SIP;
00997 saved_state=0;
00998 param_start=0;
00999 for(tmp=buffer;tmp<end;tmp++){
01000 switch(*tmp){
01001 case ' ':
01002 case'\t':
01003 switch(state){
01004 case L_VER:
01005 case L_PROTO:
01006 case F_SIP:
01007 case F_VER:
01008 case F_PROTO:
01009 break;
01010 case FIN_UDP:
01011 vb->transport.len=tmp-vb->transport.s;
01012 vb->proto=PROTO_UDP;
01013 state=F_HOST;
01014 goto main_via;
01015 case FIN_TCP:
01016
01017 vb->transport.len=tmp-vb->transport.s;
01018 vb->proto=PROTO_TCP;
01019 state=F_HOST;
01020 goto main_via;
01021 case FIN_TLS:
01022
01023 vb->transport.len=tmp-vb->transport.s;
01024 vb->proto=PROTO_TLS;
01025 state=F_HOST;
01026 goto main_via;
01027 case FIN_SCTP:
01028
01029 vb->transport.len=tmp-vb->transport.s;
01030 vb->proto=PROTO_SCTP;
01031 state=F_HOST;
01032 goto main_via;
01033 case FIN_SIP:
01034 vb->name.len=tmp-vb->name.s;
01035 state=L_VER;
01036 break;
01037 case FIN_VER:
01038 vb->version.len=tmp-vb->version.s;
01039 state=L_PROTO;
01040 break;
01041 case F_LF:
01042 case F_CRLF:
01043 case F_CR:
01044 state=saved_state;
01045 break;
01046 default:
01047 LM_ERR("bad char <%c> on state %d\n", *tmp, state);
01048 goto error;
01049 }
01050 break;
01051 case '\n':
01052 switch(state){
01053 case L_VER:
01054 case F_SIP:
01055 case F_VER:
01056 case F_PROTO:
01057 case L_PROTO:
01058 saved_state=state;
01059 state=F_LF;
01060 break;
01061 case FIN_UDP:
01062 vb->transport.len=tmp-vb->transport.s;
01063 vb->proto=PROTO_UDP;
01064 state=F_LF;
01065 saved_state=F_HOST;
01066 goto main_via;
01067 case FIN_TCP:
01068 vb->transport.len=tmp-vb->transport.s;
01069 vb->proto=PROTO_TCP;
01070 state=F_LF;
01071 saved_state=F_HOST;
01072 goto main_via;
01073 case FIN_TLS:
01074 vb->transport.len=tmp-vb->transport.s;
01075 vb->proto=PROTO_TLS;
01076 state=F_LF;
01077 saved_state=F_HOST;
01078 goto main_via;
01079 case FIN_SIP:
01080 vb->name.len=tmp-vb->name.s;
01081 state=F_LF;
01082 saved_state=L_VER;
01083 break;
01084 case FIN_VER:
01085 vb->version.len=tmp-vb->version.s;
01086 state=F_LF;
01087 saved_state=L_PROTO;
01088 break;
01089 case F_CR:
01090 state=F_CRLF;
01091 break;
01092 case F_LF:
01093 case F_CRLF:
01094 state=saved_state;
01095 goto endofheader;
01096 default:
01097 LM_ERR("bad char <%c> on state %d\n", *tmp, state);
01098 goto error;
01099 }
01100 break;
01101 case '\r':
01102 switch(state){
01103 case L_VER:
01104 case F_SIP:
01105 case F_VER:
01106 case F_PROTO:
01107 case L_PROTO:
01108 saved_state=state;
01109 state=F_CR;
01110 break;
01111 case FIN_UDP:
01112 vb->transport.len=tmp-vb->transport.s;
01113 vb->proto=PROTO_UDP;
01114 state=F_CR;
01115 saved_state=F_HOST;
01116 goto main_via;
01117 case FIN_TCP:
01118 vb->transport.len=tmp-vb->transport.s;
01119 vb->proto=PROTO_TCP;
01120 state=F_CR;
01121 saved_state=F_HOST;
01122 goto main_via;
01123 case FIN_TLS:
01124 vb->transport.len=tmp-vb->transport.s;
01125 vb->proto=PROTO_TLS;
01126 state=F_CR;
01127 saved_state=F_HOST;
01128 goto main_via;
01129 case FIN_SIP:
01130 vb->name.len=tmp-vb->name.s;
01131 state=F_CR;
01132 saved_state=L_VER;
01133 break;
01134 case FIN_VER:
01135 vb->version.len=tmp-vb->version.s;
01136 state=F_CR;
01137 saved_state=L_PROTO;
01138 break;
01139 case F_LF:
01140 case F_CR:
01141 case F_CRLF:
01142 state=saved_state;
01143 goto endofheader;
01144 default:
01145 LM_ERR("bad char <%c> on state %d\n", *tmp, state);
01146 goto error;
01147 }
01148 break;
01149
01150 case '/':
01151 switch(state){
01152 case FIN_SIP:
01153 vb->name.len=tmp-vb->name.s;
01154 state=F_VER;
01155 break;
01156 case FIN_VER:
01157 vb->version.len=tmp-vb->version.s;
01158 state=F_PROTO;
01159 break;
01160 case L_VER:
01161 state=F_VER;
01162 break;
01163 case L_PROTO:
01164 state=F_PROTO;
01165 break;
01166 default:
01167 LM_ERR("bad char <%c> on state %d\n", *tmp, state);
01168 goto error;
01169 }
01170 break;
01171
01172 case 'S':
01173 case 's':
01174 switch(state){
01175 case F_SIP:
01176 state=SIP1;
01177 vb->name.s=tmp;
01178 break;
01179 case TLS2:
01180 state=FIN_TLS;
01181 break;
01182 case F_PROTO:
01183 state=SCTP1;
01184 vb->transport.s=tmp;
01185 break;
01186 default:
01187 LM_ERR("bad char <%c> on state %d\n", *tmp, state);
01188 goto error;
01189 }
01190 break;
01191 case 'I':
01192 case 'i':
01193 switch(state){
01194 case SIP1:
01195 state=SIP2;
01196 break;
01197 default:
01198 LM_ERR("bad char <%c> on state %d\n", *tmp, state);
01199 goto error;
01200 }
01201 break;
01202 case 'p':
01203 case 'P':
01204 switch(state){
01205 case SIP2:
01206 state=FIN_SIP;
01207 break;
01208
01209 case UDP2:
01210 state=FIN_UDP;
01211 break;
01212 case TCP2:
01213 state=FIN_TCP;
01214 break;
01215 case SCTP3:
01216 state=FIN_SCTP;
01217 break;
01218 default:
01219 LM_ERR("bad char <%c> on state %d\n", *tmp, state);
01220 goto error;
01221 }
01222 break;
01223 case 'U':
01224 case 'u':
01225 switch(state){
01226 case F_PROTO:
01227 state=UDP1;
01228 vb->transport.s=tmp;
01229 break;
01230 default:
01231 LM_ERR("bad char <%c> on state %d\n", *tmp, state);
01232 goto error;
01233 }
01234 break;
01235 case 'D':
01236 case 'd':
01237 switch(state){
01238 case UDP1:
01239 state=UDP2;
01240 break;
01241 default:
01242 LM_ERR("bad char <%c> on state %d\n", *tmp, state);
01243 goto error;
01244 }
01245 break;
01246 case 'T':
01247 case 't':
01248 switch(state){
01249 case F_PROTO:
01250 state=TCP_TLS1;
01251 vb->transport.s=tmp;
01252 break;
01253 case SCTP2:
01254 state=SCTP3;
01255 break;
01256 default:
01257 LM_ERR("bad char <%c> on state %d\n", *tmp, state);
01258 goto error;
01259 }
01260 break;
01261 case 'C':
01262 case 'c':
01263 switch(state){
01264 case TCP_TLS1:
01265 state=TCP2;
01266 break;
01267 case SCTP1:
01268 state=SCTP2;
01269 break;
01270 default:
01271 LM_ERR("bad char <%c> on state %d\n", *tmp, state);
01272 goto error;
01273 }
01274 break;
01275 case 'L':
01276 case 'l':
01277 switch(state){
01278 case TCP_TLS1:
01279 state=TLS2;
01280 break;
01281 default:
01282 LM_ERR("bad char <%c> on state %d\n", *tmp, state);
01283 goto error;
01284 }
01285 break;
01286
01287 case '2':
01288 switch(state){
01289 case F_VER:
01290 state=VER1;
01291 vb->version.s=tmp;
01292 break;
01293 default:
01294 LM_ERR("bad char <%c> on state %d\n", *tmp, state);
01295 goto error;
01296 }
01297 break;
01298 case '.':
01299 switch(state){
01300 case VER1:
01301 state=VER2;
01302 break;
01303 default:
01304 LM_ERR("bad char <%c> on state %d\n", *tmp, state);
01305 goto error;
01306 }
01307 break;
01308 case '0':
01309 switch(state){
01310 case VER2:
01311 state=FIN_VER;
01312 break;
01313 default:
01314 LM_ERR("bad char <%c> on state %d\n", *tmp, state);
01315 goto error;
01316 }
01317 break;
01318
01319 default:
01320 LM_ERR("bad char <%c> on state %d\n", *tmp, state);
01321 goto error;
01322 break;
01323 }
01324 }
01325
01326
01327 LM_ERR("bad via: end of packet on state=%d\n", state);
01328 goto error;
01329
01330 main_via:
01331
01332 tmp++;
01333 c_nest=0;
01334 ;
01335 for(;*tmp;tmp++){
01336 switch(*tmp){
01337 case ' ':
01338 case '\t':
01339 switch(state){
01340 case F_HOST:
01341 break;
01342 case P_HOST:
01343
01344 vb->host.len=tmp-vb->host.s;
01345 state=L_PORT;
01346 break;
01347 case L_PORT:
01348 case F_PORT:
01349 break;
01350 case P_PORT:
01351
01352 vb->port_str.len=tmp-vb->port_str.s;
01353 state=L_PARAM;
01354 break;
01355 case L_PARAM:
01356 case F_PARAM:
01357 break;
01358 case P_PARAM:
01359
01360 state=L_PARAM;
01361 break;
01362 case L_VIA:
01363 case F_VIA:
01364 break;
01365 case F_COMMENT:
01366 case P_COMMENT:
01367 break;
01368 case F_IP6HOST:
01369 case P_IP6HOST:
01370 LM_ERR("bad ipv6 reference\n");
01371 goto error;
01372 case F_CRLF:
01373 case F_LF:
01374 case F_CR:
01375
01376 state=saved_state;
01377 break;
01378 default:
01379 LM_CRIT("on <%c>, state=%d\n",*tmp, state);
01380 goto error;
01381 }
01382 break;
01383 case '\n':
01384 switch(state){
01385 case F_HOST:
01386 case L_PORT:
01387 case F_PORT:
01388 case L_PARAM:
01389 case F_PARAM:
01390 case F_VIA:
01391 case L_VIA:
01392 case F_COMMENT:
01393 case P_COMMENT:
01394 case F_IP6HOST:
01395 case P_IP6HOST:
01396 saved_state=state;
01397 state=F_LF;
01398 break;
01399 case P_HOST:
01400
01401 vb->host.len=tmp-vb->host.s;
01402 saved_state=L_PORT;
01403 state=F_LF;
01404 break;
01405 case P_PORT:
01406
01407 vb->port_str.len=tmp-vb->port_str.s;
01408 saved_state=L_PARAM;
01409 state=F_LF;
01410 break;
01411 case P_PARAM:
01412
01413 saved_state=L_PARAM;
01414 state=F_LF;
01415 break;
01416 case F_CR:
01417 state=F_CRLF;
01418 break;
01419 case F_CRLF:
01420 case F_LF:
01421 state=saved_state;
01422 goto endofheader;
01423 default:
01424 LM_CRIT("BUG on <%c>\n",*tmp);
01425 goto error;
01426 }
01427 break;
01428 case '\r':
01429 switch(state){
01430 case F_HOST:
01431 case L_PORT:
01432 case F_PORT:
01433 case L_PARAM:
01434 case F_PARAM:
01435 case F_VIA:
01436 case L_VIA:
01437 case F_COMMENT:
01438 case P_COMMENT:
01439 case F_IP6HOST:
01440 case P_IP6HOST:
01441 saved_state=state;
01442 state=F_CR;
01443 break;
01444 case P_HOST:
01445
01446 vb->host.len=tmp-vb->host.s;
01447 saved_state=L_PORT;
01448 state=F_CR;
01449 break;
01450 case P_PORT:
01451
01452 vb->port_str.len=tmp-vb->port_str.s;
01453 saved_state=L_PARAM;
01454 state=F_CR;
01455 break;
01456 case P_PARAM:
01457
01458 saved_state=L_PARAM;
01459 state=F_CR;
01460 break;
01461 case F_CRLF:
01462 case F_CR:
01463 case F_LF:
01464 state=saved_state;
01465 goto endofheader;
01466 default:
01467 LM_CRIT("on <%c>\n",*tmp);
01468 goto error;
01469 }
01470 break;
01471
01472 case ':':
01473 switch(state){
01474 case F_HOST:
01475 case F_IP6HOST:
01476 state=P_IP6HOST;
01477 break;
01478 case P_IP6HOST:
01479 break;
01480 case P_HOST:
01481
01482 vb->host.len=tmp-vb->host.s;
01483 state=F_PORT;
01484 break;
01485 case L_PORT:
01486 state=F_PORT;
01487 break;
01488 case P_PORT:
01489 LM_ERR("bad port\n");
01490 goto error;
01491 case L_PARAM:
01492 case F_PARAM:
01493 case P_PARAM:
01494 LM_ERR("bad char <%c> in state %d\n",
01495 *tmp,state);
01496 goto error;
01497 case L_VIA:
01498 case F_VIA:
01499 LM_ERR("bad char in compact via\n");
01500 goto error;
01501 case F_CRLF:
01502 case F_LF:
01503 case F_CR:
01504
01505 goto endofheader;
01506 case F_COMMENT:
01507 vb->comment.s=tmp;
01508 state=P_COMMENT;
01509 break;
01510 case P_COMMENT:
01511 break;
01512 default:
01513 LM_CRIT("on <%c> state %d\n", *tmp, state);
01514 goto error;
01515 }
01516 break;
01517 case ';':
01518 switch(state){
01519 case F_HOST:
01520 case F_IP6HOST:
01521 LM_ERR(" no host found\n");
01522 goto error;
01523 case P_IP6HOST:
01524 LM_ERR(" bad ipv6 reference\n");
01525 goto error;
01526 case P_HOST:
01527 vb->host.len=tmp-vb->host.s;
01528 state=F_PARAM;
01529 param_start=tmp+1;
01530 break;
01531 case P_PORT:
01532
01533 vb->port_str.len=tmp-vb->port_str.s;
01534 case L_PORT:
01535 case L_PARAM:
01536 state=F_PARAM;
01537 param_start=tmp+1;
01538 break;
01539 case F_PORT:
01540 LM_ERR(" bad char <%c> in state %d\n",
01541 *tmp,state);
01542 goto error;
01543 case F_PARAM:
01544 LM_ERR("null param?\n");
01545 goto error;
01546 case P_PARAM:
01547
01548 state=F_PARAM;
01549 param_start=tmp+1;
01550 break;
01551 case L_VIA:
01552 case F_VIA:
01553 LM_ERR("bad char <%c> in next via\n", *tmp);
01554 goto error;
01555 case F_CRLF:
01556 case F_LF:
01557 case F_CR:
01558
01559 goto endofheader;
01560 case F_COMMENT:
01561 vb->comment.s=tmp;
01562 state=P_COMMENT;
01563 break;
01564 case P_COMMENT:
01565 break;
01566
01567 default:
01568 LM_CRIT("on <%c> state %d\n", *tmp, state);
01569 goto error;
01570 }
01571 break;
01572 case ',':
01573 switch(state){
01574 case F_HOST:
01575 case F_IP6HOST:
01576 LM_ERR("no host found\n");
01577 goto error;
01578 case P_IP6HOST:
01579 LM_ERR(" bad ipv6 reference\n");
01580 goto error;
01581 case P_HOST:
01582
01583 vb->host.len=tmp-vb->host.s;
01584 state=F_VIA;
01585 break;
01586 case P_PORT:
01587
01588 vb->port_str.len=tmp-vb->port_str.s;
01589 state=F_VIA;
01590 break;
01591 case L_PORT:
01592 case L_PARAM:
01593 case P_PARAM:
01594 case L_VIA:
01595 state=F_VIA;
01596 break;
01597 case F_PORT:
01598 case F_PARAM:
01599 LM_ERR("invalid char <%c> in state %d\n", *tmp,state);
01600 goto error;
01601 case F_VIA:
01602
01603 break;
01604 case F_CRLF:
01605 case F_LF:
01606 case F_CR:
01607
01608 goto endofheader;
01609 case F_COMMENT:
01610 vb->comment.s=tmp;
01611 state=P_COMMENT;
01612 break;
01613 case P_COMMENT:
01614 break;
01615 default:
01616 LM_CRIT("on <%c> state %d\n",*tmp, state);
01617 goto error;
01618 }
01619 break;
01620 case '(':
01621 switch(state){
01622 case F_HOST:
01623 case F_PORT:
01624 case F_PARAM:
01625 case F_VIA:
01626 case F_IP6HOST:
01627 case P_IP6HOST:
01628 LM_ERR(" on <%c> state %d\n", *tmp, state);
01629 goto error;
01630 case P_HOST:
01631
01632 vb->host.len=tmp-vb->host.s;
01633 state=F_COMMENT;
01634 c_nest++;
01635 break;
01636 case P_PORT:
01637
01638 vb->port_str.len=tmp-vb->port_str.s;
01639 state=F_COMMENT;
01640 c_nest++;
01641 break;
01642 case P_PARAM:
01643
01644 vb->params.len=tmp-vb->params.s;
01645 state=F_COMMENT;
01646 c_nest++;
01647 break;
01648 case L_PORT:
01649 case L_PARAM:
01650 case L_VIA:
01651 state=F_COMMENT;
01652 vb->params.len=tmp-vb->params.s;
01653 c_nest++;
01654 break;
01655 case P_COMMENT:
01656 case F_COMMENT:
01657 c_nest++;
01658 break;
01659 case F_CRLF:
01660 case F_LF:
01661 case F_CR:
01662
01663 goto endofheader;
01664 default:
01665 LM_CRIT("on <%c> state %d\n", *tmp, state);
01666 goto error;
01667 }
01668 break;
01669 case ')':
01670 switch(state){
01671 case F_COMMENT:
01672 case P_COMMENT:
01673 if (c_nest){
01674 c_nest--;
01675 if(c_nest==0){
01676 state=L_VIA;
01677 vb->comment.len=tmp-vb->comment.s;
01678 break;
01679 }
01680 }else{
01681 LM_ERR(" missing '(' - nesting= %d\n", c_nest);
01682 goto error;
01683 }
01684 break;
01685 case F_HOST:
01686 case F_PORT:
01687 case F_PARAM:
01688 case F_VIA:
01689 case P_HOST:
01690 case P_PORT:
01691 case P_PARAM:
01692 case L_PORT:
01693 case L_PARAM:
01694 case L_VIA:
01695 case F_IP6HOST:
01696 case P_IP6HOST:
01697 LM_ERR(" on <%c> state %d\n",*tmp, state);
01698 goto error;
01699 case F_CRLF:
01700 case F_LF:
01701 case F_CR:
01702
01703 goto endofheader;
01704 default:
01705 LM_CRIT("on <%c> state %d\n", *tmp, state);
01706 goto error;
01707 }
01708 break;
01709 case '[':
01710 switch(state){
01711 case F_HOST:
01712 vb->host.s=tmp;
01713 state=F_IP6HOST;
01714 break;
01715 case F_COMMENT:
01716 vb->comment.s=tmp;
01717 state=P_COMMENT;
01718 break;
01719 case P_COMMENT:
01720 break;
01721 case F_CRLF:
01722 case F_LF:
01723 case F_CR:
01724
01725 goto endofheader;
01726 default:
01727 LM_ERR("on <%c> state %d\n",*tmp, state);
01728 goto error;
01729 }
01730 break;
01731 case ']':
01732 switch(state){
01733 case P_IP6HOST:
01734
01735 vb->host.len=(tmp-vb->host.s)+1;
01736 state=L_PORT;
01737 break;
01738 case F_CRLF:
01739 case F_LF:
01740 case F_CR:
01741
01742 goto endofheader;
01743 case F_COMMENT:
01744 vb->comment.s=tmp;
01745 state=P_COMMENT;
01746 break;
01747 case P_COMMENT:
01748 break;
01749 default:
01750 LM_ERR("on <%c> state %d\n",*tmp, state);
01751 goto error;
01752 }
01753 break;
01754
01755 default:
01756 switch(state){
01757 case F_HOST:
01758 state=P_HOST;
01759 vb->host.s=tmp;
01760 break;
01761 case P_HOST:
01762 break;
01763 case F_PORT:
01764 state=P_PORT;
01765 vb->port_str.s=tmp;
01766 break;
01767 case P_PORT:
01768
01769 break;
01770 case F_PARAM:
01771 ;
01772 if(vb->params.s==0) vb->params.s=param_start;
01773 param=pkg_malloc(sizeof(struct via_param));
01774 if (param==0){
01775 LM_ERR("no pkg memory left\n");
01776 goto error;
01777 }
01778 memset(param,0, sizeof(struct via_param));
01779 param->start=param_start;
01780 tmp=parse_via_param(tmp, end, &state, &saved_state,
01781 param);
01782
01783 switch(state){
01784 case F_PARAM:
01785 param_start=tmp+1;
01786 case L_PARAM:
01787 case F_LF:
01788 case F_CR:
01789 break;
01790 case F_VIA:
01791 vb->params.len=param->start+param->size
01792 -vb->params.s;
01793 break;
01794 case END_OF_HEADER:
01795 vb->params.len=param->start+param->size
01796 -vb->params.s;
01797 break;
01798 case PARAM_ERROR:
01799 pkg_free(param);
01800 goto error;
01801 default:
01802 pkg_free(param);
01803 LM_ERR(" after parse_via_param: invalid"
01804 " char <%c> on state %d\n",*tmp, state);
01805 goto error;
01806 }
01807
01808 if (vb->last_param) vb->last_param->next=param;
01809 else vb->param_lst=param;
01810 vb->last_param=param;
01811
01812 switch(param->type){
01813 case PARAM_BRANCH:
01814 vb->branch=param;
01815 break;
01816 case PARAM_RECEIVED:
01817 vb->received=param;
01818 break;
01819 case PARAM_RPORT:
01820 vb->rport=param;
01821 break;
01822 case PARAM_I:
01823 vb->i=param;
01824 break;
01825 case PARAM_ALIAS:
01826 vb->alias=param;
01827 break;
01828 case PARAM_MADDR:
01829 vb->maddr=param;
01830 break;
01831 }
01832
01833 if (state==END_OF_HEADER){
01834 state=saved_state;
01835 goto endofheader;
01836 }
01837 break;
01838 case P_PARAM:
01839 break;
01840 case F_VIA:
01841
01842 goto nextvia;
01843 case L_PORT:
01844 case L_PARAM:
01845 case L_VIA:
01846 LM_ERR("on <%c> state %d (default)\n",*tmp, state);
01847 goto error;
01848 case F_COMMENT:
01849 state=P_COMMENT;
01850 vb->comment.s=tmp;
01851 break;
01852 case P_COMMENT:
01853 break;
01854 case F_IP6HOST:
01855 state=P_IP6HOST;
01856 break;
01857 case P_IP6HOST:
01858 break;
01859 case F_CRLF:
01860 case F_LF:
01861 case F_CR:
01862
01863 goto endofheader;
01864 default:
01865 LM_CRIT("invalid char <%c> in state %d\n",*tmp, state);
01866 goto error;
01867 }
01868
01869
01870 }
01871 }
01872
01873 LM_DBG("end of packet reached, state=%d\n", state);
01874 goto endofpacket;
01875
01876 endofheader:
01877 state=saved_state;
01878 LM_DBG("end of header reached, state=%d\n", state);
01879 endofpacket:
01880
01881 switch(state){
01882 case P_HOST:
01883 case L_PORT:
01884 case P_PORT:
01885 case L_PARAM:
01886 case P_PARAM:
01887 case P_VALUE:
01888 case GEN_PARAM:
01889 case FIN_HIDDEN:
01890 case L_VIA:
01891 break;
01892 default:
01893 LM_ERR(" invalid via - end of header in state %d\n", state);
01894 goto error;
01895 }
01896
01897
01898
01899
01900
01901
01902
01903
01904
01905
01906
01907
01908 vb->error=PARSE_OK;
01909 vb->bsize=tmp-buffer;
01910 if (vb->port_str.s){
01911 vb->port=str2s(vb->port_str.s, vb->port_str.len, &err);
01912 if (err){
01913 LM_ERR(" invalid port number <%.*s>\n",
01914 vb->port_str.len, ZSW(vb->port_str.s));
01915 goto error;
01916 }
01917 }
01918 return tmp;
01919 nextvia:
01920 LM_DBG("next_via\n");
01921 vb->error=PARSE_OK;
01922 vb->bsize=tmp-buffer;
01923 if (vb->port_str.s){
01924 vb->port=str2s(vb->port_str.s, vb->port_str.len, &err);
01925 if (err){
01926 LM_ERR(" invalid port number <%.*s>\n",
01927 vb->port_str.len, ZSW(vb->port_str.s));
01928 goto error;
01929 }
01930 }
01931 vb->next=pkg_malloc(sizeof(struct via_body));
01932 if (vb->next==0){
01933 LM_ERR(" out of pkg memory\n");
01934 goto error;
01935 }
01936 vb=vb->next;
01937 memset(vb, 0, sizeof(struct via_body));
01938 buffer=tmp;
01939 goto parse_again;
01940
01941 error:
01942 if (end>buffer){
01943 LM_ERR(" <%.*s>\n", (int)(end-buffer), ZSW(buffer));
01944 }
01945 if ((tmp>buffer)&&(tmp<end)){
01946 LM_ERR("parsed so far:<%.*s>\n",
01947 (int)(tmp-buffer), ZSW(buffer) );
01948 }else{
01949 LM_ERR("via parse failed\n");
01950 }
01951 vb->error=PARSE_ERROR;
01952 vbody->error=PARSE_ERROR;
01953
01954 return tmp;
01955 }
01956
01957
01958 static inline void free_via_param_list(struct via_param* vp)
01959 {
01960 struct via_param* foo;
01961 while(vp){
01962 foo=vp;
01963 vp=vp->next;
01964 pkg_free(foo);
01965 }
01966 }
01967
01968
01969 void free_via_list(struct via_body* vb)
01970 {
01971 struct via_body* foo;
01972 while(vb){
01973 foo=vb;
01974 vb=vb->next;
01975 if (foo->param_lst) free_via_param_list(foo->param_lst);
01976 pkg_free(foo);
01977 }
01978 }