]> git.ipfire.org Git - thirdparty/openvpn.git/commitdiff
wintun: remove SYSTEM elevation hack
authorLev Stipakov <lev@openvpn.net>
Fri, 24 Jul 2020 10:48:41 +0000 (13:48 +0300)
committerGert Doering <gert@greenie.muc.de>
Sat, 25 Jul 2020 08:10:38 +0000 (10:10 +0200)
As discussed a while ago on the mailing list and
community meetings, having SYSTEM elevation hack
inside openvpn code considered harmful.

Since interactive service is the recommended way
of using openvpn on Windows, limiting wintun usage to
interactive service should not be an issue.

Remove elevation hack code and provide an error message
telling user to use interactive service or do SYSTEM
elevation himself via psexec.

Move implementation of register_ring_buffers() to header
amd delete ring_buffer.c.

Signed-off-by: Lev Stipakov <lev@openvpn.net>
Acked-by: Gert Doering <gert@greenie.muc.de>
Message-Id: <20200724104841.89-1-lstipakov@gmail.com>
URL: https://www.mail-archive.com/openvpn-devel@lists.sourceforge.net/msg20567.html
Signed-off-by: Gert Doering <gert@greenie.muc.de>
src/openvpn/Makefile.am
src/openvpn/openvpn.vcxproj
src/openvpn/openvpn.vcxproj.filters
src/openvpn/ring_buffer.c [deleted file]
src/openvpn/ring_buffer.h
src/openvpn/tun.c
src/openvpn/win32.c
src/openvpnserv/Makefile.am
src/openvpnserv/openvpnserv.vcxproj
src/openvpnserv/openvpnserv.vcxproj.filters

index d2338e79b0436ba025d3313bca71d8422f1f73b3..37b002c614fbf80a4ed472e0e1aa2786e9db232d 100644 (file)
@@ -142,6 +142,6 @@ openvpn_LDADD = \
        $(OPTIONAL_DL_LIBS) \
        $(OPTIONAL_INOTIFY_LIBS)
 if WIN32
-openvpn_SOURCES += openvpn_win32_resources.rc block_dns.c block_dns.h ring_buffer.c ring_buffer.h
+openvpn_SOURCES += openvpn_win32_resources.rc block_dns.c block_dns.h ring_buffer.h
 openvpn_LDADD += -lgdi32 -lws2_32 -lwininet -lcrypt32 -liphlpapi -lwinmm -lfwpuclnt -lrpcrt4 -lncrypt -lsetupapi
 endif
index 2da2b870085434c201a183d43c53dd2b630f58b0..5367979de9cf0dcd646d74ec0d4f8e6fa94cacb7 100644 (file)
     <ClCompile Include="ps.c" />
     <ClCompile Include="push.c" />
     <ClCompile Include="reliable.c" />
-    <ClCompile Include="ring_buffer.c" />
     <ClCompile Include="route.c" />
     <ClCompile Include="run_command.c" />
     <ClCompile Include="schedule.c" />
index af2f0bcf83c5cbc1588e3c5fcd384a8ce57879a0..cf5748c7db198acfd6cfaf376325b5cd6061b8a3 100644 (file)
     <ClCompile Include="vlan.c">
       <Filter>Source Files</Filter>
     </ClCompile>
-    <ClCompile Include="ring_buffer.c">
-      <Filter>Source Files</Filter>
-    </ClCompile>
     <ClCompile Include="ssl_ncp.c">
       <Filter>Source Files</Filter>
     </ClCompile>
diff --git a/src/openvpn/ring_buffer.c b/src/openvpn/ring_buffer.c
deleted file mode 100644 (file)
index 8c81dc4..0000000
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- *  OpenVPN -- An application to securely tunnel IP networks
- *             over a single UDP port, with support for SSL/TLS-based
- *             session authentication and key exchange,
- *             packet encryption, packet authentication, and
- *             packet compression.
- *
- *  Copyright (C) 2002-2019 OpenVPN Inc <sales@openvpn.net>
- *                2019 Lev Stipakov <lev@openvpn.net>
- *
- *  This program is free software; you can redistribute it and/or modify
- *  it under the terms of the GNU General Public License version 2
- *  as published by the Free Software Foundation.
- *
- *  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, write to the Free Software Foundation, Inc.,
- *  51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
- */
-
-#include "ring_buffer.h"
-
-#ifdef _WIN32
-
-bool
-register_ring_buffers(HANDLE device,
-                      struct tun_ring *send_ring,
-                      struct tun_ring *receive_ring,
-                      HANDLE send_tail_moved,
-                      HANDLE receive_tail_moved)
-{
-    struct tun_register_rings rr;
-    BOOL res;
-    DWORD bytes_returned;
-
-    ZeroMemory(&rr, sizeof(rr));
-
-    rr.send.ring = send_ring;
-    rr.send.ring_size = sizeof(struct tun_ring);
-    rr.send.tail_moved = send_tail_moved;
-
-    rr.receive.ring = receive_ring;
-    rr.receive.ring_size = sizeof(struct tun_ring);
-    rr.receive.tail_moved = receive_tail_moved;
-
-    res = DeviceIoControl(device, TUN_IOCTL_REGISTER_RINGS, &rr, sizeof(rr),
-                          NULL, 0, &bytes_returned, NULL);
-
-    return res != FALSE;
-}
-
-#endif /* ifdef _WIN32 */
\ No newline at end of file
index af46f1065bf13753fe1c06c95173a174bec8ba2a..4293f633203697a397e5983b5ca1a17693d3adef 100644 (file)
@@ -94,11 +94,32 @@ struct TUN_PACKET
  *                            that data has been written to receive ring
  * @return                    true if registration is successful, false otherwise - use GetLastError()
  */
-bool register_ring_buffers(HANDLE device,
-                           struct tun_ring *send_ring,
-                           struct tun_ring *receive_ring,
-                           HANDLE send_tail_moved,
-                           HANDLE receive_tail_moved);
+static bool
+register_ring_buffers(HANDLE device,
+                      struct tun_ring *send_ring,
+                      struct tun_ring *receive_ring,
+                      HANDLE send_tail_moved,
+                      HANDLE receive_tail_moved)
+{
+    struct tun_register_rings rr;
+    BOOL res;
+    DWORD bytes_returned;
+
+    ZeroMemory(&rr, sizeof(rr));
+
+    rr.send.ring = send_ring;
+    rr.send.ring_size = sizeof(struct tun_ring);
+    rr.send.tail_moved = send_tail_moved;
+
+    rr.receive.ring = receive_ring;
+    rr.receive.ring_size = sizeof(struct tun_ring);
+    rr.receive.tail_moved = receive_tail_moved;
+
+    res = DeviceIoControl(device, TUN_IOCTL_REGISTER_RINGS, &rr, sizeof(rr),
+      NULL, 0, &bytes_returned, NULL);
+
+    return res != FALSE;
+}
 
 #endif /* ifndef OPENVPN_RING_BUFFER_H */
 #endif /* ifdef _WIN32 */
index e96368ca7078d7d270747d7d9378dcbd3eef6755..82d96927c600ba96d4c4f4d7136aed164b725b53 100644 (file)
@@ -6148,35 +6148,10 @@ wintun_register_ring_buffer(struct tuntap *tt, const char *device_guid)
     }
     else
     {
-        if (!impersonate_as_system())
-        {
-            msg(M_FATAL, "ERROR:  Failed to impersonate as SYSTEM, make sure process is running under privileged account");
-        }
-        if (!register_ring_buffers(tt->hand,
-                                   tt->wintun_send_ring,
-                                   tt->wintun_receive_ring,
-                                   tt->rw_handle.read,
-                                   tt->rw_handle.write))
-        {
-            switch (GetLastError())
-            {
-                case ERROR_ACCESS_DENIED:
-                    msg(M_FATAL, "Access denied registering ring buffers. Is this process run as SYSTEM?");
-                    break;
-
-                case ERROR_ALREADY_INITIALIZED:
-                    msg(M_NONFATAL, "Adapter %s is already in use", device_guid);
-                    break;
-
-                default:
-                    msg(M_NONFATAL | M_ERRNO, "Failed to register ring buffers");
-            }
-            ret = false;
-        }
-        if (!RevertToSelf())
-        {
-            msg(M_FATAL, "ERROR:  RevertToSelf error: %lu", GetLastError());
-        }
+        msg(M_FATAL, "ERROR:  Wintun requires SYSTEM privileges and therefore "
+                     "should be used with interactive service. If you want to "
+                     "use openvpn from command line, you need to do SYSTEM "
+                     "elevation yourself (for example with psexec).");
     }
 
     return ret;
index 303bd7af1695d97e6f2b05bebb2d19288d3dbc50..7e91316573fc1b9082727d467f22a2ac5394de9e 100644 (file)
@@ -1509,99 +1509,4 @@ send_msg_iservice(HANDLE pipe, const void *data, size_t size,
     return ret;
 }
 
-bool
-impersonate_as_system()
-{
-    HANDLE thread_token, process_snapshot, winlogon_process, winlogon_token, duplicated_token;
-    PROCESSENTRY32 entry;
-    BOOL ret;
-    DWORD pid = 0;
-    TOKEN_PRIVILEGES privileges;
-
-    CLEAR(entry);
-    CLEAR(privileges);
-
-    entry.dwSize = sizeof(PROCESSENTRY32);
-
-    privileges.PrivilegeCount = 1;
-    privileges.Privileges->Attributes = SE_PRIVILEGE_ENABLED;
-
-    if (!LookupPrivilegeValue(NULL, SE_DEBUG_NAME, &privileges.Privileges[0].Luid))
-    {
-        return false;
-    }
-
-    if (!ImpersonateSelf(SecurityImpersonation))
-    {
-        return false;
-    }
-
-    if (!OpenThreadToken(GetCurrentThread(), TOKEN_ADJUST_PRIVILEGES, FALSE, &thread_token))
-    {
-        RevertToSelf();
-        return false;
-    }
-    if (!AdjustTokenPrivileges(thread_token, FALSE, &privileges, sizeof(privileges), NULL, NULL))
-    {
-        CloseHandle(thread_token);
-        RevertToSelf();
-        return false;
-    }
-    CloseHandle(thread_token);
-
-    process_snapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
-    if (process_snapshot == INVALID_HANDLE_VALUE)
-    {
-        RevertToSelf();
-        return false;
-    }
-    for (ret = Process32First(process_snapshot, &entry); ret; ret = Process32Next(process_snapshot, &entry))
-    {
-        if (!_stricmp(entry.szExeFile, "winlogon.exe"))
-        {
-            pid = entry.th32ProcessID;
-            break;
-        }
-    }
-    CloseHandle(process_snapshot);
-    if (!pid)
-    {
-        RevertToSelf();
-        return false;
-    }
-
-    winlogon_process = OpenProcess(PROCESS_QUERY_INFORMATION, FALSE, pid);
-    if (!winlogon_process)
-    {
-        RevertToSelf();
-        return false;
-    }
-
-    if (!OpenProcessToken(winlogon_process, TOKEN_IMPERSONATE | TOKEN_DUPLICATE, &winlogon_token))
-    {
-        CloseHandle(winlogon_process);
-        RevertToSelf();
-        return false;
-    }
-    CloseHandle(winlogon_process);
-
-    if (!DuplicateToken(winlogon_token, SecurityImpersonation, &duplicated_token))
-    {
-        CloseHandle(winlogon_token);
-        RevertToSelf();
-        return false;
-    }
-    CloseHandle(winlogon_token);
-
-    if (!SetThreadToken(NULL, duplicated_token))
-    {
-        CloseHandle(duplicated_token);
-        RevertToSelf();
-        return false;
-    }
-    CloseHandle(duplicated_token);
-
-    return true;
-}
-
 #endif /* ifdef _WIN32 */
index f8d3319cc793b009a13ec47c402f2345a2047254..5dc38c9bf93c942f79f0dd03d079179f83fdf79b 100644 (file)
@@ -37,4 +37,4 @@ openvpnserv_SOURCES = \
        validate.c validate.h \
        $(top_srcdir)/src/openvpn/block_dns.c $(top_srcdir)/src/openvpn/block_dns.h \
        openvpnserv_resources.rc \
-       $(top_srcdir)/src/openvpn/ring_buffer.c $(top_srcdir)/src/openvpn/ring_buffer.h
+       $(top_srcdir)/src/openvpn/ring_buffer.h
index c5a34b87c5f3746b081a715403507536e0d80f07..5e973df41ddc693b5bc144cf496b4789ed11a59d 100644 (file)
     </Link>
   </ItemDefinitionGroup>
   <ItemGroup>
-    <ClCompile Include="..\openvpn\ring_buffer.c" />
     <ClCompile Include="automatic.c" />
     <ClCompile Include="common.c" />
     <ClCompile Include="interactive.c" />
index 3cb14ef6254d2eb1fa43314d326196ffcef79920..41ad3e8067016d394b0c52c15c698637b263a586 100644 (file)
@@ -33,9 +33,6 @@
     <ClCompile Include="..\openvpn\block_dns.c">
       <Filter>Source Files</Filter>
     </ClCompile>
-    <ClCompile Include="..\openvpn\ring_buffer.c">
-      <Filter>Source Files</Filter>
-    </ClCompile>
   </ItemGroup>
   <ItemGroup>
     <ClInclude Include="service.h">