I'm implementing a WireGuard custom client using wireguard.dll for Windows NT. I took the following example as a basis: https://git.zx2c4.com/wireguard-nt/tree/example/example.c I need to create a VPN connection with an existing server. Firstly I create the Config structure:
struct Config
{
WIREGUARD_INTERFACE Interface;
WIREGUARD_PEER Server;
WIREGUARD_ALLOWED_IP FirstPeerAllowedIP1;
};
After in main() I create an adapter and fill configuration with my data:
WIREGUARD_ADAPTER_HANDLE Adapter = WireGuardCreateAdapter(L"AdapterName", L"TunelType", NULL);
if (!Adapter)
{
std::cout << "Error of adapter creating\n";
FreeLibrary(WireGuardDll);
return 1;
}
else {
std::cout << "That's OK\n";
}
Config config;
CHAR interfacePrivateKey[] = "privatekey";
std::vector<BYTE> interfacePrivateKeyBytes = base64_decode(interfacePrivateKey); // base64_decode is a custom function. But it works correctly
CHAR serverPublicKeyStr[46] = "publicKey";
std::vector<BYTE> serverPublicKeyBytes = base64_decode(serverPublicKeyStr);
config.Interface.Flags = WIREGUARD_INTERFACE_HAS_PRIVATE_KEY;
memcpy(config.Interface.PrivateKey, &interfacePrivateKeyBytes[0], WIREGUARD_KEY_LENGTH);
config.Interface.PeersCount = 1;
config.Interface.ListenPort = NULL;
config.Server.Flags = static_cast<WIREGUARD_PEER_FLAG>(WIREGUARD_PEER_HAS_PUBLIC_KEY | WIREGUARD_PEER_HAS_ENDPOINT);
memcpy(config.Server.PublicKey, &serverPublicKeyBytes[0], WIREGUARD_KEY_LENGTH);
config.Server.Endpoint.si_family = AF_INET;
config.Server.Endpoint.Ipv4.sin_family = AF_INET;
config.Server.Endpoint.Ipv4.sin_port = htons(aPortNumber); // server port
std::cout << inet_pton(AF_INET, "x.x.x.x", &config.Server.Endpoint.Ipv4.sin_addr) << std::endl;
config.Server.AllowedIPsCount = 16;
config.Server.PersistentKeepalive = 25;
config.FirstPeerAllowedIP1.AddressFamily = AF_INET;
std::cout << inet_pton(AF_INET, "x.x.0.0", &config.FirstPeerAllowedIP1.Address) << std::endl;
config.FirstPeerAllowedIP1.Cidr = static_cast<BYTE>(16);
After that I call WireGuardSetConfiguration() and it returns NULL:(
if (!WireGuardSetConfiguration(Adapter, &config.Interface, sizeof(Config)))
{
std::cout << "Config setting failed\n" << std::endl;
FreeLibrary(WireGuardDll);
return 1;
}
The strangest thing is that if I clear config.Interface before configuration setting, it doesn't return NULL.
config.Interface = ...
ZeroMemory(&config.Interface, sizeof(config.Interface));
config.Server = ....
if (!WireGuardSetConfiguration(Adapter, &config.Interface, sizeof(Config))) ...
What could be the problem? Maybe someone knows how to solve it? I would be grateful for any help. Thanks!