回覆列表
  • 1 # 高山jJ

    核心棧、使用者棧

    32位Linux系統上,程序的地址空間為4G,包括1G的核心地址空間-----核心棧,和3G的使用者地址空間-----使用者棧。

    核心棧,是各個程序在剛開始建立的時候透過記憶體對映共享的,但是每個程序擁有獨立的4G的虛擬記憶體空間從這一點看又是獨立的,互不干擾的(只是剛開始大家都是對映的同一份記憶體複製)

    使用者棧就是大家所熟悉的記憶體四區,包括:程式碼區、全域性資料區、堆區、棧區

    使用者棧中的堆區、棧區即為程序堆、程序棧

    程序堆、程序棧與執行緒棧

    1.執行緒棧的空間開闢在所屬程序的堆區與共享記憶體區之間,執行緒與其所屬的程序共享程序的使用者空間,所以執行緒棧之間可以互訪。執行緒棧的起始地址和大小存放在pthread_attr_t 中,棧的大小並不是用來判斷棧是否越界,而是用來初始化避免棧溢位的緩衝區的大小(或者說安全間隙的大小)

    2.程序初始化的時候,系統會在程序的地址空間中建立一個堆,叫程序預設堆。程序中所有的執行緒共用這一個堆。當然,可以增加1個或幾個堆,給不同的執行緒共同使用或單獨使用。----一個程序可以多個堆

    3、建立執行緒的時候,系統會在程序的地址空間中分配1塊記憶體給執行緒棧,通常是1MB或4MB或8MB。執行緒棧是獨立的,但是還是可以互訪,因為執行緒共享記憶體空間

    4.堆的分配:從作業系統角度來看,程序分配記憶體有兩種方式,分別由兩個系統呼叫完成:brk()和mmap(),glibc中malloc封裝了

    5.執行緒棧位置-記憶體分佈測試程式碼

    [cpp] view plain copy

    #include <pthread.h>

    #include <stdio.h>

    #include <unistd.h>

    #include <string.h>

    #include <errno.h>

    #include <malloc.h>

    #include <sys/syscall.h>

    void* func(void* arg)

    {

    long int tid = (long int)syscall(SYS_gettid);

    printf("The ID of this thread is: %ld\n", tid );

    static int a=10;

    int b=11;

    int* c=(int *)malloc(sizeof(int));

    printf("in thread id:%u a:%p b:%p c:%p\n",tid,&a,&b,c);

    printf("leave thread id:%ld\n",tid);

    sleep(20);

    free((void *)c);

    }

    void main()

    {

    pthread_t th1,th2;

    printf("pid=%u\n",(int)getpid());

    func(NULL);

    int ret=pthread_create(&th1,NULL,func,NULL);

    if(ret!=0)

    {

    printf("thread1[%d]:%s\n",th1,strerror(errno));

    }

    ret=pthread_create(&th2,NULL,func,NULL);

    if(ret!=0)

    {

    printf("thread2[%d]:%s\n",th2,strerror(errno));

    }

    pthread_join(th1,NULL);

    pthread_join(th2,NULL);

    }

    輸出:

    [le@localhost threadStack]$ ./threadStack_main pid=16433

    The ID of this thread is: 16433

    in thread id:16433 a:0x60107c b:0x7fffc89ce7ac c:0x1b54010

    leave thread id:16433

    The ID of this thread is: 16461

    The ID of this thread is: 16460

    in thread id:16461 a:0x60107c b:0x7f6abb096efc c:0x7f6ab40008c0

    leave thread id:16461

    in thread id:16460 a:0x60107c b:0x7f6abb897efc c:0x7f6aac0008c0

    leave thread id:16460

    主執行緒呼叫func後

    [le@localhost threadStack]$ sudo cat /proc/16433/maps

    00400000-00401000 r-xp 00000000 fd:02 11666 /home/le/code/threadStack/threadStack_main

    00600000-00601000 r--p 00000000 fd:02 11666 /home/le/code/threadStack/threadStack_main

    00601000-00602000 rw-p 00001000 fd:02 11666 /home/le/code/threadStack/threadStack_main

    01b54000-01b75000 rw-p 00000000 00:00 0 [heap]

    7f6abb899000-7f6abba4f000 r-xp 00000000 fd:00 100678959 /usr/lib64/libc-2.17.so

    7f6abba4f000-7f6abbc4f000 ---p 001b6000 fd:00 100678959 /usr/lib64/libc-2.17.so

    7f6abbc4f000-7f6abbc53000 r--p 001b6000 fd:00 100678959 /usr/lib64/libc-2.17.so

    7f6abbc53000-7f6abbc55000 rw-p 001ba000 fd:00 100678959 /usr/lib64/libc-2.17.so

    7f6abbc55000-7f6abbc5a000 rw-p 00000000 00:00 0

    7f6abbc5a000-7f6abbc70000 r-xp 00000000 fd:00 105796566 /usr/lib64/libpthread-2.17.so

    7f6abbc70000-7f6abbe70000 ---p 00016000 fd:00 105796566 /usr/lib64/libpthread-2.17.so

    7f6abbe70000-7f6abbe71000 r--p 00016000 fd:00 105796566 /usr/lib64/libpthread-2.17.so

    7f6abbe71000-7f6abbe72000 rw-p 00017000 fd:00 105796566 /usr/lib64/libpthread-2.17.so

    7f6abbe72000-7f6abbe76000 rw-p 00000000 00:00 0

    7f6abbe76000-7f6abbe97000 r-xp 00000000 fd:00 105796545 /usr/lib64/ld-2.17.so

    7f6abc073000-7f6abc076000 rw-p 00000000 00:00 0

    7f6abc095000-7f6abc097000 rw-p 00000000 00:00 0

    7f6abc097000-7f6abc098000 r--p 00021000 fd:00 105796545 /usr/lib64/ld-2.17.so

    7f6abc098000-7f6abc099000 rw-p 00022000 fd:00 105796545 /usr/lib64/ld-2.17.so

    7f6abc099000-7f6abc09a000 rw-p 00000000 00:00 0

    7fffc89b0000-7fffc89d1000 rw-p 00000000 00:00 0 [stack]

    7fffc89fe000-7fffc8a00000 r-xp 00000000 00:00 0 [vdso]

    ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0 [vsyscall]

    兩個子執行緒啟動後

    [le@localhost threadStack]$ sudo cat /proc/16433/maps

    00400000-00401000 r-xp 00000000 fd:02 11666 /home/le/code/threadStack/threadStack_main

    00600000-00601000 r--p 00000000 fd:02 11666 /home/le/code/threadStack/threadStack_main

    00601000-00602000 rw-p 00001000 fd:02 11666 /home/le/code/threadStack/threadStack_main

    01b54000-01b75000 rw-p 00000000 00:00 0 [heap]

    7f6aac000000-7f6aac021000 rw-p 00000000 00:00 0

    7f6aac021000-7f6ab0000000 ---p 00000000 00:00 0

    7f6ab4000000-7f6ab4021000 rw-p 00000000 00:00 0

    7f6ab4021000-7f6ab8000000 ---p 00000000 00:00 0

    7f6aba897000-7f6aba898000 ---p 00000000 00:00 0

    7f6aba898000-7f6abb098000 rw-p 00000000 00:00 0 [stack:16461]

    7f6abb098000-7f6abb099000 ---p 00000000 00:00 0

    7f6abb099000-7f6abb899000 rw-p 00000000 00:00 0 [stack:16460]

    7f6abb899000-7f6abba4f000 r-xp 00000000 fd:00 100678959 /usr/lib64/libc-2.17.so

    7f6abba4f000-7f6abbc4f000 ---p 001b6000 fd:00 100678959 /usr/lib64/libc-2.17.so

    7f6abbc4f000-7f6abbc53000 r--p 001b6000 fd:00 100678959 /usr/lib64/libc-2.17.so

    7f6abbc53000-7f6abbc55000 rw-p 001ba000 fd:00 100678959 /usr/lib64/libc-2.17.so

    7f6abbc55000-7f6abbc5a000 rw-p 00000000 00:00 0

    7f6abbc5a000-7f6abbc70000 r-xp 00000000 fd:00 105796566 /usr/lib64/libpthread-2.17.so

    7f6abbc70000-7f6abbe70000 ---p 00016000 fd:00 105796566 /usr/lib64/libpthread-2.17.so

    7f6abbe70000-7f6abbe71000 r--p 00016000 fd:00 105796566 /usr/lib64/libpthread-2.17.so

    7f6abbe71000-7f

  • 中秋節和大豐收的關聯?
  • 注塑機的5種調機技巧?