diff options
author | Benny Prijono <bennylp@teluu.com> | 2007-03-24 13:00:30 +0000 |
---|---|---|
committer | Benny Prijono <bennylp@teluu.com> | 2007-03-24 13:00:30 +0000 |
commit | 37562c4e5773361453cbac8c75ebe533abb147fb (patch) | |
tree | b6317c069434236676ccef002e96175767179171 /pjnath | |
parent | 9f7d26408a37e2b085da1df5ad84794d72a7cd0e (diff) |
ICE (work in progress): implement error codes
git-svn-id: http://svn.pjsip.org/repos/pjproject/trunk@1101 74dad513-b988-da41-8d7b-12977e46ad98
Diffstat (limited to 'pjnath')
-rw-r--r-- | pjnath/build/pjnath.dsp | 4 | ||||
-rw-r--r-- | pjnath/include/pjnath.h | 1 | ||||
-rw-r--r-- | pjnath/include/pjnath/errno.h | 133 | ||||
-rw-r--r-- | pjnath/include/pjnath/ice.h | 22 | ||||
-rw-r--r-- | pjnath/include/pjnath/stun_msg.h | 1 | ||||
-rw-r--r-- | pjnath/include/pjnath/types.h | 33 | ||||
-rw-r--r-- | pjnath/src/pjnath/errno.c | 86 | ||||
-rw-r--r-- | pjnath/src/pjnath/ice.c | 305 | ||||
-rw-r--r-- | pjnath/src/pjnath/ice_stream_transport.c | 28 | ||||
-rw-r--r-- | pjnath/src/pjnath/stun_auth.c | 18 | ||||
-rw-r--r-- | pjnath/src/pjnath/stun_msg.c | 42 | ||||
-rw-r--r-- | pjnath/src/pjnath/stun_transaction.c | 7 |
12 files changed, 296 insertions, 384 deletions
diff --git a/pjnath/build/pjnath.dsp b/pjnath/build/pjnath.dsp index 83bc6a23..4ea74abd 100644 --- a/pjnath/build/pjnath.dsp +++ b/pjnath/build/pjnath.dsp @@ -41,8 +41,8 @@ RSC=rc.exe # PROP Intermediate_Dir "./output/pjnath-i386-win32-vc6-release"
# PROP Target_Dir ""
# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_MBCS" /D "_LIB" /YX /FD /c
-# ADD CPP /nologo /MD /W4 /GX /Zi /O2 /Ob2 /I "../include" /I "../../pjlib/include" /I "../../pjlib-util/include" /D "NDEBUG" /D "WIN32" /D "_MBCS" /D "_LIB" /D PJ_WIN32=1 /D PJ_M_I386=1 /FR /FD /c
-# SUBTRACT CPP /YX
+# ADD CPP /nologo /MD /W4 /GX /O1 /Ob2 /I "../include" /I "../../pjlib/include" /I "../../pjlib-util/include" /D "NDEBUG" /D "WIN32" /D "_MBCS" /D "_LIB" /D PJ_WIN32=1 /D PJ_M_I386=1 /FR /FD /c
+# SUBTRACT CPP /Z<none> /YX
# ADD BASE RSC /l 0x409 /d "NDEBUG"
# ADD RSC /l 0x409 /d "NDEBUG"
BSC32=bscmake.exe
diff --git a/pjnath/include/pjnath.h b/pjnath/include/pjnath.h index 8574631d..68eab315 100644 --- a/pjnath/include/pjnath.h +++ b/pjnath/include/pjnath.h @@ -27,3 +27,4 @@ #include <pjnath/stun_session.h> #include <pjnath/stun_transaction.h> #include <pjnath/types.h> + diff --git a/pjnath/include/pjnath/errno.h b/pjnath/include/pjnath/errno.h index 7fbd9837..c5a2afa5 100644 --- a/pjnath/include/pjnath/errno.h +++ b/pjnath/include/pjnath/errno.h @@ -23,7 +23,7 @@ #include <pj/errno.h> /** - * @defgroup PJNATH_ERROR NAT Helper Error Codes + * @defgroup PJNATH_ERROR NAT Helper Library Error Codes * @ingroup PJNATH * @{ */ @@ -35,154 +35,119 @@ #define PJNATH_ERRNO_START (PJ_ERRNO_START_USER + PJ_ERRNO_SPACE_SIZE*4) - /************************************************************ - * NEW STUN ERROR + * STUN MESSAGING ERRORS ***********************************************************/ -/* Messaging errors */ -#define PJNATH_ESTUNINATTRLEN -1 -#define PJNATH_ESTUNINMSGLEN -1 -#define PJNATH_ESTUNINMSGTYPE -1 -#define PJNATH_ESTUNFINGERPRINT -1 -#define PJNATH_ESTUNNOTRESPOND -1 -#define PJNATH_ESTUNNOXORMAP -1 /** - * @hideinitializer - * Too many STUN attributes. - */ -#define PJNATH_ESTUNTOOMANYATTR (PJNATH_ERRNO_START+110)/* 370110 */ -/** - * @hideinitializer - * Unknown STUN attribute. This error happens when the decoder encounters - * mandatory attribute type which it doesn't understand. - */ -#define PJNATH_ESTUNUNKNOWNATTR (PJNATH_ERRNO_START+111)/* 370111 */ -/** - * @hideinitializer - * Invalid STUN socket address length. - */ -#define PJNATH_ESTUNINADDRLEN (PJNATH_ERRNO_START+112)/* 370112 */ -/** - * @hideinitializer - * STUN IPv6 attribute not supported - */ -#define PJNATH_ESTUNIPV6NOTSUPP (PJNATH_ERRNO_START+113)/* 370113 */ -/** - * @hideinitializer - * Expecting STUN response message. + * Map STUN error code (300-699) into pj_status_t error space. */ -#define PJNATH_ESTUNNOTRESPONSE (PJNATH_ERRNO_START+114)/* 370114 */ -/** - * @hideinitializer - * STUN transaction ID mismatch. - */ -#define PJNATH_ESTUNINVALIDID (PJNATH_ERRNO_START+115)/* 370115 */ +#define PJ_STATUS_FROM_STUN_CODE(code) (PJNATH_ERRNO_START+code) + /** * @hideinitializer - * Unable to find handler for the request. + * Invalid STUN message length. */ -#define PJNATH_ESTUNNOHANDLER (PJNATH_ERRNO_START+116)/* 370116 */ +#define PJNATH_EINSTUNMSGLEN (PJNATH_ERRNO_START+1) /* 370001 */ /** * @hideinitializer - * Found non-FINGERPRINT attribute after MESSAGE-INTEGRITY. This is not - * valid since MESSAGE-INTEGRITY MUST be the last attribute or the - * attribute right before FINGERPRINT before the message. + * Invalid or unexpected STUN message type */ -#define PJNATH_ESTUNMSGINTPOS (PJNATH_ERRNO_START+118)/* 370118 */ +#define PJNATH_EINSTUNMSGTYPE (PJNATH_ERRNO_START+2) /* 370002 */ /** * @hideinitializer - * Found attribute after FINGERPRINT. This is not valid since FINGERPRINT - * MUST be the last attribute in the message. + * STUN transaction has timed out */ -#define PJNATH_ESTUNFINGERPOS (PJNATH_ERRNO_START+119)/* 370119 */ +#define PJNATH_ESTUNTIMEDOUT (PJNATH_ERRNO_START+3) /* 370003 */ + + + /** * @hideinitializer - * Missing STUN USERNAME attribute. - * When credential is included in the STUN message (MESSAGE-INTEGRITY is - * present), the USERNAME attribute must be present in the message. + * Too many STUN attributes. */ -#define PJNATH_ESTUNNOUSERNAME (PJNATH_ERRNO_START+120)/* 370120 */ +#define PJNATH_ESTUNTOOMANYATTR (PJNATH_ERRNO_START+21) /* 370021 */ /** * @hideinitializer - * Unknown STUN username/credential. + * Invalid STUN attribute length. */ -#define PJNATH_ESTUNUSERNAME (PJNATH_ERRNO_START+121)/* 370121 */ +#define PJNATH_ESTUNINATTRLEN (PJNATH_ERRNO_START+22) /* 370022 */ /** * @hideinitializer - * Missing/invalidSTUN MESSAGE-INTEGRITY attribute. + * Found duplicate STUN attribute. */ -#define PJNATH_ESTUNMSGINT (PJNATH_ERRNO_START+122)/* 370122 */ +#define PJNATH_ESTUNDUPATTR (PJNATH_ERRNO_START+23) /* 370023 */ + /** * @hideinitializer - * Found duplicate STUN attribute. + * STUN FINGERPRINT verification failed */ -#define PJNATH_ESTUNDUPATTR (PJNATH_ERRNO_START+123)/* 370123 */ +#define PJNATH_ESTUNFINGERPRINT (PJNATH_ERRNO_START+30) /* 370030 */ /** * @hideinitializer - * Missing STUN REALM attribute. + * Invalid STUN attribute after MESSAGE-INTEGRITY. */ -#define PJNATH_ESTUNNOREALM (PJNATH_ERRNO_START+124)/* 370124 */ +#define PJNATH_ESTUNMSGINTPOS (PJNATH_ERRNO_START+31) /* 370031 */ /** * @hideinitializer - * Missing/stale STUN NONCE attribute value. + * Invalid STUN attribute after FINGERPRINT. */ -#define PJNATH_ESTUNNONCE (PJNATH_ERRNO_START+125)/* 370125 */ +#define PJNATH_ESTUNFINGERPOS (PJNATH_ERRNO_START+33) /* 370033 */ + + /** * @hideinitializer - * STUN transaction terminates with failure. + * STUN (XOR-)MAPPED-ADDRESS attribute not found */ -#define PJNATH_ESTUNTSXFAILED (PJNATH_ERRNO_START+126)/* 370126 */ +#define PJNATH_ESTUNNOMAPPEDADDR (PJNATH_ERRNO_START+40) /* 370040 */ /** * @hideinitializer - * STUN mapped address attribute not found + * STUN IPv6 attribute not supported */ -#define PJNATH_ESTUNNOMAPPEDADDR (PJNATH_ERRNO_START+127)/* 370127 */ +#define PJNATH_ESTUNIPV6NOTSUPP (PJNATH_ERRNO_START+41) /* 370041 */ -//#define PJ_STATUS_FROM_STUN_CODE(code) (PJNATH_ERRNO_START+code) +/************************************************************ + * ICE ERROR CODES + ***********************************************************/ + /** * @hideinitializer - * No ICE checklist is formed. - */ -#define PJ_EICENOCHECKLIST -1 -/** - * @hideinitializer - * No suitable default ICE candidate for the component. + * ICE session not available */ -#define PJ_EICENOCAND -1 +#define PJNATH_ENOICE (PJNATH_ERRNO_START+80) /* 370080 */ /** * @hideinitializer - * Invalid ICE component ID + * ICE check is in progress */ -#define PJ_EICEINCOMPID -1 +#define PJNATH_EICEINPROGRESS (PJNATH_ERRNO_START+81) /* 370081 */ /** * @hideinitializer - * Invalid ICE candidate ID + * All ICE checklists failed */ -#define PJ_EICEINCANDID -1 +#define PJNATH_EICEFAILED (PJNATH_ERRNO_START+82) /* 370082 */ /** * @hideinitializer - * ICE session not available + * Invalid ICE component ID */ -#define PJ_ENOICE -1 +#define PJNATH_EICEINCOMPID (PJNATH_ERRNO_START+86) /* 370086 */ /** * @hideinitializer - * ICE check is in progress + * Invalid ICE candidate ID */ -#define PJ_EICEINPROGRESS -1 +#define PJNATH_EICEINCANDID (PJNATH_ERRNO_START+87) /* 370087 */ /** * @hideinitializer * Missing ICE SDP attribute */ -#define PJ_EICEMISSINGSDP -1 +#define PJNATH_EICEMISSINGSDP (PJNATH_ERRNO_START+90) /* 370090 */ /** * @hideinitializer * Invalid SDP "candidate" attribute */ -#define PJ_EICEINCANDSDP -1 +#define PJNATH_EICEINCANDSDP (PJNATH_ERRNO_START+91) /* 370091 */ diff --git a/pjnath/include/pjnath/ice.h b/pjnath/include/pjnath/ice.h index 8aa77cbc..10faa21f 100644 --- a/pjnath/include/pjnath/ice.h +++ b/pjnath/include/pjnath/ice.h @@ -96,7 +96,7 @@ typedef struct pj_ice_cand pj_uint32_t prio; pj_sockaddr addr; pj_sockaddr base_addr; - pj_sockaddr srv_addr; + pj_sockaddr rel_addr; pj_stun_session *stun_sess; } pj_ice_cand; @@ -204,20 +204,19 @@ struct pj_ice pj_ice_checklist clist; /* Valid list */ - unsigned valid_cnt; - unsigned valid_list[PJ_ICE_MAX_CHECKS]; + pj_ice_checklist valid_list; }; PJ_DECL(pj_status_t) pj_ice_create(pj_stun_config *stun_cfg, const char *name, pj_ice_role role, + unsigned comp_cnt, const pj_ice_cb *cb, const pj_str_t *local_ufrag, const pj_str_t *local_passwd, pj_ice **p_ice); PJ_DECL(pj_status_t) pj_ice_destroy(pj_ice *ice); -PJ_DECL(pj_status_t) pj_ice_add_comp(pj_ice *ice, unsigned comp_id); PJ_DECL(pj_status_t) pj_ice_add_cand(pj_ice *ice, unsigned comp_id, pj_ice_cand_type type, @@ -225,20 +224,13 @@ PJ_DECL(pj_status_t) pj_ice_add_cand(pj_ice *ice, const pj_str_t *foundation, const pj_sockaddr_t *addr, const pj_sockaddr_t *base_addr, - const pj_sockaddr_t *srv_addr, + const pj_sockaddr_t *rel_addr, int addr_len, unsigned *cand_id); -PJ_DECL(unsigned) pj_ice_get_cand_cnt(pj_ice *ice); -PJ_DECL(pj_status_t) pj_ice_enum_cands(pj_ice *ice, - unsigned *p_count, - unsigned cand_ids[]); -PJ_DECL(pj_status_t) pj_ice_get_default_cand(pj_ice *ice, - unsigned comp_id, - int *cand_id); -PJ_DECL(pj_status_t) pj_ice_get_cand(pj_ice *ice, - unsigned cand_id, - pj_ice_cand **p_cand); +PJ_DECL(pj_status_t) pj_ice_find_default_cand(pj_ice *ice, + unsigned comp_id, + int *cand_id); PJ_DECL(pj_status_t) pj_ice_create_check_list(pj_ice *ice, const pj_str_t *rem_ufrag, diff --git a/pjnath/include/pjnath/stun_msg.h b/pjnath/include/pjnath/stun_msg.h index 08e5672d..3362703c 100644 --- a/pjnath/include/pjnath/stun_msg.h +++ b/pjnath/include/pjnath/stun_msg.h @@ -383,7 +383,6 @@ typedef enum pj_stun_status PJ_STUN_SC_NO_BINDING = 437, /**< No Binding. */ PJ_STUN_SC_STALE_NONCE = 438, /**< Stale Nonce */ PJ_STUN_SC_TRANSITIONING = 439, /**< Transitioning. */ - PJ_STUN_SC_WRONG_USERNAME = 441, /**< Wrong Username. */ PJ_STUN_SC_UNSUPP_TRANSPORT_PROTO = 442, /**< Unsupported Transport or Protocol */ PJ_STUN_SC_INVALID_IP_ADDR = 443, /**< Invalid IP Address */ diff --git a/pjnath/include/pjnath/types.h b/pjnath/include/pjnath/types.h index d39da89e..0d9dc61c 100644 --- a/pjnath/include/pjnath/types.h +++ b/pjnath/include/pjnath/types.h @@ -29,8 +29,27 @@ /** * @defgroup PJNATH NAT Helper Library + * @{ */ +PJ_BEGIN_DECL + +/** + * Initialize pjnath library. + * + * @return Initialization status. + */ +PJ_DECL(pj_status_t) pjnath_init(void); + + +PJ_END_DECL + +/** + * @} + */ + +/* Doxygen documentation below: */ + /** * @mainpage NAT Helper Library * @@ -43,20 +62,6 @@ * Please go to the <A HREF="modules.htm"><B>Modules</B></A> page for list * of modules. * - * - * \n - * \n - * \n - * \n - * \n - * \n - * \n - * \n - * \n - * \n - * \n - * \n - * \n */ #endif /* __PJNATH_TYPES_H__ */ diff --git a/pjnath/src/pjnath/errno.c b/pjnath/src/pjnath/errno.c index bfde1bc0..7ac88922 100644 --- a/pjnath/src/pjnath/errno.c +++ b/pjnath/src/pjnath/errno.c @@ -17,6 +17,7 @@ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ #include <pjnath/errno.h> +#include <pjnath/stun_msg.h> #include <pj/string.h> @@ -32,22 +33,31 @@ static const struct const char *msg; } err_str[] = { - /* STUN */ + /* STUN related error codes */ + PJ_BUILD_ERR( PJNATH_EINSTUNMSGLEN, "Invalid STUN message length"), + PJ_BUILD_ERR( PJNATH_EINSTUNMSGTYPE, "Invalid or unexpected STUN message type"), + PJ_BUILD_ERR( PJNATH_ESTUNTIMEDOUT, "STUN transaction has timed out"), + PJ_BUILD_ERR( PJNATH_ESTUNTOOMANYATTR, "Too many STUN attributes"), - PJ_BUILD_ERR( PJNATH_ESTUNUNKNOWNATTR, "Unknown STUN attribute"), - PJ_BUILD_ERR( PJNATH_ESTUNINADDRLEN, "Invalid STUN socket address length"), - PJ_BUILD_ERR( PJNATH_ESTUNIPV6NOTSUPP, "STUN IPv6 attribute not supported"), - PJ_BUILD_ERR( PJNATH_ESTUNNOTRESPONSE, "Expecting STUN response message"), - PJ_BUILD_ERR( PJNATH_ESTUNINVALIDID, "STUN transaction ID mismatch"), - PJ_BUILD_ERR( PJNATH_ESTUNNOHANDLER, "Unable to find STUN handler for the request"), - PJ_BUILD_ERR( PJNATH_ESTUNMSGINTPOS, "Found non-FINGERPRINT attr. after MESSAGE-INTEGRITY"), - PJ_BUILD_ERR( PJNATH_ESTUNFINGERPOS, "Found STUN attribute after FINGERPRINT"), - PJ_BUILD_ERR( PJNATH_ESTUNNOUSERNAME, "Missing STUN USERNAME attribute"), - PJ_BUILD_ERR( PJNATH_ESTUNMSGINT, "Missing/invalid STUN MESSAGE-INTEGRITY attribute"), + PJ_BUILD_ERR( PJNATH_ESTUNINATTRLEN, "Invalid STUN attribute length"), PJ_BUILD_ERR( PJNATH_ESTUNDUPATTR, "Found duplicate STUN attribute"), - PJ_BUILD_ERR( PJNATH_ESTUNNOREALM, "Missing STUN REALM attribute"), - PJ_BUILD_ERR( PJNATH_ESTUNNONCE, "Missing/stale STUN NONCE attribute value"), - PJ_BUILD_ERR( PJNATH_ESTUNTSXFAILED, "STUN transaction terminates with failure"), + + PJ_BUILD_ERR( PJNATH_ESTUNFINGERPRINT, "STUN FINGERPRINT verification failed"), + PJ_BUILD_ERR( PJNATH_ESTUNMSGINTPOS, "Invalid STUN attribute after MESSAGE-INTEGRITY"), + PJ_BUILD_ERR( PJNATH_ESTUNFINGERPOS, "Invalid STUN attribute after FINGERPRINT"), + + PJ_BUILD_ERR( PJNATH_ESTUNNOMAPPEDADDR, "STUN (XOR-)MAPPED-ADDRESS attribute not found"), + PJ_BUILD_ERR( PJNATH_ESTUNIPV6NOTSUPP, "STUN IPv6 attribute not supported"), + + /* ICE related errors */ + PJ_BUILD_ERR( PJNATH_ENOICE, "ICE session not available"), + PJ_BUILD_ERR( PJNATH_EICEINPROGRESS, "ICE check is in progress"), + PJ_BUILD_ERR( PJNATH_EICEFAILED, "All ICE checklists failed"), + PJ_BUILD_ERR( PJNATH_EICEINCOMPID, "Invalid ICE component ID"), + PJ_BUILD_ERR( PJNATH_EICEINCANDID, "Invalid ICE candidate ID"), + PJ_BUILD_ERR( PJNATH_EICEMISSINGSDP, "Missing ICE SDP attribute"), + PJ_BUILD_ERR( PJNATH_EICEINCANDSDP, "Invalid SDP \"candidate\" attribute"), + }; #endif /* PJ_HAS_ERROR_STRING */ @@ -55,8 +65,8 @@ static const struct /* * pjnath_strerror() */ -PJ_DEF(pj_str_t) pjnath_strerror( pj_status_t statcode, - char *buf, pj_size_t bufsize ) +static pj_str_t pjnath_strerror(pj_status_t statcode, + char *buf, pj_size_t bufsize ) { pj_str_t errstr; @@ -106,8 +116,35 @@ PJ_DEF(pj_str_t) pjnath_strerror( pj_status_t statcode, /* Error not found. */ errstr.ptr = buf; errstr.slen = pj_ansi_snprintf(buf, bufsize, - "Unknown pjlib-util error %d", + "Unknown pjnath error %d", statcode); + if (errstr.slen < 0) errstr.slen = 0; + else if (errstr.slen > (int)bufsize) errstr.slen = bufsize; + + return errstr; +} + + +static pj_str_t pjnath_strerror2(pj_status_t statcode, + char *buf, pj_size_t bufsize ) +{ + int stun_code = statcode - PJ_STATUS_FROM_STUN_CODE(0); + const pj_str_t cmsg = pj_stun_get_err_reason(stun_code); + pj_str_t errstr; + + if (cmsg.slen == 0) { + /* Not found */ + errstr.ptr = buf; + errstr.slen = pj_ansi_snprintf(buf, bufsize, + "Unknown STUN err-code %d", + stun_code); + } else { + errstr.ptr = buf; + pj_strncpy(&errstr, &cmsg, bufsize); + } + + if (errstr.slen < 0) errstr.slen = 0; + else if (errstr.slen > (int)bufsize) errstr.slen = bufsize; return errstr; } @@ -115,7 +152,16 @@ PJ_DEF(pj_str_t) pjnath_strerror( pj_status_t statcode, PJ_DEF(pj_status_t) pjnath_init(void) { - return pj_register_strerror(PJNATH_ERRNO_START, - PJ_ERRNO_SPACE_SIZE, - &pjnath_strerror); + pj_status_t status; + + status = pj_register_strerror(PJNATH_ERRNO_START, 299, + &pjnath_strerror); + if (status != PJ_SUCCESS) + return status; + + status = pj_register_strerror(PJ_STATUS_FROM_STUN_CODE(300), + 699 - 300, + &pjnath_strerror2); + return status; } + diff --git a/pjnath/src/pjnath/ice.c b/pjnath/src/pjnath/ice.c index 9ab50262..50f911f5 100644 --- a/pjnath/src/pjnath/ice.c +++ b/pjnath/src/pjnath/ice.c @@ -57,7 +57,8 @@ static const char *clist_state_name[] = }; #define CHECK_NAME_LEN 128 -#define LOG(expr) PJ_LOG(4,expr) +#define LOG4(expr) PJ_LOG(4,expr) +#define LOG5(expr) PJ_LOG(4,expr) #define GET_LCAND_ID(cand) (cand - ice->lcand) #define GET_CHECK_ID(chk) (chk - ice->clist.checks) @@ -135,6 +136,7 @@ static pj_bool_t stun_auth_verify_nonce(const pj_stun_msg *msg, PJ_DEF(pj_status_t) pj_ice_create(pj_stun_config *stun_cfg, const char *name, pj_ice_role role, + unsigned comp_cnt, const pj_ice_cb *cb, const pj_str_t *local_ufrag, const pj_str_t *local_passwd, @@ -170,8 +172,12 @@ PJ_DEF(pj_status_t) pj_ice_create(pj_stun_config *stun_cfg, pj_memcpy(&ice->cb, cb, sizeof(*cb)); pj_memcpy(&ice->stun_cfg, stun_cfg, sizeof(*stun_cfg)); - for (i=0; i<PJ_ICE_MAX_COMP; ++i) { - ice->comp[i].nominated_check_id = -1; + ice->comp_cnt = comp_cnt; + for (i=0; i<comp_cnt; ++i) { + pj_ice_comp *comp; + comp = &ice->comp[i]; + comp->comp_id = i+1; + comp->nominated_check_id = -1; } if (local_ufrag == NULL) { @@ -192,8 +198,8 @@ PJ_DEF(pj_status_t) pj_ice_create(pj_stun_config *stun_cfg, /* Done */ *p_ice = ice; - LOG((ice->obj_name, "ICE stream session created, role is %s agent", - (ice->role==PJ_ICE_ROLE_CONTROLLING ? "controlling" : "controlled"))); + LOG4((ice->obj_name, "ICE stream session created, role is %s agent", + (ice->role==PJ_ICE_ROLE_CONTROLLING ? "controlling" : "controlled"))); return PJ_SUCCESS; } @@ -208,11 +214,7 @@ static void destroy_ice(pj_ice *ice, unsigned i; if (reason == PJ_SUCCESS) { - LOG((ice->obj_name, "Destroying ICE session")); - } - - for (i=0; i<ice->comp_cnt; ++i) { - /* Nothing to do */ + LOG4((ice->obj_name, "Destroying ICE session")); } for (i=0; i<ice->lcand_cnt; ++i) { @@ -250,39 +252,11 @@ PJ_DEF(pj_status_t) pj_ice_destroy(pj_ice *ice) /* Find component by ID */ static pj_ice_comp *find_comp(const pj_ice *ice, unsigned comp_id) { - unsigned i; - for (i=0; i<ice->comp_cnt; ++i) { - if (ice->comp[i].comp_id == comp_id) - return (pj_ice_comp *) &ice->comp[i]; - } - - return NULL; + pj_assert(comp_id > 0 && comp_id <= ice->comp_cnt); + return (pj_ice_comp*) &ice->comp[comp_id-1]; } -/* Add a new component */ -PJ_DEF(pj_status_t) pj_ice_add_comp(pj_ice *ice, unsigned comp_id) -{ - pj_ice_comp *comp; - - PJ_ASSERT_RETURN(ice && comp_id, PJ_EINVAL); - PJ_ASSERT_RETURN(ice->comp_cnt < PJ_ARRAY_SIZE(ice->comp), PJ_ETOOMANY); - PJ_ASSERT_RETURN(comp_id==ice->comp_cnt+1, PJ_EICEINCOMPID); - PJ_ASSERT_RETURN(find_comp(ice, comp_id) == NULL, PJ_EEXISTS); - - pj_mutex_lock(ice->mutex); - - comp = &ice->comp[ice->comp_cnt]; - comp->comp_id = comp_id; - comp->nominated_check_id = -1; - - /* Done */ - ice->comp_cnt++; - pj_mutex_unlock(ice->mutex); - - return PJ_SUCCESS; -} - static pj_status_t stun_auth_get_auth(void *user_data, pj_pool_t *pool, pj_str_t *realm, @@ -356,7 +330,7 @@ static pj_status_t stun_auth_get_password(const pj_stun_msg *msg, /* Incoming response is authenticated with TX credential */ /* Verify username */ if (pj_strcmp(username, &ice->tx_uname) != 0) - return -1; + return PJ_STATUS_FROM_STUN_CODE(PJ_STUN_SC_UNKNOWN_USERNAME); *data_type = 0; *data = ice->tx_pass; @@ -407,9 +381,9 @@ static pj_uint32_t CALC_CAND_PRIO(pj_ice_cand_type type, PJ_ICE_RELAYED_PREF }; - return ((1 << 24) * type_pref[type]) + - ((1 << 8) * local_pref) + - (256 - comp_id); + return ((type_pref[type] & 0xFF) << 24) + + ((local_pref & 0xFFFF) << 8) + + (((256 - comp_id) & 0xFF) << 0); } @@ -423,7 +397,7 @@ PJ_DEF(pj_status_t) pj_ice_add_cand(pj_ice *ice, const pj_str_t *foundation, const pj_sockaddr_t *addr, const pj_sockaddr_t *base_addr, - const pj_sockaddr_t *srv_addr, + const pj_sockaddr_t *rel_addr, int addr_len, unsigned *p_cand_id) { @@ -452,10 +426,10 @@ PJ_DEF(pj_status_t) pj_ice_add_cand(pj_ice *ice, lcand->prio = CALC_CAND_PRIO(type, local_pref, lcand->comp_id); pj_memcpy(&lcand->addr, addr, addr_len); pj_memcpy(&lcand->base_addr, base_addr, addr_len); - if (srv_addr) - pj_memcpy(&lcand->srv_addr, srv_addr, addr_len); + if (rel_addr) + pj_memcpy(&lcand->rel_addr, rel_addr, addr_len); else - pj_bzero(&lcand->srv_addr, sizeof(lcand->srv_addr)); + pj_bzero(&lcand->rel_addr, sizeof(lcand->rel_addr)); /* Init STUN callbacks */ pj_bzero(&sess_cb, sizeof(sess_cb)); @@ -492,7 +466,7 @@ PJ_DEF(pj_status_t) pj_ice_add_cand(pj_ice *ice, pj_ansi_strcpy(tmp, pj_inet_ntoa(lcand->addr.ipv4.sin_addr)); - LOG((ice->obj_name, + LOG4((ice->obj_name, "Candidate %d added: comp_id=%d, type=%s, foundation=%.*s, " "addr=%s:%d, base=%s:%d, prio=0x%x (%u)", ice->lcand_cnt, @@ -517,36 +491,9 @@ on_error: } -PJ_DEF(unsigned) pj_ice_get_cand_cnt(pj_ice *ice) -{ - return ice->lcand_cnt; -} - - -PJ_DEF(pj_status_t) pj_ice_enum_cands(pj_ice *ice, - unsigned *p_count, - unsigned cand_ids[]) -{ - unsigned i, count; - - PJ_ASSERT_RETURN(ice && p_count && *p_count && cand_ids, PJ_EINVAL); - - pj_mutex_lock(ice->mutex); - - count = (*p_count < ice->lcand_cnt) ? *p_count : ice->lcand_cnt; - for (i=0; i<count; ++i) - cand_ids[i] = i; - - *p_count = count; - pj_mutex_unlock(ice->mutex); - - return PJ_SUCCESS; -} - - -PJ_DEF(pj_status_t) pj_ice_get_default_cand(pj_ice *ice, - unsigned comp_id, - int *cand_id) +PJ_DEF(pj_status_t) pj_ice_find_default_cand(pj_ice *ice, + unsigned comp_id, + int *cand_id) { unsigned i; @@ -557,12 +504,11 @@ PJ_DEF(pj_status_t) pj_ice_get_default_cand(pj_ice *ice, pj_mutex_lock(ice->mutex); /* First find in valid list if we have nominated pair */ - for (i=0; i<ice->valid_cnt; ++i) { - pj_ice_cand *lcand; + for (i=0; i<ice->valid_list.count; ++i) { + pj_ice_check *check = &ice->valid_list.checks[i]; - lcand = ice->clist.checks[ice->valid_list[i]].lcand; - if (lcand->comp_id==comp_id) { - *cand_id = GET_LCAND_ID(lcand); + if (check->lcand->comp_id == comp_id) { + *cand_id = GET_LCAND_ID(check->lcand); pj_mutex_unlock(ice->mutex); return PJ_SUCCESS; } @@ -608,22 +554,10 @@ PJ_DEF(pj_status_t) pj_ice_get_default_cand(pj_ice *ice, pj_mutex_unlock(ice->mutex); pj_assert(!"Should have a candidate by now"); - return PJ_EICENOCAND; + return PJ_EBUG; } -PJ_DEF(pj_status_t) pj_ice_get_cand(pj_ice *ice, - unsigned cand_id, - pj_ice_cand **p_cand) -{ - PJ_ASSERT_RETURN(ice && p_cand, PJ_EINVAL); - PJ_ASSERT_RETURN(cand_id <= ice->lcand_cnt, PJ_EINVAL); - - *p_cand = &ice->lcand[cand_id]; - - return PJ_SUCCESS; -} - #ifndef MIN # define MIN(a,b) (a < b ? a : b) #endif @@ -689,25 +623,10 @@ static void dump_checklist(const char *title, const pj_ice *ice, unsigned i; char buffer[CHECK_NAME_LEN]; - LOG((ice->obj_name, "%s", title)); + LOG4((ice->obj_name, "%s", title)); for (i=0; i<clist->count; ++i) { const pj_ice_check *c = &clist->checks[i]; - LOG((ice->obj_name, " %s (%s, state=%s)", - dump_check(buffer, sizeof(buffer), ice, c), - (c->nominated ? "nominated" : "not nominated"), - check_state_name[c->state])); - } -} - -static void dump_valid_list(const char *title, const pj_ice *ice) -{ - unsigned i; - char buffer[CHECK_NAME_LEN]; - - LOG((ice->obj_name, "%s", title)); - for (i=0; i<ice->valid_cnt; ++i) { - const pj_ice_check *c = &ice->clist.checks[ice->valid_list[i]]; - LOG((ice->obj_name, " %s (%s, state=%s)", + LOG4((ice->obj_name, " %s (%s, state=%s)", dump_check(buffer, sizeof(buffer), ice, c), (c->nominated ? "nominated" : "not nominated"), check_state_name[c->state])); @@ -726,7 +645,7 @@ static void check_set_state(pj_ice *ice, pj_ice_check *check, pj_assert(check->state < PJ_ICE_CHECK_STATE_SUCCEEDED); - LOG((ice->obj_name, "Check %s: state changed from %s to %s", + LOG5((ice->obj_name, "Check %s: state changed from %s to %s", dump_check(buf, sizeof(buf), ice, check), check_state_name[check->state], check_state_name[st])); @@ -738,7 +657,7 @@ static void clist_set_state(pj_ice *ice, pj_ice_checklist *clist, pj_ice_checklist_state st) { if (clist->state != st) { - LOG((ice->obj_name, "Checklist: state changed from %s to %s", + LOG5((ice->obj_name, "Checklist: state changed from %s to %s", clist_state_name[clist->state], clist_state_name[st])); clist->state = st; @@ -769,32 +688,6 @@ static void sort_checklist(pj_ice_checklist *clist) } } -/* Sort valid list based on priority */ -static void sort_valid_list(pj_ice *ice) -{ - unsigned i; - - for (i=0; i<ice->valid_cnt-1; ++i) { - unsigned j, highest = i; - pj_ice_check *ci = &ice->clist.checks[ice->valid_list[i]]; - - for (j=i+1; j<ice->valid_cnt; ++j) { - pj_ice_check *cj = &ice->clist.checks[ice->valid_list[j]]; - - if (cj->prio > ci->prio) { - highest = j; - } - } - - if (highest != i) { - unsigned tmp = ice->valid_list[i]; - ice->valid_list[i] = ice->valid_list[j]; - ice->valid_list[j] = tmp; - } - } -} - - enum { SOCKADDR_EQUAL = 0, @@ -865,7 +758,7 @@ static void prune_checklist(pj_ice *ice, pj_ice_checklist *clist) /* Found duplicate, remove it */ char buf[CHECK_NAME_LEN]; - LOG((ice->obj_name, "Check %s pruned", + LOG5((ice->obj_name, "Check %s pruned", dump_check(buf, sizeof(buf), ice, &clist->checks[j]))); pj_array_erase(clist->checks, sizeof(clist->checks[0]), @@ -889,11 +782,10 @@ static void on_ice_complete(pj_ice *ice, pj_status_t status) ice->ice_status = status; /* Log message */ - LOG((ice->obj_name, "ICE process complete, status=%s", + LOG4((ice->obj_name, "ICE process complete, status=%s", pj_strerror(status, errmsg, sizeof(errmsg)).ptr)); - dump_checklist("Dumping checklist", ice, &ice->clist); - dump_valid_list("Dumping valid list", ice); + dump_checklist("Valid list", ice, &ice->valid_list); /* Call callback */ (*ice->cb.on_ice_complete)(ice, status); @@ -921,7 +813,7 @@ static pj_bool_t on_check_complete(pj_ice *ice, if (check->err_code==PJ_SUCCESS && check->nominated) { pj_ice_comp *comp; - LOG((ice->obj_name, "Check %d is successful and nominated", + LOG5((ice->obj_name, "Check %d is successful and nominated", GET_CHECK_ID(check))); for (i=0; i<ice->clist.count; ++i) { @@ -930,7 +822,7 @@ static pj_bool_t on_check_complete(pj_ice *ice, (c->state==PJ_ICE_CHECK_STATE_FROZEN || c->state==PJ_ICE_CHECK_STATE_WAITING)) { - LOG((ice->obj_name, + LOG5((ice->obj_name, "Check %d to be failed because state is %s", i, check_state_name[c->state])); check_set_state(ice, c, PJ_ICE_CHECK_STATE_FAILED, @@ -981,22 +873,6 @@ static pj_bool_t on_check_complete(pj_ice *ice, /* TODO */ -#if 0 - /* For now, just see if we have a valid pair in component 1 and - * just terminate ICE. - */ - for (i=0; i<ice->valid_cnt; ++i) { - pj_ice_check *c = &ice->clist.checks[ice->valid_list[i]]; - if (c->lcand->comp_id == 1) - break; - } - - if (i != ice->valid_cnt) { - /* ICE succeeded */ - on_ice_complete(ice, PJ_SUCCESS); - return PJ_TRUE; - } -#else /* See if all components have nominated pair. If they do, then mark * ICE processing as success, otherwise wait. */ @@ -1009,7 +885,6 @@ static pj_bool_t on_check_complete(pj_ice *ice, on_ice_complete(ice, PJ_SUCCESS); return PJ_TRUE; } -#endif /* * See if all checks in the checklist have completed. If we do, @@ -1024,7 +899,7 @@ static pj_bool_t on_check_complete(pj_ice *ice, if (i == ice->clist.count) { /* All checks have completed */ - on_ice_complete(ice, -1); + on_ice_complete(ice, PJNATH_EICEFAILED); return PJ_TRUE; } @@ -1166,7 +1041,7 @@ static pj_status_t perform_check(pj_ice *ice, pj_ice_checklist *clist, rcand = check->rcand; comp = find_comp(ice, lcand->comp_id); - LOG((ice->obj_name, + LOG5((ice->obj_name, "Sending connectivity check for check %s", dump_check(buffer, sizeof(buffer), ice, check))); @@ -1238,7 +1113,7 @@ static pj_status_t start_periodic_check(pj_timer_heap_t *th, /* Set checklist state to Running */ clist_set_state(ice, clist, PJ_ICE_CHECKLIST_ST_RUNNING); - LOG((ice->obj_name, "Starting checklist periodic check")); + LOG5((ice->obj_name, "Starting checklist periodic check")); /* Send STUN Binding request for check with highest priority on * Waiting state. @@ -1306,14 +1181,13 @@ PJ_DEF(pj_status_t) pj_ice_start_check(pj_ice *ice) unsigned i; PJ_ASSERT_RETURN(ice, PJ_EINVAL); + /* Checklist must be created */ + PJ_ASSERT_RETURN(ice->clist.count > 0, PJ_EINVALIDOP); - LOG((ice->obj_name, "Starting ICE check..")); + LOG4((ice->obj_name, "Starting ICE check..")); clist = &ice->clist; - if (clist->count == 0) - return PJ_EICENOCHECKLIST; - /* Pickup the first pair and set the state to Waiting */ clist->checks[0].state = PJ_ICE_CHECK_STATE_WAITING; cand0 = clist->checks[0].lcand; @@ -1362,9 +1236,8 @@ static void on_stun_request_complete(pj_stun_session *stun_sess, { struct req_data *rd = (struct req_data*) tdata->user_data; pj_ice *ice; - pj_ice_check *check; - const pj_ice_cand *lcand; - const pj_ice_cand *rcand; + pj_ice_check *check, *new_check; + pj_ice_cand *lcand; pj_ice_checklist *clist; pj_stun_xor_mapped_addr_attr *xaddr; char buffer[CHECK_NAME_LEN]; @@ -1378,10 +1251,12 @@ static void on_stun_request_complete(pj_stun_session *stun_sess, pj_mutex_lock(ice->mutex); - lcand = check->lcand; - rcand = check->rcand; + /* Init lcand to NULL. lcand will be found from the mapped address + * found in the response. + */ + lcand = NULL; - LOG((ice->obj_name, + LOG4((ice->obj_name, "Check %s%s: connectivity check %s", dump_check(buffer, sizeof(buffer), ice, check), (check->nominated ? " (nominated)" : " (not nominated)"), @@ -1402,29 +1277,32 @@ static void on_stun_request_complete(pj_stun_session *stun_sess, */ PJ_TODO(ICE_CHECK_RESPONSE_SOURCE_ADDRESS); - /* Get the STUN MAPPED-ADDRESS attribute. */ + /* Get the STUN XOR-MAPPED-ADDRESS attribute. */ xaddr = (pj_stun_xor_mapped_addr_attr*) pj_stun_msg_find_attr(response, PJ_STUN_ATTR_XOR_MAPPED_ADDR,0); if (!xaddr) { check_set_state(ice, check, PJ_ICE_CHECK_STATE_FAILED, - PJNATH_ESTUNNOXORMAP); + PJNATH_ESTUNNOMAPPEDADDR); on_check_complete(ice, check); pj_mutex_unlock(ice->mutex); return; } - /* If the transport address returned in XOR-MAPPED-ADDRESS does not match - * any of the local candidates that the agent knows about, the mapped - * address represents a new candidate - a peer reflexive candidate. - */ + /* Find local candidate that matches the XOR-MAPPED-ADDRESS */ + pj_assert(lcand == NULL); for (i=0; i<ice->lcand_cnt; ++i) { if (sockaddr_cmp(&xaddr->sockaddr, &ice->lcand[i].addr) == 0) { /* Match */ + lcand = &ice->lcand[i]; break; } } - if (i == ice->lcand_cnt) { + /* If the transport address returned in XOR-MAPPED-ADDRESS does not match + * any of the local candidates that the agent knows about, the mapped + * address represents a new candidate - a peer reflexive candidate. + */ + if (lcand == NULL) { unsigned cand_id; char buf[32]; pj_str_t foundation; @@ -1450,14 +1328,23 @@ static void on_stun_request_complete(pj_stun_session *stun_sess, lcand = &ice->lcand[cand_id]; } - /* Sets the state of the pair that generated the check to succeeded. */ - check_set_state(ice, check, PJ_ICE_CHECK_STATE_SUCCEEDED, PJ_SUCCESS); - - /* This is a valid pair, so add this to the valid list */ - ice->valid_list[ice->valid_cnt++] = rd->ckid; + /* Add pair to valid list */ + new_check = &ice->valid_list.checks[ice->valid_list.count++]; + new_check->lcand = lcand; + new_check->rcand = check->rcand; + new_check->prio = CALC_CHECK_PRIO(ice, lcand, check->rcand); + new_check->state = PJ_ICE_CHECK_STATE_SUCCEEDED; + new_check->nominated = check->nominated; + new_check->err_code = PJ_SUCCESS; /* Sort valid_list */ - sort_valid_list(ice); + sort_checklist(&ice->valid_list); + + + /* Sets the state of the original pair that generated the check to + * succeeded. + */ + check_set_state(ice, check, PJ_ICE_CHECK_STATE_SUCCEEDED, PJ_SUCCESS); /* Inform about check completion. * This may terminate ICE processing. @@ -1515,7 +1402,9 @@ static void on_stun_request_complete(pj_stun_session *stun_sess, pj_mutex_unlock(ice->mutex); } - +/* This callback is called by the STUN session associated with a candidate + * when it receives incoming request. + */ static pj_status_t on_stun_rx_request(pj_stun_session *sess, const pj_uint8_t *pkt, unsigned pkt_len, @@ -1540,18 +1429,14 @@ static pj_status_t on_stun_rx_request(pj_stun_session *sess, /* Reject any requests except Binding request */ if (msg->hdr.type != PJ_STUN_BINDING_REQUEST) { - pj_str_t err_msg = pj_str("Expecting Binding Request only"); status = pj_stun_session_create_response(sess, msg, PJ_STUN_SC_BAD_REQUEST, - &err_msg, &tdata); - if (status != PJ_SUCCESS) { + NULL, &tdata); + if (status != PJ_SUCCESS) return status; - } - - status = pj_stun_session_send_msg(sess, PJ_TRUE, - src_addr, src_addr_len, tdata); - return status; + return pj_stun_session_send_msg(sess, PJ_TRUE, + src_addr, src_addr_len, tdata); } @@ -1566,7 +1451,7 @@ static pj_status_t on_stun_rx_request(pj_stun_session *sess, ap = (pj_stun_priority_attr*) pj_stun_msg_find_attr(msg, PJ_STUN_ATTR_PRIORITY, 0); if (ap == 0) { - LOG((ice->obj_name, "Received Binding request with no PRIORITY")); + LOG5((ice->obj_name, "Received Binding request with no PRIORITY")); pj_mutex_unlock(ice->mutex); return PJ_SUCCESS; } @@ -1626,7 +1511,7 @@ static pj_status_t on_stun_rx_request(pj_stun_session *sess, "f%p", rcand->foundation.ptr); - LOG((ice->obj_name, + LOG4((ice->obj_name, "Added new remote candidate from the request: %s:%d", pj_inet_ntoa(rcand->addr.ipv4.sin_addr), (int)pj_ntohs(rcand->addr.ipv4.sin_port))); @@ -1678,14 +1563,14 @@ static pj_status_t on_stun_rx_request(pj_stun_session *sess, if (c->state == PJ_ICE_CHECK_STATE_FROZEN || c->state == PJ_ICE_CHECK_STATE_WAITING) { - LOG((ice->obj_name, "Performing triggered check for check %d",i)); + LOG5((ice->obj_name, "Performing triggered check for check %d",i)); perform_check(ice, &ice->clist, i); } else if (c->state == PJ_ICE_CHECK_STATE_IN_PROGRESS) { /* Should retransmit here, but how?? * TODO */ - LOG((ice->obj_name, "Triggered check for check %d not performed " + LOG5((ice->obj_name, "Triggered check for check %d not performed " "because it's in progress", i)); } else if (c->state == PJ_ICE_CHECK_STATE_SUCCEEDED) { /* Check complete for this component. @@ -1693,7 +1578,7 @@ static pj_status_t on_stun_rx_request(pj_stun_session *sess, */ pj_bool_t complete; - LOG((ice->obj_name, "Triggered check for check %d not performed " + LOG5((ice->obj_name, "Triggered check for check %d not performed " "because it's completed", i)); complete = on_check_complete(ice, c); @@ -1721,12 +1606,12 @@ static pj_status_t on_stun_rx_request(pj_stun_session *sess, c->nominated = (uc != NULL); c->err_code = PJ_SUCCESS; - LOG((ice->obj_name, "New triggered check added: %d", + LOG4((ice->obj_name, "New triggered check added: %d", ice->clist.count)); perform_check(ice, &ice->clist, ice->clist.count++); } else { - LOG((ice->obj_name, "Error: unable to perform triggered check: " + LOG4((ice->obj_name, "Error: unable to perform triggered check: " "TOO MANY CHECKS IN CHECKLIST!")); } @@ -1771,12 +1656,12 @@ PJ_DEF(pj_status_t) pj_ice_send_data( pj_ice *ice, comp = find_comp(ice, comp_id); if (comp == NULL) { - status = PJ_EICEINCOMPID; + status = PJNATH_EICEINCOMPID; goto on_return; } if (comp->nominated_check_id == -1) { - status = PJ_EICEINPROGRESS; + status = PJNATH_EICEINPROGRESS; goto on_return; } @@ -1812,7 +1697,7 @@ PJ_DEF(pj_status_t) pj_ice_on_rx_pkt( pj_ice *ice, comp = find_comp(ice, comp_id); if (comp == NULL) { - status = PJ_EICEINCOMPID; + status = PJNATH_EICEINCOMPID; goto on_return; } diff --git a/pjnath/src/pjnath/ice_stream_transport.c b/pjnath/src/pjnath/ice_stream_transport.c index 1462ff25..c479a3df 100644 --- a/pjnath/src/pjnath/ice_stream_transport.c +++ b/pjnath/src/pjnath/ice_stream_transport.c @@ -364,13 +364,13 @@ PJ_DEF(pj_status_t) pj_ice_st_add_comp(pj_ice_st *ice_st, PJ_ASSERT_RETURN(ice_st->comp_cnt < PJ_ICE_MAX_COMP, PJ_ETOOMANY); /* Component ID must be valid */ - PJ_ASSERT_RETURN(comp_id <= PJ_ICE_MAX_COMP, PJ_EICEINCOMPID); + PJ_ASSERT_RETURN(comp_id <= PJ_ICE_MAX_COMP, PJNATH_EICEINCOMPID); /* First component ID must be 1, second must be 2, etc., and * they must be registered in order. */ PJ_ASSERT_RETURN(ice_st->comps[comp_id-1] == ice_st->comp_cnt, - PJ_EICEINCOMPID); + PJNATH_EICEINCOMPID); /* All in order, add the component. */ ice_st->comps[ice_st->comp_cnt++] = comp_id; @@ -407,7 +407,7 @@ PJ_DEF(pj_status_t) pj_ice_st_add_host_interface(pj_ice_st *ice_st, PJ_ASSERT_RETURN(ice_st && comp_id, PJ_EINVAL); /* Check that component ID present */ - PJ_ASSERT_RETURN(comp_id <= ice_st->comp_cnt, PJ_EICEINCOMPID); + PJ_ASSERT_RETURN(comp_id <= ice_st->comp_cnt, PJNATH_EICEINCOMPID); /* Can't add new interface while ICE is running */ PJ_ASSERT_RETURN(ice_st->ice == NULL, PJ_EBUSY); @@ -578,20 +578,14 @@ PJ_DEF(pj_status_t) pj_ice_st_init_ice(pj_ice_st *ice_st, /* Create! */ status = pj_ice_create(&ice_st->stun_cfg, ice_st->obj_name, role, - &ice_cb, local_ufrag, local_passwd, &ice_st->ice); + ice_st->comp_cnt, &ice_cb, + local_ufrag, local_passwd, &ice_st->ice); if (status != PJ_SUCCESS) return status; /* Associate user data */ ice_st->ice->user_data = (void*)ice_st; - /* Add components */ - for (i=0; i<ice_st->comp_cnt; ++i) { - status = pj_ice_add_comp(ice_st->ice, ice_st->comps[i]); - if (status != PJ_SUCCESS) - goto on_error; - } - /* Add candidates */ for (i=0; i<ice_st->itf_cnt; ++i) { pj_ice_st_interface *is= ice_st->itfs[i]; @@ -626,20 +620,16 @@ PJ_DEF(pj_status_t) pj_ice_st_enum_cands(pj_ice_st *ice_st, { unsigned i, cnt; pj_ice_cand *pcand; - pj_status_t status; PJ_ASSERT_RETURN(ice_st && count && cand, PJ_EINVAL); PJ_ASSERT_RETURN(ice_st->ice, PJ_EINVALIDOP); - cnt = pj_ice_get_cand_cnt(ice_st->ice); + cnt = ice_st->ice->lcand_cnt; cnt = (cnt > *count) ? *count : cnt; *count = 0; for (i=0; i<cnt; ++i) { - status = pj_ice_get_cand(ice_st->ice, i, &pcand); - if (status != PJ_SUCCESS) - return status; - + pcand = &ice_st->ice->lcand[i]; pj_memcpy(&cand[i], pcand, sizeof(pj_ice_cand)); } @@ -688,7 +678,7 @@ PJ_DEF(pj_status_t) pj_ice_st_send_data( pj_ice_st *ice_st, pj_size_t data_len) { if (!ice_st->ice) - return PJ_ENOICE; + return PJNATH_ENOICE; return pj_ice_send_data(ice_st->ice, comp_id, data, data_len); } @@ -752,7 +742,7 @@ static pj_status_t on_tx_pkt(pj_ice *ice, } } if (is == NULL) { - return PJ_EICEINCANDID; + return PJNATH_EICEINCANDID; } pkt_size = size; diff --git a/pjnath/src/pjnath/stun_auth.c b/pjnath/src/pjnath/stun_auth.c index 2602bf8d..15f226dc 100644 --- a/pjnath/src/pjnath/stun_auth.c +++ b/pjnath/src/pjnath/stun_auth.c @@ -159,7 +159,7 @@ PJ_DEF(pj_status_t) pj_stun_verify_credential( const pj_uint8_t *pkt, create_challenge(pool, msg, PJ_STUN_SC_UNAUTHORIZED, NULL, &realm, &nonce, p_response); } - return PJNATH_ESTUNMSGINT; + return PJ_STATUS_FROM_STUN_CODE(PJ_STUN_SC_INTEGRITY_CHECK_FAILURE); } /* Next check that USERNAME is present */ @@ -170,7 +170,7 @@ PJ_DEF(pj_status_t) pj_stun_verify_credential( const pj_uint8_t *pkt, create_challenge(pool, msg, PJ_STUN_SC_MISSING_USERNAME, NULL, &realm, &nonce, p_response); } - return PJNATH_ESTUNNOUSERNAME; + return PJ_STATUS_FROM_STUN_CODE(PJ_STUN_SC_MISSING_USERNAME); } /* Get REALM, if any */ @@ -202,7 +202,7 @@ PJ_DEF(pj_status_t) pj_stun_verify_credential( const pj_uint8_t *pkt, create_challenge(pool, msg, PJ_STUN_SC_UNKNOWN_USERNAME, NULL, &realm, &nonce, p_response); } - return PJNATH_ESTUNUSERNAME; + return PJ_STATUS_FROM_STUN_CODE(PJ_STUN_SC_UNKNOWN_USERNAME); } @@ -217,7 +217,7 @@ PJ_DEF(pj_status_t) pj_stun_verify_credential( const pj_uint8_t *pkt, create_challenge(pool, msg, PJ_STUN_SC_MISSING_REALM, NULL, &realm, &nonce, p_response); } - return PJNATH_ESTUNNOREALM; + return PJ_STATUS_FROM_STUN_CODE(PJ_STUN_SC_MISSING_REALM); } else if (realm.slen != 0 && arealm != NULL) { /* We want long term, and REALM is present */ @@ -228,7 +228,7 @@ PJ_DEF(pj_status_t) pj_stun_verify_credential( const pj_uint8_t *pkt, create_challenge(pool, msg, PJ_STUN_SC_MISSING_NONCE, NULL, &realm, &nonce, p_response); } - return PJNATH_ESTUNNONCE; + return PJ_STATUS_FROM_STUN_CODE(PJ_STUN_SC_MISSING_NONCE); } /* Verify REALM matches */ @@ -238,7 +238,7 @@ PJ_DEF(pj_status_t) pj_stun_verify_credential( const pj_uint8_t *pkt, create_challenge(pool, msg, PJ_STUN_SC_MISSING_REALM, NULL, &realm, &nonce, p_response); } - return PJNATH_ESTUNNOREALM; + return PJ_STATUS_FROM_STUN_CODE(PJ_STUN_SC_MISSING_REALM); } /* Valid case, will validate the message integrity later */ @@ -261,7 +261,7 @@ PJ_DEF(pj_status_t) pj_stun_verify_credential( const pj_uint8_t *pkt, create_challenge(pool, msg, PJ_STUN_SC_MISSING_NONCE, NULL, &realm, &nonce, p_response); } - return PJNATH_ESTUNNONCE; + return PJ_STATUS_FROM_STUN_CODE(PJ_STUN_SC_MISSING_NONCE); } } @@ -288,7 +288,7 @@ PJ_DEF(pj_status_t) pj_stun_verify_credential( const pj_uint8_t *pkt, create_challenge(pool, msg, PJ_STUN_SC_STALE_NONCE, NULL, &realm, &nonce, p_response); } - return PJNATH_ESTUNNONCE; + return PJ_STATUS_FROM_STUN_CODE(PJ_STUN_SC_MISSING_NONCE); } } @@ -333,7 +333,7 @@ PJ_DEF(pj_status_t) pj_stun_verify_credential( const pj_uint8_t *pkt, create_challenge(pool, msg, PJ_STUN_SC_INTEGRITY_CHECK_FAILURE, NULL, &realm, &nonce, p_response); } - return PJNATH_ESTUNMSGINT; + return PJ_STATUS_FROM_STUN_CODE(PJ_STUN_SC_INTEGRITY_CHECK_FAILURE); } /* Everything looks okay! */ diff --git a/pjnath/src/pjnath/stun_msg.c b/pjnath/src/pjnath/stun_msg.c index 2fdd9027..bd32c6ba 100644 --- a/pjnath/src/pjnath/stun_msg.c +++ b/pjnath/src/pjnath/stun_msg.c @@ -64,7 +64,6 @@ static struct { PJ_STUN_SC_NO_BINDING, "No Binding"}, { PJ_STUN_SC_STALE_NONCE, "Stale Nonce"}, { PJ_STUN_SC_TRANSITIONING, "Active Destination Already Set"}, - { PJ_STUN_SC_WRONG_USERNAME, "Wrong Username"}, { PJ_STUN_SC_UNSUPP_TRANSPORT_PROTO, "Unsupported Transport Protocol"}, { PJ_STUN_SC_INVALID_IP_ADDR, "Invalid IP Address"}, { PJ_STUN_SC_INVALID_PORT, "Invalid Port"}, @@ -513,6 +512,8 @@ PJ_DEF(const char*) pj_stun_get_attr_name(unsigned attr_type) */ PJ_DEF(pj_str_t) pj_stun_get_err_reason(int err_code) { +#if 0 + /* Find error using linear search */ unsigned i; for (i=0; i<PJ_ARRAY_SIZE(stun_err_msg_map); ++i) { @@ -520,6 +521,33 @@ PJ_DEF(pj_str_t) pj_stun_get_err_reason(int err_code) return pj_str((char*)stun_err_msg_map[i].err_msg); } return pj_str(NULL); +#else + /* Find error message using binary search */ + int first = 0; + int n = PJ_ARRAY_SIZE(stun_err_msg_map); + + while (n > 0) { + int half = n/2; + int mid = first + half; + + if (stun_err_msg_map[mid].err_code < err_code) { + first = mid+1; + n -= (half+1); + } else if (stun_err_msg_map[mid].err_code > err_code) { + n = half; + } else { + first = mid; + break; + } + } + + + if (stun_err_msg_map[first].err_code == err_code) { + return pj_str((char*)stun_err_msg_map[first].err_msg); + } else { + return pj_str(NULL); + } +#endif } @@ -1579,18 +1607,18 @@ PJ_DEF(pj_status_t) pj_stun_msg_check(const pj_uint8_t *pdu, unsigned pdu_len, PJ_ASSERT_RETURN(pdu, PJ_EINVAL); if (pdu_len < sizeof(pj_stun_msg_hdr)) - return PJNATH_ESTUNINMSGLEN; + return PJNATH_EINSTUNMSGLEN; /* First byte of STUN message is always 0x00 or 0x01. */ if (*pdu != 0x00 && *pdu != 0x01) - return PJNATH_ESTUNINMSGTYPE; + return PJNATH_EINSTUNMSGTYPE; /* Check the PDU length */ msg_len = GET_VAL16(pdu, 2); if ((msg_len + 20 > pdu_len) || ((options & PJ_STUN_IS_DATAGRAM) && msg_len + 20 != pdu_len)) { - return PJNATH_ESTUNINMSGLEN; + return PJNATH_EINSTUNMSGLEN; } /* If magic is set, then there is great possibility that this is @@ -1634,7 +1662,7 @@ PJ_DEF(pj_status_t) pj_stun_msg_create_response(pj_pool_t *pool, PJ_ASSERT_RETURN(pool && p_response, PJ_EINVAL); PJ_ASSERT_RETURN(PJ_STUN_IS_REQUEST(msg_type), - PJNATH_ESTUNINMSGTYPE); + PJNATH_EINSTUNMSGTYPE); /* Create response or error response */ if (err_code) @@ -1773,7 +1801,7 @@ PJ_DEF(pj_status_t) pj_stun_msg_decode(pj_pool_t *pool, } } - return PJNATH_ESTUNUNKNOWNATTR; + return PJ_STATUS_FROM_STUN_CODE(PJ_STUN_SC_UNKNOWN_ATTRIBUTE); } } else { @@ -2102,7 +2130,7 @@ PJ_DEF(pj_status_t) pj_stun_msg_encode(pj_stun_msg *msg, if (auname == NULL) { /* Should not happen for message generated by us */ pj_assert(PJ_FALSE); - return PJNATH_ESTUNNOUSERNAME; + return PJ_STATUS_FROM_STUN_CODE(PJ_STUN_SC_MISSING_USERNAME); } /* Password must be specified */ diff --git a/pjnath/src/pjnath/stun_transaction.c b/pjnath/src/pjnath/stun_transaction.c index 2813f7ef..07ce69d7 100644 --- a/pjnath/src/pjnath/stun_transaction.c +++ b/pjnath/src/pjnath/stun_transaction.c @@ -235,7 +235,7 @@ static void retransmit_timer_callback(pj_timer_heap_t *timer_heap, PJ_LOG(4,(tsx->obj_name, "STUN timeout waiting for response")); tsx->complete = PJ_TRUE; if (tsx->cb.on_complete) { - tsx->cb.on_complete(tsx, PJNATH_ESTUNNOTRESPOND, NULL); + tsx->cb.on_complete(tsx, PJNATH_ESTUNTIMEDOUT, NULL); } return; } @@ -268,7 +268,7 @@ PJ_DEF(pj_status_t) pj_stun_client_tsx_on_rx_msg(pj_stun_client_tsx *tsx, { PJ_LOG(4,(tsx->obj_name, "STUN rx_msg() error: not response message")); - return PJNATH_ESTUNNOTRESPONSE; + return PJNATH_EINSTUNMSGTYPE; } @@ -300,7 +300,8 @@ PJ_DEF(pj_status_t) pj_stun_client_tsx_on_rx_msg(pj_stun_client_tsx *tsx, if (err_attr == NULL) { status = PJ_SUCCESS; } else { - status = PJNATH_ESTUNTSXFAILED; + status = PJ_STATUS_FROM_STUN_CODE(err_attr->err_class * 100 + + err_attr->number); } /* Call callback */ |