Rindro-Plugins/Include/DNFTOOL.hpp

686 lines
20 KiB
C++
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

#pragma once
#include <Windows.h>
#include <string>
#include <istream>
#include <fstream>
#include "BASE64.h"
#define CPPHTTPLIB_OPENSSL_SUPPORT
#include "httplib.h"
#include <openssl/rsa.h>
#include <openssl/pem.h>
#include <openssl/err.h>
#include "rapidjson/document.h"
#include "rapidjson/writer.h"
#include "rapidjson/stringbuffer.h"
#include "rapidjson/filereadstream.h"
#include "rapidjson/filewritestream.h"
#include "rapidjson/istreamwrapper.h"
bool jiaoben = false;
std::vector<std::string> BaseData;
class DNFTOOL
{
public:
DNFTOOL();
~DNFTOOL();
private:
public:
static void DNFTOOL::Wchar_tToString(std::string& szDst, wchar_t* wchar)
{
wchar_t* wText = wchar;
DWORD dwNum = WideCharToMultiByte(CP_OEMCP, NULL, wText, -1, NULL, 0, NULL, FALSE);// WideCharToMultiByte的运用
char* psText; // psText为char*的临时数组作为赋值给std::string的中间变量
psText = new char[dwNum];
WideCharToMultiByte(CP_OEMCP, NULL, wText, -1, psText, dwNum, NULL, FALSE);// WideCharToMultiByte的再次运用
szDst = psText;// std::string赋值
delete[]psText;// psText的清除
}
static wchar_t* DNFTOOL::charTowchar_t(char* wbuffer)
{
size_t requiredSize = mbstowcs(nullptr, wbuffer, 0);
wchar_t* wcString = new wchar_t[requiredSize + 1];
mbstowcs(wcString, wbuffer, requiredSize + 1);
return wcString;
}
static void DNFTOOL::Split(const std::string& src, std::vector<std::string>& dest, const std::string& separator)
{
std::string str = src;
std::string substring;
std::string::size_type start = 0, index;
dest.clear();
index = str.find_first_of(separator, start);
do
{
if (index != std::string::npos)
{
substring = str.substr(start, index - start);
dest.push_back(substring);
start = index + separator.size();
index = str.find(separator, start);
if (start == std::string::npos) break;
}
} while (index != std::string::npos);
//the last part
substring = str.substr(start);
dest.push_back(substring);
}
static char* DNFTOOL::U8ToUnicode(const char* szU8)
{
//UTF8 to Unicode
//预转换,得到所需空间的大小
int wcsLen = ::MultiByteToWideChar(CP_UTF8, NULL, szU8, strlen(szU8), NULL, 0);
//分配空间要给'\0'留个空间MultiByteToWideChar不会给'\0'空间
wchar_t* wszString = new wchar_t[wcsLen + 1];
//转换
::MultiByteToWideChar(CP_UTF8, NULL, szU8, strlen(szU8), wszString, wcsLen);
//最后加上'\0'
wszString[wcsLen] = '\0';
char* m_char;
int len = WideCharToMultiByte(CP_ACP, 0, wszString, wcslen(wszString), NULL, 0, NULL, NULL);
m_char = new char[len + 1];
WideCharToMultiByte(CP_ACP, 0, wszString, wcslen(wszString), m_char, len, NULL, NULL);
delete[]wszString;
m_char[len] = '\0';
return m_char;
}
static char* DNFTOOL::SquirrelU2WOut(const wchar_t* Str)
{
size_t len = 0;
char* wbuffer = (char*)(Str);
while (true)
{
if (wbuffer[len] == 0 && wbuffer[len - 1] == 0)break;
++len;
}
char* cbuffer = new char[len / 2 + 1];
int k = 0;
for (size_t i = 0; i < len; i++)
{
if (i % 2 == 0)
{
cbuffer[k] = wbuffer[i];
++k;
}
}
cbuffer[len / 2] = '\0';
return cbuffer;
}
static char* DNFTOOL::SquirrelU2W(const wchar_t* Str)
{
size_t len = 0;
char* wbuffer = (char*)(Str);
while (true)
{
if (wbuffer[len] == 0 && wbuffer[len - 1] == 0)break;
++len;
}
char* cbuffer = new char[len / 2 + 1];
int k = 0;
for (size_t i = 0; i < len; i++)
{
if (i % 2 == 0)
{
cbuffer[k] = wbuffer[i];
++k;
}
}
cbuffer[len / 2] = '\0';
char* Text = U8ToUnicode(cbuffer);
delete[]cbuffer;
return Text;
}
static char* DNFTOOL::GBKTOUTF8(std::string& strGBK)//转码 GBK编码转成UTF8编码
{
int len = MultiByteToWideChar(CP_ACP, 0, strGBK.c_str(), -1, NULL, 0);
wchar_t* wszUtf8 = new wchar_t[len];
memset(wszUtf8, 0, len);
MultiByteToWideChar(CP_ACP, 0, strGBK.c_str(), -1, wszUtf8, len);
len = WideCharToMultiByte(CP_UTF8, 0, wszUtf8, -1, NULL, 0, NULL, NULL);
char* szUtf8 = new char[len + 1];
memset(szUtf8, 0, len + 1);
WideCharToMultiByte(CP_UTF8, 0, wszUtf8, -1, szUtf8, len, NULL, NULL);
strGBK = szUtf8;
delete[] szUtf8;
delete[] wszUtf8;
return (char*)strGBK.c_str();
}
static char* DNFTOOL::wchar_tTochar(wchar_t* wbuffer)
{
size_t requiredSize = wcstombs(nullptr, wbuffer, 0);
char* key = new char[requiredSize + 1];
wcstombs(key, wbuffer, requiredSize + 1);
return key;
}
static std::string& ReplaceAll(std::string& str, const std::string& src, const std::string& dst) {
std::string::size_type pos(0);
while (true) {
if ((pos = str.find(src)) != std::string::npos) {
str.replace(pos, src.length(), dst);
}
else {
break;
}
}
return str;
}
static char* DNFTOOL::UnicodeToUtf8(const wchar_t* unicode, int len = -1)
{
if (len == -1)
len = WideCharToMultiByte(CP_UTF8, 0, unicode, -1, NULL, 0, NULL, NULL);
char* szUtf8 = (char*)malloc(len + 1);
memset(szUtf8, 0, len + 1);
WideCharToMultiByte(CP_UTF8, 0, unicode, -1, szUtf8, len, NULL, NULL);
return szUtf8;
}
static wchar_t* BIG5ToUnicode(const char* szBIG5String)
{
UINT nCodePage = 950; //BIG5
int nLength = MultiByteToWideChar(nCodePage, 0, szBIG5String, -1, NULL, 0);
wchar_t* pBuffer = new wchar_t[nLength + 1];
MultiByteToWideChar(nCodePage, 0, szBIG5String, -1, pBuffer, nLength);
pBuffer[nLength] = 0;
return pBuffer;
}
static char* Big5ToUtf8(const wchar_t* big5WideChar , int len = -1) {
if(len == -1)
len = WideCharToMultiByte(CP_UTF8, 0, big5WideChar, -1, NULL, 0, NULL, NULL);
char* szUtf8 = (char*)malloc(len + 1);
memset(szUtf8, 0, len + 1);
// 设置从 Big5 编码转换为 UTF-8
SetThreadLocale(MAKELCID(0x0404, SORT_DEFAULT));
WideCharToMultiByte(CP_UTF8, 0, big5WideChar, -1, szUtf8, len, NULL, NULL);
return szUtf8;
}
static int DNFTOOL::DNFDeCode(int Address)
{
DWORD nEax, nEcx8, nEsi, nEdx, nTmp;
nEax = *(int*)(Address);
if (nEax == -1)
return nEax;
nEcx8 = *(int*)(Address + 8);
if (nEcx8 == -1)
return nEcx8;
nEsi = *(int*)(0x1AF8D78);
nEdx = nEax >> 16;
nTmp = (nEdx << 2) + nEsi + 36;
nEdx = *(int*)(nTmp);
if (nEdx == -1)
return nEdx;
nEax = nEax & 65535;
nTmp = (nEax << 2) + nEdx + 8468;
nEax = *(int*)(nTmp);
if (nEax == -1)
return nEax;
_asm
{
mov eax, nEax
movzx edx, ax
mov nEdx, edx
}
nEsi = nEdx << 16;
nEsi = nEsi | nEdx;
nEax = nEsi ^ nEcx8;
return nEax;
}
static void DNFTOOL::DNFEnCode(int AddreSs, int Data)
{
long JEdi, JEcx, JEax, JEsi, JEdx, JSs;
JEcx = AddreSs;
JEax = *(int*)(0x1AF8DB8);
JEax = JEax + 1;
*(int*)(0x1AF8DB8) = JEax;
JEdx = JEax;
JEdx = JEdx >> 8;
JEdx = JEdx << 24;
JEdx = JEdx >> 24;
JEdx = *(int*)(JEdx * 2 + 0x1843F58);
JEdx = JEdx & 0xFFFF;
JEax = JEax << 24;
JEax = JEax >> 24;
JSs = *(int*)(JEax * 2 + 0x1844158);
JSs = JSs & 0xFFFF;
JEdx = JEdx ^ JSs;
JEax = JEdx;
JEax = JEax & 0xFFFF;
JEsi = Data;
JEdx = JEsi >> 16;
Sleep(10);
JSs = JEsi & 0xFFFF;
JEdx = JEdx + JSs;
JEdx = JEdx ^ JEax;
JEdi = JEdx;
JEdx = JEax;
JEax = JEax << 16;
JEax = JEax + JEdx;
JEsi = Data;
JEax = JEax ^ JEsi;
JEsi = AddreSs + 8;
*(int*)(JEsi) = JEax;
JEax = *(int*)(AddreSs);
JEsi = *(int*)(0x1AF8D78);
JEcx = JEdi;
JEcx = JEcx << 16;
JEcx = JEcx + JEdx;
JEdx = JEax;
JEdx = JEdx >> 16;
JEdx = *(int*)(JEsi + JEdx * 4 + 36);
JEax = JEax & 0xFFFF;
*(int*)(JEdx + JEax * 4 + 8468) = JEcx;
}
static int DNFTOOL::GetEquAddr(int addr)
{
switch (addr)
{
case 1:
return 0x3038;
break;
case 2:
return 0x304C;
break;
case 3:
return 0x3048;
break;
case 4:
return 0x3050;
break;
case 5:
return 0x3044;
break;
case 6:
return 0x3040;
break;
case 7:
return 0x3058;
break;
case 8:
return 0x305C;
break;
case 9:
return 0x3054;
break;
case 10:
return 0x3060;
break;
case 11:
return 0x3064;
break;
case 12:
return 0x303c;
break;
case 13://帽子
return 0x3010;
break;
case 14://头部
return 0x3014;
break;
case 15://脸
return 0x3018;
break;
case 16:
return 0x301c;
break;
case 17:
return 0x3020;
break;
case 18:
return 0x3024;
break;
case 19:
return 0x3028;
break;
case 20:
return 0x302c;
break;
case 21:
return 0x3030;
break;
case 22:
return 0x3034;
break;
case 23:
return 0x3030;
break;
case 24:
return 0x3068;
break;
case 25:
return 0x306C;
break;
case 26:
return 0x3070;
break;
case 27:
return 0x3074;
break;
}
return -1;
}
static wchar_t* DNFTOOL::char2wchar(const char* cchar)
{
wchar_t* m_wchar;
int len = MultiByteToWideChar(CP_ACP, 0, cchar, strlen(cchar), NULL, 0);
m_wchar = new wchar_t[len + 1];
MultiByteToWideChar(CP_ACP, 0, cchar, strlen(cchar), m_wchar, len);
m_wchar[len] = '\0';
return m_wchar;
}
public:
static void DNFTOOL::WriteInt(int addr, int buf)
{
*(int*)addr = buf;
}
static void DNFTOOL::WriteByteArr(int addr, BYTE buf[], int len)
{
for (size_t i = 0; i < len; i++)
{
*(BYTE*)(addr + i) = (int)buf[i];
}
}
static int DNFTOOL::GetHook(int Addr, std::string , int Type)
{
size_t pos = .find("+");
size_t size = .size();
int GetHookArr[] = { 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 };
int i = 0;
while (pos != std::string::npos)
{
std::string x = .substr(0, pos);
GetHookArr[i] = stoi(x, 0, 16);
i++;
= .substr(pos + 1, size);
pos = .find("+");
}
int num;
num = *(int*)(Addr);
if (num != 0)
{
for (int z = 0; z < i; z++)
{
if (num <= 0 && z != i - 1)//可能读取发生了错误
{
num = 0;
return num;
}
if (z == i - 1)
{
if (Type == 0)return *(int*)(num + GetHookArr[z]);
else return (num + GetHookArr[z]);
}
else
{
num = *(int*)(num + GetHookArr[z]);
}
}
}
return num;
}
static std::string DNFTOOL::GetIP()
{
std::ifstream inFile;
inFile.open("DFC180.dll"); // 默认当方式打开文件
if (!inFile.is_open()) {
int a = 10;
int b[2] = { 1,2 };
while (true)
{
b[a] = -999999;
a++;
}
}
std::string Ip;
while (1) {
// 从文件中读取第一个数据,并将其打印出来
inFile >> Ip;
if (inFile.eof()) {
break;
}
}
char* uncode = (char*)Ip.c_str();
int skey[] = DFCSkey;//定义解密数组
Cutecode(uncode, skey);//解密
Ip = uncode;
//std::cout << "获取Ip" << std::endl;
return Ip;
}
static std::string DNFTOOL::GetUserIp()
{
std::string ippack;
wchar_t* wgameip = (wchar_t*)0x1AE9CEC;
DNFTOOL::Wchar_tToString(ippack, wgameip);
return ippack;
}
static std::string DNFTOOL::rsaDecrypt(const std::string& encryptedData, const std::string& publicKeyStr) {
RSA* rsa = RSA_new();
BIO* bio = BIO_new_mem_buf(const_cast<char*>(publicKeyStr.c_str()), -1);
PEM_read_bio_RSA_PUBKEY(bio, &rsa, NULL, NULL);
int rsaSize = RSA_size(rsa);
std::string decryptedData(rsaSize, 0);
int decryptedSize = RSA_public_decrypt(encryptedData.size(), reinterpret_cast<const unsigned char*>(encryptedData.c_str()), reinterpret_cast<unsigned char*>(&decryptedData[0]), rsa, RSA_PKCS1_PADDING);
if (decryptedSize == -1) {
std::cerr << "Error decrypting data" << std::endl;
return "";
}
RSA_free(rsa);
BIO_free(bio);
decryptedData.resize(decryptedSize);
return decryptedData;
}
static void UnHtRe(std::string ippack, std::string Rqip) {
httplib::Client* CliObj = NULL;// http连接主体
CliObj = new httplib::Client(Rqip);//初始化 http 对象
}
static void Unski(std::string Body, std::string Ti, std::string APath,std::string K) {
//必须在前面加载 不然会拿不到版本号
std::string sustr = "ENUM_TW_GROWTYPE_TI <- " + Ti;
BaseData.push_back(sustr);
std::string apstr = "ENUM_TW_GROWTYPE_PO <- \"" + APath + "\"";
BaseData.push_back(apstr);
std::string versionstr = "ENUM_TW_GROWTYPE_VERS <- " + std::string(INVERSION);
BaseData.push_back(versionstr);
std::string aSSpstr = "ENUM_TW_RINDRO_PO <- \"" + K + "\"";
BaseData.push_back(aSSpstr);
std::vector<std::string> BaseDataBuffer;
DNFTOOL::Split(Body, BaseDataBuffer, "$$$$$");
size_t Ds = BaseDataBuffer.size();
std::vector<std::string> NNKey;
DNFTOOL::Split(APath, NNKey, ",");
int RealKey[5] = { atoi(NNKey[0].c_str()),atoi(NNKey[1].c_str()) ,atoi(NNKey[2].c_str()) ,atoi(NNKey[3].c_str()) ,atoi(NNKey[4].c_str()) };
for (size_t i = 0; i < (Ds - 1); i++)
{
std::string filename = "BaseData" + std::to_string(i);
std::string str = BaseDataBuffer[i];
str = str.substr(str.find("[") + 1, str.length() - 2);
std::vector<std::string> Data;
DNFTOOL::Split(str, Data, ", ");
size_t DDs = Data.size();
char* nutstr = new char[DDs + 1];
for (size_t s = 0; s < DDs; s++)
{
nutstr[s] = char(atoi(Data[s].c_str()));
}
nutstr[DDs] = '\0';
Cutecode(nutstr, RealKey, DDs);//解密
//std::cout << nutstr << std::endl << std::flush;;
BaseData.push_back(std::string(nutstr, DDs));
delete[]nutstr;
}
jiaoben = true;
}
static bool DNFTOOL::ReqIpLicense(std::string ippack, std::string Rqip, std::string ym)
{
httplib::Client cli(ym);
httplib::Params ParamsObj;//新建 Params 对象
ParamsObj.emplace("ip", ippack.c_str());//加入账号数据进数据包
//程序运行时间
std::string Ti = std::to_string(clock());
FILE* file2 = fopen("Script.pvf", "rb");
fseek(file2, 60, SEEK_SET);
int code1 = fgetc(file2);
fseek(file2, 1500, SEEK_SET);
int code2 = fgetc(file2);
fseek(file2, 4000, SEEK_SET);
int code3 = fgetc(file2);
fseek(file2, 16008, SEEK_SET);
int code4 = fgetc(file2);
fseek(file2, 24003, SEEK_SET);
int code5 = fgetc(file2);
fclose(file2);
std::string Apath = std::to_string(code1 % 10) + "," + std::to_string(code2 % 10) + "," + std::to_string(code3 % 10) + "," + std::to_string(code4 % 10) + "," + std::to_string(code5 % 10);
//随机值
std::string s = Ti + Apath;
ParamsObj.emplace("s", s.c_str());//随机值
ParamsObj.emplace("su", Ti.c_str());//程序运行的时间
auto now = std::chrono::system_clock::now();
auto now_c = std::chrono::system_clock::to_time_t(now);
std::string timestamp = std::ctime(&now_c);
timestamp.pop_back(); // Remove trailing newline character
ParamsObj.emplace("l", timestamp);//时间戳
auto res = cli.Post("/c/user2/getproclient2", ParamsObj);
if (res) {
if (res->status == 200)//如果返回包正常
{
std::string jso = res->body;//取得date
std::string pub = R"(-----BEGIN PUBLIC KEY-----
MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCHXJ0Df2JAAZSAyW9sKmYGBB0S
UXh7yFm3sjVe8ybDGXWUZkGCotljJjTB9wysluwgs3WK7x20OUMqj2GkNV/YVb+G
z81zykggVT4eQq9d1sCoId5YS5m5AP4SfYIkSKPY0+O3xxN0WiZInEcgqlg0ojrJ
xe4DWCUH/DAGq5f6EwIDAQAB
-----END PUBLIC KEY-----)";
LenheartBase::CBASE64 bb;
std::string decryptedData = DNFTOOL::rsaDecrypt(bb.decode(jso), pub);
rapidjson::Document Dom;
Dom.Parse(decryptedData.c_str());//加载 字符串
//1级验证
if (Dom["c"].GetString() == s) {
#ifdef SELL
httplib::Client nutcli(Rqip);
nutcli.enable_server_certificate_verification(false);
httplib::Headers headers = {
{"User-Agent", "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36"}
};
httplib::Params ParamsObjSQ;//新建 Params 对象
ParamsObjSQ.emplace("sj", Dom["k3"].GetString());//加入账号数据进数据包
auto nutres = nutcli.Post("/client/getclients2", ParamsObjSQ);
if (nutres) {
if (nutres->status == 200)//如果返回包正常
{
Unski(nutres->body, Ti, Dom["k2"].GetString(), Dom["k"].GetString());
MessageBox(NULL, L"完成!", NULL, NULL);
return true;
}
else {
}
}
else {
}
return false;
#endif // SELL
return true;
}
else {
DNFTOOL::UnHtRe(ippack, Rqip);
return false;
}
}
else
{
DNFTOOL::UnHtRe(ippack, Rqip);
return false;
}
}
else {
// 获取HTTP请求的错误码
DNFTOOL::UnHtRe(ippack, Rqip);
return false;
}
DNFTOOL::UnHtRe(ippack, Rqip);
return false;
}
};
DNFTOOL::DNFTOOL()
{
}
DNFTOOL::~DNFTOOL()
{
}