231 lines
7.2 KiB
C++
231 lines
7.2 KiB
C++
#include "pch.h"
|
|
#include "tunnel.h"
|
|
#include "usrerr.h"
|
|
#include <strsafe.h>
|
|
#include <tchar.h>
|
|
|
|
#include "globalcfg.h"
|
|
#include "misc.h"
|
|
|
|
#define WINENVBUF_SIZE (4096)
|
|
#define CONFIG_FILE_NAME TEXT("tunnelsdk.ini")
|
|
#define CFG_WIREGUARD_SECTION TEXT("WireGuard")
|
|
#define CFG_WIREGUARD_PATH TEXT("WireGuardExe")
|
|
#define CFG_WG_PATH TEXT("WgExe")
|
|
|
|
|
|
TUNNEL_API int GenerateWireguardKeyPairs(TCHAR* pPubKey, int pubkeySize, TCHAR* pPrivKey, int privKeySize)
|
|
{
|
|
int ret;
|
|
TCHAR cmdBuffer[MAX_PATH];
|
|
TCHAR cmdResult[MAX_PATH];
|
|
PSDK_CONFIG pCfg = GetGlobalCfgInfo();
|
|
|
|
// WireGuard 不存在或者未配置目录
|
|
if (!pCfg->wireguardCfg.wgExists || !pCfg->wireguardCfg.wireguardExists)
|
|
{
|
|
return -ERR_ITEM_UNEXISTS;
|
|
}
|
|
|
|
memset(cmdBuffer, 0, MAX_PATH);
|
|
memset(cmdResult, 0, MAX_PATH);
|
|
|
|
StringCbPrintf(cmdBuffer, MAX_PATH, TEXT("cmd.exe /C \"%s\" genkey"), pCfg->wireguardCfg.wgPath);
|
|
|
|
if ((ret = RunPipeCmd(cmdBuffer, cmdResult, MAX_PATH)) != ERR_SUCCESS)
|
|
{
|
|
SPDLOG_ERROR("Run command [{0}] error: {1}", cmdBuffer, ret);
|
|
return -ERR_CALL_SHELL;
|
|
}
|
|
|
|
SPDLOG_DEBUG("Run command [{0}] resutl \'{1}\'", cmdBuffer, cmdResult);
|
|
|
|
StringCbCopy(pPrivKey, privKeySize, cmdResult);
|
|
memset(cmdBuffer, 0, MAX_PATH);
|
|
StringCbPrintf(cmdBuffer, MAX_PATH, TEXT("cmd.exe /C echo %s | \"%s\" pubkey"), cmdResult,
|
|
pCfg->wireguardCfg.wgPath);
|
|
|
|
memset(cmdResult, 0, MAX_PATH);
|
|
if ((ret = RunPipeCmd(cmdBuffer, cmdResult, MAX_PATH)) != ERR_SUCCESS)
|
|
{
|
|
SPDLOG_ERROR("Run command [{0}] error: {1}", cmdBuffer, ret);
|
|
return -ERR_CALL_SHELL;
|
|
}
|
|
|
|
StringCbCopy(pPubKey, pubkeySize, cmdResult);
|
|
SPDLOG_DEBUG("Run command [{0}] resutl \'{1}\'", cmdBuffer, cmdResult);
|
|
|
|
return ERR_SUCCESS;
|
|
}
|
|
|
|
TUNNEL_API int SetWireguardPath(TCHAR* pPath)
|
|
{
|
|
WIN32_FIND_DATA FindFileData;
|
|
HANDLE hFind;
|
|
|
|
if (pPath == nullptr)
|
|
{
|
|
return -ERR_INPUT_PARAMS;
|
|
}
|
|
|
|
hFind = FindFirstFile(pPath, &FindFileData);
|
|
|
|
if (hFind != INVALID_HANDLE_VALUE)
|
|
{
|
|
TCHAR path[MAX_PATH] = {0};
|
|
TCHAR wgPath[MAX_PATH];
|
|
|
|
StringCbPrintf(path, MAX_PATH, TEXT("%s\\%s"), GetGlobalCfgInfo()->workDirectory, CONFIG_FILE_NAME);
|
|
|
|
SPDLOG_DEBUG(TEXT("Used configure file:{0}"), path);
|
|
|
|
WritePrivateProfileString(CFG_WIREGUARD_SECTION, CFG_WIREGUARD_PATH, pPath, path);
|
|
SPDLOG_DEBUG(TEXT("Save configure: {1} --> {0}"), pPath, CFG_WIREGUARD_PATH);
|
|
|
|
StringCbCopy(wgPath, MAX_PATH, pPath);
|
|
TCHAR* pIndex = _tcsrchr(wgPath, '\\');
|
|
|
|
if (pIndex)
|
|
{
|
|
*pIndex = 0;
|
|
StringCbCat(wgPath, MAX_PATH, "\\wg.exe");
|
|
WritePrivateProfileString(CFG_WIREGUARD_SECTION, CFG_WG_PATH, wgPath, path);
|
|
SPDLOG_DEBUG(TEXT("Save configure: {1} --> {0}"), wgPath, CFG_WG_PATH);
|
|
}
|
|
|
|
return ERR_SUCCESS;
|
|
}
|
|
else
|
|
{
|
|
return -ERR_ITEM_UNEXISTS;
|
|
}
|
|
}
|
|
|
|
TUNNEL_API int FindWireguardExe(TCHAR* pFullPath, int maxSize)
|
|
{
|
|
TCHAR path[MAX_PATH];
|
|
TCHAR wrieguardPath[MAX_PATH];
|
|
WIN32_FIND_DATA FindFileData;
|
|
HANDLE hFind;
|
|
DWORD dwRet, dwErr;
|
|
LPSTR pEnvBuf;
|
|
TCHAR *token, *p = nullptr;
|
|
|
|
memset(path, 0, MAX_PATH);
|
|
StringCbPrintf(path, MAX_PATH, TEXT("%s\\%s"), GetGlobalCfgInfo()->workDirectory, CONFIG_FILE_NAME);
|
|
GetPrivateProfileString(CFG_WIREGUARD_SECTION,CFG_WIREGUARD_PATH,TEXT(""), wrieguardPath,MAX_PATH, path);
|
|
|
|
hFind = FindFirstFile(wrieguardPath, &FindFileData);
|
|
if (hFind != INVALID_HANDLE_VALUE)
|
|
{
|
|
if (pFullPath && maxSize > 0)
|
|
{
|
|
StringCbCopy(pFullPath, maxSize, wrieguardPath);
|
|
}
|
|
|
|
StringCbCopy(GetGlobalCfgInfo()->wireguardCfg.wireguardPath, MAX_PATH, wrieguardPath);
|
|
GetGlobalCfgInfo()->wireguardCfg.wireguardExists = TRUE;
|
|
|
|
SPDLOG_DEBUG(TEXT("Ini found WireGuard at: {0}"), wrieguardPath);
|
|
|
|
memset(path, 0, MAX_PATH);
|
|
StringCbPrintf(path, MAX_PATH, TEXT("%s\\%s"), GetGlobalCfgInfo()->workDirectory, CONFIG_FILE_NAME);
|
|
GetPrivateProfileString(CFG_WIREGUARD_SECTION,CFG_WG_PATH,TEXT(""), wrieguardPath,MAX_PATH, path);
|
|
|
|
hFind = FindFirstFile(wrieguardPath, &FindFileData);
|
|
if (hFind != INVALID_HANDLE_VALUE)
|
|
{
|
|
StringCbCopy(GetGlobalCfgInfo()->wireguardCfg.wgPath, MAX_PATH, wrieguardPath);
|
|
GetGlobalCfgInfo()->wireguardCfg.wgExists = TRUE;
|
|
SPDLOG_DEBUG(TEXT("Ini found WireGuard Tools at: {0}"), wrieguardPath);
|
|
}
|
|
|
|
return ERR_SUCCESS;
|
|
}
|
|
|
|
pEnvBuf = static_cast<LPSTR>(malloc(WINENVBUF_SIZE));
|
|
if (nullptr == pEnvBuf)
|
|
{
|
|
SPDLOG_ERROR(TEXT("Malloc {0} bytes memory error"), WINENVBUF_SIZE);
|
|
return -ERR_MALLOC_MEMORY;
|
|
}
|
|
|
|
dwRet = GetEnvironmentVariable(TEXT("path"), pEnvBuf, WINENVBUF_SIZE);
|
|
|
|
if (0 == dwRet)
|
|
{
|
|
dwErr = GetLastError();
|
|
if (ERROR_ENVVAR_NOT_FOUND == dwErr)
|
|
{
|
|
SPDLOG_DEBUG(TEXT("Environment variable path does not exist."));
|
|
free(pEnvBuf);
|
|
return -ERR_FILE_NOT_EXISTS;
|
|
}
|
|
}
|
|
else if (WINENVBUF_SIZE < dwRet)
|
|
{
|
|
pEnvBuf = static_cast<LPSTR>(realloc(pEnvBuf, dwRet * sizeof(CHAR)));
|
|
if (nullptr == pEnvBuf)
|
|
{
|
|
SPDLOG_ERROR(TEXT("Malloc {0} bytes memory error"), dwRet * sizeof(CHAR));
|
|
return -ERR_MALLOC_MEMORY;
|
|
}
|
|
dwRet = GetEnvironmentVariable("path", pEnvBuf, dwRet);
|
|
if (!dwRet)
|
|
{
|
|
SPDLOG_ERROR(TEXT("GetEnvironmentVariable failed (%d)"), GetLastError());
|
|
free(pEnvBuf);
|
|
return -ERR_FILE_NOT_EXISTS;
|
|
}
|
|
}
|
|
|
|
token = strtok_s(pEnvBuf, TEXT(";"), &p);
|
|
|
|
while (token != nullptr)
|
|
{
|
|
memset(path, 0, MAX_PATH);
|
|
StringCbPrintfA(path, MAX_PATH, TEXT("%s\\wireguard.exe"), token);
|
|
|
|
hFind = FindFirstFile(path, &FindFileData);
|
|
|
|
if (hFind != INVALID_HANDLE_VALUE)
|
|
{
|
|
if (pFullPath && maxSize > 0)
|
|
{
|
|
StringCbCopy(pFullPath, maxSize, path);
|
|
}
|
|
|
|
// 保存路径到配置文件
|
|
SetWireguardPath(path);
|
|
SPDLOG_DEBUG(TEXT("Path Environment found WireGuard at: {0}"), path);
|
|
|
|
StringCbCopy(GetGlobalCfgInfo()->wireguardCfg.wireguardPath, MAX_PATH, wrieguardPath);
|
|
GetGlobalCfgInfo()->wireguardCfg.wireguardExists = TRUE;
|
|
|
|
memset(path, 0, MAX_PATH);
|
|
StringCbPrintf(path, MAX_PATH, TEXT("%s\\wg.exe"), token);
|
|
|
|
SPDLOG_DEBUG(TEXT("Find WireGuard tools at: {0}"), path);
|
|
|
|
hFind = FindFirstFile(path, &FindFileData);
|
|
if (hFind != INVALID_HANDLE_VALUE)
|
|
{
|
|
StringCbCopy(GetGlobalCfgInfo()->wireguardCfg.wgPath, MAX_PATH, path);
|
|
GetGlobalCfgInfo()->wireguardCfg.wgExists = TRUE;
|
|
|
|
SPDLOG_DEBUG(TEXT("Path Environment found WireGuard tools at: {0}"), path);
|
|
}
|
|
|
|
|
|
//TODO: throw exception by C# call, why??????
|
|
//CloseHandle(hFind);
|
|
free(pEnvBuf);
|
|
return ERR_SUCCESS;
|
|
}
|
|
token = strtok_s(nullptr, TEXT(";"), &p);
|
|
}
|
|
|
|
free(pEnvBuf);
|
|
return -ERR_FILE_NOT_EXISTS;
|
|
}
|