⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 cmds.cpp

📁 查看硬體編號
💻 CPP
📖 第 1 页 / 共 5 页
字号:
        //
        // skip this
        //
        return EXIT_OK;
    }

    rmdParams.ClassInstallHeader.cbSize = sizeof(SP_CLASSINSTALL_HEADER);
    rmdParams.ClassInstallHeader.InstallFunction = DIF_REMOVE;
    rmdParams.Scope = DI_REMOVEDEVICE_GLOBAL;
    rmdParams.HwProfile = 0;
    if(!SetupDiSetClassInstallParams(Devs,DevInfo,&rmdParams.ClassInstallHeader,sizeof(rmdParams)) ||
       !SetupDiCallClassInstaller(DIF_REMOVE,Devs,DevInfo)) {
        //
        // failed to invoke DIF_REMOVE
        //
        action = pControlContext->strFail;
    } else {
        //
        // see if device needs reboot
        //
        devParams.cbSize = sizeof(devParams);
        if(SetupDiGetDeviceInstallParams(Devs,DevInfo,&devParams) && (devParams.Flags & (DI_NEEDRESTART|DI_NEEDREBOOT))) {
            //
            // reboot required
            //
            action = pControlContext->strReboot;
            pControlContext->reboot = TRUE;
        } else {
            //
            // appears to have succeeded
            //
            action = pControlContext->strSuccess;
        }
        pControlContext->count++;
    }
    _tprintf(TEXT("%-60s: %s\n"),devID,action);

    return EXIT_OK;
}

int cmdRemove(__in LPCTSTR BaseName, __in LPCTSTR Machine, __in DWORD Flags, __in int argc, __in_ecount(argc) TCHAR* argv[])
/*++

Routine Description:

    REMOVE
    remove devices

Arguments:

    BaseName  - name of executable
    Machine   - machine name, must be NULL
    argc/argv - remaining parameters

Return Value:

    EXIT_xxxx

--*/
{
    GenericContext context;
    TCHAR strRemove[80];
    TCHAR strReboot[80];
    TCHAR strFail[80];
    int failcode = EXIT_FAIL;

    if(!argc) {
        //
        // arguments required
        //
        return EXIT_USAGE;
    }
    if(Machine) {
        //
        // must be local machine as we need to involve class/co installers
        //
        return EXIT_USAGE;
    }
    if(!LoadString(NULL,IDS_REMOVED,strRemove,ARRAYSIZE(strRemove))) {
        return EXIT_FAIL;
    }
    if(!LoadString(NULL,IDS_REMOVED_REBOOT,strReboot,ARRAYSIZE(strReboot))) {
        return EXIT_FAIL;
    }
    if(!LoadString(NULL,IDS_REMOVE_FAILED,strFail,ARRAYSIZE(strFail))) {
        return EXIT_FAIL;
    }

    context.reboot = FALSE;
    context.count = 0;
    context.strReboot = strReboot;
    context.strSuccess = strRemove;
    context.strFail = strFail;
    failcode = EnumerateDevices(BaseName,Machine,DIGCF_PRESENT,argc,argv,RemoveCallback,&context);

    if(failcode == EXIT_OK) {

        if(!context.count) {
            FormatToStream(stdout,MSG_REMOVE_TAIL_NONE);
        } else if(!context.reboot) {
            FormatToStream(stdout,MSG_REMOVE_TAIL,context.count);
        } else {
            FormatToStream(stdout,MSG_REMOVE_TAIL_REBOOT,context.count);
            failcode = EXIT_REBOOT;
        }
    }
    return failcode;
}

int cmdRescan(__in LPCTSTR BaseName, __in LPCTSTR Machine, __in DWORD Flags, __in int argc, __in_ecount(argc) TCHAR* argv[])
/*++

Routine Description:

    RESCAN
    rescan for new devices

Arguments:

    BaseName  - name of executable
    Machine   - machine name, must be NULL
    argc/argv - remaining parameters

Return Value:

    EXIT_xxxx

--*/
{

    //
    // reenumerate from the root of the devnode tree
    // totally CM based
    //
    int failcode = EXIT_FAIL;
    HMACHINE machineHandle = NULL;
    DEVINST devRoot;

    if(Machine) {
        if(CM_Connect_Machine(Machine,&machineHandle) != CR_SUCCESS) {
            return failcode;
        }
    }

    if(CM_Locate_DevNode_Ex(&devRoot,NULL,CM_LOCATE_DEVNODE_NORMAL,machineHandle) != CR_SUCCESS) {
        goto final;
    }

    FormatToStream(stdout,Machine ? MSG_RESCAN : MSG_RESCAN_LOCAL);

    if(CM_Reenumerate_DevNode_Ex(devRoot, 0, machineHandle) != CR_SUCCESS) {
        goto final;
    }

    FormatToStream(stdout,MSG_RESCAN_OK);

    failcode = EXIT_OK;

final:
    if(machineHandle) {
        CM_Disconnect_Machine(machineHandle);
    }

    return failcode;
}

int cmdClassFilter(__in LPCTSTR BaseName, __in LPCTSTR Machine, __in DWORD Flags, __in int argc, __in_ecount(argc) TCHAR* argv[])
/*++

Routine Description:

    CLASSFILTER <name> <type> <subcmds>
    Allows tweaking of class filters
    Useful for filter driver development and for Product Support

    <subcmds> is a list of the following:
    @service - sets 'after' to the first match of service after 'after'
               (reset to -1 after any other command)
    !service - deletes first match of 'service' after 'after'
    -service - insert new service directly prior to 'after', or at start
    +service - insert new service directly after 'after', or at end

    if no <subcmds> given, list the services

Arguments:

    BaseName  - name of executable
    Machine   - if non-NULL, remote machine
    argc/argv - remaining parameters - list of class names

Return Value:

    EXIT_xxxx

--*/
{
    int failcode = EXIT_FAIL;
    int argIndex;
    DWORD numGuids = 0;
    GUID guid;
    LPTSTR regval = NULL;
    HKEY hk = (HKEY)INVALID_HANDLE_VALUE;
    LPTSTR * multiVal = NULL;
    int after;
    bool modified = false;
    int span;
    SC_HANDLE SCMHandle = NULL;
    SC_HANDLE ServHandle = NULL;

    if((argc<2) || !argv[0][0]) {
        return EXIT_USAGE;
    }

    //
    // just take the first guid for the name
    //
    if(!SetupDiClassGuidsFromNameEx(argv[0],&guid,1,&numGuids,Machine,NULL)) {
        if(GetLastError() != ERROR_INSUFFICIENT_BUFFER) {
            goto final;
        }
    }
    if(numGuids == 0) {
        goto final;
    }
    if(_tcsicmp(argv[1],TEXT("upper"))==0) {
        regval = REGSTR_VAL_UPPERFILTERS;
    } else if(_tcsicmp(argv[1],TEXT("lower"))==0) {
        regval = REGSTR_VAL_LOWERFILTERS;
    } else {
        failcode = EXIT_USAGE;
        goto final;
    }

    hk = SetupDiOpenClassRegKeyEx(&guid,
                                  KEY_READ | (argc>2 ? KEY_WRITE : 0),
                                  DIOCR_INSTALLER,
                                  Machine,
                                  NULL
                                 );
    if(hk == INVALID_HANDLE_VALUE) {
        goto final;
    }
    multiVal = GetRegMultiSz(hk,regval);

    if(argc<=2) {
        //
        // just display
        //
        FormatToStream(stdout,MSG_CLASSFILTER_UNCHANGED);
        DumpArray(1,multiVal);
        failcode = EXIT_OK;
        goto final;
    }
    after = -1; // for the @service expressions
    span =  1;

    if(!multiVal) {
        multiVal = CopyMultiSz(NULL);
        if(!multiVal) {
            goto final;
        }
    }

    for(argIndex=2;argIndex<argc;argIndex++) {
        if((argv[argIndex] == NULL) ||
           (!argv[argIndex])) {
            failcode = EXIT_USAGE;
            break;
        }

        int op = argv[argIndex][0];
        LPTSTR serv = argv[argIndex]+1;
        int mark = 0;
        int cnt;
        int ent;
        LPTSTR * tmpArray;

        if(op == TEXT('=')) {
            after = -1;
            span = 1;
            op = serv[0];
            if(!op) {
                continue;
            }
            serv++;
        }

        if(!serv[0]) {
            failcode = EXIT_USAGE;
            goto final;
        }

        if((op == TEXT('@')) || (op == TEXT('!'))) {
            //
            // need to find specified service in list
            //
            for(after+=span;multiVal[after];after++) {
                if(_tcsicmp(multiVal[after],serv)==0) {
                    break;
                }
            }
            if(!multiVal[after]) {
                goto final;
            }
            if(op == TEXT('@')) {
                //
                // all we needed to do for '@'
                //
                span = 1; // span of 1
                continue;
            }
            //
            // we're modifying
            //
            int c;
            for(c = after;multiVal[c];c++) {
                multiVal[c] = multiVal[c+1];
            }
            LPTSTR * newArray = CopyMultiSz(multiVal);
            if(!newArray) {
                goto final;
            }
            DelMultiSz(multiVal);
            multiVal = newArray;
            span = 0; // span of 0 (deleted)
            modified = true;
            continue;
        }

        if(op == '+') {
            //
            // insert after
            //
            if(after<0) {
                int c;
                for(c = 0;multiVal[c];c++) {
                    // nothing
                }
                mark = c;
            }
            else {
                mark = after+span;
            }
        } else if(op == '-') {
            //
            // insert before
            //
            if(after<0) {
                mark = 0;
            } else {
                mark = after;
            }
        } else {
            //
            // not valid
            //
            failcode = EXIT_USAGE;
            goto final;
        }
        //
        // sanity - see if service exists
        //
        if(!(SCMHandle = OpenSCManager(Machine, NULL, GENERIC_READ))) {
            goto final;
        }
        ServHandle = OpenService(SCMHandle,serv,GENERIC_READ);
        if(ServHandle) {
            CloseServiceHandle(ServHandle);
        }
        CloseServiceHandle(SCMHandle);
        if(!ServHandle) {
            goto final;
        }

        //
        // need an array a little bigger
        //
        for(cnt = 0;multiVal[cnt];cnt++) {
            // nothing
        }

        tmpArray = new LPTSTR[cnt+2];
        if(!tmpArray) {
            goto final;
        }
        for(ent=0;ent<mark;ent++) {
            tmpArray[ent] = multiVal[ent];
        }
        tmpArray[ent] = serv;
        for(;ent<cnt;ent++) {
            tmpArray[ent+1] = multiVal[ent];
        }
        tmpArray[ent+1] = NULL;
        LPTSTR * newArray = CopyMultiSz(tmpArray);
        delete [] tmpArray;
        if(!newArray) {
            goto final;
        }
        DelMultiSz(multiVal);
        multiVal = newArray;
        modified = true;
        span = 1;
        after = mark;
    }

    if(modified) {
        if(multiVal[0]) {
            int len = 0;
            LPTSTR multiSz = multiVal[-1];
            LPTSTR p = multiSz;
            while(*p) {
                p+=lstrlen(p)+1;
            }
            p++; // skip past null
            len = (p-multiSz)*sizeof(TCHAR);
            LONG err = RegSetValueEx(hk,regval,0,REG_MULTI_SZ,(LPBYTE)multiSz,len);
            if(err==NO_ERROR) {
                FormatToStream(stdout,MSG_CLASSFILTER_CHANGED);
                DumpArray(1,multiVal);
                failcode = EXIT_REBOOT;
            }
        } else {
            LONG err = RegDeleteValue(hk,regval);
            if((err == NO_ERROR) || (err == ERROR_FILE_NOT_FOUND)) {
                FormatToStream(stdout,MSG_CLASSFILTER_CHANGED);
                failcode = EXIT_REBOOT;
            }
        }
    } else {
        FormatToStream(stdout,MSG_CLASSFILTER_UNCHANGED);
        DumpArray(1,multiVal);
        failcode = EXIT_OK;
    }

final:

    if(multiVal) {
        DelMultiSz(multiVal);
    }
    if(hk != (HKEY)INVALID_HANDLE_VALUE) {
        RegCloseKey(hk);
    }

    return failcode;
}

int SetHwidCallback(__in HDEVINFO Devs, __in PSP_DEVINFO_DATA DevInfo, __in DWORD Index, __in LPVOID Context)
/*++

Routine Description:

    Callback for use by SetHwid

Arguments:

    Devs    )_ uniquely identify the device
    DevInfo )
    Index    - index of device
    Context  - SetHwidContext

Return Value:

    EXIT_xxxx

--*/
{
    SP_REMOVEDEVICE_PARAMS rmdParams;
    SetHwidContext *pControlContext = (SetHwidContext*)Context;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -