Mon May 14 04:42:58 2007

Asterisk developer's documentation


utils.h

Go to the documentation of this file.
00001 /*
00002  * Asterisk -- An open source telephony toolkit.
00003  *
00004  * Copyright (C) 1999 - 2006, Digium, Inc.
00005  *
00006  * Mark Spencer <markster@digium.com>
00007  *
00008  * See http://www.asterisk.org for more information about
00009  * the Asterisk project. Please do not directly contact
00010  * any of the maintainers of this project for assistance;
00011  * the project provides a web site, mailing lists and IRC
00012  * channels for your use.
00013  *
00014  * This program is free software, distributed under the terms of
00015  * the GNU General Public License Version 2. See the LICENSE file
00016  * at the top of the source tree.
00017  */
00018 
00019 /*! \file
00020  * \brief Utility functions
00021  */
00022 
00023 #ifndef _ASTERISK_UTILS_H
00024 #define _ASTERISK_UTILS_H
00025 
00026 #include "asterisk/compat.h"
00027 
00028 #include <stdlib.h>
00029 #include <stdio.h>
00030 #include <stdarg.h>
00031 #include <netinet/in.h>
00032 #include <arpa/inet.h>  /* we want to override inet_ntoa */
00033 #include <netdb.h>
00034 #include <limits.h>
00035 
00036 #include "asterisk/lock.h"
00037 #include "asterisk/time.h"
00038 #include "asterisk/strings.h"
00039 #include "asterisk/logger.h"
00040 #include "asterisk/compiler.h"
00041 
00042 /*! \note
00043  \verbatim
00044    Note:
00045    It is very important to use only unsigned variables to hold
00046    bit flags, as otherwise you can fall prey to the compiler's
00047    sign-extension antics if you try to use the top two bits in
00048    your variable.
00049 
00050    The flag macros below use a set of compiler tricks to verify
00051    that the caller is using an "unsigned int" variable to hold
00052    the flags, and nothing else. If the caller uses any other
00053    type of variable, a warning message similar to this:
00054 
00055    warning: comparison of distinct pointer types lacks cast
00056    will be generated.
00057 
00058    The "dummy" variable below is used to make these comparisons.
00059 
00060    Also note that at -O2 or above, this type-safety checking
00061    does _not_ produce any additional object code at all.
00062  \endverbatim
00063 */
00064 
00065 extern unsigned int __unsigned_int_flags_dummy;
00066 
00067 #define ast_test_flag(p,flag)       ({ \
00068                typeof ((p)->flags) __p = (p)->flags; \
00069                typeof (__unsigned_int_flags_dummy) __x = 0; \
00070                (void) (&__p == &__x); \
00071                ((p)->flags & (flag)); \
00072                })
00073 
00074 #define ast_set_flag(p,flag)     do { \
00075                typeof ((p)->flags) __p = (p)->flags; \
00076                typeof (__unsigned_int_flags_dummy) __x = 0; \
00077                (void) (&__p == &__x); \
00078                ((p)->flags |= (flag)); \
00079                } while(0)
00080 
00081 #define ast_clear_flag(p,flag)      do { \
00082                typeof ((p)->flags) __p = (p)->flags; \
00083                typeof (__unsigned_int_flags_dummy) __x = 0; \
00084                (void) (&__p == &__x); \
00085                ((p)->flags &= ~(flag)); \
00086                } while(0)
00087 
00088 #define ast_copy_flags(dest,src,flagz) do { \
00089                typeof ((dest)->flags) __d = (dest)->flags; \
00090                typeof ((src)->flags) __s = (src)->flags; \
00091                typeof (__unsigned_int_flags_dummy) __x = 0; \
00092                (void) (&__d == &__x); \
00093                (void) (&__s == &__x); \
00094                (dest)->flags &= ~(flagz); \
00095                (dest)->flags |= ((src)->flags & (flagz)); \
00096                } while (0)
00097 
00098 #define ast_set2_flag(p,value,flag) do { \
00099                typeof ((p)->flags) __p = (p)->flags; \
00100                typeof (__unsigned_int_flags_dummy) __x = 0; \
00101                (void) (&__p == &__x); \
00102                if (value) \
00103                   (p)->flags |= (flag); \
00104                else \
00105                   (p)->flags &= ~(flag); \
00106                } while (0)
00107 
00108 #define ast_set_flags_to(p,flag,value) do { \
00109                typeof ((p)->flags) __p = (p)->flags; \
00110                typeof (__unsigned_int_flags_dummy) __x = 0; \
00111                (void) (&__p == &__x); \
00112                (p)->flags &= ~(flag); \
00113                (p)->flags |= (value); \
00114                } while (0)
00115 
00116 /* Non-type checking variations for non-unsigned int flags.  You
00117    should only use non-unsigned int flags where required by 
00118    protocol etc and if you know what you're doing :)  */
00119 #define ast_test_flag_nonstd(p,flag) \
00120                ((p)->flags & (flag))
00121 
00122 #define ast_set_flag_nonstd(p,flag)       do { \
00123                ((p)->flags |= (flag)); \
00124                } while(0)
00125 
00126 #define ast_clear_flag_nonstd(p,flag)     do { \
00127                ((p)->flags &= ~(flag)); \
00128                } while(0)
00129 
00130 #define ast_copy_flags_nonstd(dest,src,flagz)   do { \
00131                (dest)->flags &= ~(flagz); \
00132                (dest)->flags |= ((src)->flags & (flagz)); \
00133                } while (0)
00134 
00135 #define ast_set2_flag_nonstd(p,value,flag)   do { \
00136                if (value) \
00137                   (p)->flags |= (flag); \
00138                else \
00139                   (p)->flags &= ~(flag); \
00140                } while (0)
00141 
00142 #define AST_FLAGS_ALL UINT_MAX
00143 
00144 struct ast_flags {
00145    unsigned int flags;
00146 };
00147 
00148 struct ast_hostent {
00149    struct hostent hp;
00150    char buf[1024];
00151 };
00152 
00153 struct hostent *ast_gethostbyname(const char *host, struct ast_hostent *hp);
00154 
00155 /* ast_md5_hash 
00156    \brief Produces MD5 hash based on input string */
00157 void ast_md5_hash(char *output, char *input);
00158 /* ast_sha1_hash
00159    \brief Produces SHA1 hash based on input string */
00160 void ast_sha1_hash(char *output, char *input);
00161 
00162 int ast_base64encode_full(char *dst, const unsigned char *src, int srclen, int max, int linebreaks);
00163 int ast_base64encode(char *dst, const unsigned char *src, int srclen, int max);
00164 int ast_base64decode(unsigned char *dst, const char *src, int max);
00165 
00166 /*! ast_uri_encode
00167    \brief Turn text string to URI-encoded %XX version 
00168    At this point, we're converting from ISO-8859-x (8-bit), not UTF8
00169    as in the SIP protocol spec 
00170    If doreserved == 1 we will convert reserved characters also.
00171    RFC 2396, section 2.4
00172    outbuf needs to have more memory allocated than the instring
00173    to have room for the expansion. Every char that is converted
00174    is replaced by three ASCII characters.
00175    \param string  String to be converted
00176    \param outbuf  Resulting encoded string
00177    \param buflen  Size of output buffer
00178    \param doreserved Convert reserved characters
00179 */
00180 
00181 char *ast_uri_encode(const char *string, char *outbuf, int buflen, int doreserved);
00182 
00183 /*!   \brief Decode URI, URN, URL (overwrite string)
00184    \param s String to be decoded 
00185  */
00186 void ast_uri_decode(char *s);
00187 
00188 static force_inline void ast_slinear_saturated_add(short *input, short *value)
00189 {
00190    int res;
00191 
00192    res = (int) *input + *value;
00193    if (res > 32767)
00194       *input = 32767;
00195    else if (res < -32767)
00196       *input = -32767;
00197    else
00198       *input = (short) res;
00199 }
00200    
00201 static force_inline void ast_slinear_saturated_multiply(short *input, short *value)
00202 {
00203    int res;
00204 
00205    res = (int) *input * *value;
00206    if (res > 32767)
00207       *input = 32767;
00208    else if (res < -32767)
00209       *input = -32767;
00210    else
00211       *input = (short) res;
00212 }
00213 
00214 static force_inline void ast_slinear_saturated_divide(short *input, short *value)
00215 {
00216    *input /= *value;
00217 }
00218 
00219 int test_for_thread_safety(void);
00220 
00221 /*!
00222  * \brief thread-safe replacement for inet_ntoa().
00223  *
00224  * \note It is very important to note that even though this is a thread-safe
00225  *       replacement for inet_ntoa(), it is *not* reentrant.  In a single
00226  *       thread, the result from a previous call to this function is no longer
00227  *       valid once it is called again.  If the result from multiple calls to
00228  *       this function need to be kept or used at once, then the result must be
00229  *       copied to a local buffer before calling this function again.
00230  */
00231 const char *ast_inet_ntoa(struct in_addr ia);
00232 
00233 #ifdef inet_ntoa
00234 #undef inet_ntoa
00235 #endif
00236 #define inet_ntoa __dont__use__inet_ntoa__use__ast_inet_ntoa__instead__
00237 
00238 int ast_utils_init(void);
00239 int ast_wait_for_input(int fd, int ms);
00240 
00241 /*! ast_carefulwrite
00242    \brief Try to write string, but wait no more than ms milliseconds
00243    before timing out.
00244 
00245    \note If you are calling ast_carefulwrite, it is assumed that you are calling
00246    it on a file descriptor that _DOES_ have NONBLOCK set.  This way,
00247    there is only one system call made to do a write, unless we actually
00248    have a need to wait.  This way, we get better performance.
00249 */
00250 int ast_carefulwrite(int fd, char *s, int len, int timeoutms);
00251 
00252 /*! Compares the source address and port of two sockaddr_in */
00253 static force_inline int inaddrcmp(const struct sockaddr_in *sin1, const struct sockaddr_in *sin2)
00254 {
00255    return ((sin1->sin_addr.s_addr != sin2->sin_addr.s_addr) 
00256       || (sin1->sin_port != sin2->sin_port));
00257 }
00258 
00259 #define AST_STACKSIZE 240 * 1024
00260 
00261 #if defined(LOW_MEMORY)
00262 #define AST_BACKGROUND_STACKSIZE 48 * 1024
00263 #else
00264 #define AST_BACKGROUND_STACKSIZE 240 * 1024
00265 #endif
00266 
00267 void ast_register_thread(char *name);
00268 void ast_unregister_thread(void *id);
00269 
00270 int ast_pthread_create_stack(pthread_t *thread, pthread_attr_t *attr, void *(*start_routine)(void *),
00271               void *data, size_t stacksize, const char *file, const char *caller,
00272               int line, const char *start_fn);
00273 
00274 #define ast_pthread_create(a, b, c, d) ast_pthread_create_stack(a, b, c, d,         \
00275                              0,           \
00276                              __FILE__, __FUNCTION__,     \
00277                              __LINE__, #c)
00278 
00279 #define ast_pthread_create_background(a, b, c, d) ast_pthread_create_stack(a, b, c, d,       \
00280                               AST_BACKGROUND_STACKSIZE,  \
00281                               __FILE__, __FUNCTION__, \
00282                               __LINE__, #c)
00283 
00284 /*!
00285    \brief Process a string to find and replace characters
00286    \param start The string to analyze
00287    \param find The character to find
00288    \param replace_with The character that will replace the one we are looking for
00289 */
00290 char *ast_process_quotes_and_slashes(char *start, char find, char replace_with);
00291 
00292 #ifdef linux
00293 #define ast_random random
00294 #else
00295 long int ast_random(void);
00296 #endif
00297 
00298 /*! 
00299  * \brief free() wrapper
00300  *
00301  * ast_free should be used when a function pointer for free() needs to be passed
00302  * as the argument to a function. Otherwise, astmm will cause seg faults.
00303  */
00304 #ifdef __AST_DEBUG_MALLOC
00305 static void ast_free(void *ptr) attribute_unused;
00306 static void ast_free(void *ptr)
00307 {
00308    free(ptr);
00309 }
00310 #else
00311 #define ast_free free
00312 #endif
00313 
00314 #ifndef __AST_DEBUG_MALLOC
00315 
00316 #define MALLOC_FAILURE_MSG \
00317    ast_log(LOG_ERROR, "Memory Allocation Failure in function %s at line %d of %s\n", func, lineno, file);
00318 /*!
00319  * \brief A wrapper for malloc()
00320  *
00321  * ast_malloc() is a wrapper for malloc() that will generate an Asterisk log
00322  * message in the case that the allocation fails.
00323  *
00324  * The argument and return value are the same as malloc()
00325  */
00326 #define ast_malloc(len) \
00327    _ast_malloc((len), __FILE__, __LINE__, __PRETTY_FUNCTION__)
00328 
00329 AST_INLINE_API(
00330 void * attribute_malloc _ast_malloc(size_t len, const char *file, int lineno, const char *func),
00331 {
00332    void *p;
00333 
00334    if (!(p = malloc(len)))
00335       MALLOC_FAILURE_MSG;
00336 
00337    return p;
00338 }
00339 )
00340 
00341 /*!
00342  * \brief A wrapper for calloc()
00343  *
00344  * ast_calloc() is a wrapper for calloc() that will generate an Asterisk log
00345  * message in the case that the allocation fails.
00346  *
00347  * The arguments and return value are the same as calloc()
00348  */
00349 #define ast_calloc(num, len) \
00350    _ast_calloc((num), (len), __FILE__, __LINE__, __PRETTY_FUNCTION__)
00351 
00352 AST_INLINE_API(
00353 void * attribute_malloc _ast_calloc(size_t num, size_t len, const char *file, int lineno, const char *func),
00354 {
00355    void *p;
00356 
00357    if (!(p = calloc(num, len)))
00358       MALLOC_FAILURE_MSG;
00359 
00360    return p;
00361 }
00362 )
00363 
00364 /*!
00365  * \brief A wrapper for calloc() for use in cache pools
00366  *
00367  * ast_calloc_cache() is a wrapper for calloc() that will generate an Asterisk log
00368  * message in the case that the allocation fails. When memory debugging is in use,
00369  * the memory allocated by this function will be marked as 'cache' so it can be
00370  * distinguished from normal memory allocations.
00371  *
00372  * The arguments and return value are the same as calloc()
00373  */
00374 #define ast_calloc_cache(num, len) \
00375    _ast_calloc((num), (len), __FILE__, __LINE__, __PRETTY_FUNCTION__)
00376 
00377 /*!
00378  * \brief A wrapper for realloc()
00379  *
00380  * ast_realloc() is a wrapper for realloc() that will generate an Asterisk log
00381  * message in the case that the allocation fails.
00382  *
00383  * The arguments and return value are the same as realloc()
00384  */
00385 #define ast_realloc(p, len) \
00386    _ast_realloc((p), (len), __FILE__, __LINE__, __PRETTY_FUNCTION__)
00387 
00388 AST_INLINE_API(
00389 void * attribute_malloc _ast_realloc(void *p, size_t len, const char *file, int lineno, const char *func),
00390 {
00391    void *newp;
00392 
00393    if (!(newp = realloc(p, len)))
00394       MALLOC_FAILURE_MSG;
00395 
00396    return newp;
00397 }
00398 )
00399 
00400 /*!
00401  * \brief A wrapper for strdup()
00402  *
00403  * ast_strdup() is a wrapper for strdup() that will generate an Asterisk log
00404  * message in the case that the allocation fails.
00405  *
00406  * ast_strdup(), unlike strdup(), can safely accept a NULL argument. If a NULL
00407  * argument is provided, ast_strdup will return NULL without generating any
00408  * kind of error log message.
00409  *
00410  * The argument and return value are the same as strdup()
00411  */
00412 #define ast_strdup(str) \
00413    _ast_strdup((str), __FILE__, __LINE__, __PRETTY_FUNCTION__)
00414 
00415 AST_INLINE_API(
00416 char * attribute_malloc _ast_strdup(const char *str, const char *file, int lineno, const char *func),
00417 {
00418    char *newstr = NULL;
00419 
00420    if (str) {
00421       if (!(newstr = strdup(str)))
00422          MALLOC_FAILURE_MSG;
00423    }
00424 
00425    return newstr;
00426 }
00427 )
00428 
00429 /*!
00430  * \brief A wrapper for strndup()
00431  *
00432  * ast_strndup() is a wrapper for strndup() that will generate an Asterisk log
00433  * message in the case that the allocation fails.
00434  *
00435  * ast_strndup(), unlike strndup(), can safely accept a NULL argument for the
00436  * string to duplicate. If a NULL argument is provided, ast_strdup will return  
00437  * NULL without generating any kind of error log message.
00438  *
00439  * The arguments and return value are the same as strndup()
00440  */
00441 #define ast_strndup(str, len) \
00442    _ast_strndup((str), (len), __FILE__, __LINE__, __PRETTY_FUNCTION__)
00443 
00444 AST_INLINE_API(
00445 char * attribute_malloc _ast_strndup(const char *str, size_t len, const char *file, int lineno, const char *func),
00446 {
00447    char *newstr = NULL;
00448 
00449    if (str) {
00450       if (!(newstr = strndup(str, len)))
00451          MALLOC_FAILURE_MSG;
00452    }
00453 
00454    return newstr;
00455 }
00456 )
00457 
00458 /*!
00459  * \brief A wrapper for asprintf()
00460  *
00461  * ast_asprintf() is a wrapper for asprintf() that will generate an Asterisk log
00462  * message in the case that the allocation fails.
00463  *
00464  * The arguments and return value are the same as asprintf()
00465  */
00466 #define ast_asprintf(ret, fmt, ...) \
00467    _ast_asprintf((ret), __FILE__, __LINE__, __PRETTY_FUNCTION__, fmt, __VA_ARGS__)
00468 
00469 AST_INLINE_API(
00470 int _ast_asprintf(char **ret, const char *file, int lineno, const char *func, const char *fmt, ...),
00471 {
00472    int res;
00473    va_list ap;
00474 
00475    va_start(ap, fmt);
00476    if ((res = vasprintf(ret, fmt, ap)) == -1)
00477       MALLOC_FAILURE_MSG;
00478    va_end(ap);
00479 
00480    return res;
00481 }
00482 )
00483 
00484 /*!
00485  * \brief A wrapper for vasprintf()
00486  *
00487  * ast_vasprintf() is a wrapper for vasprintf() that will generate an Asterisk log
00488  * message in the case that the allocation fails.
00489  *
00490  * The arguments and return value are the same as vasprintf()
00491  */
00492 #define ast_vasprintf(ret, fmt, ap) \
00493    _ast_vasprintf((ret), __FILE__, __LINE__, __PRETTY_FUNCTION__, (fmt), (ap))
00494 
00495 AST_INLINE_API(
00496 int _ast_vasprintf(char **ret, const char *file, int lineno, const char *func, const char *fmt, va_list ap),
00497 {
00498    int res;
00499 
00500    if ((res = vasprintf(ret, fmt, ap)) == -1)
00501       MALLOC_FAILURE_MSG;
00502 
00503    return res;
00504 }
00505 )
00506 
00507 #else
00508 
00509 /* If astmm is in use, let it handle these.  Otherwise, it will report that
00510    all allocations are coming from this header file */
00511 
00512 #define ast_malloc(a)      malloc(a)
00513 #define ast_calloc(a,b)    calloc(a,b)
00514 #define ast_realloc(a,b)   realloc(a,b)
00515 #define ast_strdup(a)      strdup(a)
00516 #define ast_strndup(a,b)   strndup(a,b)
00517 #define ast_asprintf(a,b,c)   asprintf(a,b,c)
00518 #define ast_vasprintf(a,b,c)  vasprintf(a,b,c)
00519 
00520 #endif /* AST_DEBUG_MALLOC */
00521 
00522 #if !defined(ast_strdupa) && defined(__GNUC__)
00523 /*!
00524   \brief duplicate a string in memory from the stack
00525   \param s The string to duplicate
00526 
00527   This macro will duplicate the given string.  It returns a pointer to the stack
00528   allocatted memory for the new string.
00529 */
00530 #define ast_strdupa(s)                                                    \
00531    (__extension__                                                    \
00532    ({                                                                \
00533       const char *__old = (s);                                  \
00534       size_t __len = strlen(__old) + 1;                         \
00535       char *__new = __builtin_alloca(__len);                    \
00536       memcpy (__new, __old, __len);                             \
00537       __new;                                                    \
00538    }))
00539 #endif
00540 
00541 /*!
00542   \brief Disable PMTU discovery on a socket
00543   \param sock The socket to manipulate
00544   \return Nothing
00545 
00546   On Linux, UDP sockets default to sending packets with the Dont Fragment (DF)
00547   bit set. This is supposedly done to allow the application to do PMTU
00548   discovery, but Asterisk does not do this.
00549 
00550   Because of this, UDP packets sent by Asterisk that are larger than the MTU
00551   of any hop in the path will be lost. This function can be called on a socket
00552   to ensure that the DF bit will not be set.
00553  */
00554 void ast_enable_packet_fragmentation(int sock);
00555 
00556 #define ARRAY_LEN(a) (sizeof(a) / sizeof(a[0]))
00557 
00558 #endif /* _ASTERISK_UTILS_H */

Generated on Mon May 14 04:42:58 2007 for Asterisk - the Open Source PBX by  doxygen 1.5.1