summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--build/vc.common/common.props2
-rw-r--r--include/m_netlib.h80
-rw-r--r--plugins/ExternalAPI/m_proxySwitch.h8
-rw-r--r--plugins/ProxySwitch/ProxySwitch.vcxproj31
-rw-r--r--plugins/ProxySwitch/ProxySwitch.vcxproj.filters40
-rw-r--r--plugins/ProxySwitch/docs/proxySwitch.html224
-rw-r--r--plugins/ProxySwitch/docs/proxySwitch_readme.txt106
-rw-r--r--plugins/ProxySwitch/docs/proxySwitch_translation.txt18
-rw-r--r--plugins/ProxySwitch/res/Version.rc55
-rw-r--r--plugins/ProxySwitch/res/logo.icobin0 -> 10134 bytes
-rw-r--r--plugins/ProxySwitch/res/noproxy.ICObin0 -> 318 bytes
-rw-r--r--plugins/ProxySwitch/res/notif-no.ICObin0 -> 894 bytes
-rw-r--r--plugins/ProxySwitch/res/notif-yes.ICObin0 -> 894 bytes
-rw-r--r--plugins/ProxySwitch/res/proxy.ICObin0 -> 318 bytes
-rw-r--r--plugins/ProxySwitch/res/resource.rc162
-rw-r--r--plugins/ProxySwitch/src/ip.cpp728
-rw-r--r--plugins/ProxySwitch/src/main.cpp367
-rw-r--r--plugins/ProxySwitch/src/opt.cpp191
-rw-r--r--plugins/ProxySwitch/src/proxy.cpp304
-rw-r--r--plugins/ProxySwitch/src/resource.h41
-rw-r--r--plugins/ProxySwitch/src/stdafx.cxx18
-rw-r--r--plugins/ProxySwitch/src/stdafx.h212
-rw-r--r--plugins/ProxySwitch/src/version.h13
23 files changed, 2559 insertions, 41 deletions
diff --git a/build/vc.common/common.props b/build/vc.common/common.props
index 6ab75d32b8..52d7943315 100644
--- a/build/vc.common/common.props
+++ b/build/vc.common/common.props
@@ -26,7 +26,7 @@
<AdditionalOptions>/Zc:threadSafeInit- %(AdditionalOptions)</AdditionalOptions>
</ClCompile>
<Link>
- <AdditionalDependencies>winmm.lib;Wtsapi32.lib;netapi32.lib;pdh.lib;shlwapi.lib;Strmiids.lib;gdiplus.lib;dbghelp.lib;Setupapi.lib;msimg32.lib;comctl32.lib;ws2_32.lib;UxTheme.lib;Iphlpapi.lib;%(AdditionalDependencies)</AdditionalDependencies>
+ <AdditionalDependencies>Wininet.lib;winmm.lib;Wtsapi32.lib;netapi32.lib;pdh.lib;shlwapi.lib;Strmiids.lib;gdiplus.lib;dbghelp.lib;Setupapi.lib;msimg32.lib;comctl32.lib;ws2_32.lib;UxTheme.lib;Iphlpapi.lib;%(AdditionalDependencies)</AdditionalDependencies>
<GenerateDebugInformation>true</GenerateDebugInformation>
<GenerateMapFile>false</GenerateMapFile>
<SubSystem>Windows</SubSystem>
diff --git a/include/m_netlib.h b/include/m_netlib.h
index 42b0a4d432..c23d0fddc1 100644
--- a/include/m_netlib.h
+++ b/include/m_netlib.h
@@ -200,16 +200,16 @@ struct NETLIBUSERSETTINGS
EXTERN_C MIR_APP_DLL(int) Netlib_GetUserSettings(HNETLIBUSER nlu, NETLIBUSERSETTINGS *result);
-/////////////////////////////////////////////////////////////////////////////////////////
-//Gets the user-configured settings for a netlib user idetified by name
-//
-//Returns nonzero on success, 0 on failure (!! this is different to most of the rest of Miranda, but consistent with netlib)
-//This function behaves like Netlib_GetUserSettings but the user is identified
-//by the name provided by registration. When the name is not found NETLIBUSERSETTINGS is set to NULL.
-//Errors: ERROR_INVALID_PARAMETER
-
-EXTERN_C MIR_APP_DLL(int) Netlib_GetUserSettingsByName(char * UserSettingsName, NETLIBUSERSETTINGS *result);
-
+/////////////////////////////////////////////////////////////////////////////////////////
+//Gets the user-configured settings for a netlib user idetified by name
+//
+//Returns nonzero on success, 0 on failure (!! this is different to most of the rest of Miranda, but consistent with netlib)
+//This function behaves like Netlib_GetUserSettings but the user is identified
+//by the name provided by registration. When the name is not found NETLIBUSERSETTINGS is set to NULL.
+//Errors: ERROR_INVALID_PARAMETER
+
+EXTERN_C MIR_APP_DLL(int) Netlib_GetUserSettingsByName(char * UserSettingsName, NETLIBUSERSETTINGS *result);
+
/////////////////////////////////////////////////////////////////////////////////////////
// Changes the user-configurable settings for a netlib user
//
@@ -223,15 +223,15 @@ EXTERN_C MIR_APP_DLL(int) Netlib_GetUserSettingsByName(char * UserSettingsName,
EXTERN_C MIR_APP_DLL(int) Netlib_SetUserSettings(HNETLIBUSER nlu, const NETLIBUSERSETTINGS *result);
/////////////////////////////////////////////////////////////////////////////////////////
-//Changes the user-configurable settings for a netlib user idetified by name
-//
-//Returns nonzero on success, 0 on failure (!! this is different to most of the rest of Miranda, but consistent with netlib)
-//This function behaves like Netlib_SetUserSettings but the user is identified
-//by the name provided by registration. Nothing will be changed when the name is not found.
-//Errors: ERROR_INVALID_PARAMETER
-
-EXTERN_C MIR_APP_DLL(int) Netlib_SetUserSettingsByName(char * UserSettingsName, NETLIBUSERSETTINGS *result);
-
+//Changes the user-configurable settings for a netlib user idetified by name
+//
+//Returns nonzero on success, 0 on failure (!! this is different to most of the rest of Miranda, but consistent with netlib)
+//This function behaves like Netlib_SetUserSettings but the user is identified
+//by the name provided by registration. Nothing will be changed when the name is not found.
+//Errors: ERROR_INVALID_PARAMETER
+
+EXTERN_C MIR_APP_DLL(int) Netlib_SetUserSettingsByName(char * UserSettingsName, NETLIBUSERSETTINGS *result);
+
/////////////////////////////////////////////////////////////////////////////////////////
// Closes a netlib handle
//
@@ -782,26 +782,26 @@ struct NETLIBNOTIFY
#define ME_NETLIB_FASTSEND "Netlib/OnSend" // being called on every send
#define ME_NETLIB_FASTDUMP "Netlib/OnDump" // being called on every dump
-struct NETLIBCONNECTIONEVENTINFO
-{
- BOOL connected; // 1-opening socket 0-closing socket
- BOOL listening; // 1-bind 0-connect
- SOCKADDR_IN local; // local IP+port (always used)
- SOCKADDR_IN remote; // remote IP+port (only connect (opening + closing only if no proxy))
- SOCKADDR_IN proxy; // proxy IP+port (only connect when used)
- char *szSettingsModule; // name of the registered Netlib user that requested the action
-};
-
-//This event is sent as a new port is bound or a new connection opened.
-//It is NOT sent for sigle HTTP(S) requests.
-//wParam=(WPARAM)(NETLIBCONNECTIONEVENTINFO*)hInfo
-//lParam=(LPARAM)0 (not used)
-#define ME_NETLIB_EVENT_CONNECTED "Netlib/Event/Connected"
-
-//This event is sent if coneection or listening socket is closed.
-//It is NOT sent for sigle HTTP(S) requests.
-//wParam=(WPARAM)(NETLIBCONNECTIONEVENTINFO*)hInfo
-//lParam=(LPARAM)0 (not used)
-#define ME_NETLIB_EVENT_DISCONNECTED "Netlib/Event/Disconnected"
+struct NETLIBCONNECTIONEVENTINFO
+{
+ BOOL connected; // 1-opening socket 0-closing socket
+ BOOL listening; // 1-bind 0-connect
+ SOCKADDR_IN local; // local IP+port (always used)
+ SOCKADDR_IN remote; // remote IP+port (only connect (opening + closing only if no proxy))
+ SOCKADDR_IN proxy; // proxy IP+port (only connect when used)
+ char *szSettingsModule; // name of the registered Netlib user that requested the action
+};
+
+//This event is sent as a new port is bound or a new connection opened.
+//It is NOT sent for sigle HTTP(S) requests.
+//wParam=(WPARAM)(NETLIBCONNECTIONEVENTINFO*)hInfo
+//lParam=(LPARAM)0 (not used)
+#define ME_NETLIB_EVENT_CONNECTED "Netlib/Event/Connected"
+
+//This event is sent if coneection or listening socket is closed.
+//It is NOT sent for sigle HTTP(S) requests.
+//wParam=(WPARAM)(NETLIBCONNECTIONEVENTINFO*)hInfo
+//lParam=(LPARAM)0 (not used)
+#define ME_NETLIB_EVENT_DISCONNECTED "Netlib/Event/Disconnected"
#endif // M_NETLIB_H__
diff --git a/plugins/ExternalAPI/m_proxySwitch.h b/plugins/ExternalAPI/m_proxySwitch.h
new file mode 100644
index 0000000000..286afcde61
--- /dev/null
+++ b/plugins/ExternalAPI/m_proxySwitch.h
@@ -0,0 +1,8 @@
+#ifndef m_proxySwitch_h
+#define m_proxySwitch_h
+#define MS_PROXYSWITCH_SHOWMYIPADDRS "proxySwitch/ShowMyIPAddrs"
+#define MS_PROXYSWITCH_PROXYENABLE "proxySwitch/ProxyEnable"
+#define MS_PROXYSWITCH_PROXYDISABLE "proxySwitch/ProxyDisable"
+#define MS_PROXYSWITCH_POPUPSWITCH "proxySwitch/PopupSwitch"
+#define MS_PROXYSWITCH_COPYIP2CLIP "proxySwitch/CopyIP2Clipboard"
+#endif
diff --git a/plugins/ProxySwitch/ProxySwitch.vcxproj b/plugins/ProxySwitch/ProxySwitch.vcxproj
new file mode 100644
index 0000000000..c42d09cde0
--- /dev/null
+++ b/plugins/ProxySwitch/ProxySwitch.vcxproj
@@ -0,0 +1,31 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+ <ItemGroup Label="ProjectConfigurations">
+ <ProjectConfiguration Include="Debug|Win32">
+ <Configuration>Debug</Configuration>
+ <Platform>Win32</Platform>
+ </ProjectConfiguration>
+ <ProjectConfiguration Include="Debug|x64">
+ <Configuration>Debug</Configuration>
+ <Platform>x64</Platform>
+ </ProjectConfiguration>
+ <ProjectConfiguration Include="Release|Win32">
+ <Configuration>Release</Configuration>
+ <Platform>Win32</Platform>
+ </ProjectConfiguration>
+ <ProjectConfiguration Include="Release|x64">
+ <Configuration>Release</Configuration>
+ <Platform>x64</Platform>
+ </ProjectConfiguration>
+ </ItemGroup>
+ <PropertyGroup Label="Globals">
+ <ProjectGuid>{7446276D-5845-4258-A245-83D1D4D3CEC3}</ProjectGuid>
+ <ProjectName>ProxySwitch</ProjectName>
+ </PropertyGroup>
+ <ImportGroup Label="PropertySheets">
+ <Import Project="$(ProjectDir)..\..\build\vc.common\plugin.props" />
+ </ImportGroup>
+ <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+ <Link />
+ </ItemDefinitionGroup>
+</Project> \ No newline at end of file
diff --git a/plugins/ProxySwitch/ProxySwitch.vcxproj.filters b/plugins/ProxySwitch/ProxySwitch.vcxproj.filters
new file mode 100644
index 0000000000..fa727737dc
--- /dev/null
+++ b/plugins/ProxySwitch/ProxySwitch.vcxproj.filters
@@ -0,0 +1,40 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+ <Import Project="$(ProjectDir)..\..\build\vc.common\common.filters" />
+ <ItemGroup>
+ <ClCompile Include="src\stdafx.cxx">
+ <Filter>Source Files</Filter>
+ </ClCompile>
+ <ClCompile Include="src\*.cpp">
+ <Filter>Source Files</Filter>
+ </ClCompile>
+ <ClCompile Include="src\*.cpp">
+ <Filter>Source Files</Filter>
+ </ClCompile>
+ <ClCompile Include="src\*.cpp">
+ <Filter>Source Files</Filter>
+ </ClCompile>
+ <ClCompile Include="src\*.cpp">
+ <Filter>Source Files</Filter>
+ </ClCompile>
+ </ItemGroup>
+ <ItemGroup>
+ <ClInclude Include="src\*.h">
+ <Filter>Header Files</Filter>
+ </ClInclude>
+ <ClInclude Include="src\*.h">
+ <Filter>Header Files</Filter>
+ </ClInclude>
+ <ClInclude Include="src\*.h">
+ <Filter>Header Files</Filter>
+ </ClInclude>
+ </ItemGroup>
+ <ItemGroup>
+ <ResourceCompile Include="res\*.rc">
+ <Filter>Resource Files</Filter>
+ </ResourceCompile>
+ <ResourceCompile Include="res\*.rc">
+ <Filter>Resource Files</Filter>
+ </ResourceCompile>
+ </ItemGroup>
+</Project> \ No newline at end of file
diff --git a/plugins/ProxySwitch/docs/proxySwitch.html b/plugins/ProxySwitch/docs/proxySwitch.html
new file mode 100644
index 0000000000..8106e13d1e
--- /dev/null
+++ b/plugins/ProxySwitch/docs/proxySwitch.html
@@ -0,0 +1,224 @@
+<html>
+<head>
+<title>proxySwith - Automatic proxy settings manager</title>
+<link rel="stylesheet" href="proxySwitch.css" type="text/css" />
+<link rev="made" href="mailto:" />
+</head>
+
+<body>
+
+<p><a name="__index__"></a></p>
+<!-- INDEX BEGIN -->
+
+<ul>
+
+ <li><a href="#name">NAME</a></li>
+ <li><a href="#features">FEATURES</a></li>
+ <ul>
+
+ <li><a href="#screenshot">Screenshot</a></li>
+ </ul>
+
+ <li><a href="#requirements">REQUIREMENTS</a></li>
+ <li><a href="#download">DOWNLOAD</a></li>
+ <ul>
+
+ <li><a href="#plugin">Plugin</a></li>
+ <li><a href="#miranda">Miranda</a></li>
+ </ul>
+
+ <li><a href="#change_history">CHANGE HISTORY</a></li>
+ <li><a href="#author">AUTHOR</a></li>
+</ul>
+<!-- INDEX END -->
+
+<hr />
+<p>
+</p>
+<h1><a name="name">NAME</a></h1>
+<p>proxySwith - Automatic proxy settings manager</p>
+<p>
+</p>
+<hr />
+<h1><a name="features">FEATURES</a></h1>
+<p>proxySwitch can enable/disable proxy in Miranda IM, Internet Explorer, and
+Firefox based on the current IP address and defined rules. This plugin
+is useful mainly for laptop/notebook owners.</p>
+<p></p>
+<ul>
+<li><a name="item_enables_2fdisables_proxy_for_all_miranda_im_plugin">enables/disables proxy for all Miranda IM plugins on startup and later on any IP address change</a><br />
+</li>
+<li><a name="item_reconnects_all_miranda_im_protocols_if_necessary">reconnects all Miranda IM protocols if necessary</a><br />
+</li>
+<li><a name="item_notifies_user_on_every_network_interface_ip_addres">notifies user on every network interface IP address change</a><br />
+</li>
+<li><a name="item_recognizes_which_network_interface_is_used_by_mira">recognizes which network interface is used by Miranda IM and reconnects if that interface loses IP address</a><br />
+</li>
+<li><a name="item_addresses">can display current IP addresses (per interface)</a><br />
+</li>
+<li><a name="item_clipboard">can copy current IP address to clipboard (per interface)</a><br />
+</li>
+<li><a name="item_explorer">enables/disables proxy for Internet Explorer (no need to restart IE)</a><br />
+</li>
+<li><a name="item_firefox">enables/disables proxy for Firefox (you must close and rerun Firefox)</a><br />
+</li>
+<p></p></ul>
+<p>Why I wrote this plugin? Because I don't want to do many things manually:</p>
+<p></p>
+<ul>
+<li><a name="item_i_have_to_use_a_proxy_server_at_work_but_i_don_27t">I have to use a proxy server at work but I don't have one at home this plugin will change the settings for me when I change the place</a><br />
+</li>
+<li><a name="item_cable">I'm connected to LAN and Wifi at the same time and when I unplug the ethernet cable (rushing to the meeting) I want Miranda to reconnect using Wifi but only if it was connected via ethernet cable</a><br />
+</li>
+<p></p></ul>
+<p>And what the plugin can't do?</p>
+<p></p>
+<ul>
+<li><a name="item_if_you_need_other_software_27s_proxy_usage_to_be_m">If you need other software's proxy usage to be managed by this plugin feel free to modify the source and build your version of proxySwitch.</a><br />
+</li>
+<li><a name="item_home">It's not intended for changing the proxy setup. If you need proxy_1 at work and proxy_2 at home (or other location) this plugin will be useless for you. Well, this functionality could be added... Any volunteers?</a><br />
+</li>
+<p></p></ul>
+<p>
+</p>
+<h2><a name="screenshot">Screenshot</a></h2>
+<div align=center>
+<img src=screenshot.gif width=500 height=364 border=1 hspace=10>
+</div><p>
+</p>
+<hr />
+<h1><a name="requirements">REQUIREMENTS</a></h1>
+<p>This plugin requires modified Netlib. It is not possible to change the
+proxy settings run-time and it is not possible to determine which network
+interface is used by Miranda IM without this modification. It means that
+you need new modified miranda32.exe!</p>
+<p>If you compile miranda for yourself you can download a patch file otherwise
+pre-compiled binary is ready for you.</p>
+<p>The updated Miranda should have ``(Netlib modf)'' tag on the About dialog.</p>
+<p>I hope my modification will be soon incorporated into Miranda IM v0.4 official source tree.</p>
+<p>
+</p>
+<hr />
+<h1><a name="download">DOWNLOAD</a></h1>
+<p>
+</p>
+<h2><a name="plugin">Plugin</a></h2>
+<p>Download or install the plugin using Miranda Installer. The source
+is available also. Please note the requirements above.</p>
+<table style="border: 2px solid #a82013; font-size: 95%; background-color: #ffffe0;">
+<col style="width: 10em;">
+<col style="width: 5em;">
+<col style="width: 13em;">
+<tr>
+ <td>Plugin binaries</td>
+ <td>v1.0.0.1</td>
+ <td><a href="http://miranda-im.org/download/feed.php?dlfile=1682">proxySwitch.zip</a></td>
+</tr>
+<tr>
+ <td style="border-top: 1px solid #B82619;">Plugin installation</td>
+ <td style="border-top: 1px solid #B82619;">v1.0.0.1</td>
+ <td style="border-top: 1px solid #B82619;"><a href="http://miranda-im.org/download/feed.php?mirinst=1&dlfile=1682">proxySwitch.mir</a></td>
+</tr>
+<tr>
+ <td style="border-top: 1px solid #B82619;">Plugin source</td>
+ <td style="border-top: 1px solid #B82619;">v1.0.0.1</td>
+ <td style="border-top: 1px solid #B82619;"><a href="http://miranda-im.org/download/feed.php?dlsource=1682">proxySwitch_src.zip</a></td>
+</tr>
+</table><p>
+</p>
+<h2><a name="miranda">Miranda</a></h2>
+<p>Replace your miranda32.exe with the respective version downloaded from this
+page. Or you can download a patch file to modify the source and you can
+compile it for yourself.</p>
+<table style="border: 2px solid #a82013; font-size: 95%; background-color: #ffffe0;">
+<col style="width: 14em;">
+<col style="width: 6em;">
+<col style="width: 20em;">
+<tr>
+ <td>Modified miranda32.exe</td>
+ <td>v0.3.3.1</td>
+ <td><a href="http://trooper.tricube.cz/miranda-0.3.3.1.zip">miranda-0.3.3.1.zip</a></td>
+</tr>
+<tr>
+ <td>&nbsp;</td>
+ <td>v0.3.4</td>
+ <td><a href="http://trooper.tricube.cz/miranda-0.3.4.zip">miranda-0.3.4.zip</a></td>
+</tr>
+<tr>
+ <td>&nbsp;</td>
+ <td>v0.4</td>
+ <td><a href="http://trooper.tricube.cz/miranda-0.4.zip">miranda-0.4.zip</a></td>
+</tr>
+<tr>
+ <td style="border-top: 1px solid #B82619;">Miranda source diff</td>
+ <td style="border-top: 1px solid #B82619;">v0.3.3.1</td>
+ <td style="border-top: 1px solid #B82619;"><a href="http://trooper.tricube.cz/miranda_modif_netlib_v0331.diff">miranda_modif_netlib_v0331.diff</a></td>
+</tr>
+<tr>
+ <td>&nbsp;</td>
+ <td>v0.3.4</td>
+ <td><a href="http://trooper.tricube.cz/miranda_modif_netlib_v034x.diff">miranda_modif_netlib_v034x.diff</a></td>
+</tr>
+<tr>
+ <td>&nbsp;</td>
+ <td>v0.4</td>
+ <td><a href="http://trooper.tricube.cz/miranda_modif_netlib_v04xx.diff">miranda_modif_netlib_v04xx.diff</a></td>
+</tr>
+</table><p>Apply the diff to the Miranda source manually or using Cygwin GNU patch program:</p>
+</p><pre>
+patch -l -u -d miranda_src331 -p 1 &lt; miranda_modif_netlib_v03xx.diff
+</pre>
+
+<p>
+</p>
+<hr />
+<h1><a name="change_history">CHANGE HISTORY</a></h1>
+<p></p>
+<dl>
+<dt><strong><a name="item_1">v1.0.0.1 (2005-03-11)</a></strong><br />
+</dt>
+<p></p>
+<ul>
+<li><a name="item_plugin_can_now_handle_firefox_proxy_settings_but_u">Plugin can now handle Firefox proxy settings but unlike IE you have to close and reopen Firefox windows to take the change effect</a><br />
+</li>
+<li><a name="item_reconnects_miranda_on_any_ip_address_change_if_off">Reconnects Miranda on any IP address change if offline and Always Reconnect is selected</a><br />
+</li>
+<li><a name="item_fixed_detection_of_network_interfaces_used_by_mira">Fixed detection of network interfaces used by Miranda IM</a><br />
+</li>
+<li><a name="item_fixed_options_ui_layout">Fixed options UI layout</a><br />
+</li>
+<p></p></ul>
+<p></p></dl>
+<p></p>
+<dl>
+<dt><strong><a name="item_2">v0.0.2 (2005-01-18)</a></strong><br />
+</dt>
+<p></p>
+<ul>
+<li><a name="item_improved_detection_of_network_interface_used_by_mi">Improved detection of network interface used by Miranda IM now does not require Win XP+</a><br />
+</li>
+<li><a name="item_fixed">Fixed (enlarged) UI to enable translation to other languages</a><br />
+</li>
+<li><a name="item_fixed_crash_when_new_network_interface_is_discover">Fixed crash when new network interface is discovered or existing one is disabled</a><br />
+</li>
+<p></p></ul>
+<p></p></dl>
+<p></p>
+<dl>
+<dt><strong>v0.0.1 (2005-01-15)</strong><br />
+</dt>
+<p></p>
+<ul>
+<li><a name="item_first_public_release">First public release</a><br />
+</li>
+<p></p></ul>
+<p></p></dl>
+<p>
+</p>
+<hr />
+<h1><a name="author">AUTHOR</a></h1>
+<p>Petr Smejkal &lt;<em><a href="mailto:petr.smejkal@seznam.cz">petr.smejkal@seznam.cz</a></em>&gt;, 11 March 2005.</p>
+
+</body>
+
+</html>
diff --git a/plugins/ProxySwitch/docs/proxySwitch_readme.txt b/plugins/ProxySwitch/docs/proxySwitch_readme.txt
new file mode 100644
index 0000000000..bb79a0c3c6
--- /dev/null
+++ b/plugins/ProxySwitch/docs/proxySwitch_readme.txt
@@ -0,0 +1,106 @@
+NAME
+ proxySwith - Automatic proxy settings manager
+
+FEATURES
+ proxySwitch can enable/disable proxy in Miranda IM, Internet Explorer,
+ and Firefox based on the current IP address and defined rules. This
+ plugin is useful mainly for laptop/notebook owners.
+
+ * enables/disables proxy for all Miranda IM plugins on startup and later
+ on any IP address change
+ * reconnects all Miranda IM protocols if necessary
+ * notifies user on every network interface IP address change
+ * recognizes which network interface is used by Miranda IM and
+ reconnects if that interface loses IP address
+ * can display current IP addresses (per interface)
+ * can copy current IP address to clipboard (per interface)
+ * enables/disables proxy for Internet Explorer (no need to restart IE)
+ * enables/disables proxy for Firefox (you must close and rerun Firefox)
+
+ Why I wrote this plugin? Because I don't want to do many things
+ manually:
+
+ * I have to use a proxy server at work but I don't have one at home this
+ plugin will change the settings for me when I change the place
+ * I'm connected to LAN and Wifi at the same time and when I unplug the
+ ethernet cable (rushing to the meeting) I want Miranda to reconnect
+ using Wifi but only if it was connected via ethernet cable
+
+ And what the plugin can't do?
+
+ * If you need other software's proxy usage to be managed by this plugin
+ feel free to modify the source and build your version of proxySwitch.
+ * It's not intended for changing the proxy setup. If you need proxy_1 at
+ work and proxy_2 at home (or other location) this plugin will be useless
+ for you. Well, this functionality could be added... Any volunteers?
+
+ Screenshot
+ http://trooper.tricube.cz/screenshot.gif
+
+REQUIREMENTS
+ This plugin requires modified Netlib. It is not possible to change the
+ proxy settings run-time and it is not possible to determine which
+ network interface is used by Miranda IM without this modification. It
+ means that you need new modified miranda32.exe!
+
+ If you compile miranda for yourself you can download a patch file
+ otherwise pre-compiled binary is ready for you.
+
+ The updated Miranda should have "(Netlib modf)" tag on the About dialog.
+
+ I hope my modification will be soon incorporated into Miranda IM v0.4
+ official source tree.
+
+DOWNLOAD
+ Plugin
+ Download or install the plugin using Miranda Installer. The source is
+ available also. Please note the requirements above.
+
+ http://miranda-im.org/download/feed.php?dlfile=1682
+ http://miranda-im.org/download/feed.php?mirinst=1&dlfile=1682
+ http://miranda-im.org/download/feed.php?dlsource=1682
+
+ Miranda
+ Replace your miranda32.exe with the respective version downloaded from
+ this page. Or you can download a patch file to modify the source and you
+ can compile it for yourself.
+
+ http://trooper.tricube.cz/miranda-0.3.3.1.zip
+ http://trooper.tricube.cz/miranda-0.3.4.zip
+ http://trooper.tricube.cz/miranda-0.4.zip
+
+ http://trooper.tricube.cz/miranda_modif_netlib_v0331.diff
+ http://trooper.tricube.cz/miranda_modif_netlib_v034x.diff
+ http://trooper.tricube.cz/miranda_modif_netlib_v04xx.diff
+
+ Apply the diff to the Miranda source manually or using Cygwin GNU patch
+ program:
+
+ patch -l -u -d miranda_src331 -p 1 < miranda_modif_netlib_v03xx.diff
+
+CHANGE HISTORY
+ v1.0.0.1 (2005-03-11)
+
+ * Plugin can now handle Firefox proxy settings but unlike IE you
+ have to close and reopen Firefox windows to take the change
+ effect
+ * Reconnects Miranda on any IP address change if offline and
+ Always Reconnect is selected
+ * Fixed detection of network interfaces used by Miranda IM
+ * Fixed options UI layout
+
+ v0.0.2 (2005-01-18)
+
+ * Improved detection of network interface used by Miranda IM now
+ does not require Win XP+
+ * Fixed (enlarged) UI to enable translation to other languages
+ * Fixed crash when new network interface is discovered or
+ existing one is disabled
+
+ v0.0.1 (2005-01-15)
+
+ * First public release
+
+AUTHOR
+ Petr Smejkal <petr.smejkal@seznam.cz>, 11 March 2005.
+
diff --git a/plugins/ProxySwitch/docs/proxySwitch_translation.txt b/plugins/ProxySwitch/docs/proxySwitch_translation.txt
new file mode 100644
index 0000000000..8f92382500
--- /dev/null
+++ b/plugins/ProxySwitch/docs/proxySwitch_translation.txt
@@ -0,0 +1,18 @@
+[Current IP address]
+[Direct]
+[Disable &IP change notification]
+[Disable Proxy]
+[Enable &IP change notification]
+[Enable Proxy]
+[IP Change Notification]
+[Network]
+[PopUps]
+[Proxy Settings && Interfaces]
+[Proxy]
+[Show my &IP Addresses]
+[This plugin requires modified version of Miranda IM.\nIt is not able to change proxy settings now!\nRead proxySwitch_readme.txt for more information.]
+[\nExplorer ]
+[\nFirefox ]
+[\nMiranda ]
+[disconnected]
+[proxySwitch]
diff --git a/plugins/ProxySwitch/res/Version.rc b/plugins/ProxySwitch/res/Version.rc
new file mode 100644
index 0000000000..37934706a0
--- /dev/null
+++ b/plugins/ProxySwitch/res/Version.rc
@@ -0,0 +1,55 @@
+// Microsoft Visual C++ generated resource script.
+//
+#ifdef APSTUDIO_INVOKED
+#error this file is not editable by Microsoft Visual C++
+#endif //APSTUDIO_INVOKED
+
+#include "..\src\version.h"
+
+#define APSTUDIO_READONLY_SYMBOLS
+#include "afxres.h"
+#undef APSTUDIO_READONLY_SYMBOLS
+
+/////////////////////////////////////////////////////////////////////////////
+// English (U.S.) resources
+
+#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU)
+#ifdef _WIN32
+LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US
+#pragma code_page(1252)
+#endif //_WIN32
+
+VS_VERSION_INFO VERSIONINFO
+ FILEVERSION __FILEVERSION_STRING
+ PRODUCTVERSION __FILEVERSION_STRING
+ FILEFLAGSMASK 0x17L
+#ifdef _DEBUG
+ FILEFLAGS 0x1L
+#else
+ FILEFLAGS 0x0L
+#endif
+ FILEOS 0x4L
+ FILETYPE 0x2L
+ FILESUBTYPE 0x0L
+BEGIN
+ BLOCK "StringFileInfo"
+ BEGIN
+ BLOCK "000004b0"
+ BEGIN
+ VALUE "Author", __AUTHOR
+ VALUE "FileDescription", __DESCRIPTION
+ VALUE "FileVersion", __VERSION_STRING
+ VALUE "InternalName", __PLUGIN_NAME
+ VALUE "LegalCopyright", __COPYRIGHT
+ VALUE "OriginalFilename", __FILENAME
+ VALUE "ProductName", __PLUGIN_NAME
+ END
+ END
+ BLOCK "VarFileInfo"
+ BEGIN
+ VALUE "Translation", 0x0, 1200
+ END
+END
+
+#endif // English (U.S.) resources
+/////////////////////////////////////////////////////////////////////////////
diff --git a/plugins/ProxySwitch/res/logo.ico b/plugins/ProxySwitch/res/logo.ico
new file mode 100644
index 0000000000..e18fe3620b
--- /dev/null
+++ b/plugins/ProxySwitch/res/logo.ico
Binary files differ
diff --git a/plugins/ProxySwitch/res/noproxy.ICO b/plugins/ProxySwitch/res/noproxy.ICO
new file mode 100644
index 0000000000..323fc8c466
--- /dev/null
+++ b/plugins/ProxySwitch/res/noproxy.ICO
Binary files differ
diff --git a/plugins/ProxySwitch/res/notif-no.ICO b/plugins/ProxySwitch/res/notif-no.ICO
new file mode 100644
index 0000000000..cf49d99e5e
--- /dev/null
+++ b/plugins/ProxySwitch/res/notif-no.ICO
Binary files differ
diff --git a/plugins/ProxySwitch/res/notif-yes.ICO b/plugins/ProxySwitch/res/notif-yes.ICO
new file mode 100644
index 0000000000..7d7af2e746
--- /dev/null
+++ b/plugins/ProxySwitch/res/notif-yes.ICO
Binary files differ
diff --git a/plugins/ProxySwitch/res/proxy.ICO b/plugins/ProxySwitch/res/proxy.ICO
new file mode 100644
index 0000000000..f0ecb38912
--- /dev/null
+++ b/plugins/ProxySwitch/res/proxy.ICO
Binary files differ
diff --git a/plugins/ProxySwitch/res/resource.rc b/plugins/ProxySwitch/res/resource.rc
new file mode 100644
index 0000000000..c7e299dc1e
--- /dev/null
+++ b/plugins/ProxySwitch/res/resource.rc
@@ -0,0 +1,162 @@
+//Microsoft Developer Studio generated resource script.
+//
+#include "..\src\resource.h"
+
+#define APSTUDIO_READONLY_SYMBOLS
+/////////////////////////////////////////////////////////////////////////////
+//
+// Generated from the TEXTINCLUDE 2 resource.
+//
+#include "afxres.h"
+
+/////////////////////////////////////////////////////////////////////////////
+#undef APSTUDIO_READONLY_SYMBOLS
+
+/////////////////////////////////////////////////////////////////////////////
+// Neutral resources
+
+#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_NEU)
+#ifdef _WIN32
+LANGUAGE LANG_NEUTRAL, SUBLANG_NEUTRAL
+#pragma code_page(1250)
+#endif //_WIN32
+
+/////////////////////////////////////////////////////////////////////////////
+//
+// Icon
+//
+
+// Icon with lowest ID value placed first to ensure application icon
+// remains consistent on all systems.
+IDI_LOGO ICON "logo.ico"
+IDI_PROXY ICON "proxy.ico"
+IDI_NOTIF_1 ICON "notif-yes.ico"
+IDI_NOTIF_0 ICON "notif-no.ico"
+
+
+/////////////////////////////////////////////////////////////////////////////
+//
+// DESIGNINFO
+//
+
+#ifdef APSTUDIO_INVOKED
+GUIDELINES DESIGNINFO DISCARDABLE
+BEGIN
+ IDD_OPTIONS, DIALOG
+ BEGIN
+ LEFTMARGIN, 7
+ RIGHTMARGIN, 295
+ TOPMARGIN, 7
+ BOTTOMMARGIN, 184
+ END
+END
+#endif // APSTUDIO_INVOKED
+
+
+/////////////////////////////////////////////////////////////////////////////
+//
+// Dialog
+//
+
+IDD_OPTIONS DIALOGEX 0, 0, 302, 191
+STYLE DS_MODALFRAME | WS_CHILD
+EXSTYLE WS_EX_CONTROLPARENT
+FONT 8, "MS Shell Dlg"
+BEGIN
+ GROUPBOX "Network Addresses",IDC_STATIC,7,5,287,56,WS_GROUP
+ CONTROL "Direct connection",IDC_STATIC,"Static",SS_SIMPLE,15,20,
+ 84,8
+ EDITTEXT IDC_EDIT_NOPROXY,101,17,183,14,ES_AUTOHSCROLL
+ CONTROL "Use proxy",IDC_STATIC,"Static",SS_SIMPLE,40,40,61,8
+ EDITTEXT IDC_EDIT_USEPROXY,101,37,183,14,ES_AUTOHSCROLL
+ PUSHBUTTON "?",IDC_BTN_HELP,15,39,14,12,BS_FLAT | NOT WS_TABSTOP
+ GROUPBOX "General",IDC_STATIC,7,65,144,118,WS_GROUP
+ CONTROL "Manage Miranda IM proxy",IDC_CHECK_MIRANDA,"Button",
+ BS_AUTOCHECKBOX | WS_TABSTOP,15,78,131,10
+ CONTROL "Manage Internet Explorer proxy",IDC_CHECK_IE,"Button",
+ BS_AUTOCHECKBOX | WS_TABSTOP,15,92,132,10
+ CONTROL "Manage Firefox proxy",IDC_CHECK_FIREFOX,"Button",
+ BS_AUTOCHECKBOX | WS_TABSTOP,15,106,132,10
+ CONTROL "Reconnect if IP address changes",
+ IDC_CHECK_ALWAY_RECONNECT,"Button",BS_AUTOCHECKBOX |
+ WS_TABSTOP,15,120,132,10
+ CONTROL "Display 'Show my IP' in menu",IDC_CHECK_SHOWMYIPMENU,
+ "Button",BS_AUTOCHECKBOX | WS_TABSTOP,15,134,130,10
+ CONTROL "Display 'Proxy && IP' submenu",IDC_CHECK_PROXYIPMENU,
+ "Button",BS_AUTOCHECKBOX | WS_TABSTOP,15,148,131,10
+ LTEXT "Hide interfaces",IDC_STATIC,15,165,62,8
+ EDITTEXT IDC_EDIT_HIDEINTF,80,161,62,14,ES_AUTOHSCROLL
+ GROUPBOX "PopUp Options",IDC_STATIC,160,65,134,118,WS_GROUP
+ CONTROL "Enable popups",IDC_CHECK_POPUPS,"Button",
+ BS_AUTOCHECKBOX | WS_TABSTOP,168,78,122,10
+ CONTROL "",IDC_TEXTCOLOR,"ColourPicker",WS_TABSTOP,168,94,39,11
+ CONTROL "Text color",IDC_STATIC,"Static",SS_SIMPLE,215,94,75,8
+ CONTROL "",IDC_BGCOLOR,"ColourPicker",WS_TABSTOP,168,111,39,11
+ CONTROL "Background color",IDC_STATIC,"Static",SS_SIMPLE,215,111,
+ 75,8
+ CONTROL "Use default popup colors",IDC_CHECK_DEFAULTCOLORS,
+ "Button",BS_AUTOCHECKBOX | WS_TABSTOP,168,129,122,10
+ CONTROL "Show proxy status on change",IDC_CHECK_SHOWPROXYSTATUS,
+ "Button",BS_AUTOCHECKBOX | WS_TABSTOP,168,143,123,10
+ CTEXT "Restart of IM Miranda is required.",IDC_RESTARTREQUIRED,
+ 164,164,127,8,NOT WS_VISIBLE
+ LTEXT "Enter semicolon (;) separated list of IP network addresses in any of the formats below:\n\tip/bits\t(10.0.0.1/24)\t\tip/mask\t(10.0.0.1/255.255.255.0)\n\tip1-2\t(10.0.0.1-50)\t\tip1-ip2\t(10.0.0.1-10.0.2.255)",
+ IDC_HELP_1,7,66,287,32,NOT WS_VISIBLE | NOT WS_GROUP
+ LTEXT "Any entry in the 'Use proxy' list can be prefixed by an exclamation mark (!) to increase its priority. Entries with wrong syntax will be ignored. The program checks the IP addresses in the following way:",
+ IDC_HELP_2,7,98,287,27,NOT WS_VISIBLE | NOT WS_GROUP
+ LTEXT "\t1) Use proxy if any interface has prioritized 'Use proxy' address\n\t2) Don't use proxy if any interface has 'Direct connection' address\n\t3) Use proxy if any interface has 'Use proxy' address\n\t4) Do nothing if unknown or any at all addresses found",
+ IDC_HELP_3,7,125,287,59,NOT WS_VISIBLE | NOT WS_GROUP
+END
+
+#endif // Neutral resources
+/////////////////////////////////////////////////////////////////////////////
+
+
+/////////////////////////////////////////////////////////////////////////////
+// Czech resources
+
+#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_CSY)
+#ifdef _WIN32
+LANGUAGE LANG_CZECH, SUBLANG_DEFAULT
+#pragma code_page(1250)
+#endif //_WIN32
+
+#ifdef APSTUDIO_INVOKED
+/////////////////////////////////////////////////////////////////////////////
+//
+// TEXTINCLUDE
+//
+
+1 TEXTINCLUDE DISCARDABLE
+BEGIN
+ "resource.h\0"
+END
+
+2 TEXTINCLUDE DISCARDABLE
+BEGIN
+ "#include ""afxres.h""\r\n"
+ "\0"
+END
+
+3 TEXTINCLUDE DISCARDABLE
+BEGIN
+ "\r\n"
+ "\0"
+END
+
+#endif // APSTUDIO_INVOKED
+
+#endif // Czech resources
+/////////////////////////////////////////////////////////////////////////////
+
+
+
+#ifndef APSTUDIO_INVOKED
+/////////////////////////////////////////////////////////////////////////////
+//
+// Generated from the TEXTINCLUDE 3 resource.
+//
+
+
+/////////////////////////////////////////////////////////////////////////////
+#endif // not APSTUDIO_INVOKED
diff --git a/plugins/ProxySwitch/src/ip.cpp b/plugins/ProxySwitch/src/ip.cpp
new file mode 100644
index 0000000000..abd793e3eb
--- /dev/null
+++ b/plugins/ProxySwitch/src/ip.cpp
@@ -0,0 +1,728 @@
+/*
+proxySwitch
+
+The plugin watches IP address changes, reports them via popups and adjusts
+the proxy settings of Miranda and Internet Explorer accordingly.
+*/
+
+#include "stdafx.h"
+
+//#define IP_DEBUG
+#ifdef IP_DEBUG
+#pragma comment (lib, "user32")
+#pragma comment (lib, "iphlpapi")
+#pragma comment (lib, "ws2_32")
+#define PopupMyIPAddrs(x) printf("PopupMyIPAddrs(%s)\n", x);
+#define GetCurrentProcessId() 13604
+NETWORK_INTERFACE_LIST NIF_List;
+CRITICAL_SECTION csNIF_List;
+char opt_hideIntf[MAX_IPLIST_LENGTH];
+void UpdateInterfacesMenu (void) { }
+PLUGINLINK *pluginLink;
+int main(void) {
+ NETWORK_INTERFACE_LIST list;
+ char opt[200] = "2.252.83.0-2.252.85.0;10.100.0.0/16;2.252.83.32-38;;;32.64.128.0/255.255.255.0";
+ IP_RANGE_LIST range;
+ InitializeCriticalSection(&csNIF_List);
+ lstrcpy(opt_hideIntf, "VMnet*");
+ printf("Started\n");
+ printf("IP Helper procs: %s\n", Load_ExIpHelper_Procedures() ? "Loaded" : "Not found");
+ if ( Create_NIF_List( &list ) >=0 ) {
+ printf("%s\n", Print_NIF_List(list, NULL));
+
+ Create_Range_List( &range, opt, FALSE );
+ printf("'%s' matches: %s\n", opt, Match_Range_List(range, list) ? "yes" : "no" );
+ Free_Range_List( &range );
+
+
+ Free_NIF_List( &list );
+ }
+ DeleteCriticalSection(&csNIF_List);
+ printf("Finished\n");
+ return 0;
+}
+#endif
+
+wchar_t tempstr[MAX_SECONDLINE];
+
+/* ################################################################################ */
+
+#ifndef IP_DEBUG
+void IP_WatchDog (void *arg) {
+ OVERLAPPED overlap;
+ DWORD ret;
+ wchar_t msg[300];
+ HANDLE event_list[2];
+ HANDLE hand = WSACreateEvent();
+ overlap.hEvent = WSACreateEvent();
+
+ for (;;) {
+
+ ret = NotifyAddrChange(&hand, &overlap);
+ if (ret != NO_ERROR && WSAGetLastError() != WSA_IO_PENDING) {
+ wchar_t err[100];
+ mir_snwprintf(err, L"NotifyAddrChange Error: %d/nRestart Miranda IM to restore IP monitor.", WSAGetLastError());
+ ERRORMSG(err);
+ break;
+ }
+
+ event_list[0] = overlap.hEvent;
+ event_list[1] = hEventRebound;
+
+ ret = MsgWaitForMultipleObjectsEx( 2, event_list, INFINITE, 0, MWMO_ALERTABLE );
+ if (ret == WAIT_IO_COMPLETION && Miranda_IsTerminated()) break;
+ if (ret == WAIT_OBJECT_0 || ret == WAIT_TIMEOUT || ret == (WAIT_OBJECT_0+1) ) {
+ NETWORK_INTERFACE_LIST list;
+
+ if ( Create_NIF_List_Ex( &list ) >=0 ) {
+ int change = INCUPD_INTACT;
+
+ EnterCriticalSection(&csNIF_List);
+ change = IncUpdate_NIF_List(&NIF_List, list);
+ if ( change != INCUPD_INTACT && change != INCUPD_CONN_BIND ) {
+ char proxy = -1;
+ int change_Miranda = 0;
+ int reset_Miranda = 0;
+ int change_IE = 0;
+ int change_Firefox = 0;
+ IP_RANGE_LIST range;
+
+ if ( proxy == -1 ) {
+ Create_Range_List( &range, opt_useProxy, TRUE );
+ if ( Match_Range_List( range, NIF_List ) ) proxy = 1;
+ Free_Range_List( &range );
+ }
+ if ( proxy == -1 ) {
+ Create_Range_List( &range, opt_noProxy, FALSE );
+ if ( Match_Range_List( range, NIF_List ) ) proxy = 0;
+ Free_Range_List( &range );
+ }
+ if ( proxy == -1 ) {
+ Create_Range_List( &range, opt_useProxy, FALSE );
+ if ( Match_Range_List( range, NIF_List ) ) proxy = 1;
+ Free_Range_List( &range );
+ }
+
+ if ( proxy != -1 && proxy != Get_Miranda_Proxy_Status() ) change_Miranda = reset_Miranda = opt_miranda;
+ if ( proxy != -1 && proxy != Get_IE_Proxy_Status() ) change_IE = opt_ie;
+ if ( proxy != -1 && proxy != Get_Firefox_Proxy_Status() ) change_Firefox = opt_firefox;
+ if ( opt_alwayReconnect ) reset_Miranda = 1;
+
+ mir_wstrcpy(msg, L"");
+ if ( opt_showProxyState && change_Miranda ) {
+ mir_wstrcat(msg, TranslateT("\nMiranda "));
+ mir_wstrcat(msg, proxy ? TranslateT("Proxy") : TranslateT("Direct"));
+ }
+ if ( opt_showProxyState && change_IE ) {
+ mir_wstrcat(msg, TranslateT("\nExplorer "));
+ mir_wstrcat(msg, proxy ? TranslateT("Proxy") : TranslateT("Direct"));
+ }
+ if ( opt_showProxyState && change_Firefox ) {
+ mir_wstrcat(msg, TranslateT("\nFirefox "));
+ mir_wstrcat(msg, proxy ? TranslateT("Proxy") : TranslateT("Direct"));
+ }
+ UpdateInterfacesMenu();
+ PopupMyIPAddrs(mir_wstrlen(msg) ? msg : NULL);
+
+ if ( change_IE ) Set_IE_Proxy_Status( proxy );
+ if ( change_Firefox ) Set_Firefox_Proxy_Status( proxy );
+ if ( reset_Miranda ) {
+ PROTO_SETTINGS protocols;
+ Disconnect_All_Protocols( &protocols, change_Miranda );
+ Sleep( 1000 );
+ if ( change_Miranda ) Set_Miranda_Proxy_Status( proxy );
+ Connect_All_Protocols( &protocols );
+ }
+ }
+ LeaveCriticalSection(&csNIF_List);
+
+ Free_NIF_List( &list );
+ }
+ }
+
+ ResetEvent(hEventRebound);
+ WSAResetEvent(hand);
+ WSAResetEvent(overlap.hEvent);
+ }
+
+ WSACloseEvent(hand);
+ WSACloseEvent(overlap.hEvent);
+}
+#endif
+
+/* ################################################################################ */
+
+int Create_NIF_List_Ex (NETWORK_INTERFACE_LIST *list) {
+ UINT delay = 1;
+ int out;
+
+ while ( (out = Create_NIF_List(list)) == -2 && delay < 10 ) {
+ Sleep(delay*50);
+ delay++;
+ }
+ if (out == -2) ERRORMSG(TranslateT("Cannot retrieve IP or Adapter data."));
+ return out < 0 ? -1 : out;
+}
+
+PNETWORK_INTERFACE Find_NIF_IP(NETWORK_INTERFACE_LIST list, const LONG IP) {
+ UCHAR idx = 0;
+ UCHAR i;
+
+ while (idx < list.count) {
+ for (i = 0; i < list.item[idx].IPcount; i++) {
+ if (list.item[idx].IP[i] == IP) return &(list.item[idx]);
+ }
+ idx++;
+ }
+ return NULL;
+}
+
+int Create_NIF_List (NETWORK_INTERFACE_LIST *list) {
+
+ PIP_ADAPTER_INFO pAdapterInfo, pAdapt;
+ PIP_ADDR_STRING pAddrStr;
+ PIP_ADAPTER_ADDRESSES pAddresses, pAddr;
+ PNETWORK_INTERFACE nif;
+ ULONG outBufLen;
+ wchar_t *tmp_opt, *intf, *rest, *name;
+ BOOL skip;
+ DWORD out;
+ UCHAR idx;
+
+ // prepare and load IP_ADAPTER_ADDRESSES
+ outBufLen = 0;
+ if (GetAdaptersAddresses(AF_INET, 0, NULL, NULL, &outBufLen) == ERROR_BUFFER_OVERFLOW) {
+ pAddresses = (PIP_ADAPTER_ADDRESSES) malloc(outBufLen);
+ if (pAddresses == NULL) {
+ ERRORMSG(TranslateT("Cannot allocate memory for pAddresses"));
+ return -1;
+ }
+ if ((out = GetAdaptersAddresses(AF_INET, 0, NULL, pAddresses, &outBufLen)) != ERROR_SUCCESS) {
+ free(pAddresses);
+ return -2;
+ }
+ } else {
+ ERRORMSG(TranslateT("GetAdaptersAddresses sizing failed"));
+ return -1;
+ }
+
+ // prepare and load IP_ADAPTER_INFO
+ outBufLen = 0;
+ if (GetAdaptersInfo(NULL, &outBufLen) == ERROR_BUFFER_OVERFLOW) {
+ pAdapterInfo = (PIP_ADAPTER_INFO) malloc(outBufLen);
+ if (pAdapterInfo == NULL) {
+ ERRORMSG(TranslateT("Cannot allocate memory for pAdapterInfo"));
+ free(pAddresses);
+ return -1;
+ }
+ if (GetAdaptersInfo(pAdapterInfo, &outBufLen) != NO_ERROR) {
+ free(pAdapterInfo);
+ free(pAddresses);
+ return -2;
+ }
+ } else {
+ ERRORMSG(TranslateT("GetAdaptersInfo sizing failed"));
+ free(pAddresses);
+ return -1;
+ }
+
+ ZeroMemory(list, sizeof(NETWORK_INTERFACE_LIST));
+
+ pAdapt = pAdapterInfo;
+ while (pAdapt) {
+
+ // add a new interface into the list
+ list->count++;
+ list->item = (PNETWORK_INTERFACE)mir_realloc( list->item, list->count * sizeof(NETWORK_INTERFACE) );
+ nif = &(list->item[list->count - 1]);
+ ZeroMemory(nif, sizeof(NETWORK_INTERFACE));
+
+ // copy AdapterName
+ nif->AdapterName = (char*)mir_alloc(mir_strlen(pAdapt->AdapterName)+4);
+ nif->AdapterName = mir_strdup(pAdapt->AdapterName);
+
+ // find its FriendlyName and copy it
+ pAddr = pAddresses;
+ while(pAddr && mir_strcmp(pAddr->AdapterName, pAdapt->AdapterName)) {
+ pAddr = pAddr->Next;
+ }
+ if ( pAddr ) {
+ nif->FriendlyName = (wchar_t*)mir_alloc(wcslen(pAddr->FriendlyName)+4);
+ nif->FriendlyName = mir_wstrdup(pAddr->FriendlyName);
+ }
+
+ skip = FALSE;
+ tmp_opt = intf = rest = mir_wstrdup( opt_hideIntf );
+ while ( rest && rest[0] && ! skip ) {
+ rest = wcschr( rest, ';' );
+ if ( rest != NULL ) {
+ rest[0] = 0;
+ rest++;
+ }
+ if ( intf[0] ) {
+ if ( intf[mir_wstrlen(intf)-1] == '*' && mir_wstrlen(intf)-1 <= mir_wstrlen(nif->FriendlyName) ) {
+ intf[mir_wstrlen(intf)-1] = 0;
+ name = nif->FriendlyName;
+ skip = TRUE;
+ while ( intf[0] ) {
+ if ( intf[0] != name[0] ) {
+ skip = FALSE;
+ break;
+ }
+ intf++;
+ name++;
+ }
+ }
+ if ( mir_wstrcmp(nif->FriendlyName, intf) == 0 ) {
+ skip = TRUE;
+ }
+ }
+ intf = rest;
+ }
+ free(tmp_opt);
+
+ if ( skip ) {
+ list->count--;
+ list->item = (PNETWORK_INTERFACE)mir_realloc( list->item, list->count * sizeof(NETWORK_INTERFACE) );
+ pAdapt = pAdapt->Next;
+ continue;
+ }
+
+ // get required size for IPstr and IP
+ outBufLen = 0;
+ pAddrStr = &(pAdapt->IpAddressList);
+ while(pAddrStr) {
+ if ( strcmp("0.0.0.0", pAddrStr->IpAddress.String) ) {
+ nif->IPcount++; // count IP addresses
+ outBufLen += strlen(pAddrStr->IpAddress.String); // count length of IPstr
+ }
+ pAddrStr = pAddrStr->Next;
+ if (pAddrStr) outBufLen += 2; // count length of IPstr (add ", ")
+ }
+
+ // create IPstr and IP
+ if ( nif->IPcount ) {
+ nif->IPstr = (char*)mir_alloc( outBufLen+4 );
+ strcpy(nif->IPstr, "");
+ nif->IP = (LONG*)mir_alloc( (nif->IPcount+1) * sizeof(LONG) );
+ outBufLen = 0;
+ pAddrStr = &(pAdapt->IpAddressList);
+ while(pAddrStr) {
+ if ( strcmp("0.0.0.0", pAddrStr->IpAddress.String) ) {
+ strcat( nif->IPstr, pAddrStr->IpAddress.String );
+ nif->IP[outBufLen] = inet_addr( pAddrStr->IpAddress.String );
+ outBufLen++;
+ }
+ pAddrStr = pAddrStr->Next;
+ if (pAddrStr) strcat( nif->IPstr, ", ");
+ }
+ nif->IP[outBufLen] = 0L;
+ }
+ pAdapt = pAdapt->Next;
+ }
+
+ free(pAdapterInfo);
+ free(pAddresses);
+
+ EnterCriticalSection(&csConnection_List);
+ for ( idx=0 ; idx < Connection_List.count ; idx++ ) {
+ nif = Find_NIF_IP( *list, Connection_List.item[idx].IP );
+ if ( nif ) {
+ nif->Bound = 1;
+ }
+ }
+ LeaveCriticalSection(&csConnection_List);
+
+ return 0;
+}
+
+/* ################################################################################ */
+
+PNETWORK_INTERFACE Find_NIF_AdapterName ( NETWORK_INTERFACE_LIST list, const char *AdapterName) {
+ UCHAR idx = 0;
+
+ while ( idx < list.count ) {
+ if ( strcmp(list.item[idx].AdapterName, AdapterName) == 0 ) return &(list.item[idx]);
+ idx++;
+ }
+ return NULL;
+}
+
+PNETWORK_INTERFACE Find_NIF_MenuItem ( NETWORK_INTERFACE_LIST list, const HGENMENU MenuItem) {
+ UCHAR idx = 0;
+
+ while ( idx < list.count ) {
+ if ( list.item[idx].MenuItem == MenuItem ) return &(list.item[idx]);
+ idx++;
+ }
+ return NULL;
+}
+
+/* ################################################################################ */
+
+BOOL Compare_NIF_Lists (NETWORK_INTERFACE_LIST list1, NETWORK_INTERFACE_LIST list2) {
+ UCHAR idx = 0;
+
+ if ( list1.count != list2.count ) return 1;
+ while ( idx < list1.count ) {
+ if ( mir_strcmp(list1.item[idx].AdapterName, list2.item[idx].AdapterName) ) return 1;
+ if ( mir_strcmp(list1.item[idx].IPstr, list2.item[idx].IPstr) ) return 1;
+ if ( mir_wstrcmp(list1.item[idx].FriendlyName, list2.item[idx].FriendlyName) ) return 1;
+ idx++;
+ }
+ return 0;
+}
+
+/* ################################################################################ */
+
+int IncUpdate_NIF_List (NETWORK_INTERFACE_LIST *trg, NETWORK_INTERFACE_LIST src) {
+ UCHAR idx;
+ PNETWORK_INTERFACE nif;
+ int change = INCUPD_INTACT;
+
+ for (idx = 0 ; idx < src.count ; idx++) {
+ nif = Find_NIF_AdapterName( *trg, src.item[idx].AdapterName );
+ if ( nif ) {
+ if ( nif->Disabled ) nif->Disabled = 0;
+ if ( strcmp(NVL(nif->IPstr), NVL(src.item[idx].IPstr)) ) {
+ if (nif->IPstr) free(nif->IPstr);
+ nif->IPstr = src.item[idx].IPstr ? mir_strdup( src.item[idx].IPstr ) : NULL;
+ INCUPD(change, INCUPD_UPDATED);
+ }
+ if ( mir_wstrcmp(NVLW(nif->FriendlyName), NVLW(src.item[idx].FriendlyName)) ) {
+ if (nif->FriendlyName) free(nif->FriendlyName);
+ nif->FriendlyName = src.item[idx].FriendlyName ? mir_wstrdup( src.item[idx].FriendlyName ) : NULL;
+ INCUPD(change, INCUPD_UPDATED);
+ }
+ if ( nif->IPcount != src.item[idx].IPcount ) {
+ if ( nif->IPcount > src.item[idx].IPcount && nif->Bound ) {
+ INCUPD(change, INCUPD_CONN_LOST );
+ UnboundConnections( nif->IP, src.item[idx].IP );
+ }
+ nif->IPcount = src.item[idx].IPcount;
+ if (nif->IP) free(nif->IP);
+ if (src.item[idx].IP) {
+ nif->IP = (LONG*)mir_alloc( (nif->IPcount+1) * sizeof(LONG) );
+ memcpy( nif->IP, src.item[idx].IP, (nif->IPcount+1) * sizeof(LONG) );
+ } else {
+ nif->IP = NULL;
+ }
+ INCUPD(change, INCUPD_UPDATED);
+ } else {
+ if ( nif->IPcount > 0 && memcmp( nif->IP, src.item[idx].IP, nif->IPcount * sizeof(LONG) ) ) {
+ free(nif->IP);
+ nif->IP = (LONG*)mir_alloc( (nif->IPcount+1) * sizeof(LONG) );
+ memcpy( nif->IP, src.item[idx].IP, (nif->IPcount+1) * sizeof(LONG) );
+ INCUPD(change, INCUPD_UPDATED);
+ }
+ }
+ if ( nif->Bound != src.item[idx].Bound ) {
+ nif->Bound = src.item[idx].Bound;
+ INCUPD(change, INCUPD_CONN_BIND);
+ }
+ } else {
+ trg->count++;
+ trg->item = (PNETWORK_INTERFACE)mir_realloc( trg->item, trg->count * sizeof(NETWORK_INTERFACE) );
+ nif = &(trg->item[trg->count - 1]);
+ ZeroMemory(nif, sizeof(NETWORK_INTERFACE));
+ nif->AdapterName = src.item[idx].AdapterName ? mir_strdup( src.item[idx].AdapterName ) : NULL;
+ nif->FriendlyName = src.item[idx].FriendlyName ? mir_wstrdup( src.item[idx].FriendlyName ) : NULL;
+ nif->IPstr = src.item[idx].IPstr ? strdup( src.item[idx].IPstr ) : NULL;
+ nif->IPcount = src.item[idx].IPcount;
+ nif->Bound = src.item[idx].Bound;
+ if ( nif->IPcount > 0 ) {
+ nif->IP = (LONG*)mir_alloc( (nif->IPcount+1) * sizeof(LONG) );
+ memcpy( nif->IP, src.item[idx].IP, (nif->IPcount+1) * sizeof(LONG) );
+ }
+ INCUPD(change, INCUPD_UPDATED);
+ }
+ }
+ for (idx = 0 ; idx < trg->count ; idx++) {
+ if ( trg->item[idx].Disabled ) continue;
+ nif = Find_NIF_AdapterName( src, trg->item[idx].AdapterName );
+ if ( ! nif ) {
+ if ( trg->item[idx].Bound ) {
+ INCUPD(change, INCUPD_CONN_LOST );
+ UnboundConnections( trg->item[idx].IP, NULL );
+ } else {
+ INCUPD(change, INCUPD_UPDATED );
+ }
+ if (trg->item[idx].IPstr) free(trg->item[idx].IPstr);
+ if (trg->item[idx].IP) free(trg->item[idx].IP);
+ trg->item[idx].IPstr = NULL;
+ trg->item[idx].IPcount = 0;
+ trg->item[idx].IP = NULL;
+ trg->item[idx].Bound = FALSE;
+ trg->item[idx].Disabled = 1;
+ }
+ }
+ return change;
+}
+
+/* ################################################################################ */
+
+wchar_t *Print_NIF (PNETWORK_INTERFACE nif) {
+ ZeroMemory( tempstr, sizeof(tempstr) );
+ mir_snwprintf( tempstr, L"%s:\t%s", nif->FriendlyName, nif->IPstr ? _A2T(nif->IPstr) : TranslateT("disconnected"));
+ return tempstr;
+}
+
+wchar_t *Print_NIF_List (NETWORK_INTERFACE_LIST list, wchar_t *msg) {
+ UCHAR idx;
+ int pos = 0;
+
+ ZeroMemory( tempstr, sizeof(tempstr) );
+ for( idx = 0 ; idx < list.count ; idx++ ) {
+ pos += mir_snwprintf( tempstr+pos, _countof(tempstr), L"%s:\t%s%s%s\n",
+ list.item[idx].FriendlyName,
+ list.item[idx].Bound ? L"[u]":L"",
+ list.item[idx].IPstr ? _A2T(list.item[idx].IPstr) : TranslateT("disconnected"),
+ list.item[idx].Bound ? L"[/u]":L""
+ );
+ }
+ if ( msg ) mir_wstrcat(tempstr, msg); else tempstr[mir_wstrlen(tempstr)-1] = 0;
+ return tempstr;
+}
+
+/* ################################################################################ */
+
+void Free_NIF (PNETWORK_INTERFACE nif) {
+ if (nif->AdapterName) free(nif->AdapterName);
+ if (nif->FriendlyName) free(nif->FriendlyName);
+ if (nif->IPstr) free(nif->IPstr);
+ if (nif->IP) free(nif->IP);
+ ZeroMemory(nif, sizeof(NETWORK_INTERFACE));
+}
+
+void Free_NIF_List (NETWORK_INTERFACE_LIST *list) {
+ UCHAR idx;
+
+ for( idx = 0 ; idx < list->count ; idx++ ) {
+ Free_NIF( &(list->item[idx]) );
+ }
+ free( list->item );
+ ZeroMemory(list, sizeof(NETWORK_INTERFACE_LIST));
+}
+
+/* ################################################################################ */
+
+void Parse_Range ( PIP_RANGE range, wchar_t *str, BOOL prioritized ) {
+ wchar_t *ext;
+ unsigned long num;
+
+ range->cmpType = CMP_SKIP;
+
+ if ((str[0] == '!' && ! prioritized) || (str[0] != '!' && prioritized)) {
+ range->mask = range->net = 0L;
+ return;
+ }
+ if (str[0] == '!') str++;
+
+ // ip/mask
+ if ( (ext = wcschr( str, '/' )) != NULL ) {
+ ext[0] = 0; ext++;
+
+ // ip/bits (10.0.0.1/16)
+ if ( wcsspn(ext, DIGITS) == mir_wstrlen(ext) ) {
+ num = _wtol(ext);
+ if ( num >= 0 && num <= 32 && (range->net = inet_addr(_T2A(str))) != INADDR_NONE ) {
+ range->cmpType = CMP_MASK;
+ range->mask = NETORDER(num ? ~(0xFFFFFFFF >> (num)) : ~0);
+ range->net = range->net & range->mask;
+ }
+ } else {
+
+ // ip/subnet (10.0.0.1/255.255.0.0)
+ if ( (range->net = inet_addr(_T2A(str))) != INADDR_NONE && (range->mask = inet_addr(_T2A(ext))) != INADDR_NONE ) {
+ for ( num = 0 ; num < 32 ; num++ ) {
+ if ( range->mask == NETORDER(num ? ~(0xFFFFFFFF >> (32-num)) : ~0)) {
+ range->cmpType = CMP_MASK;
+ range->net = range->net & range->mask;
+ break;
+ }
+ }
+ }}
+ } else {
+
+ // ipbegin-end
+ if ( (ext = wcschr( str, '-' )) != NULL ) {
+ ext[0] = 0; ext++;
+
+ // ipA.B.C.D1-D2 (10.0.0.1-12)
+ if ( wcsspn(ext, DIGITS) == mir_wstrlen(ext) ) {
+ num = _wtol(ext);
+ if ( num > 0 && num <= 255 && (range->loIP = inet_addr(_T2A(str))) != INADDR_NONE && (range->loIP >> 24) <= num ) {
+ range->cmpType = CMP_SPAN;
+ range->hiIP = ((range->loIP & 0x00FFFFFF) | (num << 24));
+ range->loIP = (range->loIP);
+ }
+ } else {
+
+ // ipstart-ipend (10.0.0.1-10.0.10.255)
+ if ( (range->loIP = inet_addr(_T2A(str))) != INADDR_NONE && (range->hiIP = inet_addr(_T2A(ext))) != INADDR_NONE ) {
+
+ range->loIP = (range->loIP);
+ range->hiIP = (range->hiIP);
+ if ( range->loIP <= range->hiIP ) {
+ range->cmpType = CMP_SPAN;
+ }
+ }
+ }} else {
+
+ // ip
+ if ( mir_wstrlen(str) > 0 && (range->net = inet_addr(_T2A(str))) != INADDR_NONE ) {
+ range->cmpType = CMP_MASK;
+ range->mask = 0xFFFFFFFF;
+ }}}
+
+ if ( range->cmpType == CMP_SKIP ) {
+ range->mask = range->net = 0L;
+ }
+}
+
+int Create_Range_List ( IP_RANGE_LIST *list, wchar_t *str, BOOL prioritized ) {
+ wchar_t *range, *rest, *tmp;
+ int size, idx;
+
+ ZeroMemory(list, sizeof(IP_RANGE_LIST));
+
+ // get expected number of ranges
+ range = str;
+ size = mir_wstrlen( range ) > 0 ? 1 : 0;
+ while ( range[0] ) { if ( range[0] == ';') size++; range++; };
+
+ if (size == 0) return 0;
+
+ // alloc required space
+ list->item = (PIP_RANGE)mir_alloc( size * sizeof( IP_RANGE ) );
+ ZeroMemory( list->item, size * sizeof( IP_RANGE ) );
+
+ tmp = range = rest = mir_wstrdup( str );
+ idx = 0;
+ while ( rest && rest[0] ) {
+ rest = wcschr( rest, ';' );
+ if ( rest != NULL ) {
+ rest[0] = 0;
+ rest++;
+ }
+ Parse_Range( &(list->item[idx]), range, prioritized );
+ if ( list->item[idx].cmpType != CMP_SKIP ) idx++;
+ range = rest;
+ }
+
+ list->count = idx;
+ list->item = (PIP_RANGE)mir_realloc( list->item, (idx+1) * sizeof( IP_RANGE ) );
+
+ ZeroMemory( &(list->item[idx]), sizeof( IP_RANGE ) );
+ list->item[idx].cmpType = CMP_END;
+
+ free( tmp );
+
+ return 0;
+}
+
+int Match_Range_List (IP_RANGE_LIST range, NETWORK_INTERFACE_LIST nif) {
+ PIP_RANGE rng;
+ UCHAR idx;
+ ULONG *ip;
+
+ if ( range.count == 0 || nif.count == 0 ) return 0;
+
+ rng = range.item;
+ while( rng->cmpType != CMP_END ) {
+
+ switch ( rng->cmpType ) {
+ case CMP_SKIP:
+ break;
+
+ case CMP_MASK:
+ for ( idx = 0 ; idx < nif.count ; idx++ ) {
+ ip = (ULONG *)nif.item[idx].IP;
+ while (ip && *ip) {
+ if ( (ULONG)(*ip & rng->mask) == rng->net ) return 1;
+ ip++;
+ }
+ }
+ break;
+
+ case CMP_SPAN:
+ for ( idx = 0 ; idx < nif.count ; idx++ ) {
+ ip = (ULONG *)nif.item[idx].IP;
+ while (ip && *ip) {
+ if ( (NETORDER(rng->loIP) <= NETORDER(*ip)) && (NETORDER(*ip) <= NETORDER(rng->hiIP)) ) return 1;
+ ip++;
+ }
+ }
+ break;
+ }
+ rng++;
+ }
+
+ return 0;
+}
+
+void Free_Range_List (IP_RANGE_LIST *list) {
+ if ( list->item ) free( list->item );
+ ZeroMemory(list, sizeof(IP_RANGE_LIST));
+}
+
+
+int ManageConnections (WPARAM wParam,LPARAM lParam) {
+ NETLIBCONNECTIONEVENTINFO *info = (NETLIBCONNECTIONEVENTINFO *)wParam;
+ int found;
+ UCHAR i;
+
+ EnterCriticalSection(&csConnection_List);
+ found = -1;
+ for (i=0 ; i<Connection_List.count ; i++) {
+ if ( Connection_List.item[i].IP == info->local.sin_addr.s_addr && Connection_List.item[i].Port == info->local.sin_port ) {
+ found = i;
+ break;
+ }
+ }
+ if ( (found >= 0 && info->connected) || (found == -1 && !info->connected)) {
+ LeaveCriticalSection(&csConnection_List);
+ return 0;
+ }
+ if ( found >= 0 ) {
+ Connection_List.count--;
+ for( i=found ; i<Connection_List.count ; i++ ) memcpy( &(Connection_List.item[i]), &(Connection_List.item[i+1]), sizeof(ACTIVE_CONNECTION) );
+ } else {
+ if ( Connection_List.count >= Connection_List._alloc ) {
+ Connection_List._alloc += 10;
+ Connection_List.item = (PACTIVE_CONNECTION)mir_realloc( Connection_List.item, Connection_List._alloc * sizeof(ACTIVE_CONNECTION) );
+ }
+ Connection_List.item[Connection_List.count].IP = info->local.sin_addr.s_addr;
+ Connection_List.item[Connection_List.count].Port = info->local.sin_port;
+ Connection_List.count++;
+ }
+ LeaveCriticalSection(&csConnection_List);
+
+ SetEvent( hEventRebound );
+
+ return 0;
+}
+
+void UnboundConnections ( LONG *OldIP, LONG *NewIP ) {
+ UCHAR i, j;
+ LONG *IP;
+
+ while ( OldIP != NULL && *OldIP != 0 ) {
+ IP = NewIP;
+ while ( IP != NULL && *IP != 0 && *IP != *OldIP ) IP++;
+ if ( IP == NULL || *IP != *OldIP ) {
+ EnterCriticalSection(&csConnection_List);
+ i = 0;
+ while ( i < Connection_List.count ) {
+ if (Connection_List.item[i].IP == (ULONG)*OldIP) {
+ Connection_List.count--;
+ for( j=i ; j<Connection_List.count ; j++ ) memcpy( &(Connection_List.item[j]), &(Connection_List.item[j+1]), sizeof(ACTIVE_CONNECTION) );
+ } else {
+ i++;
+ }
+ }
+ LeaveCriticalSection(&csConnection_List);
+ }
+ OldIP++;
+ }
+}
diff --git a/plugins/ProxySwitch/src/main.cpp b/plugins/ProxySwitch/src/main.cpp
new file mode 100644
index 0000000000..5266e901aa
--- /dev/null
+++ b/plugins/ProxySwitch/src/main.cpp
@@ -0,0 +1,367 @@
+/*
+proxySwitch
+
+The plugin watches IP address changes, reports them via popups and adjusts
+the proxy settings of Miranda and Internet Explorer accordingly.
+*/
+
+#include "stdafx.h"
+
+CMPlugin g_plugin;
+
+PLUGININFOEX pluginInfoEx =
+{
+ sizeof(PLUGININFOEX),
+ __PLUGIN_NAME,
+ PLUGIN_MAKE_VERSION(__MAJOR_VERSION, __MINOR_VERSION, __RELEASE_NUM, __BUILD_NUM),
+ __DESCRIPTION,
+ __AUTHOR,
+ __COPYRIGHT,
+ __AUTHORWEB,
+ UNICODE_AWARE,
+ // {4DF0C267-6EFB-4410-B651-385F87158509}
+ { 0x4df0c267, 0x6efb, 0x4410,{ 0xb6, 0x51, 0x38, 0x5f, 0x87, 0x15, 0x85, 0x9 } }
+};
+
+CMPlugin::CMPlugin() :
+ PLUGIN<CMPlugin>(MODULENAME, pluginInfoEx)
+{}
+
+HGENMENU hEnableDisablePopupMenu = 0;
+
+NETWORK_INTERFACE_LIST NIF_List;
+CRITICAL_SECTION csNIF_List;
+ACTIVE_CONNECTION_LIST Connection_List;
+CRITICAL_SECTION csConnection_List;
+HANDLE hEventRebound = NULL;
+
+wchar_t opt_useProxy[MAX_IPLIST_LENGTH];
+wchar_t opt_noProxy[MAX_IPLIST_LENGTH];
+wchar_t opt_hideIntf[MAX_IPLIST_LENGTH];
+UINT opt_defaultColors;
+UINT opt_popups;
+UINT opt_showProxyState;
+UINT opt_miranda;
+UINT opt_ie;
+UINT opt_firefox;
+UINT opt_showMyIP;
+UINT opt_showProxyIP;
+UINT opt_alwayReconnect;
+UINT opt_startup;
+UINT opt_not_restarted;
+COLORREF opt_bgColor;
+COLORREF opt_txtColor;
+
+UINT opt_popupPluginInstalled;
+
+static HANDLE hEventConnect = NULL;
+static HANDLE hEventDisconnect = NULL;
+static HANDLE hSvcCopyClip0 = NULL;
+static HANDLE hSvcCopyClip1 = NULL;
+static HANDLE hSvcCopyClip2 = NULL;
+static HANDLE hSvcCopyClip3 = NULL;
+static HANDLE hSvcCopyClip4 = NULL;
+static HANDLE hSvcCopyClip5 = NULL;
+static HANDLE hSvcPopupSwitch = NULL;
+static HANDLE hSvcProxyDisable = NULL;
+static HANDLE hSvcProxyEnable = NULL;
+static HANDLE hSvcShowMyIP = NULL;
+
+/* ################################################################################ */
+
+static int ShowMyIPAddrs(WPARAM wParam, LPARAM lParam)
+{
+ PopupMyIPAddrs(NULL);
+ return 0;
+}
+
+void PopupMyIPAddrs(wchar_t *msg)
+{
+ POPUPDATAW ppd;
+ NETWORK_INTERFACE_LIST list;
+
+ ZeroMemory(&ppd, sizeof(ppd));
+
+ if (Create_NIF_List_Ex(&list) >= 0) {
+
+ wcsncpy_s(ppd.lpwzText, Print_NIF_List(list, msg), _TRUNCATE);
+
+ if (opt_popupPluginInstalled) {
+ LoadSettings();
+ ppd.lchIcon = LoadIcon(g_plugin.getInst(), MAKEINTRESOURCE(IDI_PROXY));
+ wcsncpy_s(ppd.lpwzContactName, TranslateT("Current IP address"), _TRUNCATE);
+ ppd.colorBack = opt_defaultColors ? 0 : opt_bgColor;
+ ppd.colorText = opt_defaultColors ? 0 : opt_txtColor;
+ CallService(MS_POPUP_ADDPOPUP, (WPARAM)&ppd, 0);
+ }
+ else {
+ MessageBox(NULL, ppd.lpwzText, _A2T(MODULENAME), MB_OK | MB_ICONINFORMATION);
+ }
+
+ Free_NIF_List(&list);
+ }
+}
+
+static int ProxyEnable(WPARAM wParam, LPARAM lParam)
+{
+ Set_IE_Proxy_Status(1);
+ Set_Miranda_Proxy_Status(1);
+ Set_Firefox_Proxy_Status(1);
+ return 0;
+}
+
+static int ProxyDisable(WPARAM wParam, LPARAM lParam)
+{
+ Set_IE_Proxy_Status(0);
+ Set_Miranda_Proxy_Status(0);
+ Set_Firefox_Proxy_Status(0);
+ return 0;
+}
+
+/* ################################################################################ */
+
+void CopyIP2Clipboard(UCHAR idx)
+{
+ EnterCriticalSection(&csNIF_List);
+ if (NIF_List.item[idx].IPcount == 0) {
+ LeaveCriticalSection(&csNIF_List);
+ return;
+ }
+ if (!OpenClipboard(NULL)) {
+ LeaveCriticalSection(&csNIF_List);
+ return;
+ }
+ EmptyClipboard();
+ SetClipboardData(CF_UNICODETEXT, (HANDLE)NIF_List.item[idx].IPstr);
+ CloseClipboard();
+ LeaveCriticalSection(&csNIF_List);
+}
+
+static int CopyIP2Clipboard0(WPARAM wParam, LPARAM lParam) { CopyIP2Clipboard(0); return 0; }
+static int CopyIP2Clipboard1(WPARAM wParam, LPARAM lParam) { CopyIP2Clipboard(1); return 0; }
+static int CopyIP2Clipboard2(WPARAM wParam, LPARAM lParam) { CopyIP2Clipboard(2); return 0; }
+static int CopyIP2Clipboard3(WPARAM wParam, LPARAM lParam) { CopyIP2Clipboard(3); return 0; }
+static int CopyIP2Clipboard4(WPARAM wParam, LPARAM lParam) { CopyIP2Clipboard(4); return 0; }
+static int CopyIP2Clipboard5(WPARAM wParam, LPARAM lParam) { CopyIP2Clipboard(5); return 0; }
+
+void UpdateInterfacesMenu(void)
+{
+ UCHAR idx;
+ CMenuItem mi(g_plugin);
+ char svc[60];
+
+ if (!opt_showProxyIP && !opt_not_restarted) return;
+
+ EnterCriticalSection(&csNIF_List);
+ for (idx = 0; idx < NIF_List.count; idx++) {
+ if (NIF_List.item[idx].MenuItem) {
+ // set new name and flags
+ //mi.name.w = Print_NIF(&(NIF_List.item[idx]));
+ //if (NIF_List.item[idx].IPcount == 0) mi.flags |= CMIF_GRAYED;
+ //mi.flags |= CMIM_FLAGS | CMIM_NAME;
+ // update menu item
+ Menu_ModifyItem(NIF_List.item[idx].MenuItem, Print_NIF(&(NIF_List.item[idx])), INVALID_HANDLE_VALUE, CMIF_GRAYED);
+ //CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)NIF_List.item[idx].MenuItem, (LPARAM)&mi);
+ }
+ else {
+ // add a new menu item
+ sprintf(svc, "%s%d", MS_PROXYSWITCH_COPYIP2CLIP, idx);
+ mi.position = 0xC00000;
+ mi.flags = CMIF_UNICODE;
+ mi.root = g_plugin.addRootMenu(MO_MAIN, LPGENW("Proxy Settings && Interfaces"), 0xC0000000);
+ Menu_ConfigureItem(mi.root, MCI_OPT_UID, "68AB766F-09F1-4C4C-9AE1-4135617741C9");
+
+ SET_UID(mi, 0x8295e40d, 0xa262, 0x434b, 0xa4, 0xb3, 0x57, 0x6b, 0xe0, 0xfc, 0x8f, 0x68);
+ mi.name.w = Print_NIF(&(NIF_List.item[idx]));
+ mi.pszService = svc;
+ //mi.pszPopupName = Translate("Proxy Settings && Interfaces");
+ //mi.popupPosition = 0xC0000000;
+ NIF_List.item[idx].MenuItem = Menu_AddMainMenuItem(&mi);
+ // menu cannot be grayed when creating, so we have to do it after that
+ if (NIF_List.item[idx].IPcount == 0) {
+ //ZeroMemory(&mi, sizeof(mi));
+ //mi.cbSize = sizeof(mi);
+ //mi.flags |= CMIF_GRAYED;
+ Menu_ModifyItem(NIF_List.item[idx].MenuItem, Print_NIF(&(NIF_List.item[idx])), INVALID_HANDLE_VALUE, CMIF_GRAYED);
+ //CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)NIF_List.item[idx].MenuItem, (LPARAM)&mi);
+ }
+ // create and register service for this menu item
+ switch (idx) {
+ case 0: hSvcCopyClip0 = CreateServiceFunction(svc, CopyIP2Clipboard0); break;
+ case 1: hSvcCopyClip1 = CreateServiceFunction(svc, CopyIP2Clipboard1); break;
+ case 2: hSvcCopyClip2 = CreateServiceFunction(svc, CopyIP2Clipboard2); break;
+ case 3: hSvcCopyClip3 = CreateServiceFunction(svc, CopyIP2Clipboard3); break;
+ case 4: hSvcCopyClip4 = CreateServiceFunction(svc, CopyIP2Clipboard4); break;
+ case 5: hSvcCopyClip5 = CreateServiceFunction(svc, CopyIP2Clipboard5); break;
+ }
+ }
+ }
+ LeaveCriticalSection(&csNIF_List);
+}
+
+/* ################################################################################ */
+
+void UpdatePopupMenu(BOOL State)
+{
+ CMenuItem mi(g_plugin);
+
+ if (!hEnableDisablePopupMenu) return;
+
+ //ZeroMemory(&mi, sizeof(mi));
+ //mi.cbSize = sizeof(mi);
+
+ // popup is now disabled
+ if (State == FALSE) {
+ mi.name.w = LPGENW("Enable &IP change notification");
+ mi.hIcon = LoadIcon(g_plugin.getInst(), MAKEINTRESOURCE(IDI_NOTIF_0));
+
+ // popup is now enabled
+ }
+ else {
+ mi.name.w = LPGENW("Disable &IP change notification");
+ mi.hIcon = LoadIcon(g_plugin.getInst(), MAKEINTRESOURCE(IDI_NOTIF_1));
+ }
+ //mi.flags = CMIM_ICON | CMIM_NAME;
+
+ // update menu item
+ Menu_ModifyItem(hEnableDisablePopupMenu, mi.name.w);
+ //CallService(MS_CLIST_MODIFYMENUITEM, (WPARAM)hEnableDisablePopupMenu, (LPARAM)&mi);
+}
+
+static int PopupSwitch(WPARAM wParam, LPARAM lParam)
+{
+ opt_popups = !opt_popups;
+ UpdatePopupMenu(opt_popups);
+ SaveSettings();
+ return 0;
+}
+
+/* ################################################################################ */
+
+int CMPlugin::Load()
+{
+ char proxy = -1;
+ IP_RANGE_LIST range;
+
+ opt_startup = FALSE;
+ opt_not_restarted = FALSE;
+
+ LoadSettings();
+
+ InitializeCriticalSection(&csConnection_List);
+ InitializeCriticalSection(&csNIF_List);
+
+ ZeroMemory(&Connection_List, sizeof(Connection_List));
+ Create_NIF_List_Ex(&NIF_List);
+
+ if (opt_ie || opt_miranda || opt_firefox) {
+ Create_Range_List(&range, opt_useProxy, TRUE);
+ if (Match_Range_List(range, NIF_List)) proxy = 1;
+ Free_Range_List(&range);
+ if (proxy == -1) {
+ Create_Range_List(&range, opt_noProxy, FALSE);
+ if (Match_Range_List(range, NIF_List)) proxy = 0;
+ Free_Range_List(&range);
+ }
+ if (proxy == -1) {
+ Create_Range_List(&range, opt_useProxy, FALSE);
+ if (Match_Range_List(range, NIF_List)) proxy = 1;
+ Free_Range_List(&range);
+ }
+ if (proxy != -1) {
+ if (opt_miranda && Get_Miranda_Proxy_Status() != proxy) Set_Miranda_Proxy_Status(proxy);
+ if (opt_ie && Get_IE_Proxy_Status() != proxy) Set_IE_Proxy_Status(proxy);
+ if (opt_firefox && Get_Firefox_Proxy_Status() != proxy) Set_Firefox_Proxy_Status(proxy);
+ }
+ }
+
+ HookEvent(ME_OPT_INITIALISE, OptInit);
+ HookEvent(ME_SYSTEM_MODULESLOADED, Init);
+ HookEvent(ME_NETLIB_EVENT_CONNECTED, ManageConnections);
+ HookEvent(ME_NETLIB_EVENT_DISCONNECTED, ManageConnections);
+
+ return 0;
+}
+
+int Init(WPARAM wParam, LPARAM lParam)
+{
+ CMenuItem mi(g_plugin);
+
+ opt_popupPluginInstalled = ServiceExists(MS_POPUP_ADDPOPUP);
+
+
+ hEventRebound = CreateEvent(NULL, TRUE, FALSE, NULL);
+ mir_forkthread(IP_WatchDog, 0);
+
+ if (opt_showMyIP) {
+ hSvcShowMyIP = CreateServiceFunction(MS_PROXYSWITCH_SHOWMYIPADDRS, ShowMyIPAddrs);
+ //ZeroMemory(&mi, sizeof(mi));
+ //mi.cbSize = sizeof(mi);
+ SET_UID(mi, 0x53b0835b, 0x7162, 0x4272, 0x83, 0x3b, 0x3f, 0x60, 0x9e, 0xe, 0x76, 0x4a);
+ mi.position = 0xC0000000;
+ mi.flags = CMIF_UNICODE;
+ mi.hIcon = LoadIcon(g_plugin.getInst(), MAKEINTRESOURCE(IDI_LOGO));
+ mi.name.w = LPGENW("Show my &IP Addresses");
+ mi.pszService = MS_PROXYSWITCH_SHOWMYIPADDRS;
+ Menu_AddMainMenuItem(&mi);
+ }
+
+ if (opt_showProxyIP) {
+
+ hSvcProxyDisable = CreateServiceFunction(MS_PROXYSWITCH_PROXYDISABLE, ProxyDisable);
+ //ZeroMemory(&mi, sizeof(mi));
+ //mi.cbSize = sizeof(mi);
+ SET_UID(mi, 0xf93289a9, 0x3bad, 0x424b, 0xb2, 0x72, 0x14, 0xa7, 0x45, 0xa5, 0x8, 0x9c);
+ mi.position = 1;
+ mi.name.w = LPGENW("Disable Proxy");
+ mi.pszService = MS_PROXYSWITCH_PROXYDISABLE;
+ mi.root = g_plugin.addRootMenu(MO_MAIN, LPGENW("Proxy Settings && Interfaces"), 0xC0000000);
+ Menu_ConfigureItem(mi.root, MCI_OPT_UID, "A9684E9E-E621-4962-986F-576897928D27");
+ //mi.pszPopupName = Translate("Proxy Settings && Interfaces");
+ //mi.popupPosition = 0xC0000000;
+ Menu_AddMainMenuItem(&mi);
+
+ hSvcProxyEnable = CreateServiceFunction(MS_PROXYSWITCH_PROXYENABLE, ProxyEnable);
+ //ZeroMemory(&mi, sizeof(mi));
+ //mi.cbSize = sizeof(mi);
+ mi.position = 1;
+ mi.name.w = LPGENW("Enable Proxy");
+ mi.pszService = MS_PROXYSWITCH_PROXYENABLE;
+ mi.root = g_plugin.addRootMenu(MO_MAIN, LPGENW("Proxy Settings && Interfaces"), 0xC0000000);
+ Menu_ConfigureItem(mi.root, MCI_OPT_UID, "B37E5BBE-19CF-4C78-AE53-A0DB11656C36");
+ //mi.pszPopupName = Translate("Proxy Settings && Interfaces");
+ //mi.popupPosition = 0xC0000000;
+ Menu_AddMainMenuItem(&mi);
+
+ UpdateInterfacesMenu();
+ }
+
+ if (opt_popupPluginInstalled) {
+ hSvcPopupSwitch = CreateServiceFunction(MS_PROXYSWITCH_POPUPSWITCH, PopupSwitch);
+ //ZeroMemory(&mi, sizeof(mi));
+ //mi.cbSize = sizeof(mi);
+ mi.name.w = LPGENW("IP Change Notification");
+ mi.hIcon = LoadIcon(g_plugin.getInst(), MAKEINTRESOURCE(IDI_LOGO));
+ mi.root = g_plugin.addRootMenu(MO_MAIN, LPGENW("PopUps"), 0xC0000000);
+ Menu_ConfigureItem(mi.root, MCI_OPT_UID, "185AC334-E90E-46C6-83A2-D4E36CB257D9");
+ //mi.pszPopupName = Translate("PopUps");
+ mi.pszService = MS_PROXYSWITCH_POPUPSWITCH;
+ hEnableDisablePopupMenu = Menu_AddMainMenuItem(&mi);
+
+ UpdatePopupMenu(opt_popups);
+ }
+
+ return 0;
+}
+
+int CMPlugin::Unload()
+{
+ if (hEventRebound)
+ CloseHandle(hEventRebound);
+ EnterCriticalSection(&csNIF_List);
+ Free_NIF_List(&NIF_List);
+ LeaveCriticalSection(&csNIF_List);
+ DeleteCriticalSection(&csNIF_List);
+ DeleteCriticalSection(&csConnection_List);
+ return 0;
+}
diff --git a/plugins/ProxySwitch/src/opt.cpp b/plugins/ProxySwitch/src/opt.cpp
new file mode 100644
index 0000000000..44273f705e
--- /dev/null
+++ b/plugins/ProxySwitch/src/opt.cpp
@@ -0,0 +1,191 @@
+/*
+proxySwitch
+
+The plugin watches IP address changes, reports them via popups and adjusts
+the proxy settings of Miranda and Internet Explorer accordingly.
+*/
+
+#include "stdafx.h"
+
+int help_shown;
+
+void ShowHelp( HWND hdlg, int showhide_help ) {
+ int showhide_others = showhide_help == SW_SHOW ? SW_HIDE : SW_SHOW;
+ help_shown = showhide_help;
+
+ ShowWindow(GetDlgItem(hdlg, IDC_HELP_1), showhide_help);
+ ShowWindow(GetDlgItem(hdlg, IDC_HELP_2), showhide_help);
+ ShowWindow(GetDlgItem(hdlg, IDC_HELP_3), showhide_help);
+
+ ShowWindow(GetDlgItem(hdlg, IDC_CHECK_MIRANDA), showhide_others);
+ ShowWindow(GetDlgItem(hdlg, IDC_CHECK_IE), showhide_others);
+ ShowWindow(GetDlgItem(hdlg, IDC_CHECK_FIREFOX), showhide_others);
+ ShowWindow(GetDlgItem(hdlg, IDC_CHECK_PROXYIPMENU), showhide_others);
+ ShowWindow(GetDlgItem(hdlg, IDC_CHECK_SHOWMYIPMENU), showhide_others);
+ ShowWindow(GetDlgItem(hdlg, IDC_CHECK_DEFAULTCOLORS), showhide_others);
+ ShowWindow(GetDlgItem(hdlg, IDC_CHECK_SHOWPROXYSTATUS), showhide_others);
+ ShowWindow(GetDlgItem(hdlg, IDC_CHECK_ALWAY_RECONNECT), showhide_others);
+ ShowWindow(GetDlgItem(hdlg, IDC_CHECK_POPUPS), showhide_others);
+ ShowWindow(GetDlgItem(hdlg, IDC_BGCOLOR), showhide_others);
+ ShowWindow(GetDlgItem(hdlg, IDC_TEXTCOLOR), showhide_others);
+ ShowWindow(GetDlgItem(hdlg, IDC_EDIT_HIDEINTF), showhide_others);
+}
+
+
+BOOL CALLBACK OptionsProc(HWND hdlg,UINT msg,WPARAM wparam,LPARAM lparam) {
+
+ switch(msg) {
+
+ case WM_INITDIALOG:
+ opt_startup = TRUE;
+ LoadSettings();
+ ShowHelp( hdlg, SW_HIDE );
+ SetDlgItemText(hdlg, IDC_EDIT_USEPROXY, opt_useProxy);
+ SetDlgItemText(hdlg, IDC_EDIT_NOPROXY, opt_noProxy);
+ CheckDlgButton(hdlg, IDC_CHECK_MIRANDA, opt_miranda ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hdlg, IDC_CHECK_IE, opt_ie ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hdlg, IDC_CHECK_FIREFOX, opt_firefox ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hdlg, IDC_CHECK_SHOWMYIPMENU, opt_showMyIP ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hdlg, IDC_CHECK_PROXYIPMENU, opt_showProxyIP ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hdlg, IDC_CHECK_ALWAY_RECONNECT, opt_alwayReconnect ? BST_CHECKED : BST_UNCHECKED);
+ SetDlgItemText(hdlg, IDC_EDIT_HIDEINTF, opt_hideIntf);
+ SendDlgItemMessage(hdlg,IDC_BGCOLOR,CPM_SETCOLOUR,0,opt_bgColor);
+ SendDlgItemMessage(hdlg,IDC_TEXTCOLOR,CPM_SETCOLOUR,0,opt_txtColor);
+ CheckDlgButton(hdlg, IDC_CHECK_POPUPS, opt_popups ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hdlg, IDC_CHECK_DEFAULTCOLORS, opt_defaultColors ? BST_CHECKED : BST_UNCHECKED);
+ CheckDlgButton(hdlg, IDC_CHECK_SHOWPROXYSTATUS, opt_showProxyState ? BST_CHECKED : BST_UNCHECKED);
+ EnableWindow(GetDlgItem(hdlg, IDC_CHECK_FIREFOX), Firefox_Installed());
+ EnableWindow(GetDlgItem(hdlg, IDC_CHECK_POPUPS), opt_popupPluginInstalled);
+ EnableWindow(GetDlgItem(hdlg, IDC_BGCOLOR), opt_popupPluginInstalled && opt_popups && !opt_defaultColors);
+ EnableWindow(GetDlgItem(hdlg, IDC_TEXTCOLOR), opt_popupPluginInstalled && opt_popups && !opt_defaultColors);
+ EnableWindow(GetDlgItem(hdlg, IDC_CHECK_DEFAULTCOLORS), opt_popupPluginInstalled && opt_popups);
+ EnableWindow(GetDlgItem(hdlg, IDC_CHECK_SHOWPROXYSTATUS), opt_popupPluginInstalled && opt_popups);
+ ShowWindow(GetDlgItem(hdlg, IDC_RESTARTREQUIRED), opt_not_restarted ? SW_SHOW : SW_HIDE);
+ TranslateDialogDefault(hdlg);
+ opt_startup = FALSE;
+ return 1;
+
+ case WM_NOTIFY:
+ switch (((LPNMHDR)lparam)->code) {
+ case PSN_APPLY:
+ opt_not_restarted = opt_not_restarted || IsDlgButtonChecked(hdlg,IDC_CHECK_PROXYIPMENU) != opt_showProxyIP || IsDlgButtonChecked(hdlg,IDC_CHECK_SHOWMYIPMENU) != opt_showMyIP;
+ ShowWindow(GetDlgItem(hdlg, IDC_RESTARTREQUIRED), opt_not_restarted ? SW_SHOW : SW_HIDE);
+ GetDlgItemText(hdlg,IDC_EDIT_NOPROXY,opt_noProxy,MAX_IPLIST_LENGTH);
+ GetDlgItemText(hdlg,IDC_EDIT_USEPROXY,opt_useProxy,MAX_IPLIST_LENGTH);
+ GetDlgItemText(hdlg,IDC_EDIT_HIDEINTF,opt_hideIntf,MAX_IPLIST_LENGTH);
+ opt_miranda = IsDlgButtonChecked(hdlg,IDC_CHECK_MIRANDA);
+ opt_ie = IsDlgButtonChecked(hdlg,IDC_CHECK_IE);
+ opt_firefox = IsDlgButtonChecked(hdlg,IDC_CHECK_FIREFOX);
+ opt_showMyIP = IsDlgButtonChecked(hdlg,IDC_CHECK_SHOWMYIPMENU);
+ opt_showProxyIP = IsDlgButtonChecked(hdlg,IDC_CHECK_PROXYIPMENU);
+ opt_alwayReconnect = IsDlgButtonChecked(hdlg,IDC_CHECK_ALWAY_RECONNECT);
+ opt_popups = IsDlgButtonChecked(hdlg,IDC_CHECK_POPUPS);
+ opt_defaultColors = IsDlgButtonChecked(hdlg,IDC_CHECK_DEFAULTCOLORS);
+ opt_showProxyState = IsDlgButtonChecked(hdlg,IDC_CHECK_SHOWPROXYSTATUS);
+ opt_bgColor = SendDlgItemMessage(hdlg,IDC_BGCOLOR,CPM_GETCOLOUR,0,0);
+ opt_txtColor = SendDlgItemMessage(hdlg,IDC_TEXTCOLOR,CPM_GETCOLOUR,0,0);
+ SaveSettings();
+ UpdatePopupMenu(opt_popups);
+ return 1;
+ }
+ break;
+
+ case WM_COMMAND:
+ if (opt_startup) return 0;
+ if (HIWORD(wparam)==BN_CLICKED && GetFocus()==(HWND)lparam && LOWORD(wparam)!=IDC_BTN_HELP) SendMessage(GetParent(hdlg),PSM_CHANGED,0,0);
+ switch(LOWORD(wparam)) {
+
+ case IDC_BTN_HELP:
+ ShowHelp( hdlg, help_shown == SW_SHOW ? SW_HIDE : SW_SHOW );
+ break;
+
+ case IDC_EDIT_USEPROXY:
+ case IDC_EDIT_NOPROXY:
+ case IDC_EDIT_HIDEINTF:
+ if (HIWORD(wparam) == EN_CHANGE && (HWND)lparam == GetFocus()) SendMessage(GetParent(hdlg),PSM_CHANGED,0,0);
+ break;
+
+ case IDC_BGCOLOR:
+ case IDC_TEXTCOLOR:
+ if (HIWORD(wparam) == CPN_COLOURCHANGED) SendMessage(GetParent(hdlg), PSM_CHANGED, 0, 0);
+ break;
+
+ case IDC_CHECK_PROXYIPMENU:
+ case IDC_CHECK_SHOWMYIPMENU:
+ ShowWindow(GetDlgItem(hdlg, IDC_RESTARTREQUIRED), opt_not_restarted || (IsDlgButtonChecked(hdlg,IDC_CHECK_PROXYIPMENU) != opt_showProxyIP || IsDlgButtonChecked(hdlg,IDC_CHECK_SHOWMYIPMENU) != opt_showMyIP) ? SW_SHOW : SW_HIDE );
+ break;
+
+ case IDC_CHECK_DEFAULTCOLORS:
+ case IDC_CHECK_POPUPS:
+ if ( ! opt_popupPluginInstalled ) break;
+ EnableWindow(GetDlgItem(hdlg, IDC_BGCOLOR), IsDlgButtonChecked(hdlg,IDC_CHECK_POPUPS) && !IsDlgButtonChecked(hdlg,IDC_CHECK_DEFAULTCOLORS));
+ EnableWindow(GetDlgItem(hdlg, IDC_TEXTCOLOR), IsDlgButtonChecked(hdlg,IDC_CHECK_POPUPS) && !IsDlgButtonChecked(hdlg,IDC_CHECK_DEFAULTCOLORS));
+ EnableWindow(GetDlgItem(hdlg, IDC_CHECK_DEFAULTCOLORS), IsDlgButtonChecked(hdlg,IDC_CHECK_POPUPS));
+ EnableWindow(GetDlgItem(hdlg, IDC_CHECK_SHOWPROXYSTATUS), IsDlgButtonChecked(hdlg,IDC_CHECK_POPUPS));
+ SendMessage(GetParent(hdlg), PSM_CHANGED, 0, 0);
+ break;
+ }
+ break;
+
+ case WM_CLOSE:
+ EndDialog(hdlg,0);
+ break;
+ }
+ return 0;
+}
+
+
+int OptInit(WPARAM wParam,LPARAM lParam) {
+ OPTIONSDIALOGPAGE odp = { 0 };
+
+ //ZeroMemory(&odp,sizeof(odp));
+ //odp.cbSize=sizeof(odp);
+ odp.position=95600;
+ odp.hInstance= g_plugin.getInst();
+ odp.pszTemplate=MAKEINTRESOURCEA(IDD_OPTIONS);
+ odp.pfnDlgProc=OptionsProc;
+ odp.szGroup.w=LPGENW("Network");
+ odp.szTitle.w= LPGENW("proxySwitch");
+ odp.flags=ODPF_BOLDGROUPS | ODPF_UNICODE;
+ g_plugin.addOptions(wParam, &odp);
+
+ return 0;
+}
+
+void LoadSettings(void) {
+ DBVARIANT dbv;
+ if (db_get(NULL, MODULENAME,"UseProxyIPNets",&dbv)) lstrcpy(opt_useProxy, L""); else lstrcpy(opt_useProxy, dbv.pwszVal);
+ db_free(&dbv);
+ if (db_get(NULL, MODULENAME,"NoProxyIPNets",&dbv)) lstrcpy(opt_noProxy, L""); else lstrcpy(opt_noProxy, dbv.pwszVal);
+ db_free(&dbv);
+ if (db_get(NULL, MODULENAME,"HideInterfaces",&dbv)) lstrcpy(opt_hideIntf, L""); else lstrcpy(opt_hideIntf, dbv.pwszVal);
+ db_free(&dbv);
+ opt_miranda = db_get_b(NULL, MODULENAME,"ManageMirandaProxy",TRUE);
+ opt_ie = db_get_b(NULL,MODULENAME,"ManageIEProxy",FALSE);
+ opt_firefox = db_get_b(NULL,MODULENAME,"ManageFirefoxProxy",FALSE) && Firefox_Installed();
+ opt_alwayReconnect = db_get_b(NULL,MODULENAME,"AlwaysReconnect",FALSE);
+ opt_showMyIP = db_get_b(NULL,MODULENAME,"ShowMyIP",TRUE);
+ opt_showProxyIP = db_get_b(NULL,MODULENAME,"ShowProxyIP",TRUE);
+ opt_popups = db_get_b(NULL,MODULENAME,"PopupEnabled",TRUE);
+ opt_defaultColors = db_get_b(NULL,MODULENAME,"PopupDefaultColors",TRUE);
+ opt_showProxyState = db_get_b(NULL,MODULENAME,"ShowProxyStatus",TRUE);
+ opt_bgColor = db_get_dw(NULL,MODULENAME,"PopupBgColor",GetSysColor(COLOR_BTNFACE));
+ opt_txtColor = db_get_dw(NULL,MODULENAME,"PopupTxtColor",GetSysColor(COLOR_WINDOWTEXT));
+}
+
+void SaveSettings(void) {
+ db_set_ws(NULL, MODULENAME, "UseProxyIPNets", opt_useProxy);
+ db_set_ws(NULL, MODULENAME, "NoProxyIPNets", opt_noProxy);
+ db_set_ws(NULL, MODULENAME, "HideInterfaces", opt_hideIntf);
+ db_set_b(NULL, MODULENAME, "ManageMirandaProxy", (BYTE)opt_miranda );
+ db_set_b(NULL, MODULENAME, "ManageIEProxy", (BYTE)opt_ie );
+ db_set_b(NULL, MODULENAME, "ManageFirefoxProxy", (BYTE)opt_firefox );
+ db_set_b(NULL, MODULENAME, "AlwaysReconnect", (BYTE)opt_alwayReconnect);
+ db_set_b(NULL, MODULENAME, "ShowMyIP", (BYTE)opt_showMyIP );
+ db_set_b(NULL, MODULENAME, "ShowProxyIP", (BYTE)opt_showProxyIP );
+ db_set_b(NULL, MODULENAME, "PopupEnabled", (BYTE)opt_popups );
+ db_set_b(NULL, MODULENAME, "PopupDefaultColors", (BYTE)opt_defaultColors );
+ db_set_b(NULL, MODULENAME, "ShowProxyStatus", (BYTE)opt_showProxyState);
+ db_set_dw(NULL, MODULENAME, "PopupBgColor", (DWORD)opt_bgColor );
+ db_set_dw(NULL, MODULENAME, "PopupTxtColor", (DWORD)opt_txtColor );
+}
diff --git a/plugins/ProxySwitch/src/proxy.cpp b/plugins/ProxySwitch/src/proxy.cpp
new file mode 100644
index 0000000000..5e5ad46e65
--- /dev/null
+++ b/plugins/ProxySwitch/src/proxy.cpp
@@ -0,0 +1,304 @@
+/*
+proxySwitch
+
+The plugin watches IP address changes, reports them via popups and adjusts
+the proxy settings of Miranda and Internet Explorer accordingly.
+*/
+
+#include "stdafx.h"
+
+/* ################################################################################ */
+
+int Enum_Settings(const char *szSetting,LPARAM lParam) {
+ PPROXY_SETTINGS ps = (PPROXY_SETTINGS)lParam;
+
+ if ( strcmp(szSetting, "NLUseProxy") != 0 && stricmp(szSetting, "useproxy") != 0 ) return 0;
+
+ if ( ps->count >= ps->_alloc ) {
+ ps->_alloc += 10;
+ ps->item = (PPROXY_SETTING)mir_realloc( ps->item, ps->_alloc * sizeof(PROXY_SETTING) );
+ ZeroMemory( &(ps->item[ps->count]), 10 * sizeof(PROXY_SETTING) );
+ }
+ strncpy( ps->item[ps->count].ModuleName, ps->_current_module, MAXLABELLENGTH-1 );
+ strncpy( ps->item[ps->count].SettingName, szSetting, MAXLABELLENGTH-1 );
+ ps->count++;
+
+ return 0;
+}
+
+int Enum_Modules(const char *szModuleName,DWORD ofsModuleName,LPARAM lParam) {
+ //DBCONTACTENUMSETTINGS e;
+ MCONTACT hContact = NULL;
+
+ ((PPROXY_SETTINGS)lParam)->_current_module = szModuleName;
+
+ //e.pfnEnumProc = Enum_Settings;
+ //e.lParam = lParam;
+ //e.szModule = szModuleName;
+ db_enum_settings(hContact, (DBSETTINGENUMPROC)Enum_Settings, szModuleName, (void*)lParam);
+ //CallService(MS_DB_CONTACT_ENUMSETTINGS, (WPARAM)hContact,(LPARAM)&e);
+
+ return 0;
+}
+
+/* ################################################################################ */
+
+void Create_Proxy_Settings_List ( PPROXY_SETTINGS ps ) {
+
+ ZeroMemory( ps, sizeof(PROXY_SETTINGS) );
+ ps->_alloc = 10;
+ ps->item = (PPROXY_SETTING)mir_alloc( ps->_alloc * sizeof(PROXY_SETTING) );
+ ZeroMemory( ps->item, ps->_alloc * sizeof(PROXY_SETTING) );
+
+ db_enum_modules((DBMODULEENUMPROC)Enum_Modules);
+ //CallService(MS_DB_MODULES_ENUM, (WPARAM)ps, (LPARAM)Enum_Modules );
+
+ ps->_alloc = ps->count+1;
+ ps->item = (PPROXY_SETTING)mir_realloc( ps->item, ps->_alloc * sizeof(PROXY_SETTING) );
+ ZeroMemory( &(ps->item[ps->count]), sizeof(PROXY_SETTING));
+ ps->_current_module = NULL;
+}
+
+/* ################################################################################ */
+
+void Free_Proxy_Settings_List( PPROXY_SETTINGS ps ) {
+ if ( ps->item ) free( ps->item );
+ ZeroMemory( ps, sizeof(PROXY_SETTINGS) );
+}
+
+/* ################################################################################ */
+
+char Get_Miranda_Proxy_Status (void) {
+ PROXY_SETTINGS ps;
+ int i, p;
+ char proxy;
+ proxy = PROXY_NO_CONFIG;
+
+ Create_Proxy_Settings_List( &ps );
+ for ( i = 0 ; i < ps.count ; i++ ) {
+ p = db_get_b(NULL,ps.item[i].ModuleName,ps.item[i].SettingName,FALSE);
+ if (proxy == PROXY_NO_CONFIG) { proxy = p; continue; }
+ if (proxy != p) { proxy = PROXY_MIXED; break; }
+ }
+ Free_Proxy_Settings_List( &ps );
+ return proxy;
+}
+
+/* ################################################################################ */
+
+void Set_Miranda_Proxy_Status (char proxy) {
+ PROXY_SETTINGS ps;
+ NETLIBUSERSETTINGS nlus;
+ int i;
+
+ if ( proxy < 0 ) return;
+ Create_Proxy_Settings_List( &ps );
+ for ( i = 0 ; i < ps.count ; i++ ) {
+ if ( ps.item[i].SettingName[0] != 0 ) db_set_b(NULL,ps.item[i].ModuleName,ps.item[i].SettingName,proxy);
+ ZeroMemory( &nlus, sizeof(nlus) );
+ nlus.cbSize = sizeof(nlus);
+ if (Netlib_GetUserSettingsByName(ps.item[i].ModuleName, &nlus) ) {
+ nlus.useProxy = proxy;
+ nlus.szProxyAuthPassword = NEWSTR_ALLOCA(nlus.szProxyAuthPassword);
+ nlus.szProxyAuthUser = NEWSTR_ALLOCA(nlus.szProxyAuthUser);
+ nlus.szProxyServer = NEWSTR_ALLOCA(nlus.szProxyServer);
+ nlus.szIncomingPorts = NEWSTR_ALLOCA(nlus.szIncomingPorts);
+ nlus.szOutgoingPorts = NEWSTR_ALLOCA(nlus.szOutgoingPorts);
+ Netlib_SetUserSettingsByName(ps.item[i].ModuleName, &nlus);
+ }
+ }
+ Free_Proxy_Settings_List( &ps );
+}
+
+/* ################################################################################ */
+
+char Get_IE_Proxy_Status (void) {
+ INTERNET_PER_CONN_OPTION_LIST list;
+ INTERNET_PER_CONN_OPTION option[1];
+ unsigned long nSize = sizeof(INTERNET_PER_CONN_OPTION_LIST);
+
+ option[0].dwOption = INTERNET_PER_CONN_FLAGS;
+
+ list.dwSize = sizeof(INTERNET_PER_CONN_OPTION_LIST);
+ list.pszConnection = NULL;
+ list.dwOptionCount = 1;
+ list.dwOptionError = 0;
+ list.pOptions = option;
+
+ if(!InternetQueryOption(NULL, INTERNET_OPTION_PER_CONNECTION_OPTION, &list, &nSize)) return -1;
+
+ return
+ option[0].Value.dwValue & PROXY_TYPE_PROXY ? 1 : 0;
+}
+
+/* ################################################################################ */
+
+void Set_IE_Proxy_Status (char proxy) {
+ INTERNET_PER_CONN_OPTION_LIST list;
+ INTERNET_PER_CONN_OPTION option[1];
+ unsigned long nSize = sizeof(INTERNET_PER_CONN_OPTION_LIST);
+
+ if ( proxy < 0 ) return;
+ option[0].dwOption = INTERNET_PER_CONN_FLAGS;
+ option[0].Value.dwValue = proxy ? PROXY_TYPE_PROXY | PROXY_TYPE_DIRECT : PROXY_TYPE_DIRECT;
+
+ list.dwSize = sizeof(INTERNET_PER_CONN_OPTION_LIST);
+ list.pszConnection = NULL;
+ list.dwOptionCount = 1;
+ list.dwOptionError = 0;
+ list.pOptions = option;
+
+ if(!InternetSetOption(NULL, INTERNET_OPTION_PER_CONNECTION_OPTION, &list, nSize)) return;
+
+ InternetQueryOption( NULL, INTERNET_OPTION_SETTINGS_CHANGED , NULL, 0 );
+ InternetQueryOption( NULL, INTERNET_OPTION_REFRESH , NULL, 0 );
+}
+
+/* ################################################################################ */
+
+char Get_Firefox_Proxy_Status (void) {
+ wchar_t path[MAX_PATH];
+ wchar_t prefs[MAX_PATH];
+ char line[500];
+ FILE *fP;
+ struct _stat info;
+ struct _wfinddata_t dir;
+ long hFile;
+ char *setting;
+ int p, proxy;
+
+ ZeroMemory(&info, sizeof(info));
+ proxy = PROXY_NO_CONFIG;
+ if ( ! SHGetSpecialFolderPath(NULL, path, CSIDL_APPDATA, 0) ) return proxy;
+ mir_wstrcat(path, L"\\Mozilla\\Firefox\\Profiles\\*");
+ if( (hFile = _wfindfirst( path, &dir )) != -1L ) {
+ do {
+ if (! (dir.attrib & _A_SUBDIR) || dir.name[0] == '.') continue;
+ mir_wstrcpy(prefs, path); prefs[mir_wstrlen(prefs)-1] = 0;
+ mir_wstrcat(prefs, dir.name);
+ mir_wstrcat(prefs, L"\\prefs.js");
+ if ( (fP = _wfopen(prefs, L"r")) != NULL ) {
+ p = 0;
+ while ( fgets(line, 500, fP) ) {
+ if ( (setting = strstr( line, "user_pref(\"network.proxy.type\",")) != NULL ) {
+ setting += 31;
+ p = atoi(setting);
+ p = p == 3 ? 0 : p > 0;
+ break;
+ }
+ }
+ fclose(fP);
+ proxy = proxy == -2 ? p : (proxy == p ? p : -1);
+ }
+ } while (_wfindnext( hFile, &dir ) == 0);
+ _findclose( hFile );
+ }
+ return proxy;
+}
+
+/* ################################################################################ */
+
+void Set_Firefox_Proxy_Status (char proxy) {
+ wchar_t path[MAX_PATH];
+ wchar_t prefsR[MAX_PATH];
+ wchar_t prefsW[MAX_PATH];
+ char line[500];
+ FILE *fR, *fW;
+ struct _stat info;
+ struct _wfinddata_t dir;
+ long hFile;
+ char done;
+
+ ZeroMemory(&info, sizeof(info));
+ if ( ! SHGetSpecialFolderPath(NULL, path, CSIDL_APPDATA, 0) ) return;
+ mir_wstrcat(path, L"\\Mozilla\\Firefox\\Profiles\\*");
+ if( (hFile = _wfindfirst( path, &dir )) != -1L ) {
+ do {
+ if (! (dir.attrib & _A_SUBDIR) || dir.name[0] == '.') continue;
+ mir_wstrcpy(prefsR, path); prefsR[mir_wstrlen(prefsR)-1] = 0;
+ mir_wstrcat(prefsR, dir.name);
+ mir_wstrcat(prefsR, L"\\prefs.js");
+ done = 0;
+ if ((fR = _wfopen(prefsR, L"r")) != NULL) {
+ mir_wstrcpy(prefsW, prefsR);
+ mir_wstrcat(prefsW, L"~");
+ if ((fW = _wfopen(prefsW, L"w")) != NULL) {
+ while ( fgets(line, 500, fR) ) {
+ if ( strstr( line, "\"network.proxy.type\"")) continue;
+ if ( strstr( line, "\"network.proxy") && ! done) {
+ fprintf(fW, "user_pref(\"network.proxy.type\", %d);\n", proxy);
+ done = 1;
+ }
+ fprintf(fW, "%s", line);
+ }
+ if (! done) {
+ fprintf(fW, "user_pref(\"network.proxy.type\", %d);\n", proxy);
+ done = 1;
+ }
+ fclose(fW);
+ }
+ fclose(fR);
+ }
+ if ( done ) {
+ _wremove(prefsR);
+ _wrename(prefsW, prefsR);
+ }
+ } while (_wfindnext( hFile, &dir ) == 0);
+ _findclose( hFile );
+ }
+}
+
+/* ################################################################################ */
+
+char Firefox_Installed(void) {
+ wchar_t path[MAX_PATH];
+ struct _stat info;
+ ZeroMemory(&info, sizeof(info));
+
+ if ( SHGetSpecialFolderPath(NULL, path, CSIDL_APPDATA, 0) ) {
+ mir_wstrcat(path, L"\\Mozilla\\Firefox\\Profiles");
+ if ( _wstat(path, &info) == 0 && info.st_mode & _S_IFDIR == _S_IFDIR) {
+ return 1;
+ }
+ }
+ return 0;
+}
+
+/* ################################################################################ */
+
+void Disconnect_All_Protocols (PPROTO_SETTINGS settings, int disconnect) {
+ int count, c, i, status;
+ PROTOCOLDESCRIPTOR **plist;
+
+ Proto_EnumProtocols(&c, &plist);
+
+ ZeroMemory( settings, sizeof (PROTO_SETTINGS) );
+ settings->item = (PPROTO_SETTING)mir_alloc( c * sizeof(PROTO_SETTING) );
+ ZeroMemory( settings->item, c * sizeof(PROTO_SETTING) );
+
+ for( i=0 ; i<c ; i++ ) {
+ if ( plist[i]->type != PROTOTYPE_PROTOCOL ) continue;
+ if ( CallProtoService( plist[i]->szName, PS_GETCAPS, PFLAGNUM_2, 0 ) == 0 ) continue;
+ status = CallProtoService( plist[i]->szName, PS_GETSTATUS, 0, 0 );
+ mir_strncpy( settings->item[count].ProtoName, plist[i]->szName, MAXLABELLENGTH-1 );
+ if ( status != ID_STATUS_OFFLINE && disconnect ) {
+ CallProtoService( plist[i]->szName, PS_SETSTATUS, ID_STATUS_OFFLINE, 0 );
+ }
+ if ( status < MAX_CONNECT_RETRIES ) status = ID_STATUS_ONLINE;
+ if ( status == ID_STATUS_OFFLINE ) status = ID_STATUS_ONLINE;
+ settings->item[count].Status = status;
+ count++;
+ }
+ settings->count = count;
+}
+
+/* ################################################################################ */
+
+void Connect_All_Protocols (PPROTO_SETTINGS settings) {
+ int i;
+ for( i=0 ; i<settings->count ; i++ ) {
+ CallProtoService( settings->item[i].ProtoName, PS_SETSTATUS, settings->item[i].Status, 0 );
+ }
+ free( settings->item );
+ ZeroMemory( settings, sizeof (PROTO_SETTINGS) );
+}
diff --git a/plugins/ProxySwitch/src/resource.h b/plugins/ProxySwitch/src/resource.h
new file mode 100644
index 0000000000..8fa07ce325
--- /dev/null
+++ b/plugins/ProxySwitch/src/resource.h
@@ -0,0 +1,41 @@
+//{{NO_DEPENDENCIES}}
+// Microsoft Developer Studio generated include file.
+// Used by proxySwitch.rc
+//
+#define IDI_LOGO 101
+#define IDI_PROXY 102
+#define IDI_NOPROXY 103
+#define IDD_OPTIONS 103
+#define IDI_NOTIF_0 104
+#define IDI_NOTIF_1 105
+#define IDC_EDIT_USEPROXY 1002
+#define IDC_EDIT_NOPROXY 1004
+#define IDC_CHECK_DEFAULTCOLORS 1009
+#define IDC_CHECK_POPUPS 1010
+#define IDC_CHECK_MIRANDA 1014
+#define IDC_CHECK_IE 1015
+#define IDC_CHECK_IE2 1016
+#define IDC_CHECK_FIREFOX 1016
+#define IDC_CHECK_SHOWMYIPMENU 1021
+#define IDC_CHECK_PROXYIPMENU 1022
+#define IDC_CHECK_ALWAY_RECONNECT 1024
+#define IDC_EDIT_HIDEINTF 1025
+#define IDC_RESTARTREQUIRED 1026
+#define IDC_BTN_HELP 1027
+#define IDC_HELP_1 1028
+#define IDC_HELP_2 1029
+#define IDC_HELP_3 1030
+#define IDC_CHECK_SHOWPROXYSTATUS 1031
+#define IDC_TEXTCOLOR 2041
+#define IDC_BGCOLOR 2042
+
+// Next default values for new objects
+//
+#ifdef APSTUDIO_INVOKED
+#ifndef APSTUDIO_READONLY_SYMBOLS
+#define _APS_NEXT_RESOURCE_VALUE 107
+#define _APS_NEXT_COMMAND_VALUE 40001
+#define _APS_NEXT_CONTROL_VALUE 1032
+#define _APS_NEXT_SYMED_VALUE 101
+#endif
+#endif
diff --git a/plugins/ProxySwitch/src/stdafx.cxx b/plugins/ProxySwitch/src/stdafx.cxx
new file mode 100644
index 0000000000..18ec0f9dc4
--- /dev/null
+++ b/plugins/ProxySwitch/src/stdafx.cxx
@@ -0,0 +1,18 @@
+/*
+Copyright (C) 2012-18 Miranda NG team (https://miranda-ng.org)
+
+This program is free software; you can redistribute it and/or
+modify it under the terms of the GNU General Public License
+as published by the Free Software Foundation version 2
+of the License.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#include "stdafx.h" \ No newline at end of file
diff --git a/plugins/ProxySwitch/src/stdafx.h b/plugins/ProxySwitch/src/stdafx.h
new file mode 100644
index 0000000000..b29a511db7
--- /dev/null
+++ b/plugins/ProxySwitch/src/stdafx.h
@@ -0,0 +1,212 @@
+#ifndef proxySwitch_h
+#define proxySwitch_h
+
+#include <winsock2.h>
+#include <windows.h>
+#include <iprtrmib.h>
+#include <iphlpapi.h>
+#include <stdio.h>
+#include <commctrl.h>
+#include <Wininet.h>
+#include <shlobj.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <io.h>
+#include <malloc.h>
+
+#include "newpluginapi.h"
+#include "m_system.h"
+#include "m_options.h"
+#include "m_clist.h"
+#include "m_skin.h"
+#include "m_langpack.h"
+#include "m_popup.h"
+#include "m_database.h"
+#include "m_netlib.h"
+#include "m_utils.h"
+#include "m_protocols.h"
+#include "m_protosvc.h"
+
+#include <m_proxySwitch.h>
+
+#include "resource.h"
+#include "version.h"
+
+#define MODULENAME "ProxySwitch"
+
+struct CMPlugin : public PLUGIN<CMPlugin>
+{
+ CMPlugin();
+
+ int Load() override;
+ int Unload() override;
+};
+
+#define NVL(x) x == NULL ? "" : x
+#define NVLW(x) x == NULL ? L"" : x
+#define ERRORMSG(msg) MessageBox(NULL,msg,_A2T(MODULENAME),MB_OK | MB_ICONERROR);
+#define MAX_IPLIST_LENGTH 500
+
+/**** Types ********************************************************************************/
+
+// structure holding network interface description and information
+typedef struct {
+ char *AdapterName;
+ wchar_t *FriendlyName;
+ char *IPstr;
+ LONG *IP;
+ UCHAR IPcount;
+ HGENMENU MenuItem;
+ BOOL Bound;
+ BOOL Disabled;
+} NETWORK_INTERFACE, *PNETWORK_INTERFACE;
+
+// list of structures holding network interfaces description and information
+typedef struct {
+ PNETWORK_INTERFACE item;
+ UCHAR count;
+} NETWORK_INTERFACE_LIST;
+
+// structure holding an information about local end of an active connections
+typedef struct {
+ ULONG IP;
+ unsigned short Port;
+} ACTIVE_CONNECTION, *PACTIVE_CONNECTION;
+
+// list of structures holding local end of active connections
+typedef struct {
+ PACTIVE_CONNECTION item;
+ UCHAR count;
+ UCHAR _alloc;
+} ACTIVE_CONNECTION_LIST;
+
+
+/**** Global variables *********************************************************************/
+
+extern NETWORK_INTERFACE_LIST NIF_List;
+extern ACTIVE_CONNECTION_LIST Connection_List;
+extern CRITICAL_SECTION csNIF_List;
+extern CRITICAL_SECTION csConnection_List;
+extern HANDLE hEventRebound;
+
+/**** Options ******************************************************************************/
+
+extern wchar_t opt_useProxy[MAX_IPLIST_LENGTH];
+extern wchar_t opt_noProxy[MAX_IPLIST_LENGTH];
+extern wchar_t opt_hideIntf[MAX_IPLIST_LENGTH];
+extern UINT opt_defaultColors;
+extern UINT opt_popups;
+extern UINT opt_showProxyState;
+extern UINT opt_miranda;
+extern UINT opt_ie;
+extern UINT opt_firefox;
+extern UINT opt_showMyIP;
+extern UINT opt_showProxyIP;
+extern UINT opt_alwayReconnect;
+extern UINT opt_startup;
+extern UINT opt_not_restarted;
+extern COLORREF opt_bgColor;
+extern COLORREF opt_txtColor;
+
+extern UINT opt_popupPluginInstalled;
+
+void LoadSettings(void);
+void SaveSettings(void);
+
+/**** Service & Event handlers *************************************************************/
+
+void PopupMyIPAddrs(wchar_t *msg);
+
+int OptInit(WPARAM wParam,LPARAM lParam);
+int Init (WPARAM wParam,LPARAM lParam);
+void UpdateInterfacesMenu(void);
+void UpdatePopupMenu(BOOL State);
+
+/**** Network ******************************************************************************/
+
+#define NETORDER(a) ((((a) & 0xFFL)<<24) | (((a) & 0xFF00L)<<8) | (((a) & 0xFF0000L)>>8) | (((a) & 0xFF000000L)>>24))
+
+#define INCUPD_INTACT 0
+#define INCUPD_CONN_BIND 1
+#define INCUPD_UPDATED 2
+#define INCUPD_CONN_LOST 3
+#define INCUPD(x, y) x = (x) > (y) ? (x) : (y)
+
+#define DIGITS L"0123456789"
+#define CMP_SKIP 0
+#define CMP_MASK 1
+#define CMP_SPAN 2
+#define CMP_END 3
+
+typedef struct {
+ unsigned char cmpType;
+ union { ULONG loIP; ULONG net; };
+ union { ULONG hiIP; ULONG mask; };
+} IP_RANGE, *PIP_RANGE;
+
+typedef struct {
+ PIP_RANGE item;
+ UCHAR count;
+} IP_RANGE_LIST;
+
+void IP_WatchDog (void *arg);
+
+int Create_NIF_List (NETWORK_INTERFACE_LIST *list);
+int Create_NIF_List_Ex (NETWORK_INTERFACE_LIST *list);
+BOOL Compare_NIF_Lists (NETWORK_INTERFACE_LIST list1, NETWORK_INTERFACE_LIST list2);
+int IncUpdate_NIF_List (NETWORK_INTERFACE_LIST *trg, NETWORK_INTERFACE_LIST src);
+wchar_t *Print_NIF_List (NETWORK_INTERFACE_LIST list, wchar_t *msg);
+wchar_t *Print_NIF (PNETWORK_INTERFACE nif);
+void Free_NIF (PNETWORK_INTERFACE nif);
+void Free_NIF_List (NETWORK_INTERFACE_LIST *list);
+
+int Create_Range_List (IP_RANGE_LIST *list, wchar_t *str, BOOL prioritized );
+int Match_Range_List (IP_RANGE_LIST range, NETWORK_INTERFACE_LIST ip);
+void Free_Range_List (IP_RANGE_LIST *list);
+
+int ManageConnections (WPARAM wParam,LPARAM lParam);
+void UnboundConnections (LONG *OldIP, LONG *NewIP);
+
+/**** Proxy/Connection Modification and Query routines *************************************/
+
+#define MAXLABELLENGTH 64
+
+#define PROXY_NO_CONFIG -2
+#define PROXY_MIXED -1
+#define PROXY_DISABLED 0
+#define PROXY_ENABLED 1
+
+typedef struct {
+ char ModuleName[MAXLABELLENGTH];
+ char SettingName[MAXLABELLENGTH];
+} PROXY_SETTING, *PPROXY_SETTING;
+
+typedef struct {
+ PPROXY_SETTING item;
+ UCHAR count;
+ const char *_current_module;
+ UCHAR _alloc;
+} PROXY_SETTINGS, *PPROXY_SETTINGS;
+
+typedef struct {
+ char ProtoName[MAXLABELLENGTH];
+ DWORD Status;
+} PROTO_SETTING, *PPROTO_SETTING;
+
+typedef struct {
+ PPROTO_SETTING item;
+ UCHAR count;
+} PROTO_SETTINGS, *PPROTO_SETTINGS;
+
+void Create_Proxy_Settings_List ( PPROXY_SETTINGS ps );
+void Free_Proxy_Settings_List( PPROXY_SETTINGS ps );
+char Get_Miranda_Proxy_Status (void);
+void Set_Miranda_Proxy_Status (char proxy);
+char Get_IE_Proxy_Status (void);
+void Set_IE_Proxy_Status (char proxy);
+char Get_Firefox_Proxy_Status (void);
+void Set_Firefox_Proxy_Status (char proxy);
+char Firefox_Installed(void);
+void Disconnect_All_Protocols (PPROTO_SETTINGS settings, int disconnect);
+void Connect_All_Protocols (PPROTO_SETTINGS settings);
+#endif
diff --git a/plugins/ProxySwitch/src/version.h b/plugins/ProxySwitch/src/version.h
new file mode 100644
index 0000000000..d2fc801bf4
--- /dev/null
+++ b/plugins/ProxySwitch/src/version.h
@@ -0,0 +1,13 @@
+#define __MAJOR_VERSION 1
+#define __MINOR_VERSION 0
+#define __RELEASE_NUM 0
+#define __BUILD_NUM 1
+
+#include <stdver.h>
+
+#define __PLUGIN_NAME "ProxySwitch"
+#define __FILENAME "ProxySwitch.dll"
+#define __DESCRIPTION "The plugin watches IP address changes, displays popups, and adjusts the proxy settings of Miranda, Internet Explorer and Firefox."
+#define __AUTHOR "Petr Smejkal"
+#define __AUTHORWEB "https://miranda-ng.org/p/ProxySwitch/"
+#define __COPYRIGHT "© 2005 Petr Smejkal"