Ignore:
Timestamp:
Feb 20, 2007 9:58:36 PM (17 years ago)
Author:
bennylp
Message:

Checked in latest changes in iceproject branch before merging in to the trunk

File:
1 edited

Legend:

Unmodified
Added
Removed
  • pjproject/branches/iceproject/pjlib-util/src/pjlib-util/stun_msg.c

    r929 r990  
    8080#define ATTR_HDR_LEN        4 
    8181 
     82#define getval16(p, pos)    (pj_uint16_t)(((p)[(pos)] << 8) | \ 
     83                                          ((p)[(pos) + 1] << 0)) 
     84 
    8285 
    8386////////////////////////////////////////////////////////////////////////////// 
     
    9396pj_stun_generic_ip_addr_attr_create(pj_pool_t *pool, 
    9497                                    int attr_type, 
    95                                     pj_uint32_t ip_addr, 
    96                                     int port, 
     98                                    pj_bool_t xor_ed, 
     99                                    unsigned addr_len, 
     100                                    const pj_sockaddr_t *addr, 
    97101                                    pj_stun_generic_ip_addr_attr **p_attr) 
    98102{ 
    99103    pj_stun_generic_ip_addr_attr *attr; 
    100104 
    101     PJ_ASSERT_RETURN(pool && p_attr, PJ_EINVAL); 
     105    PJ_ASSERT_RETURN(pool && addr_len && addr && p_attr, PJ_EINVAL); 
     106    PJ_ASSERT_RETURN(addr_len == sizeof(pj_sockaddr_in) || 
     107                     addr_len == sizeof(pj_sockaddr_in6), PJ_EINVAL); 
    102108 
    103109    attr = PJ_POOL_ZALLOC_TYPE(pool, pj_stun_generic_ip_addr_attr); 
    104110    INIT_ATTR(attr, attr_type, STUN_GENERIC_IP_ADDR_LEN); 
    105     attr->family = 1; 
    106     attr->port = (pj_uint16_t) port; 
    107     attr->addr.ipv4 = ip_addr; 
     111 
     112    if (!xor_ed) { 
     113        pj_memcpy(&attr->addr, addr, addr_len); 
     114    } else if (addr_len == sizeof(pj_sockaddr_in)) { 
     115        const pj_sockaddr_in *addr4 = (const pj_sockaddr_in*) addr; 
     116 
     117        pj_sockaddr_in_init(&attr->addr.ipv4, NULL, 0); 
     118        attr->addr.ipv4.sin_port = (pj_uint16_t)(addr4->sin_port ^ 0x2112); 
     119        attr->addr.ipv4.sin_addr.s_addr = (addr4->sin_addr.s_addr ^  
     120                                           pj_htonl(0x2112A442)); 
     121    } else { 
     122        return PJ_ENOTSUP; 
     123    } 
    108124 
    109125    *p_attr = attr; 
     
    117133                                               void **p_attr) 
    118134{ 
    119     enum 
    120     { 
    121         ATTR_LEN = STUN_GENERIC_IP_ADDR_LEN + ATTR_HDR_LEN 
    122     }; 
    123135    pj_stun_generic_ip_addr_attr *attr; 
    124  
    125     /* Check that the struct address is valid */ 
    126     pj_assert(sizeof(pj_stun_generic_ip_addr_attr) == ATTR_LEN); 
     136    pj_uint32_t val; 
    127137 
    128138    /* Create the attribute */ 
    129     attr = PJ_POOL_ALLOC_TYPE(pool, pj_stun_generic_ip_addr_attr); 
    130     pj_memcpy(attr, buf, ATTR_LEN); 
    131  
    132     /* Check address family is valid (only supports ipv4 for now) */ 
    133     if (attr->family != 1) 
    134         return PJLIB_UTIL_ESTUNINATTR; 
     139    attr = PJ_POOL_ZALLOC_TYPE(pool, pj_stun_generic_ip_addr_attr); 
     140    pj_memcpy(attr, buf, ATTR_HDR_LEN); 
    135141 
    136142    /* Convert to host byte order */ 
    137143    attr->hdr.type = pj_ntohs(attr->hdr.type); 
    138144    attr->hdr.length = pj_ntohs(attr->hdr.length); 
    139     attr->port = pj_ntohs(attr->port); 
    140     attr->addr.ipv4 = pj_ntohl(attr->addr.ipv4); 
    141145 
    142146    /* Check that the attribute length is valid */ 
     
    144148        return PJLIB_UTIL_ESTUNINATTRLEN; 
    145149 
     150    /* Check address family */ 
     151    val = *(pj_uint8_t*)(buf + ATTR_HDR_LEN + 1); 
     152 
     153    /* Check address family is valid (only supports ipv4 for now) */ 
     154    if (val != 1) 
     155        return PJLIB_UTIL_ESTUNINATTR; 
     156 
     157    /* Get port and address */ 
     158    pj_sockaddr_in_init(&attr->addr.ipv4, NULL, 0); 
     159    attr->addr.ipv4.sin_port = getval16(buf, ATTR_HDR_LEN + 2); 
     160    pj_memcpy(&attr->addr.ipv4.sin_addr, buf+ATTR_HDR_LEN+4, 4); 
     161 
    146162    /* Done */ 
    147163    *p_attr = attr; 
     
    154170                                               unsigned len, unsigned *printed) 
    155171{ 
    156     enum 
    157     { 
    158         ATTR_LEN = STUN_GENERIC_IP_ADDR_LEN + ATTR_HDR_LEN 
     172    enum { 
     173        ATTR_LEN = ATTR_HDR_LEN + STUN_GENERIC_IP_ADDR_LEN 
    159174    }; 
     175    pj_uint8_t *start_buf = buf; 
     176    const pj_stun_generic_ip_addr_attr *ca =  
     177        (const pj_stun_generic_ip_addr_attr *)a; 
    160178    pj_stun_generic_ip_addr_attr *attr; 
    161179 
     
    163181        return PJ_ETOOSMALL; 
    164182 
    165     /* Copy and convert attribute to network byte order */ 
    166     pj_memcpy(buf, a, ATTR_LEN); 
     183    /* Copy and convert headers to network byte order */ 
     184    pj_memcpy(buf, a, ATTR_HDR_LEN); 
    167185    attr = (pj_stun_generic_ip_addr_attr*) buf; 
    168186    attr->hdr.type = pj_htons(attr->hdr.type); 
    169     attr->hdr.length = pj_htons(attr->hdr.length); 
    170     attr->port = pj_htons(attr->port); 
    171     attr->addr.ipv4 = pj_htonl(attr->addr.ipv4); 
    172  
    173     /* Done */ 
    174     *printed = ATTR_LEN; 
     187    attr->hdr.length = pj_htons((pj_uint16_t)ATTR_LEN); 
     188    buf += ATTR_HDR_LEN; 
     189     
     190    /* Ignored */ 
     191    *buf++ = '\0'; 
     192 
     193    /* Family (IPv4 only for now) */ 
     194    PJ_ASSERT_RETURN(ca->addr.addr.sa_family == PJ_AF_INET, PJ_EINVAL); 
     195    *buf++ = 1; 
     196 
     197    /* Port */ 
     198    pj_memcpy(buf, &ca->addr.ipv4.sin_port, 2); 
     199    buf += 2; 
     200 
     201    /* Address */ 
     202    pj_memcpy(buf, &ca->addr.ipv4.sin_addr, 4); 
     203    buf += 4; 
     204 
     205    pj_assert(buf - start_buf == ATTR_LEN); 
     206 
     207    /* Done */ 
     208    *printed = buf - start_buf; 
    175209 
    176210    return PJ_SUCCESS; 
     
    214248 
    215249    /* Create the attribute */ 
    216     attr = PJ_POOL_ALLOC_TYPE(pool, pj_stun_generic_string_attr); 
     250    attr = PJ_POOL_ZALLOC_TYPE(pool, pj_stun_generic_string_attr); 
    217251 
    218252    /* Copy the header */ 
     
    247281    /* Calculated total attr_len (add padding if necessary) */ 
    248282    *printed = (ca->value.slen + ATTR_HDR_LEN + 3) & (~3); 
    249     if (len < *printed) 
     283    if (len < *printed) { 
     284        *printed = 0; 
    250285        return PJ_ETOOSMALL; 
     286    } 
    251287 
    252288    /* Copy header */ 
    253289    pj_memcpy(buf, a, ATTR_HDR_LEN); 
     290    attr = (pj_stun_attr_hdr*)buf; 
    254291 
    255292    /* Set the correct length */ 
    256     attr = (pj_stun_attr_hdr*)buf; 
    257293    attr->length = (pj_uint16_t) ca->value.slen; 
    258294 
     
    265301 
    266302    /* Done */ 
     303    return PJ_SUCCESS; 
     304} 
     305 
     306 
     307////////////////////////////////////////////////////////////////////////////// 
     308/* 
     309 * STUN empty attribute (used by USE-CANDIDATE). 
     310 */ 
     311 
     312/* 
     313 * Create a STUN empty attribute. 
     314 */ 
     315PJ_DEF(pj_status_t)  
     316pj_stun_empty_attr_create(pj_pool_t *pool, 
     317                          int attr_type, 
     318                          pj_stun_empty_attr **p_attr) 
     319{ 
     320    pj_stun_empty_attr *attr; 
     321 
     322    PJ_ASSERT_RETURN(pool && p_attr, PJ_EINVAL); 
     323 
     324    attr = PJ_POOL_ZALLOC_TYPE(pool, pj_stun_empty_attr); 
     325    INIT_ATTR(attr, attr_type, sizeof(pj_stun_empty_attr)); 
     326 
     327    *p_attr = attr; 
     328 
     329    return PJ_SUCCESS; 
     330} 
     331 
     332 
     333static pj_status_t decode_empty_attr(pj_pool_t *pool,  
     334                                     const pj_uint8_t *buf,  
     335                                     void **p_attr) 
     336{ 
     337    pj_stun_empty_attr *attr; 
     338 
     339    /* Check that the struct address is valid */ 
     340    pj_assert(sizeof(pj_stun_empty_attr) == ATTR_HDR_LEN); 
     341 
     342    /* Create the attribute */ 
     343    attr = PJ_POOL_ZALLOC_TYPE(pool, pj_stun_empty_attr); 
     344    pj_memcpy(attr, buf, ATTR_HDR_LEN); 
     345 
     346    /* Convert to host byte order */ 
     347    attr->hdr.type = pj_ntohs(attr->hdr.type); 
     348    attr->hdr.length = pj_ntohs(attr->hdr.length); 
     349 
     350    /* Check that the attribute length is valid */ 
     351    if (attr->hdr.length != ATTR_HDR_LEN) 
     352        return PJLIB_UTIL_ESTUNINATTRLEN; 
     353 
     354    /* Done */ 
     355    *p_attr = attr; 
     356 
     357    return PJ_SUCCESS; 
     358} 
     359 
     360 
     361static pj_status_t encode_empty_attr(const void *a, pj_uint8_t *buf,  
     362                                     unsigned len, unsigned *printed) 
     363{ 
     364    pj_stun_empty_attr *attr; 
     365 
     366    if (len < ATTR_HDR_LEN)  
     367        return PJ_ETOOSMALL; 
     368 
     369    /* Copy and convert attribute to network byte order */ 
     370    pj_memcpy(buf, a, ATTR_HDR_LEN); 
     371    attr = (pj_stun_empty_attr*) buf; 
     372    attr->hdr.type = pj_htons(attr->hdr.type); 
     373    attr->hdr.length = pj_htons(attr->hdr.length); 
     374 
     375    /* Done */ 
     376    *printed = ATTR_HDR_LEN; 
     377 
    267378    return PJ_SUCCESS; 
    268379} 
     
    312423 
    313424    /* Create the attribute */ 
    314     attr = PJ_POOL_ALLOC_TYPE(pool, pj_stun_generic_uint_attr); 
     425    attr = PJ_POOL_ZALLOC_TYPE(pool, pj_stun_generic_uint_attr); 
    315426    pj_memcpy(attr, buf, ATTR_LEN); 
    316427 
     
    397508 
    398509    /* Create attribute */ 
    399     attr = PJ_POOL_ALLOC_TYPE(pool, pj_stun_msg_integrity_attr); 
     510    attr = PJ_POOL_ZALLOC_TYPE(pool, pj_stun_msg_integrity_attr); 
    400511    pj_memcpy(attr, buf, sizeof(pj_stun_msg_integrity_attr)); 
    401512    attr->hdr.type = pj_ntohs(attr->hdr.type); 
     
    486597 
    487598    /* Create the attribute */ 
    488     attr = PJ_POOL_ALLOC_TYPE(pool, pj_stun_error_code_attr); 
     599    attr = PJ_POOL_ZALLOC_TYPE(pool, pj_stun_error_code_attr); 
    489600 
    490601    /* Copy the header */ 
     
    683794 
    684795    /* Create the attribute */ 
    685     attr = PJ_POOL_ALLOC_TYPE(pool, pj_stun_binary_attr); 
     796    attr = PJ_POOL_ZALLOC_TYPE(pool, pj_stun_binary_attr); 
    686797 
    687798    /* Copy the header */ 
     
    740851struct attr_desc 
    741852{ 
    742     unsigned  type; 
    743     const char *attr_name; 
    744  
    745853    pj_status_t (*decode_attr)(pj_pool_t *pool, const pj_uint8_t *buf,  
    746854                               void **p_attr); 
     
    748856                               unsigned len, unsigned *printed); 
    749857 
    750 } attr_desc[] =  
    751 { 
    752     { 
    753         PJ_STUN_ATTR_MAPPED_ADDR, 
    754         "MAPPED-ADDRESS", 
     858}; 
     859 
     860struct attr_desc mandatory_attr_desc[] =  
     861{ 
     862    { 
     863        /* type zero */ 
     864        NULL, 
     865        NULL 
     866    }, 
     867    { 
     868        /* PJ_STUN_ATTR_MAPPED_ADDR, */ 
    755869        &decode_generic_ip_addr_attr, 
    756870        &encode_generic_ip_addr_attr 
    757871    }, 
    758872    { 
    759         PJ_STUN_ATTR_RESPONSE_ADDR, 
    760         "RESPONSE-ADDRESS", 
     873        /* PJ_STUN_ATTR_RESPONSE_ADDR, */ 
    761874        &decode_generic_ip_addr_attr, 
    762875        &encode_generic_ip_addr_attr 
    763876    }, 
    764877    { 
    765         PJ_STUN_ATTR_CHANGE_REQUEST, 
    766         "CHANGE-REQUEST", 
     878        /* PJ_STUN_ATTR_CHANGE_REQUEST, */ 
     879        &decode_generic_uint_attr, 
     880        &encode_generic_uint_attr 
     881    }, 
     882    { 
     883        /* PJ_STUN_ATTR_SOURCE_ADDR, */ 
    767884        &decode_generic_ip_addr_attr, 
    768885        &encode_generic_ip_addr_attr 
    769886    }, 
    770887    { 
    771         PJ_STUN_ATTR_SOURCE_ADDR, 
    772         "SOURCE-ADDRESS", 
     888        /* PJ_STUN_ATTR_CHANGED_ADDR, */ 
    773889        &decode_generic_ip_addr_attr, 
    774890        &encode_generic_ip_addr_attr 
    775891    }, 
    776892    { 
    777         PJ_STUN_ATTR_CHANGED_ADDR, 
    778         "CHANGED-ADDRESS", 
     893        /* PJ_STUN_ATTR_USERNAME, */ 
     894        &decode_generic_string_attr, 
     895        &encode_generic_string_attr 
     896    }, 
     897    { 
     898        /* PJ_STUN_ATTR_PASSWORD, */ 
     899        &decode_generic_string_attr, 
     900        &encode_generic_string_attr 
     901    }, 
     902    { 
     903        /* PJ_STUN_ATTR_MESSAGE_INTEGRITY, */ 
     904        &decode_msg_integrity_attr, 
     905        &encode_msg_integrity_attr 
     906    }, 
     907    { 
     908        /* PJ_STUN_ATTR_ERROR_CODE, */ 
     909        &decode_error_code_attr, 
     910        &encode_error_code_attr 
     911    }, 
     912    { 
     913        /* PJ_STUN_ATTR_UNKNOWN_ATTRIBUTES, */ 
     914        &decode_unknown_attr, 
     915        &encode_unknown_attr 
     916    }, 
     917    { 
     918        /* PJ_STUN_ATTR_REFLECTED_FROM, */ 
    779919        &decode_generic_ip_addr_attr, 
    780920        &encode_generic_ip_addr_attr 
    781921    }, 
    782922    { 
    783         PJ_STUN_ATTR_USERNAME, 
    784         "USERNAME", 
     923        /* ID 0x000C is not assigned */ 
     924        NULL, 
     925        NULL 
     926    }, 
     927    { 
     928        /* PJ_STUN_ATTR_LIFETIME, */ 
     929        &decode_generic_uint_attr, 
     930        &encode_generic_uint_attr 
     931    }, 
     932    { 
     933        /* ID 0x000E is not assigned */ 
     934        NULL, 
     935        NULL 
     936    }, 
     937    { 
     938        /* ID 0x000F is not assigned */ 
     939        NULL, 
     940        NULL 
     941    }, 
     942    { 
     943        /* PJ_STUN_ATTR_BANDWIDTH, */ 
     944        &decode_generic_uint_attr, 
     945        &encode_generic_uint_attr 
     946    }, 
     947    { 
     948        /* ID 0x0011 is not assigned */ 
     949        NULL, 
     950        NULL 
     951    }, 
     952    { 
     953        /* PJ_STUN_ATTR_REMOTE_ADDRESS, */ 
     954        &decode_generic_ip_addr_attr, 
     955        &encode_generic_ip_addr_attr 
     956    }, 
     957    { 
     958        /* PJ_STUN_ATTR_DATA, */ 
     959        &decode_binary_attr, 
     960        &encode_binary_attr 
     961    }, 
     962    { 
     963        /* PJ_STUN_ATTR_REALM, */ 
    785964        &decode_generic_string_attr, 
    786965        &encode_generic_string_attr 
    787966    }, 
    788967    { 
    789         PJ_STUN_ATTR_PASSWORD, 
    790         "PASSWORD", 
     968        /* PJ_STUN_ATTR_NONCE, */ 
    791969        &decode_generic_string_attr, 
    792970        &encode_generic_string_attr 
    793971    }, 
    794972    { 
    795         PJ_STUN_ATTR_MESSAGE_INTEGRITY, 
    796         "MESSAGE-INTEGRITY", 
    797         &decode_msg_integrity_attr, 
    798         &encode_msg_integrity_attr 
    799     }, 
    800     { 
    801         PJ_STUN_ATTR_ERROR_CODE, 
    802         "ERROR-CODE", 
    803         &decode_error_code_attr, 
    804         &encode_error_code_attr 
    805     }, 
    806     { 
    807         PJ_STUN_ATTR_UNKNOWN_ATTRIBUTES, 
    808         "UNKNOWN-ATTRIBUTES", 
    809         &decode_unknown_attr, 
    810         &encode_unknown_attr 
    811     }, 
    812     { 
    813         PJ_STUN_ATTR_REFLECTED_FROM, 
    814         "REFLECTED-FROM", 
     973        /* PJ_STUN_ATTR_RELAY_ADDRESS, */ 
    815974        &decode_generic_ip_addr_attr, 
    816975        &encode_generic_ip_addr_attr 
    817976    }, 
    818977    { 
    819         PJ_STUN_ATTR_REALM, 
    820         "REALM", 
     978        /* PJ_STUN_ATTR_REQUESTED_ADDR_TYPE, */ 
     979        &decode_generic_uint_attr, 
     980        &encode_generic_uint_attr 
     981    }, 
     982    { 
     983        /* PJ_STUN_ATTR_REQUESTED_PORT_PROPS, */ 
     984        &decode_generic_uint_attr, 
     985        &encode_generic_uint_attr 
     986    }, 
     987    { 
     988        /* PJ_STUN_ATTR_REQUESTED_TRANSPORT, */ 
     989        &decode_generic_uint_attr, 
     990        &encode_generic_uint_attr 
     991    }, 
     992    { 
     993        /* ID 0x001A is not assigned */ 
     994        NULL, 
     995        NULL 
     996    }, 
     997    { 
     998        /* ID 0x001B is not assigned */ 
     999        NULL, 
     1000        NULL 
     1001    }, 
     1002    { 
     1003        /* ID 0x001C is not assigned */ 
     1004        NULL, 
     1005        NULL 
     1006    }, 
     1007    { 
     1008        /* ID 0x001D is not assigned */ 
     1009        NULL, 
     1010        NULL 
     1011    }, 
     1012    { 
     1013        /* ID 0x001E is not assigned */ 
     1014        NULL, 
     1015        NULL 
     1016    }, 
     1017    { 
     1018        /* ID 0x001F is not assigned */ 
     1019        NULL, 
     1020        NULL 
     1021    }, 
     1022    { 
     1023        /* PJ_STUN_ATTR_XOR_MAPPED_ADDRESS, */ 
     1024        &decode_generic_ip_addr_attr, 
     1025        &encode_generic_ip_addr_attr 
     1026    }, 
     1027    { 
     1028        /* PJ_STUN_ATTR_TIMER_VAL, */ 
     1029        &decode_generic_uint_attr, 
     1030        &encode_generic_uint_attr 
     1031    }, 
     1032    { 
     1033        /* PJ_STUN_ATTR_REQUESTED_IP, */ 
     1034        &decode_generic_ip_addr_attr, 
     1035        &encode_generic_ip_addr_attr 
     1036    }, 
     1037    { 
     1038        /* PJ_STUN_ATTR_XOR_REFLECTED_FROM, */ 
     1039        &decode_generic_ip_addr_attr, 
     1040        &encode_generic_ip_addr_attr 
     1041    }, 
     1042    { 
     1043        /* PJ_STUN_ATTR_PRIORITY, */ 
     1044        &decode_generic_uint_attr, 
     1045        &encode_generic_uint_attr 
     1046    }, 
     1047    { 
     1048        /* PJ_STUN_ATTR_USE_CANDIDATE, */ 
     1049        &decode_empty_attr, 
     1050        &encode_empty_attr 
     1051    }, 
     1052    { 
     1053        /* PJ_STUN_ATTR_XOR_INTERNAL_ADDR, */ 
     1054        &decode_generic_ip_addr_attr, 
     1055        &encode_generic_ip_addr_attr 
     1056    }, 
     1057 
     1058    /* Sentinel */ 
     1059    { 
     1060        /* PJ_STUN_ATTR_END_MANDATORY_ATTR */ 
     1061        NULL, 
     1062        NULL 
     1063    } 
     1064}; 
     1065 
     1066static struct attr_desc extended_attr_desc[] = 
     1067{ 
     1068    { 
     1069        /* PJ_STUN_ATTR_FINGERPRINT, */ 
     1070        &decode_generic_uint_attr, 
     1071        &encode_generic_uint_attr 
     1072    }, 
     1073    { 
     1074        /* PJ_STUN_ATTR_SERVER, */ 
    8211075        &decode_generic_string_attr, 
    8221076        &encode_generic_string_attr 
    8231077    }, 
    8241078    { 
    825         PJ_STUN_ATTR_NONCE, 
    826         "NONCE", 
    827         &decode_generic_string_attr, 
    828         &encode_generic_string_attr 
    829     }, 
    830     { 
    831         PJ_STUN_ATTR_XOR_MAPPED_ADDRESS, 
    832         "XOR-MAPPED-ADDRESS", 
     1079        /* PJ_STUN_ATTR_ALTERNATE_SERVER, */ 
    8331080        &decode_generic_ip_addr_attr, 
    8341081        &encode_generic_ip_addr_attr 
    8351082    }, 
    8361083    { 
    837         PJ_STUN_ATTR_FINGERPRINT, 
    838         "FINGERPRINT", 
     1084        /* PJ_STUN_ATTR_REFRESH_INTERVAL, */ 
    8391085        &decode_generic_uint_attr, 
    8401086        &encode_generic_uint_attr 
    8411087    }, 
    842     { 
    843         PJ_STUN_ATTR_SERVER, 
    844         "SERVER", 
    845         &decode_generic_string_attr, 
    846         &encode_generic_string_attr 
    847     }, 
    848     { 
    849         PJ_STUN_ATTR_ALTERNATE_SERVER, 
    850         "ALTERNATE-SERVER", 
    851         &decode_generic_ip_addr_attr, 
    852         &encode_generic_ip_addr_attr 
    853     }, 
    854     { 
    855         PJ_STUN_ATTR_REFRESH_INTERVAL, 
    856         "REFRESH-INTERVAL", 
    857         &decode_generic_uint_attr, 
    858         &encode_generic_uint_attr 
    859     }, 
    860     { 
    861         PJ_STUN_ATTR_LIFETIME, 
    862         "LIFETIME", 
    863         &decode_generic_uint_attr, 
    864         &encode_generic_uint_attr 
    865     }, 
    866     { 
    867         PJ_STUN_ATTR_BANDWIDTH, 
    868         "BANDWIDTH", 
    869         &decode_generic_uint_attr, 
    870         &encode_generic_uint_attr 
    871     }, 
    872     { 
    873         PJ_STUN_ATTR_REMOTE_ADDRESS, 
    874         "REMOTE-ADDRESS", 
    875         &decode_generic_ip_addr_attr, 
    876         &encode_generic_ip_addr_attr 
    877     }, 
    878     { 
    879         PJ_STUN_ATTR_DATA, 
    880         "DATA", 
    881         &decode_binary_attr, 
    882         &encode_binary_attr 
    883     }, 
    884     { 
    885         PJ_STUN_ATTR_RELAY_ADDRESS, 
    886         "RELAY-ADDRESS", 
    887         &decode_generic_ip_addr_attr, 
    888         &encode_generic_ip_addr_attr 
    889     }, 
    890     { 
    891         PJ_STUN_ATTR_REQUESTED_PORT_PROPS, 
    892         "REQUESTED-PORT-PROPS", 
    893         &decode_generic_uint_attr, 
    894         &encode_generic_uint_attr 
    895     }, 
    896     { 
    897         PJ_STUN_ATTR_REQUESTED_TRANSPORT, 
    898         "REQUESTED-TRANSPORT", 
    899         &decode_generic_uint_attr, 
    900         &encode_generic_uint_attr 
    901     }, 
    902     { 
    903         PJ_STUN_ATTR_REQUESTED_IP, 
    904         "STUN REQUESTED-IP", 
    905         &decode_generic_ip_addr_attr, 
    906         &encode_generic_ip_addr_attr 
    907     }, 
    908     { 
    909         PJ_STUN_ATTR_TIMER_VAL, 
    910         "TIMER-VAL", 
    911         &decode_generic_uint_attr, 
    912         &encode_generic_uint_attr 
    913     } 
    9141088}; 
    9151089 
    916 static struct attr_desc *find_attr_desc(unsigned attr_type) 
    917 { 
    918     unsigned i; 
    919  
    920     for (i=0; i<PJ_ARRAY_SIZE(attr_desc); ++i) { 
    921         if (attr_desc[i].type == attr_type) 
    922             return &attr_desc[i]; 
    923     } 
    924  
    925     return NULL; 
    926 } 
    927  
     1090 
     1091static const struct attr_desc *find_attr_desc(unsigned attr_type) 
     1092{ 
     1093    struct attr_desc *desc; 
     1094 
     1095    /* Check that attr_desc array is valid */ 
     1096    pj_assert(PJ_ARRAY_SIZE(mandatory_attr_desc)== 
     1097              PJ_STUN_ATTR_END_MANDATORY_ATTR+1); 
     1098    pj_assert(mandatory_attr_desc[PJ_STUN_ATTR_END_MANDATORY_ATTR].decode_attr 
     1099              == NULL); 
     1100    pj_assert(mandatory_attr_desc[PJ_STUN_ATTR_USE_CANDIDATE].decode_attr  
     1101              == &decode_empty_attr); 
     1102    pj_assert(PJ_ARRAY_SIZE(extended_attr_desc) == 
     1103              PJ_STUN_ATTR_END_EXTENDED_ATTR-PJ_STUN_ATTR_START_EXTENDED_ATTR); 
     1104 
     1105    if (attr_type < PJ_STUN_ATTR_START_EXTENDED_ATTR) 
     1106        desc = &mandatory_attr_desc[attr_type]; 
     1107    else if (attr_type >= PJ_STUN_ATTR_START_EXTENDED_ATTR && 
     1108             attr_type < PJ_STUN_ATTR_END_EXTENDED_ATTR) 
     1109        desc = &extended_attr_desc[attr_type-PJ_STUN_ATTR_START_EXTENDED_ATTR]; 
     1110    else 
     1111        return NULL; 
     1112 
     1113    return desc->decode_attr == NULL ? NULL : desc; 
     1114} 
    9281115 
    9291116 
     
    9331120PJ_DEF(pj_status_t) pj_stun_msg_create( pj_pool_t *pool, 
    9341121                                        unsigned msg_type, 
     1122                                        pj_uint32_t magic, 
    9351123                                        const pj_uint8_t tsx_id[12], 
    9361124                                        pj_stun_msg **p_msg) 
     
    9421130    msg = PJ_POOL_ZALLOC_TYPE(pool, pj_stun_msg); 
    9431131    msg->hdr.type = (pj_uint16_t) msg_type; 
    944     msg->hdr.magic = (pj_uint32_t) PJ_STUN_MAGIC; 
     1132    msg->hdr.magic = magic; 
    9451133 
    9461134    if (tsx_id) { 
     
    9691157 
    9701158/* 
     1159 * Add STUN attribute to STUN message. 
     1160 */ 
     1161PJ_DEF(pj_status_t) pj_stun_msg_add_attr(pj_stun_msg *msg, 
     1162                                         pj_stun_attr_hdr *attr) 
     1163{ 
     1164    PJ_ASSERT_RETURN(msg && attr, PJ_EINVAL); 
     1165    PJ_ASSERT_RETURN(msg->attr_count < PJ_STUN_MAX_ATTR, PJ_ETOOMANY); 
     1166 
     1167    msg->attr[msg->attr_count++] = attr; 
     1168    return PJ_SUCCESS; 
     1169} 
     1170 
     1171 
     1172/* 
    9711173 * Check that the PDU is potentially a valid STUN message. 
    9721174 */ 
     
    9851187    /* First byte of STUN message is always 0x00 or 0x01. */ 
    9861188    if ((*(const char*)pdu) != 0x00 && (*(const char*)pdu) != 0x01) 
    987         return PJ_FALSE; 
     1189        return PJLIB_UTIL_ESTUNINMSGTYPE; 
    9881190 
    9891191    /* If magic is set, then there is great possibility that this is 
     
    9911193     */ 
    9921194    if (pj_ntohl(hdr->magic) == PJ_STUN_MAGIC) 
    993         return PJ_TRUE; 
     1195        return PJ_SUCCESS; 
    9941196 
    9951197    /* Check the PDU length */ 
    9961198    if (pj_ntohs(hdr->length) > pdu_len) 
    997         return PJ_FALSE; 
     1199        return PJLIB_UTIL_ESTUNINMSGLEN; 
    9981200 
    9991201    /* Could be a STUN message */ 
    1000     return PJ_TRUE; 
     1202    return PJ_SUCCESS; 
    10011203} 
    10021204 
     
    10311233 
    10321234    /* Create the message, copy the header, and convert to host byte order */ 
    1033     msg = PJ_POOL_ALLOC_TYPE(pool, pj_stun_msg); 
     1235    msg = PJ_POOL_ZALLOC_TYPE(pool, pj_stun_msg); 
    10341236    pj_memcpy(&msg->hdr, pdu, sizeof(pj_stun_msg_hdr)); 
    10351237    msg->hdr.type = pj_ntohs(msg->hdr.type); 
     
    10401242    pdu_len -= sizeof(pj_stun_msg_hdr); 
    10411243 
     1244    if (p_err_code) 
     1245        *p_err_code = 0; 
     1246 
    10421247    /* Parse attributes */ 
    10431248    uattr_cnt = 0; 
    10441249    while (pdu_len > 0) { 
    10451250        unsigned attr_type, attr_val_len; 
    1046         struct attr_desc *adesc; 
     1251        const struct attr_desc *adesc; 
    10471252 
    10481253        /* Get attribute type and length. If length is not aligned 
     
    10531258        attr_val_len = (attr_val_len + 3) & (~3); 
    10541259 
    1055         /* Get the attribute descriptor */ 
    1056         adesc = find_attr_desc(attr_type); 
    1057  
    10581260        /* Check length */ 
    10591261        if (pdu_len < attr_val_len) 
    10601262            return PJLIB_UTIL_ESTUNINATTRLEN; 
     1263 
     1264        /* Get the attribute descriptor */ 
     1265        adesc = find_attr_desc(attr_type); 
    10611266 
    10621267        if (adesc == NULL) { 
     
    10761281                 * if we don't understand the attribute. 
    10771282                 */ 
    1078                 if (p_err_code) 
     1283                if (p_err_code && *p_err_code == 0) 
    10791284                    *p_err_code = PJ_STUN_STATUS_UNKNOWN_ATTRIBUTE; 
    10801285 
     
    10901295            if (status != PJ_SUCCESS) { 
    10911296                PJ_LOG(4,(THIS_FILE,  
    1092                           "Error parsing STUN %s attribute: status=%d", 
    1093                           adesc->attr_name, status)); 
     1297                          "Error parsing STUN attribute type %d: status=%d", 
     1298                          attr_type, status)); 
    10941299                return status; 
    10951300            } 
     
    11511356    /* Print each attribute */ 
    11521357    for (i=0; i<msg->attr_count; ++i) { 
    1153         struct attr_desc *adesc; 
     1358        const struct attr_desc *adesc; 
    11541359        const pj_stun_attr_hdr *attr_hdr; 
    11551360        unsigned printed; 
     
    11691374    } 
    11701375 
    1171     /* Update the message length in the header */ 
     1376    /* Update the message length in the header.  
     1377     * Note that length is not including the 20 bytes header. 
     1378     */ 
    11721379    hdr->length = pj_htons((pj_uint16_t)(buf - start)); 
    11731380 
Note: See TracChangeset for help on using the changeset viewer.