??xml version="1.0" encoding="utf-8" standalone="yes"?>
1、TerminateProcess
最原始、最暴力的强制console退出的Ҏ。consoleq程毫无q手之力over了。但我希望console在推Z前至能处理一?#8220;后事”?br>
2、signal / raise
原来windows也有signalQ不qkill换成了raise。但是相对Unixpd的signal功能差很远了。而且有一个麻烦的地方是raise只能Ҏconsole生效Q而不能对指定的process?br> 可以在signal里面指定一个call back函数Q在收到SIGINT/SIGTERM之类的时候,处理一下事情,然后通知各个U程l束?br> 既然不能raise其他q程Q是否这个功能就不能用了呢?其实可以考虑一下CreateRemoteThreadQ然后在别h的进E里面raise……
3、SetConsoleCtrlHandler / GenerateConsoleCtrlEvent
q个是console专门用来处理Ctrl-C/Ctrl-Break/以及windowsx事g{的处理Ҏ。比signal更强大。而且说明中写了,可以对其他的q程q行处理Q还可以对进E组处理Q。用|上的话说就是:很女子,很弓虽!
但是要注意,如果要对其创建的子进E进行处理的时候,创徏子进E必要使用CREATE_NEW_PROCESS_GROUP标志。另外一点,文档写的比较隐晦的就是,q程必须要有consoleH口。否则,调用GenerateConsoleCtrlEvent会返?Q说ERROR_INVALID_HANDLE?br> 问题来了QService本n是没有consoleH口的,Service建立的子q程必要自带H口了。但是一般ؓ了美观,Service启动的进E都不想带有H口。那变成了子进E没有consoleH口QGenerateConsoleCtrlEvent失效了?br> 在网上查了很多资料(怎么没看到很黄很暴力呢?Q?Q,其中?strong>
Louis K. Thomas
<louiSendSignal 提到一U做法,是先获得kernel32!CtrlRoutine的入口,然后通过CreateRemoteThread的方法,让远E的console来执行kernel32!CtrlRoutine。但q种Ҏ有个问题Q在获得kernel32!CtrlRoutine的时候,也是使用GenerateConsoleCtrlEvent来获得。但是Service自己本n没有consoleH口Q一调用GenerateConsoleCtrlEvent也是出错?br>而另一?google讨论l?/a> 文章Q里面提到原来可以先AllocConsole、然后GenerateConsoleCtrlEvent、然后FreeConsole……于是解决Ҏ变成:
Service里面:
先AllocConsole
然后利用GenerateConsoleCtrlEvent获得kernel32!CtrlRoutine
然后FreeConsole
当需要结束进E的时候,p用CreateRemoteThreadQ把kernel32!CtrlRoutine的代码注入到子process中执?br> q样大家都看不到consoleH口Qservice里面AllocConsole很快Q看不到H口出来Q甚x疑根本就有没有窗口出来)Q同时又能通知子进E优雅地退出?br>
存在问题Q如果我的机器作为服务器启动Q即没有q入d状态,不知道这样启动的Service会不会有问题呢?Q暂时还没有旉试?br>
]]> sth@hotm ail.co m> ?/span>
]]>
OpenDBXQ一个开源的、简单的、可以访问多U数据库的Ccd。按作者说的,已经支持Q?br />
而且好像是用动态蝲入模块方式,即dlopen打开相应驱动模块的so的方式,是有点ODBC的味道?br />不过支持的数据类型以及SQL查询的功能有限?br />留着以后可能会有些参考h倹{?img src ="http://www.shnenglu.com/cyt/aggbug/20908.html" width = "1" height = "1" />
]]>
q几天要原来目的C++代码?2bit的^台移植到64bit的^台。由于以前编写类库的时候已l十分小心,也早有预谋,所以竟然很利的全部编译通过Q而且-Wall下面都没有Q何warning。满心欢喜之下运行了E序。谁知道马上是一个Segment faul。沮丧之余用gdb跟踪了半天都不知道什么地方的问题。加上valgrindQ也是一头雾_竟然是说标准STL的hash_map的问题……最后在一ơ跟t的时候,无意中检查一个指针的初始化|发现不ؓI,原因应该在q里?br />L代码的上下文Q原来指针是跟一个int攑֜同一个union当中Q而union的初始化只初始化了intQ而没有初始化指针。在64bit机器的gcc下,int?2bit而指针是64bitQ所以就D指针不ؓI的现象。所以赶紧把代码中所有union的地斚w扑և来检查一遍。幸好unionq种东西qx不敢多用Q也没发现其他的异常。程序重新编译,再运行,没有Segment fault了?br />
然后再运行了一批unit test。发现其中有几个不能通过Q其原因其实也是比较无聊。都是自׃心之过Q?br />1、sha1的代码copy php的,其中一个php_uint32变量竟然自己写了unigned longQ傻瓜致?br />2、有个地方保存各U长度整数到文gQ因为偷懒,把函数写成了模板Q大概就是:
template<typename typeInt>
int write(typeInt n) {
writeToFile( &n, sizeof(n));
}
然后一个不心Q想写个string的长度的时候就变成了: write( str.length() );
str.length()cd是size_tQ?4bitQ与32bitpȝ的不一P当然也就出错了?br /> 其实qx都已l很心Q尽量用static_cast强制转换为特定长度类型的变量再输出的了,偏偏是漏了一两个地方?/p>
]]>
db4ol我的印象就是不依赖关系数据库的“Hibernate”,完全是全自动对象序列化 + 强查询。按照官方给出的数据Q其嵌入式的应用环境下性能真的是无出其右了。但按我的理解,׃没有低粒度锁Q必然存在无法解决的q发冲突Q或者ƈ发读问题不大Qƈ发更Ҏ能应该会有影响。究竟用了什么超强技术那׃知道Q或者有I找来研I一下。个人感觉db4oq不是要用来替代数据库,而是数据保存的一个辅助。十分适合用于Cachepȝ或者应用于嵌入式设备。db4o只提供Java和C#接口Q对于目前PDA应用来说g要求高了炏V就如Rayman所_解决了CPU和内存问题还有一个电源问题估计PDAq期也无法解冟?span style="COLOR: red">Christof一再强调其三段式事务保证数据文件完_快速易用的开发模式;大规模数据的支持……至于他们公司的开源盈利模式,弟英文水^有限Q听不懂了?br /> 很久以前提到过GigaBaseQ似乎就是db4o的C++版本。不qC++先天不Q缺反机Ӟ实现当然不能像db4o般优了。但gq个选择也不错,可以告别BerkeleyDB、sqlit……从此步入OO数据保存的“天堂”…?/font>
]]>
]]>
]]>
a、OCIStmtPrepare预处理SQL语句Q?insert into mytable (myimg) values (empty_blob()) returning myimg into :pImg"
b、调用OCIDescriptorAllocQ用参数OCI_DTYPE_LOBQ获得一个LOB的句?br /> c、用OCIStmtBindByPos或者OCIStmtBindByNameQ把LOB句柄和参?pImgl定
d、OCIStmtExecute执行
e、OCILobWrite往LOB里面写数?br /> f、commit和释放资源等{?br />
问题是这个SQL语句也太特别了,和其他数据库的SQL不一栗但是在java的实CQƈ不需要这么奇怪的语法?br /> insert into mytable (myimg) values(?)
p够了?br /> 在我们的应用中,能够l一同一USQL的写法当然是最好的Q最好就是:
insert into mytable (myimg) values (:pImg) 那就和其他的数据处理一致了?br />
做了很多的尝试,l于扑ֈ解决的方法:
a、OCIStmtPrepare预处理SQL语句Q?insert into mytable (myimg) values (:pImg)"
b、调用OCIDescriptorAllocQ用参数OCI_DTYPE_LOBQ获得一个LOB的句?br /> c、通过OCILobCreateTemporary函数QؓLOB句柄创徏临时LOB对象
d、OCILobWriteAppend往LOB句柄写数?br /> e、用OCIStmtBindByPos或者OCIStmtBindByNameQ把LOB句柄和参?pImgl定
f、OCIStmtExecute执行
g、commit和释放资源等{?br />
l过单的装QLOB操作单很多了Q?br /> TDBConnection conn = TDatabase::getConnection( strConnection );
TDBStatement dbStatement(conn.getStatement());
dbStatement.prepareSQL( "insert into mytable (myimg) values (:pImg)" );
dbStatement.getParam("pImg").attachInputStream( fStream );
dbStatement.execSQL();
conn.commite();
2、空字符?br /> 插入一个空字符ԌOCIBindByPos/OCIBindByName的时候,那个字符串的数据cdQ不能是SQLT_LVCQ用SQLT_CHR倒是没有问题?br /> 具体Z么,只有Oracle自己知道了?br />
3、指定IPq接Oracle
通过OCIServerAttach里面指定l定的SIDq接数据库。用SIDq接Oracle当然有它的好处。奇怪的是JDBC能用IP和Port指定q接哪个Oracle?br /> NOCI的帮助都找不到IPq接Ҏ。google了很久,扑ֈ解决的方法,自己生成SIDQ?br /> string strSID = "(DESCRIPTION=(ADDRESS_LIST=(ADDRESS=(PROTOCOL=TCP)(HOST=%1)(PORT=%2)))(CONNECT_DATA=(SERVICE_NAME=%3)))";
里面?1设ؓOracle服务器的IPQ?2设ؓOracle服务器的PortQ一般是1521Q?3是database的名字?br /> 把这个字W串攑օOCIServerAttach
froofyJIT:
{_BLOCK_.header.logo} {_BLOCK_.header.site_name} |
{secondary_links}
{primary_links} |
{_BLOCK_.header.title} {_BLOCK_.header.help} {_BLOCK_.header.message} |
1?amp;的{?BR> 以前一直都不知道,原来在SQLPlus中,&的含义是让用戯入参数?BR>例如Qinsert into my_table values('0=0&1=0&2=0');
执行SQLPlus的时候,׃提示Q?BR>Enter value for 1: abc
Enter value for 2: efg
然后实际插入的结果是Q?BR>insert into my_table values('0=0abc=0efg=0');
要去掉这个功能有两种实现ҎQ?BR> A、用转义字符Q在QQ友e点的帮助下,扑ֈ下面q段话:
SQLPLUS recognizes the '&' "and" character as a substitution character for data input.
So to store a string such as "Johnson & Son" into an Oracle table, use an escape character, as in 'Johnson \& Son' (with the \&).
But first turn on escape character processing:
SQL> set escape \
B、更单,关闭q个功能p了:
SET DEFINE OFF;
Use SET DEFINE OFF to prevent scanning for the substitution character. Reference: bug 13199
2、md5
其实应该不算是奇怪问题,׃shell scrip调用的一批初始化数据库数据的SQL语句惛_mysql和Oracle之间通用Q即不想mysql中管理一份,oracle中管理一份。其实语句大部分都是相同Q但唯独有个初始化管理员密码的SQL语句Cȝ。密码是md5加密的,插入mysql的时候可以用mysql的md5函数Q但是Oracle没有同名的函数。网上google一把,很多解决ҎQ但试了几个都不行。后来综合了几个的做法,最l得Z个结果:
CREATE OR REPLACE FUNCTION md5(passwd IN VARCHAR2) RETURN VARCHAR2
IS
retval varchar2(32);
BEGIN
retval := lower( utl_raw.cast_to_raw(DBMS_OBFUSCATION_TOOLKIT.MD5(INPUT_STRING => passwd)) );
RETURN retval;
END;
q来公司其中一个项目需要程序在g++ 3.4.3下编译,而源代码在g++ 3.2.3下面一个Warning都没有,但是?.4.3下则一堆Error了。后来发现原来g++ 3.4.3严格了很多。其中“出问题”最多的是这U情况:
class TObjBase
{
public:
TObjBase(void) : m_nVal(0) {}
~TObjBase(void) {}
int getVal(void) const { return m_nVal; }
void setVal(int n) { m_nVal = n; }
protected:
int m_nVal;
};
template<class typeObj>
class TExtObj : public typeObj
{
public:
TExtObj(void) : typeObj() {}
int getExtVal(void) const { return getVal() + 100; }
};
q是一U比较常见的应用QAdapter和Decorator模式都会用到q种技术。但问题在于g++ 3.4.3却说int getExtVal(void) const { return getVal() + 100; }q一行错误,getVal()找不到?/P>
的确Q单以TExtObjq个cȝ来,怎么也是找不到getVal()的定义在哪里。g++ 3.2.3以及VC6、VC7{,均以十分怿开发者的态度猜测q个函数必定在其他地方定义了Q有可能是外部独立的函数、有可能是typeObj的成员函数。但g++ 3.4.3却非要程序员很负责Q的告诉编译器Q究竟是哪一个getVal()Q于是解x法:
Ҏ一Q?BR>int getExtVal(void) const { return typeObj::getVal() + 100; }
或?/P>
Ҏ二:
int getExtVal(void) const { return this->getVal() + 100; }
当然Q如果是外部的独立函敎ͼ那就是:
int getExtVal(void) const { return ::getVal() + 100; }
然而,在getVal()是虚函数的时候,Ҏ一和方法二是有区别的,q个是需要十分小心的事情。方法一是无Z么时候都会调用typeObj的getVal()Q方法二是调用当前类最适合的虚函数getVal()?BR>
void TMyClass::onLoad(TStorage & s)
{
s >> member1;
s >> member2;
......
}
假如s满了QSave的时候)或者s数据不QLoad的时候)Q函C{待Q直到s可用或者出错退出。相当于q程的Stack帮我们保存了I/O状态的上下文?/P>
但是现在要{到异步方式I/OQ当s“不可用”的时候,U程应该中断当前的操作,把I/O状态的上下文保存下来,转而做其他的操作?BR>所以麻烦就来了Q要自己做这个上下文的保存。一般来说要记录以下的内容:
1、操作到哪一个成员?BR>2、假如成员是一个普通的cd、那p记录操作到类型的哪一个byte?BR>2、如果成员是一个复合类型,同样Q递归地回C1?/P>
因此Q上下文保存的结果一般都是一个自己做的stackQ里面就是记录这个递归的过E?/P>
其实xQ何苦ؓ了省那几十k的空间折自己呢Q例如输出,先用同步的方式把数据记录在内存,然后p录内存的起始地址和长度,异步处理的时候就把内存输出,如果没有输出完的Q就C未输出部分的起始地址和长度,{待下一ơ?BR>不过当结果比较庞大的时候,q是需要自己慢慢苦qԌ真是悲惨…?/P>