Skip to content

LA glibc下libcbench测例b_pthread_create_serial1测试项设置了非法线程栈大小 #47

@yuanmu2004

Description

@yuanmu2004

在测试LoongArch glibc的libcbench测例时发现爆内存,经检查是mmap映射了过多的虚拟地址空间所致,内核打印的调试信息中包含数条以下调试信息:

[sys_mmap] addr:0x0, length:0x801000, prot:MmapProt(0x0), flags:MmapFlags(MAP_PRIVATE | MAP_ANONYMOUS | MAP_STACK), fd:18446744073709551615, offset:0x0

阅读位于 libc-bench/pthread.c:35的源码可知,该测试项创建了2500个线程,并意图为每个线程分配16384字节大小的栈空间。pthread_create使用mmap系统调用分配线程栈,在用户为attr设置了栈大小stacksize的情况下,mmap系统调用的length参数理应为stacksize+guardsize,这与实际情况不符。

阅读glibc代码发现,在测例调用pthread_attr_setstacksize时,glibc设置attr中的stacksize字段前,会检查传入的stacksize是否大于等于PTHREAD_STACK_MIN(参见nptl/pthread_attr_setstacksize.c),这个值在LA架构下等于131072。不满足时不修改attr->stacksize字段并返回错误码。在线程创建时,attr->stacksize仍为缺省值,故glibc使用默认的__default_pthread_attr.internal.stacksize,这个值在__pthread_early_init中被初始化为rlimit_stack,这个值在我们内核的设计中是8MB。我们尝试修改了prlimit64系统调用的返回值,观察到mmap分配的内核栈大小也改变了,验证了这一猜想。

对libc-bench进行反汇编,也能验证这个猜想。以下是pthread_attr_setstacksize的汇编代码:

000000012001a954 <__pthread_attr_setstacksize>:
check_stacksize_attr():
/home/airxs/user/gnu/build-cross-tools-hf/glibc-2.38/nptl/../sysdeps/nptl/pthreadP.h:707
   12001a954:	1400040c 	lu12i.w     	$t0, 32
   12001a958:	6c000cac 	bgeu        	$a1, $t0, 12	# 12001a964 <__pthread_attr_setstacksize+0x10>
__pthread_attr_setstacksize():
/home/airxs/user/gnu/build-cross-tools-hf/glibc-2.38/nptl/pthread_attr_setstacksize.c:38
   12001a95c:	02805804 	li.w        	$a0, 22
/home/airxs/user/gnu/build-cross-tools-hf/glibc-2.38/nptl/pthread_attr_setstacksize.c:43
   12001a960:	4c000020 	ret
/home/airxs/user/gnu/build-cross-tools-hf/glibc-2.38/nptl/pthread_attr_setstacksize.c:40
   12001a964:	29c08085 	st.d        	$a1, $a0, 32
/home/airxs/user/gnu/build-cross-tools-hf/glibc-2.38/nptl/pthread_attr_setstacksize.c:42
   12001a968:	00150004 	move        	$a0, $zero
   12001a96c:	4c000020 	ret

第一行lu12i.w $t0, 32,便是glibc中LA架构的PTHREAD_STACK_MIN值131072。

这个问题可能导致大多数队伍使用正常手段无法通过LA架构glibc的libc-bench测例,希望老师能修复这个问题。

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions