|
|
楼主 |
发表于 2011-7-15 17:28:52
|
显示全部楼层
以下有关upnp的接口来自emule,
$ L4 V7 e$ w( o4 x& h9 ] C5 b+ k+ M4 T0 r+ N
( T. J# C/ L* }8 L, Z5 U; K///////////////////////////////////////////
6 I- t. S1 B4 h7 p+ O//upnp的抽象接口类,只需调用这些接口即可实现端口映射功能.
9 N- F+ j" j1 `% X/ i1 g* x
8 |# q( |2 Z8 [% @. c. W
0 j! i) M6 ]$ l" l H l# p5 h#pragma once# n( S: Y, G- l: q s+ H
#include <exception>
5 t; u, z) ]2 H# k0 L* a. O' U7 t2 w. J: s) M
+ Q7 q6 u) i4 V8 V3 ^! @
enum TRISTATE{ }% D& v; G6 e9 ~2 q Y
TRIS_FALSE,; L) [1 V% b. E9 J/ f0 Z; r
TRIS_UNKNOWN,& I) x5 B: {$ e, k3 `- T2 A, A
TRIS_TRUE
- ]0 U2 I; m! |9 H3 M5 n5 B1 m};% a/ o- P/ t9 q1 n
2 t Q2 R _8 @# C* M% ~2 q$ H
% { k# d$ L5 o( \2 c3 venum UPNP_IMPLEMENTATION{
3 l; e0 @! L. t) V. {* o! a! F UPNP_IMPL_WINDOWSERVICE = 0,- ]2 A8 J9 K; E: j. m1 r
UPNP_IMPL_MINIUPNPLIB,
* U7 s$ K3 X4 Z- k/ i c UPNP_IMPL_NONE /*last*/3 |( c: C, }2 D$ m2 }/ f O/ h6 L
};4 A6 G! A' U; k+ e4 s% t. [* z' j
# H4 q; m5 j8 C* V2 C5 M$ S
5 E0 [9 A }' }; X& |2 [
) U' {- F5 n" S. i* a/ |9 g; V. H% Z) j; c
class CUPnPImpl+ d+ M1 w( I: S- V4 S
{
2 A2 M3 M5 e' v+ T- z/ fpublic:) j3 ?5 o; ~7 k4 B3 [8 y3 c2 T
CUPnPImpl();
" _& j' w. c0 A- }. u. l virtual ~CUPnPImpl();+ [4 |$ p" a( O/ F0 H
struct UPnPError : std::exception {};- _: P' l7 t+ ~+ E. I
enum {
2 z1 y2 q* E5 Y# y, d/ x0 v& Q7 ` UPNP_OK,; t' g, E/ n( J* O
UPNP_FAILED,5 J! r/ K8 i7 Q( _; t
UPNP_TIMEOUT
8 ^7 R3 m) A! P6 Y };! `9 D2 Y: z$ X
& }& Y6 p& ~% `; v5 m! d }+ p8 H- n1 G
virtual void StartDiscovery(uint16 nTCPPort, uint16 nUDPPort, uint16 nTCPWebPort) = 0;4 M9 W. e- w& {* b. W G
virtual bool CheckAndRefresh() = 0;) U' K6 |; P" W3 [: ]" Z1 o
virtual void StopAsyncFind() = 0;+ h i- \- N) k' P
virtual void DeletePorts() = 0;0 v) e$ u0 z! I+ `5 @2 w# D
virtual bool IsReady() = 0;) _- u, g$ ^2 d% k
virtual int GetImplementationID() = 0;
* |2 x; I: }# x; m4 J . n+ {8 f$ S4 O$ l0 A
void LateEnableWebServerPort(uint16 nPort); // Add Webserverport on already installed portmapping/ q% D: L4 l; v
; ^ U9 Z3 B7 F0 P o! X% T3 A
9 I% Z0 l5 S* _$ p void SetMessageOnResult(HWND hWindow, UINT nMessageID);
1 v1 g0 Q/ m8 y8 [# a TRISTATE ArePortsForwarded() const { return m_bUPnPPortsForwarded; }- ^! s2 Q9 }6 v1 f! @) M5 J. u- m
uint16 GetUsedTCPPort() { return m_nTCPPort; }
! ]& Q( r+ w/ z/ B uint16 GetUsedUDPPort() { return m_nUDPPort; }
, D& w# i9 f& e! _0 @$ s. l# x! }
* O+ ?9 R# h" O ]4 O& u& z- r8 A, {8 ^6 u- X( u
// Implementation+ j& [% @, Q* k% o8 R
protected:# N! z" [& |1 e; S
volatile TRISTATE m_bUPnPPortsForwarded;; y& P3 t) [! r, M4 y
void SendResultMessage();# {7 C( O# d7 B& _
uint16 m_nUDPPort;
, d% v, ~, S$ e uint16 m_nTCPPort;) ?" k' @+ H+ W5 S+ ]1 d' S: N
uint16 m_nTCPWebPort;- Q [0 z: o, I, j3 {# f, S
bool m_bCheckAndRefresh;4 w3 ^. B% B4 i
# e0 y# ?% [. t) ?" c( ?. L! x" T
) k: F9 v; |" X k( L7 S
private:
3 ^! u0 }0 l; L$ Q HWND m_hResultMessageWindow;
, C1 y z# c. F; G2 ]* |) C6 ` UINT m_nResultMessageID;. x$ Q% L1 B1 F4 D P5 U! |' m4 {
6 u0 V5 y* `+ _
. h% Q, `" ?' U; T
};7 c! J7 i) a+ S( n7 z2 A
3 y$ ^' R# G& Z
9 J8 F: [( w+ P' b! G h// Dummy Implementation to be used when no other implementation is available& m7 [) e3 X' v' d$ d# i/ l9 @0 e
class CUPnPImplNone: public CUPnPImpl( p5 T( t2 }: P! ?% k* P O
{+ V% @: T! a& o
public:
) P: I* [* ?# Z$ v4 Q virtual void StartDiscovery(uint16, uint16, uint16) { ASSERT( false ); }
8 |+ a- H1 V( k, R. T virtual bool CheckAndRefresh() { return false; }
- U- g0 L9 J4 V5 x( }5 Z virtual void StopAsyncFind() { }# y @, |) ?! L: R
virtual void DeletePorts() { }
% |: i3 i' ]1 u- g7 b virtual bool IsReady() { return false; }
0 ^! j! r8 ]4 u6 W0 ]0 X/ m virtual int GetImplementationID() { return UPNP_IMPL_NONE; }
/ K8 n3 I+ D5 I! x};1 _2 J- Z/ Z% q1 g6 @' ]
' s+ j& T: j0 V& R5 {1 v) g5 v" }2 H. W
- m' n2 F2 k$ l+ K5 A. \
/////////////////////////////////////
0 _2 I: @6 z5 T//下面是使用windows操作系统自带的UPNP功能的子类8 S0 A& i/ J. D$ m9 _) W0 E
2 k5 {* P" s3 Q" b! z" u9 T
/ F' r! z8 z, @1 ~8 ]4 s: ^# x2 t
#pragma once; T' t5 |$ Q( l# g Q
#pragma warning( disable: 4355 )
. M% C8 c$ V) U5 z2 @) a3 h' t0 b7 D1 r- e' A* {% u/ |9 i( y
1 e7 t# ^) ?1 T3 ~' g7 J2 i
#include "UPnPImpl.h"
+ f0 g' T# | \6 K" L#include <upnp.h>7 ~' j3 ]- O R8 M5 e# c
#include <iphlpapi.h>4 z+ H1 f+ F `# i9 K
#include <comdef.h># ~( F! v( v+ }
#include <winsvc.h>
- m$ D5 e T% @% ?# n( `# t4 {: G% S ?- H! v* b
5 n" d5 ?, A" V5 `1 P0 `: B$ X, n
#include <vector>. U5 @# Q( N% q
#include <exception>
( l; B7 r5 z6 R2 d! h#include <functional>- ]9 T9 M; t; W D& t# o& x N6 j
( |2 Q' P% H( Y& c- u
% O6 O; H3 z, T) _( F, l5 y; b- ]9 A
$ ~; x: u N( V. U6 S6 b& I$ ]6 S/ ?8 C# p
typedef _com_ptr_t<_com_IIID<IUPnPDeviceFinder,&IID_IUPnPDeviceFinder> > FinderPointer;
& o3 T- k9 N2 z) B' [ Ltypedef _com_ptr_t<_com_IIID<IUPnPDevice,&IID_IUPnPDevice> > DevicePointer;/ B2 k; k& H8 K6 f: O0 h; V# P
typedef _com_ptr_t<_com_IIID<IUPnPService,&IID_IUPnPService> > ServicePointer;
D- g1 s6 V& M3 ?6 P2 Gtypedef _com_ptr_t<_com_IIID<IUPnPDeviceFinderCallback,&IID_IUPnPDeviceFinderCallback> > DeviceFinderCallback;
- G+ c( z1 K, N7 b/ E! W( rtypedef _com_ptr_t<_com_IIID<IUPnPServiceCallback,&IID_IUPnPServiceCallback> > ServiceCallback;
9 C: a' V9 R* s) D6 S! K" Mtypedef _com_ptr_t<_com_IIID<IEnumUnknown,&IID_IEnumUnknown> > EnumUnknownPtr;
( X4 Q J) s8 j9 W% [typedef _com_ptr_t<_com_IIID<IUnknown,&IID_IUnknown> > UnknownPtr;/ e( Q" j& a# m# g: ^( O
2 `" Z" K. p" n, B8 h! S" }; q, x2 s6 ]3 l: W
typedef DWORD (WINAPI* TGetBestInterface) (
: y$ n, _9 \- t1 c IPAddr dwDestAddr,5 U3 _6 y, L& ~1 ]1 K1 V, }
PDWORD pdwBestIfIndex5 {, G8 y y2 w$ b& ?/ l b
);: k8 M' @% h8 }( h" G& g8 y
n+ K8 E0 {5 {7 `+ K3 f) z0 B' v5 h1 v# c, |. R/ f
typedef DWORD (WINAPI* TGetIpAddrTable) ($ T+ k2 {8 N o5 k: Z" N
PMIB_IPADDRTABLE pIpAddrTable,2 q9 ], J. V& f
PULONG pdwSize,
% F; {4 z$ s6 _, O BOOL bOrder
3 k* p# U( p: q3 l1 n. P; E);" [) b1 j- n' U, u, u, d
$ Y2 k9 V7 ]" J9 `4 q( ^. M
. o1 M1 A: X; C: `; @* }* {0 Jtypedef DWORD (WINAPI* TGetIfEntry) (
: K5 _" h& `7 v' O k1 L% p0 ? PMIB_IFROW pIfRow7 R3 m# J; p/ ^4 r' s, r* i% P
);
$ j" }, U- `- I7 s8 X0 e5 g5 C8 t! L8 D" x- R: X( N0 s% {# ^1 C
' q6 N7 P; F2 NCString translateUPnPResult(HRESULT hr);: v. x( k& a+ o1 r0 z
HRESULT UPnPMessage(HRESULT hr);
# S3 M5 b' y0 R+ a. }7 Y( H2 L/ l" r! d6 A- q7 p# {$ p
, V; l0 s) ?# ^6 Z$ `
class CUPnPImplWinServ: public CUPnPImpl
5 e4 R0 _, h! v, T1 J4 i{
0 C2 R: h! G" [$ G, |4 @ friend class CDeviceFinderCallback;
7 h; f% B. \' b3 u5 x5 ^ friend class CServiceCallback;; \: e; R8 Q6 u6 }7 V3 e$ I
// Construction9 [+ R1 @4 }: S9 Y* _
public:9 y8 B3 k6 [* {$ e6 k" F; F
virtual ~CUPnPImplWinServ();
- k# m |* C7 g& a& u: ? {0 D0 | CUPnPImplWinServ();
1 I k% h" t/ |* z7 t1 y" ^2 ]+ G+ q0 X' c- _+ D) {+ ?+ @
3 |, u8 x2 v# W1 i) F$ t: ^ virtual void StartDiscovery(uint16 nTCPPort, uint16 nUDPPort, uint16 nTCPWebPort) { StartDiscovery(nTCPPort, nUDPPort, nTCPWebPort, false); }- ~- r) M1 d; b6 j6 @" T5 @
virtual void StopAsyncFind();
3 f ]9 d. G: P) b0 c( l* P3 H9 d& Y virtual void DeletePorts();
- x% K' h+ B1 d! C) o virtual bool IsReady();" X# y8 x- `, d& L" z* M
virtual int GetImplementationID() { return UPNP_IMPL_WINDOWSERVICE; } w" B8 `+ Q4 ^/ S6 [
) w- s4 l) @4 c0 U4 o$ V, P/ a4 A$ r/ l* @6 ^+ H, F
// No Support for Refreshing on this (fallback) implementation yet - in many cases where it would be needed (router reset etc)# h4 g8 F2 x; O3 T, y
// the windows side of the implementation tends to get bugged untill reboot anyway. Still might get added later' Z2 u2 c1 D" F* `4 _
virtual bool CheckAndRefresh() { return false; };
5 T+ k" P- E$ W }5 W' k @8 F
; M" P4 @9 X1 d& q- }7 h
, K3 s/ Z# w$ t# N% S @protected:
1 c& C" @4 q4 [ z7 p# H% s. L+ u void StartDiscovery(uint16 nTCPPort, uint16 nUDPPort, uint16 nTCPWebPort, bool bSecondTry);, [7 ~; x8 l+ f/ `6 f0 c
void AddDevice(DevicePointer pDevice, bool bAddChilds, int nLevel = 0);" a& @* U; }& D6 \2 F" I0 D
void RemoveDevice(CComBSTR bsUDN);
# d0 D# z8 J, z/ [. n bool OnSearchComplete();9 Z) v/ k" _6 t6 w
void Init();
, `! J; D8 `4 r8 E! N; i7 _8 s, s# B. {( m e" x) C
7 S: C4 X8 s1 y5 E4 j
inline bool IsAsyncFindRunning() 1 J! e( U; G8 k' @
{
% Q/ Q" l- g# k T e if ( m_pDeviceFinder != NULL && m_bAsyncFindRunning && GetTickCount() - m_tLastEvent > 10000 )
' I' c% S/ {7 e1 p5 I% L {
. R# q8 Y9 N( u# a7 b. L m_pDeviceFinder->CancelAsyncFind( m_nAsyncFindHandle );% R& J! a5 |6 U. Z' V' W! y' P
m_bAsyncFindRunning = false;
9 Y- ?4 |1 \" E: { }$ H4 v$ }- \9 z+ Z$ A
MSG msg;
& D1 v5 L/ B$ P while ( PeekMessage( &msg, NULL, 0, 0, PM_REMOVE ) )
9 D# P( ~; R9 \! f9 M, q0 s {
2 U, y3 l! M7 X( l- H" Z9 T6 Y5 r8 H TranslateMessage( &msg );3 ?2 o- o4 n Y* f* n- K" b2 v
DispatchMessage( &msg );
* @! Z! E0 ^$ C: C }
1 m2 \; I' s) i0 V8 \ return m_bAsyncFindRunning;4 U. s0 x4 f# r' X; T, N
}; R4 }( X0 ^# u6 {8 h+ j) E. w
9 F8 F5 J/ B7 n
s7 @" i+ F6 G% g/ o9 f9 l TRISTATE m_bUPnPDeviceConnected;
1 ?% a" {: d- d9 I, I! e# U7 P) ^* v5 R9 p3 W% m7 z/ @2 `7 \
8 U. V7 y5 i) z5 I// Implementation
+ h$ r/ x7 X0 Q0 s: _ // API functions
4 J1 e1 }: z$ U" L SC_HANDLE (WINAPI *m_pfnOpenSCManager)(LPCTSTR, LPCTSTR, DWORD);: O1 a8 u& e( S S9 t
SC_HANDLE (WINAPI *m_pfnOpenService)(SC_HANDLE, LPCTSTR, DWORD);
# g! U9 X# }) t" \" ]+ R; F BOOL (WINAPI *m_pfnQueryServiceStatusEx)(SC_HANDLE, SC_STATUS_TYPE, LPBYTE, DWORD, LPDWORD);
. H5 C; e4 Q. o2 l+ L, s7 I BOOL (WINAPI *m_pfnCloseServiceHandle)(SC_HANDLE);% E* A* ^. |; k' d
BOOL (WINAPI *m_pfnStartService)(SC_HANDLE, DWORD, LPCTSTR*);& |0 H; E- H) J: t9 o
BOOL (WINAPI *m_pfnControlService)(SC_HANDLE, DWORD, LPSERVICE_STATUS);
; t2 p* ^5 r w6 ~: P( d/ _ I+ `' u- P: U2 g
) v! X8 @5 u7 N/ u TGetBestInterface m_pfGetBestInterface;$ ^5 X. \2 j7 i, V1 Z1 q9 P8 A/ D6 e$ ^
TGetIpAddrTable m_pfGetIpAddrTable;
, v7 p; {# y+ s6 U$ a TGetIfEntry m_pfGetIfEntry;
# o6 E( U1 [ L/ \$ c+ P, E/ k8 S! z! ?8 _. D
8 n* e" p0 O- B
static FinderPointer CreateFinderInstance();
) z9 S6 ^% ?+ k {$ V2 i/ P% S( Q' O) r struct FindDevice : std::unary_function< DevicePointer, bool >
, E2 X( r! @# C, O% d {
4 Q0 b6 |, P& l; L/ g: c FindDevice(const CComBSTR& udn) : m_udn( udn ) {}
& s% B+ a- w/ d+ B/ {0 }0 `2 \* a1 _ result_type operator()(argument_type device) const3 I7 F9 ]! s$ g( b; p# q
{
% g: _+ d2 Q+ _* ~3 o6 @& }" ~ CComBSTR deviceName;
/ F8 j" L7 P# ]2 @ HRESULT hr = device->get_UniqueDeviceName( &deviceName );0 P4 V2 A4 m* P2 }! E
; ]1 _9 ]7 R- n" {
5 W) x! i8 ?# O$ q) q if ( FAILED( hr ) )' x* L* M6 D% q$ S" x1 U0 l9 p
return UPnPMessage( hr ), false;
; k/ o# z( t* f$ C6 c5 A8 [; m, n j& p% I, t. z
5 H6 l0 E- C# B
return wcscmp( deviceName.m_str, m_udn ) == 0;
; w) w/ y; ~, `; c# \ }
1 n/ z1 D6 r1 l5 } CComBSTR m_udn;: R9 T8 w3 } y; Y: f% z' x
};! P0 F+ l5 b: M9 \6 O8 Y
8 E8 U6 X( A. ~5 z6 N. Y void ProcessAsyncFind(CComBSTR bsSearchType);
( O" a: _: }2 K, V" m% O$ ~( c2 j HRESULT GetDeviceServices(DevicePointer pDevice);& u1 E) c9 v! V8 X- c8 g- ^. m8 z
void StartPortMapping();% {7 H/ v. k. a9 \: x
HRESULT MapPort(const ServicePointer& service);. D+ q# s5 L2 L: g/ w4 w
void DeleteExistingPortMappings(ServicePointer pService);4 c: E2 w; V+ p/ ~
void CreatePortMappings(ServicePointer pService);
# {2 a5 k/ _4 a. U8 ? HRESULT SaveServices(EnumUnknownPtr pEU, const LONG nTotalItems);/ J) }1 D. y z
HRESULT InvokeAction(ServicePointer pService, CComBSTR action,
* l2 x: I: N# A; K: i$ _3 A LPCTSTR pszInArgString, CString& strResult);( a; ^7 p0 x& P9 i. l% E
void StopUPnPService();8 _% \$ x" w. P k: v. C0 g
. E/ `# e3 ?, a' R
7 @$ g( O; ?! G- `3 i/ n
// Utility functions0 h% A8 W: z+ w2 \4 a4 t1 _/ @
HRESULT CreateSafeArray(const VARTYPE vt, const ULONG nArgs, SAFEARRAY** ppsa);( _7 g( Q1 t+ `
INT_PTR CreateVarFromString(const CString& strArgs, VARIANT*** pppVars);- Q9 K u1 c+ [! L. R. v& u
INT_PTR GetStringFromOutArgs(const VARIANT* pvaOutArgs, CString& strArgs);
" q9 S$ s" d: C. w void DestroyVars(const INT_PTR nCount, VARIANT*** pppVars);" H9 u+ H) Y' t/ Z
HRESULT GetSafeArrayBounds(SAFEARRAY* psa, LONG* pLBound, LONG* pUBound);
* p- R- ~! v+ g" C2 v$ M HRESULT GetVariantElement(SAFEARRAY* psa, LONG pos, VARIANT* pvar);
9 ?2 y* d; v) j6 y Y! u, ^# s, r% L CString GetLocalRoutableIP(ServicePointer pService);- m4 q; V" L+ v
& l: [0 _. \3 `& P6 A/ m
& n8 Z$ F4 s. n9 m" d G// Private members
/ k& {+ E, L/ e# s p: Oprivate:
& D& J5 J1 ~/ X7 b9 N9 j DWORD m_tLastEvent; // When the last event was received?
% @+ w7 z0 w b3 P% d1 x& G std::vector< DevicePointer > m_pDevices;0 ]8 U# M9 ]# i: C
std::vector< ServicePointer > m_pServices; l8 c8 s; l4 P7 w, Q4 e! s% x$ v
FinderPointer m_pDeviceFinder;
2 r4 z. k4 v! E' Z F DeviceFinderCallback m_pDeviceFinderCallback;. m g- ^2 G. S
ServiceCallback m_pServiceCallback;
K# V. u# w4 z) {" g
7 d# K5 L. K4 d! } Z' g( B1 m* n/ ]. S' h) v5 z& t7 h& v3 v
LONG m_nAsyncFindHandle;
+ L" D1 w/ {) I7 x8 I bool m_bCOM;
0 u9 f3 V+ D# k! w2 W" I! T bool m_bPortIsFree;
/ ^# A; w5 h. I( h% A CString m_sLocalIP;* O* {: [' O* m0 X( R
CString m_sExternalIP;4 B8 L* B: }5 L2 b- ~, t) x% m
bool m_bADSL; // Is the device ADSL?' x& M# j( l% q, A" V3 m W3 J* `% s
bool m_ADSLFailed; // Did port mapping failed for the ADSL device?
. l: {/ W3 p1 m+ F5 h bool m_bInited;9 z4 p& b+ t. F
bool m_bAsyncFindRunning;& ~; b6 g# z9 k/ J& R M$ J# y% _+ V
HMODULE m_hADVAPI32_DLL;; {- Z. A5 e2 v) E( p- c
HMODULE m_hIPHLPAPI_DLL;
5 W- f" G# ]2 c bool m_bSecondTry;# ]" J, Y3 q+ N# Y# x9 c$ g
bool m_bServiceStartedByEmule;3 t7 Z0 l7 \4 l3 s
bool m_bDisableWANIPSetup;2 t, \2 S) y" \1 [
bool m_bDisableWANPPPSetup;
" ^- K, J4 K! z& i" H' u
: c, X4 C& V' I+ c* h" Z/ t+ W7 c; m6 N% X7 p7 |
};, I7 {5 A& e; n% z4 b4 e( E
/ S3 S8 s# J) j9 G% s" C2 W8 P( K/ E8 A+ J5 p9 L% `
// DeviceFinder Callback
, S, ?' |, ?( {6 v4 hclass CDeviceFinderCallback" C" v, B8 l8 Y3 U" V/ i
: public IUPnPDeviceFinderCallback6 A( i" Y) T. [/ g: m, n
{2 e' X7 a0 s8 _: B- m K
public:* x" V+ Z ~: g c$ z. W/ d
CDeviceFinderCallback(CUPnPImplWinServ& instance): S' g! Y; l0 k" E
: m_instance( instance )# o8 \# F8 N; R0 S
{ m_lRefCount = 0; }
1 [. U9 U$ [$ e4 b3 q
/ z8 g4 e' a; E& z! V: H% ?: B& |' Q: T. M1 n
STDMETHODIMP QueryInterface(REFIID iid, LPVOID* ppvObject);
) L( z- G6 g4 W4 p& m; h STDMETHODIMP_(ULONG) AddRef();
# h# C* X% |1 `* p" C STDMETHODIMP_(ULONG) Release();; C- Z; ^! `7 \
+ v( `3 V3 Q$ i/ k! b/ Z
" Z6 x8 K2 z9 G3 z0 ?0 P: B# g- G
// implementation2 B; j" K& Q- t# o5 D
private:
5 `, r* p1 O$ ~- | HRESULT __stdcall DeviceAdded(LONG nFindData, IUPnPDevice* pDevice);
5 q) ^+ X6 y c3 J HRESULT __stdcall DeviceRemoved(LONG nFindData, BSTR bsUDN);
: t* D9 k7 p: C9 A+ F& o4 P& a HRESULT __stdcall SearchComplete(LONG nFindData);
3 y |# b) t# Z8 n4 s: T( q4 S" e. O% q8 j" A! R
6 H6 I; z# l7 g' m( zprivate:' E) M7 v$ p1 q4 s! v
CUPnPImplWinServ& m_instance;
6 T6 W. G1 d6 [. c+ y LONG m_lRefCount;% R( X5 w* c1 t6 S# l
};
. B" j2 ], H+ }/ D8 h2 ^7 U3 I$ B8 p+ D4 X y
# ?# x5 @ [! K2 ?9 v$ N' A4 k1 s
// Service Callback
; A! O: \% x! Y$ C- A9 M7 Aclass CServiceCallback
; Y* R( a% V( z! x : public IUPnPServiceCallback8 ~- I1 L$ k4 L8 A- d1 c6 J) n$ J
{
8 }( |& W! l( j2 [& dpublic:. V5 Y; t+ |0 a" w4 ]- R
CServiceCallback(CUPnPImplWinServ& instance)
* y7 S* e* S: a: y p+ b : m_instance( instance )% K8 I4 k3 h e1 [' ^5 O7 h- Y
{ m_lRefCount = 0; }
0 Y p8 K R/ X; y% G
) w5 m" i& g- W6 `3 {% t) w J: e STDMETHODIMP QueryInterface(REFIID iid, LPVOID* ppvObject);. l( Z( ?0 {0 ^
STDMETHODIMP_(ULONG) AddRef();' G, o# W" t. I$ V# C
STDMETHODIMP_(ULONG) Release();, o$ @7 S! o8 o
, u. N+ w e5 F; }
5 U4 @+ ]1 R k$ y// implementation
' N. Y% D% }) \- vprivate:- Y* I9 Y @7 @, n: b, F$ K
HRESULT __stdcall StateVariableChanged(IUPnPService* pService, LPCWSTR pszStateVarName, VARIANT varValue);4 S7 r7 w, E! S d, ^* r2 r. n
HRESULT __stdcall ServiceInstanceDied(IUPnPService* pService);/ g( |; M* i. F7 q% x' r
- ~: }$ n, z& \: W3 y
5 G2 p7 Z+ Q6 s9 Cprivate:
! n( f. _9 U' S/ @9 A. Y, m: K1 C7 n9 P CUPnPImplWinServ& m_instance;
% X" a$ w$ N1 U; t' f( A8 G- s+ g LONG m_lRefCount;. g, f- ~: s; X
};
3 ~# A6 W' o' L7 n
2 V8 [, A& w, }% C1 [' K* v. k& l! N+ e9 q- i
/////////////////////////////////////////////////4 t( G, w* N* n
- N& r$ L" P0 F7 g( [
6 \* u% S/ W3 L- m使用时只需要使用抽象类的接口。" K; x% l$ N3 l7 @9 K
CUPnPImpl::SetMessageOnResult设置需要接受UPNP端口映射是否成功的窗口句柄和消息ID.
& S6 A& V7 S0 kCUPnPImpl::StartDiscovery将开启一个异步设备查找并进行端口映射,其参数为需要映射的内网端口.! L7 m/ |5 ]$ |. O) z
CUPnPImpl::StopAsyncFind停止设备查找.! f, X5 S. U7 H
CUPnPImpl::DeletePorts删除端口映射. |
|