Free session focus dialog
[siplcs.git] / src / uuid.c
blobcf7bb476f02289f5fffa60e139d5981f357132c2
1 /**
2 * @file uuid.c
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; either version 2 of the License, or
7 * (at your option) any later version.
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
14 * You should have received a copy of the GNU General Public License
15 * along with this program; if not, write to the Free Software
16 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
18 #include <stdio.h>
19 #include <stdlib.h>
20 #include <string.h>
22 #include <fcntl.h>
23 #include <unistd.h>
26 #ifndef _WIN32
27 #include <sys/ioctl.h>
28 #include <sys/types.h>
29 #include <sys/socket.h>
30 #include <netinet/in.h>
31 #include <net/if.h>
32 #else
33 #ifdef _DLL
34 #define _WS2TCPIP_H_
35 #define _WINSOCK2API_
36 #define _LIBC_INTERNAL_
37 #endif /* _DLL */
38 #include "internal.h"
39 #include <iphlpapi.h>
40 #endif /* _WIN32 */
42 #include <cipher.h>
43 #include <glib.h>
44 #include <glib/gprintf.h>
45 #include "uuid.h"
47 static const char *epid_ns_uuid = "fcacfb03-8a73-46ef-91b1-e5ebeeaba4fe";
49 #define UUID_OFFSET_TO_LAST_SEGMENT 24
51 void readUUID(const char *string, sipe_uuid_t *uuid)
53 int i;
54 sscanf(string, "%08x-%04hx-%04hx-%02hhx%02hhx-", &uuid->time_low
55 , &uuid->time_mid, &uuid->time_hi_and_version
56 , &uuid->clock_seq_hi_and_reserved
57 , &uuid->clock_seq_low );
59 for(i=0;i<6;i++)
61 sscanf(&string[UUID_OFFSET_TO_LAST_SEGMENT+i*2], "%02hhx", &uuid->node[i]);
65 void printUUID(sipe_uuid_t *uuid, char *string)
67 int i;
68 size_t pos;
69 sprintf(string, "%08x-%04x-%04x-%02x%02x-", uuid->time_low
70 , uuid->time_mid, uuid->time_hi_and_version
71 , uuid->clock_seq_hi_and_reserved
72 , uuid->clock_seq_low
74 pos = strlen(string);
75 for(i=0;i<6;i++)
77 pos += sprintf(&string[pos], "%02x", uuid->node[i]);
81 void createUUIDfromHash(sipe_uuid_t *uuid, const unsigned char *hash)
83 memcpy(uuid, hash, sizeof(sipe_uuid_t));
84 uuid->time_hi_and_version &= 0x0FFF;
85 uuid->time_hi_and_version |= 0x5000;
86 uuid->clock_seq_hi_and_reserved &= 0x3F;
87 uuid->clock_seq_hi_and_reserved |= 0x80;
90 char *generateUUIDfromEPID(const gchar *epid)
92 sipe_uuid_t result;
93 PurpleCipherContext *ctx;
94 unsigned char hash[20];
95 char buf[512];
97 readUUID(epid_ns_uuid, &result);
98 memcpy(buf, &result, sizeof(sipe_uuid_t));
99 strcpy(&buf[sizeof(sipe_uuid_t)], epid);
101 ctx = purple_cipher_context_new_by_name("sha1", NULL);
102 purple_cipher_context_append(ctx, (guchar *) buf, strlen(buf));
103 purple_cipher_context_digest(ctx, sizeof(hash), hash, NULL);
104 purple_cipher_context_destroy(ctx);
106 createUUIDfromHash(&result, hash);
107 printUUID(&result, buf);
108 return g_strdup(buf);
111 #ifndef _WIN32
112 long mac_addr_sys (const unsigned char *addr)
114 /* implementation for Linux */
115 struct ifreq ifr;
116 struct ifreq *IFR;
117 struct ifconf ifc;
118 char buf[1024];
119 int s, i;
120 int ok = 0;
122 s = socket(AF_INET, SOCK_DGRAM, 0);
123 if (s==-1) {
124 return -1;
127 ifc.ifc_len = sizeof(buf);
128 ifc.ifc_buf = buf;
129 ioctl(s, SIOCGIFCONF, &ifc);
131 IFR = ifc.ifc_req;
132 for (i = ifc.ifc_len / sizeof(struct ifreq); --i >= 0; IFR++) {
134 strcpy(ifr.ifr_name, IFR->ifr_name);
135 if (ioctl(s, SIOCGIFFLAGS, &ifr) == 0) {
136 if (! (ifr.ifr_flags & IFF_LOOPBACK)) {
137 #ifdef __FreeBSD__
138 if (ioctl(s, SIOCGIFMAC, &ifr) == 0) {
139 #else
140 if (ioctl(s, SIOCGIFHWADDR, &ifr) == 0) {
141 #endif
142 ok = 1;
143 break;
149 close(s);
150 if (ok) {
151 memmove((void *)addr, ifr.ifr_ifru.ifru_addr.sa_data, 6);
153 else {
154 return -1;
156 return 0;
159 #else
161 static char *get_mac_address_win(const char *ip_address)
163 IP_ADAPTER_INFO AdapterInfo[16]; // for up to 16 NICs
164 DWORD ulOutBufLen = sizeof(AdapterInfo);
165 PIP_ADAPTER_INFO pAdapter_res = NULL;
166 PIP_ADAPTER_INFO pAdapter = NULL;
167 DWORD dwRetVal = 0;
168 UINT i;
169 char *res = NULL;
171 if ((dwRetVal = GetAdaptersInfo(AdapterInfo, &ulOutBufLen)) == NO_ERROR) {
172 pAdapter = AdapterInfo;
173 pAdapter_res = pAdapter;
174 while (pAdapter) {
175 if (!g_ascii_strcasecmp(pAdapter->IpAddressList.IpAddress.String, ip_address)) {
176 pAdapter_res = pAdapter;
177 break;
179 pAdapter = pAdapter->Next;
181 } else {
182 printf("GetAdaptersInfo failed with error: %d\n", dwRetVal);
185 if (pAdapter_res && pAdapter_res->AddressLength) {
186 gchar nmac[13];
187 for (i = 0; i < pAdapter_res->AddressLength; i++) {
188 g_sprintf(&nmac[(i*2)], "%02X", (int)pAdapter_res->Address[i]);
190 res = g_strndup(nmac, pAdapter_res->AddressLength * 2);
191 printf("NIC: %s, IP Address: %s, MAC Address: %s\n", pAdapter_res->Description, pAdapter_res->IpAddressList.IpAddress.String, res);
192 } else {
193 res = g_strdup("01010101");
196 //@TODO free AdapterInfo
197 return res;
199 #endif /* _WIN32 */
201 gchar * sipe_uuid_get_macaddr(const char *ip_address)
203 #ifndef _WIN32
204 guchar addr[6];
205 long mac_add = mac_addr_sys(addr);
206 gchar nmac[13];
208 if (mac_add == 0){
209 int i,j;
210 for (i = 0,j=0; i < 6; i++,j+=2) {
211 g_sprintf(&nmac[j], "%02X", addr[i]);
213 return g_strdup(nmac);
215 return g_strdup("01010101"); //Default
216 #else
217 return get_mac_address_win(ip_address);
218 #endif /* _WIN32 */