* @brief This function will send an event to the event object. * If there is a thread suspended on the event, the thread will be resumed. * * @note When using this function, you need to use the parameter (set) to specify the event flag of the event object, * then the function will traverse the list of suspended threads waiting on the event object. * If the
| 1964 | * If the return value is any other values, it means that the event detach failed. |
| 1965 | */ |
| 1966 | rt_err_t rt_event_send(rt_event_t event, rt_uint32_t set) |
| 1967 | { |
| 1968 | struct rt_list_node *n; |
| 1969 | struct rt_thread *thread; |
| 1970 | rt_sched_lock_level_t slvl; |
| 1971 | rt_base_t level; |
| 1972 | rt_base_t status; |
| 1973 | rt_bool_t need_schedule; |
| 1974 | rt_uint32_t need_clear_set = 0; |
| 1975 | |
| 1976 | /* parameter check */ |
| 1977 | RT_ASSERT(event != RT_NULL); |
| 1978 | RT_ASSERT(rt_object_get_type(&event->parent.parent) == RT_Object_Class_Event); |
| 1979 | |
| 1980 | if (set == 0) |
| 1981 | return -RT_ERROR; |
| 1982 | |
| 1983 | need_schedule = RT_FALSE; |
| 1984 | |
| 1985 | level = rt_spin_lock_irqsave(&(event->spinlock)); |
| 1986 | |
| 1987 | /* set event */ |
| 1988 | event->set |= set; |
| 1989 | |
| 1990 | RT_OBJECT_HOOK_CALL(rt_object_put_hook, (&(event->parent.parent))); |
| 1991 | |
| 1992 | rt_sched_lock(&slvl); |
| 1993 | if (!rt_list_isempty(&event->parent.suspend_thread)) |
| 1994 | { |
| 1995 | /* search thread list to resume thread */ |
| 1996 | n = event->parent.suspend_thread.next; |
| 1997 | while (n != &(event->parent.suspend_thread)) |
| 1998 | { |
| 1999 | /* get thread */ |
| 2000 | thread = RT_THREAD_LIST_NODE_ENTRY(n); |
| 2001 | |
| 2002 | status = -RT_ERROR; |
| 2003 | if (thread->event_info & RT_EVENT_FLAG_AND) |
| 2004 | { |
| 2005 | if ((thread->event_set & event->set) == thread->event_set) |
| 2006 | { |
| 2007 | /* received an AND event */ |
| 2008 | status = RT_EOK; |
| 2009 | } |
| 2010 | } |
| 2011 | else if (thread->event_info & RT_EVENT_FLAG_OR) |
| 2012 | { |
| 2013 | if (thread->event_set & event->set) |
| 2014 | { |
| 2015 | /* save the received event set */ |
| 2016 | thread->event_set = thread->event_set & event->set; |
| 2017 | |
| 2018 | /* received an OR event */ |
| 2019 | status = RT_EOK; |
| 2020 | } |
| 2021 | } |
| 2022 | else |
| 2023 | { |