2009/12/21

Perl Threads

不得不说,perl 在M$ windows 下面实现的模拟fork真的是不堪一用,有很多限制,比如说: 不能fork 超过64次。也不能怪Perl,windows 对进程的处理就跟 Unix 大不相同!不过好在对于Thread的支持 Windows倒是没什么大问题。

给一个Windows下Perl多线程编程的小例子,自己留着慢慢用:) 里面用到:线程同步,变量共享。(需要Perl 5.8或者以上版本来支持 threads模块; say 这个好像是 Perl 5.10的feature, 其实就就print自动帮你加一个回车换行!)

use strict;
use warnings;

use feature qw(switch say);

use threads;
use threads::shared;
use Thread::Semaphore;

my $n = 9;

# shared variant across threads
my $arg :shared;

sub thread_proc
{
    my $sem = shift;

    for (1..$n) {
        # TODO: prepare works.
        sleep(1); # dummy 
        
        # wait until main thread wait me up!
        $sem->down;

        # TODO: Do my business~~~
        say "thread: $arg"; # dummy task
        sleep(1);   # dummy
    }

    say "thread_proc is over";
}

my $sem = new Thread::Semaphore();
my $thr = threads->create('thread_proc', $sem);
$sem->down; # Lock the semaphore

# Main thread
for(1..9)
{           
    # TODO: prepare works
    $arg = "$_ String " . ($_ * 1273);
    say "main: $arg";

    # Wait up the thread
    $sem->up;

    # TODO: Do some other works.
    sleep(3); # dummy task;
}

# wait for the thread to die
$thr->join();

print "end \n";

2009/12/14

通过虚拟机进行 Windows Kernel Debug

文介绍了硬件方式,这次来个更快的,通过虚拟机进行 Windows Kernel Debug。现在计算机硬件如此强大,我们完全可以把Target运行在一个虚拟机内,然后通过宿主机来调试。

首先,target——也就是虚拟机,也要进行同样的启动配置,让它进入debug模式。

其次,配置虚拟机程序,让它把target的COM端口 映射到一个命名管道。


以Virtual PC2007为例子,需要把Target的端口映射成一个 命名管道。其他的虚拟及程序如 VMWare 以及 VirtualBox也都有相应的设置。

然后,修改 windbg的参数,通过命名管道连接target
windbg -k com:pipe,port=\\.\pipe\com2,resets=0,reconnect
连接搞定!!!

效果和使用一个 单独的target计算机一样 :D

Windows Kernel Debug

Debug 对于程序开发来说是非常非常重要的手段。一个良好的Debug开发环境会让开发工作无往而不利。 对于 Microsoft Windows这样的庞然大物,内核开发的调试工作是非常有挑战性的。Windows 驱动程序开发,这些都需要进行内核级别的调试。当然,Microsoft的同志们,感触肯定比我们要多,因为他们每天都要在上面工作。
Microsoft实际上也已经作了大量的工作,对于Windows内核开发而言,内核的调试其实还是很简单的。

1, 硬件环境准备
进行windows内核调试,原则上需要两台计算机:一个运行测试代码叫做target;另一个运行debugger 叫做 Host。在Target与Host之间需要 通讯连接。目前比较常见的有三种: 串口,USB, 和1394。 串口是最常见的,下面就以串口为例。

Figure 1 Target and Host.
(from http://www.wd-3.com/archive/RemoteDbg.htm, Author: Jolyon Wright)
可以把 Host COM1 连接 Target COM1;也可以 Host COM2 连 Target COM1。
连接的时候不需要 一一对应。

2,Target 设置
所谓Target设置,其实就是打开Target计算机 Windows操作系统的调试选项。Windows都是内置内核调试功能的, 但是缺省关闭的。需要通过修改启动参数 (boot option) 打开。

对于Windows server 2003/XP/2000 操作系统,可以修改 Boot.ini 在启动项的后面加上
“/debug /debugport=COM2 /baudrate=115200”
看起来就象下面这样:
multi(0)disk(0)rdisk(0)partition(1)\WINDOWS="Windows XP Debug1" /fastdetect /debug /debugport=COM1 /baudrate=115200
这里 debugport 可以用COM1/2, Baudrate也可以作相应的调整 115200是不错的选择。

对于Windows Vista/2008/7 操作系统,需要使用 bcdedit来设置。这里需要两步:
第一: 打开debug
bcdedit /debug [on | off]
第二: 设置debug参数
bcdedit /dbgsettings SERIAL DEBUGPORT:2 BAUDRATE:115200
第二步其实可以跳过,系统缺省使用串口COM1, 速率:115200。

然后重新启动Target,进入调试模式。 其实在调试模式下,如果没有连上Debugger,系统运行起来就跟普通的系统差不多,可能会慢一些。


3, Host调试软件
Host 需要安装 Debugging Tools for Windows (http://www.microsoft.com/whdc/devtools/downloads.mspx)
安装完毕后,就可以使用Windbg连接 target。建议使用 6.11或更高的版本。

运行参数:
windbg -k com:port=Com1,baud=115200

Windbg启动后应该显示:
Microsoft (R) Windows Debugger Version 6.1.0017.2
Copyright (c) Microsoft Corporation. All rights reserved.
Opened \\.\com1
Waiting to reconnect...

Target连接成功后应该显示:
Connected to Windows XP 2600 x86 compatible target, ptr64 FALSE
Kernel Debugger connection established.
Symbol search path is: \\Sysphus\softshared\symbols\KillerApp\sym;SRV*\\Sysphus\softshared\symbols\SymStore*http://msdl.microsoft.com/download/symbols
Executable search path is:
Windows XP Kernel Version 2600 MP (1 procs) Checked x86 compatible
Built by: 2600.xpsp1.020828-1920

显示的内容会随着Target运行软件的版本而有些不同。
在windbg 通过 ctrl+break键 来中断 target,进入调试交互状态,这时候Target就像死了一样,别紧张,这是因为你再通过debugger来 控制它。

4, Host 配置Symbol Path
调试中有一个很重的步骤就是 Symbol,没有Symbol 在调试中寸步难行,我们只能面对一堆二进制代码。微软提供的Symbol支持方案配置很灵活,可以有本地symbol 也可以通过Symbol server, symbol cache。 关于symbol 在 Debugging Tools for Windows的 帮助文件中 专门有一个章节介绍: Debuggers >> Symbols
比较快捷的办法:下载 Windows Symbol Files;同时配置 Microsoft的symbol server。
A, 下载相应版本的 Windows Symbol Files http://www.microsoft.com/whdc/devtools/debugging/symbolpkg.mspx
安装到 一个位置:如 C:\WinSymbols
B, 在Windbg中设置 Symbol paths: File--> Symbol File Path 快捷方式(Ctrl+S)
设置path 为:
C:\WinSymbols;d:\OtherPath\To\the\build\pdb;srv*D:\Symbols*http://msdl.microsoft.com/download/symbols
这里D:\Symbols 是用来保存从 Microsoft symbol服务器下载回来的 pdb。

剩下的工作就是学习如何使用 windbg了。 :)

Goood luck~~~

2009/11/30

如果安装 Chrome OS 的系统免费怎样?

关于Google Chrome OS的讨论已经很多了,有人说好,有人说滥。总的来说 Chrome OS 的核心问题还是PC的味道还不足!怎么都还是一个 Internet 的终端,虽然它也许能够在浏览器中执行 native code,但是再怎么搞也还不是全功能的 PC,不能与 Microsoft Windows 抗衡。

但是如果 安装了 Chrome OS 的netbook 免费送给你那会怎样? 你会不会想要一个? 比较可能的方案是: 将Chrome OS上网本与无线运营商的宽带服务绑定, 签一个 2年的每月 $30 的合约,白送你一个 Chrome OS 上网本!WIFI 自然是由Google 自家提供! Chrome OS 功能虽然弱,比起手机啥的还是要强大很多了吧?

这可以制造一个传统PC完全不同的用户体验,完全不一样的应用环境,完全不同的商业模式。如果用户完全适应了这样的 应用环境,还有谁会去买Windows? 微软的用户优势将当然无存! 有点耸人听闻? :)

也许这就是将来的互联网, 就如同 Sun Microsystem 的口号:网络就是计算机!

2009/11/20

Google Chromium OS 那点儿事儿

Google 要做操作系统了! 哦,怎么又是Chromium? 不是已经有了一个Google Chrome了?

Google Chromium OS 的口号就是 “浏览器就是你的操作系统”!


很明显,Chromium的目标就是上网本。NVIDIA 在这里也后很多动作,特别是她们的 Tegra SoC芯片,在这个完全以浏览器为核心的平台上,用户尽可以忘掉自己用的是 Intel, AMD, X86, AMD64, or ARM。 其实这也符合Google的利益, 很难有x86的CPU卖到 20美元以下,而最贵的ARM CPU也就是20美元。 ARM架构的上网本,无疑会极大程度的推动 上网本的价格 更平民化。 越多的人拥有 上网本,就为Google提供了更多的用户。

这里的潜台词就是:“您上internet吗? 如果上internet就用Google吧!我们是最好的!” 听到这个,微软 一定要昏倒了。不过也不必反映过度,这终究只是一个新兴的领域。谁工作做的更到位,谁就会领先。 微软要加油了!

2009/10/02

从Graphic PU走向General PU

G300 作为 nVidia 的下一代GPU,3引入很多变化: 512 CUDA Cores, L1/L2 cache, GigaThread, ECC memory controller. 看起来都更像是一个General Processing Unit.

nVidia 还是有雄心壮志的,对于nVidia而言,这是一个大胆的尝试。从架构上看,确实可以被称为下一代。

in reference to: Next Generation CUDA Architecture, Code Named Fermi (view on Google Sidewiki)

2009/09/28

Google Voice and bandwidth.com

It isn't a secret that the land line provided by Google Voice is ordered from Bandwidth.com -- The 4st fastest growing privately held company in U.S.A. Bandwidth.com is a company in RTP, North Carolina.

The small high-tech company always be the source of creatures! Why we don't have these in China? //sigh

2009/09/02

VIM Wiki

非常不错的网站 介绍了很多VIM的技巧。今天用到了一个小技巧,如何在VIM内排序。在VIM7.0
这个非常简单,可以直接使用内置的`:sort' 命令。当然,还可以剔除重复的 `:sort u'.

2009/08/13

What's Byte Order Mark (BOM) in Unicode

When a BOM is used, is it only in 16-bit Unicode text?

A: No, a BOM can be used as a signature no matter how the Unicode text is transformed: UTF-16, UTF-8, UTF-7, etc. The exact bytes comprising the BOM will be whatever the Unicode character FEFF is converted into by that transformation format. In that form, the BOM serves to indicate both that it is a Unicode file, and which of the formats it is in. Examples:

Bytes Encoding Form
00 00 FE FF UTF-32, big-endian
FF FE 00 00 UTF-32, little-endian
FE FF UTF-16, big-endian
FF FE UTF-16, little-endian
EF BB BF UTF-8

链接是 UTF系列问题的权威解答FAQ,强烈建议阅读!

VIM unicode

在 MS Windows 下面由于受 Byte Order Mark (BOM) 的控制, 需要对GVIM 做一些配置才能正常工作。 这包括 tenc, enc, fencs, guifont, guifontwide。 这样一来,vim就可以自动 根据BOM做出正确的显示了,同时也可以自动识别GBK和BIG5。


if has("multi_byte")
set encoding=unicode
let &termencoding = &encoding
" Set default encoding as UTF-8 with BOM
setglobal fileencoding=utf-8 bomb
" Auto detect the file encoding BOM unicode, utf-8, GBK, Big5, Latin1
set fileencodings=ucs-bom,utf-8,cp936,cp950,latin1

" Walkaround the encoding problem for fenc=utf-8 && enc=ucs-2
augroup i18n
autocmd!
autocmd BufReadPost * if &fileencoding == "utf-8" | let &encoding = &fileencoding | endif
augroup END
endif

" Enable the Chinese characters
"set guifont=Bitstream\ Vera\ Sans\ Mono:h10:cANSI,NSimSun:h11:cGB2312
set guifont=Consolas:h11:cANSI,NSimSun:h11:cGB2312
set guifontwide=NSimSun:h11:cGB2312

2009/08/12

Google Wave Sandbox

This is the first time for me to use Google Wave. It looks a little strange as a fresh user. We MUST fully understand "what is a WAVE?"
  • IM?
  • Word?
  • Blog?
  • twitter?
  • SNS?
Are you understanding this? It might be better if there are some others in my Wave. I need to take a look at the Google Wave API to find more.

It just likes someone said, "It looks more like a Microsoft product, not Google!" I think, it still takes time to figure out "What's a Wave?"

2009/07/14

Hex string to ASCII string in Perl

If you want to convert a string "ABCDEFG" to Hex mode like "07,41,42,43,44,45,46,47" -- a length prefix with all the others in HEX mode. How to do it in Perl?

You can do
$to = join(",", map { unpack('H2', $_) } chr(length($from)), split(/(?=.)/, $from));

or
$to = join(",", map { unpack('H2', $_) } split(/(?=.)/, pack('W/a', $from)));


How to do the reverse??? A question for you :P

2009/06/30

An English-to-Chinese Dictionary based on the evil Google Suggest Quries


<SearchPlugin xmlns="http://www.mozilla.org/2006/browser/search/">
<ShortName>gDictionary</ShortName>
<Description>Google English-Chinese Dictionary</Description>
<InputEncoding>UTF-8</InputEncoding>
<Image width="16" height="16">data:image/png;base64,AAABAAEAEBAAAAEAGABoAwAAFgAAACgAAAAQAAAAIAAAAAEAGAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAADs9Pt8xetPtu9FsfFNtu%2BTzvb2%2B%2Fne4dFJeBw0egA%2FfAJAfAA8ewBBegAAAAD%2B%2FPtft98Mp%2BwWsfAVsvEbs%2FQeqvF8xO7%2F%2F%2F63yqkxdgM7gwE%2FggM%2BfQA%2BegBDeQDe7PIbotgQufcMufEPtfIPsvAbs%2FQvq%2Bfz%2Bf%2F%2B%2B%2FZKhR05hgBBhQI8hgBAgAI9ewD0%2B%2Fg3pswAtO8Cxf4Kw%2FsJvvYAqupKsNv%2B%2Fv7%2F%2FP5VkSU0iQA7jQA9hgBDgQU%2BfQH%2F%2Ff%2FQ6fM4sM4KsN8AteMCruIqqdbZ7PH8%2Fv%2Fg6Nc%2Fhg05kAA8jAM9iQI%2BhQA%2BgQDQu6b97uv%2F%2F%2F7V8Pqw3eiWz97q8%2Ff%2F%2F%2F%2F7%2FPptpkkqjQE4kwA7kAA5iwI8iAA8hQCOSSKdXjiyflbAkG7u2s%2F%2B%2F%2F39%2F%2F7r8utrqEYtjQE8lgA7kwA7kwA9jwA9igA9hACiWSekVRyeSgiYSBHx6N%2F%2B%2Fv7k7OFRmiYtlAA5lwI7lwI4lAA7kgI9jwE9iwI4iQCoVhWcTxCmb0K%2BooT8%2Fv%2F7%2F%2F%2FJ2r8fdwI1mwA3mQA3mgA8lAE8lAE4jwA9iwE%2BhwGfXifWvqz%2B%2Ff%2F58u%2Fev6Dt4tr%2B%2F%2F2ZuIUsggA7mgM6mAM3lgA5lgA6kQE%2FkwBChwHt4dv%2F%2F%2F728ei1bCi7VAC5XQ7kz7n%2F%2F%2F6bsZkgcB03lQA9lgM7kwA2iQktZToPK4r9%2F%2F%2F9%2F%2F%2FSqYK5UwDKZAS9WALIkFn%2B%2F%2F3%2F%2BP8oKccGGcIRJrERILYFEMwAAuEAAdX%2F%2Ff7%2F%2FP%2B%2BfDvGXQLIZgLEWgLOjlf7%2F%2F%2F%2F%2F%2F9QU90EAPQAAf8DAP0AAfMAAOUDAtr%2F%2F%2F%2F7%2B%2Fu2bCTIYwDPZgDBWQDSr4P%2F%2Fv%2F%2F%2FP5GRuABAPkAA%2FwBAfkDAPAAAesAAN%2F%2F%2B%2Fz%2F%2F%2F64g1C5VwDMYwK8Yg7y5tz8%2Fv%2FV1PYKDOcAAP0DAf4AAf0AAfYEAOwAAuAAAAD%2F%2FPvi28ymXyChTATRrIb8%2F%2F3v8fk6P8MAAdUCAvoAAP0CAP0AAfYAAO4AAACAAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAACAAQAA</Image>
<Url type="application/x-suggestions+json" method="GET" template="http://suggestqueries.google.com/complete/search?client=suggest&amp;hjson=t&amp;ds=d&amp;hl=zh-CN&amp;q={searchTerms}"></Url>
<Url type="text/html" method="GET" template="http://www.google.com/dictionary?aq=f&amp;langpair=en|zh-CN&amp;hl=en&amp;q={searchTerms}"></Url>
<SearchForm>http://www.google.com/dictionary</SearchForm>
</SearchPlugin>

2009/06/29

Small Skills of Command Prompt for Windows

There are some useful skills for CMD.exe in Windows.

1, How to do a substring in the CMD.exe -- %VAR_NAME:~POS,LEN%
for example
set name=fingercat
echo %name:~6,3%
This will give you a "cat" ;)

2, How to get the input of user as a string?
On windows 2000 or later. It is simple.
set /p answer=Prompt Message Here
echo %answer%
This will give you the input stirng of user.

Windows Command Prompt (.bat) file never suppose to be a powerful shell. But Microsoft really give it more an more power until a real PowerShell came into place.

2009/06/10

Inside the Erlang VM - focus on SMP

It discussed the current status and possible future of SMP enabled Erlang VM.
It is worth to read!

2009/04/22

VIMRC file


source $VIMRUNTIME/vimrc_example.vim
source $VIMRUNTIME/gvimrc_example.vim
set nobackup
set ch=1
set tabstop=4
set shiftwidth=4
"set softtabstop=4
set expandtab
colorscheme darkblue
"colorscheme oceandeep


" Enable the Chinese characters
set guifont=Bitstream\ Vera\ Sans\ Mono:h10:cANSI,NSimSun:h12:cGB2312
set guifontwide=NSimSun:h12:cGB2312


" display the syntax name under the cursor
map <F12> :echo synIDattr(synIDtrans(synID(line("."), col("."), 1)), "name")<CR>


" We can navigate the list by using the <F3> and <S-F3>
map <F3> :cnext<CR>
map <S-F3> :cprevious<CR>


" Let's help the tab navigation a little
map <F9> :tabprevious<CR>
map <S-F9> :tabnext<CR>


" Tlist
map <F5> :Tlist<CR>
set tags=./tags,../tags,../../tags

2009/03/15

C++ reinterpret_cast

说起 C++ 的类型转换,一共有四种:

  • dynamic_cast
  • static_cast
  • reinterpret_cast
  • const_cast
其中 reinterpret_cast 是很有意思的,它可以被看作是 C 语言中强制类型转换的功能,它是一种非检查的暴力转换手段。通过它,我们可以把 指向 int* 转换为 double* 。

当然也可以用来做函数指针的转换,比如:

void FuncA(char *src, int len, int *pLen)
{
*pLen = len;
}

int _tmain(int argc, _TCHAR* argv[])
{
bool (*func_ptr) (char*, int);

func_ptr = reinterpret_cast<bool (*)(char*, int)>(&FuncA);

return 0;
}

当然了也可以用来转换 类成员函数,如:

class ObjectA
{
public:
void FuncA(char *src, int len, int *pLen)
{
*pLen = len;
}

bool FuncB(char *src, int len, int *pLen)
{
*pLen = len;
return false;
}
};

class ObjectB
{

};

int _tmain(int argc, _TCHAR* argv[])
{
bool (ObjectB::*func_ptr) (char*, int);

//ObjectA obj;
func_ptr = reinterpret_cast<bool (ObjectB::*)(char*, int)>(&ObjectA::FuncB);

return 0;
}

但是不能在普通函数和类成员函数之间转换。

2009/02/25

Install Safari4 without installation on Windows

First, Extract the Safari.cab into a folder. The Safari.cab is from Safari.msi of SafariSetup.exe, you can open the .exe and .msi by using 7-zip tool. :D

Second, put the file into the right folder. If you have MinGW or Cygwin, you can use this script to move all the files into the right folder.

for i in *; do fp=${i//_/\/}; echo $fp; f=$(basename $fp); eval "p=\${fp%$f}"; if [ $fp != $f ];then if [ ! -d $p ];then mkdir -p $p; fi; mv $i $fp; fi; done


Now ready to go! Safari4 beta is a green software.

2009/02/16

NORTEL 幽默

NORTEL 从来就不缺乏有才华的人,这个我曾经工作过的百年老店今天已经是风雨飘摇。
看看这些 NORTEL 员工们制作的讽刺剧吧!

我不得不赞叹,太油菜了!

2009/01/20

Java GUI Effectives

Java gets widely usage on Server side, while the client technology is still evolution continuously. Since Java 5.0, more and more interesting GUI feature are added into the JVM. They are:
  • OpenGL-based render pipeline
    As you know, Swing renders all the widgets by itself, that's the reason why some case the Java GUI looks so strange. :) Previously on Microsoft Windows, the DirectDraw and Direct3D was the only choice. But now you can use OpenGL pipeline as well.
    It is disabled by default, but it can enabled by setting
    -Dsun.java2d.opengl=true
  • Font Anti-Aliasing
    It is an important feature for the font anti-aliasing. Now it is possible for Java application to specify the Font Anti-Aliasing feature by itself with system property:
    -Dawt.useSystemAAFontSettings=lcd

  • Metal and Nimbus Look and Feel
    Metal (from Java 5.0) and Nimbus (from Java 6.0u10) are available in standard JRE distribution.
Really hope Java could be better and better~~~

2009/01/16

C++ vtable

在 C++ 的OO模型中,很重要的一个特性是运行时多态。运行时多态是通过类的虚方法实现的。看下面这个例子:


struct IObject {
  virtual void MethodA() = 0;  
  virtual int  MethodB(char *) = 0;
};

class A : public IObject {
public:
  virtual void MethodA() {
    std::cout << "method A" << std::endl;
  };

  virtual int MethodB(char *p) {
    std::cout << "method B " << p << std::endl;
    return 0;
  };

public:
  int MethodC(int c) {
    std::cout << "method C non-virtual" << std::endl;
    return ++c;
  }
private:
  int mem_;
};

int main(int argc, cahr *argv[])
{
  IObject *pObj = new A;

  pObj->MethodA();
  pObj->MethodB(NULL);

  // FIXME: This is a compile error!
  pObj->MethodC(1); // error

  delete A;

  return 0;
};

C++ 运行时多态, 在执行代码中,主要通过 vtable 实现。让我们用C来重新描述上面的例子。


// VTABLE of class IObject
struct I_IObject {
  void *pMethodA(void);
  int  *pMethodB(char *);
};

// Instance variant type of IObject
struct IObject {
  struct I_IObject *vtable_this;
};

// VTABLE of class A
struct A;
struct I_A {
  void *pDtor(A*)
};

// Instance object variant type of class A
struct A {
  struct I_IObject *vtable_IObject;
  struct I_A *vtable_this;

  int *pMethodC(int);
  int mem_;
};

void A_MethodA (void) {
  printf("method A\n");
}

int  A_MethodB (char *p) {
  printf("method B %s\n", p);
}

int  A_MethodC (int c) {
  printf("method C non-virtual\n");
  return ++c;
}

void A_dtor(struct A *_this) {
  free(_this);
}

struct A *A_ctor() {
  struct A *p = malloc(sizeof(struct A));

  // Non-virtual function will be assign the value directly.
  p.pMethodC = &A_MethodC;

  /////////////////////////////////////////////////
  // vtable initialization code
#ifdef A_MethodA
  p.vtable_IObject->pMethodA = &A_MethodA;
#else
  p.vtable_IObject->pMethodA = &IObject_MethodA; // Warning!
#endif

#ifdef A_MethodB
  p.vtable_IObject->pMethodB = &A_MethodB;
#else
  p.vtable_IObject->pMethodB = &IObject_MethodB; // Warning!
#endif

  // vtable of A itself
  p.vtable_self->pDtor = &A_dtor;

  return p;
}

int main(int argc, char *argv[])
{
  IObject *pObj = (IObject*) A_ctor();

  pObj->vtable_self->pMethodA();
  pObj->vtable_self->pMethodB(NULL);

  A_dtor(pObj);

  return 0;
}




C的定价物确实有些繁琐,不过基本的结构就是这样了。具体说来是这样:
1,如果一个类 virtual function, 这些 virtual funciton 就会被统一在一个 vtable 中;
2,包含 virtual function 的class 都会有一个指向 vtable structure的指针,如果当前类重写了 virtual function, 在对象初始化的时候相应的虚函数指针就会被替换;
3,虚函数的调用一律通过vtable定位,因为存在vtable这一层中继,就可以保证在运行态可以通过父类的指针执行指向子类对象的方法,因为类对象初始化的时候正确的重写了vtable的内容。
4,一个对象多一个包含virtual function的基类,就会在类变量的结构中多引入一个指向父类vtable structure的指针。在类对象初始化的时候,就需要更多的 vtable 初始化代码。:D

多重继承会导致 vtable 膨胀, Microsoft ATL 引入了一个 ATL_NO_VTABLE __declspec(novtable) C++ 扩展。关于这个,下回再说~~~

其实这个例子里面还有一个小问题, 不知道大家能不能看出来啊!

2009/01/15

Nortel files for bankruptcy

百年老店终于也挺不住了, NT的问题是积重难返,如果没有本质性的改变,估计会就此消失了。即便能恢复回来,估计也就不剩什么了~~~ :(

BlockChain 相关电子书

@copyright of Sam Chadwick   - https://thehub.thomsonreuters.com/groups/bitcoin/blog/2017/09/10/blockchain-paper Blockchain Papers A c...