summaryrefslogtreecommitdiffstats
blob: a489add08d616dfed328b413c577fc162888a6c2 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
/*
 * Copyright (c) 2010-2011 Thilo Cestonaro
 * Licensed under the simplified BSD license.
 * See Documentation/Licenses/BSD-simplified.txt for more information.
 */

/*
 * Copyright (c) 2013 Isode Limited.
 * All rights reserved.
 * See the COPYING file for more information.
 */

#include <Swiften/Base/Platform.h>
#include <Swiften/Network/MacOSXProxyProvider.h>

#include <stdio.h>
#include <stdlib.h>
#include <iostream>
#include <boost/numeric/conversion/cast.hpp>
#include <utility>

#ifndef SWIFTEN_PLATFORM_IPHONE
#include <SystemConfiguration/SystemConfiguration.h>
#endif

#pragma clang diagnostic ignored "-Wdisabled-macro-expansion"

using namespace Swift;

#ifndef SWIFTEN_PLATFORM_IPHONE
static HostAddressPort getFromDictionary(CFDictionaryRef dict, CFStringRef enabledKey, CFStringRef hostKey, CFStringRef portKey) {
	CFNumberRef numberValue = NULL;
	HostAddressPort ret = HostAddressPort(HostAddress(), 0);

	if(CFDictionaryGetValueIfPresent(dict, reinterpret_cast<const void*> (enabledKey), reinterpret_cast<const void**> (&numberValue)) == true) {
		const int i = 0;
		CFNumberRef zero = CFNumberCreate(kCFAllocatorDefault, kCFNumberIntType, &i);
		CFComparisonResult result = CFNumberCompare(numberValue, zero, NULL);
		CFRelease(zero);

		if(result != kCFCompareEqualTo) {
			int port = 0;
			std::string host = "";

			try {
				CFNumberRef numberValue = reinterpret_cast<CFNumberRef> (CFDictionaryGetValue(dict, portKey));
				if(numberValue != NULL) {
					CFNumberGetValue(numberValue, kCFNumberIntType, &port);
				}

				CFStringRef stringValue = reinterpret_cast<CFStringRef> (CFDictionaryGetValue(dict, hostKey));
				if(stringValue != NULL) {
					std::vector<char> buffer;
 					// length must be +1 for the ending zero; and the Docu of CFStringGetCString tells it like
					// if the string is toby the length must be at least 5.
					CFIndex length = CFStringGetLength(stringValue) + 1;
					buffer.resize(boost::numeric_cast<size_t>(length));
					if(CFStringGetCString(stringValue, &buffer[0], length, kCFStringEncodingMacRoman)) {
						for(std::vector<char>::iterator iter = buffer.begin(); iter != buffer.end(); ++iter) {
							host += *iter;
						}
					}
				}
			}
			catch(...) {
				std::cerr << "Exception caught ... " << std::endl;
			}
			
			if(host != "" && port != 0) {
				ret = HostAddressPort(HostAddress(host), port);
			}
		}
	}
	return ret;
}
#endif
namespace Swift {

MacOSXProxyProvider::MacOSXProxyProvider() {
}

HostAddressPort MacOSXProxyProvider::getHTTPConnectProxy() const {
	HostAddressPort result;
#ifndef SWIFTEN_PLATFORM_IPHONE
	CFDictionaryRef proxies = SCDynamicStoreCopyProxies(NULL);
	if(proxies != NULL) {
		result = getFromDictionary(proxies, kSCPropNetProxiesHTTPEnable, kSCPropNetProxiesHTTPProxy, kSCPropNetProxiesHTTPPort);
		CFRelease(proxies);
	}
#endif
	return result;
}

HostAddressPort MacOSXProxyProvider::getSOCKS5Proxy() const {
	HostAddressPort result;
#ifndef SWIFTEN_PLATFORM_IPHONE
	CFDictionaryRef proxies = SCDynamicStoreCopyProxies(NULL);
	if(proxies != NULL) {
		result = getFromDictionary(proxies, kSCPropNetProxiesSOCKSEnable, kSCPropNetProxiesSOCKSProxy, kSCPropNetProxiesSOCKSPort);
		CFRelease(proxies);
	}
#endif
	return result;
}

}