本帖子主题:
如何在UNIX下实现COM组件的运行环境的小“讨论”
----欢迎C++,COM,UNIX高手----
至于如何用代码实现,那是非常复杂的工程,我们不谈
至于是否有现存的这样的项目进行,我们可以参考他们的做法,但是不做仔细转研
这个讨论侧重从头开始建立这样一个COM运行环境,在UNIX上面我们需要做些什么。
为了好说,好记,把这个讨论的主题起个名字:COMX
起头:
COMX的功能:
1 不需要考虑兼容Windows下面的既有dll
2 不需要兼容COM组件规范
3 自己实现一个组件二进制借口规范
4 在UNIX上面写其他C++程序,
1 可以初始化COM环境调用他人编写的COMX组件
2 可以把自己的代码实现成COMX组件
望集思广益
注:
1 这个讨论将不会持续很久,一个周末左右,因为,不希望占用过多的时间。
2 继续思考 将会编号 陆续发表
3 问题求解 将会编号 陆续发表
4 然后希望最后产生的文档将被整理成一篇具备参考价值的COM别样文章。
不是很细节的第一步思考,下个帖子发出基于这个思考产生的继续思考,每一个跟贴
会产生更多的继续思考,我会给予编号,我还不是能够在不需要查阅参考资料的前提
下有疑问的,我会陆续发表编号的 “问题求解”
思考从这里开始 Start here
1 项目提交形式: libComX.so
2 unix C 客户代码访问方法?
#include <comx.h>
//初始化COMX环境
COMXRunTime comruntime;
//创建COMX组件对象实例 继续思考1 实现组件ProgID,GUID,IID这丫东西
COMXObject * comobject=comruntime.newComObject("LIB.CLASSNAME");
//开始使用COMX组件对象
comobject->Shout();
//销毁COMX组件对象,从这里可以 继续思考2 实现应用计数这丫东西
comruntime.destroyComObject("");
//destroyComX(comruntime);
3 如何实现COM接口?
思考:
要实现COM接口,就是说在2的注释中使用comobject这个指针访问组件的方法,而且
comx运行环境能够根据一个ProgID找到COMX组件的物理位置(继续思考3:根据ProgID
找到.SO的位置,然后动态载入内存),动态的加载了某一个so文件以后,根据CLASSID
找到相关类的(问题求解1:是否有这样机制支持)二进制代码入口点,boot,然后调入
内存,返回COMX对象的指针,如果能够顺利地实现这样的问题,那么就可以顺利的
实现COMX接口。余下的问题就是使用
这个指针了。
===================================
上面一个帖子产生了一些问题:
1 继续思考1 实现组件ProgID,GUID,IID这丫东西
2 继续思考2 实现应用计数这丫东西
3 继续思考3:根据ProgID找到.SO的位置,然后动态载入内存
4 问题求解1:是否有这样机制支持动态加载动态库中某一些对象,函数
问题求解 需要您的支持,希望得到一些您的宝贵建议和指导,谢谢您
对 继续思考1的思考:
1 实现组件ProgID,GUID,IID这丫东西
程序在内存中运行到这里,发现一个string,然后到某一个特定的COMX数据库寻找
相关的动态库以前注册过的信息,比如一个条目可能像这样:
ProgID="ADODB.CONNECTION"
DllPath="/usr/lib/libADODB.so"
其它(继续思考4:还需要保存什么信息)(问题求解2:还需要保存什么信息)
引出问题:(继续思考5)
COMX组件的注册方法:使用RegComX实用程序 这样
RegComX libADODB.so install
RegComX libADODB.so uninstall
继续引出问题:(继续思考6)
libADODB.so文件需要提供相关的二进制类的文本信息
当在数据库中找到一个合适的条目后,就可以顺利的加载二进制comx对象,而且顺利
的返回指针。这个问题被解。
========================================
继续思考2 实现应用计数这丫东西
我想,实现引用计数是为了让COMX运行环境自己来卸载内存中不再使用的COMX binary 对象
如果每个COMX客户情愿自己销毁对象本身比如(delete comobject;),或者我们的COMX运行
环境就此打住不打算实现这个功能,我想是不需要实现引用计数的,不过既然探讨到这里,
顺带着思考一下这个问题,当然会有专门的段落来给出一个如何思考继续扩充COMX的功能的
引子(叫引子是因为我既然已经想明白这些问题,而且也不准备去真正实现这样的系统,所以
我大概也没有多少可能继续写下去)
首先,定义一个int变量:refcount(够了,我们的COMX服务器对象不可能一下在在内存中被
超过maxint的客户访问),(思考修改1: comx运行环境应该在内存中只存在一份实体,其它
comx客户都必须通过一个指针访问同样的运行环境,我前面的代码没有很好的说明这个问题)
,comx运行环境,会对客户的请求某一个comx服务器对象进行计数,如果内存中没有对象的
实体,就去so文件中加载,如果已经有,refcount++,如果客户不再使用这个对象
(封闭思考1 不专门对封闭思考继续思考,到此点到就算,如何发现客户不再适用对象),
就refcount==,如果为0,销毁这个object.
refcount应该由comx服务器实现,为什么?comx运行环境去保存这个变量太麻烦吧?
问题得解
继续思考3:根据ProgID找到.SO的位置,然后动态载入内存
继续思考一已经模糊的谈到了这个问题的解决方案,问题是,如何确定一个so文件中包含这样
的一个接口(继续思考7: Queryinterface诞生),而且这个queryinterface函数应该最好由
COMX服务器提供,假若每一个COMX服务器类都提供了QueryInterface方法,那么必须在任何
一个so文件(支持comx)中都包含一段queryinterface的代码,返回本so中是否实现comx
运行环境要求创建的接口(接口和实现接口这个概念,在这里被我故意混淆了,看来确实一个
COMX的侧重点是在二进制代码重用,而不是继承等,可以使用聚合的办法来重用代码,彻底抛弃
继承的方法重用代码)(继续思考8:一个SO包含若干class二进制代码,实现comx服务器的程序里,
或者需要用其他方法,让queryinterface函数能够知道一个class的位置,返回指针,如果class
不在这个so中,还需要提供继续搜索的机制),有就返回指针(当然是到内存以后才会有指针),
没有就返回失败信息,一切到失败结束。(继续思考9:Queryinterface到底返回什么?class在
文件中的偏移量?)。客户得到指针以后,就可以访问那段内存中包含的代码了。
--------------------------------------
继续思考4:还需要保存什么信息
继续思考5: libADODB.so 提供给regComx程序的信息
继续思考6:libADODB.so文件需要提供相关的二进制类的文本信息
继续思考7: Queryinterface诞生
继续思考8:一个SO包含若干class二进制代码,实现comx服务器的程序里,
或者需要用其他方法,让queryinterface函数能够知道一个class的位置,
返回指针,如果class不在这个so中,还需要提供继续搜索的机制
继续思考9:Queryinterface到底返回什么?class在文件中的偏移量
思考修改1: comx运行环境应该在内存中只存在一份实体,其它comx客户都必须通过一
个指针访问同样的运行环境,我前面的代码没有很好的说明这个问题
问题求解2:还需要保存什么信息
封闭思考1 不专门对封闭思考继续思考,到此点到就算,如何发现客户不再适用对象
==========================================================
本文地址:http://com.8s8s.com/it/it25456.htm