1 /*
2 **  OSSP uuid - Universally Unique Identifier
3 **  Copyright (c) 2004-2008 Ralf S. Engelschall <rse@engelschall.com>
4 **  Copyright (c) 2004-2008 The OSSP Project <http://www.ossp.org/>
5 **
6 **  This file is part of OSSP uuid, a library for the generation
7 **  of UUIDs which can found at http://www.ossp.org/pkg/lib/uuid/
8 **
9 **  Permission to use, copy, modify, and distribute this software for
10 **  any purpose with or without fee is hereby granted, provided that
11 **  the above copyright notice and this permission notice appear in all
12 **  copies.
13 **
14 **  THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
15 **  WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
16 **  MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
17 **  IN NO EVENT SHALL THE AUTHORS AND COPYRIGHT HOLDERS AND THEIR
18 **  CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
19 **  SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
20 **  LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
21 **  USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
22 **  ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
23 **  OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
24 **  OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
25 **  SUCH DAMAGE.
26 **
27 **  uuid++.cc: library C++ API implementation
28 */
29 
30 #include <string.h>
31 #include <stdarg.h>
32 
33 #include "uuid++.hh"
34 
35 /*  standard constructor */
uuid()36 uuid::uuid()
37 {
38     uuid_rc_t rc;
39     if ((rc = uuid_create(&ctx)) != UUID_RC_OK)
40         throw uuid_error_t(rc);
41 }
42 
43 /*  copy constructor */
uuid(const uuid & obj)44 uuid::uuid(const uuid &obj)
45 {
46     /* Notice: the copy constructor is the same as the assignment
47        operator (with the object as the argument) below, except that
48        (1) no check for self-assignment is required, (2) no existing
49        internals have to be destroyed and (3) no return value is given back. */
50     uuid_rc_t rc;
51     if ((rc = uuid_clone(obj.ctx, &ctx)) != UUID_RC_OK)
52         throw uuid_error_t(rc);
53     return;
54 }
55 
56 /*  extra constructor via C API object */
uuid(const uuid_t * obj)57 uuid::uuid(const uuid_t *obj)
58 {
59     uuid_rc_t rc;
60     if (obj == NULL)
61         throw uuid_error_t(UUID_RC_ARG);
62     if ((rc = uuid_clone(obj, &ctx)) != UUID_RC_OK)
63         throw uuid_error_t(rc);
64     return;
65 }
66 
67 /*  extra constructor via binary representation */
uuid(const void * bin)68 uuid::uuid(const void *bin)
69 {
70     uuid_rc_t rc;
71     if (bin == NULL)
72         throw uuid_error_t(UUID_RC_ARG);
73     if ((rc = uuid_create(&ctx)) != UUID_RC_OK)
74         throw uuid_error_t(rc);
75     import(bin);
76     return;
77 }
78 
79 /*  extra constructor via string representation */
uuid(const char * str)80 uuid::uuid(const char *str)
81 {
82     uuid_rc_t rc;
83     if (str == NULL)
84         throw uuid_error_t(UUID_RC_ARG);
85     if ((rc = uuid_create(&ctx)) != UUID_RC_OK)
86         throw uuid_error_t(rc);
87     import(str);
88     return;
89 }
90 
91 /*  standard destructor */
~uuid()92 uuid::~uuid()
93 {
94     uuid_destroy(ctx);
95     return;
96 }
97 
98 /*  assignment operator: import of other C++ API object */
operator =(const uuid & obj)99 uuid &uuid::operator=(const uuid &obj)
100 {
101     uuid_rc_t rc;
102     if (this == &obj)
103         return *this;
104     if ((rc = uuid_destroy(ctx)) != UUID_RC_OK)
105         throw uuid_error_t(rc);
106     if ((rc = uuid_clone(obj.ctx, &ctx)) != UUID_RC_OK)
107         throw uuid_error_t(rc);
108     return *this;
109 }
110 
111 /*  assignment operator: import of other C API object */
operator =(const uuid_t * obj)112 uuid &uuid::operator=(const uuid_t *obj)
113 {
114     uuid_rc_t rc;
115     if (obj == NULL)
116         throw uuid_error_t(UUID_RC_ARG);
117     if ((rc = uuid_clone(obj, &ctx)) != UUID_RC_OK)
118         throw uuid_error_t(rc);
119     return *this;
120 }
121 
122 /*  assignment operator: import of binary representation */
operator =(const void * bin)123 uuid &uuid::operator=(const void *bin)
124 {
125     if (bin == NULL)
126         throw uuid_error_t(UUID_RC_ARG);
127     import(bin);
128     return *this;
129 }
130 
131 /*  assignment operator: import of string representation */
operator =(const char * str)132 uuid &uuid::operator=(const char *str)
133 {
134     if (str == NULL)
135         throw uuid_error_t(UUID_RC_ARG);
136     import(str);
137     return *this;
138 }
139 
140 /*  method: clone object */
clone(void)141 uuid uuid::clone(void)
142 {
143     return new uuid(this);
144 }
145 
146 /*  method: loading existing UUID by name */
load(const char * name)147 void uuid::load(const char *name)
148 {
149     uuid_rc_t rc;
150     if (name == NULL)
151         throw uuid_error_t(UUID_RC_ARG);
152     if ((rc = uuid_load(ctx, name)) != UUID_RC_OK)
153         throw uuid_error_t(rc);
154     return;
155 }
156 
157 /*  method: making new UUID one from scratch */
make(unsigned int mode,...)158 void uuid::make(unsigned int mode, ...)
159 {
160     uuid_rc_t rc;
161     va_list ap;
162 
163     va_start(ap, mode);
164     if ((mode & UUID_MAKE_V3) || (mode & UUID_MAKE_V5)) {
165         const uuid *ns = (const uuid *)va_arg(ap, const uuid *);
166         const char *name = (const char *)va_arg(ap, char *);
167         if (ns == NULL || name == NULL)
168             throw uuid_error_t(UUID_RC_ARG);
169         rc = uuid_make(ctx, mode, ns->ctx, name);
170     }
171     else
172         rc = uuid_make(ctx, mode);
173     va_end(ap);
174     if (rc != UUID_RC_OK)
175         throw uuid_error_t(rc);
176     return;
177 }
178 
179 /*  method: comparison for Nil UUID */
isnil(void)180 int uuid::isnil(void)
181 {
182     uuid_rc_t rc;
183     int rv;
184 
185     if ((rc = uuid_isnil(ctx, &rv)) != UUID_RC_OK)
186         throw uuid_error_t(rc);
187     return rv;
188 }
189 
190 /*  method: comparison against other object */
compare(const uuid & obj)191 int uuid::compare(const uuid &obj)
192 {
193     uuid_rc_t rc;
194     int rv;
195 
196     if ((rc = uuid_compare(ctx, obj.ctx, &rv)) != UUID_RC_OK)
197         throw uuid_error_t(rc);
198     return rv;
199 }
200 
201 /*  method: comparison for equality */
operator ==(const uuid & obj)202 int uuid::operator==(const uuid &obj)
203 {
204     return (compare(obj) == 0);
205 }
206 
207 /*  method: comparison for inequality */
operator !=(const uuid & obj)208 int uuid::operator!=(const uuid &obj)
209 {
210     return (compare(obj) != 0);
211 }
212 
213 /*  method: comparison for lower-than */
operator <(const uuid & obj)214 int uuid::operator<(const uuid &obj)
215 {
216     return (compare(obj) < 0);
217 }
218 
219 /*  method: comparison for lower-than-or-equal */
operator <=(const uuid & obj)220 int uuid::operator<=(const uuid &obj)
221 {
222     return (compare(obj) <= 0);
223 }
224 
225 /*  method: comparison for greater-than */
operator >(const uuid & obj)226 int uuid::operator>(const uuid &obj)
227 {
228     return (compare(obj) > 0);
229 }
230 
231 /*  method: comparison for greater-than-or-equal */
operator >=(const uuid & obj)232 int uuid::operator>=(const uuid &obj)
233 {
234     return (compare(obj) >= 0);
235 }
236 
237 /*  method: import binary representation */
import(const void * bin)238 void uuid::import(const void *bin)
239 {
240     uuid_rc_t rc;
241     if ((rc = uuid_import(ctx, UUID_FMT_BIN, bin, UUID_LEN_BIN)) != UUID_RC_OK)
242         throw uuid_error_t(rc);
243     return;
244 }
245 
246 /*  method: import string or single integer value representation */
import(const char * str)247 void uuid::import(const char *str)
248 {
249     uuid_rc_t rc;
250     if ((rc = uuid_import(ctx, UUID_FMT_STR, str, UUID_LEN_STR)) != UUID_RC_OK)
251         if ((rc = uuid_import(ctx, UUID_FMT_SIV, str, UUID_LEN_SIV)) != UUID_RC_OK)
252             throw uuid_error_t(rc);
253     return;
254 }
255 
256 /*  method: export binary representation */
binary(void)257 void *uuid::binary(void)
258 {
259     uuid_rc_t rc;
260     void *bin = NULL;
261     if ((rc = uuid_export(ctx, UUID_FMT_BIN, &bin, NULL)) != UUID_RC_OK)
262         throw uuid_error_t(rc);
263     return bin;
264 }
265 
266 /*  method: export string representation */
string(void)267 char *uuid::string(void)
268 {
269     uuid_rc_t rc;
270     char *str = NULL;
271     if ((rc = uuid_export(ctx, UUID_FMT_STR, (void **)&str, NULL)) != UUID_RC_OK)
272         throw uuid_error_t(rc);
273     return str;
274 }
275 
276 /*  method: export single integer value representation */
integer(void)277 char *uuid::integer(void)
278 {
279     uuid_rc_t rc;
280     char *str = NULL;
281     if ((rc = uuid_export(ctx, UUID_FMT_SIV, (void **)&str, NULL)) != UUID_RC_OK)
282         throw uuid_error_t(rc);
283     return str;
284 }
285 
286 /*  method: export textual summary representation */
summary(void)287 char *uuid::summary(void)
288 {
289     uuid_rc_t rc;
290     char *txt = NULL;
291     if ((rc = uuid_export(ctx, UUID_FMT_TXT, (void **)&txt, NULL)) != UUID_RC_OK)
292         throw uuid_error_t(rc);
293     return txt;
294 }
295 
296 /*  method: return library version */
version(void)297 unsigned long uuid::version(void)
298 {
299     return uuid_version();
300 }
301 
302