|
|
(dlutyuanhongl发表于2005-3-15 23:14:04)6 n- ?$ l3 `6 g0 n% Z6 D
0 K; z4 U: {0 g' A这几天,由于工作的实际需要,需要对光驱,软驱,USB的启用和禁用实现控制。参考大家提供的对网卡禁用的代码,实现了光驱,软驱,USB的启用和禁用。主要实现代码如下:9 m! M1 d/ A' O, I6 Q6 r1 t0 B3 o
// 必要的头文件和要链接的LIB文件
$ c+ x/ w& O+ {' c6 d#include <setupapi.h>
, D$ P7 k8 x. f( Y3 P& g#include <shlwapi.h>& g! G: ^3 i, Y. g: @" A. W/ M
#pragma comment(lib, "setupapi.lib")
" q i& P3 J' K+ t#pragma comment(lib, "shlwapi.lib")
- D8 p$ H5 H/ v. g1 @
W9 E' s$ k; O& |# g// device information set(我把它译为设备信息集)0 P8 u! v A' E: d& [$ A
HDEVINFO hDevInfo = NULL;7 j \$ h* |' E9 Y* n
$ ^( V2 M- H" @0 T+ g
// 出错信息- [* }$ I: v8 l
void FormatMSG(DWORD dwError, LPTSTR * lpszMsg)& J9 o/ t$ N$ u8 B5 _$ u. M
{ t4 f1 Y( f$ s9 L9 V
BOOL bOk = FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM ! F9 u% h9 N* \# u6 G' M
| FORMAT_MESSAGE_ALLOCATE_BUFFER,
# v9 B8 Y0 V: I- _ NULL,* [. u; r O8 n; K9 K% z
dwError," }+ F+ X8 q1 T! b) x3 w0 X
MAKELANGID(LANG_CHINESE, SUBLANG_CHINESE_SIMPLIFIED),+ {; N/ g( |' g
(LPTSTR)lpszMsg,0 |: K( {. W G4 L
0,$ e+ H% H1 Q; |! q# w
NULL);, o* P) p8 H- j7 l6 ^- {: y" b
6 M6 s3 q3 Z+ ^if (!bOk)8 ?, r# {8 w; c/ ]$ i
{$ H* N: }/ _0 R& r4 I& B, Z
HMODULE hDll = LoadLibraryEx(_T("netmsg.dll"),' \7 C/ _, T- w' P' T
NULL,
9 ~+ u, C' r ~& }% F B DONT_RESOLVE_DLL_REFERENCES);' L0 ?) {/ h! y- `; V5 b( a
if (NULL != hDll)
- |' K/ D- Z" h# x" b/ d {
8 G$ M. r7 S9 S: ] FormatMessage(FORMAT_MESSAGE_FROM_HMODULE |
$ b4 g' }( V0 B. F3 n6 ~% ^ FORMAT_MESSAGE_FROM_SYSTEM,
1 n) `$ i" P; h) E# I hDll,
8 S; G" w' ? Q/ ] dwError,
% C I7 `1 B; U1 e( c# E1 X. H MAKELANGID(LANG_CHINESE, SUBLANG_CHINESE_SIMPLIFIED),
& N; D! N0 j7 h/ V$ l (LPTSTR)lpszMsg,. x1 z, c, o# u( a7 I
0,
' u; V$ J W) S" u NULL);
8 ~/ y/ I* G: ^/ c s FreeLibrary(hDll);. {9 U o! j' T' y
}6 a+ O5 ]4 e. l8 {
}: S) G. E0 \' k6 O( p& Z
}" R, V v7 c# I! g& E! S
, c6 p3 \- c/ c. Q0 @BOOL ChangeStatus(DWORD NewStatus,
& q4 ]5 D* Y" X DWORD SelectedItem, + A' D0 _. p. j* T d! ?' B6 p, ^# q
HDEVINFO hDevInfo)8 W. P0 x p1 G- h0 G( N
{; t* X/ n2 F( I( L
LPTSTR lpszMsg = NULL;
1 p/ |" {9 F5 T# I6 h% IHCURSOR hCursor = NULL;
, f; y3 L& T. ]: { ztry% L$ l" T9 F2 x0 Y9 X
{
9 {8 g7 ^4 ` [! X( \( ] SP_PROPCHANGE_PARAMS PropChangeParams = 2 f( ^' p5 q( }3 S( \0 X
{sizeof(SP_CLASSINSTALL_HEADER)};) G/ s5 q4 X- W# ?+ [# g9 R
SP_DEVINFO_DATA DeviceInfoData = {sizeof(SP_DEVINFO_DATA)};
5 w$ Y& z# k ]& V0 h' y* W3 H4 o B; |
hCursor = SetCursor(LoadCursor(NULL, IDC_WAIT));0 I" G: V+ G+ {; t' I7 B/ ]( m
6 d% L6 d& Z- [2 [# p4 H0 q9 n2 w
// Get a handle to the Selected Item.
; k- d) W8 x. i, ~4 d- _ if (!SetupDiEnumDeviceInfo(hDevInfo, SelectedItem, &DeviceInfoData)). F/ \1 _. y$ J1 Q* w9 }
{* K) D0 A7 m0 o* S
FormatMSG(GetLastError(), &lpszMsg);
# i2 k0 y: w' \ throw lpszMsg;' k* k+ `# I3 q) ^
}) J; J4 X' }; ]) k+ K1 v1 P* }0 @
, ]2 n/ s, W0 T% _# b6 c4 ]
// Set the PropChangeParams structure.9 x) I( s9 Q3 K
PropChangeParams.ClassInstallHeader.InstallFunction = 8 O# @4 N# h9 D2 k, Q
DIF_PROPERTYCHANGE;" s0 Q! w6 ^# f
PropChangeParams.Scope = DICS_FLAG_GLOBAL;. D' C, Z9 N" h6 ` i! @
PropChangeParams.StateChange = NewStatus;
6 x ]( v8 @5 O ^. P
. w. G& {4 o4 d- f if (!SetupDiSetClassInstallParams(hDevInfo,/ A7 c3 q8 a, k: r
&DeviceInfoData,
7 C r) ?' H6 I2 z0 R (SP_CLASSINSTALL_HEADER *)& ropChangeParams,
$ N% |/ H+ m* F$ k sizeof(PropChangeParams)))
3 @0 W+ Z+ v* R3 s1 \ {5 T5 a& g- F0 v
FormatMSG(GetLastError(), &lpszMsg);- b* G( y2 Y% @2 f! ~0 u
throw lpszMsg;$ |3 x0 L+ \$ T/ M) }# k3 c
}- E! J6 E4 }1 t5 ]( }+ ~
/ ~* v1 ?: D S9 y) A8 P6 g/ V // Call the ClassInstaller and perform the change.( M( H1 `1 o( E7 D% R
if (!SetupDiCallClassInstaller(DIF_PROPERTYCHANGE,
8 n" ^* m' D) t( Y0 k% b hDevInfo,6 _, }; \6 i" J7 [$ d7 l
&DeviceInfoData))
. W5 Z3 e( P' M t+ K H {# q- I) n2 J9 s n7 g* x# y
FormatMSG(GetLastError(), &lpszMsg);
* i0 l1 ]# ]4 A throw lpszMsg;8 E9 l' e' v4 w/ o
}
7 B2 p' c7 D( z( G8 i
1 N. K7 P& N @1 {7 ~4 O+ A( L SetCursor(hCursor); 9 S0 I2 M+ M: w
return TRUE;4 n& Q$ J8 E7 A4 E) `* f0 ?
}) I4 ~. U' |1 {+ `9 r, D
catch (TCHAR * pszError)2 |: C1 \# h6 o4 @
{ `5 \5 k# Q4 F9 D. a$ H! d
SetCursor(hCursor);7 {' Q, o# v& V* q4 W8 w
::MessageBox(NULL,! C4 g& s" H; y( x& T# Y
pszError,. K! m5 O, E& x \- ?! c
_T("提示"),
! R# o7 F! |6 @- B2 ~7 Q4 S9 E MB_OK);
4 F! b* E" S, G0 p: W! t& v4 p if (NULL != lpszMsg) c/ k: c Z6 X. s8 t
{
: m5 a q1 C( B1 r& L- a% \ LocalFree((HLOCAL)lpszMsg);
; F3 P& T0 \% b2 V$ @/ Y8 D } " b K8 }( N, p" e, e$ r
return FALSE;
* x, M- y9 p- n8 o}
: e' `. w% D9 l' G- x% d5 b- h}% E3 b4 z( s7 g- l
( q( f9 ^- v: X1 F// 这些设备的启用和禁用主要有此函数实现1 ^, C- M k. ^ e3 b- Z5 O
// 参数说明,nStatus 可取3个值,-1 :啥也不做
. ?) D& g0 J! S w( A( ^// 0 禁用设备,1启用设备。
! N: N5 z0 w/ ?5 X6 T, l: _& i6 z// nIndex用于控制是对光驱,软驱还是对USB启用或禁用% \' ?, t5 t5 P& D4 Q) h
// 也是可取3个值,0 代表软驱,1 代表光驱
3 X% s4 p8 T, J+ n1 c/ a// 2 代表USB1 ^' j' ?9 d8 [9 |% v
// 譬如要对光驱实现禁用,可以这样调用此函数
& b @$ k" u/ Z// ControlDisk(0, 1);8 e4 j9 Q$ v! _: o1 F7 S, o8 z
BOOL ControlDisk(int nStatus, int nIndex)5 r" a7 T7 L8 [6 m) f$ N& Q$ ]1 Y) f
{
: w) b) o% r+ j& B) Dif (-1 == nStatus)
$ W6 P- D, N w; u( C{
! y) x0 {$ M& B return FALSE;7 ?2 @0 q/ |% s+ s- r
} # E0 _1 c$ ], d) r
# _1 n% p" V: n( H. B
LPTSTR lpszMsg = NULL;
. W! K7 Y& J! Y5 z, E! {try
h. j- x- i. r0 [{6 v+ F: j7 l2 G+ A
TCHAR * GUIDString = NULL;+ m$ p5 g/ k/ v0 J9 d5 z
GUID guid;: z8 J7 u6 i' o) B$ Z8 Y% k3 M& F
ZeroMemory(&guid, sizeof(GUID));) W, R" c- m- \! q3 p! @
switch(nIndex)
6 p2 s V0 M3 b, o: C( R {
# d' O# ^: b" R6 K case 0: // 0 代表软驱
) F. P0 r8 [5 O5 N% F GUIDString = _T("4D36E980-E325-11CE-BFC1-08002BE10318");
3 D, h( B0 l# S* U UuidFromString((unsigned char *)GUIDString, &guid);
5 ?: m7 f3 j' p* \ break;
/ G: y. x) K0 D6 `4 F case 1: // 1 代表光驱 ) H. o: o; ]3 r+ W7 [
GUIDString = _T("4D36E965-E325-11CE-BFC1-08002BE10318");5 P: f" L) [# y% z9 P# A+ U
UuidFromString((unsigned char *)GUIDString, &guid);; v- N3 g" o) F/ I' Y$ ~. `
break;
" ~4 P3 Y% `. X! f2 M8 O- x2 h case 2: // 2 代表USB, W. G% f' a$ q! Y
GUIDString = _T("36FC9E60-C465-11CF-8056-444553540000");
' E7 W; E+ O$ U, @ UuidFromString((unsigned char *)GUIDString, &guid);. p! n( O' P6 X- m
break;
5 m+ d6 b) S0 X' \ }
% K6 H* D: l, \- _% M4 c4 |
) Y+ K! l( p( H1 A" W6 t% } hDevInfo = SetupDiGetClassDevs(&guid,
6 v4 i" {/ _7 Y; Q& r! l T NULL,( ]2 ?( L W3 p5 J# u; \; P
NULL,
( T. O/ _) Y; V5 O% G! K DIGCF_PRESENT);- s- u8 U0 ?+ m# c. G2 K$ _ x+ @% ?# ~
if (INVALID_HANDLE_VALUE == hDevInfo)
0 q' @0 v4 K; h- ?# ? {) \# \% r* }% ]" ~/ v# ?
FormatMSG(GetLastError(), &lpszMsg);
, g2 C0 n! Q5 P; @, m; y throw lpszMsg; M5 N) l# v$ W0 [2 @% a
}2 p1 V' c: B$ U0 C) O
" f9 ?) l: o- j) ?0 Q% Q, J DWORD i;
( p! L+ d# `# P* |: q& E. o SP_DEVINFO_DATA DeviceInfoData;
" H% D: I: P, X' d3 D8 V ZeroMemory(&DeviceInfoData, sizeof(SP_DEVINFO_DATA));
4 j- q& P( ~3 S" w0 h* w- M1 Q DeviceInfoData.cbSize = sizeof(SP_DEVINFO_DATA);
" B1 }& j: }5 b4 l" H, E1 S: b& ~4 B; v$ ^! Z& t) h. C$ W2 [
for (i = 0; SetupDiEnumDeviceInfo(hDevInfo, i, &DeviceInfoData); ++i)
# O( M m% L$ a- t {
' w# z r; B! H* d9 C- p5 R if (1 == nStatus)* Q! x F F' [) h
{0 n/ P Z: D# O w2 ^+ N
StateChange(DICS_ENABLE, i, hDevInfo);
2 _# j: y: f( l }
. a- c# z4 @: B+ t# Q, p else if (0 == nStatus)
+ J. @$ p5 M; x3 K& p {' P" r& E: P7 N: g- q
StateChange(DICS_DISABLE, i, hDevInfo);
9 h7 T9 p" s1 [ } 6 Y9 L7 s a: V+ E' H6 s/ f# X* f
} A- }2 H& ]6 x9 L! p9 i. V
+ X2 u0 u; L+ U, h- h6 ^ // 释放 device information set
1 `) e9 g) @+ K3 b: l- o. X8 o return SetupDiDestroyDeviceInfoList(hDevInfo);
# q! F: O8 H( o, ^}
/ k7 y6 b a3 `catch (TCHAR * pszError)0 g$ B8 o6 R, j' Y6 b6 |. z! m# `5 P
{' i1 C' c! b$ O$ H8 \' l: }
::MessageBox(NULL,6 A" r$ f! M! ^) J; f
pszError,+ H5 t) r) @7 F& ~8 R4 y
_T("提示"),
5 ~, ^3 z) I' C7 j) C5 O MB_OK);
4 `* U& \) p% Y0 f0 N! e+ C if (NULL != lpszMsg)
# n! J* t( | O" b {* I, [3 S, H6 W# f/ K; X; S
LocalFree((HLOCAL)lpszMsg);
& H( s; y1 ^; I I! N4 d }
1 Z$ _* w8 \, g) [5 A return FALSE;
- n, x7 ^9 u) n# S9 r& \* i7 {}
5 ?! d7 C2 m# Nreturn FALSE;
- q% }& V( g- N |7 u9 P, X}
( [. p" k6 l- G2 B5 n( y
2 D5 p' B! |+ P# j5 C( c' H H 经测试这样对光驱,软驱和USB实现禁用没有问题,但是当禁用过之后如果要对USB实现启用必须两次调用ControlDisk(1, 2);这个函数才可,其余的两个启用没什么问题。还有要说的就是我不是用的枚举所有的设备,然后再过滤(网上的那个禁用网卡的就是这种方法)。( r# `/ H9 B$ ^. Z; b: v! \
据我观察,在注册表的此项下下:
: J y/ z, r) i HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Class\
8 {/ |5 B1 z2 b5 S6 { 有很多GUID,每个GUID代表一个设备,譬如这个是USB的
. o; ` q* M: I" i2 q% G {36FC9E60-C465-11CF-8056-444553540000}
) Z% H+ `% i# D" M; i/ V 这个是CDROM的 P9 x8 V6 \) q' _/ u9 o/ ~
{4D36E965-E325-11CE-BFC1-08002BE10318}等等了。- R5 Y% e; y' l
这些值你即使把它改为别的GUID,我使用原来的GUID仍然可以实现我的功能。 |
|