cygwin下的cygheap:从父进程到子进程的复制

本文探讨了Cygwin环境下子进程的初始化过程,重点介绍了cygheap_fixup_in_child函数如何通过复制父进程的cygheap来设置子进程的堆空间,并分析了cygheap_init函数的作用。

快乐虾

http://blog.youkuaiyun.com/lights_joy/

lights@hb165.com

本文适用于

Cygwin checkout-2008-09-28

vs2008

欢迎转载,但请保留作者信息

Cygwin里的子进程在跳转到正确的位置之前要做一些特定的处理,这个处理由child_info_fork::handle_fork函数完成,在child_info_fork::handle_fork函数调用的第一个函数就是cygheap_fixup_in_child

cygheap_fixup_in_child (false);

看它的实现:

/* Called by fork or spawn to reallocate cygwin heap */

void __stdcall

cygheap_fixup_in_child (bool execed)

{

cygheap_max = child_proc_info->cygheap;

cygheap = (init_cygheap *) cygheap_max;

_csbrk ((char *) child_proc_info->cygheap_max - (char *) cygheap);

child_copy (child_proc_info->parent, false, "cygheap", cygheap, cygheap_max, NULL);

cygheap_init ();

debug_fixup_after_fork_exec ();

if (execed)

{

cygheap->hooks.next = NULL;

cygheap->user_heap.base = NULL; /* We can allocate the heap anywhere */

/* Walk the allocated memory chain looking for orphaned memory from

previous execs */

for (_cmalloc_entry *rvc = cygheap->chain; rvc; rvc = rvc->prev)

{

cygheap_entry *ce = (cygheap_entry *) rvc->data;

if (!rvc->ptr || rvc->b >= NBUCKETS || ce->type <= HEAP_1_START)

continue;

else if (ce->type < HEAP_1_MAX)

ce->type += HEAP_1_MAX; /* Mark for freeing after next exec */

else

_cfree (ce); /* Marked by parent for freeing in child */

}

}

}

在这里child_proc_info是父进程调用CreateProcess时传递进来的参数,其cygheapcygheap_max保存了父进程的cygheap的范围,这个函数做的第一件事就是将父进程这一段空间的内容复制到子进程相当地址的空间中,这个功能由child_copy函数完成。

紧接着,又调用了一个叫cygheap_init的函数:

extern "C" void __stdcall

cygheap_init ()

{

cygheap_protect.init ("cygheap_protect");

if (!cygheap)

{

cygheap = (init_cygheap *) memset (_cygheap_start, 0,

_cygheap_mid - _cygheap_start);

cygheap_max = cygheap;

_csbrk (sizeof (*cygheap));

}

if (!cygheap->fdtab)

cygheap->fdtab.init ();

if (!cygheap->sigs)

sigalloc ();

}

此时,由于cygheap的内容已经从父进程完整复制过来,这个函数相当于什么事没做。唯一有效果的就是cygheap_protect.init函数调用。

cygheap_init之后,是一行空语句:

# define debug_fixup_after_fork_exec() do {} while (0)

由于从child_info_fork::handle_fork传递进来的execedfalse,因此函数执行到此结束。

1 参考资料

cygwin下的/etc/fstab(2009-9-7)

cygwin关键技术:fork(2009-9-4)

cygwin关键技术:设备模拟(2009-9-4)

cygwin关键技术cygheap(2009-9-2)

cygwin关键技术:tls(2009-8-24)

vs2008下使用cygwin23):stdinstdoutstderr(2008-10-21)

vs2008下使用cygwin22):使用tls(2008-10-20)

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值