Core/General: Add #ifdef needed on FreeBSD.
[asterisk/asterisk.git] / main / utils.c
1 /*
2  * Asterisk -- An open source telephony toolkit.
3  *
4  * Copyright (C) 1999 - 2006, Digium, Inc.
5  *
6  * See http://www.asterisk.org for more information about
7  * the Asterisk project. Please do not directly contact
8  * any of the maintainers of this project for assistance;
9  * the project provides a web site, mailing lists and IRC
10  * channels for your use.
11  *
12  * This program is free software, distributed under the terms of
13  * the GNU General Public License Version 2. See the LICENSE file
14  * at the top of the source tree.
15  */
16
17 /*! \file
18  *
19  * \brief Utility functions
20  *
21  * \note These are important for portability and security,
22  * so please use them in favour of other routines.
23  * Please consult the CODING GUIDELINES for more information.
24  */
25
26 /*** MODULEINFO
27         <support_level>core</support_level>
28  ***/
29
30 #include "asterisk.h"
31
32 ASTERISK_REGISTER_FILE()
33
34 #include <ctype.h>
35 #include <fcntl.h>
36 #include <sys/stat.h>
37 #include <sys/syscall.h>
38 #include <unistd.h>
39 #if defined(__APPLE__)
40 #include <mach/mach.h>
41 #elif defined(HAVE_SYS_THR_H)
42 #include <sys/thr.h>
43 #endif
44
45 #include "asterisk/network.h"
46 #include "asterisk/ast_version.h"
47
48 #define AST_API_MODULE          /* ensure that inlinable API functions will be built in lock.h if required */
49 #include "asterisk/lock.h"
50 #include "asterisk/io.h"
51 #include "asterisk/md5.h"
52 #include "asterisk/sha1.h"
53 #include "asterisk/cli.h"
54 #include "asterisk/linkedlists.h"
55 #include "asterisk/astobj2.h"
56
57 #define AST_API_MODULE          /* ensure that inlinable API functions will be built in this module if required */
58 #include "asterisk/strings.h"
59
60 #define AST_API_MODULE          /* ensure that inlinable API functions will be built in this module if required */
61 #include "asterisk/time.h"
62
63 #define AST_API_MODULE          /* ensure that inlinable API functions will be built in this module if required */
64 #include "asterisk/stringfields.h"
65
66 #define AST_API_MODULE          /* ensure that inlinable API functions will be built in this module if required */
67 #include "asterisk/utils.h"
68
69 #define AST_API_MODULE
70 #include "asterisk/threadstorage.h"
71
72 #define AST_API_MODULE
73 #include "asterisk/config.h"
74
75 static char base64[64];
76 static char b2a[256];
77
78 AST_THREADSTORAGE(inet_ntoa_buf);
79
80 #if !defined(HAVE_GETHOSTBYNAME_R_5) && !defined(HAVE_GETHOSTBYNAME_R_6)
81
82 #define ERANGE 34       /*!< duh? ERANGE value copied from web... */
83 #undef gethostbyname
84
85 AST_MUTEX_DEFINE_STATIC(__mutex);
86
87 /*! \brief Reentrant replacement for gethostbyname for BSD-based systems.
88 \note This
89 routine is derived from code originally written and placed in the public
90 domain by Enzo Michelangeli <em@em.no-ip.com> */
91
92 static int gethostbyname_r (const char *name, struct hostent *ret, char *buf,
93                                 size_t buflen, struct hostent **result,
94                                 int *h_errnop)
95 {
96         int hsave;
97         struct hostent *ph;
98         ast_mutex_lock(&__mutex); /* begin critical area */
99         hsave = h_errno;
100
101         ph = gethostbyname(name);
102         *h_errnop = h_errno; /* copy h_errno to *h_herrnop */
103         if (ph == NULL) {
104                 *result = NULL;
105         } else {
106                 char **p, **q;
107                 char *pbuf;
108                 int nbytes = 0;
109                 int naddr = 0, naliases = 0;
110                 /* determine if we have enough space in buf */
111
112                 /* count how many addresses */
113                 for (p = ph->h_addr_list; *p != 0; p++) {
114                         nbytes += ph->h_length; /* addresses */
115                         nbytes += sizeof(*p); /* pointers */
116                         naddr++;
117                 }
118                 nbytes += sizeof(*p); /* one more for the terminating NULL */
119
120                 /* count how many aliases, and total length of strings */
121                 for (p = ph->h_aliases; *p != 0; p++) {
122                         nbytes += (strlen(*p)+1); /* aliases */
123                         nbytes += sizeof(*p);  /* pointers */
124                         naliases++;
125                 }
126                 nbytes += sizeof(*p); /* one more for the terminating NULL */
127
128                 /* here nbytes is the number of bytes required in buffer */
129                 /* as a terminator must be there, the minimum value is ph->h_length */
130                 if (nbytes > buflen) {
131                         *result = NULL;
132                         ast_mutex_unlock(&__mutex); /* end critical area */
133                         return ERANGE; /* not enough space in buf!! */
134                 }
135
136                 /* There is enough space. Now we need to do a deep copy! */
137                 /* Allocation in buffer:
138                         from [0] to [(naddr-1) * sizeof(*p)]:
139                         pointers to addresses
140                         at [naddr * sizeof(*p)]:
141                         NULL
142                         from [(naddr+1) * sizeof(*p)] to [(naddr+naliases) * sizeof(*p)] :
143                         pointers to aliases
144                         at [(naddr+naliases+1) * sizeof(*p)]:
145                         NULL
146                         then naddr addresses (fixed length), and naliases aliases (asciiz).
147                 */
148
149                 *ret = *ph;   /* copy whole structure (not its address!) */
150
151                 /* copy addresses */
152                 q = (char **)buf; /* pointer to pointers area (type: char **) */
153                 ret->h_addr_list = q; /* update pointer to address list */
154                 pbuf = buf + ((naddr + naliases + 2) * sizeof(*p)); /* skip that area */
155                 for (p = ph->h_addr_list; *p != 0; p++) {
156                         memcpy(pbuf, *p, ph->h_length); /* copy address bytes */
157                         *q++ = pbuf; /* the pointer is the one inside buf... */
158                         pbuf += ph->h_length; /* advance pbuf */
159                 }
160                 *q++ = NULL; /* address list terminator */
161
162                 /* copy aliases */
163                 ret->h_aliases = q; /* update pointer to aliases list */
164                 for (p = ph->h_aliases; *p != 0; p++) {
165                         strcpy(pbuf, *p); /* copy alias strings */
166                         *q++ = pbuf; /* the pointer is the one inside buf... */
167                         pbuf += strlen(*p); /* advance pbuf */
168                         *pbuf++ = 0; /* string terminator */
169                 }
170                 *q++ = NULL; /* terminator */
171
172                 strcpy(pbuf, ph->h_name); /* copy alias strings */
173                 ret->h_name = pbuf;
174                 pbuf += strlen(ph->h_name); /* advance pbuf */
175                 *pbuf++ = 0; /* string terminator */
176
177                 *result = ret;  /* and let *result point to structure */
178
179         }
180         h_errno = hsave;  /* restore h_errno */
181         ast_mutex_unlock(&__mutex); /* end critical area */
182
183         return (*result == NULL); /* return 0 on success, non-zero on error */
184 }
185
186
187 #endif
188
189 /*! \brief Re-entrant (thread safe) version of gethostbyname that replaces the
190    standard gethostbyname (which is not thread safe)
191 */
192 struct hostent *ast_gethostbyname(const char *host, struct ast_hostent *hp)
193 {
194         int res;
195         int herrno;
196         int dots = 0;
197         const char *s;
198         struct hostent *result = NULL;
199         /* Although it is perfectly legitimate to lookup a pure integer, for
200            the sake of the sanity of people who like to name their peers as
201            integers, we break with tradition and refuse to look up a
202            pure integer */
203         s = host;
204         res = 0;
205         while (s && *s) {
206                 if (*s == '.')
207                         dots++;
208                 else if (!isdigit(*s))
209                         break;
210                 s++;
211         }
212         if (!s || !*s) {
213                 /* Forge a reply for IP's to avoid octal IP's being interpreted as octal */
214                 if (dots != 3)
215                         return NULL;
216                 memset(hp, 0, sizeof(struct ast_hostent));
217                 hp->hp.h_addrtype = AF_INET;
218                 hp->hp.h_addr_list = (void *) hp->buf;
219                 hp->hp.h_addr = hp->buf + sizeof(void *);
220                 /* For AF_INET, this will always be 4 */
221                 hp->hp.h_length = 4;
222                 if (inet_pton(AF_INET, host, hp->hp.h_addr) > 0)
223                         return &hp->hp;
224                 return NULL;
225
226         }
227 #ifdef HAVE_GETHOSTBYNAME_R_5
228         result = gethostbyname_r(host, &hp->hp, hp->buf, sizeof(hp->buf), &herrno);
229
230         if (!result || !hp->hp.h_addr_list || !hp->hp.h_addr_list[0])
231                 return NULL;
232 #else
233         res = gethostbyname_r(host, &hp->hp, hp->buf, sizeof(hp->buf), &result, &herrno);
234
235         if (res || !result || !hp->hp.h_addr_list || !hp->hp.h_addr_list[0])
236                 return NULL;
237 #endif
238         return &hp->hp;
239 }
240
241 /*! \brief Produce 32 char MD5 hash of value. */
242 void ast_md5_hash(char *output, const char *input)
243 {
244         struct MD5Context md5;
245         unsigned char digest[16];
246         char *ptr;
247         int x;
248
249         MD5Init(&md5);
250         MD5Update(&md5, (const unsigned char *) input, strlen(input));
251         MD5Final(digest, &md5);
252         ptr = output;
253         for (x = 0; x < 16; x++)
254                 ptr += sprintf(ptr, "%02hhx", digest[x]);
255 }
256
257 /*! \brief Produce 40 char SHA1 hash of value. */
258 void ast_sha1_hash(char *output, const char *input)
259 {
260         struct SHA1Context sha;
261         char *ptr;
262         int x;
263         uint8_t Message_Digest[20];
264
265         SHA1Reset(&sha);
266
267         SHA1Input(&sha, (const unsigned char *) input, strlen(input));
268
269         SHA1Result(&sha, Message_Digest);
270         ptr = output;
271         for (x = 0; x < 20; x++)
272                 ptr += sprintf(ptr, "%02hhx", Message_Digest[x]);
273 }
274
275 /*! \brief Produce a 20 byte SHA1 hash of value. */
276 void ast_sha1_hash_uint(uint8_t *digest, const char *input)
277 {
278         struct SHA1Context sha;
279
280         SHA1Reset(&sha);
281
282         SHA1Input(&sha, (const unsigned char *) input, strlen(input));
283
284         SHA1Result(&sha, digest);
285 }
286
287 /*! \brief decode BASE64 encoded text */
288 int ast_base64decode(unsigned char *dst, const char *src, int max)
289 {
290         int cnt = 0;
291         unsigned int byte = 0;
292         unsigned int bits = 0;
293         int incnt = 0;
294         while(*src && *src != '=' && (cnt < max)) {
295                 /* Shift in 6 bits of input */
296                 byte <<= 6;
297                 byte |= (b2a[(int)(*src)]) & 0x3f;
298                 bits += 6;
299                 src++;
300                 incnt++;
301                 /* If we have at least 8 bits left over, take that character
302                    off the top */
303                 if (bits >= 8)  {
304                         bits -= 8;
305                         *dst = (byte >> bits) & 0xff;
306                         dst++;
307                         cnt++;
308                 }
309         }
310         /* Don't worry about left over bits, they're extra anyway */
311         return cnt;
312 }
313
314 /*! \brief encode text to BASE64 coding */
315 int ast_base64encode_full(char *dst, const unsigned char *src, int srclen, int max, int linebreaks)
316 {
317         int cnt = 0;
318         int col = 0;
319         unsigned int byte = 0;
320         int bits = 0;
321         int cntin = 0;
322         /* Reserve space for null byte at end of string */
323         max--;
324         while ((cntin < srclen) && (cnt < max)) {
325                 byte <<= 8;
326                 byte |= *(src++);
327                 bits += 8;
328                 cntin++;
329                 if ((bits == 24) && (cnt + 4 <= max)) {
330                         *dst++ = base64[(byte >> 18) & 0x3f];
331                         *dst++ = base64[(byte >> 12) & 0x3f];
332                         *dst++ = base64[(byte >> 6) & 0x3f];
333                         *dst++ = base64[byte & 0x3f];
334                         cnt += 4;
335                         col += 4;
336                         bits = 0;
337                         byte = 0;
338                 }
339                 if (linebreaks && (cnt < max) && (col == 64)) {
340                         *dst++ = '\n';
341                         cnt++;
342                         col = 0;
343                 }
344         }
345         if (bits && (cnt + 4 <= max)) {
346                 /* Add one last character for the remaining bits,
347                    padding the rest with 0 */
348                 byte <<= 24 - bits;
349                 *dst++ = base64[(byte >> 18) & 0x3f];
350                 *dst++ = base64[(byte >> 12) & 0x3f];
351                 if (bits == 16)
352                         *dst++ = base64[(byte >> 6) & 0x3f];
353                 else
354                         *dst++ = '=';
355                 *dst++ = '=';
356                 cnt += 4;
357         }
358         if (linebreaks && (cnt < max)) {
359                 *dst++ = '\n';
360                 cnt++;
361         }
362         *dst = '\0';
363         return cnt;
364 }
365
366 int ast_base64encode(char *dst, const unsigned char *src, int srclen, int max)
367 {
368         return ast_base64encode_full(dst, src, srclen, max, 0);
369 }
370
371 static void base64_init(void)
372 {
373         int x;
374         memset(b2a, -1, sizeof(b2a));
375         /* Initialize base-64 Conversion table */
376         for (x = 0; x < 26; x++) {
377                 /* A-Z */
378                 base64[x] = 'A' + x;
379                 b2a['A' + x] = x;
380                 /* a-z */
381                 base64[x + 26] = 'a' + x;
382                 b2a['a' + x] = x + 26;
383                 /* 0-9 */
384                 if (x < 10) {
385                         base64[x + 52] = '0' + x;
386                         b2a['0' + x] = x + 52;
387                 }
388         }
389         base64[62] = '+';
390         base64[63] = '/';
391         b2a[(int)'+'] = 62;
392         b2a[(int)'/'] = 63;
393 }
394
395 const struct ast_flags ast_uri_http = {AST_URI_UNRESERVED};
396 const struct ast_flags ast_uri_http_legacy = {AST_URI_LEGACY_SPACE | AST_URI_UNRESERVED};
397 const struct ast_flags ast_uri_sip_user = {AST_URI_UNRESERVED | AST_URI_SIP_USER_UNRESERVED};
398
399 char *ast_uri_encode(const char *string, char *outbuf, int buflen, struct ast_flags spec)
400 {
401         const char *ptr  = string;      /* Start with the string */
402         char *out = outbuf;
403         const char *mark = "-_.!~*'()"; /* no encode set, RFC 2396 section 2.3, RFC 3261 sec 25 */
404         const char *user_unreserved = "&=+$,;?/"; /* user-unreserved set, RFC 3261 sec 25 */
405
406         while (*ptr && out - outbuf < buflen - 1) {
407                 if (ast_test_flag(&spec, AST_URI_LEGACY_SPACE) && *ptr == ' ') {
408                         /* for legacy encoding, encode spaces as '+' */
409                         *out = '+';
410                         out++;
411                 } else if (!(ast_test_flag(&spec, AST_URI_MARK)
412                                 && strchr(mark, *ptr))
413                         && !(ast_test_flag(&spec, AST_URI_ALPHANUM)
414                                 && ((*ptr >= '0' && *ptr <= '9')
415                                 || (*ptr >= 'A' && *ptr <= 'Z')
416                                 || (*ptr >= 'a' && *ptr <= 'z')))
417                         && !(ast_test_flag(&spec, AST_URI_SIP_USER_UNRESERVED)
418                                 && strchr(user_unreserved, *ptr))) {
419
420                         if (out - outbuf >= buflen - 3) {
421                                 break;
422                         }
423                         out += sprintf(out, "%%%02hhX", (unsigned char) *ptr);
424                 } else {
425                         *out = *ptr;    /* Continue copying the string */
426                         out++;
427                 }
428                 ptr++;
429         }
430
431         if (buflen) {
432                 *out = '\0';
433         }
434
435         return outbuf;
436 }
437
438 void ast_uri_decode(char *s, struct ast_flags spec)
439 {
440         char *o;
441         unsigned int tmp;
442
443         for (o = s; *s; s++, o++) {
444                 if (ast_test_flag(&spec, AST_URI_LEGACY_SPACE) && *s == '+') {
445                         /* legacy mode, decode '+' as space */
446                         *o = ' ';
447                 } else if (*s == '%' && s[1] != '\0' && s[2] != '\0' && sscanf(s + 1, "%2x", &tmp) == 1) {
448                         /* have '%', two chars and correct parsing */
449                         *o = tmp;
450                         s += 2; /* Will be incremented once more when we break out */
451                 } else /* all other cases, just copy */
452                         *o = *s;
453         }
454         *o = '\0';
455 }
456
457 char *ast_escape_quoted(const char *string, char *outbuf, int buflen)
458 {
459         const char *ptr  = string;
460         char *out = outbuf;
461         char *allow = "\t\v !"; /* allow LWS (minus \r and \n) and "!" */
462
463         while (*ptr && out - outbuf < buflen - 1) {
464                 if (!(strchr(allow, *ptr))
465                         && !(*ptr >= '#' && *ptr <= '[') /* %x23 - %x5b */
466                         && !(*ptr >= ']' && *ptr <= '~') /* %x5d - %x7e */
467                         && !((unsigned char) *ptr > 0x7f)) {             /* UTF8-nonascii */
468
469                         if (out - outbuf >= buflen - 2) {
470                                 break;
471                         }
472                         out += sprintf(out, "\\%c", (unsigned char) *ptr);
473                 } else {
474                         *out = *ptr;
475                         out++;
476                 }
477                 ptr++;
478         }
479
480         if (buflen) {
481                 *out = '\0';
482         }
483
484         return outbuf;
485 }
486
487 char *ast_escape_semicolons(const char *string, char *outbuf, int buflen)
488 {
489         const char *ptr = string;
490         char *out = outbuf;
491
492         if (string == NULL || outbuf == NULL) {
493                 ast_assert(string != NULL && outbuf != NULL);
494                 return NULL;
495         }
496
497         while (*ptr && out - outbuf < buflen - 1) {
498                 if (*ptr == ';') {
499                         if (out - outbuf >= buflen - 2) {
500                                 break;
501                         }
502                         strcpy(out, "\\;");
503                         out += 2;
504                 } else {
505                         *out = *ptr;
506                         out++;
507                 }
508                 ptr++;
509         }
510
511         if (buflen) {
512                 *out = '\0';
513         }
514
515         return outbuf;
516 }
517
518 void ast_unescape_quoted(char *quote_str)
519 {
520         int esc_pos;
521         int unesc_pos;
522         int quote_str_len = strlen(quote_str);
523
524         for (esc_pos = 0, unesc_pos = 0;
525                 esc_pos < quote_str_len;
526                 esc_pos++, unesc_pos++) {
527                 if (quote_str[esc_pos] == '\\') {
528                         /* at least one more char and current is \\ */
529                         esc_pos++;
530                         if (esc_pos >= quote_str_len) {
531                                 break;
532                         }
533                 }
534
535                 quote_str[unesc_pos] = quote_str[esc_pos];
536         }
537         quote_str[unesc_pos] = '\0';
538 }
539
540 int ast_xml_escape(const char *string, char * const outbuf, const size_t buflen)
541 {
542         char *dst = outbuf;
543         char *end = outbuf + buflen - 1; /* save one for the null terminator */
544
545         /* Handle the case for the empty output buffer */
546         if (buflen == 0) {
547                 return -1;
548         }
549
550         /* Escaping rules from http://www.w3.org/TR/REC-xml/#syntax */
551         /* This also prevents partial entities at the end of a string */
552         while (*string && dst < end) {
553                 const char *entity = NULL;
554                 int len = 0;
555
556                 switch (*string) {
557                 case '<':
558                         entity = "&lt;";
559                         len = 4;
560                         break;
561                 case '&':
562                         entity = "&amp;";
563                         len = 5;
564                         break;
565                 case '>':
566                         /* necessary if ]]> is in the string; easier to escape them all */
567                         entity = "&gt;";
568                         len = 4;
569                         break;
570                 case '\'':
571                         /* necessary in single-quoted strings; easier to escape them all */
572                         entity = "&apos;";
573                         len = 6;
574                         break;
575                 case '"':
576                         /* necessary in double-quoted strings; easier to escape them all */
577                         entity = "&quot;";
578                         len = 6;
579                         break;
580                 default:
581                         *dst++ = *string++;
582                         break;
583                 }
584
585                 if (entity) {
586                         ast_assert(len == strlen(entity));
587                         if (end - dst < len) {
588                                 /* no room for the entity; stop */
589                                 break;
590                         }
591                         /* just checked for length; strcpy is fine */
592                         strcpy(dst, entity);
593                         dst += len;
594                         ++string;
595                 }
596         }
597         /* Write null terminator */
598         *dst = '\0';
599         /* If any chars are left in string, return failure */
600         return *string == '\0' ? 0 : -1;
601 }
602
603 /*! \brief  ast_inet_ntoa: Recursive thread safe replacement of inet_ntoa */
604 const char *ast_inet_ntoa(struct in_addr ia)
605 {
606         char *buf;
607
608         if (!(buf = ast_threadstorage_get(&inet_ntoa_buf, INET_ADDRSTRLEN)))
609                 return "";
610
611         return inet_ntop(AF_INET, &ia, buf, INET_ADDRSTRLEN);
612 }
613
614 static int dev_urandom_fd = -1;
615
616 #ifndef __linux__
617 #undef pthread_create /* For ast_pthread_create function only */
618 #endif /* !__linux__ */
619
620 #if !defined(LOW_MEMORY)
621
622 #ifdef DEBUG_THREADS
623
624 /*! \brief A reasonable maximum number of locks a thread would be holding ... */
625 #define AST_MAX_LOCKS 64
626
627 /* Allow direct use of pthread_mutex_t and friends */
628 #undef pthread_mutex_t
629 #undef pthread_mutex_lock
630 #undef pthread_mutex_unlock
631 #undef pthread_mutex_init
632 #undef pthread_mutex_destroy
633
634 /*!
635  * \brief Keep track of which locks a thread holds
636  *
637  * There is an instance of this struct for every active thread
638  */
639 struct thr_lock_info {
640         /*! The thread's ID */
641         pthread_t thread_id;
642         /*! The thread name which includes where the thread was started */
643         const char *thread_name;
644         /*! This is the actual container of info for what locks this thread holds */
645         struct {
646                 const char *file;
647                 const char *func;
648                 const char *lock_name;
649                 void *lock_addr;
650                 int times_locked;
651                 int line_num;
652                 enum ast_lock_type type;
653                 /*! This thread is waiting on this lock */
654                 int pending:2;
655                 /*! A condition has suspended this lock */
656                 int suspended:1;
657 #ifdef HAVE_BKTR
658                 struct ast_bt *backtrace;
659 #endif
660         } locks[AST_MAX_LOCKS];
661         /*! This is the number of locks currently held by this thread.
662          *  The index (num_locks - 1) has the info on the last one in the
663          *  locks member */
664         unsigned int num_locks;
665         /*! The LWP id (which GDB prints) */
666         int lwp;
667         /*! Protects the contents of the locks member
668          * Intentionally not ast_mutex_t */
669         pthread_mutex_t lock;
670         AST_LIST_ENTRY(thr_lock_info) entry;
671 };
672
673 /*!
674  * \brief Locked when accessing the lock_infos list
675  */
676 AST_MUTEX_DEFINE_STATIC(lock_infos_lock);
677 /*!
678  * \brief A list of each thread's lock info
679  */
680 static AST_LIST_HEAD_NOLOCK_STATIC(lock_infos, thr_lock_info);
681
682 /*!
683  * \brief Destroy a thread's lock info
684  *
685  * This gets called automatically when the thread stops
686  */
687 static void lock_info_destroy(void *data)
688 {
689         struct thr_lock_info *lock_info = data;
690         int i;
691
692         pthread_mutex_lock(&lock_infos_lock.mutex);
693         AST_LIST_REMOVE(&lock_infos, lock_info, entry);
694         pthread_mutex_unlock(&lock_infos_lock.mutex);
695
696
697         for (i = 0; i < lock_info->num_locks; i++) {
698                 if (lock_info->locks[i].pending == -1) {
699                         /* This just means that the last lock this thread went for was by
700                          * using trylock, and it failed.  This is fine. */
701                         break;
702                 }
703
704                 ast_log(LOG_ERROR,
705                         "Thread '%s' still has a lock! - '%s' (%p) from '%s' in %s:%d!\n",
706                         lock_info->thread_name,
707                         lock_info->locks[i].lock_name,
708                         lock_info->locks[i].lock_addr,
709                         lock_info->locks[i].func,
710                         lock_info->locks[i].file,
711                         lock_info->locks[i].line_num
712                 );
713         }
714
715         pthread_mutex_destroy(&lock_info->lock);
716         if (lock_info->thread_name) {
717                 ast_free((void *) lock_info->thread_name);
718         }
719         ast_free(lock_info);
720 }
721
722 /*!
723  * \brief The thread storage key for per-thread lock info
724  */
725 AST_THREADSTORAGE_CUSTOM(thread_lock_info, NULL, lock_info_destroy);
726 #ifdef HAVE_BKTR
727 void ast_store_lock_info(enum ast_lock_type type, const char *filename,
728         int line_num, const char *func, const char *lock_name, void *lock_addr, struct ast_bt *bt)
729 #else
730 void ast_store_lock_info(enum ast_lock_type type, const char *filename,
731         int line_num, const char *func, const char *lock_name, void *lock_addr)
732 #endif
733 {
734         struct thr_lock_info *lock_info;
735         int i;
736
737         if (!(lock_info = ast_threadstorage_get(&thread_lock_info, sizeof(*lock_info))))
738                 return;
739
740         pthread_mutex_lock(&lock_info->lock);
741
742         for (i = 0; i < lock_info->num_locks; i++) {
743                 if (lock_info->locks[i].lock_addr == lock_addr) {
744                         lock_info->locks[i].times_locked++;
745 #ifdef HAVE_BKTR
746                         lock_info->locks[i].backtrace = bt;
747 #endif
748                         pthread_mutex_unlock(&lock_info->lock);
749                         return;
750                 }
751         }
752
753         if (lock_info->num_locks == AST_MAX_LOCKS) {
754                 /* Can't use ast_log here, because it will cause infinite recursion */
755                 fprintf(stderr, "XXX ERROR XXX A thread holds more locks than '%d'."
756                         "  Increase AST_MAX_LOCKS!\n", AST_MAX_LOCKS);
757                 pthread_mutex_unlock(&lock_info->lock);
758                 return;
759         }
760
761         if (i && lock_info->locks[i - 1].pending == -1) {
762                 /* The last lock on the list was one that this thread tried to lock but
763                  * failed at doing so.  It has now moved on to something else, so remove
764                  * the old lock from the list. */
765                 i--;
766                 lock_info->num_locks--;
767                 memset(&lock_info->locks[i], 0, sizeof(lock_info->locks[0]));
768         }
769
770         lock_info->locks[i].file = filename;
771         lock_info->locks[i].line_num = line_num;
772         lock_info->locks[i].func = func;
773         lock_info->locks[i].lock_name = lock_name;
774         lock_info->locks[i].lock_addr = lock_addr;
775         lock_info->locks[i].times_locked = 1;
776         lock_info->locks[i].type = type;
777         lock_info->locks[i].pending = 1;
778 #ifdef HAVE_BKTR
779         lock_info->locks[i].backtrace = bt;
780 #endif
781         lock_info->num_locks++;
782
783         pthread_mutex_unlock(&lock_info->lock);
784 }
785
786 void ast_mark_lock_acquired(void *lock_addr)
787 {
788         struct thr_lock_info *lock_info;
789
790         if (!(lock_info = ast_threadstorage_get(&thread_lock_info, sizeof(*lock_info))))
791                 return;
792
793         pthread_mutex_lock(&lock_info->lock);
794         if (lock_info->locks[lock_info->num_locks - 1].lock_addr == lock_addr) {
795                 lock_info->locks[lock_info->num_locks - 1].pending = 0;
796         }
797         pthread_mutex_unlock(&lock_info->lock);
798 }
799
800 void ast_mark_lock_failed(void *lock_addr)
801 {
802         struct thr_lock_info *lock_info;
803
804         if (!(lock_info = ast_threadstorage_get(&thread_lock_info, sizeof(*lock_info))))
805                 return;
806
807         pthread_mutex_lock(&lock_info->lock);
808         if (lock_info->locks[lock_info->num_locks - 1].lock_addr == lock_addr) {
809                 lock_info->locks[lock_info->num_locks - 1].pending = -1;
810                 lock_info->locks[lock_info->num_locks - 1].times_locked--;
811         }
812         pthread_mutex_unlock(&lock_info->lock);
813 }
814
815 int ast_find_lock_info(void *lock_addr, char *filename, size_t filename_size, int *lineno, char *func, size_t func_size, char *mutex_name, size_t mutex_name_size)
816 {
817         struct thr_lock_info *lock_info;
818         int i = 0;
819
820         if (!(lock_info = ast_threadstorage_get(&thread_lock_info, sizeof(*lock_info))))
821                 return -1;
822
823         pthread_mutex_lock(&lock_info->lock);
824
825         for (i = lock_info->num_locks - 1; i >= 0; i--) {
826                 if (lock_info->locks[i].lock_addr == lock_addr)
827                         break;
828         }
829
830         if (i == -1) {
831                 /* Lock not found :( */
832                 pthread_mutex_unlock(&lock_info->lock);
833                 return -1;
834         }
835
836         ast_copy_string(filename, lock_info->locks[i].file, filename_size);
837         *lineno = lock_info->locks[i].line_num;
838         ast_copy_string(func, lock_info->locks[i].func, func_size);
839         ast_copy_string(mutex_name, lock_info->locks[i].lock_name, mutex_name_size);
840
841         pthread_mutex_unlock(&lock_info->lock);
842
843         return 0;
844 }
845
846 void ast_suspend_lock_info(void *lock_addr)
847 {
848         struct thr_lock_info *lock_info;
849         int i = 0;
850
851         if (!(lock_info = ast_threadstorage_get(&thread_lock_info, sizeof(*lock_info)))) {
852                 return;
853         }
854
855         pthread_mutex_lock(&lock_info->lock);
856
857         for (i = lock_info->num_locks - 1; i >= 0; i--) {
858                 if (lock_info->locks[i].lock_addr == lock_addr)
859                         break;
860         }
861
862         if (i == -1) {
863                 /* Lock not found :( */
864                 pthread_mutex_unlock(&lock_info->lock);
865                 return;
866         }
867
868         lock_info->locks[i].suspended = 1;
869
870         pthread_mutex_unlock(&lock_info->lock);
871 }
872
873 void ast_restore_lock_info(void *lock_addr)
874 {
875         struct thr_lock_info *lock_info;
876         int i = 0;
877
878         if (!(lock_info = ast_threadstorage_get(&thread_lock_info, sizeof(*lock_info))))
879                 return;
880
881         pthread_mutex_lock(&lock_info->lock);
882
883         for (i = lock_info->num_locks - 1; i >= 0; i--) {
884                 if (lock_info->locks[i].lock_addr == lock_addr)
885                         break;
886         }
887
888         if (i == -1) {
889                 /* Lock not found :( */
890                 pthread_mutex_unlock(&lock_info->lock);
891                 return;
892         }
893
894         lock_info->locks[i].suspended = 0;
895
896         pthread_mutex_unlock(&lock_info->lock);
897 }
898
899
900 #ifdef HAVE_BKTR
901 void ast_remove_lock_info(void *lock_addr, struct ast_bt *bt)
902 #else
903 void ast_remove_lock_info(void *lock_addr)
904 #endif
905 {
906         struct thr_lock_info *lock_info;
907         int i = 0;
908
909         if (!(lock_info = ast_threadstorage_get(&thread_lock_info, sizeof(*lock_info))))
910                 return;
911
912         pthread_mutex_lock(&lock_info->lock);
913
914         for (i = lock_info->num_locks - 1; i >= 0; i--) {
915                 if (lock_info->locks[i].lock_addr == lock_addr)
916                         break;
917         }
918
919         if (i == -1) {
920                 /* Lock not found :( */
921                 pthread_mutex_unlock(&lock_info->lock);
922                 return;
923         }
924
925         if (lock_info->locks[i].times_locked > 1) {
926                 lock_info->locks[i].times_locked--;
927 #ifdef HAVE_BKTR
928                 lock_info->locks[i].backtrace = bt;
929 #endif
930                 pthread_mutex_unlock(&lock_info->lock);
931                 return;
932         }
933
934         if (i < lock_info->num_locks - 1) {
935                 /* Not the last one ... *should* be rare! */
936                 memmove(&lock_info->locks[i], &lock_info->locks[i + 1],
937                         (lock_info->num_locks - (i + 1)) * sizeof(lock_info->locks[0]));
938         }
939
940         lock_info->num_locks--;
941
942         pthread_mutex_unlock(&lock_info->lock);
943 }
944
945 static const char *locktype2str(enum ast_lock_type type)
946 {
947         switch (type) {
948         case AST_MUTEX:
949                 return "MUTEX";
950         case AST_RDLOCK:
951                 return "RDLOCK";
952         case AST_WRLOCK:
953                 return "WRLOCK";
954         }
955
956         return "UNKNOWN";
957 }
958
959 #ifdef HAVE_BKTR
960 static void append_backtrace_information(struct ast_str **str, struct ast_bt *bt)
961 {
962         char **symbols;
963         int num_frames;
964
965         if (!bt) {
966                 ast_str_append(str, 0, "\tNo backtrace to print\n");
967                 return;
968         }
969
970         /* store frame count locally to avoid the memory corruption that
971          * sometimes happens on virtualized CentOS 6.x systems */
972         num_frames = bt->num_frames;
973         if ((symbols = ast_bt_get_symbols(bt->addresses, num_frames))) {
974                 int frame_iterator;
975
976                 for (frame_iterator = 0; frame_iterator < num_frames; ++frame_iterator) {
977                         ast_str_append(str, 0, "\t%s\n", symbols[frame_iterator]);
978                 }
979
980                 ast_std_free(symbols);
981         } else {
982                 ast_str_append(str, 0, "\tCouldn't retrieve backtrace symbols\n");
983         }
984 }
985 #endif
986
987 static void append_lock_information(struct ast_str **str, struct thr_lock_info *lock_info, int i)
988 {
989         int j;
990         ast_mutex_t *lock;
991         struct ast_lock_track *lt;
992
993         ast_str_append(str, 0, "=== ---> %sLock #%d (%s): %s %d %s %s %p (%d%s)\n",
994                                    lock_info->locks[i].pending > 0 ? "Waiting for " :
995                                    lock_info->locks[i].pending < 0 ? "Tried and failed to get " : "", i,
996                                    lock_info->locks[i].file,
997                                    locktype2str(lock_info->locks[i].type),
998                                    lock_info->locks[i].line_num,
999                                    lock_info->locks[i].func, lock_info->locks[i].lock_name,
1000                                    lock_info->locks[i].lock_addr,
1001                                    lock_info->locks[i].times_locked,
1002                                    lock_info->locks[i].suspended ? " - suspended" : "");
1003 #ifdef HAVE_BKTR
1004         append_backtrace_information(str, lock_info->locks[i].backtrace);
1005 #endif
1006
1007         if (!lock_info->locks[i].pending || lock_info->locks[i].pending == -1)
1008                 return;
1009
1010         /* We only have further details for mutexes right now */
1011         if (lock_info->locks[i].type != AST_MUTEX)
1012                 return;
1013
1014         lock = lock_info->locks[i].lock_addr;
1015         lt = lock->track;
1016         ast_reentrancy_lock(lt);
1017         for (j = 0; *str && j < lt->reentrancy; j++) {
1018                 ast_str_append(str, 0, "=== --- ---> Locked Here: %s line %d (%s)\n",
1019                                            lt->file[j], lt->lineno[j], lt->func[j]);
1020         }
1021         ast_reentrancy_unlock(lt);
1022 }
1023
1024
1025 /*! This function can help you find highly temporal locks; locks that happen for a
1026     short time, but at unexpected times, usually at times that create a deadlock,
1027         Why is this thing locked right then? Who is locking it? Who am I fighting
1028     with for this lock?
1029
1030         To answer such questions, just call this routine before you would normally try
1031         to aquire a lock. It doesn't do anything if the lock is not acquired. If the
1032         lock is taken, it will publish a line or two to the console via ast_log().
1033
1034         Sometimes, the lock message is pretty uninformative. For instance, you might
1035         find that the lock is being aquired deep within the astobj2 code; this tells
1036         you little about higher level routines that call the astobj2 routines.
1037         But, using gdb, you can set a break at the ast_log below, and for that
1038         breakpoint, you can set the commands:
1039           where
1040           cont
1041         which will give a stack trace and continue. -- that aught to do the job!
1042
1043 */
1044 void ast_log_show_lock(void *this_lock_addr)
1045 {
1046         struct thr_lock_info *lock_info;
1047         struct ast_str *str;
1048
1049         if (!(str = ast_str_create(4096))) {
1050                 ast_log(LOG_NOTICE,"Could not create str\n");
1051                 return;
1052         }
1053
1054
1055         pthread_mutex_lock(&lock_infos_lock.mutex);
1056         AST_LIST_TRAVERSE(&lock_infos, lock_info, entry) {
1057                 int i;
1058                 pthread_mutex_lock(&lock_info->lock);
1059                 for (i = 0; str && i < lock_info->num_locks; i++) {
1060                         /* ONLY show info about this particular lock, if
1061                            it's acquired... */
1062                         if (lock_info->locks[i].lock_addr == this_lock_addr) {
1063                                 append_lock_information(&str, lock_info, i);
1064                                 ast_log(LOG_NOTICE, "%s", ast_str_buffer(str));
1065                                 break;
1066                         }
1067                 }
1068                 pthread_mutex_unlock(&lock_info->lock);
1069         }
1070         pthread_mutex_unlock(&lock_infos_lock.mutex);
1071         ast_free(str);
1072 }
1073
1074
1075 struct ast_str *ast_dump_locks(void)
1076 {
1077         struct thr_lock_info *lock_info;
1078         struct ast_str *str;
1079
1080         if (!(str = ast_str_create(4096))) {
1081                 return NULL;
1082         }
1083
1084         ast_str_append(&str, 0, "\n"
1085                        "=======================================================================\n"
1086                        "=== %s\n"
1087                        "=== Currently Held Locks\n"
1088                        "=======================================================================\n"
1089                        "===\n"
1090                        "=== <pending> <lock#> (<file>): <lock type> <line num> <function> <lock name> <lock addr> (times locked)\n"
1091                        "===\n", ast_get_version());
1092
1093         if (!str) {
1094                 return NULL;
1095         }
1096
1097         pthread_mutex_lock(&lock_infos_lock.mutex);
1098         AST_LIST_TRAVERSE(&lock_infos, lock_info, entry) {
1099                 int i;
1100                 int header_printed = 0;
1101                 pthread_mutex_lock(&lock_info->lock);
1102                 for (i = 0; str && i < lock_info->num_locks; i++) {
1103                         /* Don't show suspended locks */
1104                         if (lock_info->locks[i].suspended) {
1105                                 continue;
1106                         }
1107
1108                         if (!header_printed) {
1109                                 if (lock_info->lwp != -1) {
1110                                         ast_str_append(&str, 0, "=== Thread ID: 0x%lx LWP:%d (%s)\n",
1111                                                 (long unsigned) lock_info->thread_id, lock_info->lwp, lock_info->thread_name);
1112                                 } else {
1113                                         ast_str_append(&str, 0, "=== Thread ID: 0x%lx (%s)\n",
1114                                                 (long unsigned) lock_info->thread_id, lock_info->thread_name);
1115                                 }
1116                                 header_printed = 1;
1117                         }
1118
1119                         append_lock_information(&str, lock_info, i);
1120                 }
1121                 pthread_mutex_unlock(&lock_info->lock);
1122                 if (!str) {
1123                         break;
1124                 }
1125                 if (header_printed) {
1126                         ast_str_append(&str, 0, "=== -------------------------------------------------------------------\n"
1127                                 "===\n");
1128                 }
1129                 if (!str) {
1130                         break;
1131                 }
1132         }
1133         pthread_mutex_unlock(&lock_infos_lock.mutex);
1134
1135         if (!str) {
1136                 return NULL;
1137         }
1138
1139         ast_str_append(&str, 0, "=======================================================================\n"
1140                        "\n");
1141
1142         return str;
1143 }
1144
1145 static char *handle_show_locks(struct ast_cli_entry *e, int cmd, struct ast_cli_args *a)
1146 {
1147         struct ast_str *str;
1148
1149         switch (cmd) {
1150         case CLI_INIT:
1151                 e->command = "core show locks";
1152                 e->usage =
1153                         "Usage: core show locks\n"
1154                         "       This command is for lock debugging.  It prints out which locks\n"
1155                         "are owned by each active thread.\n";
1156                 return NULL;
1157
1158         case CLI_GENERATE:
1159                 return NULL;
1160         }
1161
1162         str = ast_dump_locks();
1163         if (!str) {
1164                 return CLI_FAILURE;
1165         }
1166
1167         ast_cli(a->fd, "%s", ast_str_buffer(str));
1168
1169         ast_free(str);
1170
1171         return CLI_SUCCESS;
1172 }
1173
1174 static struct ast_cli_entry utils_cli[] = {
1175         AST_CLI_DEFINE(handle_show_locks, "Show which locks are held by which thread"),
1176 };
1177
1178 #endif /* DEBUG_THREADS */
1179
1180 /*
1181  * support for 'show threads'. The start routine is wrapped by
1182  * dummy_start(), so that ast_register_thread() and
1183  * ast_unregister_thread() know the thread identifier.
1184  */
1185 struct thr_arg {
1186         void *(*start_routine)(void *);
1187         void *data;
1188         char *name;
1189 };
1190
1191 /*
1192  * on OS/X, pthread_cleanup_push() and pthread_cleanup_pop()
1193  * are odd macros which start and end a block, so they _must_ be
1194  * used in pairs (the latter with a '1' argument to call the
1195  * handler on exit.
1196  * On BSD we don't need this, but we keep it for compatibility.
1197  */
1198 static void *dummy_start(void *data)
1199 {
1200         void *ret;
1201         struct thr_arg a = *((struct thr_arg *) data);  /* make a local copy */
1202 #ifdef DEBUG_THREADS
1203         struct thr_lock_info *lock_info;
1204         pthread_mutexattr_t mutex_attr;
1205
1206         if (!(lock_info = ast_threadstorage_get(&thread_lock_info, sizeof(*lock_info))))
1207                 return NULL;
1208
1209         lock_info->thread_id = pthread_self();
1210         lock_info->lwp = ast_get_tid();
1211         lock_info->thread_name = strdup(a.name);
1212
1213         pthread_mutexattr_init(&mutex_attr);
1214         pthread_mutexattr_settype(&mutex_attr, AST_MUTEX_KIND);
1215         pthread_mutex_init(&lock_info->lock, &mutex_attr);
1216         pthread_mutexattr_destroy(&mutex_attr);
1217
1218         pthread_mutex_lock(&lock_infos_lock.mutex); /* Intentionally not the wrapper */
1219         AST_LIST_INSERT_TAIL(&lock_infos, lock_info, entry);
1220         pthread_mutex_unlock(&lock_infos_lock.mutex); /* Intentionally not the wrapper */
1221 #endif /* DEBUG_THREADS */
1222
1223         /* note that even though data->name is a pointer to allocated memory,
1224            we are not freeing it here because ast_register_thread is going to
1225            keep a copy of the pointer and then ast_unregister_thread will
1226            free the memory
1227         */
1228         ast_free(data);
1229         ast_register_thread(a.name);
1230         pthread_cleanup_push(ast_unregister_thread, (void *) pthread_self());
1231
1232         ret = a.start_routine(a.data);
1233
1234         pthread_cleanup_pop(1);
1235
1236         return ret;
1237 }
1238
1239 #endif /* !LOW_MEMORY */
1240
1241 int ast_pthread_create_stack(pthread_t *thread, pthread_attr_t *attr, void *(*start_routine)(void *),
1242                              void *data, size_t stacksize, const char *file, const char *caller,
1243                              int line, const char *start_fn)
1244 {
1245 #if !defined(LOW_MEMORY)
1246         struct thr_arg *a;
1247 #endif
1248
1249         if (!attr) {
1250                 attr = ast_alloca(sizeof(*attr));
1251                 pthread_attr_init(attr);
1252         }
1253
1254 #if defined(__linux__) || defined(__FreeBSD__)
1255         /* On Linux and FreeBSD , pthread_attr_init() defaults to PTHREAD_EXPLICIT_SCHED,
1256            which is kind of useless. Change this here to
1257            PTHREAD_INHERIT_SCHED; that way the -p option to set realtime
1258            priority will propagate down to new threads by default.
1259            This does mean that callers cannot set a different priority using
1260            PTHREAD_EXPLICIT_SCHED in the attr argument; instead they must set
1261            the priority afterwards with pthread_setschedparam(). */
1262         if ((errno = pthread_attr_setinheritsched(attr, PTHREAD_INHERIT_SCHED)))
1263                 ast_log(LOG_WARNING, "pthread_attr_setinheritsched: %s\n", strerror(errno));
1264 #endif
1265
1266         if (!stacksize)
1267                 stacksize = AST_STACKSIZE;
1268
1269         if ((errno = pthread_attr_setstacksize(attr, stacksize ? stacksize : AST_STACKSIZE)))
1270                 ast_log(LOG_WARNING, "pthread_attr_setstacksize: %s\n", strerror(errno));
1271
1272 #if !defined(LOW_MEMORY)
1273         if ((a = ast_malloc(sizeof(*a)))) {
1274                 a->start_routine = start_routine;
1275                 a->data = data;
1276                 start_routine = dummy_start;
1277                 if (ast_asprintf(&a->name, "%-20s started at [%5d] %s %s()",
1278                              start_fn, line, file, caller) < 0) {
1279                         a->name = NULL;
1280                 }
1281                 data = a;
1282         }
1283 #endif /* !LOW_MEMORY */
1284
1285         return pthread_create(thread, attr, start_routine, data); /* We're in ast_pthread_create, so it's okay */
1286 }
1287
1288
1289 int ast_pthread_create_detached_stack(pthread_t *thread, pthread_attr_t *attr, void *(*start_routine)(void *),
1290                              void *data, size_t stacksize, const char *file, const char *caller,
1291                              int line, const char *start_fn)
1292 {
1293         unsigned char attr_destroy = 0;
1294         int res;
1295
1296         if (!attr) {
1297                 attr = ast_alloca(sizeof(*attr));
1298                 pthread_attr_init(attr);
1299                 attr_destroy = 1;
1300         }
1301
1302         if ((errno = pthread_attr_setdetachstate(attr, PTHREAD_CREATE_DETACHED)))
1303                 ast_log(LOG_WARNING, "pthread_attr_setdetachstate: %s\n", strerror(errno));
1304
1305         res = ast_pthread_create_stack(thread, attr, start_routine, data,
1306                                        stacksize, file, caller, line, start_fn);
1307
1308         if (attr_destroy)
1309                 pthread_attr_destroy(attr);
1310
1311         return res;
1312 }
1313
1314 int ast_wait_for_input(int fd, int ms)
1315 {
1316         struct pollfd pfd[1];
1317
1318         memset(pfd, 0, sizeof(pfd));
1319         pfd[0].fd = fd;
1320         pfd[0].events = POLLIN | POLLPRI;
1321         return ast_poll(pfd, 1, ms);
1322 }
1323
1324 int ast_wait_for_output(int fd, int ms)
1325 {
1326         struct pollfd pfd[1];
1327
1328         memset(pfd, 0, sizeof(pfd));
1329         pfd[0].fd = fd;
1330         pfd[0].events = POLLOUT;
1331         return ast_poll(pfd, 1, ms);
1332 }
1333
1334 static int wait_for_output(int fd, int timeoutms)
1335 {
1336         struct pollfd pfd = {
1337                 .fd = fd,
1338                 .events = POLLOUT,
1339         };
1340         int res;
1341         struct timeval start = ast_tvnow();
1342         int elapsed = 0;
1343
1344         /* poll() until the fd is writable without blocking */
1345         while ((res = ast_poll(&pfd, 1, timeoutms - elapsed)) <= 0) {
1346                 if (res == 0) {
1347                         /* timed out. */
1348 #ifndef STANDALONE
1349                         ast_debug(1, "Timed out trying to write\n");
1350 #endif
1351                         return -1;
1352                 } else if (res == -1) {
1353                         /* poll() returned an error, check to see if it was fatal */
1354
1355                         if (errno == EINTR || errno == EAGAIN) {
1356                                 elapsed = ast_tvdiff_ms(ast_tvnow(), start);
1357                                 if (elapsed >= timeoutms) {
1358                                         return -1;
1359                                 }
1360                                 /* This was an acceptable error, go back into poll() */
1361                                 continue;
1362                         }
1363
1364                         /* Fatal error, bail. */
1365                         ast_log(LOG_ERROR, "poll returned error: %s\n", strerror(errno));
1366
1367                         return -1;
1368                 }
1369                 elapsed = ast_tvdiff_ms(ast_tvnow(), start);
1370                 if (elapsed >= timeoutms) {
1371                         return -1;
1372                 }
1373         }
1374
1375         return 0;
1376 }
1377
1378 /*!
1379  * Try to write string, but wait no more than ms milliseconds before timing out.
1380  *
1381  * \note The code assumes that the file descriptor has NONBLOCK set,
1382  * so there is only one system call made to do a write, unless we actually
1383  * have a need to wait.  This way, we get better performance.
1384  * If the descriptor is blocking, all assumptions on the guaranteed
1385  * detail do not apply anymore.
1386  */
1387 int ast_carefulwrite(int fd, char *s, int len, int timeoutms)
1388 {
1389         struct timeval start = ast_tvnow();
1390         int res = 0;
1391         int elapsed = 0;
1392
1393         while (len) {
1394                 if (wait_for_output(fd, timeoutms - elapsed)) {
1395                         return -1;
1396                 }
1397
1398                 res = write(fd, s, len);
1399
1400                 if (res < 0 && errno != EAGAIN && errno != EINTR) {
1401                         /* fatal error from write() */
1402                         ast_log(LOG_ERROR, "write() returned error: %s\n", strerror(errno));
1403                         return -1;
1404                 }
1405
1406                 if (res < 0) {
1407                         /* It was an acceptable error */
1408                         res = 0;
1409                 }
1410
1411                 /* Update how much data we have left to write */
1412                 len -= res;
1413                 s += res;
1414                 res = 0;
1415
1416                 elapsed = ast_tvdiff_ms(ast_tvnow(), start);
1417                 if (elapsed >= timeoutms) {
1418                         /* We've taken too long to write
1419                          * This is only an error condition if we haven't finished writing. */
1420                         res = len ? -1 : 0;
1421                         break;
1422                 }
1423         }
1424
1425         return res;
1426 }
1427
1428 int ast_careful_fwrite(FILE *f, int fd, const char *src, size_t len, int timeoutms)
1429 {
1430         struct timeval start = ast_tvnow();
1431         int n = 0;
1432         int elapsed = 0;
1433
1434         while (len) {
1435                 if (wait_for_output(fd, timeoutms - elapsed)) {
1436                         /* poll returned a fatal error, so bail out immediately. */
1437                         return -1;
1438                 }
1439
1440                 /* Clear any errors from a previous write */
1441                 clearerr(f);
1442
1443                 n = fwrite(src, 1, len, f);
1444
1445                 if (ferror(f) && errno != EINTR && errno != EAGAIN) {
1446                         /* fatal error from fwrite() */
1447                         if (!feof(f)) {
1448                                 /* Don't spam the logs if it was just that the connection is closed. */
1449                                 ast_log(LOG_ERROR, "fwrite() returned error: %s\n", strerror(errno));
1450                         }
1451                         n = -1;
1452                         break;
1453                 }
1454
1455                 /* Update for data already written to the socket */
1456                 len -= n;
1457                 src += n;
1458
1459                 elapsed = ast_tvdiff_ms(ast_tvnow(), start);
1460                 if (elapsed >= timeoutms) {
1461                         /* We've taken too long to write
1462                          * This is only an error condition if we haven't finished writing. */
1463                         n = len ? -1 : 0;
1464                         break;
1465                 }
1466         }
1467
1468         errno = 0;
1469         while (fflush(f)) {
1470                 if (errno == EAGAIN || errno == EINTR) {
1471                         /* fflush() does not appear to reset errno if it flushes
1472                          * and reaches EOF at the same time. It returns EOF with
1473                          * the last seen value of errno, causing a possible loop.
1474                          * Also usleep() to reduce CPU eating if it does loop */
1475                         errno = 0;
1476                         usleep(1);
1477                         continue;
1478                 }
1479                 if (errno && !feof(f)) {
1480                         /* Don't spam the logs if it was just that the connection is closed. */
1481                         ast_log(LOG_ERROR, "fflush() returned error: %s\n", strerror(errno));
1482                 }
1483                 n = -1;
1484                 break;
1485         }
1486
1487         return n < 0 ? -1 : 0;
1488 }
1489
1490 char *ast_strip_quoted(char *s, const char *beg_quotes, const char *end_quotes)
1491 {
1492         char *e;
1493         char *q;
1494
1495         s = ast_strip(s);
1496         if ((q = strchr(beg_quotes, *s)) && *q != '\0') {
1497                 e = s + strlen(s) - 1;
1498                 if (*e == *(end_quotes + (q - beg_quotes))) {
1499                         s++;
1500                         *e = '\0';
1501                 }
1502         }
1503
1504         return s;
1505 }
1506
1507 char *ast_strsep(char **iss, const char sep, uint32_t flags)
1508 {
1509         char *st = *iss;
1510         char *is;
1511         int inquote = 0;
1512         int found = 0;
1513         char stack[8];
1514
1515         if (iss == NULL || *iss == '\0') {
1516                 return NULL;
1517         }
1518
1519         memset(stack, 0, sizeof(stack));
1520
1521         for(is = st; *is; is++) {
1522                 if (*is == '\\') {
1523                         if (*++is != '\0') {
1524                                 is++;
1525                         } else {
1526                                 break;
1527                         }
1528                 }
1529
1530                 if (*is == '\'' || *is == '"') {
1531                         if (*is == stack[inquote]) {
1532                                 stack[inquote--] = '\0';
1533                         } else {
1534                                 if (++inquote >= sizeof(stack)) {
1535                                         return NULL;
1536                                 }
1537                                 stack[inquote] = *is;
1538                         }
1539                 }
1540
1541                 if (*is == sep && !inquote) {
1542                         *is = '\0';
1543                         found = 1;
1544                         *iss = is + 1;
1545                         break;
1546                 }
1547         }
1548         if (!found) {
1549                 *iss = NULL;
1550         }
1551
1552         if (flags & AST_STRSEP_STRIP) {
1553                 st = ast_strip_quoted(st, "'\"", "'\"");
1554         }
1555
1556         if (flags & AST_STRSEP_TRIM) {
1557                 st = ast_strip(st);
1558         }
1559
1560         if (flags & AST_STRSEP_UNESCAPE) {
1561                 ast_unescape_quoted(st);
1562         }
1563
1564         return st;
1565 }
1566
1567 char *ast_unescape_semicolon(char *s)
1568 {
1569         char *e;
1570         char *work = s;
1571
1572         while ((e = strchr(work, ';'))) {
1573                 if ((e > work) && (*(e-1) == '\\')) {
1574                         memmove(e - 1, e, strlen(e) + 1);
1575                         work = e;
1576                 } else {
1577                         work = e + 1;
1578                 }
1579         }
1580
1581         return s;
1582 }
1583
1584 /* !\brief unescape some C sequences in place, return pointer to the original string.
1585  */
1586 char *ast_unescape_c(char *src)
1587 {
1588         char c, *ret, *dst;
1589
1590         if (src == NULL)
1591                 return NULL;
1592         for (ret = dst = src; (c = *src++); *dst++ = c ) {
1593                 if (c != '\\')
1594                         continue;       /* copy char at the end of the loop */
1595                 switch ((c = *src++)) {
1596                 case '\0':      /* special, trailing '\' */
1597                         c = '\\';
1598                         break;
1599                 case 'b':       /* backspace */
1600                         c = '\b';
1601                         break;
1602                 case 'f':       /* form feed */
1603                         c = '\f';
1604                         break;
1605                 case 'n':
1606                         c = '\n';
1607                         break;
1608                 case 'r':
1609                         c = '\r';
1610                         break;
1611                 case 't':
1612                         c = '\t';
1613                         break;
1614                 }
1615                 /* default, use the char literally */
1616         }
1617         *dst = '\0';
1618         return ret;
1619 }
1620
1621 /*
1622  * Standard escape sequences - Note, '\0' is not included as a valid character
1623  * to escape, but instead is used here as a NULL terminator for the string.
1624  */
1625 char escape_sequences[] = {
1626         '\a', '\b', '\f', '\n', '\r', '\t', '\v', '\\', '\'', '\"', '\?', '\0'
1627 };
1628
1629 /*
1630  * Standard escape sequences output map (has to maintain matching order with
1631  * escape_sequences). '\0' is included here as a NULL terminator for the string.
1632  */
1633 static char escape_sequences_map[] = {
1634         'a', 'b', 'f', 'n', 'r', 't', 'v', '\\', '\'', '"', '?', '\0'
1635 };
1636
1637 char *ast_escape(char *dest, const char *s, size_t size, const char *to_escape)
1638 {
1639         char *p;
1640         char *c;
1641
1642         if (!dest || !size) {
1643                 return dest;
1644         }
1645         if (ast_strlen_zero(s)) {
1646                 *dest = '\0';
1647                 return dest;
1648         }
1649
1650         if (ast_strlen_zero(to_escape)) {
1651                 ast_copy_string(dest, s, size);
1652                 return dest;
1653         }
1654
1655         for (p = dest; *s && --size; ++s, ++p) {
1656                 /* If in the list of characters to escape then escape it */
1657                 if (strchr(to_escape, *s)) {
1658                         if (!--size) {
1659                                 /* Not enough room left for the escape sequence. */
1660                                 break;
1661                         }
1662
1663                         /*
1664                          * See if the character to escape is part of the standard escape
1665                          * sequences. If so we'll have to use its mapped counterpart
1666                          * otherwise just use the current character.
1667                          */
1668                         c = strchr(escape_sequences, *s);
1669                         *p++ = '\\';
1670                         *p = c ? escape_sequences_map[c - escape_sequences] : *s;
1671                 } else {
1672                         *p = *s;
1673                 }
1674         }
1675         *p = '\0';
1676
1677         return dest;
1678 }
1679
1680 char *ast_escape_c(char *dest, const char *s, size_t size)
1681 {
1682         /*
1683          * Note - This is an optimized version of ast_escape. When looking only
1684          * for escape_sequences a couple of checks used in the generic case can
1685          * be left out thus making it slightly more efficient.
1686          */
1687         char *p;
1688         char *c;
1689
1690         if (!dest || !size) {
1691                 return dest;
1692         }
1693         if (ast_strlen_zero(s)) {
1694                 *dest = '\0';
1695                 return dest;
1696         }
1697
1698         for (p = dest; *s && --size; ++s, ++p) {
1699                 /*
1700                  * See if the character to escape is part of the standard escape
1701                  * sequences. If so use its mapped counterpart.
1702                  */
1703                 c = strchr(escape_sequences, *s);
1704                 if (c) {
1705                         if (!--size) {
1706                                 /* Not enough room left for the escape sequence. */
1707                                 break;
1708                         }
1709
1710                         *p++ = '\\';
1711                         *p = escape_sequences_map[c - escape_sequences];
1712                 } else {
1713                         *p = *s;
1714                 }
1715         }
1716         *p = '\0';
1717
1718         return dest;
1719 }
1720
1721 static char *escape_alloc(const char *s, size_t *size)
1722 {
1723         if (!s) {
1724                 return NULL;
1725         }
1726
1727         /*
1728          * The result string needs to be twice the size of the given
1729          * string just in case every character in it needs to be escaped.
1730          */
1731         *size = strlen(s) * 2 + 1;
1732         return ast_malloc(*size);
1733 }
1734
1735 char *ast_escape_alloc(const char *s, const char *to_escape)
1736 {
1737         size_t size = 0;
1738         char *dest = escape_alloc(s, &size);
1739
1740         return ast_escape(dest, s, size, to_escape);
1741 }
1742
1743 char *ast_escape_c_alloc(const char *s)
1744 {
1745         size_t size = 0;
1746         char *dest = escape_alloc(s, &size);
1747
1748         return ast_escape_c(dest, s, size);
1749 }
1750
1751 int ast_build_string_va(char **buffer, size_t *space, const char *fmt, va_list ap)
1752 {
1753         int result;
1754
1755         if (!buffer || !*buffer || !space || !*space)
1756                 return -1;
1757
1758         result = vsnprintf(*buffer, *space, fmt, ap);
1759
1760         if (result < 0)
1761                 return -1;
1762         else if (result > *space)
1763                 result = *space;
1764
1765         *buffer += result;
1766         *space -= result;
1767         return 0;
1768 }
1769
1770 int ast_build_string(char **buffer, size_t *space, const char *fmt, ...)
1771 {
1772         va_list ap;
1773         int result;
1774
1775         va_start(ap, fmt);
1776         result = ast_build_string_va(buffer, space, fmt, ap);
1777         va_end(ap);
1778
1779         return result;
1780 }
1781
1782 int ast_regex_string_to_regex_pattern(const char *regex_string, struct ast_str **regex_pattern)
1783 {
1784         int regex_len = strlen(regex_string);
1785         int ret = 3;
1786
1787         /* Chop off the leading / if there is one */
1788         if ((regex_len >= 1) && (regex_string[0] == '/')) {
1789                 ast_str_set(regex_pattern, 0, "%s", regex_string + 1);
1790                 ret -= 2;
1791         }
1792
1793         /* Chop off the ending / if there is one */
1794         if ((regex_len > 1) && (regex_string[regex_len - 1] == '/')) {
1795                 ast_str_truncate(*regex_pattern, -1);
1796                 ret -= 1;
1797         }
1798
1799         return ret;
1800 }
1801
1802 int ast_true(const char *s)
1803 {
1804         if (ast_strlen_zero(s))
1805                 return 0;
1806
1807         /* Determine if this is a true value */
1808         if (!strcasecmp(s, "yes") ||
1809             !strcasecmp(s, "true") ||
1810             !strcasecmp(s, "y") ||
1811             !strcasecmp(s, "t") ||
1812             !strcasecmp(s, "1") ||
1813             !strcasecmp(s, "on"))
1814                 return -1;
1815
1816         return 0;
1817 }
1818
1819 int ast_false(const char *s)
1820 {
1821         if (ast_strlen_zero(s))
1822                 return 0;
1823
1824         /* Determine if this is a false value */
1825         if (!strcasecmp(s, "no") ||
1826             !strcasecmp(s, "false") ||
1827             !strcasecmp(s, "n") ||
1828             !strcasecmp(s, "f") ||
1829             !strcasecmp(s, "0") ||
1830             !strcasecmp(s, "off"))
1831                 return -1;
1832
1833         return 0;
1834 }
1835
1836 #define ONE_MILLION     1000000
1837 /*
1838  * put timeval in a valid range. usec is 0..999999
1839  * negative values are not allowed and truncated.
1840  */
1841 static struct timeval tvfix(struct timeval a)
1842 {
1843         if (a.tv_usec >= ONE_MILLION) {
1844                 ast_log(LOG_WARNING, "warning too large timestamp %ld.%ld\n",
1845                         (long)a.tv_sec, (long int) a.tv_usec);
1846                 a.tv_sec += a.tv_usec / ONE_MILLION;
1847                 a.tv_usec %= ONE_MILLION;
1848         } else if (a.tv_usec < 0) {
1849                 ast_log(LOG_WARNING, "warning negative timestamp %ld.%ld\n",
1850                         (long)a.tv_sec, (long int) a.tv_usec);
1851                 a.tv_usec = 0;
1852         }
1853         return a;
1854 }
1855
1856 struct timeval ast_tvadd(struct timeval a, struct timeval b)
1857 {
1858         /* consistency checks to guarantee usec in 0..999999 */
1859         a = tvfix(a);
1860         b = tvfix(b);
1861         a.tv_sec += b.tv_sec;
1862         a.tv_usec += b.tv_usec;
1863         if (a.tv_usec >= ONE_MILLION) {
1864                 a.tv_sec++;
1865                 a.tv_usec -= ONE_MILLION;
1866         }
1867         return a;
1868 }
1869
1870 struct timeval ast_tvsub(struct timeval a, struct timeval b)
1871 {
1872         /* consistency checks to guarantee usec in 0..999999 */
1873         a = tvfix(a);
1874         b = tvfix(b);
1875         a.tv_sec -= b.tv_sec;
1876         a.tv_usec -= b.tv_usec;
1877         if (a.tv_usec < 0) {
1878                 a.tv_sec-- ;
1879                 a.tv_usec += ONE_MILLION;
1880         }
1881         return a;
1882 }
1883
1884 int ast_remaining_ms(struct timeval start, int max_ms)
1885 {
1886         int ms;
1887
1888         if (max_ms < 0) {
1889                 ms = max_ms;
1890         } else {
1891                 ms = max_ms - ast_tvdiff_ms(ast_tvnow(), start);
1892                 if (ms < 0) {
1893                         ms = 0;
1894                 }
1895         }
1896
1897         return ms;
1898 }
1899
1900 void ast_format_duration_hh_mm_ss(int duration, char *buf, size_t length)
1901 {
1902         int durh, durm, durs;
1903         durh = duration / 3600;
1904         durm = (duration % 3600) / 60;
1905         durs = duration % 60;
1906         snprintf(buf, length, "%02d:%02d:%02d", durh, durm, durs);
1907 }
1908
1909 #undef ONE_MILLION
1910
1911 #ifndef linux
1912 AST_MUTEX_DEFINE_STATIC(randomlock);
1913 #endif
1914
1915 long int ast_random(void)
1916 {
1917         long int res;
1918
1919         if (dev_urandom_fd >= 0) {
1920                 int read_res = read(dev_urandom_fd, &res, sizeof(res));
1921                 if (read_res > 0) {
1922                         long int rm = RAND_MAX;
1923                         res = res < 0 ? ~res : res;
1924                         rm++;
1925                         return res % rm;
1926                 }
1927         }
1928
1929         /* XXX - Thread safety really depends on the libc, not the OS.
1930          *
1931          * But... popular Linux libc's (uClibc, glibc, eglibc), all have a
1932          * somewhat thread safe random(3) (results are random, but not
1933          * reproducible). The libc's for other systems (BSD, et al.), not so
1934          * much.
1935          */
1936 #ifdef linux
1937         res = random();
1938 #else
1939         ast_mutex_lock(&randomlock);
1940         res = random();
1941         ast_mutex_unlock(&randomlock);
1942 #endif
1943         return res;
1944 }
1945
1946 void ast_replace_subargument_delimiter(char *s)
1947 {
1948         for (; *s; s++) {
1949                 if (*s == '^') {
1950                         *s = ',';
1951                 }
1952         }
1953 }
1954
1955 char *ast_process_quotes_and_slashes(char *start, char find, char replace_with)
1956 {
1957         char *dataPut = start;
1958         int inEscape = 0;
1959         int inQuotes = 0;
1960
1961         for (; *start; start++) {
1962                 if (inEscape) {
1963                         *dataPut++ = *start;       /* Always goes verbatim */
1964                         inEscape = 0;
1965                 } else {
1966                         if (*start == '\\') {
1967                                 inEscape = 1;      /* Do not copy \ into the data */
1968                         } else if (*start == '\'') {
1969                                 inQuotes = 1 - inQuotes;   /* Do not copy ' into the data */
1970                         } else {
1971                                 /* Replace , with |, unless in quotes */
1972                                 *dataPut++ = inQuotes ? *start : ((*start == find) ? replace_with : *start);
1973                         }
1974                 }
1975         }
1976         if (start != dataPut)
1977                 *dataPut = 0;
1978         return dataPut;
1979 }
1980
1981 void ast_join_delim(char *s, size_t len, const char * const w[], unsigned int size, char delim)
1982 {
1983         int x, ofs = 0;
1984         const char *src;
1985
1986         /* Join words into a string */
1987         if (!s)
1988                 return;
1989         for (x = 0; ofs < len && x < size && w[x] ; x++) {
1990                 if (x > 0)
1991                         s[ofs++] = delim;
1992                 for (src = w[x]; *src && ofs < len; src++)
1993                         s[ofs++] = *src;
1994         }
1995         if (ofs == len)
1996                 ofs--;
1997         s[ofs] = '\0';
1998 }
1999
2000 char *ast_to_camel_case_delim(const char *s, const char *delim)
2001 {
2002         char *res = ast_strdup(s);
2003         char *front, *back, *buf = res;
2004         int size;
2005
2006         front = strtok_r(buf, delim, &back);
2007
2008         while (front) {
2009                 size = strlen(front);
2010                 *front = toupper(*front);
2011                 ast_copy_string(buf, front, size + 1);
2012                 buf += size;
2013                 front = strtok_r(NULL, delim, &back);
2014         }
2015
2016         return res;
2017 }
2018
2019 /*
2020  * stringfields support routines.
2021  */
2022
2023 /* this is a little complex... string fields are stored with their
2024    allocated size in the bytes preceding the string; even the
2025    constant 'empty' string has to be this way, so the code that
2026    checks to see if there is enough room for a new string doesn't
2027    have to have any special case checks
2028 */
2029
2030 static const struct {
2031         ast_string_field_allocation allocation;
2032         char string[1];
2033 } __ast_string_field_empty_buffer;
2034
2035 ast_string_field __ast_string_field_empty = __ast_string_field_empty_buffer.string;
2036
2037 #define ALLOCATOR_OVERHEAD 48
2038
2039 static size_t optimal_alloc_size(size_t size)
2040 {
2041         unsigned int count;
2042
2043         size += ALLOCATOR_OVERHEAD;
2044
2045         for (count = 1; size; size >>= 1, count++);
2046
2047         return (1 << count) - ALLOCATOR_OVERHEAD;
2048 }
2049
2050 /*! \brief add a new block to the pool.
2051  * We can only allocate from the topmost pool, so the
2052  * fields in *mgr reflect the size of that only.
2053  */
2054 static int add_string_pool(struct ast_string_field_mgr *mgr, struct ast_string_field_pool **pool_head,
2055                            size_t size, const char *file, int lineno, const char *func)
2056 {
2057         struct ast_string_field_pool *pool;
2058         size_t alloc_size = optimal_alloc_size(sizeof(*pool) + size);
2059
2060 #if defined(__AST_DEBUG_MALLOC)
2061         if (!(pool = __ast_calloc(1, alloc_size, file, lineno, func))) {
2062                 return -1;
2063         }
2064 #else
2065         if (!(pool = ast_calloc(1, alloc_size))) {
2066                 return -1;
2067         }
2068 #endif
2069
2070         pool->prev = *pool_head;
2071         pool->size = alloc_size - sizeof(*pool);
2072         *pool_head = pool;
2073         mgr->last_alloc = NULL;
2074
2075         return 0;
2076 }
2077
2078 /*
2079  * This is an internal API, code should not use it directly.
2080  * It initializes all fields as empty, then uses 'size' for 3 functions:
2081  * size > 0 means initialize the pool list with a pool of given size.
2082  *      This must be called right after allocating the object.
2083  * size = 0 means release all pools except the most recent one.
2084  *      If the first pool was allocated via embedding in another
2085  *      object, that pool will be preserved instead.
2086  *      This is useful to e.g. reset an object to the initial value.
2087  * size < 0 means release all pools.
2088  *      This must be done before destroying the object.
2089  */
2090 int __ast_string_field_init(struct ast_string_field_mgr *mgr, struct ast_string_field_pool **pool_head,
2091                             int needed, const char *file, int lineno, const char *func)
2092 {
2093         const char **p = (const char **) pool_head + 1;
2094         struct ast_string_field_pool *cur = NULL;
2095         struct ast_string_field_pool *preserve = NULL;
2096
2097         /* clear fields - this is always necessary */
2098         while ((struct ast_string_field_mgr *) p != mgr) {
2099                 *p++ = __ast_string_field_empty;
2100         }
2101
2102         mgr->last_alloc = NULL;
2103 #if defined(__AST_DEBUG_MALLOC)
2104         mgr->owner_file = file;
2105         mgr->owner_func = func;
2106         mgr->owner_line = lineno;
2107 #endif
2108         if (needed > 0) {               /* allocate the initial pool */
2109                 *pool_head = NULL;
2110                 mgr->embedded_pool = NULL;
2111                 return add_string_pool(mgr, pool_head, needed, file, lineno, func);
2112         }
2113
2114         /* if there is an embedded pool, we can't actually release *all*
2115          * pools, we must keep the embedded one. if the caller is about
2116          * to free the structure that contains the stringfield manager
2117          * and embedded pool anyway, it will be freed as part of that
2118          * operation.
2119          */
2120         if ((needed < 0) && mgr->embedded_pool) {
2121                 needed = 0;
2122         }
2123
2124         if (needed < 0) {               /* reset all pools */
2125                 cur = *pool_head;
2126         } else if (mgr->embedded_pool) { /* preserve the embedded pool */
2127                 preserve = mgr->embedded_pool;
2128                 cur = *pool_head;
2129         } else {                        /* preserve the last pool */
2130                 if (*pool_head == NULL) {
2131                         ast_log(LOG_WARNING, "trying to reset empty pool\n");
2132                         return -1;
2133                 }
2134                 preserve = *pool_head;
2135                 cur = preserve->prev;
2136         }
2137
2138         if (preserve) {
2139                 preserve->prev = NULL;
2140                 preserve->used = preserve->active = 0;
2141         }
2142
2143         while (cur) {
2144                 struct ast_string_field_pool *prev = cur->prev;
2145
2146                 if (cur != preserve) {
2147                         ast_free(cur);
2148                 }
2149                 cur = prev;
2150         }
2151
2152         *pool_head = preserve;
2153
2154         return 0;
2155 }
2156
2157 ast_string_field __ast_string_field_alloc_space(struct ast_string_field_mgr *mgr,
2158                                                 struct ast_string_field_pool **pool_head, size_t needed)
2159 {
2160         char *result = NULL;
2161         size_t space = (*pool_head)->size - (*pool_head)->used;
2162         size_t to_alloc;
2163
2164         /* Make room for ast_string_field_allocation and make it a multiple of that. */
2165         to_alloc = ast_make_room_for(needed, ast_string_field_allocation);
2166         ast_assert(to_alloc % ast_alignof(ast_string_field_allocation) == 0);
2167
2168         if (__builtin_expect(to_alloc > space, 0)) {
2169                 size_t new_size = (*pool_head)->size;
2170
2171                 while (new_size < to_alloc) {
2172                         new_size *= 2;
2173                 }
2174
2175 #if defined(__AST_DEBUG_MALLOC)
2176                 if (add_string_pool(mgr, pool_head, new_size, mgr->owner_file, mgr->owner_line, mgr->owner_func))
2177                         return NULL;
2178 #else
2179                 if (add_string_pool(mgr, pool_head, new_size, __FILE__, __LINE__, __FUNCTION__))
2180                         return NULL;
2181 #endif
2182         }
2183
2184         /* pool->base is always aligned (gcc aligned attribute). We ensure that
2185          * to_alloc is also a multiple of ast_alignof(ast_string_field_allocation)
2186          * causing result to always be aligned as well; which in turn fixes that
2187          * AST_STRING_FIELD_ALLOCATION(result) is aligned. */
2188         result = (*pool_head)->base + (*pool_head)->used;
2189         (*pool_head)->used += to_alloc;
2190         (*pool_head)->active += needed;
2191         result += ast_alignof(ast_string_field_allocation);
2192         AST_STRING_FIELD_ALLOCATION(result) = needed;
2193         mgr->last_alloc = result;
2194
2195         return result;
2196 }
2197
2198 int __ast_string_field_ptr_grow(struct ast_string_field_mgr *mgr,
2199                                 struct ast_string_field_pool **pool_head, size_t needed,
2200                                 const ast_string_field *ptr)
2201 {
2202         ssize_t grow = needed - AST_STRING_FIELD_ALLOCATION(*ptr);
2203         size_t space = (*pool_head)->size - (*pool_head)->used;
2204
2205         if (*ptr != mgr->last_alloc) {
2206                 return 1;
2207         }
2208
2209         if (space < grow) {
2210                 return 1;
2211         }
2212
2213         (*pool_head)->used += grow;
2214         (*pool_head)->active += grow;
2215         AST_STRING_FIELD_ALLOCATION(*ptr) += grow;
2216
2217         return 0;
2218 }
2219
2220 void __ast_string_field_release_active(struct ast_string_field_pool *pool_head,
2221                                        const ast_string_field ptr)
2222 {
2223         struct ast_string_field_pool *pool, *prev;
2224
2225         if (ptr == __ast_string_field_empty) {
2226                 return;
2227         }
2228
2229         for (pool = pool_head, prev = NULL; pool; prev = pool, pool = pool->prev) {
2230                 if ((ptr >= pool->base) && (ptr <= (pool->base + pool->size))) {
2231                         pool->active -= AST_STRING_FIELD_ALLOCATION(ptr);
2232                         if (pool->active == 0) {
2233                                 if (prev) {
2234                                         prev->prev = pool->prev;
2235                                         ast_free(pool);
2236                                 } else {
2237                                         pool->used = 0;
2238                                 }
2239                         }
2240                         break;
2241                 }
2242         }
2243 }
2244
2245 void __ast_string_field_ptr_build_va(struct ast_string_field_mgr *mgr,
2246                                      struct ast_string_field_pool **pool_head,
2247                                      ast_string_field *ptr, const char *format, va_list ap)
2248 {
2249         size_t needed;
2250         size_t available;
2251         size_t space = (*pool_head)->size - (*pool_head)->used;
2252         int res;
2253         ssize_t grow;
2254         char *target;
2255         va_list ap2;
2256
2257         /* if the field already has space allocated, try to reuse it;
2258            otherwise, try to use the empty space at the end of the current
2259            pool
2260         */
2261         if (*ptr != __ast_string_field_empty) {
2262                 target = (char *) *ptr;
2263                 available = AST_STRING_FIELD_ALLOCATION(*ptr);
2264                 if (*ptr == mgr->last_alloc) {
2265                         available += space;
2266                 }
2267         } else {
2268                 /* pool->used is always a multiple of ast_alignof(ast_string_field_allocation)
2269                  * so we don't need to re-align anything here.
2270                  */
2271                 target = (*pool_head)->base + (*pool_head)->used + ast_alignof(ast_string_field_allocation);
2272                 if (space > ast_alignof(ast_string_field_allocation)) {
2273                         available = space - ast_alignof(ast_string_field_allocation);
2274                 } else {
2275                         available = 0;
2276                 }
2277         }
2278
2279         va_copy(ap2, ap);
2280         res = vsnprintf(target, available, format, ap2);
2281         va_end(ap2);
2282
2283         if (res < 0) {
2284                 /* Are we out of memory? */
2285                 return;
2286         }
2287         if (res == 0) {
2288                 __ast_string_field_release_active(*pool_head, *ptr);
2289                 *ptr = __ast_string_field_empty;
2290                 return;
2291         }
2292         needed = (size_t)res + 1; /* NUL byte */
2293
2294         if (needed > available) {
2295                 /* the allocation could not be satisfied using the field's current allocation
2296                    (if it has one), or the space available in the pool (if it does not). allocate
2297                    space for it, adding a new string pool if necessary.
2298                 */
2299                 if (!(target = (char *) __ast_string_field_alloc_space(mgr, pool_head, needed))) {
2300                         return;
2301                 }
2302                 vsprintf(target, format, ap);
2303                 va_end(ap); /* XXX va_end without va_start? */
2304                 __ast_string_field_release_active(*pool_head, *ptr);
2305                 *ptr = target;
2306         } else if (*ptr != target) {
2307                 /* the allocation was satisfied using available space in the pool, but not
2308                    using the space already allocated to the field
2309                 */
2310                 __ast_string_field_release_active(*pool_head, *ptr);
2311                 mgr->last_alloc = *ptr = target;
2312                 ast_assert(needed < (ast_string_field_allocation)-1);
2313                 AST_STRING_FIELD_ALLOCATION(target) = (ast_string_field_allocation)needed;
2314                 (*pool_head)->used += ast_make_room_for(needed, ast_string_field_allocation);
2315                 (*pool_head)->active += needed;
2316         } else if ((grow = (needed - AST_STRING_FIELD_ALLOCATION(*ptr))) > 0) {
2317                 /* the allocation was satisfied by using available space in the pool *and*
2318                    the field was the last allocated field from the pool, so it grew
2319                 */
2320                 AST_STRING_FIELD_ALLOCATION(*ptr) += grow;
2321                 (*pool_head)->used += ast_align_for(grow, ast_string_field_allocation);
2322                 (*pool_head)->active += grow;
2323         }
2324 }
2325
2326 void __ast_string_field_ptr_build(struct ast_string_field_mgr *mgr,
2327                                   struct ast_string_field_pool **pool_head,
2328                                   ast_string_field *ptr, const char *format, ...)
2329 {
2330         va_list ap;
2331
2332         va_start(ap, format);
2333         __ast_string_field_ptr_build_va(mgr, pool_head, ptr, format, ap);
2334         va_end(ap);
2335 }
2336
2337 void *__ast_calloc_with_stringfields(unsigned int num_structs, size_t struct_size, size_t field_mgr_offset,
2338                                      size_t field_mgr_pool_offset, size_t pool_size, const char *file,
2339                                      int lineno, const char *func)
2340 {
2341         struct ast_string_field_mgr *mgr;
2342         struct ast_string_field_pool *pool;
2343         struct ast_string_field_pool **pool_head;
2344         size_t pool_size_needed = sizeof(*pool) + pool_size;
2345         size_t size_to_alloc = optimal_alloc_size(struct_size + pool_size_needed);
2346         void *allocation;
2347         unsigned int x;
2348
2349 #if defined(__AST_DEBUG_MALLOC)
2350         if (!(allocation = __ast_calloc(num_structs, size_to_alloc, file, lineno, func))) {
2351                 return NULL;
2352         }
2353 #else
2354         if (!(allocation = ast_calloc(num_structs, size_to_alloc))) {
2355                 return NULL;
2356         }
2357 #endif
2358
2359         for (x = 0; x < num_structs; x++) {
2360                 void *base = allocation + (size_to_alloc * x);
2361                 const char **p;
2362
2363                 mgr = base + field_mgr_offset;
2364                 pool_head = base + field_mgr_pool_offset;
2365                 pool = base + struct_size;
2366
2367                 p = (const char **) pool_head + 1;
2368                 while ((struct ast_string_field_mgr *) p != mgr) {
2369                         *p++ = __ast_string_field_empty;
2370                 }
2371
2372                 mgr->embedded_pool = pool;
2373                 *pool_head = pool;
2374                 pool->size = size_to_alloc - struct_size - sizeof(*pool);
2375 #if defined(__AST_DEBUG_MALLOC)
2376                 mgr->owner_file = file;
2377                 mgr->owner_func = func;
2378                 mgr->owner_line = lineno;
2379 #endif
2380         }
2381
2382         return allocation;
2383 }
2384
2385 /* end of stringfields support */
2386
2387 AST_MUTEX_DEFINE_STATIC(fetchadd_m); /* used for all fetc&add ops */
2388
2389 int ast_atomic_fetchadd_int_slow(volatile int *p, int v)
2390 {
2391         int ret;
2392         ast_mutex_lock(&fetchadd_m);
2393         ret = *p;
2394         *p += v;
2395         ast_mutex_unlock(&fetchadd_m);
2396         return ret;
2397 }
2398
2399 /*! \brief
2400  * get values from config variables.
2401  */
2402 int ast_get_timeval(const char *src, struct timeval *dst, struct timeval _default, int *consumed)
2403 {
2404         long double dtv = 0.0;
2405         int scanned;
2406
2407         if (dst == NULL)
2408                 return -1;
2409
2410         *dst = _default;
2411
2412         if (ast_strlen_zero(src))
2413                 return -1;
2414
2415         /* only integer at the moment, but one day we could accept more formats */
2416         if (sscanf(src, "%30Lf%n", &dtv, &scanned) > 0) {
2417                 dst->tv_sec = dtv;
2418                 dst->tv_usec = (dtv - dst->tv_sec) * 1000000.0;
2419                 if (consumed)
2420                         *consumed = scanned;
2421                 return 0;
2422         } else
2423                 return -1;
2424 }
2425
2426 /*! \brief
2427  * get values from config variables.
2428  */
2429 int ast_get_time_t(const char *src, time_t *dst, time_t _default, int *consumed)
2430 {
2431         long t;
2432         int scanned;
2433
2434         if (dst == NULL)
2435                 return -1;
2436
2437         *dst = _default;
2438
2439         if (ast_strlen_zero(src))
2440                 return -1;
2441
2442         /* only integer at the moment, but one day we could accept more formats */
2443         if (sscanf(src, "%30ld%n", &t, &scanned) == 1) {
2444                 *dst = t;
2445                 if (consumed)
2446                         *consumed = scanned;
2447                 return 0;
2448         } else
2449                 return -1;
2450 }
2451
2452 void ast_enable_packet_fragmentation(int sock)
2453 {
2454 #if defined(HAVE_IP_MTU_DISCOVER)
2455         int val = IP_PMTUDISC_DONT;
2456
2457         if (setsockopt(sock, IPPROTO_IP, IP_MTU_DISCOVER, &val, sizeof(val)))
2458                 ast_log(LOG_WARNING, "Unable to disable PMTU discovery. Large UDP packets may fail to be delivered when sent from this socket.\n");
2459 #endif /* HAVE_IP_MTU_DISCOVER */
2460 }
2461
2462 int ast_mkdir(const char *path, int mode)
2463 {
2464         char *ptr;
2465         int len = strlen(path), count = 0, x, piececount = 0;
2466         char *tmp = ast_strdupa(path);
2467         char **pieces;
2468         char *fullpath = ast_alloca(len + 1);
2469         int res = 0;
2470
2471         for (ptr = tmp; *ptr; ptr++) {
2472                 if (*ptr == '/')
2473                         count++;
2474         }
2475
2476         /* Count the components to the directory path */
2477         pieces = ast_alloca(count * sizeof(*pieces));
2478         for (ptr = tmp; *ptr; ptr++) {
2479                 if (*ptr == '/') {
2480                         *ptr = '\0';
2481                         pieces[piececount++] = ptr + 1;
2482                 }
2483         }
2484
2485         *fullpath = '\0';
2486         for (x = 0; x < piececount; x++) {
2487                 /* This looks funky, but the buffer is always ideally-sized, so it's fine. */
2488                 strcat(fullpath, "/");
2489                 strcat(fullpath, pieces[x]);
2490                 res = mkdir(fullpath, mode);
2491                 if (res && errno != EEXIST)
2492                         return errno;
2493         }
2494         return 0;
2495 }
2496
2497 static int safe_mkdir(const char *base_path, char *path, int mode)
2498 {
2499         RAII_VAR(char *, absolute_path, NULL, ast_std_free);
2500
2501         absolute_path = realpath(path, NULL);
2502
2503         if (absolute_path) {
2504                 /* Path exists, but is it in the right place? */
2505                 if (!ast_begins_with(absolute_path, base_path)) {
2506                         return EPERM;
2507                 }
2508
2509                 /* It is in the right place! */
2510                 return 0;
2511         } else {
2512                 /* Path doesn't exist. */
2513
2514                 /* The slash terminating the subpath we're checking */
2515                 char *path_term = strchr(path, '/');
2516                 /* True indicates the parent path is within base_path */
2517                 int parent_is_safe = 0;
2518                 int res;
2519
2520                 while (path_term) {
2521                         RAII_VAR(char *, absolute_subpath, NULL, ast_std_free);
2522
2523                         /* Truncate the path one past the slash */
2524                         char c = *(path_term + 1);
2525                         *(path_term + 1) = '\0';
2526                         absolute_subpath = realpath(path, NULL);
2527
2528                         if (absolute_subpath) {
2529                                 /* Subpath exists, but is it safe? */
2530                                 parent_is_safe = ast_begins_with(
2531                                         absolute_subpath, base_path);
2532                         } else if (parent_is_safe) {
2533                                 /* Subpath does not exist, but parent is safe
2534                                  * Create it */
2535                                 res = mkdir(path, mode);
2536                                 if (res != 0) {
2537                                         ast_assert(errno != EEXIST);
2538                                         return errno;
2539                                 }
2540                         } else {
2541                                 /* Subpath did not exist, parent was not safe
2542                                  * Fail! */
2543                                 errno = EPERM;
2544                                 return errno;
2545                         }
2546                         /* Restore the path */
2547                         *(path_term + 1) = c;
2548                         /* Move on to the next slash */
2549                         path_term = strchr(path_term + 1, '/');
2550                 }
2551
2552                 /* Now to build the final path, but only if it's safe */
2553                 if (!parent_is_safe) {
2554                         errno = EPERM;
2555                         return errno;
2556                 }
2557
2558                 res = mkdir(path, mode);
2559                 if (res != 0 && errno != EEXIST) {
2560                         return errno;
2561                 }
2562
2563                 return 0;
2564         }
2565 }
2566
2567 int ast_safe_mkdir(const char *base_path, const char *path, int mode)
2568 {
2569         RAII_VAR(char *, absolute_base_path, NULL, ast_std_free);
2570         RAII_VAR(char *, p, NULL, ast_free);
2571
2572         if (base_path == NULL || path == NULL) {
2573                 errno = EFAULT;
2574                 return errno;
2575         }
2576
2577         p = ast_strdup(path);
2578         if (p == NULL) {
2579                 errno = ENOMEM;
2580                 return errno;
2581         }
2582
2583         absolute_base_path = realpath(base_path, NULL);
2584         if (absolute_base_path == NULL) {
2585                 return errno;
2586         }
2587
2588         return safe_mkdir(absolute_base_path, p, mode);
2589 }
2590
2591 static void utils_shutdown(void)
2592 {
2593         close(dev_urandom_fd);
2594         dev_urandom_fd = -1;
2595 #if defined(DEBUG_THREADS) && !defined(LOW_MEMORY)
2596         ast_cli_unregister_multiple(utils_cli, ARRAY_LEN(utils_cli));
2597 #endif
2598 }
2599
2600 int ast_utils_init(void)
2601 {
2602         dev_urandom_fd = open("/dev/urandom", O_RDONLY);
2603         base64_init();
2604 #ifdef DEBUG_THREADS
2605 #if !defined(LOW_MEMORY)
2606         ast_cli_register_multiple(utils_cli, ARRAY_LEN(utils_cli));
2607 #endif
2608 #endif
2609         ast_register_cleanup(utils_shutdown);
2610         return 0;
2611 }
2612
2613
2614 /*!
2615  *\brief Parse digest authorization header.
2616  *\return Returns -1 if we have no auth or something wrong with digest.
2617  *\note This function may be used for Digest request and responce header.
2618  * request arg is set to nonzero, if we parse Digest Request.
2619  * pedantic arg can be set to nonzero if we need to do addition Digest check.
2620  */
2621 int ast_parse_digest(const char *digest, struct ast_http_digest *d, int request, int pedantic) {
2622         char *c;
2623         struct ast_str *str = ast_str_create(16);
2624
2625         /* table of recognised keywords, and places where they should be copied */
2626         const struct x {
2627                 const char *key;
2628                 const ast_string_field *field;
2629         } *i, keys[] = {
2630                 { "username=", &d->username },
2631                 { "realm=", &d->realm },
2632                 { "nonce=", &d->nonce },
2633                 { "uri=", &d->uri },
2634                 { "domain=", &d->domain },
2635                 { "response=", &d->response },
2636                 { "cnonce=", &d->cnonce },
2637                 { "opaque=", &d->opaque },
2638                 /* Special cases that cannot be directly copied */
2639                 { "algorithm=", NULL },
2640                 { "qop=", NULL },
2641                 { "nc=", NULL },
2642                 { NULL, 0 },
2643         };
2644
2645         if (ast_strlen_zero(digest) || !d || !str) {
2646                 ast_free(str);
2647                 return -1;
2648         }
2649
2650         ast_str_set(&str, 0, "%s", digest);
2651
2652         c = ast_skip_blanks(ast_str_buffer(str));
2653
2654         if (strncasecmp(c, "Digest ", strlen("Digest "))) {
2655                 ast_log(LOG_WARNING, "Missing Digest.\n");
2656                 ast_free(str);
2657                 return -1;
2658         }
2659         c += strlen("Digest ");
2660
2661         /* lookup for keys/value pair */
2662         while (c && *c && *(c = ast_skip_blanks(c))) {
2663                 /* find key */
2664                 for (i = keys; i->key != NULL; i++) {
2665                         char *src, *separator;
2666                         int unescape = 0;
2667                         if (strncasecmp(c, i->key, strlen(i->key)) != 0) {
2668                                 continue;
2669                         }
2670
2671                         /* Found. Skip keyword, take text in quotes or up to the separator. */
2672                         c += strlen(i->key);
2673                         if (*c == '"') {
2674                                 src = ++c;
2675                                 separator = "\"";
2676                                 unescape = 1;
2677                         } else {
2678                                 src = c;
2679                                 separator = ",";
2680                         }
2681                         strsep(&c, separator); /* clear separator and move ptr */
2682                         if (unescape) {
2683                                 ast_unescape_c(src);
2684                         }
2685                         if (i->field) {
2686                                 ast_string_field_ptr_set(d, i->field, src);
2687                         } else {
2688                                 /* Special cases that require additional procesing */
2689                                 if (!strcasecmp(i->key, "algorithm=")) {
2690                                         if (strcasecmp(src, "MD5")) {
2691                                                 ast_log(LOG_WARNING, "Digest algorithm: \"%s\" not supported.\n", src);
2692                                                 ast_free(str);
2693                                                 return -1;
2694                                         }
2695                                 } else if (!strcasecmp(i->key, "qop=") && !strcasecmp(src, "auth")) {
2696                                         d->qop = 1;
2697                                 } else if (!strcasecmp(i->key, "nc=")) {
2698                                         unsigned long u;
2699                                         if (sscanf(src, "%30lx", &u) != 1) {
2700                                                 ast_log(LOG_WARNING, "Incorrect Digest nc value: \"%s\".\n", src);
2701                                                 ast_free(str);
2702                                                 return -1;
2703                                         }
2704                                         ast_string_field_set(d, nc, src);
2705                                 }
2706                         }
2707                         break;
2708                 }
2709                 if (i->key == NULL) { /* not found, try ',' */
2710                         strsep(&c, ",");
2711                 }
2712         }
2713         ast_free(str);
2714
2715         /* Digest checkout */
2716         if (ast_strlen_zero(d->realm) || ast_strlen_zero(d->nonce)) {
2717                 /* "realm" and "nonce" MUST be always exist */
2718                 return -1;
2719         }
2720
2721         if (!request) {
2722                 /* Additional check for Digest response */
2723                 if (ast_strlen_zero(d->username) || ast_strlen_zero(d->uri) || ast_strlen_zero(d->response)) {
2724                         return -1;
2725                 }
2726
2727                 if (pedantic && d->qop && (ast_strlen_zero(d->cnonce) || ast_strlen_zero(d->nc))) {
2728                         return -1;
2729                 }
2730         }
2731
2732         return 0;
2733 }
2734
2735 #ifndef __AST_DEBUG_MALLOC
2736 int _ast_asprintf(char **ret, const char *file, int lineno, const char *func, const char *fmt, ...)
2737 {
2738         int res;
2739         va_list ap;
2740
2741         va_start(ap, fmt);
2742         if ((res = vasprintf(ret, fmt, ap)) == -1) {
2743                 MALLOC_FAILURE_MSG;
2744         }
2745         va_end(ap);
2746
2747         return res;
2748 }
2749 #endif
2750
2751 int ast_get_tid(void)
2752 {
2753         int ret = -1;
2754 #if defined (__linux) && defined(SYS_gettid)
2755         ret = syscall(SYS_gettid); /* available since Linux 1.4.11 */
2756 #elif defined(__sun)
2757         ret = pthread_self();
2758 #elif defined(__APPLE__)
2759         ret = mach_thread_self();
2760         mach_port_deallocate(mach_task_self(), ret);
2761 #elif defined(__FreeBSD__) && defined(HAVE_SYS_THR_H)
2762         long lwpid;
2763         thr_self(&lwpid); /* available since sys/thr.h creation 2003 */
2764         ret = lwpid;
2765 #endif
2766         return ret;
2767 }
2768
2769 char *ast_utils_which(const char *binary, char *fullpath, size_t fullpath_size)
2770 {
2771         const char *envPATH = getenv("PATH");
2772         char *tpath, *path;
2773         struct stat unused;
2774         if (!envPATH) {
2775                 return NULL;
2776         }
2777         tpath = ast_strdupa(envPATH);
2778         while ((path = strsep(&tpath, ":"))) {
2779                 snprintf(fullpath, fullpath_size, "%s/%s", path, binary);
2780                 if (!stat(fullpath, &unused)) {
2781                         return fullpath;
2782                 }
2783         }
2784         return NULL;
2785 }
2786
2787 void ast_do_crash(void)
2788 {
2789 #if defined(DO_CRASH)
2790         abort();
2791         /*
2792          * Just in case abort() doesn't work or something else super
2793          * silly, and for Qwell's amusement.
2794          */
2795         *((int *) 0) = 0;
2796 #endif  /* defined(DO_CRASH) */
2797 }
2798
2799 #if defined(AST_DEVMODE)
2800 void __ast_assert_failed(int condition, const char *condition_str, const char *file, int line, const char *function)
2801 {
2802         /*
2803          * Attempt to put it into the logger, but hope that at least
2804          * someone saw the message on stderr ...
2805          */
2806         ast_log(__LOG_ERROR, file, line, function, "FRACK!, Failed assertion %s (%d)\n",
2807                 condition_str, condition);
2808         fprintf(stderr, "FRACK!, Failed assertion %s (%d) at line %d in %s of %s\n",
2809                 condition_str, condition, line, function, file);
2810
2811         /* Generate a backtrace for the assert */
2812         ast_log_backtrace();
2813
2814         /*
2815          * Give the logger a chance to get the message out, just in case
2816          * we abort(), or Asterisk crashes due to whatever problem just
2817          * happened after we exit ast_assert().
2818          */
2819         usleep(1);
2820         ast_do_crash();
2821 }
2822 #endif  /* defined(AST_DEVMODE) */
2823
2824 char *ast_eid_to_str(char *s, int maxlen, struct ast_eid *eid)
2825 {
2826         int x;
2827         char *os = s;
2828         if (maxlen < 18) {
2829                 if (s && (maxlen > 0)) {
2830                         *s = '\0';
2831                 }
2832         } else {
2833                 for (x = 0; x < 5; x++) {
2834                         sprintf(s, "%02hhx:", eid->eid[x]);
2835                         s += 3;
2836                 }
2837                 sprintf(s, "%02hhx", eid->eid[5]);
2838         }
2839         return os;
2840 }
2841
2842 void ast_set_default_eid(struct ast_eid *eid)
2843 {
2844 #if defined(SIOCGIFHWADDR) && defined(HAVE_STRUCT_IFREQ_IFR_IFRU_IFRU_HWADDR)
2845         int s, x = 0;
2846         char eid_str[20];
2847         struct ifreq ifr;
2848         static const unsigned int MAXIF = 10;
2849
2850         s = socket(AF_INET, SOCK_STREAM, 0);
2851         if (s < 0) {
2852                 return;
2853         }
2854         for (x = 0; x < MAXIF; x++) {
2855                 static const char *prefixes[] = { "eth", "em" };
2856                 unsigned int i;
2857
2858                 for (i = 0; i < ARRAY_LEN(prefixes); i++) {
2859                         memset(&ifr, 0, sizeof(ifr));
2860                         snprintf(ifr.ifr_name, sizeof(ifr.ifr_name), "%s%d", prefixes[i], x);
2861                         if (!ioctl(s, SIOCGIFHWADDR, &ifr)) {
2862                                 break;
2863                         }
2864                 }
2865
2866                 if (i == ARRAY_LEN(prefixes)) {
2867                         /* Try pciX#[1..N] */
2868                         for (i = 0; i < MAXIF; i++) {
2869                                 memset(&ifr, 0, sizeof(ifr));
2870                                 snprintf(ifr.ifr_name, sizeof(ifr.ifr_name), "pci%d#%u", x, i);
2871                                 if (!ioctl(s, SIOCGIFHWADDR, &ifr)) {
2872                                         break;
2873                                 }
2874                         }
2875                         if (i == MAXIF) {
2876                                 continue;
2877                         }
2878                 }
2879
2880                 memcpy(eid, ((unsigned char *)&ifr.ifr_hwaddr) + 2, sizeof(*eid));
2881                 ast_debug(1, "Seeding global EID '%s' from '%s' using 'siocgifhwaddr'\n", ast_eid_to_str(eid_str, sizeof(eid_str), eid), ifr.ifr_name);
2882                 close(s);
2883                 return;
2884         }
2885         close(s);
2886 #else
2887 #if defined(ifa_broadaddr) && !defined(SOLARIS)
2888         char eid_str[20];
2889         struct ifaddrs *ifap;
2890
2891         if (getifaddrs(&ifap) == 0) {
2892                 struct ifaddrs *p;
2893                 for (p = ifap; p; p = p->ifa_next) {
2894                         if ((p->ifa_addr->sa_family == AF_LINK) && !(p->ifa_flags & IFF_LOOPBACK) && (p->ifa_flags & IFF_RUNNING)) {
2895                                 struct sockaddr_dl* sdp = (struct sockaddr_dl*) p->ifa_addr;
2896                                 memcpy(&(eid->eid), sdp->sdl_data + sdp->sdl_nlen, 6);
2897                                 ast_debug(1, "Seeding global EID '%s' from '%s' using 'getifaddrs'\n", ast_eid_to_str(eid_str, sizeof(eid_str), eid), p->ifa_name);
2898                                 freeifaddrs(ifap);
2899                                 return;
2900                         }
2901                 }
2902                 freeifaddrs(ifap);
2903         }
2904 #endif
2905 #endif
2906         ast_debug(1, "No ethernet interface found for seeding global EID. You will have to set it manually.\n");
2907 }
2908
2909 int ast_str_to_eid(struct ast_eid *eid, const char *s)
2910 {
2911         unsigned int eid_int[6];
2912         int x;
2913
2914         if (sscanf(s, "%2x:%2x:%2x:%2x:%2x:%2x", &eid_int[0], &eid_int[1], &eid_int[2],
2915                  &eid_int[3], &eid_int[4], &eid_int[5]) != 6) {
2916                         return -1;
2917         }
2918
2919         for (x = 0; x < 6; x++) {
2920                 eid->eid[x] = eid_int[x];
2921         }
2922
2923         return 0;
2924 }
2925
2926 int ast_eid_cmp(const struct ast_eid *eid1, const struct ast_eid *eid2)
2927 {
2928         return memcmp(eid1, eid2, sizeof(*eid1));
2929 }