当前位置:七道奇文章资讯编程技术VC/C++编程
日期:2011-03-22 13:55:00  来源:本站整理

用拷贝钩子实现对文件夹的监控[VC/C++编程]

赞助商链接



  本文“用拷贝钩子实现对文件夹的监控[VC/C++编程]”是由七道奇为您精心收集,来源于网络转载,文章版权归文章作者所有,本站不对其观点以及内容做任何评价,请读者自行判断,以下是其具体内容:

ICopyHook是一个用于成立拷贝钩子处理程序COM接口,它决意一个文件夹大概打印机对象能否可以被移动,拷贝,重命名或删除.Shell在履行这些操作之前,会调用ICopyHook接口的CopyCallback办法对它们举行考证.CopyCallback返回一个int值指导Shell能否应当持续履行这个操作.返回值IDYES表示持续,而返回值IDNO和IDCANCEL则表示终止.

一个文件夹对象可以安装多个拷贝钩子处理程序.假如呈现这种情形,Shell会顺次调用每个处理程序.只有当每个处理程序都返回IDYES时,Shell才真正履行用户恳求的操作.

拷贝钩子处理程序的作用是在上述四种操作履行前对它们举行考证,但是Shell并不会把操作的后果告诉给拷贝钩子处理程序.而windows供应的API函数FindFirstChangeNotification和FindNextChangeNotification却可以实现这个功效.因此,只有把这种两种办法结合起来,才能对一个文件夹的状况举行完好的监控.

拷贝钩子处理程序实现并不艰难,首先成立一个作为进程内组件的COM对象,它只需求表露一个ICopyHook接口(当然还有IUnknown).然后用regsrv32.exe注册这个COM组件.最后一步是向Shell注册你的这个拷贝钩子处理程序,办法是在注册表HKEY_CLASSES_ROOT\Directory\Shellex\CopyHookHandlers下成立一个名称肆意的sub key,在此sub key中成立一个范例为REG_SZ的项并将你的COM对象的CLSID作为它的默许值便可以了.

下面就是一个拷贝钩子的实现程序(注:以下代码经老妖窜改并增添了具体操作历程,在BCB6中成功编译并通过测试)

1. 从ICopyHook接口成立TCopyHook,从IClassFactory接口成立TClassFactory:

// TCopyHook.h
// TCopyHook类实现了ICopyHook接口,TClassFactory实现了IClassFactory接口
//---------------------------------------------------------------------------
#define NO_WIN32_LEAN_AND_MEAN
#include <shlobj.h>
//---------------------------------------------------------------------------
class TCopyHook: public ICopyHook
{
public:
   TCopyHook():m_refcnt(0) {}
   STDMETHODIMP QueryInterface(REFIID iid,void **ppvObject);
   STDMETHODIMP_(ULONG) AddRef();
   STDMETHODIMP_(ULONG) Release();
   STDMETHODIMP_(UINT) CopyCallback(HWND hwnd, UINT wFunc, UINT wFlags,
       LPCTSTR pszSrcFile, DWORD dwSrcAttribs,
       LPCTSTR pszDestFile, DWORD dwDestAttribs);
private:
   int m_refcnt;
};
//---------------------------------------------------------------------------
class TClassFactory : public IClassFactory
{
public:
   TClassFactory():m_refcnt(0) {}
   STDMETHODIMP QueryInterface(REFIID iid, void **ppvObject);
   STDMETHODIMP_(ULONG) AddRef();
   STDMETHODIMP_(ULONG) Release();
   STDMETHODIMP CreateInstance(IUnknown *pUnkOuter, REFIID riid, void **ppvObject);
   STDMETHODIMP LockServer(BOOL fLock);
private:
   int m_refcnt;
};
// TCopyHook.cpp
// TCopyHook对象和TClassFactory对象的实现文件
#include <stdio.h>
#include "TCopyHook.h"
//---------------------------------------------------------------------------
extern LONG nLocks;     // 对象计数,用于DllCanUnloadNow
ULONG __stdcall TCopyHook::AddRef()
{
   if(m_refcnt == 0)
     nLocks++;
   m_refcnt++;
   return m_refcnt;
}
//---------------------------------------------------------------------------
ULONG __stdcall TCopyHook::Release()
{
   int nNewCnt = --m_refcnt;
   if(nNewCnt <= 0)
   {
     nLocks--;
     delete this;
   }
   return nNewCnt;
}
//---------------------------------------------------------------------------
HRESULT __stdcall TCopyHook::QueryInterface(REFIID dwIID, void **ppvObject)
{
   if(dwIID == IID_IUnknown)
     *ppvObject = static_cast<IUnknown*>(this);
   else
     if(dwIID == IID_IShellCopyHook)
       *ppvObject = static_cast<ICopyHook*>(this);
     else
       return E_NOINTERFACE;
   reinterpret_cast<IUnknown*>(*ppvObject)->AddRef();
   return S_OK;
}
//---------------------------------------------------------------------------
// 这就是CopyCallback办法,拷贝钩子的全部功效由它实现.参数的具体值参看MSDN
UINT __stdcall TCopyHook::CopyCallback(HWND hwnd, UINT wFunc, UINT wFlags,
     LPCTSTR pszSrcFile, DWORD dwSrcAttribs,
     LPCTSTR pszDestFile, DWORD dwDestAttribs)
{
   char szMessage[MAX_PATH+14];
   sprintf(szMessage, "对%s举行的操作,能否持续?", pszSrcFile);
   return MessageBox(NULL, szMessage, "确认", MB_YESNO | MB_ICONEXCLAMATION);
}
//---------------------------------------------------------------------------
ULONG __stdcall TClassFactory::AddRef()
{
   if(m_refcnt==0)
     nLocks++;
   m_refcnt++;
   return m_refcnt;
}
//---------------------------------------------------------------------------
ULONG __stdcall TClassFactory::Release()
{
   int nNewCnt = --m_refcnt;
   if(nNewCnt <= 0)
   {
     nLocks--;
     delete this;
   }
   return nNewCnt;
}
//---------------------------------------------------------------------------
HRESULT __stdcall TClassFactory::QueryInterface(REFIID dwIID, void **ppvObject)
{
   if(dwIID == IID_IUnknown)
     *ppvObject = static_cast<IUnknown*>(this);
   else
     if(dwIID == IID_IClassFactory)
       *ppvObject = static_cast<IClassFactory*>(this);
     else
       return E_NOINTERFACE;
   reinterpret_cast<IUnknown*>(*ppvObject)->AddRef();
   return S_OK;
}
//---------------------------------------------------------------------------
HRESULT __stdcall TClassFactory::CreateInstance(IUnknown* pUnkownOuter,
     REFIID riid, void** ppvObj)
{
   if(pUnkownOuter != NULL)
     return CLASS_E_NOAGGREGATION;
   TCopyHook *pObj = new TCopyHook;
   pObj->AddRef();
   HRESULT hr = pObj->QueryInterface(riid, ppvObj);
   pObj->Release();
   return hr;
}
//---------------------------------------------------------------------------
HRESULT __stdcall TClassFactory::LockServer(BOOL fLock)
{
   if(fLock)
     nLocks++;
   else
     nLocks--;
   return S_OK;
}


  以上是“用拷贝钩子实现对文件夹的监控[VC/C++编程]”的内容,如果你对以上该文章内容感兴趣,你可以看看七道奇为您推荐以下文章:
  • 用拷贝钩子实现对文件夹的监控
  • 本文地址: 与您的QQ/BBS好友分享!
    • 好的评价 如果您觉得此文章好,就请您
        0%(0)
    • 差的评价 如果您觉得此文章差,就请您
        0%(0)

    文章评论评论内容只代表网友观点,与本站立场无关!

       评论摘要(共 0 条,得分 0 分,平均 0 分) 查看完整评论
    Copyright © 2020-2022 www.xiamiku.com. All Rights Reserved .