1*b1cdbd2cSJim Jagielski /**************************************************************
2*b1cdbd2cSJim Jagielski *
3*b1cdbd2cSJim Jagielski * Licensed to the Apache Software Foundation (ASF) under one
4*b1cdbd2cSJim Jagielski * or more contributor license agreements. See the NOTICE file
5*b1cdbd2cSJim Jagielski * distributed with this work for additional information
6*b1cdbd2cSJim Jagielski * regarding copyright ownership. The ASF licenses this file
7*b1cdbd2cSJim Jagielski * to you under the Apache License, Version 2.0 (the
8*b1cdbd2cSJim Jagielski * "License"); you may not use this file except in compliance
9*b1cdbd2cSJim Jagielski * with the License. You may obtain a copy of the License at
10*b1cdbd2cSJim Jagielski *
11*b1cdbd2cSJim Jagielski * http://www.apache.org/licenses/LICENSE-2.0
12*b1cdbd2cSJim Jagielski *
13*b1cdbd2cSJim Jagielski * Unless required by applicable law or agreed to in writing,
14*b1cdbd2cSJim Jagielski * software distributed under the License is distributed on an
15*b1cdbd2cSJim Jagielski * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16*b1cdbd2cSJim Jagielski * KIND, either express or implied. See the License for the
17*b1cdbd2cSJim Jagielski * specific language governing permissions and limitations
18*b1cdbd2cSJim Jagielski * under the License.
19*b1cdbd2cSJim Jagielski *
20*b1cdbd2cSJim Jagielski *************************************************************/
21*b1cdbd2cSJim Jagielski
22*b1cdbd2cSJim Jagielski
23*b1cdbd2cSJim Jagielski
24*b1cdbd2cSJim Jagielski // MARKER(update_precomp.py): autogen include statement, do not remove
25*b1cdbd2cSJim Jagielski #include "precompiled_sal.hxx"
26*b1cdbd2cSJim Jagielski
27*b1cdbd2cSJim Jagielski #include <string.h>
28*b1cdbd2cSJim Jagielski #include <stdlib.h>
29*b1cdbd2cSJim Jagielski
30*b1cdbd2cSJim Jagielski #include <osl/mutex.hxx>
31*b1cdbd2cSJim Jagielski #include <rtl/random.h>
32*b1cdbd2cSJim Jagielski #include <rtl/uuid.h>
33*b1cdbd2cSJim Jagielski #include <rtl/digest.h>
34*b1cdbd2cSJim Jagielski
35*b1cdbd2cSJim Jagielski #define SWAP_INT32_TO_NETWORK(x)\
36*b1cdbd2cSJim Jagielski { sal_uInt32 y = x;\
37*b1cdbd2cSJim Jagielski sal_uInt8 *p = (sal_uInt8 * )&(x); \
38*b1cdbd2cSJim Jagielski p[0] = (sal_uInt8) ( ( y >> 24 ) & 0xff );\
39*b1cdbd2cSJim Jagielski p[1] = (sal_uInt8) ( ( y >> 16 ) & 0xff );\
40*b1cdbd2cSJim Jagielski p[2] = (sal_uInt8) ( ( y >> 8 ) & 0xff );\
41*b1cdbd2cSJim Jagielski p[3] = (sal_uInt8) ( ( y ) & 0xff);\
42*b1cdbd2cSJim Jagielski }
43*b1cdbd2cSJim Jagielski #define SWAP_INT16_TO_NETWORK(x)\
44*b1cdbd2cSJim Jagielski { sal_uInt16 y = x;\
45*b1cdbd2cSJim Jagielski sal_uInt8 *p = (sal_uInt8 * )&(x); \
46*b1cdbd2cSJim Jagielski p[0] = (sal_uInt8) ( ( y >> 8 ) & 0xff );\
47*b1cdbd2cSJim Jagielski p[1] = (sal_uInt8) ( ( y ) & 0xff);\
48*b1cdbd2cSJim Jagielski }
49*b1cdbd2cSJim Jagielski
50*b1cdbd2cSJim Jagielski #define SWAP_NETWORK_TO_INT16(x)\
51*b1cdbd2cSJim Jagielski { sal_uInt16 y = x;\
52*b1cdbd2cSJim Jagielski sal_uInt8 *p = (sal_uInt8 * )&(y);\
53*b1cdbd2cSJim Jagielski x = ( ( ((sal_uInt16)p[0]) & 0xff) << 8 ) |\
54*b1cdbd2cSJim Jagielski ( ( (sal_uInt16)p[1]) & 0xff);\
55*b1cdbd2cSJim Jagielski }
56*b1cdbd2cSJim Jagielski #define SWAP_NETWORK_TO_INT32(x)\
57*b1cdbd2cSJim Jagielski { sal_uInt32 y = x;\
58*b1cdbd2cSJim Jagielski sal_uInt8 *p = (sal_uInt8 * )&(y); \
59*b1cdbd2cSJim Jagielski x = ( ( ((sal_uInt32)p[0]) & 0xff) << 24 ) |\
60*b1cdbd2cSJim Jagielski ( ( ((sal_uInt32)p[1]) & 0xff) << 16 ) |\
61*b1cdbd2cSJim Jagielski ( ( ((sal_uInt32)p[2]) & 0xff) << 8 ) |\
62*b1cdbd2cSJim Jagielski ( ( (sal_uInt32)p[3]) & 0xff);\
63*b1cdbd2cSJim Jagielski }
64*b1cdbd2cSJim Jagielski
65*b1cdbd2cSJim Jagielski typedef struct _UUID
66*b1cdbd2cSJim Jagielski {
67*b1cdbd2cSJim Jagielski sal_uInt32 time_low;
68*b1cdbd2cSJim Jagielski sal_uInt16 time_mid;
69*b1cdbd2cSJim Jagielski sal_uInt16 time_hi_and_version;
70*b1cdbd2cSJim Jagielski sal_uInt8 clock_seq_hi_and_reserved;
71*b1cdbd2cSJim Jagielski sal_uInt8 clock_seq_low;
72*b1cdbd2cSJim Jagielski sal_uInt8 node[6];
73*b1cdbd2cSJim Jagielski } UUID;
74*b1cdbd2cSJim Jagielski
write_v3(sal_uInt8 * pUuid)75*b1cdbd2cSJim Jagielski static void write_v3( sal_uInt8 *pUuid )
76*b1cdbd2cSJim Jagielski {
77*b1cdbd2cSJim Jagielski UUID uuid;
78*b1cdbd2cSJim Jagielski // copy to avoid alignment problems
79*b1cdbd2cSJim Jagielski memcpy( &uuid , pUuid , 16 );
80*b1cdbd2cSJim Jagielski
81*b1cdbd2cSJim Jagielski SWAP_NETWORK_TO_INT32( uuid.time_low );
82*b1cdbd2cSJim Jagielski SWAP_NETWORK_TO_INT16( uuid.time_mid );
83*b1cdbd2cSJim Jagielski SWAP_NETWORK_TO_INT16( uuid.time_hi_and_version );
84*b1cdbd2cSJim Jagielski
85*b1cdbd2cSJim Jagielski /* put in the variant and version bits */
86*b1cdbd2cSJim Jagielski uuid.time_hi_and_version &= 0x0FFF;
87*b1cdbd2cSJim Jagielski uuid.time_hi_and_version |= (3 << 12);
88*b1cdbd2cSJim Jagielski uuid.clock_seq_hi_and_reserved &= 0x3F;
89*b1cdbd2cSJim Jagielski uuid.clock_seq_hi_and_reserved |= 0x80;
90*b1cdbd2cSJim Jagielski
91*b1cdbd2cSJim Jagielski SWAP_INT32_TO_NETWORK( uuid.time_low );
92*b1cdbd2cSJim Jagielski SWAP_INT16_TO_NETWORK( uuid.time_mid );
93*b1cdbd2cSJim Jagielski SWAP_INT16_TO_NETWORK( uuid.time_hi_and_version );
94*b1cdbd2cSJim Jagielski
95*b1cdbd2cSJim Jagielski memcpy( pUuid , &uuid , 16 );
96*b1cdbd2cSJim Jagielski }
97*b1cdbd2cSJim Jagielski
98*b1cdbd2cSJim Jagielski
rtl_createUuid(sal_uInt8 * pTargetUUID,const sal_uInt8 *,sal_Bool)99*b1cdbd2cSJim Jagielski extern "C" void SAL_CALL rtl_createUuid( sal_uInt8 *pTargetUUID ,
100*b1cdbd2cSJim Jagielski const sal_uInt8 *, sal_Bool )
101*b1cdbd2cSJim Jagielski {
102*b1cdbd2cSJim Jagielski {
103*b1cdbd2cSJim Jagielski osl::MutexGuard g(osl::Mutex::getGlobalMutex());
104*b1cdbd2cSJim Jagielski static rtlRandomPool pool = NULL;
105*b1cdbd2cSJim Jagielski if (pool == NULL) {
106*b1cdbd2cSJim Jagielski pool = rtl_random_createPool();
107*b1cdbd2cSJim Jagielski if (pool == NULL) {
108*b1cdbd2cSJim Jagielski abort();
109*b1cdbd2cSJim Jagielski // only possible way to signal failure here (rtl_createUuid
110*b1cdbd2cSJim Jagielski // being part of a fixed C API)
111*b1cdbd2cSJim Jagielski }
112*b1cdbd2cSJim Jagielski }
113*b1cdbd2cSJim Jagielski if (rtl_random_getBytes(pool, pTargetUUID, 16) != rtl_Random_E_None) {
114*b1cdbd2cSJim Jagielski abort();
115*b1cdbd2cSJim Jagielski // only possible way to signal failure here (rtl_createUuid
116*b1cdbd2cSJim Jagielski // being part of a fixed C API)
117*b1cdbd2cSJim Jagielski }
118*b1cdbd2cSJim Jagielski }
119*b1cdbd2cSJim Jagielski // See ITU-T Recommendation X.667:
120*b1cdbd2cSJim Jagielski pTargetUUID[6] &= 0x0F;
121*b1cdbd2cSJim Jagielski pTargetUUID[6] |= 0x40;
122*b1cdbd2cSJim Jagielski pTargetUUID[8] &= 0x3F;
123*b1cdbd2cSJim Jagielski pTargetUUID[8] |= 0x80;
124*b1cdbd2cSJim Jagielski }
125*b1cdbd2cSJim Jagielski
126*b1cdbd2cSJim Jagielski
rtl_createNamedUuid(sal_uInt8 * pTargetUUID,const sal_uInt8 * pNameSpaceUUID,const rtl_String * pName)127*b1cdbd2cSJim Jagielski extern "C" void SAL_CALL rtl_createNamedUuid( sal_uInt8 *pTargetUUID,
128*b1cdbd2cSJim Jagielski const sal_uInt8 *pNameSpaceUUID,
129*b1cdbd2cSJim Jagielski const rtl_String *pName )
130*b1cdbd2cSJim Jagielski {
131*b1cdbd2cSJim Jagielski rtlDigest digest = rtl_digest_createMD5 ();
132*b1cdbd2cSJim Jagielski
133*b1cdbd2cSJim Jagielski rtl_digest_updateMD5( digest, pNameSpaceUUID , 16 );
134*b1cdbd2cSJim Jagielski rtl_digest_updateMD5( digest, pName->buffer , pName->length );
135*b1cdbd2cSJim Jagielski
136*b1cdbd2cSJim Jagielski rtl_digest_getMD5( digest, pTargetUUID , 16 );
137*b1cdbd2cSJim Jagielski rtl_digest_destroyMD5 (digest);
138*b1cdbd2cSJim Jagielski
139*b1cdbd2cSJim Jagielski write_v3(pTargetUUID);
140*b1cdbd2cSJim Jagielski }
141*b1cdbd2cSJim Jagielski
142*b1cdbd2cSJim Jagielski
143*b1cdbd2cSJim Jagielski
rtl_compareUuid(const sal_uInt8 * pUUID1,const sal_uInt8 * pUUID2)144*b1cdbd2cSJim Jagielski extern "C" sal_Int32 SAL_CALL rtl_compareUuid( const sal_uInt8 *pUUID1 , const sal_uInt8 *pUUID2 )
145*b1cdbd2cSJim Jagielski {
146*b1cdbd2cSJim Jagielski int i;
147*b1cdbd2cSJim Jagielski UUID u1;
148*b1cdbd2cSJim Jagielski UUID u2;
149*b1cdbd2cSJim Jagielski memcpy( &u1 , pUUID1 , 16 );
150*b1cdbd2cSJim Jagielski memcpy( &u2 , pUUID2 , 16 );
151*b1cdbd2cSJim Jagielski
152*b1cdbd2cSJim Jagielski SWAP_NETWORK_TO_INT32( u1.time_low );
153*b1cdbd2cSJim Jagielski SWAP_NETWORK_TO_INT16( u1.time_mid );
154*b1cdbd2cSJim Jagielski SWAP_NETWORK_TO_INT16( u1.time_hi_and_version );
155*b1cdbd2cSJim Jagielski
156*b1cdbd2cSJim Jagielski SWAP_NETWORK_TO_INT32( u2.time_low );
157*b1cdbd2cSJim Jagielski SWAP_NETWORK_TO_INT16( u2.time_mid );
158*b1cdbd2cSJim Jagielski SWAP_NETWORK_TO_INT16( u2.time_hi_and_version );
159*b1cdbd2cSJim Jagielski
160*b1cdbd2cSJim Jagielski #define CHECK(f1, f2) if (f1 != f2) return f1 < f2 ? -1 : 1;
161*b1cdbd2cSJim Jagielski CHECK(u1.time_low, u2.time_low);
162*b1cdbd2cSJim Jagielski CHECK(u1.time_mid, u2.time_mid);
163*b1cdbd2cSJim Jagielski CHECK(u1.time_hi_and_version, u2.time_hi_and_version);
164*b1cdbd2cSJim Jagielski CHECK(u1.clock_seq_hi_and_reserved, u2.clock_seq_hi_and_reserved);
165*b1cdbd2cSJim Jagielski CHECK(u1.clock_seq_low, u2.clock_seq_low);
166*b1cdbd2cSJim Jagielski for (i = 0; i < 6; i++)
167*b1cdbd2cSJim Jagielski {
168*b1cdbd2cSJim Jagielski if (u1.node[i] < u2.node[i])
169*b1cdbd2cSJim Jagielski return -1;
170*b1cdbd2cSJim Jagielski if (u1.node[i] > u2.node[i])
171*b1cdbd2cSJim Jagielski return 1;
172*b1cdbd2cSJim Jagielski }
173*b1cdbd2cSJim Jagielski return 0;
174*b1cdbd2cSJim Jagielski
175*b1cdbd2cSJim Jagielski }
176*b1cdbd2cSJim Jagielski
177