正在显示
5 个修改的文件
包含
73 行增加
和
44 行删除
| @@ -9,15 +9,20 @@ | @@ -9,15 +9,20 @@ | ||
| 9 | #include <stdlib.h> | 9 | #include <stdlib.h> |
| 10 | #include <setjmp.h> | 10 | #include <setjmp.h> |
| 11 | 11 | ||
| 12 | -jmp_buf env_func1; | 12 | +jmp_buf context; |
| 13 | 13 | ||
| 14 | void func1() | 14 | void func1() |
| 15 | { | 15 | { |
| 16 | #if defined(__amd64__) || defined(__x86_64__) | 16 | #if defined(__amd64__) || defined(__x86_64__) |
| 17 | register long int rsp0 asm("rsp"); | 17 | register long int rsp0 asm("rsp"); |
| 18 | 18 | ||
| 19 | - int ret = setjmp(env_func1); | ||
| 20 | - printf("setjmp func0 ret=%d, rsp=%#lx\n", ret, rsp0); | 19 | + int ret = setjmp(context); |
| 20 | + printf("setjmp func1 ret=%d, rsp=%#lx\n", ret, rsp0); | ||
| 21 | + // enter by longjmp | ||
| 22 | + if (ret != 0) { | ||
| 23 | + printf("call by longjmp.\n"); | ||
| 24 | + exit(0); | ||
| 25 | + } | ||
| 21 | #endif | 26 | #endif |
| 22 | } | 27 | } |
| 23 | 28 | ||
| @@ -49,15 +54,15 @@ void func0() | @@ -49,15 +54,15 @@ void func0() | ||
| 49 | // for glibc 2.4+, it's not possible to get and set the sp in jmp_buf | 54 | // for glibc 2.4+, it's not possible to get and set the sp in jmp_buf |
| 50 | /** | 55 | /** |
| 51 | for example, the following is show the jmp_buf when setjmp: | 56 | for example, the following is show the jmp_buf when setjmp: |
| 52 | - (gdb) x /64xb env_func1[0].__jmpbuf | ||
| 53 | - 0x600ca0 <env_func1>: 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00 | ||
| 54 | - 0x600ca8 <env_func1+8>: 0xf8 0xc1 0x71 0xe5 0xa8 0x88 0xb4 0x15 | ||
| 55 | - 0x600cb0 <env_func1+16>: 0xa0 0x05 0x40 0x00 0x00 0x00 0x00 0x00 | ||
| 56 | - 0x600cb8 <env_func1+24>: 0x90 0xe4 0xff 0xff 0xff 0x7f 0x00 0x00 | ||
| 57 | - 0x600cc0 <env_func1+32>: 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00 | ||
| 58 | - 0x600cc8 <env_func1+40>: 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00 | ||
| 59 | - 0x600cd0 <env_func1+48>: 0xf8 0xc1 0x51 0xe5 0xa8 0x88 0xb4 0x15 | ||
| 60 | - 0x600cd8 <env_func1+56>: 0xf8 0xc1 0xd9 0x2f 0xd7 0x77 0x4b 0xea | 57 | + (gdb) x /64xb context[0].__jmpbuf |
| 58 | + 0x600ca0 <context>: 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00 | ||
| 59 | + 0x600ca8 <context+8>: 0xf8 0xc1 0x71 0xe5 0xa8 0x88 0xb4 0x15 | ||
| 60 | + 0x600cb0 <context+16>: 0xa0 0x05 0x40 0x00 0x00 0x00 0x00 0x00 | ||
| 61 | + 0x600cb8 <context+24>: 0x90 0xe4 0xff 0xff 0xff 0x7f 0x00 0x00 | ||
| 62 | + 0x600cc0 <context+32>: 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00 | ||
| 63 | + 0x600cc8 <context+40>: 0x00 0x00 0x00 0x00 0x00 0x00 0x00 0x00 | ||
| 64 | + 0x600cd0 <context+48>: 0xf8 0xc1 0x51 0xe5 0xa8 0x88 0xb4 0x15 | ||
| 65 | + 0x600cd8 <context+56>: 0xf8 0xc1 0xd9 0x2f 0xd7 0x77 0x4b 0xea | ||
| 61 | (gdb) p /x $sp | 66 | (gdb) p /x $sp |
| 62 | $4 = 0x7fffffffe380 | 67 | $4 = 0x7fffffffe380 |
| 63 | we cannot finger the sp out. | 68 | we cannot finger the sp out. |
| @@ -65,12 +70,12 @@ void func0() | @@ -65,12 +70,12 @@ void func0() | ||
| 65 | */ | 70 | */ |
| 66 | register long int rsp0 asm("rsp"); | 71 | register long int rsp0 asm("rsp"); |
| 67 | 72 | ||
| 68 | - int ret = setjmp(env_func1); | 73 | + int ret = setjmp(context); |
| 69 | printf("setjmp func0 ret=%d, rsp=%#lx\n", ret, rsp0); | 74 | printf("setjmp func0 ret=%d, rsp=%#lx\n", ret, rsp0); |
| 70 | 75 | ||
| 71 | printf("after setjmp: "); | 76 | printf("after setjmp: "); |
| 72 | for (int i = 0; i < 8; i++) { | 77 | for (int i = 0; i < 8; i++) { |
| 73 | - printf("env[%d]=%#x, ", i, (int)env_func1[0].__jmpbuf[i]); | 78 | + printf("env[%d]=%#x, ", i, (int)context[0].__jmpbuf[i]); |
| 74 | } | 79 | } |
| 75 | printf("\n"); | 80 | printf("\n"); |
| 76 | 81 | ||
| @@ -100,7 +105,7 @@ void func0() | @@ -100,7 +105,7 @@ void func0() | ||
| 100 | */ | 105 | */ |
| 101 | /** | 106 | /** |
| 102 | For example, on raspberry-pi, armv6 cpu: | 107 | For example, on raspberry-pi, armv6 cpu: |
| 103 | - (gdb) x /64 env_func1[0].__jmpbuf | 108 | + (gdb) x /64 context[0].__jmpbuf |
| 104 | v1, 0: 0x00 0x00 0x00 0x00 | 109 | v1, 0: 0x00 0x00 0x00 0x00 |
| 105 | v2, 1: 0x00 0x00 0x00 0x00 | 110 | v2, 1: 0x00 0x00 0x00 0x00 |
| 106 | v3, 2: 0x2c 0x84 0x00 0x00 | 111 | v3, 2: 0x2c 0x84 0x00 0x00 |
| @@ -116,19 +121,18 @@ void func0() | @@ -116,19 +121,18 @@ void func0() | ||
| 116 | (gdb) p /x $pc | 121 | (gdb) p /x $pc |
| 117 | $4 = 0x850c | 122 | $4 = 0x850c |
| 118 | */ | 123 | */ |
| 119 | - int ret = setjmp(env_func1); | 124 | + int ret = setjmp(context); |
| 120 | printf("setjmp func1 ret=%d\n", ret); | 125 | printf("setjmp func1 ret=%d\n", ret); |
| 121 | 126 | ||
| 122 | printf("after setjmp: "); | 127 | printf("after setjmp: "); |
| 123 | for (int i = 0; i < 64; i++) { | 128 | for (int i = 0; i < 64; i++) { |
| 124 | - printf("env[%d]=%#x, ", i, (int)env_func1[0].__jmpbuf[i]); | 129 | + printf("env[%d]=%#x, ", i, (int)context[0].__jmpbuf[i]); |
| 125 | } | 130 | } |
| 126 | 131 | ||
| 127 | printf("func0 terminated\n"); | 132 | printf("func0 terminated\n"); |
| 128 | #endif | 133 | #endif |
| 129 | } | 134 | } |
| 130 | 135 | ||
| 131 | -extern uintptr_t _jmpbuf_sp (__jmp_buf regs); | ||
| 132 | int main(int argc, char** argv) { | 136 | int main(int argc, char** argv) { |
| 133 | #if defined(__amd64__) || defined(__x86_64__) | 137 | #if defined(__amd64__) || defined(__x86_64__) |
| 134 | printf("x86_64 sizeof(long int)=%d, sizeof(long)=%d, " | 138 | printf("x86_64 sizeof(long int)=%d, sizeof(long)=%d, " |
| @@ -143,6 +147,7 @@ int main(int argc, char** argv) { | @@ -143,6 +147,7 @@ int main(int argc, char** argv) { | ||
| 143 | #endif | 147 | #endif |
| 144 | 148 | ||
| 145 | func0(); | 149 | func0(); |
| 150 | + longjmp(context, 1); | ||
| 146 | 151 | ||
| 147 | printf("terminated\n"); | 152 | printf("terminated\n"); |
| 148 | 153 |
| @@ -411,15 +411,6 @@ extern _st_eventsys_t *_st_eventsys; | @@ -411,15 +411,6 @@ extern _st_eventsys_t *_st_eventsys; | ||
| 411 | ST_END_MACRO | 411 | ST_END_MACRO |
| 412 | 412 | ||
| 413 | /* | 413 | /* |
| 414 | - * Initialize the thread context preparing it to execute _main | ||
| 415 | - */ | ||
| 416 | -#ifdef MD_INIT_CONTEXT | ||
| 417 | - #define _ST_INIT_CONTEXT MD_INIT_CONTEXT | ||
| 418 | -#else | ||
| 419 | - #error Unknown OS | ||
| 420 | -#endif | ||
| 421 | - | ||
| 422 | -/* | ||
| 423 | * Number of bytes reserved under the stack "bottom" | 414 | * Number of bytes reserved under the stack "bottom" |
| 424 | */ | 415 | */ |
| 425 | #define _ST_STACK_PAD_SIZE MD_STACK_PAD_SIZE | 416 | #define _ST_STACK_PAD_SIZE MD_STACK_PAD_SIZE |
| @@ -107,13 +107,6 @@ | @@ -107,13 +107,6 @@ | ||
| 107 | 107 | ||
| 108 | #if defined(__mips__) | 108 | #if defined(__mips__) |
| 109 | #define MD_STACK_GROWS_DOWN | 109 | #define MD_STACK_GROWS_DOWN |
| 110 | - | ||
| 111 | - #define MD_INIT_CONTEXT(_thread, _sp, _main) \ | ||
| 112 | - ST_BEGIN_MACRO \ | ||
| 113 | - MD_SETJMP((_thread)->context); \ | ||
| 114 | - _thread->context[0].__jmpbuf[0].__pc = (__ptr_t) _main; \ | ||
| 115 | - _thread->context[0].__jmpbuf[0].__sp = _sp; \ | ||
| 116 | - ST_END_MACRO | ||
| 117 | #else /* Not or mips */ | 110 | #else /* Not or mips */ |
| 118 | /* | 111 | /* |
| 119 | * On linux, there are a few styles of jmpbuf format. These vary based | 112 | * On linux, there are a few styles of jmpbuf format. These vary based |
| @@ -166,13 +159,6 @@ | @@ -166,13 +159,6 @@ | ||
| 166 | #else | 159 | #else |
| 167 | #error "Unknown CPU architecture" | 160 | #error "Unknown CPU architecture" |
| 168 | #endif /* Cases with common MD_INIT_CONTEXT and different SP locations */ | 161 | #endif /* Cases with common MD_INIT_CONTEXT and different SP locations */ |
| 169 | - | ||
| 170 | - #define MD_INIT_CONTEXT(_thread, _sp, _main) \ | ||
| 171 | - ST_BEGIN_MACRO \ | ||
| 172 | - if (MD_SETJMP((_thread)->context)) \ | ||
| 173 | - _main(); \ | ||
| 174 | - MD_GET_SP(_thread) = (long) (_sp); \ | ||
| 175 | - ST_END_MACRO | ||
| 176 | #endif /* Cases with different MD_INIT_CONTEXT */ | 162 | #endif /* Cases with different MD_INIT_CONTEXT */ |
| 177 | 163 | ||
| 178 | #if defined(MD_USE_BUILTIN_SETJMP) && !defined(USE_LIBC_SETJMP) | 164 | #if defined(MD_USE_BUILTIN_SETJMP) && !defined(USE_LIBC_SETJMP) |
| @@ -553,6 +553,20 @@ _st_thread_t *st_thread_create(void *(*start)(void *arg), void *arg, int joinabl | @@ -553,6 +553,20 @@ _st_thread_t *st_thread_create(void *(*start)(void *arg), void *arg, int joinabl | ||
| 553 | * grows downward. Both stacks start in the middle and grow outward | 553 | * grows downward. Both stacks start in the middle and grow outward |
| 554 | * from each other. | 554 | * from each other. |
| 555 | */ | 555 | */ |
| 556 | + /** | ||
| 557 | + The below comments is by winlin: | ||
| 558 | + The Stack public structure: | ||
| 559 | + +--------------------------------------------------------------+ | ||
| 560 | + | stack | | ||
| 561 | + +--------------------------------------------------------------+ | ||
| 562 | + bottom top | ||
| 563 | + The code bellow use the stack as: | ||
| 564 | + +-----------------+-----------------+-------------+------------+ | ||
| 565 | + | stack of thread |pad+align(128B+) |thread(336B) | keys(128B) | | ||
| 566 | + +-----------------+-----------------+-------------+------------+ | ||
| 567 | + bottom sp trd ptds top | ||
| 568 | + (context[0].__jmpbuf.sp) (private_data) | ||
| 569 | + */ | ||
| 556 | sp = sp - (ST_KEYS_MAX * sizeof(void *)); | 570 | sp = sp - (ST_KEYS_MAX * sizeof(void *)); |
| 557 | ptds = (void **) sp; | 571 | ptds = (void **) sp; |
| 558 | sp = sp - sizeof(_st_thread_t); | 572 | sp = sp - sizeof(_st_thread_t); |
| @@ -575,8 +589,19 @@ _st_thread_t *st_thread_create(void *(*start)(void *arg), void *arg, int joinabl | @@ -575,8 +589,19 @@ _st_thread_t *st_thread_create(void *(*start)(void *arg), void *arg, int joinabl | ||
| 575 | trd->stack = stack; | 589 | trd->stack = stack; |
| 576 | trd->start = start; | 590 | trd->start = start; |
| 577 | trd->arg = arg; | 591 | trd->arg = arg; |
| 578 | - | ||
| 579 | - _ST_INIT_CONTEXT(trd, stack->sp, _st_thread_main); | 592 | + |
| 593 | +// by winlin, expand macro MD_INIT_CONTEXT | ||
| 594 | +#if defined(__mips__) | ||
| 595 | + MD_SETJMP((trd)->context); | ||
| 596 | + trd->context[0].__jmpbuf[0].__pc = (__ptr_t) _st_thread_main; | ||
| 597 | + trd->context[0].__jmpbuf[0].__sp = stack->sp; | ||
| 598 | +#else | ||
| 599 | + int ret_setjmp = 0; | ||
| 600 | + if ((ret_setjmp = MD_SETJMP((trd)->context)) != 0) { | ||
| 601 | + _st_thread_main(); | ||
| 602 | + } | ||
| 603 | + MD_GET_SP(trd) = (long) (stack->sp); | ||
| 604 | +#endif | ||
| 580 | 605 | ||
| 581 | /* If thread is joinable, allocate a termination condition variable */ | 606 | /* If thread is joinable, allocate a termination condition variable */ |
| 582 | if (joinable) { | 607 | if (joinable) { |
| @@ -46,6 +46,21 @@ int huge_stack_test() | @@ -46,6 +46,21 @@ int huge_stack_test() | ||
| 46 | return 0; | 46 | return 0; |
| 47 | } | 47 | } |
| 48 | 48 | ||
| 49 | +int sleep_test() | ||
| 50 | +{ | ||
| 51 | + srs_trace("==================================================="); | ||
| 52 | + srs_trace("sleep test: start"); | ||
| 53 | + | ||
| 54 | + srs_trace("1. sleep..."); | ||
| 55 | + | ||
| 56 | + st_usleep(sleep_ms * 1000); | ||
| 57 | + srs_trace("2. sleep ok"); | ||
| 58 | + | ||
| 59 | + srs_trace("sleep test: end"); | ||
| 60 | + | ||
| 61 | + return 0; | ||
| 62 | +} | ||
| 63 | + | ||
| 49 | void* thread_func(void* arg) | 64 | void* thread_func(void* arg) |
| 50 | { | 65 | { |
| 51 | srs_trace("1. thread run"); | 66 | srs_trace("1. thread run"); |
| @@ -68,8 +83,10 @@ int thread_test() | @@ -68,8 +83,10 @@ int thread_test() | ||
| 68 | st_thread_join(trd, NULL); | 83 | st_thread_join(trd, NULL); |
| 69 | srs_trace("3. thread joined"); | 84 | srs_trace("3. thread joined"); |
| 70 | 85 | ||
| 86 | + st_thread_exit(NULL); | ||
| 87 | + srs_trace("4. all thread completed"); | ||
| 88 | + | ||
| 71 | srs_trace("thread test: end"); | 89 | srs_trace("thread test: end"); |
| 72 | - exit(0); | ||
| 73 | 90 | ||
| 74 | return 0; | 91 | return 0; |
| 75 | } | 92 | } |
| @@ -342,6 +359,11 @@ int main(int argc, char** argv) | @@ -342,6 +359,11 @@ int main(int argc, char** argv) | ||
| 342 | return -1; | 359 | return -1; |
| 343 | } | 360 | } |
| 344 | 361 | ||
| 362 | + if (sleep_test() < 0) { | ||
| 363 | + srs_trace("sleep_test failed"); | ||
| 364 | + return -1; | ||
| 365 | + } | ||
| 366 | + | ||
| 345 | if (thread_test() < 0) { | 367 | if (thread_test() < 0) { |
| 346 | srs_trace("thread_test failed"); | 368 | srs_trace("thread_test failed"); |
| 347 | return -1; | 369 | return -1; |
-
请 注册 或 登录 后发表评论