ActiveX控件localhost可以调用,内外网IP不可以的解决办法
来源:互联网 发布:淘宝ysl口红正品店铺 编辑:程序博客网 时间:2024/05/09 17:15
开发ActiveX控件过程中遇到这样的问题:
本机上开发完成后,用TstCon测试接口没问题。js写静态页面测试调用没问题。但是给到web端开发,他们使用内网IP或者外网地址时,会报错。如图:
开始以为是IE本地设置的问题,把对ActiveX限制的都改为允许,但是试了之后还是不行。后来联想到是否是因为本地调试IE用的Intranet策略,而以IP方式访问IE采用的是Internet策略。所以果断去设置Internet选项,如图,。
点开自定义级别,
把上图中『对未标记为可安全执行脚本的ActiveX控件初始化并执行脚本』改为启用后,发现有的机器可以,有的不成,而且设置后IE会提示不安全之类的。看起来很不优雅。果断放弃修改IE设置。
仔细想想,自己写的跟官方提供的一些控件理论上除了没有数字签名外,应该没别的不同,于是尝试增加数字签名,当然这个是没有认证的。尝试后这个方案也失败了。
找资料看到这样一篇文章:http://www.xuebuyuan.com/758961.html
里面讲到,在IE的中级安全设置上,是允许脚本安全的ActiveX创建并且不予警告的。那么IE怎么知道一个插件式脚本安全的呢?
①通过查询ActiveX是否实现了IObjectSafety接口,并且返回脚本安全;
②查询ActiveX是否在注册表Component Category Manager里表明自己实现了 CATID_SafeForInitializing 和 CATID_SafeForScripting。此方法修改DllRegisterServer函数
所以,问题的关键是我们自己的ActiveX控件 实现CATID_SafeForInitializing 和 CATID_SafeForScripting,以及IObjectSafety接口。
那就来吧。
①实现CATID_SafeForInitializing 和 CATID_Safeforscripting
XXX.h中声明(以下XXX代表你的工程名,比如MyActiveX,则XXX.h表示MyActiveX.h)
包含头文件文件 #include "comcat.h"
HRESULT CreateComponentCategory(CATID catid, WCHAR* catDescription);HRESULT RegisterCLSIDInCategory(REFCLSID clsid, CATID catid);
①xxxCtrl.h中声明:
//ObjSafeDECLARE_INTERFACE_MAP()BEGIN_INTERFACE_PART(ObjSafe, IObjectSafety)STDMETHOD_(HRESULT, GetInterfaceSafetyOptions) (/* [in] */ REFIID riid,/* [out] */ DWORD __RPC_FAR *pdwSupportedOptions,/* [out] */ DWORD __RPC_FAR *pdwEnabledOptions);STDMETHOD_(HRESULT, SetInterfaceSafetyOptions) (/* [in] */ REFIID riid,/* [in] */ DWORD dwOptionSetMask,/* [in] */ DWORD dwEnabledOptions);END_INTERFACE_PART(ObjSafe);②xxxCtrl.cpp中实现:
const CATID CATID_SafeForScripting ={ 0x7dd95801, 0x9882, 0x11cf, { 0x9f, 0xa9, 0x00, 0xaa, 0x00, 0x6c, 0x42, 0xc4 } };const CATID CATID_SafeForInitializing ={ 0x7dd95802, 0x9882, 0x11cf, { 0x9f, 0xa9, 0x00, 0xaa, 0x00, 0x6c, 0x42, 0xc4 } };// 创建组件种类 HRESULT CreateComponentCategory(CATID catid, WCHAR* catDescription){ICatRegister* pcr = NULL;HRESULT hr = S_OK;hr = CoCreateInstance(CLSID_StdComponentCategoriesMgr, NULL, CLSCTX_INPROC_SERVER, IID_ICatRegister, (void**)&pcr);if (FAILED(hr)) return hr;// Make sure the HKCR\Component Categories\{..catid...} // key is registered. CATEGORYINFO catinfo;catinfo.catid = catid;catinfo.lcid = 0x0409; // english // Make sure the provided description is not too long. // Only copy the first 127 characters if it is. int len = wcslen(catDescription);if (len>127) len = 127;wcsncpy(catinfo.szDescription, catDescription, len);// Make sure the description is null terminated. catinfo.szDescription[len] = '\0';hr = pcr->RegisterCategories(1, &catinfo);pcr->Release();return hr;}// 注册组件种类 HRESULT RegisterCLSIDInCategory(REFCLSID clsid, CATID catid){// Register your component categories information. ICatRegister* pcr = NULL;HRESULT hr = S_OK;hr = CoCreateInstance(CLSID_StdComponentCategoriesMgr, NULL, CLSCTX_INPROC_SERVER, IID_ICatRegister, (void**)&pcr);if (SUCCEEDED(hr)) {// Register this category as being "implemented" by the class. CATID rgcatid[1];rgcatid[0] = catid;hr = pcr->RegisterClassImplCategories(clsid, 1, rgcatid);}if (pcr != NULL) pcr->Release();return hr;}STDAPI DllRegisterServer(void) 函数中,添加:
// 标记控件初始化安全. // 创建初始化安全组件种类 HRESULT hr = CreateComponentCategory(CATID_SafeForInitializing, L"Controls safely initializable from persistent data!");if (FAILED(hr)) return hr;// 注册初始化安全 hr = RegisterCLSIDInCategory(BASED_CODE _tlid, CATID_SafeForInitializing);if (FAILED(hr)) return hr;// 标记控件脚本安全 // 创建脚本安全组件种类 hr = CreateComponentCategory(CATID_SafeForScripting, L"Controls safely scriptable!");if (FAILED(hr)) return hr;// 注册脚本安全组件种类 hr = RegisterCLSIDInCategory(BASED_CODE _tlid, CATID_SafeForScripting);if (FAILED(hr)) return hr;
// 删除控件初始化安全入口. HRESULT hr = UnRegisterCLSIDInCategory(BASED_CODE _tlid, CATID_SafeForInitializing);if (FAILED(hr)) return hr;// 删除控件脚本安全入口 hr = UnRegisterCLSIDInCategory(BASED_CODE _tlid, CATID_SafeForScripting);if (FAILED(hr)) return hr;
xxxCtrl.h中添加:
//ObjSafeDECLARE_INTERFACE_MAP()BEGIN_INTERFACE_PART(ObjSafe, IObjectSafety)STDMETHOD_(HRESULT, GetInterfaceSafetyOptions) (/* [in] */ REFIID riid,/* [out] */ DWORD __RPC_FAR *pdwSupportedOptions,/* [out] */ DWORD __RPC_FAR *pdwEnabledOptions);STDMETHOD_(HRESULT, SetInterfaceSafetyOptions) (/* [in] */ REFIID riid,/* [in] */ DWORD dwOptionSetMask,/* [in] */ DWORD dwEnabledOptions);END_INTERFACE_PART(ObjSafe);
//接口映射BEGIN_INTERFACE_MAP(CRtmpDumpCtrlCtrl, COleControl)INTERFACE_PART(CRtmpDumpCtrlCtrl, IID_IObjectSafety, ObjSafe)END_INTERFACE_MAP()ULONG FAR EXPORT CRtmpDumpCtrlCtrl::XObjSafe::AddRef(){METHOD_PROLOGUE(CRtmpDumpCtrlCtrl, ObjSafe)return pThis->ExternalAddRef();}ULONG FAR EXPORT CRtmpDumpCtrlCtrl::XObjSafe::Release(){METHOD_PROLOGUE(CRtmpDumpCtrlCtrl, ObjSafe)return pThis->ExternalRelease();}HRESULT FAR EXPORT CRtmpDumpCtrlCtrl::XObjSafe::QueryInterface(REFIID iid, void FAR* FAR* ppvObj){METHOD_PROLOGUE(CRtmpDumpCtrlCtrl, ObjSafe)return (HRESULT)pThis->ExternalQueryInterface(&iid, ppvObj);}const DWORD dwSupportedBits = INTERFACESAFE_FOR_UNTRUSTED_CALLER | INTERFACESAFE_FOR_UNTRUSTED_DATA;const DWORD dwNotSupportedBits = ~dwSupportedBits;HRESULT STDMETHODCALLTYPECRtmpDumpCtrlCtrl::XObjSafe::GetInterfaceSafetyOptions(/* [in] */ REFIID riid,/* [out] */ DWORD __RPC_FAR *pdwSupportedOptions,/* [out] */ DWORD __RPC_FAR *pdwEnabledOptions){METHOD_PROLOGUE(CRtmpDumpCtrlCtrl, ObjSafe)HRESULT retval = ResultFromScode(S_OK);// does interface exist? IUnknown FAR* punkInterface;retval = pThis->ExternalQueryInterface(&riid, (void **)&punkInterface);if (retval != E_NOINTERFACE){ // interface exists punkInterface->Release(); // release it--just checking! }// we support both kinds of safety and have always both set, regardless of interface *pdwSupportedOptions = *pdwEnabledOptions = dwSupportedBits;return retval; // E_NOINTERFACE if QI failed }HRESULT STDMETHODCALLTYPECRtmpDumpCtrlCtrl::XObjSafe::SetInterfaceSafetyOptions(/* [in] */ REFIID riid,/* [in] */ DWORD dwOptionSetMask,/* [in] */ DWORD dwEnabledOptions){METHOD_PROLOGUE(CRtmpDumpCtrlCtrl, ObjSafe)// does interface exist? IUnknown FAR* punkInterface;pThis->ExternalQueryInterface(&riid, (void**)&punkInterface);if (punkInterface){ // interface exists punkInterface->Release(); // release it--just checking! }else{ // interface doesn't exist return ResultFromScode(E_NOINTERFACE);}// can't set bits we don't support if (dwOptionSetMask & dwNotSupportedBits){return ResultFromScode(E_FAIL);}// can't set bits we do support to zero dwEnabledOptions &= dwSupportedBits;// (we already know there are no extra bits in mask ) if ((dwOptionSetMask&dwEnabledOptions) != dwOptionSetMask){return ResultFromScode(E_FAIL);}//don't need to change anything since we're always safe return ResultFromScode(S_OK);}
参考文章:
https://support.microsoft.com/zh-cn/kb/161873
https://msdn.microsoft.com/zh-cn/library/aa751977(v=vs.85).aspx
http://blog.sina.com.cn/s/blog_4f9fc08e01014ipt.html
http://www.xuebuyuan.com/758961.html
http://blog.csdn.net/aasmfox/article/details/38616997
乌云的两篇好文:
http://drops.wooyun.org/papers/5673
http://drops.wooyun.org/papers/7521
- ActiveX控件localhost可以调用,内外网IP不可以的解决办法
- 对于tomcat不可以通过IP或者127.0.0.1访问,而只可以通过localhost访问的解决办法
- vue-cli起的webpack项目 用localhost可以访问,但是切换到ip就不可以访问
- JS可以调用Curl 的Activex控件
- IIS 用localhost可以,用本机IP不可以访问
- apache php localhost,127.0.0.1可以访问,ip不可以访问
- jboss5可以使用http://localhost/和http://127.0.0.1/ 不可以ip访问
- java连接oracle数据库用本机IP地址不可以,而用localhost可以
- ExtJs弹窗第一次可以第二次不可以的解决办法
- tomcat部署项目时localhost:8080不可以访问,新建的项目可以访问
- 可以访问127.0.0.1,但不可以访问localhost
- activex控件中调用get_Script失败的解决办法
- swf调用页面的方法 IIS下可以调用 文件夹里面不可以 权限问题解决方案
- 一次调用ACTIVEX控件中出现的问题.不可访问构建函数.
- java -version可以查看jdk版本,但是javac不可以查看jdk版本的解决办法
- 静态方法的内部可以不可以调用非静态的方法吗?
- tomcat服务器输入localhost可以访问,ip无法访问解决办法
- tomcat服务器输入localhost可以访问,ip无法访问解决办法
- Haar分类器学习总结
- chrome下document.documentElement.scrollTop为0的解决方案
- Unity3D游戏开发之史上最简单的鼠标点击控制人物走动实现
- java poi导出excel 表格
- 263. Ugly Number
- ActiveX控件localhost可以调用,内外网IP不可以的解决办法
- usb封包格式
- 把玩之python爬虫cookie篇
- Kafka0.8.2.1删除topic逻辑
- android studio中使用MPChart图表的准备
- OpenCV各种版本官方下载
- spark-shell的限制
- ElasticSearch安装
- 关于事件分发的笔记