#include "l_squirrel.h" #include "l_squirrel_register.hpp" #include #include #include #include #include #include #include #include #include static char szGamePathA[256]; void setupLogger() { getConfigPath(szGamePathA, sizeof(szGamePathA)); std::string Path = std::string(szGamePathA); std::string log_filename = "log/dps_log/" + Path.substr(Path.find("cfg") + 4) + "/log_"; char time_buffer[100]; std::time_t now = std::time(nullptr); std::tm *local_time = std::localtime(&now); strftime(time_buffer, sizeof(time_buffer), "%Y-%m-%d_%H-%M-%S", local_time); log_filename += std::string(time_buffer) + ".txt"; auto console_sink = std::make_shared(); console_sink->set_level(spdlog::level::info); console_sink->set_pattern("[multi_sink_example] [%^%l%$] %v"); auto file_sink = std::make_shared(log_filename, true); file_sink->set_level(spdlog::level::info); file_sink->set_pattern("[%Y-%m-%d %H:%M:%S] [%^%l%$] %v"); auto logger = std::make_shared("logger", spdlog::sinks_init_list{console_sink, file_sink}); logger->set_level(spdlog::level::info); logger->flush_on(spdlog::level::info); logger->info("欢迎使用Dps插件"); spdlog::register_logger(logger); spdlog::set_default_logger(logger); } // 虚拟机对象 HSQUIRRELVM v; // Lock std::recursive_mutex SqMtx; // static void printfunc(HSQUIRRELVM v, const SQChar *s, ...) // { // fflush(stdout); // va_list vl; // va_start(vl, s); // scvprintf(stdout, s, vl); // va_end(vl); // printf("\n"); // fflush(stdout); // } static void printfunc(HSQUIRRELVM v, const SQChar *s, ...) { va_list vl; va_start(vl, s); char buf[1024]; vsnprintf(buf, sizeof(buf), s, vl); va_end(vl); spdlog::info(buf); } // static void errorfunc(HSQUIRRELVM v, const SQChar *s, ...) // { // fflush(stderr); // va_list vl; // va_start(vl, s); // scvprintf(stderr, s, vl); // va_end(vl); // printf("\n"); // fflush(stderr); // } static void errorfunc(HSQUIRRELVM v, const SQChar *s, ...) { va_list vl; va_start(vl, s); char buf[1024]; vsnprintf(buf, sizeof(buf), s, vl); va_end(vl); spdlog::error(buf); } // 加密函数 static std::string encryptDecrypt(const std::string &input, const std::string &key) { std::string output = input; for (size_t i = 0; i < input.size(); i++) { output[i] = input[i] ^ key[i % key.size()]; // 使用异或运算进行加密 } return output; } // 判断是否处理加密 static std::string IsencryptDecrypt(const std::string &input, const std::string &FileName) { if (FileName.find(".nut") != std::string::npos) return input; else return encryptDecrypt(input, "Rindro-Aurora"); } static void ReloadingScript(HSQUIRRELVM v, std::string FilePath) { // 爬取出所有的脚本文件 std::vector vec = Tool::GetListFilesR(FilePath); std::map SquirrelFilePath; for (auto it = vec.cbegin(); it != vec.cend(); ++it) { std::string FileName = FilePath + *it; if (FileName.find(".nut") == std::string::npos && FileName.find(".sut") == std::string::npos) continue; std::fstream F; F.open((FileName).c_str(), std::ios::in); std::stringstream ContentStringStream; ContentStringStream << F.rdbuf(); std::string ContentString(ContentStringStream.str()); F.close(); std::string RealContentString = IsencryptDecrypt(ContentString, FileName); SquirrelFilePath[FileName] = RealContentString; } std::map SquirrelLastFilePath; for (auto it = SquirrelFilePath.begin(); it != SquirrelFilePath.end(); it++) { std::string Sourcename = it->first; std::string ContentString = it->second; if (SQ_SUCCEEDED(sq_compilebuffer(v, (SQChar *)(ContentString.c_str()), ContentString.length(), (SQChar *)(Sourcename.c_str()), true))) { sq_pushroottable(v); sq_call(v, 1, 1, 1); sq_pop(v, 1); } else { SquirrelLastFilePath[Sourcename] = ContentString; } } while (SquirrelLastFilePath.size() > 0) { std::map FailMapBuffer; for (auto it = SquirrelLastFilePath.begin(); it != SquirrelLastFilePath.end(); it++) { std::string Sourcename = it->first; std::string ContentString = it->second; if (SQ_SUCCEEDED(sq_compilebuffer(v, (SQChar *)(ContentString.c_str()), ContentString.length(), (SQChar *)(Sourcename.c_str()), true))) { sq_pushroottable(v); if (SQ_FAILED(sq_call(v, 1, 1, 1))) { FailMapBuffer[Sourcename] = ContentString; }; sq_pop(v, 1); }; } SquirrelLastFilePath.clear(); if (FailMapBuffer.size() > 0) { for (auto it = FailMapBuffer.begin(); it != FailMapBuffer.end(); it++) { std::string Sourcename = it->first; std::string ContentString = it->second; SquirrelLastFilePath[Sourcename] = ContentString; } } } } static SQInteger SqReloadScript(HSQUIRRELVM v) { ReloadingScript(v, "/dp_s/Dps_A/"); ReloadingScript(v, "/dp_s/Dps_B/"); ReloadingScript(v, "/dp_s/Dps_C/"); return 0; } void InitSquirrel() { std::cout << "OpenSSL version: " << OPENSSL_VERSION_TEXT << std::endl; asio::io_context io_context; asio::ssl::context ctx(asio::ssl::context::tlsv12_client); asio::ssl::stream socket(io_context, ctx); asio::ip::tcp::resolver resolver(io_context); auto endpoints = resolver.resolve("www.rindro.cn", "https"); asio::connect(socket.lowest_layer(), endpoints); socket.handshake(asio::ssl::stream_base::handshake_type::client); std::string post_data = "key1=value1&key2=value2"; std::string request = "POST /c/user/getServiceUrl HTTP/1.1\r\n"; request += "Host: www.rindro.cn\r\n"; request += "Content-Length: " + std::to_string(post_data.size()) + "\r\n"; request += "Content-Type: application/x-www-form-urlencoded\r\n"; request += "\r\n"; request += post_data; asio::write(socket, asio::buffer(request)); asio::streambuf response; asio::read_until(socket, response, "\r\n"); std::istream response_stream(&response); std::string http_version; response_stream >> http_version; std::stringstream ss; ss << &response; std::string response_data = ss.str(); std::cout << "Server Response: " << response_data << std::endl; std::lock_guard lock(SqMtx); v = sq_open(4096); // 创建虚拟机,其栈的初始大小为1024 sq_pushroottable(v); sqstd_register_bloblib(v); sqstd_register_iolib(v); sqstd_register_systemlib(v); sqstd_register_mathlib(v); sqstd_register_stringlib(v); sqstd_seterrorhandlers(v); setupLogger(); sq_setprintfunc(v, printfunc, errorfunc); // sets the print function // 输出版本信息 // scfprintf(stdout, _SC("%s %s (%d bits)\n"), SQUIRREL_VERSION, SQUIRREL_COPYRIGHT, (int)sizeof(SQInteger) * 8); // 注册全局NutApi GlobaRegisterSquirrel(v); // 加载基础脚本文件 ReloadingScript(v, "/dp_s/Dps_A/"); ReloadingScript(v, "/dp_s/Dps_B/"); ReloadingScript(v, "/dp_s/Dps_C/"); // 执行虚拟机Main函数 SQInteger top = sq_gettop(v); // saves the stack size before the call sq_pushroottable(v); // pushes the global table sq_pushstring(v, _SC("main"), -1); if (SQ_SUCCEEDED(sq_get(v, -2))) { // gets the field 'foo' from the global table sq_pushroottable(v); // push the 'this' (in this case is the global table) sq_call(v, 1, SQFalse, SQTrue); // calls the function } sq_settop(v, top); // restores the original stack size sq_pushroottable(v); sq_pushstring(v, "sq_ReloadScript", -1); sq_newclosure(v, SqReloadScript, 0); // create a new function sq_newslot(v, -3, SQFalse); sq_pop(v, 1); // pops the root table }