创建时间: 2025-08-18 08:42:00
更新时间: 2025-08-19 06:32:41
#include <windows.h>
#include <wincrypt.h>
#include <iphlpapi.h>
#include <intrin.h>
#include <VersionHelpers.h>
#include <rpc.h>
#include <winhttp.h>
#include <string>
#include <vector>
#include <iomanip>
#include <sstream>
#include <iostream>
#include <nlohmann/json.hpp>
// 感谢 Yume 提出的openssl 会被hook的bug 欢迎进他的群 868318886
// 需要libs的联系Fonnt 或者 自己vcpkg下载
// 最新一次更新 8.17 21.06
#pragma comment(lib, "winhttp.lib")
#pragma comment(lib, "crypt32.lib")
#pragma comment(lib, "iphlpapi.lib")
#pragma comment(lib, "Rpcrt4.lib")
#define BASE_URL L"lifey.icu"
#define PORT 80
#define APP_ID "您的appid"
#define SECRET "您项目的加密密钥"
#define AES_BLOCK_SIZE 16
#define AES_KEY_SIZE 32
using json = nlohmann::json;
void setupConsoleEncoding() {
SetConsoleOutputCP(CP_UTF8);
SetConsoleCP(CP_UTF8);
HANDLE hConsole = GetStdHandle(STD_OUTPUT_HANDLE);
if (hConsole != INVALID_HANDLE_VALUE) {
CONSOLE_FONT_INFOEX fontInfo = { 0 };
fontInfo.cbSize = sizeof(CONSOLE_FONT_INFOEX);
if (GetCurrentConsoleFontEx(hConsole, FALSE, &fontInfo)) {
wcscpy_s(fontInfo.FaceName, L"SimHei");
SetCurrentConsoleFontEx(hConsole, FALSE, &fontInfo);
}
}
}
namespace CustomBase64 {
static const std::string base64_chars =
"ABCDEFGHIJKLMNOPQRSTUVWXYZ"
"abcdefghijklmnopqrstuvwxyz"
"0123456789+/";
static inline bool is_base64(unsigned char c) {
return (isalnum(c) || (c == '+') || (c == '/'));
}
std::string encode(const std::string& input) {
std::string ret;
int i = 0;
int j = 0;
unsigned char char_array_3[3];
unsigned char char_array_4[4];
size_t in_len = input.size();
const char* bytes_to_encode = input.data();
while (in_len--) {
char_array_3[i++] = *(bytes_to_encode++);
if (i == 3) {
char_array_4[0] = (char_array_3[0] & 0xfc) >> 2;
char_array_4[1] = ((char_array_3[0] & 0x03) << 4) + ((char_array_3[1] & 0xf0) >> 4);
char_array_4[2] = ((char_array_3[1] & 0x0f) << 2) + ((char_array_3[2] & 0xc0) >> 6);
char_array_4[3] = char_array_3[2] & 0x3f;
for (i = 0; (i < 4); i++)
ret += base64_chars[char_array_4[i]];
i = 0;
}
}
if (i) {
for (j = i; j < 3; j++)
char_array_3[j] = '\0';
char_array_4[0] = (char_array_3[0] & 0xfc) >> 2;
char_array_4[1] = ((char_array_3[0] & 0x03) << 4) + ((char_array_3[1] & 0xf0) >> 4);
char_array_4[2] = ((char_array_3[1] & 0x0f) << 2) + ((char_array_3[2] & 0xc0) >> 6);
char_array_4[3] = char_array_3[2] & 0x3f;
for (j = 0; (j < i + 1); j++)
ret += base64_chars[char_array_4[j]];
while ((i++ < 3))
ret += '=';
}
return ret;
}
std::string decode(const std::string& encoded_string) {
size_t in_len = encoded_string.size();
int i = 0;
int j = 0;
int in_ = 0;
unsigned char char_array_4[4], char_array_3[3];
std::string ret;
while (in_len-- && (encoded_string[in_] != '=') && is_base64(encoded_string[in_])) {
char_array_4[i++] = encoded_string[in_]; in_++;
if (i == 4) {
for (i = 0; i < 4; i++)
char_array_4[i] = static_cast<unsigned char>(base64_chars.find(char_array_4[i]));
char_array_3[0] = (char_array_4[0] << 2) + ((char_array_4[1] & 0x30) >> 4);
char_array_3[1] = ((char_array_4[1] & 0xf) << 4) + ((char_array_4[2] & 0x3c) >> 2);
char_array_3[2] = ((char_array_4[2] & 0x3) << 6) + char_array_4[3];
for (i = 0; (i < 3); i++)
ret += char_array_3[i];
i = 0;
}
}
if (i) {
for (j = i; j < 4; j++)
char_array_4[j] = 0;
for (j = 0; j < 4; j++)
char_array_4[j] = static_cast<unsigned char>(base64_chars.find(char_array_4[j]));
char_array_3[0] = (char_array_4[0] << 2) + ((char_array_4[1] & 0x30) >> 4);
char_array_3[1] = ((char_array_4[1] & 0xf) << 4) + ((char_array_4[2] & 0x3c) >> 2);
char_array_3[2] = ((char_array_4[2] & 0x3) << 6) + char_array_4[3];
for (j = 0; (j < i - 1); j++) ret += char_array_3[j];
}
return ret;
}
}
void secureRandomBytes(BYTE* buf, size_t len) {
HCRYPTPROV hProv;
if (CryptAcquireContext(&hProv, NULL, NULL, PROV_RSA_FULL, CRYPT_VERIFYCONTEXT)) {
CryptGenRandom(hProv, (DWORD)len, buf);
CryptReleaseContext(hProv, 0);
}
}
void printByteArray(const BYTE* data, size_t len, const std::string& label) {
std::cout << label << ": ";
for (size_t i = 0; i < len; ++i) {
std::cout << std::hex << std::setw(2) << std::setfill('0') << (int)data[i];
}
std::cout << std::dec << std::endl;
}
class SecureAES {
private:
std::vector<BYTE> key;
void prepareKey(const std::string& secret) {
std::string decodedKey = CustomBase64::decode(secret);
std::cout << "密钥Base64解码后长度: " << decodedKey.size() << "字节" << std::endl;
std::vector<BYTE> tempKey(decodedKey.begin(), decodedKey.end());
if (tempKey.size() < AES_KEY_SIZE) {
std::cout << "密钥长度不足" << AES_KEY_SIZE << "字节,补充至" << AES_KEY_SIZE << "字节" << std::endl;
tempKey.resize(AES_KEY_SIZE, 0x00);
}
else if (tempKey.size() > AES_KEY_SIZE) {
std::cout << "密钥长度超过" << AES_KEY_SIZE << "字节,截断至" << AES_KEY_SIZE << "字节" << std::endl;
tempKey.resize(AES_KEY_SIZE);
}
key = tempKey;
printByteArray(key.data(), key.size(), "最终使用的AES密钥");
}
public:
SecureAES(const std::string& secret) {
prepareKey(secret);
}
std::string encrypt(const std::string& plaintext) {
HCRYPTPROV hProv = NULL;
HCRYPTKEY hKey = NULL;
DWORD dwMode = CRYPT_MODE_CBC;
BYTE iv[AES_BLOCK_SIZE];
secureRandomBytes(iv, AES_BLOCK_SIZE);
printByteArray(iv, AES_BLOCK_SIZE, "生成的IV");
if (!CryptAcquireContext(&hProv, NULL, NULL, PROV_RSA_AES, CRYPT_VERIFYCONTEXT)) {
std::cerr << "CryptAcquireContext失败: " << GetLastError() << std::endl;
return "";
}
DWORD keyLen = (DWORD)key.size();
std::vector<BYTE> keyBlob;
BLOBHEADER bh;
bh.bType = PLAINTEXTKEYBLOB;
bh.bVersion = CUR_BLOB_VERSION;
bh.reserved = 0;
bh.aiKeyAlg = CALG_AES_256;
DWORD blobSize = sizeof(BLOBHEADER) + sizeof(DWORD) + keyLen;
keyBlob.resize(blobSize);
memcpy(keyBlob.data(), &bh, sizeof(BLOBHEADER));
memcpy(keyBlob.data() + sizeof(BLOBHEADER), &keyLen, sizeof(DWORD));
memcpy(keyBlob.data() + sizeof(BLOBHEADER) + sizeof(DWORD), key.data(), keyLen);
if (!CryptImportKey(hProv, keyBlob.data(), blobSize, 0, 0, &hKey)) {
std::cerr << "CryptImportKey失败: " << GetLastError() << std::endl;
CryptReleaseContext(hProv, 0);
return "";
}
if (!CryptSetKeyParam(hKey, KP_MODE, (BYTE*)&dwMode, 0) ||
!CryptSetKeyParam(hKey, KP_IV, iv, 0)) {
std::cerr << "CryptSetKeyParam失败: " << GetLastError() << std::endl;
CryptDestroyKey(hKey);
CryptReleaseContext(hProv, 0);
return "";
}
DWORD dwDataLen = (DWORD)plaintext.size();
DWORD dwBufLen = dwDataLen + AES_BLOCK_SIZE;
std::vector<BYTE> ciphertext(dwBufLen);
memcpy(ciphertext.data(), plaintext.data(), dwDataLen);
if (!CryptEncrypt(hKey, 0, TRUE, 0, ciphertext.data(), &dwDataLen, dwBufLen)) {
std::cerr << "CryptEncrypt失败: " << GetLastError() << std::endl;
CryptDestroyKey(hKey);
CryptReleaseContext(hProv, 0);
return "";
}
CryptDestroyKey(hKey);
CryptReleaseContext(hProv, 0);
std::vector<BYTE> combined;
combined.insert(combined.end(), iv, iv + AES_BLOCK_SIZE);
combined.insert(combined.end(), ciphertext.begin(), ciphertext.begin() + dwDataLen);
std::string encrypted = CustomBase64::encode(std::string(combined.begin(), combined.end()));
std::cout << "加密后的数据长度: " << encrypted.size() << "字节" << std::endl;
return encrypted;
}
std::string decrypt(const std::string& ciphertext) {
std::string decoded = CustomBase64::decode(ciphertext);
std::cout << "解密时Base64解码后的数据长度: " << decoded.size() << "字节" << std::endl;
if (decoded.size() <= AES_BLOCK_SIZE) {
std::cerr << "密文长度不足" << std::endl;
return "";
}
const BYTE* iv = reinterpret_cast<const BYTE*>(decoded.data());
const BYTE* encryptedData = iv + AES_BLOCK_SIZE;
DWORD encryptedDataLen = (DWORD)(decoded.size() - AES_BLOCK_SIZE);
printByteArray(iv, AES_BLOCK_SIZE, "解密使用的IV");
HCRYPTPROV hProv = NULL;
HCRYPTKEY hKey = NULL;
DWORD dwMode = CRYPT_MODE_CBC;
if (!CryptAcquireContext(&hProv, NULL, NULL, PROV_RSA_AES, CRYPT_VERIFYCONTEXT)) {
std::cerr << "CryptAcquireContext失败: " << GetLastError() << std::endl;
return "";
}
DWORD keyLen = (DWORD)key.size();
std::vector<BYTE> keyBlob;
BLOBHEADER bh;
bh.bType = PLAINTEXTKEYBLOB;
bh.bVersion = CUR_BLOB_VERSION;
bh.reserved = 0;
bh.aiKeyAlg = CALG_AES_256;
DWORD blobSize = sizeof(BLOBHEADER) + sizeof(DWORD) + keyLen;
keyBlob.resize(blobSize);
memcpy(keyBlob.data(), &bh, sizeof(BLOBHEADER));
memcpy(keyBlob.data() + sizeof(BLOBHEADER), &keyLen, sizeof(DWORD));
memcpy(keyBlob.data() + sizeof(BLOBHEADER) + sizeof(DWORD), key.data(), keyLen);
if (!CryptImportKey(hProv, keyBlob.data(), blobSize, 0, 0, &hKey)) {
std::cerr << "CryptImportKey失败: " << GetLastError() << std::endl;
CryptReleaseContext(hProv, 0);
return "";
}
if (!CryptSetKeyParam(hKey, KP_MODE, (BYTE*)&dwMode, 0) ||
!CryptSetKeyParam(hKey, KP_IV, (BYTE*)iv, 0)) {
std::cerr << "CryptSetKeyParam失败: " << GetLastError() << std::endl;
CryptDestroyKey(hKey);
CryptReleaseContext(hProv, 0);
return "";
}
DWORD dwDataLen = encryptedDataLen;
std::vector<BYTE> plaintext(dwDataLen);
memcpy(plaintext.data(), encryptedData, dwDataLen);
if (!CryptDecrypt(hKey, 0, TRUE, 0, plaintext.data(), &dwDataLen)) {
std::cerr << "CryptDecrypt失败: " << GetLastError() << std::endl;
CryptDestroyKey(hKey);
CryptReleaseContext(hProv, 0);
return "";
}
CryptDestroyKey(hKey);
CryptReleaseContext(hProv, 0);
return std::string(plaintext.begin(), plaintext.begin() + dwDataLen);
}
};
std::string getDeviceFingerprint() {
std::string deviceInfo;
deviceInfo = "Windows";
if (IsWindows10OrGreater()) {
deviceInfo += "-10+";
}
else if (IsWindows8Point1OrGreater()) {
deviceInfo += "-8.1";
}
else if (IsWindows8OrGreater()) {
deviceInfo += "-8";
}
else if (IsWindows7OrGreater()) {
deviceInfo += "-7";
}
else if (IsWindowsVistaOrGreater()) {
deviceInfo += "-Vista";
}
else if (IsWindowsXPOrGreater()) {
deviceInfo += "-XP";
}
else {
deviceInfo += "-Unknown";
}
int cpuInfo[4] = { -1 };
__cpuid(cpuInfo, 1);
char cpuId[32];
snprintf(cpuId, sizeof(cpuId), "%08X%08X", cpuInfo[3], cpuInfo[0]);
deviceInfo += "-cpu:";
deviceInfo += cpuId;
IP_ADAPTER_INFO adapterInfo[16];
ULONG bufLen = sizeof(adapterInfo);
if (GetAdaptersInfo(adapterInfo, &bufLen) == ERROR_SUCCESS) {
PIP_ADAPTER_INFO pAdapterInfo = adapterInfo;
char macAddr[18];
snprintf(macAddr, sizeof(macAddr), "%02X-%02X-%02X-%02X-%02X-%02X",
pAdapterInfo->Address[0], pAdapterInfo->Address[1],
pAdapterInfo->Address[2], pAdapterInfo->Address[3],
pAdapterInfo->Address[4], pAdapterInfo->Address[5]);
deviceInfo += "-mac:";
deviceInfo += macAddr;
}
HCRYPTPROV hProv = 0;
HCRYPTHASH hHash = 0;
BYTE rgbHash[32];
DWORD cbHash = 32;
CHAR rgbDigits[] = "0123456789abcdef";
if (!CryptAcquireContext(&hProv, NULL, NULL, PROV_RSA_AES, CRYPT_VERIFYCONTEXT)) {
return "";
}
if (!CryptCreateHash(hProv, CALG_SHA_256, 0, 0, &hHash)) {
CryptReleaseContext(hProv, 0);
return "";
}
if (!CryptHashData(hHash, (BYTE*)deviceInfo.c_str(), (DWORD)deviceInfo.size(), 0)) {
CryptDestroyHash(hHash);
CryptReleaseContext(hProv, 0);
return "";
}
if (!CryptGetHashParam(hHash, HP_HASHVAL, rgbHash, &cbHash, 0)) {
CryptDestroyHash(hHash);
CryptReleaseContext(hProv, 0);
return "";
}
std::stringstream ss;
for (DWORD i = 0; i < cbHash; i++) {
ss << rgbDigits[rgbHash[i] >> 4] << rgbDigits[rgbHash[i] & 0xf];
}
CryptDestroyHash(hHash);
CryptReleaseContext(hProv, 0);
return ss.str();
}
std::string generateUUID() {
UUID uuid;
UuidCreate(&uuid);
RPC_CSTR str;
UuidToStringA(&uuid, &str);
std::string result(reinterpret_cast<char*>(str));
RpcStringFreeA(&str);
return result;
}
class SecureClientSession {
private:
std::string sessionId;
std::string sessionKey;
long long expireTime = 0;
std::string token;
std::string appId;
std::string secret;
SecureAES aes;
json buildSecureRequest(const std::string& path, const json& payload) {
json payloadCopy = payload;
payloadCopy["timestamp"] = static_cast<long long>(time(nullptr) * 1000);
payloadCopy["nonce"] = generateUUID();
std::string payloadStr = payloadCopy.dump();
std::cout << "发送的原始数据: " << payloadStr << std::endl;
std::string encrypted = aes.encrypt(payloadStr);
return {
{"encrypted_data", encrypted},
{"appid", appId},
{"encryption_key", secret}
};
}
json sendSecureRequest(const std::string& path, const json& payload) {
json req = buildSecureRequest(path, payload);
std::string reqStr = req.dump();
std::cout << "发送的请求数据大小: " << reqStr.size() << "字节" << std::endl;
HINTERNET hSession = WinHttpOpen(L"SecureClient/1.0",
WINHTTP_ACCESS_TYPE_DEFAULT_PROXY,
WINHTTP_NO_PROXY_NAME,
WINHTTP_NO_PROXY_BYPASS, 0);
if (!hSession) {
std::cerr << "WinHttpOpen失败: " << GetLastError() << std::endl;
return nullptr;
}
HINTERNET hConnect = WinHttpConnect(hSession, BASE_URL, PORT, 0);
if (!hConnect) {
std::cerr << "WinHttpConnect失败: " << GetLastError() << std::endl;
WinHttpCloseHandle(hSession);
return nullptr;
}
std::wstring widePath(path.begin(), path.end());
HINTERNET hRequest = WinHttpOpenRequest(hConnect, L"POST", widePath.c_str(),
NULL, WINHTTP_NO_REFERER,
WINHTTP_DEFAULT_ACCEPT_TYPES,
0);
if (!hRequest) {
std::cerr << "WinHttpOpenRequest失败: " << GetLastError() << std::endl;
WinHttpCloseHandle(hConnect);
WinHttpCloseHandle(hSession);
return nullptr;
}
std::wstring headers = L"Content-Type: application/json; charset=utf-8";
if (!WinHttpAddRequestHeaders(hRequest, headers.c_str(), (DWORD)headers.length(), WINHTTP_ADDREQ_FLAG_ADD)) {
std::cerr << "WinHttpAddRequestHeaders失败: " << GetLastError() << std::endl;
}
std::string response;
if (WinHttpSendRequest(hRequest,
WINHTTP_NO_ADDITIONAL_HEADERS, 0,
(LPVOID)reqStr.c_str(), (DWORD)reqStr.size(),
(DWORD)reqStr.size(), 0)) {
if (WinHttpReceiveResponse(hRequest, NULL)) {
DWORD dwSize = 0;
DWORD dwDownloaded = 0;
LPSTR pszOutBuffer;
do {
dwSize = 0;
if (!WinHttpQueryDataAvailable(hRequest, &dwSize)) {
std::cerr << "WinHttpQueryDataAvailable失败: " << GetLastError() << std::endl;
break;
}
pszOutBuffer = new char[dwSize + 1];
if (!pszOutBuffer) {
std::cerr << "内存分配失败" << std::endl;
break;
}
ZeroMemory(pszOutBuffer, dwSize + 1);
if (!WinHttpReadData(hRequest, (LPVOID)pszOutBuffer, dwSize, &dwDownloaded)) {
std::cerr << "WinHttpReadData失败: " << GetLastError() << std::endl;
delete[] pszOutBuffer;
break;
}
response.append(pszOutBuffer, dwDownloaded);
delete[] pszOutBuffer;
} while (dwSize > 0);
}
else {
std::cerr << "WinHttpReceiveResponse失败: " << GetLastError() << std::endl;
}
}
else {
std::cerr << "WinHttpSendRequest失败: " << GetLastError() << std::endl;
}
WinHttpCloseHandle(hRequest);
WinHttpCloseHandle(hConnect);
WinHttpCloseHandle(hSession);
try {
if (response.empty()) {
std::cerr << "未收到服务器响应" << std::endl;
return nullptr;
}
if (response.substr(0, 15).find("<!doctype html>") != std::string::npos) {
std::cerr << "服务器返回错误页面,可能是密钥问题" << std::endl;
return nullptr;
}
json root = json::parse(response);
if (root.contains("encrypted_response")) {
std::string decrypted = aes.decrypt(root["encrypted_response"].get<std::string>());
return json::parse(decrypted);
}
else {
std::cerr << "服务器响应不包含encrypted_response字段" << std::endl;
return root;
}
}
catch (const std::exception& e) {
std::cerr << "JSON解析错误: " << e.what() << std::endl;
std::cerr << "原始响应: " << response << std::endl;
}
return nullptr;
}
public:
SecureClientSession(const std::string& app_id, const std::string& secret)
: appId(app_id), secret(secret), aes(secret) {
}
bool activateCard(const std::string& cardKey) {
json payload = {
{"action", "activate"},
{"card_key", cardKey},
{"device_id", getDeviceFingerprint()},
{"appid", appId}
};
json res = sendSecureRequest("/api/user/activate-card", payload);
if (res != nullptr && res.contains("success") && res["success"].get<bool>()) {
std::cout << "成功: " << res["message"].get<std::string>() << std::endl;
return true;
}
else if (res != nullptr && res.contains("message")) {
std::cout << "错误: " << res["message"].get<std::string>() << std::endl;
}
return false;
}
bool login(const std::string& user, const std::string& pwd) {
json payload = {
{"action", "login"},
{"username", user},
{"password", pwd},
{"device_id", getDeviceFingerprint()},
{"appid", appId}
};
json res = sendSecureRequest("/api/user/encrypted-login", payload);
if (res != nullptr && res.contains("success") && res["success"].get<bool>()) {
token = res["encrypted_token"].get<std::string>();
sessionId = res["session_id"].get<std::string>();
sessionKey = res["session_key"].get<std::string>();
expireTime = res["expire_time"].get<long long>();
return true;
}
else if (res != nullptr && res.contains("message")) {
std::cout << "登录失败: " << res["message"].get<std::string>() << std::endl;
}
return false;
}
void printSessionInfo() {
std::cout << "会话ID: " << sessionId << std::endl;
time_t t = static_cast<time_t>(expireTime / 1000);
struct tm timeinfo;
localtime_s(&timeinfo, &t);
char buffer[80];
strftime(buffer, sizeof(buffer), "%Y-%m-%d %H:%M:%S", &timeinfo);
std::cout << "until至: " << buffer << std::endl;
}
};
int main() {
setupConsoleEncoding();
std::cout << "SECRET: " << SECRET << std::endl;
std::string decodedSecret = CustomBase64::decode(SECRET);
std::cout << "SECRET Base64: " << decodedSecret.size() << "bytes" << std::endl;
SecureClientSession client(APP_ID, SECRET);
std::string username, password;
std::cout << "username: ";
std::cin >> username;
std::cout << "password: ";
std::cin >> password;
if (client.login(username, password)) {
std::cout << "LoginSuccessful" << std::endl;
std::cout << "DeviceID: " << getDeviceFingerprint() << std::endl;
client.printSessionInfo();
}
else {
std::cout << "DeviceID: " << getDeviceFingerprint() << std::endl;
std::cout << "Login Failed" << std::endl;
}
system("pause");
return 0;
}