mirror of
https://github.com/ossrs/srs.git
synced 2025-02-13 03:41:55 +00:00
ST: Replace macros with explicit code for better understanding. v7.0.7 (#4149)
Improvements for ST(State Threads): 1. ST: Use g++ for CXX compiler. 2. ST: Remove macros for clist. 3. ST: Remove macros for global thread and vp. 4. ST: Remove macros for vp queue operations. 5. ST: Remove macros for context switch. 6. ST: Remove macros for setjmp/longjmp. 7. ST: Remove macro for stack pad. 8. ST: Refine macro for valgrind. --------- Co-authored-by: Jacob Su <suzp1984@gmail.com>
This commit is contained in:
parent
0d76081430
commit
ff6a608099
15 changed files with 228 additions and 285 deletions
19
trunk/3rdparty/st-srs/Makefile
vendored
19
trunk/3rdparty/st-srs/Makefile
vendored
|
@ -46,6 +46,7 @@ VERSION = 1.9
|
||||||
##########################
|
##########################
|
||||||
|
|
||||||
CC = cc
|
CC = cc
|
||||||
|
CXX = g++
|
||||||
AR = ar
|
AR = ar
|
||||||
LD = ld
|
LD = ld
|
||||||
RANLIB = ranlib
|
RANLIB = ranlib
|
||||||
|
@ -207,7 +208,8 @@ OBJS = $(TARGETDIR)/sched.o \
|
||||||
$(TARGETDIR)/sync.o \
|
$(TARGETDIR)/sync.o \
|
||||||
$(TARGETDIR)/key.o \
|
$(TARGETDIR)/key.o \
|
||||||
$(TARGETDIR)/io.o \
|
$(TARGETDIR)/io.o \
|
||||||
$(TARGETDIR)/event.o
|
$(TARGETDIR)/event.o \
|
||||||
|
$(TARGETDIR)/common.o
|
||||||
OBJS += $(EXTRA_OBJS)
|
OBJS += $(EXTRA_OBJS)
|
||||||
HEADER = $(TARGETDIR)/st.h
|
HEADER = $(TARGETDIR)/st.h
|
||||||
SLIBRARY = $(TARGETDIR)/libst.a
|
SLIBRARY = $(TARGETDIR)/libst.a
|
||||||
|
@ -270,21 +272,16 @@ $(HEADER): public.h
|
||||||
rm -f $@
|
rm -f $@
|
||||||
cp public.h $@
|
cp public.h $@
|
||||||
|
|
||||||
$(TARGETDIR)/md_linux.o: md_linux.S
|
$(TARGETDIR)/%.o: %.S
|
||||||
$(CC) $(CFLAGS) -c $< -o $@
|
|
||||||
|
|
||||||
$(TARGETDIR)/md_linux2.o: md_linux2.S
|
|
||||||
$(CC) $(CFLAGS) -c $< -o $@
|
|
||||||
|
|
||||||
$(TARGETDIR)/md_darwin.o: md_darwin.S
|
|
||||||
$(CC) $(CFLAGS) -c $< -o $@
|
|
||||||
|
|
||||||
$(TARGETDIR)/md_cygwin64.o: md_cygwin64.S
|
|
||||||
$(CC) $(CFLAGS) -c $< -o $@
|
$(CC) $(CFLAGS) -c $< -o $@
|
||||||
|
|
||||||
$(TARGETDIR)/%.o: %.c common.h md.h
|
$(TARGETDIR)/%.o: %.c common.h md.h
|
||||||
$(CC) $(CFLAGS) -c $< -o $@
|
$(CC) $(CFLAGS) -c $< -o $@
|
||||||
|
|
||||||
|
# Note that we use C++98 standard for the C++ files.
|
||||||
|
$(TARGETDIR)/%.o: %.cc common.h md.h
|
||||||
|
$(CXX) $(CFLAGS) -c $< -o $@ -std=c++98
|
||||||
|
|
||||||
clean:
|
clean:
|
||||||
rm -rf *_OPT *_DBG obj st.pc
|
rm -rf *_OPT *_DBG obj st.pc
|
||||||
|
|
||||||
|
|
23
trunk/3rdparty/st-srs/common.c
vendored
Normal file
23
trunk/3rdparty/st-srs/common.c
vendored
Normal file
|
@ -0,0 +1,23 @@
|
||||||
|
/* SPDX-License-Identifier: MIT */
|
||||||
|
/* Copyright (c) 2021-2022 The SRS Authors */
|
||||||
|
|
||||||
|
#include "common.h"
|
||||||
|
|
||||||
|
void _st_switch_context(_st_thread_t *thread)
|
||||||
|
{
|
||||||
|
ST_SWITCH_OUT_CB(thread);
|
||||||
|
|
||||||
|
if (!_st_md_cxt_save(thread->context)) {
|
||||||
|
_st_vp_schedule();
|
||||||
|
}
|
||||||
|
|
||||||
|
ST_DEBUG_ITERATE_THREADS();
|
||||||
|
ST_SWITCH_IN_CB(thread);
|
||||||
|
}
|
||||||
|
|
||||||
|
void _st_restore_context(_st_thread_t *thread)
|
||||||
|
{
|
||||||
|
_st_this_thread = thread;
|
||||||
|
_st_md_cxt_restore(thread->context, 1);
|
||||||
|
}
|
||||||
|
|
161
trunk/3rdparty/st-srs/common.h
vendored
161
trunk/3rdparty/st-srs/common.h
vendored
|
@ -69,13 +69,8 @@
|
||||||
#include "public.h"
|
#include "public.h"
|
||||||
#include "md.h"
|
#include "md.h"
|
||||||
|
|
||||||
/* merge from https://github.com/toffaletti/state-threads/commit/7f57fc9acc05e657bca1223f1e5b9b1a45ed929b */
|
#ifdef __cplusplus
|
||||||
#ifndef MD_VALGRIND
|
extern "C" {
|
||||||
#ifndef NVALGRIND
|
|
||||||
#define NVALGRIND
|
|
||||||
#endif
|
|
||||||
#else
|
|
||||||
#undef NVALGRIND
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
||||||
|
@ -88,58 +83,37 @@ typedef struct _st_clist {
|
||||||
struct _st_clist *prev;
|
struct _st_clist *prev;
|
||||||
} _st_clist_t;
|
} _st_clist_t;
|
||||||
|
|
||||||
/* Insert element "_e" into the list, before "_l" */
|
/* Initialize a circular list */
|
||||||
#define ST_INSERT_BEFORE(_e,_l) \
|
static inline void st_clist_init(_st_clist_t *l)
|
||||||
ST_BEGIN_MACRO \
|
{
|
||||||
(_e)->next = (_l); \
|
l->next = l;
|
||||||
(_e)->prev = (_l)->prev; \
|
l->prev = l;
|
||||||
(_l)->prev->next = (_e); \
|
}
|
||||||
(_l)->prev = (_e); \
|
|
||||||
ST_END_MACRO
|
|
||||||
|
|
||||||
/* Insert element "_e" into the list, after "_l" */
|
|
||||||
#define ST_INSERT_AFTER(_e,_l) \
|
|
||||||
ST_BEGIN_MACRO \
|
|
||||||
(_e)->next = (_l)->next; \
|
|
||||||
(_e)->prev = (_l); \
|
|
||||||
(_l)->next->prev = (_e); \
|
|
||||||
(_l)->next = (_e); \
|
|
||||||
ST_END_MACRO
|
|
||||||
|
|
||||||
/* Return the element following element "_e" */
|
|
||||||
#define ST_NEXT_LINK(_e) ((_e)->next)
|
|
||||||
|
|
||||||
/* Append an element "_e" to the end of the list "_l" */
|
|
||||||
#define ST_APPEND_LINK(_e,_l) ST_INSERT_BEFORE(_e,_l)
|
|
||||||
|
|
||||||
/* Insert an element "_e" at the head of the list "_l" */
|
|
||||||
#define ST_INSERT_LINK(_e,_l) ST_INSERT_AFTER(_e,_l)
|
|
||||||
|
|
||||||
/* Return the head/tail of the list */
|
|
||||||
#define ST_LIST_HEAD(_l) (_l)->next
|
|
||||||
#define ST_LIST_TAIL(_l) (_l)->prev
|
|
||||||
|
|
||||||
/* Remove the element "_e" from it's circular list */
|
/* Remove the element "_e" from it's circular list */
|
||||||
#define ST_REMOVE_LINK(_e) \
|
static inline void st_clist_remove(_st_clist_t *e)
|
||||||
ST_BEGIN_MACRO \
|
{
|
||||||
(_e)->prev->next = (_e)->next; \
|
e->prev->next = e->next;
|
||||||
(_e)->next->prev = (_e)->prev; \
|
e->next->prev = e->prev;
|
||||||
ST_END_MACRO
|
}
|
||||||
|
|
||||||
/* Return non-zero if the given circular list "_l" is empty, */
|
/* Insert element "_e" into the list, before "_l" */
|
||||||
/* zero if the circular list is not empty */
|
static inline void st_clist_insert_before(_st_clist_t *e, _st_clist_t *l)
|
||||||
#define ST_CLIST_IS_EMPTY(_l) \
|
{
|
||||||
((_l)->next == (_l))
|
e->next = l;
|
||||||
|
e->prev = l->prev;
|
||||||
|
l->prev->next = e;
|
||||||
|
l->prev = e;
|
||||||
|
}
|
||||||
|
|
||||||
/* Initialize a circular list */
|
/* Insert element "_e" into the list, after "_l" */
|
||||||
#define ST_INIT_CLIST(_l) \
|
static inline void st_clist_insert_after(_st_clist_t *e, _st_clist_t *l)
|
||||||
ST_BEGIN_MACRO \
|
{
|
||||||
(_l)->next = (_l); \
|
e->next = l->next;
|
||||||
(_l)->prev = (_l); \
|
e->prev = l;
|
||||||
ST_END_MACRO
|
l->next->prev = e;
|
||||||
|
l->next = e;
|
||||||
#define ST_INIT_STATIC_CLIST(_l) \
|
}
|
||||||
{(_l), (_l)}
|
|
||||||
|
|
||||||
|
|
||||||
/*****************************************
|
/*****************************************
|
||||||
|
@ -158,7 +132,7 @@ typedef struct _st_stack {
|
||||||
char *stk_top; /* Highest address of stack's usable portion */
|
char *stk_top; /* Highest address of stack's usable portion */
|
||||||
void *sp; /* Stack pointer from C's point of view */
|
void *sp; /* Stack pointer from C's point of view */
|
||||||
/* merge from https://github.com/toffaletti/state-threads/commit/7f57fc9acc05e657bca1223f1e5b9b1a45ed929b */
|
/* merge from https://github.com/toffaletti/state-threads/commit/7f57fc9acc05e657bca1223f1e5b9b1a45ed929b */
|
||||||
#ifndef NVALGRIND
|
#ifdef MD_VALGRIND
|
||||||
/* id returned by VALGRIND_STACK_REGISTER */
|
/* id returned by VALGRIND_STACK_REGISTER */
|
||||||
/* http://valgrind.org/docs/manual/manual-core-adv.html */
|
/* http://valgrind.org/docs/manual/manual-core-adv.html */
|
||||||
unsigned long valgrind_stack_id;
|
unsigned long valgrind_stack_id;
|
||||||
|
@ -270,48 +244,6 @@ extern __thread _st_vp_t _st_this_vp;
|
||||||
extern __thread _st_thread_t *_st_this_thread;
|
extern __thread _st_thread_t *_st_this_thread;
|
||||||
extern __thread _st_eventsys_t *_st_eventsys;
|
extern __thread _st_eventsys_t *_st_eventsys;
|
||||||
|
|
||||||
#define _ST_CURRENT_THREAD() (_st_this_thread)
|
|
||||||
#define _ST_SET_CURRENT_THREAD(_thread) (_st_this_thread = (_thread))
|
|
||||||
|
|
||||||
#define _ST_LAST_CLOCK (_st_this_vp.last_clock)
|
|
||||||
|
|
||||||
#define _ST_RUNQ (_st_this_vp.run_q)
|
|
||||||
#define _ST_IOQ (_st_this_vp.io_q)
|
|
||||||
#define _ST_ZOMBIEQ (_st_this_vp.zombie_q)
|
|
||||||
#ifdef DEBUG
|
|
||||||
#define _ST_THREADQ (_st_this_vp.thread_q)
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#define _ST_PAGE_SIZE (_st_this_vp.pagesize)
|
|
||||||
|
|
||||||
#define _ST_SLEEPQ (_st_this_vp.sleep_q)
|
|
||||||
#define _ST_SLEEPQ_SIZE (_st_this_vp.sleepq_size)
|
|
||||||
|
|
||||||
#define _ST_VP_IDLE() (*_st_eventsys->dispatch)()
|
|
||||||
|
|
||||||
|
|
||||||
/*****************************************
|
|
||||||
* vp queues operations
|
|
||||||
*/
|
|
||||||
|
|
||||||
#define _ST_ADD_IOQ(_pq) ST_APPEND_LINK(&_pq.links, &_ST_IOQ)
|
|
||||||
#define _ST_DEL_IOQ(_pq) ST_REMOVE_LINK(&_pq.links)
|
|
||||||
|
|
||||||
#define _ST_ADD_RUNQ(_thr) ST_APPEND_LINK(&(_thr)->links, &_ST_RUNQ)
|
|
||||||
#define _ST_INSERT_RUNQ(_thr) ST_INSERT_LINK(&(_thr)->links, &_ST_RUNQ)
|
|
||||||
#define _ST_DEL_RUNQ(_thr) ST_REMOVE_LINK(&(_thr)->links)
|
|
||||||
|
|
||||||
#define _ST_ADD_SLEEPQ(_thr, _timeout) _st_add_sleep_q(_thr, _timeout)
|
|
||||||
#define _ST_DEL_SLEEPQ(_thr) _st_del_sleep_q(_thr)
|
|
||||||
|
|
||||||
#define _ST_ADD_ZOMBIEQ(_thr) ST_APPEND_LINK(&(_thr)->links, &_ST_ZOMBIEQ)
|
|
||||||
#define _ST_DEL_ZOMBIEQ(_thr) ST_REMOVE_LINK(&(_thr)->links)
|
|
||||||
|
|
||||||
#ifdef DEBUG
|
|
||||||
#define _ST_ADD_THREADQ(_thr) ST_APPEND_LINK(&(_thr)->tlink, &_ST_THREADQ)
|
|
||||||
#define _ST_DEL_THREADQ(_thr) ST_REMOVE_LINK(&(_thr)->tlink)
|
|
||||||
#endif
|
|
||||||
|
|
||||||
|
|
||||||
/*****************************************
|
/*****************************************
|
||||||
* Thread states and flags
|
* Thread states and flags
|
||||||
|
@ -411,39 +343,18 @@ extern __thread _st_eventsys_t *_st_eventsys;
|
||||||
* Switch away from the current thread context by saving its state and
|
* Switch away from the current thread context by saving its state and
|
||||||
* calling the thread scheduler
|
* calling the thread scheduler
|
||||||
*/
|
*/
|
||||||
#define _ST_SWITCH_CONTEXT(_thread) \
|
void _st_switch_context(_st_thread_t *thread);
|
||||||
ST_BEGIN_MACRO \
|
|
||||||
ST_SWITCH_OUT_CB(_thread); \
|
|
||||||
if (!MD_SETJMP((_thread)->context)) { \
|
|
||||||
_st_vp_schedule(); \
|
|
||||||
} \
|
|
||||||
ST_DEBUG_ITERATE_THREADS(); \
|
|
||||||
ST_SWITCH_IN_CB(_thread); \
|
|
||||||
ST_END_MACRO
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Restore a thread context that was saved by _ST_SWITCH_CONTEXT or
|
* Restore a thread context that was saved by _st_switch_context or
|
||||||
* initialized by _ST_INIT_CONTEXT
|
* initialized by _ST_INIT_CONTEXT
|
||||||
*/
|
*/
|
||||||
#define _ST_RESTORE_CONTEXT(_thread) \
|
void _st_restore_context(_st_thread_t *thread);
|
||||||
ST_BEGIN_MACRO \
|
|
||||||
_ST_SET_CURRENT_THREAD(_thread); \
|
|
||||||
MD_LONGJMP((_thread)->context, 1); \
|
|
||||||
ST_END_MACRO
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Initialize the thread context preparing it to execute _main
|
|
||||||
*/
|
|
||||||
#ifdef MD_INIT_CONTEXT
|
|
||||||
#define _ST_INIT_CONTEXT MD_INIT_CONTEXT
|
|
||||||
#else
|
|
||||||
#error Unknown OS
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Number of bytes reserved under the stack "bottom"
|
* Number of bytes reserved under the stack "bottom"
|
||||||
*/
|
*/
|
||||||
#define _ST_STACK_PAD_SIZE MD_STACK_PAD_SIZE
|
#define _ST_STACK_PAD_SIZE 128
|
||||||
|
|
||||||
|
|
||||||
/*****************************************
|
/*****************************************
|
||||||
|
@ -471,5 +382,9 @@ ssize_t st_write(_st_netfd_t *fd, const void *buf, size_t nbyte, st_utime_t time
|
||||||
int st_poll(struct pollfd *pds, int npds, st_utime_t timeout);
|
int st_poll(struct pollfd *pds, int npds, st_utime_t timeout);
|
||||||
_st_thread_t *st_thread_create(void *(*start)(void *arg), void *arg, int joinable, int stk_size);
|
_st_thread_t *st_thread_create(void *(*start)(void *arg), void *arg, int joinable, int stk_size);
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
} /* extern "C" */
|
||||||
|
#endif
|
||||||
|
|
||||||
#endif /* !__ST_COMMON_H__ */
|
#endif /* !__ST_COMMON_H__ */
|
||||||
|
|
||||||
|
|
2
trunk/3rdparty/st-srs/docs/timeout_heap.txt
vendored
2
trunk/3rdparty/st-srs/docs/timeout_heap.txt
vendored
|
@ -22,7 +22,7 @@ appropriate for ST than introducing a separate array.
|
||||||
Thus, the new ST timeout heap works by organizing the existing
|
Thus, the new ST timeout heap works by organizing the existing
|
||||||
_st_thread_t objects in a balanced binary tree, just as they were
|
_st_thread_t objects in a balanced binary tree, just as they were
|
||||||
previously organized into a doubly-linked, sorted list. The global
|
previously organized into a doubly-linked, sorted list. The global
|
||||||
_ST_SLEEPQ variable, formerly a linked list head, is now simply a
|
_st_this_vp.sleep_q variable, formerly a linked list head, is now simply a
|
||||||
pointer to the root of this tree, and the root node of the tree is the
|
pointer to the root of this tree, and the root node of the tree is the
|
||||||
thread with the earliest timeout. Each thread object has two child
|
thread with the earliest timeout. Each thread object has two child
|
||||||
pointers, "left" and "right", pointing to threads with later timeouts.
|
pointers, "left" and "right", pointing to threads with later timeouts.
|
||||||
|
|
48
trunk/3rdparty/st-srs/event.c
vendored
48
trunk/3rdparty/st-srs/event.c
vendored
|
@ -233,7 +233,7 @@ ST_HIDDEN void _st_select_find_bad_fd(void)
|
||||||
|
|
||||||
_ST_SELECT_MAX_OSFD = -1;
|
_ST_SELECT_MAX_OSFD = -1;
|
||||||
|
|
||||||
for (q = _ST_IOQ.next; q != &_ST_IOQ; q = q->next) {
|
for (q = _st_this_vp.io_q.next; q != &_st_this_vp.io_q; q = q->next) {
|
||||||
pq = _ST_POLLQUEUE_PTR(q);
|
pq = _ST_POLLQUEUE_PTR(q);
|
||||||
notify = 0;
|
notify = 0;
|
||||||
epds = pq->pds + pq->npds;
|
epds = pq->pds + pq->npds;
|
||||||
|
@ -254,7 +254,7 @@ ST_HIDDEN void _st_select_find_bad_fd(void)
|
||||||
}
|
}
|
||||||
|
|
||||||
if (notify) {
|
if (notify) {
|
||||||
ST_REMOVE_LINK(&pq->links);
|
st_clist_remove(&pq->links);
|
||||||
pq->on_ioq = 0;
|
pq->on_ioq = 0;
|
||||||
/*
|
/*
|
||||||
* Decrement the count of descriptors for each descriptor/event
|
* Decrement the count of descriptors for each descriptor/event
|
||||||
|
@ -281,9 +281,9 @@ ST_HIDDEN void _st_select_find_bad_fd(void)
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pq->thread->flags & _ST_FL_ON_SLEEPQ)
|
if (pq->thread->flags & _ST_FL_ON_SLEEPQ)
|
||||||
_ST_DEL_SLEEPQ(pq->thread);
|
_st_del_sleep_q(pq->thread);
|
||||||
pq->thread->state = _ST_ST_RUNNABLE;
|
pq->thread->state = _ST_ST_RUNNABLE;
|
||||||
_ST_ADD_RUNQ(pq->thread);
|
st_clist_insert_before(&pq->thread->links, &_st_this_vp.run_q);
|
||||||
} else {
|
} else {
|
||||||
if (_ST_SELECT_MAX_OSFD < pq_max_osfd)
|
if (_ST_SELECT_MAX_OSFD < pq_max_osfd)
|
||||||
_ST_SELECT_MAX_OSFD = pq_max_osfd;
|
_ST_SELECT_MAX_OSFD = pq_max_osfd;
|
||||||
|
@ -315,11 +315,11 @@ ST_HIDDEN void _st_select_dispatch(void)
|
||||||
wp = &w;
|
wp = &w;
|
||||||
ep = &e;
|
ep = &e;
|
||||||
|
|
||||||
if (_ST_SLEEPQ == NULL) {
|
if (_st_this_vp.sleep_q == NULL) {
|
||||||
tvp = NULL;
|
tvp = NULL;
|
||||||
} else {
|
} else {
|
||||||
min_timeout = (_ST_SLEEPQ->due <= _ST_LAST_CLOCK) ? 0 :
|
min_timeout = (_st_this_vp.sleep_q->due <= _st_this_vp.last_clock) ? 0 :
|
||||||
(_ST_SLEEPQ->due - _ST_LAST_CLOCK);
|
(_st_this_vp.sleep_q->due - _st_this_vp.last_clock);
|
||||||
timeout.tv_sec = (int) (min_timeout / 1000000);
|
timeout.tv_sec = (int) (min_timeout / 1000000);
|
||||||
timeout.tv_usec = (int) (min_timeout % 1000000);
|
timeout.tv_usec = (int) (min_timeout % 1000000);
|
||||||
tvp = &timeout;
|
tvp = &timeout;
|
||||||
|
@ -331,7 +331,7 @@ ST_HIDDEN void _st_select_dispatch(void)
|
||||||
/* Notify threads that are associated with the selected descriptors */
|
/* Notify threads that are associated with the selected descriptors */
|
||||||
if (nfd > 0) {
|
if (nfd > 0) {
|
||||||
_ST_SELECT_MAX_OSFD = -1;
|
_ST_SELECT_MAX_OSFD = -1;
|
||||||
for (q = _ST_IOQ.next; q != &_ST_IOQ; q = q->next) {
|
for (q = _st_this_vp.io_q.next; q != &_st_this_vp.io_q; q = q->next) {
|
||||||
pq = _ST_POLLQUEUE_PTR(q);
|
pq = _ST_POLLQUEUE_PTR(q);
|
||||||
notify = 0;
|
notify = 0;
|
||||||
epds = pq->pds + pq->npds;
|
epds = pq->pds + pq->npds;
|
||||||
|
@ -359,7 +359,7 @@ ST_HIDDEN void _st_select_dispatch(void)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (notify) {
|
if (notify) {
|
||||||
ST_REMOVE_LINK(&pq->links);
|
st_clist_remove(&pq->links);
|
||||||
pq->on_ioq = 0;
|
pq->on_ioq = 0;
|
||||||
/*
|
/*
|
||||||
* Decrement the count of descriptors for each descriptor/event
|
* Decrement the count of descriptors for each descriptor/event
|
||||||
|
@ -386,9 +386,9 @@ ST_HIDDEN void _st_select_dispatch(void)
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pq->thread->flags & _ST_FL_ON_SLEEPQ)
|
if (pq->thread->flags & _ST_FL_ON_SLEEPQ)
|
||||||
_ST_DEL_SLEEPQ(pq->thread);
|
_st_del_sleep_q(pq->thread);
|
||||||
pq->thread->state = _ST_ST_RUNNABLE;
|
pq->thread->state = _ST_ST_RUNNABLE;
|
||||||
_ST_ADD_RUNQ(pq->thread);
|
st_clist_insert_before(&pq->thread->links, &_st_this_vp.run_q);
|
||||||
} else {
|
} else {
|
||||||
if (_ST_SELECT_MAX_OSFD < pq_max_osfd)
|
if (_ST_SELECT_MAX_OSFD < pq_max_osfd)
|
||||||
_ST_SELECT_MAX_OSFD = pq_max_osfd;
|
_ST_SELECT_MAX_OSFD = pq_max_osfd;
|
||||||
|
@ -697,10 +697,10 @@ ST_HIDDEN void _st_kq_dispatch(void)
|
||||||
int nfd, i, osfd, notify, filter;
|
int nfd, i, osfd, notify, filter;
|
||||||
short events, revents;
|
short events, revents;
|
||||||
|
|
||||||
if (_ST_SLEEPQ == NULL) {
|
if (_st_this_vp.sleep_q == NULL) {
|
||||||
tsp = NULL;
|
tsp = NULL;
|
||||||
} else {
|
} else {
|
||||||
min_timeout = (_ST_SLEEPQ->due <= _ST_LAST_CLOCK) ? 0 : (_ST_SLEEPQ->due - _ST_LAST_CLOCK);
|
min_timeout = (_st_this_vp.sleep_q->due <= _st_this_vp.last_clock) ? 0 : (_st_this_vp.sleep_q->due - _st_this_vp.last_clock);
|
||||||
timeout.tv_sec = (time_t) (min_timeout / 1000000);
|
timeout.tv_sec = (time_t) (min_timeout / 1000000);
|
||||||
timeout.tv_nsec = (long) ((min_timeout % 1000000) * 1000);
|
timeout.tv_nsec = (long) ((min_timeout % 1000000) * 1000);
|
||||||
tsp = &timeout;
|
tsp = &timeout;
|
||||||
|
@ -735,7 +735,7 @@ ST_HIDDEN void _st_kq_dispatch(void)
|
||||||
|
|
||||||
_st_kq_data->dellist_cnt = 0;
|
_st_kq_data->dellist_cnt = 0;
|
||||||
|
|
||||||
for (q = _ST_IOQ.next; q != &_ST_IOQ; q = q->next) {
|
for (q = _st_this_vp.io_q.next; q != &_st_this_vp.io_q; q = q->next) {
|
||||||
pq = _ST_POLLQUEUE_PTR(q);
|
pq = _ST_POLLQUEUE_PTR(q);
|
||||||
notify = 0;
|
notify = 0;
|
||||||
epds = pq->pds + pq->npds;
|
epds = pq->pds + pq->npds;
|
||||||
|
@ -756,7 +756,7 @@ ST_HIDDEN void _st_kq_dispatch(void)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (notify) {
|
if (notify) {
|
||||||
ST_REMOVE_LINK(&pq->links);
|
st_clist_remove(&pq->links);
|
||||||
pq->on_ioq = 0;
|
pq->on_ioq = 0;
|
||||||
for (pds = pq->pds; pds < epds; pds++) {
|
for (pds = pq->pds; pds < epds; pds++) {
|
||||||
osfd = pds->fd;
|
osfd = pds->fd;
|
||||||
|
@ -782,9 +782,9 @@ ST_HIDDEN void _st_kq_dispatch(void)
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pq->thread->flags & _ST_FL_ON_SLEEPQ)
|
if (pq->thread->flags & _ST_FL_ON_SLEEPQ)
|
||||||
_ST_DEL_SLEEPQ(pq->thread);
|
_st_del_sleep_q(pq->thread);
|
||||||
pq->thread->state = _ST_ST_RUNNABLE;
|
pq->thread->state = _ST_ST_RUNNABLE;
|
||||||
_ST_ADD_RUNQ(pq->thread);
|
st_clist_insert_before(&pq->thread->links, &_st_this_vp.run_q);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -811,7 +811,7 @@ ST_HIDDEN void _st_kq_dispatch(void)
|
||||||
_st_kq_data->pid = getpid();
|
_st_kq_data->pid = getpid();
|
||||||
/* Re-register all descriptors on ioq with new kqueue */
|
/* Re-register all descriptors on ioq with new kqueue */
|
||||||
memset(_st_kq_data->fd_data, 0, _st_kq_data->fd_data_size * sizeof(_kq_fd_data_t));
|
memset(_st_kq_data->fd_data, 0, _st_kq_data->fd_data_size * sizeof(_kq_fd_data_t));
|
||||||
for (q = _ST_IOQ.next; q != &_ST_IOQ; q = q->next) {
|
for (q = _st_this_vp.io_q.next; q != &_st_this_vp.io_q; q = q->next) {
|
||||||
pq = _ST_POLLQUEUE_PTR(q);
|
pq = _ST_POLLQUEUE_PTR(q);
|
||||||
_st_kq_pollset_add(pq->pds, pq->npds);
|
_st_kq_pollset_add(pq->pds, pq->npds);
|
||||||
}
|
}
|
||||||
|
@ -1064,10 +1064,10 @@ ST_HIDDEN void _st_epoll_dispatch(void)
|
||||||
++_st_stat_epoll;
|
++_st_stat_epoll;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
if (_ST_SLEEPQ == NULL) {
|
if (_st_this_vp.sleep_q == NULL) {
|
||||||
timeout = -1;
|
timeout = -1;
|
||||||
} else {
|
} else {
|
||||||
min_timeout = (_ST_SLEEPQ->due <= _ST_LAST_CLOCK) ? 0 : (_ST_SLEEPQ->due - _ST_LAST_CLOCK);
|
min_timeout = (_st_this_vp.sleep_q->due <= _st_this_vp.last_clock) ? 0 : (_st_this_vp.sleep_q->due - _st_this_vp.last_clock);
|
||||||
timeout = (int) (min_timeout / 1000);
|
timeout = (int) (min_timeout / 1000);
|
||||||
|
|
||||||
// At least wait 1ms when <1ms, to avoid epoll_wait spin loop.
|
// At least wait 1ms when <1ms, to avoid epoll_wait spin loop.
|
||||||
|
@ -1105,7 +1105,7 @@ ST_HIDDEN void _st_epoll_dispatch(void)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
for (q = _ST_IOQ.next; q != &_ST_IOQ; q = q->next) {
|
for (q = _st_this_vp.io_q.next; q != &_st_this_vp.io_q; q = q->next) {
|
||||||
pq = _ST_POLLQUEUE_PTR(q);
|
pq = _ST_POLLQUEUE_PTR(q);
|
||||||
notify = 0;
|
notify = 0;
|
||||||
epds = pq->pds + pq->npds;
|
epds = pq->pds + pq->npds;
|
||||||
|
@ -1135,7 +1135,7 @@ ST_HIDDEN void _st_epoll_dispatch(void)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (notify) {
|
if (notify) {
|
||||||
ST_REMOVE_LINK(&pq->links);
|
st_clist_remove(&pq->links);
|
||||||
pq->on_ioq = 0;
|
pq->on_ioq = 0;
|
||||||
/*
|
/*
|
||||||
* Here we will only delete/modify descriptors that
|
* Here we will only delete/modify descriptors that
|
||||||
|
@ -1144,9 +1144,9 @@ ST_HIDDEN void _st_epoll_dispatch(void)
|
||||||
_st_epoll_pollset_del(pq->pds, pq->npds);
|
_st_epoll_pollset_del(pq->pds, pq->npds);
|
||||||
|
|
||||||
if (pq->thread->flags & _ST_FL_ON_SLEEPQ)
|
if (pq->thread->flags & _ST_FL_ON_SLEEPQ)
|
||||||
_ST_DEL_SLEEPQ(pq->thread);
|
_st_del_sleep_q(pq->thread);
|
||||||
pq->thread->state = _ST_ST_RUNNABLE;
|
pq->thread->state = _ST_ST_RUNNABLE;
|
||||||
_ST_ADD_RUNQ(pq->thread);
|
st_clist_insert_before(&pq->thread->links, &_st_this_vp.run_q);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
4
trunk/3rdparty/st-srs/key.c
vendored
4
trunk/3rdparty/st-srs/key.c
vendored
|
@ -78,7 +78,7 @@ int st_key_getlimit(void)
|
||||||
|
|
||||||
int st_thread_setspecific(int key, void *value)
|
int st_thread_setspecific(int key, void *value)
|
||||||
{
|
{
|
||||||
_st_thread_t *me = _ST_CURRENT_THREAD();
|
_st_thread_t *me = _st_this_thread;
|
||||||
return st_thread_setspecific2(me, key, value);
|
return st_thread_setspecific2(me, key, value);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -107,7 +107,7 @@ void *st_thread_getspecific(int key)
|
||||||
if (key < 0 || key >= key_max)
|
if (key < 0 || key >= key_max)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
return ((_ST_CURRENT_THREAD())->private_data[key]);
|
return _st_this_thread->private_data[key];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
33
trunk/3rdparty/st-srs/md.h
vendored
33
trunk/3rdparty/st-srs/md.h
vendored
|
@ -74,13 +74,11 @@ typedef struct _st_jmp_buf {
|
||||||
long __jmpbuf[22];
|
long __jmpbuf[22];
|
||||||
} _st_jmp_buf_t[1];
|
} _st_jmp_buf_t[1];
|
||||||
|
|
||||||
|
/* Defined in *.S file and implemented by ASM. */
|
||||||
extern int _st_md_cxt_save(_st_jmp_buf_t env);
|
extern int _st_md_cxt_save(_st_jmp_buf_t env);
|
||||||
extern void _st_md_cxt_restore(_st_jmp_buf_t env, int val);
|
extern void _st_md_cxt_restore(_st_jmp_buf_t env, int val);
|
||||||
|
|
||||||
/* Always use builtin setjmp/longjmp, use asm code. */
|
/* Always use builtin setjmp/longjmp, use asm code. */
|
||||||
#define MD_USE_BUILTIN_SETJMP
|
|
||||||
#define MD_SETJMP(env) _st_md_cxt_save(env)
|
|
||||||
#define MD_LONGJMP(env, val) _st_md_cxt_restore(env, val)
|
|
||||||
#if defined(USE_LIBC_SETJMP)
|
#if defined(USE_LIBC_SETJMP)
|
||||||
#error The libc setjmp is not supported now
|
#error The libc setjmp is not supported now
|
||||||
#endif
|
#endif
|
||||||
|
@ -102,13 +100,6 @@ extern void _st_md_cxt_restore(_st_jmp_buf_t env, int val);
|
||||||
#else
|
#else
|
||||||
#error Unknown CPU architecture
|
#error Unknown CPU architecture
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#define MD_INIT_CONTEXT(_thread, _sp, _main) \
|
|
||||||
ST_BEGIN_MACRO \
|
|
||||||
if (MD_SETJMP((_thread)->context)) \
|
|
||||||
_main(); \
|
|
||||||
MD_GET_SP(_thread) = (long) (_sp); \
|
|
||||||
ST_END_MACRO
|
|
||||||
|
|
||||||
#define MD_GET_UTIME() \
|
#define MD_GET_UTIME() \
|
||||||
struct timeval tv; \
|
struct timeval tv; \
|
||||||
|
@ -161,14 +152,7 @@ extern void _st_md_cxt_restore(_st_jmp_buf_t env, int val);
|
||||||
#define MD_GET_SP(_t) *((long *)&((_t)->context[0].__jmpbuf[0]))
|
#define MD_GET_SP(_t) *((long *)&((_t)->context[0].__jmpbuf[0]))
|
||||||
#else
|
#else
|
||||||
#error "Unknown CPU architecture"
|
#error "Unknown CPU architecture"
|
||||||
#endif /* Cases with common MD_INIT_CONTEXT and different SP locations */
|
#endif
|
||||||
|
|
||||||
#define MD_INIT_CONTEXT(_thread, _sp, _main) \
|
|
||||||
ST_BEGIN_MACRO \
|
|
||||||
if (MD_SETJMP((_thread)->context)) \
|
|
||||||
_main(); \
|
|
||||||
MD_GET_SP(_thread) = (long) (_sp); \
|
|
||||||
ST_END_MACRO
|
|
||||||
|
|
||||||
#elif defined (CYGWIN64)
|
#elif defined (CYGWIN64)
|
||||||
|
|
||||||
|
@ -177,21 +161,12 @@ extern void _st_md_cxt_restore(_st_jmp_buf_t env, int val);
|
||||||
#define MD_ACCEPT_NB_INHERITED
|
#define MD_ACCEPT_NB_INHERITED
|
||||||
#define MD_HAVE_SOCKLEN_T
|
#define MD_HAVE_SOCKLEN_T
|
||||||
|
|
||||||
#define MD_USE_BUILTIN_SETJMP
|
|
||||||
|
|
||||||
#if defined(__amd64__) || defined(__x86_64__)
|
#if defined(__amd64__) || defined(__x86_64__)
|
||||||
#define MD_GET_SP(_t) *((long *)&((_t)->context[0].__jmpbuf[6]))
|
#define MD_GET_SP(_t) *((long *)&((_t)->context[0].__jmpbuf[6]))
|
||||||
#else
|
#else
|
||||||
#error Unknown CPU architecture
|
#error Unknown CPU architecture
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#define MD_INIT_CONTEXT(_thread, _sp, _main) \
|
|
||||||
ST_BEGIN_MACRO \
|
|
||||||
if (MD_SETJMP((_thread)->context)) \
|
|
||||||
_main(); \
|
|
||||||
MD_GET_SP(_thread) = (long) (_sp); \
|
|
||||||
ST_END_MACRO
|
|
||||||
|
|
||||||
#define MD_GET_UTIME() \
|
#define MD_GET_UTIME() \
|
||||||
struct timeval tv; \
|
struct timeval tv; \
|
||||||
(void) gettimeofday(&tv, NULL); \
|
(void) gettimeofday(&tv, NULL); \
|
||||||
|
@ -201,10 +176,6 @@ extern void _st_md_cxt_restore(_st_jmp_buf_t env, int val);
|
||||||
#error Unknown OS
|
#error Unknown OS
|
||||||
#endif /* OS */
|
#endif /* OS */
|
||||||
|
|
||||||
#ifndef MD_STACK_PAD_SIZE
|
|
||||||
#define MD_STACK_PAD_SIZE 128
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if !defined(MD_HAVE_SOCKLEN_T) && !defined(socklen_t)
|
#if !defined(MD_HAVE_SOCKLEN_T) && !defined(socklen_t)
|
||||||
#define socklen_t int
|
#define socklen_t int
|
||||||
#endif
|
#endif
|
||||||
|
|
131
trunk/3rdparty/st-srs/sched.c
vendored
131
trunk/3rdparty/st-srs/sched.c
vendored
|
@ -50,7 +50,7 @@
|
||||||
#include "common.h"
|
#include "common.h"
|
||||||
|
|
||||||
/* merge from https://github.com/toffaletti/state-threads/commit/7f57fc9acc05e657bca1223f1e5b9b1a45ed929b */
|
/* merge from https://github.com/toffaletti/state-threads/commit/7f57fc9acc05e657bca1223f1e5b9b1a45ed929b */
|
||||||
#ifndef NVALGRIND
|
#ifdef MD_VALGRIND
|
||||||
#include <valgrind/valgrind.h>
|
#include <valgrind/valgrind.h>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
@ -89,7 +89,7 @@ int st_poll(struct pollfd *pds, int npds, st_utime_t timeout)
|
||||||
struct pollfd *pd;
|
struct pollfd *pd;
|
||||||
struct pollfd *epd = pds + npds;
|
struct pollfd *epd = pds + npds;
|
||||||
_st_pollq_t pq;
|
_st_pollq_t pq;
|
||||||
_st_thread_t *me = _ST_CURRENT_THREAD();
|
_st_thread_t *me = _st_this_thread;
|
||||||
int n;
|
int n;
|
||||||
|
|
||||||
if (me->flags & _ST_FL_INTERRUPT) {
|
if (me->flags & _ST_FL_INTERRUPT) {
|
||||||
|
@ -105,17 +105,17 @@ int st_poll(struct pollfd *pds, int npds, st_utime_t timeout)
|
||||||
pq.npds = npds;
|
pq.npds = npds;
|
||||||
pq.thread = me;
|
pq.thread = me;
|
||||||
pq.on_ioq = 1;
|
pq.on_ioq = 1;
|
||||||
_ST_ADD_IOQ(pq);
|
st_clist_insert_before(&pq.links, &_st_this_vp.io_q);
|
||||||
if (timeout != ST_UTIME_NO_TIMEOUT)
|
if (timeout != ST_UTIME_NO_TIMEOUT)
|
||||||
_ST_ADD_SLEEPQ(me, timeout);
|
_st_add_sleep_q(me, timeout);
|
||||||
me->state = _ST_ST_IO_WAIT;
|
me->state = _ST_ST_IO_WAIT;
|
||||||
|
|
||||||
_ST_SWITCH_CONTEXT(me);
|
_st_switch_context(me);
|
||||||
|
|
||||||
n = 0;
|
n = 0;
|
||||||
if (pq.on_ioq) {
|
if (pq.on_ioq) {
|
||||||
/* If we timed out, the pollq might still be on the ioq. Remove it */
|
/* If we timed out, the pollq might still be on the ioq. Remove it */
|
||||||
_ST_DEL_IOQ(pq);
|
st_clist_remove(&pq.links);
|
||||||
(*_st_eventsys->pollset_del)(pds, npds);
|
(*_st_eventsys->pollset_del)(pds, npds);
|
||||||
} else {
|
} else {
|
||||||
/* Count the number of ready descriptors */
|
/* Count the number of ready descriptors */
|
||||||
|
@ -139,14 +139,14 @@ void _st_vp_schedule(void)
|
||||||
{
|
{
|
||||||
_st_thread_t *thread;
|
_st_thread_t *thread;
|
||||||
|
|
||||||
if (_ST_RUNQ.next != &_ST_RUNQ) {
|
if (_st_this_vp.run_q.next != &_st_this_vp.run_q) {
|
||||||
#if defined(DEBUG) && defined(DEBUG_STATS)
|
#if defined(DEBUG) && defined(DEBUG_STATS)
|
||||||
++_st_stat_thread_run;
|
++_st_stat_thread_run;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* Pull thread off of the run queue */
|
/* Pull thread off of the run queue */
|
||||||
thread = _ST_THREAD_PTR(_ST_RUNQ.next);
|
thread = _ST_THREAD_PTR(_st_this_vp.run_q.next);
|
||||||
_ST_DEL_RUNQ(thread);
|
st_clist_remove(&thread->links);
|
||||||
} else {
|
} else {
|
||||||
#if defined(DEBUG) && defined(DEBUG_STATS)
|
#if defined(DEBUG) && defined(DEBUG_STATS)
|
||||||
++_st_stat_thread_idle;
|
++_st_stat_thread_idle;
|
||||||
|
@ -159,7 +159,7 @@ void _st_vp_schedule(void)
|
||||||
|
|
||||||
/* Resume the thread */
|
/* Resume the thread */
|
||||||
thread->state = _ST_ST_RUNNING;
|
thread->state = _ST_ST_RUNNING;
|
||||||
_ST_RESTORE_CONTEXT(thread);
|
_st_restore_context(thread);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -182,16 +182,16 @@ int st_init(void)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
// Initialize the thread-local variables.
|
// Initialize the thread-local variables.
|
||||||
ST_INIT_CLIST(&_st_free_stacks);
|
st_clist_init(&_st_free_stacks);
|
||||||
|
|
||||||
// Initialize ST.
|
// Initialize ST.
|
||||||
memset(&_st_this_vp, 0, sizeof(_st_vp_t));
|
memset(&_st_this_vp, 0, sizeof(_st_vp_t));
|
||||||
|
|
||||||
ST_INIT_CLIST(&_ST_RUNQ);
|
st_clist_init(&_st_this_vp.run_q);
|
||||||
ST_INIT_CLIST(&_ST_IOQ);
|
st_clist_init(&_st_this_vp.io_q);
|
||||||
ST_INIT_CLIST(&_ST_ZOMBIEQ);
|
st_clist_init(&_st_this_vp.zombie_q);
|
||||||
#ifdef DEBUG
|
#ifdef DEBUG
|
||||||
ST_INIT_CLIST(&_ST_THREADQ);
|
st_clist_init(&_st_this_vp.thread_q);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
if ((*_st_eventsys->init)() < 0)
|
if ((*_st_eventsys->init)() < 0)
|
||||||
|
@ -208,7 +208,7 @@ int st_init(void)
|
||||||
return -1;
|
return -1;
|
||||||
_st_this_vp.idle_thread->flags = _ST_FL_IDLE_THREAD;
|
_st_this_vp.idle_thread->flags = _ST_FL_IDLE_THREAD;
|
||||||
_st_active_count--;
|
_st_active_count--;
|
||||||
_ST_DEL_RUNQ(_st_this_vp.idle_thread);
|
st_clist_remove(&_st_this_vp.idle_thread->links);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Initialize primordial thread
|
* Initialize primordial thread
|
||||||
|
@ -219,10 +219,10 @@ int st_init(void)
|
||||||
thread->private_data = (void **) (thread + 1);
|
thread->private_data = (void **) (thread + 1);
|
||||||
thread->state = _ST_ST_RUNNING;
|
thread->state = _ST_ST_RUNNING;
|
||||||
thread->flags = _ST_FL_PRIMORDIAL;
|
thread->flags = _ST_FL_PRIMORDIAL;
|
||||||
_ST_SET_CURRENT_THREAD(thread);
|
_st_this_thread = thread;
|
||||||
_st_active_count++;
|
_st_active_count++;
|
||||||
#ifdef DEBUG
|
#ifdef DEBUG
|
||||||
_ST_ADD_THREADQ(thread);
|
st_clist_insert_before(&thread->tlink, &_st_this_vp.thread_q);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
@ -261,17 +261,17 @@ st_switch_cb_t st_set_switch_out_cb(st_switch_cb_t cb)
|
||||||
/* ARGSUSED */
|
/* ARGSUSED */
|
||||||
void *_st_idle_thread_start(void *arg)
|
void *_st_idle_thread_start(void *arg)
|
||||||
{
|
{
|
||||||
_st_thread_t *me = _ST_CURRENT_THREAD();
|
_st_thread_t *me = _st_this_thread;
|
||||||
|
|
||||||
while (_st_active_count > 0) {
|
while (_st_active_count > 0) {
|
||||||
/* Idle vp till I/O is ready or the smallest timeout expired */
|
/* Idle vp till I/O is ready or the smallest timeout expired */
|
||||||
_ST_VP_IDLE();
|
(*_st_eventsys->dispatch)();
|
||||||
|
|
||||||
/* Check sleep queue for expired threads */
|
/* Check sleep queue for expired threads */
|
||||||
_st_vp_check_clock();
|
_st_vp_check_clock();
|
||||||
|
|
||||||
me->state = _ST_ST_RUNNABLE;
|
me->state = _ST_ST_RUNNABLE;
|
||||||
_ST_SWITCH_CONTEXT(me);
|
_st_switch_context(me);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* No more threads */
|
/* No more threads */
|
||||||
|
@ -284,7 +284,7 @@ void *_st_idle_thread_start(void *arg)
|
||||||
|
|
||||||
void st_thread_exit(void *retval)
|
void st_thread_exit(void *retval)
|
||||||
{
|
{
|
||||||
_st_thread_t *thread = _ST_CURRENT_THREAD();
|
_st_thread_t *thread = _st_this_thread;
|
||||||
|
|
||||||
thread->retval = retval;
|
thread->retval = retval;
|
||||||
_st_thread_cleanup(thread);
|
_st_thread_cleanup(thread);
|
||||||
|
@ -292,13 +292,13 @@ void st_thread_exit(void *retval)
|
||||||
if (thread->term) {
|
if (thread->term) {
|
||||||
/* Put thread on the zombie queue */
|
/* Put thread on the zombie queue */
|
||||||
thread->state = _ST_ST_ZOMBIE;
|
thread->state = _ST_ST_ZOMBIE;
|
||||||
_ST_ADD_ZOMBIEQ(thread);
|
st_clist_insert_before(&thread->links, &_st_this_vp.zombie_q);
|
||||||
|
|
||||||
/* Notify on our termination condition variable */
|
/* Notify on our termination condition variable */
|
||||||
st_cond_signal(thread->term);
|
st_cond_signal(thread->term);
|
||||||
|
|
||||||
/* Switch context and come back later */
|
/* Switch context and come back later */
|
||||||
_ST_SWITCH_CONTEXT(thread);
|
_st_switch_context(thread);
|
||||||
|
|
||||||
/* Continue the cleanup */
|
/* Continue the cleanup */
|
||||||
st_cond_destroy(thread->term);
|
st_cond_destroy(thread->term);
|
||||||
|
@ -306,11 +306,11 @@ void st_thread_exit(void *retval)
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef DEBUG
|
#ifdef DEBUG
|
||||||
_ST_DEL_THREADQ(thread);
|
st_clist_remove(&thread->tlink);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* merge from https://github.com/toffaletti/state-threads/commit/7f57fc9acc05e657bca1223f1e5b9b1a45ed929b */
|
/* merge from https://github.com/toffaletti/state-threads/commit/7f57fc9acc05e657bca1223f1e5b9b1a45ed929b */
|
||||||
#ifndef NVALGRIND
|
#ifdef MD_VALGRIND
|
||||||
if (!(thread->flags & _ST_FL_PRIMORDIAL)) {
|
if (!(thread->flags & _ST_FL_PRIMORDIAL)) {
|
||||||
VALGRIND_STACK_DEREGISTER(thread->stack->valgrind_stack_id);
|
VALGRIND_STACK_DEREGISTER(thread->stack->valgrind_stack_id);
|
||||||
}
|
}
|
||||||
|
@ -320,7 +320,7 @@ void st_thread_exit(void *retval)
|
||||||
_st_stack_free(thread->stack);
|
_st_stack_free(thread->stack);
|
||||||
|
|
||||||
/* Find another thread to run */
|
/* Find another thread to run */
|
||||||
_ST_SWITCH_CONTEXT(thread);
|
_st_switch_context(thread);
|
||||||
/* Not going to land here */
|
/* Not going to land here */
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -334,7 +334,7 @@ int st_thread_join(_st_thread_t *thread, void **retvalp)
|
||||||
errno = EINVAL;
|
errno = EINVAL;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
if (_ST_CURRENT_THREAD() == thread) {
|
if (_st_this_thread == thread) {
|
||||||
errno = EDEADLK;
|
errno = EDEADLK;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
@ -358,8 +358,8 @@ int st_thread_join(_st_thread_t *thread, void **retvalp)
|
||||||
* When it gets scheduled later, it will do the clean up.
|
* When it gets scheduled later, it will do the clean up.
|
||||||
*/
|
*/
|
||||||
thread->state = _ST_ST_RUNNABLE;
|
thread->state = _ST_ST_RUNNABLE;
|
||||||
_ST_DEL_ZOMBIEQ(thread);
|
st_clist_remove(&thread->links);
|
||||||
_ST_ADD_RUNQ(thread);
|
st_clist_insert_before(&thread->links, &_st_this_vp.run_q);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -367,7 +367,7 @@ int st_thread_join(_st_thread_t *thread, void **retvalp)
|
||||||
|
|
||||||
void _st_thread_main(void)
|
void _st_thread_main(void)
|
||||||
{
|
{
|
||||||
_st_thread_t *thread = _ST_CURRENT_THREAD();
|
_st_thread_t *thread = _st_this_thread;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Cap the stack by zeroing out the saved return address register
|
* Cap the stack by zeroing out the saved return address register
|
||||||
|
@ -392,7 +392,7 @@ void _st_thread_main(void)
|
||||||
static _st_thread_t **heap_insert(_st_thread_t *thread) {
|
static _st_thread_t **heap_insert(_st_thread_t *thread) {
|
||||||
int target = thread->heap_index;
|
int target = thread->heap_index;
|
||||||
int s = target;
|
int s = target;
|
||||||
_st_thread_t **p = &_ST_SLEEPQ;
|
_st_thread_t **p = &_st_this_vp.sleep_q;
|
||||||
int bits = 0;
|
int bits = 0;
|
||||||
int bit;
|
int bit;
|
||||||
int index = 1;
|
int index = 1;
|
||||||
|
@ -434,14 +434,14 @@ static void heap_delete(_st_thread_t *thread) {
|
||||||
int s, bit;
|
int s, bit;
|
||||||
|
|
||||||
/* First find and unlink the last heap element */
|
/* First find and unlink the last heap element */
|
||||||
p = &_ST_SLEEPQ;
|
p = &_st_this_vp.sleep_q;
|
||||||
s = _ST_SLEEPQ_SIZE;
|
s = _st_this_vp.sleepq_size;
|
||||||
while (s) {
|
while (s) {
|
||||||
s >>= 1;
|
s >>= 1;
|
||||||
bits++;
|
bits++;
|
||||||
}
|
}
|
||||||
for (bit = bits - 2; bit >= 0; bit--) {
|
for (bit = bits - 2; bit >= 0; bit--) {
|
||||||
if (_ST_SLEEPQ_SIZE & (1 << bit)) {
|
if (_st_this_vp.sleepq_size & (1 << bit)) {
|
||||||
p = &((*p)->right);
|
p = &((*p)->right);
|
||||||
} else {
|
} else {
|
||||||
p = &((*p)->left);
|
p = &((*p)->left);
|
||||||
|
@ -449,7 +449,7 @@ static void heap_delete(_st_thread_t *thread) {
|
||||||
}
|
}
|
||||||
t = *p;
|
t = *p;
|
||||||
*p = NULL;
|
*p = NULL;
|
||||||
--_ST_SLEEPQ_SIZE;
|
--_st_this_vp.sleepq_size;
|
||||||
if (t != thread) {
|
if (t != thread) {
|
||||||
/*
|
/*
|
||||||
* Insert the unlinked last element in place of the element we are deleting
|
* Insert the unlinked last element in place of the element we are deleting
|
||||||
|
@ -503,9 +503,9 @@ static void heap_delete(_st_thread_t *thread) {
|
||||||
|
|
||||||
void _st_add_sleep_q(_st_thread_t *thread, st_utime_t timeout)
|
void _st_add_sleep_q(_st_thread_t *thread, st_utime_t timeout)
|
||||||
{
|
{
|
||||||
thread->due = _ST_LAST_CLOCK + timeout;
|
thread->due = _st_this_vp.last_clock + timeout;
|
||||||
thread->flags |= _ST_FL_ON_SLEEPQ;
|
thread->flags |= _ST_FL_ON_SLEEPQ;
|
||||||
thread->heap_index = ++_ST_SLEEPQ_SIZE;
|
thread->heap_index = ++_st_this_vp.sleepq_size;
|
||||||
heap_insert(thread);
|
heap_insert(thread);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -527,9 +527,9 @@ void _st_vp_check_clock(void)
|
||||||
|
|
||||||
now = st_utime();
|
now = st_utime();
|
||||||
#if defined(DEBUG) && defined(DEBUG_STATS)
|
#if defined(DEBUG) && defined(DEBUG_STATS)
|
||||||
elapsed = now < _ST_LAST_CLOCK? 0 : now - _ST_LAST_CLOCK; // Might step back.
|
elapsed = now < _st_this_vp.last_clock? 0 : now - _st_this_vp.last_clock; // Might step back.
|
||||||
#endif
|
#endif
|
||||||
_ST_LAST_CLOCK = now;
|
_st_this_vp.last_clock = now;
|
||||||
|
|
||||||
#if defined(DEBUG) && defined(DEBUG_STATS)
|
#if defined(DEBUG) && defined(DEBUG_STATS)
|
||||||
if (elapsed <= 10000) {
|
if (elapsed <= 10000) {
|
||||||
|
@ -558,12 +558,12 @@ void _st_vp_check_clock(void)
|
||||||
_st_last_tset = now;
|
_st_last_tset = now;
|
||||||
}
|
}
|
||||||
|
|
||||||
while (_ST_SLEEPQ != NULL) {
|
while (_st_this_vp.sleep_q != NULL) {
|
||||||
thread = _ST_SLEEPQ;
|
thread = _st_this_vp.sleep_q;
|
||||||
ST_ASSERT(thread->flags & _ST_FL_ON_SLEEPQ);
|
ST_ASSERT(thread->flags & _ST_FL_ON_SLEEPQ);
|
||||||
if (thread->due > now)
|
if (thread->due > now)
|
||||||
break;
|
break;
|
||||||
_ST_DEL_SLEEPQ(thread);
|
_st_del_sleep_q(thread);
|
||||||
|
|
||||||
/* If thread is waiting on condition variable, set the time out flag */
|
/* If thread is waiting on condition variable, set the time out flag */
|
||||||
if (thread->state == _ST_ST_COND_WAIT)
|
if (thread->state == _ST_ST_COND_WAIT)
|
||||||
|
@ -573,14 +573,14 @@ void _st_vp_check_clock(void)
|
||||||
ST_ASSERT(!(thread->flags & _ST_FL_IDLE_THREAD));
|
ST_ASSERT(!(thread->flags & _ST_FL_IDLE_THREAD));
|
||||||
thread->state = _ST_ST_RUNNABLE;
|
thread->state = _ST_ST_RUNNABLE;
|
||||||
// Insert at the head of RunQ, to execute timer first.
|
// Insert at the head of RunQ, to execute timer first.
|
||||||
_ST_INSERT_RUNQ(thread);
|
st_clist_insert_after(&thread->links, &_st_this_vp.run_q);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void st_thread_yield()
|
void st_thread_yield()
|
||||||
{
|
{
|
||||||
_st_thread_t *me = _ST_CURRENT_THREAD();
|
_st_thread_t *me = _st_this_thread;
|
||||||
|
|
||||||
#if defined(DEBUG) && defined(DEBUG_STATS)
|
#if defined(DEBUG) && defined(DEBUG_STATS)
|
||||||
++_st_stat_thread_yield;
|
++_st_stat_thread_yield;
|
||||||
|
@ -590,7 +590,7 @@ void st_thread_yield()
|
||||||
_st_vp_check_clock();
|
_st_vp_check_clock();
|
||||||
|
|
||||||
// If not thread in RunQ to yield to, ignore and continue to run.
|
// If not thread in RunQ to yield to, ignore and continue to run.
|
||||||
if (_ST_RUNQ.next == &_ST_RUNQ) {
|
if (_st_this_vp.run_q.next == &_st_this_vp.run_q) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -600,10 +600,10 @@ void st_thread_yield()
|
||||||
|
|
||||||
// Append thread to the tail of RunQ, we will back after all threads executed.
|
// Append thread to the tail of RunQ, we will back after all threads executed.
|
||||||
me->state = _ST_ST_RUNNABLE;
|
me->state = _ST_ST_RUNNABLE;
|
||||||
_ST_ADD_RUNQ(me);
|
st_clist_insert_before(&me->links, &_st_this_vp.run_q);
|
||||||
|
|
||||||
// Yield to other threads in the RunQ.
|
// Yield to other threads in the RunQ.
|
||||||
_ST_SWITCH_CONTEXT(me);
|
_st_switch_context(me);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -619,11 +619,11 @@ void st_thread_interrupt(_st_thread_t *thread)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if (thread->flags & _ST_FL_ON_SLEEPQ)
|
if (thread->flags & _ST_FL_ON_SLEEPQ)
|
||||||
_ST_DEL_SLEEPQ(thread);
|
_st_del_sleep_q(thread);
|
||||||
|
|
||||||
/* Make thread runnable */
|
/* Make thread runnable */
|
||||||
thread->state = _ST_ST_RUNNABLE;
|
thread->state = _ST_ST_RUNNABLE;
|
||||||
_ST_ADD_RUNQ(thread);
|
st_clist_insert_before(&thread->links, &_st_this_vp.run_q);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -637,7 +637,7 @@ _st_thread_t *st_thread_create(void *(*start)(void *arg), void *arg, int joinabl
|
||||||
/* Adjust stack size */
|
/* Adjust stack size */
|
||||||
if (stk_size == 0)
|
if (stk_size == 0)
|
||||||
stk_size = ST_DEFAULT_STACK_SIZE;
|
stk_size = ST_DEFAULT_STACK_SIZE;
|
||||||
stk_size = ((stk_size + _ST_PAGE_SIZE - 1) / _ST_PAGE_SIZE) * _ST_PAGE_SIZE;
|
stk_size = ((stk_size + _st_this_vp.pagesize - 1) / _st_this_vp.pagesize) * _st_this_vp.pagesize;
|
||||||
stack = _st_stack_new(stk_size);
|
stack = _st_stack_new(stk_size);
|
||||||
if (!stack)
|
if (!stack)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
@ -663,7 +663,10 @@ _st_thread_t *st_thread_create(void *(*start)(void *arg), void *arg, int joinabl
|
||||||
thread->start = start;
|
thread->start = start;
|
||||||
thread->arg = arg;
|
thread->arg = arg;
|
||||||
|
|
||||||
_ST_INIT_CONTEXT(thread, stack->sp, _st_thread_main);
|
/* Note that we must directly call rather than call any functions. */
|
||||||
|
if (_st_md_cxt_save(thread->context))
|
||||||
|
_st_thread_main();
|
||||||
|
MD_GET_SP(thread) = (long)(stack->sp);
|
||||||
|
|
||||||
/* If thread is joinable, allocate a termination condition variable */
|
/* If thread is joinable, allocate a termination condition variable */
|
||||||
if (joinable) {
|
if (joinable) {
|
||||||
|
@ -677,13 +680,13 @@ _st_thread_t *st_thread_create(void *(*start)(void *arg), void *arg, int joinabl
|
||||||
/* Make thread runnable */
|
/* Make thread runnable */
|
||||||
thread->state = _ST_ST_RUNNABLE;
|
thread->state = _ST_ST_RUNNABLE;
|
||||||
_st_active_count++;
|
_st_active_count++;
|
||||||
_ST_ADD_RUNQ(thread);
|
st_clist_insert_before(&thread->links, &_st_this_vp.run_q);
|
||||||
#ifdef DEBUG
|
#ifdef DEBUG
|
||||||
_ST_ADD_THREADQ(thread);
|
st_clist_insert_before(&thread->tlink, &_st_this_vp.thread_q);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* merge from https://github.com/toffaletti/state-threads/commit/7f57fc9acc05e657bca1223f1e5b9b1a45ed929b */
|
/* merge from https://github.com/toffaletti/state-threads/commit/7f57fc9acc05e657bca1223f1e5b9b1a45ed929b */
|
||||||
#ifndef NVALGRIND
|
#ifdef MD_VALGRIND
|
||||||
if (!(thread->flags & _ST_FL_PRIMORDIAL)) {
|
if (!(thread->flags & _ST_FL_PRIMORDIAL)) {
|
||||||
thread->stack->valgrind_stack_id = VALGRIND_STACK_REGISTER(thread->stack->stk_top, thread->stack->stk_bottom);
|
thread->stack->valgrind_stack_id = VALGRIND_STACK_REGISTER(thread->stack->stk_top, thread->stack->stk_bottom);
|
||||||
}
|
}
|
||||||
|
@ -695,7 +698,7 @@ _st_thread_t *st_thread_create(void *(*start)(void *arg), void *arg, int joinabl
|
||||||
|
|
||||||
_st_thread_t *st_thread_self(void)
|
_st_thread_t *st_thread_self(void)
|
||||||
{
|
{
|
||||||
return _ST_CURRENT_THREAD();
|
return _st_this_thread;
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef DEBUG
|
#ifdef DEBUG
|
||||||
|
@ -717,7 +720,7 @@ void _st_iterate_threads(void)
|
||||||
if (!_st_iterate_threads_flag) {
|
if (!_st_iterate_threads_flag) {
|
||||||
if (thread) {
|
if (thread) {
|
||||||
memcpy(thread->context, save_jb, sizeof(_st_jmp_buf_t));
|
memcpy(thread->context, save_jb, sizeof(_st_jmp_buf_t));
|
||||||
MD_LONGJMP(orig_jb, 1);
|
_st_md_cxt_restore(orig_jb, 1);
|
||||||
}
|
}
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -726,25 +729,25 @@ void _st_iterate_threads(void)
|
||||||
memcpy(thread->context, save_jb, sizeof(_st_jmp_buf_t));
|
memcpy(thread->context, save_jb, sizeof(_st_jmp_buf_t));
|
||||||
_st_show_thread_stack(thread, NULL);
|
_st_show_thread_stack(thread, NULL);
|
||||||
} else {
|
} else {
|
||||||
if (MD_SETJMP(orig_jb)) {
|
if (_st_md_cxt_save(orig_jb)) {
|
||||||
_st_iterate_threads_flag = 0;
|
_st_iterate_threads_flag = 0;
|
||||||
thread = NULL;
|
thread = NULL;
|
||||||
_st_show_thread_stack(thread, "Iteration completed");
|
_st_show_thread_stack(thread, "Iteration completed");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
thread = _ST_CURRENT_THREAD();
|
thread = _st_this_thread;
|
||||||
_st_show_thread_stack(thread, "Iteration started");
|
_st_show_thread_stack(thread, "Iteration started");
|
||||||
}
|
}
|
||||||
|
|
||||||
q = thread->tlink.next;
|
q = thread->tlink.next;
|
||||||
if (q == &_ST_THREADQ)
|
if (q == &_st_this_vp.thread_q)
|
||||||
q = q->next;
|
q = q->next;
|
||||||
ST_ASSERT(q != &_ST_THREADQ);
|
ST_ASSERT(q != &_st_this_vp.thread_q);
|
||||||
thread = _ST_THREAD_THREADQ_PTR(q);
|
thread = _ST_THREAD_THREADQ_PTR(q);
|
||||||
if (thread == _ST_CURRENT_THREAD())
|
if (thread == _st_this_thread)
|
||||||
MD_LONGJMP(orig_jb, 1);
|
_st_md_cxt_restore(orig_jb, 1);
|
||||||
memcpy(save_jb, thread->context, sizeof(_st_jmp_buf_t));
|
memcpy(save_jb, thread->context, sizeof(_st_jmp_buf_t));
|
||||||
MD_LONGJMP(thread->context, 1);
|
_st_md_cxt_restore(thread->context, 1);
|
||||||
}
|
}
|
||||||
#endif /* DEBUG */
|
#endif /* DEBUG */
|
||||||
|
|
||||||
|
|
10
trunk/3rdparty/st-srs/stk.c
vendored
10
trunk/3rdparty/st-srs/stk.c
vendored
|
@ -50,7 +50,7 @@
|
||||||
|
|
||||||
|
|
||||||
/* How much space to leave between the stacks, at each end */
|
/* How much space to leave between the stacks, at each end */
|
||||||
#define REDZONE _ST_PAGE_SIZE
|
#define REDZONE _st_this_vp.pagesize
|
||||||
|
|
||||||
__thread _st_clist_t _st_free_stacks;
|
__thread _st_clist_t _st_free_stacks;
|
||||||
__thread int _st_num_free_stacks = 0;
|
__thread int _st_num_free_stacks = 0;
|
||||||
|
@ -71,7 +71,7 @@ _st_stack_t *_st_stack_new(int stack_size)
|
||||||
ts = _ST_THREAD_STACK_PTR(qp);
|
ts = _ST_THREAD_STACK_PTR(qp);
|
||||||
if (ts->stk_size >= stack_size) {
|
if (ts->stk_size >= stack_size) {
|
||||||
/* Found a stack that is big enough */
|
/* Found a stack that is big enough */
|
||||||
ST_REMOVE_LINK(&ts->links);
|
st_clist_remove(&ts->links);
|
||||||
_st_num_free_stacks--;
|
_st_num_free_stacks--;
|
||||||
ts->links.next = NULL;
|
ts->links.next = NULL;
|
||||||
ts->links.prev = NULL;
|
ts->links.prev = NULL;
|
||||||
|
@ -80,7 +80,7 @@ _st_stack_t *_st_stack_new(int stack_size)
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
extra = _st_randomize_stacks ? _ST_PAGE_SIZE : 0;
|
extra = _st_randomize_stacks ? _st_this_vp.pagesize : 0;
|
||||||
/* If not cache stack, we will free all stack in the list, which contains the stack to be freed.
|
/* If not cache stack, we will free all stack in the list, which contains the stack to be freed.
|
||||||
* Note that we should never directly free it at _st_stack_free, because it is still be used,
|
* Note that we should never directly free it at _st_stack_free, because it is still be used,
|
||||||
* and will cause crash. */
|
* and will cause crash. */
|
||||||
|
@ -90,7 +90,7 @@ _st_stack_t *_st_stack_new(int stack_size)
|
||||||
/* Before qp is freed, move to next one, because the qp will be freed when free the ts. */
|
/* Before qp is freed, move to next one, because the qp will be freed when free the ts. */
|
||||||
qp = qp->next;
|
qp = qp->next;
|
||||||
|
|
||||||
ST_REMOVE_LINK(&ts->links);
|
st_clist_remove(&ts->links);
|
||||||
_st_num_free_stacks--;
|
_st_num_free_stacks--;
|
||||||
|
|
||||||
#if defined(DEBUG) && !defined(MD_NO_PROTECT)
|
#if defined(DEBUG) && !defined(MD_NO_PROTECT)
|
||||||
|
@ -142,7 +142,7 @@ void _st_stack_free(_st_stack_t *ts)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
/* Put the stack on the free list */
|
/* Put the stack on the free list */
|
||||||
ST_APPEND_LINK(&ts->links, _st_free_stacks.prev);
|
st_clist_insert_before(&ts->links, _st_free_stacks.prev);
|
||||||
_st_num_free_stacks++;
|
_st_num_free_stacks++;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
40
trunk/3rdparty/st-srs/sync.c
vendored
40
trunk/3rdparty/st-srs/sync.c
vendored
|
@ -87,7 +87,7 @@ int st_set_utime_function(st_utime_t (*func)(void))
|
||||||
|
|
||||||
st_utime_t st_utime_last_clock(void)
|
st_utime_t st_utime_last_clock(void)
|
||||||
{
|
{
|
||||||
return _ST_LAST_CLOCK;
|
return _st_this_vp.last_clock;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -116,7 +116,7 @@ time_t st_time(void)
|
||||||
|
|
||||||
int st_usleep(st_utime_t usecs)
|
int st_usleep(st_utime_t usecs)
|
||||||
{
|
{
|
||||||
_st_thread_t *me = _ST_CURRENT_THREAD();
|
_st_thread_t *me = _st_this_thread;
|
||||||
|
|
||||||
if (me->flags & _ST_FL_INTERRUPT) {
|
if (me->flags & _ST_FL_INTERRUPT) {
|
||||||
me->flags &= ~_ST_FL_INTERRUPT;
|
me->flags &= ~_ST_FL_INTERRUPT;
|
||||||
|
@ -126,11 +126,11 @@ int st_usleep(st_utime_t usecs)
|
||||||
|
|
||||||
if (usecs != ST_UTIME_NO_TIMEOUT) {
|
if (usecs != ST_UTIME_NO_TIMEOUT) {
|
||||||
me->state = _ST_ST_SLEEPING;
|
me->state = _ST_ST_SLEEPING;
|
||||||
_ST_ADD_SLEEPQ(me, usecs);
|
_st_add_sleep_q(me, usecs);
|
||||||
} else
|
} else
|
||||||
me->state = _ST_ST_SUSPENDED;
|
me->state = _ST_ST_SUSPENDED;
|
||||||
|
|
||||||
_ST_SWITCH_CONTEXT(me);
|
_st_switch_context(me);
|
||||||
|
|
||||||
if (me->flags & _ST_FL_INTERRUPT) {
|
if (me->flags & _ST_FL_INTERRUPT) {
|
||||||
me->flags &= ~_ST_FL_INTERRUPT;
|
me->flags &= ~_ST_FL_INTERRUPT;
|
||||||
|
@ -158,7 +158,7 @@ _st_cond_t *st_cond_new(void)
|
||||||
|
|
||||||
cvar = (_st_cond_t *) calloc(1, sizeof(_st_cond_t));
|
cvar = (_st_cond_t *) calloc(1, sizeof(_st_cond_t));
|
||||||
if (cvar) {
|
if (cvar) {
|
||||||
ST_INIT_CLIST(&cvar->wait_q);
|
st_clist_init(&cvar->wait_q);
|
||||||
}
|
}
|
||||||
|
|
||||||
return cvar;
|
return cvar;
|
||||||
|
@ -180,7 +180,7 @@ int st_cond_destroy(_st_cond_t *cvar)
|
||||||
|
|
||||||
int st_cond_timedwait(_st_cond_t *cvar, st_utime_t timeout)
|
int st_cond_timedwait(_st_cond_t *cvar, st_utime_t timeout)
|
||||||
{
|
{
|
||||||
_st_thread_t *me = _ST_CURRENT_THREAD();
|
_st_thread_t *me = _st_this_thread;
|
||||||
int rv;
|
int rv;
|
||||||
|
|
||||||
if (me->flags & _ST_FL_INTERRUPT) {
|
if (me->flags & _ST_FL_INTERRUPT) {
|
||||||
|
@ -191,14 +191,14 @@ int st_cond_timedwait(_st_cond_t *cvar, st_utime_t timeout)
|
||||||
|
|
||||||
/* Put caller thread on the condition variable's wait queue */
|
/* Put caller thread on the condition variable's wait queue */
|
||||||
me->state = _ST_ST_COND_WAIT;
|
me->state = _ST_ST_COND_WAIT;
|
||||||
ST_APPEND_LINK(&me->wait_links, &cvar->wait_q);
|
st_clist_insert_before(&me->wait_links, &cvar->wait_q);
|
||||||
|
|
||||||
if (timeout != ST_UTIME_NO_TIMEOUT)
|
if (timeout != ST_UTIME_NO_TIMEOUT)
|
||||||
_ST_ADD_SLEEPQ(me, timeout);
|
_st_add_sleep_q(me, timeout);
|
||||||
|
|
||||||
_ST_SWITCH_CONTEXT(me);
|
_st_switch_context(me);
|
||||||
|
|
||||||
ST_REMOVE_LINK(&me->wait_links);
|
st_clist_remove(&me->wait_links);
|
||||||
rv = 0;
|
rv = 0;
|
||||||
|
|
||||||
if (me->flags & _ST_FL_TIMEDOUT) {
|
if (me->flags & _ST_FL_TIMEDOUT) {
|
||||||
|
@ -231,11 +231,11 @@ static int _st_cond_signal(_st_cond_t *cvar, int broadcast)
|
||||||
thread = _ST_THREAD_WAITQ_PTR(q);
|
thread = _ST_THREAD_WAITQ_PTR(q);
|
||||||
if (thread->state == _ST_ST_COND_WAIT) {
|
if (thread->state == _ST_ST_COND_WAIT) {
|
||||||
if (thread->flags & _ST_FL_ON_SLEEPQ)
|
if (thread->flags & _ST_FL_ON_SLEEPQ)
|
||||||
_ST_DEL_SLEEPQ(thread);
|
_st_del_sleep_q(thread);
|
||||||
|
|
||||||
/* Make thread runnable */
|
/* Make thread runnable */
|
||||||
thread->state = _ST_ST_RUNNABLE;
|
thread->state = _ST_ST_RUNNABLE;
|
||||||
_ST_ADD_RUNQ(thread);
|
st_clist_insert_before(&thread->links, &_st_this_vp.run_q);
|
||||||
if (!broadcast)
|
if (!broadcast)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -267,7 +267,7 @@ _st_mutex_t *st_mutex_new(void)
|
||||||
|
|
||||||
lock = (_st_mutex_t *) calloc(1, sizeof(_st_mutex_t));
|
lock = (_st_mutex_t *) calloc(1, sizeof(_st_mutex_t));
|
||||||
if (lock) {
|
if (lock) {
|
||||||
ST_INIT_CLIST(&lock->wait_q);
|
st_clist_init(&lock->wait_q);
|
||||||
lock->owner = NULL;
|
lock->owner = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -290,7 +290,7 @@ int st_mutex_destroy(_st_mutex_t *lock)
|
||||||
|
|
||||||
int st_mutex_lock(_st_mutex_t *lock)
|
int st_mutex_lock(_st_mutex_t *lock)
|
||||||
{
|
{
|
||||||
_st_thread_t *me = _ST_CURRENT_THREAD();
|
_st_thread_t *me = _st_this_thread;
|
||||||
|
|
||||||
if (me->flags & _ST_FL_INTERRUPT) {
|
if (me->flags & _ST_FL_INTERRUPT) {
|
||||||
me->flags &= ~_ST_FL_INTERRUPT;
|
me->flags &= ~_ST_FL_INTERRUPT;
|
||||||
|
@ -311,11 +311,11 @@ int st_mutex_lock(_st_mutex_t *lock)
|
||||||
|
|
||||||
/* Put caller thread on the mutex's wait queue */
|
/* Put caller thread on the mutex's wait queue */
|
||||||
me->state = _ST_ST_LOCK_WAIT;
|
me->state = _ST_ST_LOCK_WAIT;
|
||||||
ST_APPEND_LINK(&me->wait_links, &lock->wait_q);
|
st_clist_insert_before(&me->wait_links, &lock->wait_q);
|
||||||
|
|
||||||
_ST_SWITCH_CONTEXT(me);
|
_st_switch_context(me);
|
||||||
|
|
||||||
ST_REMOVE_LINK(&me->wait_links);
|
st_clist_remove(&me->wait_links);
|
||||||
|
|
||||||
if ((me->flags & _ST_FL_INTERRUPT) && lock->owner != me) {
|
if ((me->flags & _ST_FL_INTERRUPT) && lock->owner != me) {
|
||||||
me->flags &= ~_ST_FL_INTERRUPT;
|
me->flags &= ~_ST_FL_INTERRUPT;
|
||||||
|
@ -332,7 +332,7 @@ int st_mutex_unlock(_st_mutex_t *lock)
|
||||||
_st_thread_t *thread;
|
_st_thread_t *thread;
|
||||||
_st_clist_t *q;
|
_st_clist_t *q;
|
||||||
|
|
||||||
if (lock->owner != _ST_CURRENT_THREAD()) {
|
if (lock->owner != _st_this_thread) {
|
||||||
errno = EPERM;
|
errno = EPERM;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
@ -343,7 +343,7 @@ int st_mutex_unlock(_st_mutex_t *lock)
|
||||||
lock->owner = thread;
|
lock->owner = thread;
|
||||||
/* Make thread runnable */
|
/* Make thread runnable */
|
||||||
thread->state = _ST_ST_RUNNABLE;
|
thread->state = _ST_ST_RUNNABLE;
|
||||||
_ST_ADD_RUNQ(thread);
|
st_clist_insert_before(&thread->links, &_st_this_vp.run_q);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -363,7 +363,7 @@ int st_mutex_trylock(_st_mutex_t *lock)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Got the mutex */
|
/* Got the mutex */
|
||||||
lock->owner = _ST_CURRENT_THREAD();
|
lock->owner = _st_this_thread;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
6
trunk/configure
vendored
6
trunk/configure
vendored
|
@ -128,7 +128,7 @@ fi
|
||||||
|
|
||||||
# Start to generate the Makefile.
|
# Start to generate the Makefile.
|
||||||
cat << END >> ${SRS_OBJS}/Makefile
|
cat << END >> ${SRS_OBJS}/Makefile
|
||||||
GCC = ${SRS_TOOL_CC}
|
CC = ${SRS_TOOL_CC}
|
||||||
CXX = ${SRS_TOOL_CXX}
|
CXX = ${SRS_TOOL_CXX}
|
||||||
AR = ${SRS_TOOL_AR}
|
AR = ${SRS_TOOL_AR}
|
||||||
LINK = ${SRS_TOOL_CXX}
|
LINK = ${SRS_TOOL_CXX}
|
||||||
|
@ -514,7 +514,7 @@ cat << END > ${SRS_MAKEFILE}
|
||||||
.PHONY: clean_srs clean_modules clean_openssl clean_srtp2 clean_opus clean_ffmpeg clean_st
|
.PHONY: clean_srs clean_modules clean_openssl clean_srtp2 clean_opus clean_ffmpeg clean_st
|
||||||
.PHONY: st ffmpeg
|
.PHONY: st ffmpeg
|
||||||
|
|
||||||
GCC = ${SRS_TOOL_CC}
|
CC = ${SRS_TOOL_CC}
|
||||||
CXX = ${SRS_TOOL_CXX}
|
CXX = ${SRS_TOOL_CXX}
|
||||||
AR = ${SRS_TOOL_AR}
|
AR = ${SRS_TOOL_AR}
|
||||||
LINK = ${SRS_TOOL_LD}
|
LINK = ${SRS_TOOL_LD}
|
||||||
|
@ -606,7 +606,7 @@ clean_st:
|
||||||
st:
|
st:
|
||||||
@rm -f ${SRS_OBJS}/srs srs_utest
|
@rm -f ${SRS_OBJS}/srs srs_utest
|
||||||
@\$(MAKE)\$(JOBS) -C ${SRS_OBJS}/${SRS_PLATFORM}/st-srs clean
|
@\$(MAKE)\$(JOBS) -C ${SRS_OBJS}/${SRS_PLATFORM}/st-srs clean
|
||||||
@env EXTRA_CFLAGS="${_ST_EXTRA_CFLAGS}" \$(MAKE)\$(JOBS) -C ${SRS_OBJS}/${SRS_PLATFORM}/st-srs ${_ST_MAKE_ARGS} CC=\$(GCC) AR=\$(AR) LD=\$(LINK) RANDLIB=\$(RANDLIB)
|
@env EXTRA_CFLAGS="${_ST_EXTRA_CFLAGS}" \$(MAKE)\$(JOBS) -C ${SRS_OBJS}/${SRS_PLATFORM}/st-srs ${_ST_MAKE_ARGS} CC=\$(CC) CXX=\$(CXX) AR=\$(AR) LD=\$(LINK) RANDLIB=\$(RANDLIB)
|
||||||
@echo "Please rebuild srs by: make"
|
@echo "Please rebuild srs by: make"
|
||||||
|
|
||||||
ffmpeg:
|
ffmpeg:
|
||||||
|
|
|
@ -7,6 +7,7 @@ The changelog for SRS.
|
||||||
<a name="v7-changes"></a>
|
<a name="v7-changes"></a>
|
||||||
|
|
||||||
## SRS 7.0 Changelog
|
## SRS 7.0 Changelog
|
||||||
|
* v7.0, 2024-08-21, Merge [#4149](https://github.com/ossrs/srs/pull/4149): ST: Replace macros with explicit code for better understanding. v7.0.7 (#4149)
|
||||||
* v7.0, 2024-08-21, Merge [#4150](https://github.com/ossrs/srs/pull/4150): API: Support new HTTP API for VALGRIND. v7.0.6 (#4150)
|
* v7.0, 2024-08-21, Merge [#4150](https://github.com/ossrs/srs/pull/4150): API: Support new HTTP API for VALGRIND. v7.0.6 (#4150)
|
||||||
* v7.0, 2024-08-15, Merge [#4144](https://github.com/ossrs/srs/pull/4144): HTTP-FLV: Crash when multiple viewers. v7.0.5 (#4144)
|
* v7.0, 2024-08-15, Merge [#4144](https://github.com/ossrs/srs/pull/4144): HTTP-FLV: Crash when multiple viewers. v7.0.5 (#4144)
|
||||||
* v7.0, 2024-08-15, Merge [#4142](https://github.com/ossrs/srs/pull/4142): Config: Add more utest for env config. v7.0.4 (#4142)
|
* v7.0, 2024-08-15, Merge [#4142](https://github.com/ossrs/srs/pull/4142): Config: Add more utest for env config. v7.0.4 (#4142)
|
||||||
|
|
7
trunk/research/st/.gitignore
vendored
7
trunk/research/st/.gitignore
vendored
|
@ -3,3 +3,10 @@ udp-client
|
||||||
cost
|
cost
|
||||||
cost.log
|
cost.log
|
||||||
thread-join
|
thread-join
|
||||||
|
st-cond
|
||||||
|
hello-st
|
||||||
|
hello-world
|
||||||
|
huge-threads
|
||||||
|
exceptions
|
||||||
|
hello
|
||||||
|
pthreads
|
||||||
|
|
26
trunk/research/st/st-cond.cpp
Normal file
26
trunk/research/st/st-cond.cpp
Normal file
|
@ -0,0 +1,26 @@
|
||||||
|
/*
|
||||||
|
g++ st-cond.cpp ../../objs/st/libst.a -g -O0 -o st-cond && ./st-cond
|
||||||
|
*/
|
||||||
|
#include <stdio.h>
|
||||||
|
#include "../../objs/st/st.h"
|
||||||
|
|
||||||
|
st_cond_t lock;
|
||||||
|
|
||||||
|
void* foo(void*) {
|
||||||
|
st_cond_wait(lock);
|
||||||
|
printf("Hello World, ST!\n");
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
int main() {
|
||||||
|
st_init();
|
||||||
|
lock = st_cond_new();
|
||||||
|
|
||||||
|
st_thread_create(foo, NULL, 0, 0);
|
||||||
|
st_sleep(1);
|
||||||
|
st_cond_signal(lock);
|
||||||
|
st_sleep(1);
|
||||||
|
|
||||||
|
st_cond_destroy(lock);
|
||||||
|
return 0;
|
||||||
|
}
|
|
@ -9,6 +9,6 @@
|
||||||
|
|
||||||
#define VERSION_MAJOR 7
|
#define VERSION_MAJOR 7
|
||||||
#define VERSION_MINOR 0
|
#define VERSION_MINOR 0
|
||||||
#define VERSION_REVISION 6
|
#define VERSION_REVISION 7
|
||||||
|
|
||||||
#endif
|
#endif
|
Loading…
Reference in a new issue