/src/pjsip/pjlib/src/pj/guid_simple.c
Line | Count | Source (jump to first uncovered line) |
1 | | /* |
2 | | * Copyright (C) 2008-2011 Teluu Inc. (http://www.teluu.com) |
3 | | * Copyright (C) 2003-2008 Benny Prijono <benny@prijono.org> |
4 | | * |
5 | | * This program is free software; you can redistribute it and/or modify |
6 | | * it under the terms of the GNU General Public License as published by |
7 | | * the Free Software Foundation; either version 2 of the License, or |
8 | | * (at your option) any later version. |
9 | | * |
10 | | * This program is distributed in the hope that it will be useful, |
11 | | * but WITHOUT ANY WARRANTY; without even the implied warranty of |
12 | | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
13 | | * GNU General Public License for more details. |
14 | | * |
15 | | * You should have received a copy of the GNU General Public License |
16 | | * along with this program; if not, write to the Free Software |
17 | | * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
18 | | */ |
19 | | #include <pj/guid.h> |
20 | | #include <pj/assert.h> |
21 | | #include <pj/rand.h> |
22 | | #include <pj/os.h> |
23 | | #include <pj/string.h> |
24 | | |
25 | | PJ_DEF_DATA(const unsigned) PJ_GUID_STRING_LENGTH=32; |
26 | | |
27 | | static char guid_chars[64]; |
28 | | |
29 | | PJ_DEF(unsigned) pj_GUID_STRING_LENGTH() |
30 | 0 | { |
31 | 0 | return PJ_GUID_STRING_LENGTH; |
32 | 0 | } |
33 | | |
34 | | static void init_guid_chars(void) |
35 | 1 | { |
36 | 1 | char *p = guid_chars; |
37 | 1 | unsigned i; |
38 | | |
39 | 11 | for (i=0; i<10; ++i) |
40 | 10 | *p++ = '0'+i; |
41 | | |
42 | 27 | for (i=0; i<26; ++i) { |
43 | 26 | *p++ = 'a'+i; |
44 | 26 | *p++ = 'A'+i; |
45 | 26 | } |
46 | | |
47 | 1 | *p++ = '-'; |
48 | 1 | *p++ = '.'; |
49 | 1 | } |
50 | | |
51 | | PJ_DEF(pj_str_t*) pj_generate_unique_string(pj_str_t *str) |
52 | 1 | { |
53 | 1 | char *p, *end; |
54 | | |
55 | 1 | PJ_CHECK_STACK(); |
56 | | |
57 | 1 | if (guid_chars[0] == '\0') { |
58 | 1 | pj_enter_critical_section(); |
59 | 1 | if (guid_chars[0] == '\0') { |
60 | 1 | init_guid_chars(); |
61 | 1 | } |
62 | 1 | pj_leave_critical_section(); |
63 | 1 | } |
64 | | |
65 | | /* This would only work if PJ_GUID_STRING_LENGTH is multiple of 2 bytes */ |
66 | 1 | pj_assert(PJ_GUID_STRING_LENGTH % 2 == 0); |
67 | | |
68 | 9 | for (p=str->ptr, end=p+PJ_GUID_STRING_LENGTH; p<end; ) { |
69 | 8 | pj_uint32_t rand_val = pj_rand(); |
70 | 8 | pj_uint32_t rand_idx = RAND_MAX; |
71 | | |
72 | 40 | for ( ; rand_idx>0 && p<end; rand_idx>>=8, rand_val>>=8, p++) { |
73 | 32 | *p = guid_chars[(rand_val & 0xFF) & 63]; |
74 | 32 | } |
75 | 8 | } |
76 | | |
77 | 1 | str->slen = PJ_GUID_STRING_LENGTH; |
78 | 1 | return str; |
79 | 1 | } |
80 | | |