1 /* 2 * Copyright (c)2019 ZeroTier, Inc. 3 * 4 * Use of this software is governed by the Business Source License included 5 * in the LICENSE.TXT file in the project's root directory. 6 * 7 * Change Date: 2025-01-01 8 * 9 * On the date above, in accordance with the Business Source License, use 10 * of this software will be governed by version 2.0 of the Apache License. 11 */ 12 /****/ 13 14 #ifndef ZT_WINDOWSETHERNETTAP_HPP 15 #define ZT_WINDOWSETHERNETTAP_HPP 16 17 #include <stdio.h> 18 #include <stdlib.h> 19 20 #include <ifdef.h> 21 22 #include <string> 23 #include <queue> 24 #include <stdexcept> 25 26 #include "../node/Constants.hpp" 27 #include "../node/Mutex.hpp" 28 #include "../node/MulticastGroup.hpp" 29 #include "../node/InetAddress.hpp" 30 #include "../osdep/Thread.hpp" 31 #include "EthernetTap.hpp" 32 33 namespace ZeroTier { 34 35 class WindowsEthernetTap : public EthernetTap 36 { 37 public: 38 /** 39 * Installs a new instance of the ZT tap driver 40 * 41 * @param pathToInf Path to zttap driver .inf file 42 * @param deviceInstanceId Buffer to fill with device instance ID on success (and if SetupDiGetDeviceInstanceIdA succeeds, which it should) 43 * @return Empty string on success, otherwise an error message 44 */ 45 static std::string addNewPersistentTapDevice(const char *pathToInf,std::string &deviceInstanceId); 46 47 /** 48 * Uninstalls all persistent tap devices that have legacy drivers 49 * 50 * @return Empty string on success, otherwise an error message 51 */ 52 static std::string destroyAllLegacyPersistentTapDevices(); 53 54 /** 55 * Uninstalls all persistent tap devices on the system 56 * 57 * @return Empty string on success, otherwise an error message 58 */ 59 static std::string destroyAllPersistentTapDevices(); 60 61 /** 62 * Uninstalls a specific persistent tap device by instance ID 63 * 64 * @param instanceId Device instance ID 65 * @return Empty string on success, otherwise an error message 66 */ 67 static std::string deletePersistentTapDevice(const char *instanceId); 68 69 /** 70 * Disable a persistent tap device by instance ID 71 * 72 * @param instanceId Device instance ID 73 * @param enabled Enable device? 74 * @return True if device was found and disabled 75 */ 76 static bool setPersistentTapDeviceState(const char *instanceId,bool enabled); 77 78 WindowsEthernetTap( 79 const char *hp, 80 const MAC &mac, 81 unsigned int mtu, 82 unsigned int metric, 83 uint64_t nwid, 84 const char *friendlyName, 85 void (*handler)(void *,void *,uint64_t,const MAC &,const MAC &,unsigned int,unsigned int,const void *,unsigned int), 86 void *arg); 87 88 virtual ~WindowsEthernetTap(); 89 90 virtual void setEnabled(bool en); 91 virtual bool enabled() const; 92 virtual bool addIp(const InetAddress &ip); 93 virtual bool removeIp(const InetAddress &ip); 94 virtual std::vector<InetAddress> ips() const; 95 virtual void put(const MAC &from,const MAC &to,unsigned int etherType,const void *data,unsigned int len); 96 virtual std::string deviceName() const; 97 virtual void setFriendlyName(const char *friendlyName); 98 virtual std::string friendlyName() const; 99 virtual void scanMulticastGroups(std::vector<MulticastGroup> &added,std::vector<MulticastGroup> &removed); 100 virtual void setMtu(unsigned int mtu); 101 virtual void setDns(const char* domain, const std::vector<InetAddress> &servers); 102 luid() const103 inline const NET_LUID &luid() const { return _deviceLuid; } guid() const104 inline const GUID &guid() const { return _deviceGuid; } instanceId() const105 inline const std::string &instanceId() const { return _deviceInstanceId; } 106 NET_IFINDEX interfaceIndex() const; 107 108 void threadMain() 109 throw(); 110 isInitialized() const111 bool isInitialized() const { return _initialized; }; 112 113 private: 114 NET_IFINDEX _getDeviceIndex(); // throws on failure 115 std::vector<std::string> _getRegistryIPv4Value(const char *regKey); 116 void _setRegistryIPv4Value(const char *regKey,const std::vector<std::string> &value); 117 void _syncIps(); 118 119 void (*_handler)(void *,void *,uint64_t,const MAC &,const MAC &,unsigned int,unsigned int,const void *,unsigned int); 120 void *_arg; 121 MAC _mac; 122 uint64_t _nwid; 123 volatile unsigned int _mtu; 124 Thread _thread; 125 126 volatile HANDLE _tap; 127 HANDLE _injectSemaphore; 128 129 GUID _deviceGuid; 130 NET_LUID _deviceLuid; 131 std::string _netCfgInstanceId; 132 std::string _deviceInstanceId; 133 std::string _mySubkeyName; 134 std::string _friendlyName; 135 Mutex _friendlyName_m; 136 137 std::vector<InetAddress> _assignedIps; // IPs assigned with addIp 138 Mutex _assignedIps_m; 139 140 std::vector<MulticastGroup> _multicastGroups; 141 142 struct _InjectPending 143 { 144 unsigned int len; 145 char data[ZT_MAX_MTU + 32]; 146 }; 147 std::queue<_InjectPending> _injectPending; 148 Mutex _injectPending_m; 149 150 std::string _pathToHelpers; 151 152 volatile bool _run; 153 volatile bool _initialized; 154 volatile bool _enabled; 155 }; 156 157 } // namespace ZeroTier 158 159 #endif 160