首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> VC >> VC 教學

VC++ 限制軟體試用次數:利用檔案時間分鐘欄位儲存計數器

     編輯:VC 教學

前言

軟體試用版常需限制使用次數。本文介紹一種隱蔽度較高的方法:將計數器儲存在執行檔自身的「最後修改時間」分鐘欄位(FAT/NTFS 時間戳記結構中第 5-10 位元)。每次啟動遞增,超過上限則拒絕執行。示例使用 DOS 中斷 INT 21h 功能,適用於 16 位元環境教學;32/64 位元 VC++ 應改用 Win32 API GetFileTime/SetFileTime。

時間戳記結構(DOS 格式)

位元15-1110-54-0
含義小時 (0-23)分鐘 (0-59)秒/2 (0-29)

分鐘欄位共 6 位元,可儲存 0-63,足夠作為試用計數器。

教學用 DOS 中斷實作(16 位元)


#include 
#include 

int CheckTrialCount()
{
    union REGS in, out;
    struct SREGS seg;
    unsigned handle, minutes;

    // 1. 開啟自身執行檔
    in.h.ah = 0x3D; in.h.al = 0; // 讀取模式
    segread(&seg);
    in.x.dx = (unsigned)"TEST.EXE"; // 檔名
    intdosx(&in, &out, &seg);
    if (out.x.cflag) return 0; // 開啟失敗
    handle = out.x.ax;

    // 2. 讀取檔案時間
    in.x.ax = 0x5700; in.x.bx = handle;
    intdosx(&in, &out, &seg);
    minutes = (out.x.cx & 0x07E0) >> 5; // 取出分鐘位元

    if (minutes < 40) { // 試用上限 40 次
        // 3. 遞增分鐘並寫回
        in.x.ax = 0x5701; in.x.bx = handle;
        in.x.cx = out.x.cx + 0x0020; // 分鐘 +1 (bit 5)
        in.x.dx = out.x.dx;
        intdosx(&in, &out, &seg);

        // 4. 關閉檔案
        in.h.ah = 0x3E; in.x.bx = handle;
        intdosx(&in, &out, &seg);
        return 2; // 允許試用
    }

    // 關閉檔案
    in.h.ah = 0x3E; in.x.bx = handle;
    intdosx(&in, &out, &seg);
    return 1; // 次數用盡
}

int main()
{
    int ret = CheckTrialCount();
    if (ret == 0) printf("開啟檔案失敗,請勿竄改!\n");
    else if (ret == 1) printf("試用次數已達上限!\n");
    else printf("歡迎試用!剩餘 %d 次。\n", 40 - (ret==2?1:0));
    return 0;
}

32/64 位元 VC++ 正確實作(Win32 API)


#include 

bool IncrementTrialCount(LPCTSTR exePath, int maxTrials = 40)
{
    HANDLE hFile = CreateFile(exePath, GENERIC_READ | GENERIC_WRITE,
                              FILE_SHARE_READ, NULL, OPEN_EXISTING,
                              FILE_ATTRIBUTE_NORMAL, NULL);
    if (hFile == INVALID_HANDLE_VALUE) return false;

    FILETIME ftCreate, ftAccess, ftWrite;
    if (!GetFileTime(hFile, &ftCreate, &ftAccess, &ftWrite)) {
        CloseHandle(hFile); return false;
    }

    // 轉為 SYSTEMTIME 方便操作
    SYSTEMTIME st;
    FileTimeToSystemTime(&ftWrite, &st);

    if (st.wMinute < maxTrials) {
        st.wMinute += 1;
        SystemTimeToFileTime(&st, &ftWrite);
        SetFileTime(hFile, &ftCreate, &ftAccess, &ftWrite);
        CloseHandle(hFile);
        return true; // 允許
    }

    CloseHandle(hFile);
    return false; // 超過上限
}

安全性與局限性分析

  • 隱蔽性:一般使用者不會注意檔案時間分鐘變化。
  • 易繞過:工具(如 Touch、Attribute Changer)可輕易修改時間;複製檔案會重置時間。
  • 副作用:修改執行檔時間可能觸發防毒軟體警示、影響數位簽章驗證、破壞增量備份邏輯。
  • 現代替代方案:註冊表、隱藏檔案、雲端驗證、硬體鎖、加密授權檔等更健全。

教學價值

本方法展示了檔案系統中繼資料的結構與底層 API 操作,適合理解 FILETIME、INT 21h、GetFileTime/SetFileTime 機制,實際商業軟體保護請採用成熟授權方案。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved