步骤2.1:创建一个新的受保护应用程序
在第一阶段,我们制作了几个简单的应用程序来测试授权系统的 API。现在,在第二阶段,我们将只创建一个应用程序。它也将是一个控制台应用程序,其中 foo() 函数仅在注册版本中工作。这是我们的测试应用程序的代码:
#include <windows.h> #include <stdio.h> #include "VMProtectSDK.h" #define PRINT_HELPER(state, flag) if (state & flag) printf("%s ", #flag) void print_state(INT state) { if (state == 0) { printf("state = 0\n"); return; } printf("state = "); PRINT_HELPER(state, SERIAL_STATE_FLAG_CORRUPTED); PRINT_HELPER(state, SERIAL_STATE_FLAG_INVALID); PRINT_HELPER(state, SERIAL_STATE_FLAG_BLACKLISTED); PRINT_HELPER(state, SERIAL_STATE_FLAG_DATE_EXPIRED); PRINT_HELPER(state, SERIAL_STATE_FLAG_RUNNING_TIME_OVER); PRINT_HELPER(state, SERIAL_STATE_FLAG_BAD_HWID); PRINT_HELPER(state, SERIAL_STATE_FLAG_MAX_BUILD_EXPIRED); printf("\n"); } char *read_serial(const char *fname) { FILE *f; if (0 != fopen_s(&f, fname, "rb")) return NULL; fseek(f, 0, SEEK_END); int s = ftell(f); fseek(f, 0, SEEK_SET); char *buf = new char[s + 1]; fread(buf, s, 1, f); buf[s] = 0; fclose(f); return buf; } // foo() 用法很短,但我们需要它是一个单独的函数 // 所以我们要求编译器不要内联编译它 __declspec(noinline) void foo() { printf("我是 foo 函数!\n"); } int main(int argc, char **argv) { char *serial = read_serial("serial.txt"); int res = VMProtectSetSerialNumber(serial); delete [] serial; if (res) { printf("序列号错误\n"); print_state(res); return 0; } printf("序列号正确,调用foo()\n"); foo(); printf("已完成\n"); return 0; }
在没有调试信息的情况下编译程序,但在链接器设置中,我们启用了 MAP 文件的创建 – 我们需要它来使用 VMProtect。运行程序后,我们应该看到以下文本:
序列号错误 state = SERIAL_STATE_FLAG_INVALID
目前,授权系统仍然在测试模式下工作,因为该文件没有经过 VMProtect 处理,并且其中不包含许可模块。在 下一步 我们将创建一个 VMProtect 工程并将尝试保护我们的应用程序。