summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorBernard Xiong <[email protected]>2019-05-20 20:33:07 +0800
committerGitHub <[email protected]>2019-05-20 20:33:07 +0800
commitb2ae7d72f923e1638f72d8eba5c2131389b741b0 (patch)
treeab526e2e216f5f656b9c6a53221382d07c7bac2e /src
parentd778c9df25cbbd8e202a0133453e4c8b8e179eff (diff)
parent35eff9a85dd1e922f98d36deed84bdfb3c8319f7 (diff)
Merge pull request #2703 from armink/lts-v3.1.x
Lts v3.1.x
Diffstat (limited to 'src')
-rw-r--r--src/Kconfig12
-rw-r--r--src/clock.c15
-rw-r--r--src/cpu.c14
-rw-r--r--src/idle.c4
-rw-r--r--src/ipc.c8
-rw-r--r--src/kservice.c125
-rw-r--r--src/memheap.c4
-rw-r--r--src/object.c20
-rw-r--r--src/scheduler.c13
9 files changed, 153 insertions, 62 deletions
diff --git a/src/Kconfig b/src/Kconfig
index babbc83a01..2ad1518054 100644
--- a/src/Kconfig
+++ b/src/Kconfig
@@ -8,6 +8,14 @@ config RT_NAME_MAX
Each kernel object, such as thread, timer, semaphore etc, has a name,
the RT_NAME_MAX is the maximal size of this object name.
+config RT_USING_ARCH_DATA_TYPE
+ bool "Use the data types defined in ARCH_CPU"
+ default n
+ help
+ For the data type like, `rt_uint8/int8_t, rt_uint16/int16_t, rt_uint32/int32_t`,
+ BSP can define these basic data types in ARCH_CPU level.
+
+ Please re-define these data types in rtconfig_project.h file.
config RT_ALIGN_SIZE
int "Alignment size for CPU architecture data access"
default 4
@@ -75,7 +83,7 @@ config IDLE_THREAD_STACK_SIZE
config RT_USING_TIMER_SOFT
bool "Enable software timer with a timer thread"
- default n
+ default y
help
the timeout function context of soft-timer is under a high priority timer
thread.
@@ -99,7 +107,7 @@ if RT_DEBUG
config RT_DEBUG_COLOR
bool "Enable color debugging log"
- default y
+ default n
config RT_DEBUG_INIT_CONFIG
bool "Enable debugging of components initialization"
diff --git a/src/clock.c b/src/clock.c
index 36ff398376..e969a19b5e 100644
--- a/src/clock.c
+++ b/src/clock.c
@@ -98,15 +98,20 @@ void rt_tick_increase(void)
*
* @return the calculated tick
*/
-int rt_tick_from_millisecond(rt_int32_t ms)
+rt_tick_t rt_tick_from_millisecond(rt_int32_t ms)
{
- int tick;
+ rt_tick_t tick;
if (ms < 0)
- tick = RT_WAITING_FOREVER;
+ {
+ tick = (rt_tick_t)RT_WAITING_FOREVER;
+ }
else
- tick = (RT_TICK_PER_SECOND * ms + 999) / 1000;
-
+ {
+ tick = RT_TICK_PER_SECOND * (ms / 1000);
+ tick += (RT_TICK_PER_SECOND * (ms % 1000) + 999) / 1000;
+ }
+
/* return the calculated tick */
return tick;
}
diff --git a/src/cpu.c b/src/cpu.c
new file mode 100644
index 0000000000..5cba05fe70
--- /dev/null
+++ b/src/cpu.c
@@ -0,0 +1,14 @@
+/*
+ * Copyright (c) 2006-2018, RT-Thread Development Team
+ *
+ * SPDX-License-Identifier: Apache-2.0
+ *
+ * Change Logs:
+ * Date Author Notes
+ * 2018-10-30 Bernard The first version
+ */
+
+#include <rtthread.h>
+#include <rthw.h>
+
+/* nothing on non-smp version */
diff --git a/src/idle.c b/src/idle.c
index 9906ed7848..bf5f2d1dc8 100644
--- a/src/idle.c
+++ b/src/idle.c
@@ -221,6 +221,7 @@ void rt_thread_idle_excute(void)
}
}
+extern void rt_system_power_manager(void);
static void rt_thread_idle_entry(void *parameter)
{
while (1)
@@ -239,6 +240,9 @@ static void rt_thread_idle_entry(void *parameter)
#endif
rt_thread_idle_excute();
+#ifdef RT_USING_PM
+ rt_system_power_manager();
+#endif
}
}
diff --git a/src/ipc.c b/src/ipc.c
index 56045911a8..36b714d19f 100644
--- a/src/ipc.c
+++ b/src/ipc.c
@@ -200,6 +200,7 @@ rt_err_t rt_sem_init(rt_sem_t sem,
rt_uint8_t flag)
{
RT_ASSERT(sem != RT_NULL);
+ RT_ASSERT(value < 0x10000U);
/* init object */
rt_object_init(&(sem->parent.parent), RT_Object_Class_Semaphore, name);
@@ -208,7 +209,7 @@ rt_err_t rt_sem_init(rt_sem_t sem,
rt_ipc_object_init(&(sem->parent));
/* set init value */
- sem->value = value;
+ sem->value = (rt_uint16_t)value;
/* set parent */
sem->parent.parent.flag = flag;
@@ -260,6 +261,7 @@ rt_sem_t rt_sem_create(const char *name, rt_uint32_t value, rt_uint8_t flag)
rt_sem_t sem;
RT_DEBUG_NOT_IN_INTERRUPT;
+ RT_ASSERT(value < 0x10000U);
/* allocate object */
sem = (rt_sem_t)rt_object_allocate(RT_Object_Class_Semaphore, name);
@@ -750,8 +752,8 @@ __again:
if (thread->error != RT_EOK)
{
- /* interrupt by signal, try it again */
- if (thread->error == -RT_EINTR) goto __again;
+ /* interrupt by signal, try it again */
+ if (thread->error == -RT_EINTR) goto __again;
/* return error */
return thread->error;
diff --git a/src/kservice.c b/src/kservice.c
index 7a3772473f..1d3dace340 100644
--- a/src/kservice.c
+++ b/src/kservice.c
@@ -133,20 +133,21 @@ void *rt_memset(void *s, int c, rt_ubase_t count)
return s;
#else
-#define LBLOCKSIZE (sizeof(rt_int32_t))
-#define UNALIGNED(X) ((rt_int32_t)X & (LBLOCKSIZE - 1))
+#define LBLOCKSIZE (sizeof(long))
+#define UNALIGNED(X) ((long)X & (LBLOCKSIZE - 1))
#define TOO_SMALL(LEN) ((LEN) < LBLOCKSIZE)
- int i;
+ unsigned int i;
char *m = (char *)s;
- rt_uint32_t buffer;
- rt_uint32_t *aligned_addr;
- rt_uint32_t d = c & 0xff;
+ unsigned long buffer;
+ unsigned long *aligned_addr;
+ unsigned int d = c & 0xff; /* To avoid sign extension, copy C to an
+ unsigned variable. */
if (!TOO_SMALL(count) && !UNALIGNED(s))
{
/* If we get this far, we know that n is large and m is word-aligned. */
- aligned_addr = (rt_uint32_t *)s;
+ aligned_addr = (unsigned long *)s;
/* Store D into each char sized location in BUFFER so that
* we can set large blocks quickly.
@@ -226,25 +227,24 @@ void *rt_memcpy(void *dst, const void *src, rt_ubase_t count)
return dst;
#else
-#define UNALIGNED(X, Y) \
- (((rt_int32_t)X & (sizeof(rt_int32_t) - 1)) | \
- ((rt_int32_t)Y & (sizeof(rt_int32_t) - 1)))
-#define BIGBLOCKSIZE (sizeof(rt_int32_t) << 2)
-#define LITTLEBLOCKSIZE (sizeof(rt_int32_t))
+#define UNALIGNED(X, Y) \
+ (((long)X & (sizeof (long) - 1)) | ((long)Y & (sizeof (long) - 1)))
+#define BIGBLOCKSIZE (sizeof (long) << 2)
+#define LITTLEBLOCKSIZE (sizeof (long))
#define TOO_SMALL(LEN) ((LEN) < BIGBLOCKSIZE)
char *dst_ptr = (char *)dst;
char *src_ptr = (char *)src;
- rt_int32_t *aligned_dst;
- rt_int32_t *aligned_src;
+ long *aligned_dst;
+ long *aligned_src;
int len = count;
/* If the size is small, or either SRC or DST is unaligned,
then punt into the byte copy loop. This should be rare. */
if (!TOO_SMALL(len) && !UNALIGNED(src_ptr, dst_ptr))
{
- aligned_dst = (rt_int32_t *)dst_ptr;
- aligned_src = (rt_int32_t *)src_ptr;
+ aligned_dst = (long *)dst_ptr;
+ aligned_src = (long *)src_ptr;
/* Copy 4X long words at a time if possible. */
while (len >= BIGBLOCKSIZE)
@@ -545,24 +545,45 @@ RTM_EXPORT(rt_show_version);
/* private function */
#define isdigit(c) ((unsigned)((c) - '0') < 10)
-rt_inline rt_int32_t divide(rt_int32_t *n, rt_int32_t base)
+#ifdef RT_PRINTF_LONGLONG
+rt_inline int divide(long long *n, int base)
+{
+ int res;
+
+ /* optimized for processor which does not support divide instructions. */
+ if (base == 10)
+ {
+ res = (int)(((unsigned long long)*n) % 10U);
+ *n = (long long)(((unsigned long long)*n) / 10U);
+ }
+ else
+ {
+ res = (int)(((unsigned long long)*n) % 16U);
+ *n = (long long)(((unsigned long long)*n) / 16U);
+ }
+
+ return res;
+}
+#else
+rt_inline int divide(long *n, int base)
{
- rt_int32_t res;
+ int res;
/* optimized for processor which does not support divide instructions. */
if (base == 10)
{
- res = ((rt_uint32_t) * n) % 10U;
- *n = ((rt_uint32_t) * n) / 10U;
+ res = (int)(((unsigned long)*n) % 10U);
+ *n = (long)(((unsigned long)*n) / 10U);
}
else
{
- res = ((rt_uint32_t) * n) % 16U;
- *n = ((rt_uint32_t) * n) / 16U;
+ res = (int)(((unsigned long)*n) % 16U);
+ *n = (long)(((unsigned long)*n) / 16U);
}
return res;
}
+#endif
rt_inline int skip_atoi(const char **s)
{
@@ -584,7 +605,11 @@ rt_inline int skip_atoi(const char **s)
#ifdef RT_PRINTF_PRECISION
static char *print_number(char *buf,
char *end,
+#ifdef RT_PRINTF_LONGLONG
+ long long num,
+#else
long num,
+#endif
int base,
int s,
int precision,
@@ -592,7 +617,11 @@ static char *print_number(char *buf,
#else
static char *print_number(char *buf,
char *end,
+#ifdef RT_PRINTF_LONGLONG
+ long long num,
+#else
long num,
+#endif
int base,
int s,
int type)
@@ -668,7 +697,7 @@ static char *print_number(char *buf,
while (size-- > 0)
{
- if (buf <= end)
+ if (buf < end)
*buf = ' ';
++ buf;
}
@@ -676,11 +705,11 @@ static char *print_number(char *buf,
if (sign)
{
- if (buf <= end)
+ if (buf < end)
{
*buf = sign;
- -- size;
}
+ -- size;
++ buf;
}
@@ -689,16 +718,16 @@ static char *print_number(char *buf,
{
if (base == 8)
{
- if (buf <= end)
+ if (buf < end)
*buf = '0';
++ buf;
}
else if (base == 16)
{
- if (buf <= end)
+ if (buf < end)
*buf = '0';
++ buf;
- if (buf <= end)
+ if (buf < end)
{
*buf = type & LARGE ? 'X' : 'x';
}
@@ -712,7 +741,7 @@ static char *print_number(char *buf,
{
while (size-- > 0)
{
- if (buf <= end)
+ if (buf < end)
*buf = c;
++ buf;
}
@@ -721,7 +750,7 @@ static char *print_number(char *buf,
#ifdef RT_PRINTF_PRECISION
while (i < precision--)
{
- if (buf <= end)
+ if (buf < end)
*buf = '0';
++ buf;
}
@@ -730,14 +759,14 @@ static char *print_number(char *buf,
/* put number in the temporary buffer */
while (i-- > 0 && (precision_bak != 0))
{
- if (buf <= end)
+ if (buf < end)
*buf = tmp[i];
++ buf;
}
while (size-- > 0)
{
- if (buf <= end)
+ if (buf < end)
*buf = ' ';
++ buf;
}
@@ -769,7 +798,7 @@ rt_int32_t rt_vsnprintf(char *buf,
#endif
str = buf;
- end = buf + size - 1;
+ end = buf + size;
/* Make sure end is always >= buf */
if (end < buf)
@@ -782,7 +811,7 @@ rt_int32_t rt_vsnprintf(char *buf,
{
if (*fmt != '%')
{
- if (str <= end)
+ if (str < end)
*str = *fmt;
++ str;
continue;
@@ -863,20 +892,20 @@ rt_int32_t rt_vsnprintf(char *buf,
{
while (--field_width > 0)
{
- if (str <= end) *str = ' ';
+ if (str < end) *str = ' ';
++ str;
}
}
/* get character */
c = (rt_uint8_t)va_arg(args, int);
- if (str <= end) *str = c;
+ if (str < end) *str = c;
++ str;
/* put width */
while (--field_width > 0)
{
- if (str <= end) *str = ' ';
+ if (str < end) *str = ' ';
++ str;
}
continue;
@@ -894,21 +923,21 @@ rt_int32_t rt_vsnprintf(char *buf,
{
while (len < field_width--)
{
- if (str <= end) *str = ' ';
+ if (str < end) *str = ' ';
++ str;
}
}
for (i = 0; i < len; ++i)
{
- if (str <= end) *str = *s;
+ if (str < end) *str = *s;
++ str;
++ s;
}
while (len < field_width--)
{
- if (str <= end) *str = ' ';
+ if (str < end) *str = ' ';
++ str;
}
continue;
@@ -931,7 +960,7 @@ rt_int32_t rt_vsnprintf(char *buf,
continue;
case '%':
- if (str <= end) *str = '%';
+ if (str < end) *str = '%';
++ str;
continue;
@@ -953,12 +982,12 @@ rt_int32_t rt_vsnprintf(char *buf,
break;
default:
- if (str <= end) *str = '%';
+ if (str < end) *str = '%';
++ str;
if (*fmt)
{
- if (str <= end) *str = *fmt;
+ if (str < end) *str = *fmt;
++ str;
}
else
@@ -995,8 +1024,14 @@ rt_int32_t rt_vsnprintf(char *buf,
#endif
}
- if (str <= end) *str = '\0';
- else *end = '\0';
+ if (size > 0)
+ {
+ if (str < end) *str = '\0';
+ else
+ {
+ end[-1] = '\0';
+ }
+ }
/* the trailing null byte doesn't count towards the total
* ++str;
diff --git a/src/memheap.c b/src/memheap.c
index 946f163b64..eb5d710029 100644
--- a/src/memheap.c
+++ b/src/memheap.c
@@ -50,7 +50,7 @@
rt_err_t rt_memheap_init(struct rt_memheap *memheap,
const char *name,
void *start_addr,
- rt_uint32_t size)
+ rt_size_t size)
{
struct rt_memheap_item *item;
@@ -135,7 +135,7 @@ rt_err_t rt_memheap_detach(struct rt_memheap *heap)
}
RTM_EXPORT(rt_memheap_detach);
-void *rt_memheap_alloc(struct rt_memheap *heap, rt_uint32_t size)
+void *rt_memheap_alloc(struct rt_memheap *heap, rt_size_t size)
{
rt_err_t result;
rt_uint32_t free_size;
diff --git a/src/object.c b/src/object.c
index 70b9a5c04e..e85737ce8f 100644
--- a/src/object.c
+++ b/src/object.c
@@ -240,6 +240,7 @@ void rt_object_init(struct rt_object *object,
const char *name)
{
register rt_base_t temp;
+ struct rt_list_node *node = RT_NULL;
struct rt_object_information *information;
#ifdef RT_USING_MODULE
struct rt_dlmodule *module = dlmodule_self();
@@ -249,11 +250,26 @@ void rt_object_init(struct rt_object *object,
information = rt_object_get_information(type);
RT_ASSERT(information != RT_NULL);
- /* initialize object's parameters */
+ /* check object type to avoid re-initialization */
+
+ /* enter critical */
+ rt_enter_critical();
+ /* try to find object */
+ for (node = information->object_list.next;
+ node != &(information->object_list);
+ node = node->next)
+ {
+ struct rt_object *obj;
+
+ obj = rt_list_entry(node, struct rt_object, list);
+ RT_ASSERT(obj != object);
+ }
+ /* leave critical */
+ rt_exit_critical();
+ /* initialize object's parameters */
/* set object type to static */
object->type = type | RT_Object_Class_Static;
-
/* copy name */
rt_strncpy(object->name, name, RT_NAME_MAX);
diff --git a/src/scheduler.c b/src/scheduler.c
index 0219ef4fcc..4bb82bd95c 100644
--- a/src/scheduler.c
+++ b/src/scheduler.c
@@ -74,7 +74,11 @@ static void _rt_scheduler_stack_check(struct rt_thread *thread)
{
RT_ASSERT(thread != RT_NULL);
+#if defined(ARCH_CPU_STACK_GROWS_UPWARD)
+ if (*((rt_uint8_t *)((rt_ubase_t)thread->stack_addr + thread->stack_size - 1)) != '#' ||
+#else
if (*((rt_uint8_t *)thread->stack_addr) != '#' ||
+#endif
(rt_uint32_t)thread->sp <= (rt_uint32_t)thread->stack_addr ||
(rt_uint32_t)thread->sp >
(rt_uint32_t)thread->stack_addr + (rt_uint32_t)thread->stack_size)
@@ -189,7 +193,7 @@ void rt_schedule(void)
struct rt_thread *from_thread;
/* disable interrupt */
- level = rt_hw_interrupt_disable();
+ level = rt_hw_interrupt_disable();
/* check the scheduler is enabled or not */
if (rt_scheduler_lock_nest == 0)
@@ -389,14 +393,17 @@ void rt_exit_critical(void)
level = rt_hw_interrupt_disable();
rt_scheduler_lock_nest --;
-
if (rt_scheduler_lock_nest <= 0)
{
rt_scheduler_lock_nest = 0;
/* enable interrupt */
rt_hw_interrupt_enable(level);
- rt_schedule();
+ if (rt_current_thread)
+ {
+ /* if scheduler is started, do a schedule */
+ rt_schedule();
+ }
}
else
{