📄 tx_efs.c
字号:
/**************************************************************************/
/* */
/* Copyright (c) 1996-2000 by Express Logic Inc. */
/* */
/* This software is copyrighted by and is the sole property of Express */
/* Logic, Inc. All rights, title, ownership, or other interests */
/* in the software remain the property of Express Logic, Inc. This */
/* software may only be used in accordance with the corresponding */
/* license agreement. Any unauthorized use, duplication, transmission, */
/* distribution, or disclosure of this software is expressly forbidden. */
/* */
/* This Copyright notice may not be removed or modified without prior */
/* written consent of Express Logic, Inc. */
/* */
/* Express Logic, Inc. reserves the right to modify this software */
/* without notice. */
/* */
/* Express Logic, Inc. */
/* 11440 West Bernardo Court info@expresslogic.com */
/* Suite 366 http://www.expresslogic.com */
/* San Diego, CA 92127 */
/* */
/**************************************************************************/
/**************************************************************************/
/**************************************************************************/
/** */
/** ThreadX Component */
/** */
/** Event Flags (EVE) */
/** */
/**************************************************************************/
/**************************************************************************/
#define TX_SOURCE_CODE
/* Include necessary system files. */
#include "tx_api.h"
#include "tx_thr.h"
#include "tx_tim.h"
#include "tx_eve.h"
/**************************************************************************/
/* */
/* FUNCTION RELEASE */
/* */
/* _tx_event_flags_set PORTABLE C */
/* 3.0f */
/* AUTHOR */
/* */
/* William E. Lamie, Express Logic, Inc. */
/* */
/* DESCRIPTION */
/* */
/* This function sets the specified flags in the event group based on */
/* the set option specified. All threads suspended on the group whose */
/* get request can now be satisfied are resumed. */
/* */
/* INPUT */
/* */
/* group_ptr Pointer to group control block */
/* flags_to_set Event flags to set */
/* set_option Specified either AND or OR */
/* operation on the event flags */
/* */
/* OUTPUT */
/* */
/* TX_SUCCESS Always returns success */
/* */
/* CALLS */
/* */
/* _tx_timer_deactivate Deactivate timer routine */
/* _tx_thread_resume Resume thread service */
/* _tx_thread_system_return Return to system routine */
/* */
/* CALLED BY */
/* */
/* Application Code */
/* */
/* RELEASE HISTORY */
/* */
/* DATE NAME DESCRIPTION */
/* */
/* 12-31-1996 William E. Lamie Initial Version 3.0 */
/* 07-04-1997 William E. Lamie Corrected a problem setting */
/* event flags from ISRs with */
/* thread preemption, resulting*/
/* in version 3.0a */
/* 11-11-1997 William E. Lamie Modified comment(s), */
/* resulting in version 3.0b. */
/* 03-01-1998 William E. Lamie Corrected problem building */
/* the satisfied thread list */
/* when two or more threads */
/* are satisfied, resulting in */
/* 01-01-1999 William E. Lamie Corrected problem setting */
/* events from ISRs while the */
/* same event flag group is */
/* being set from a thread, */
/* resulting in version 3.0e. */
/* 11-01-1999 William E. Lamie Modified comment(s), */
/* added logic to track events,*/
/* added logic the optimizes */
/* processing when a single */
/* thread is suspended on the */
/* event flag group, resulting */
/* in version 3.0f. */
/* */
/**************************************************************************/
UINT _tx_event_flags_set(TX_EVENT_FLAGS_GROUP *group_ptr, ULONG flags_to_set,
UINT set_option)
{
TX_INTERRUPT_SAVE_AREA
REG_1 UINT status; /* Return status */
REG_2 TX_THREAD *thread_ptr; /* Working thread pointer */
REG_3 TX_THREAD *next_thread_ptr; /* Next thread in satisfied list */
REG_4 TX_THREAD *satisfied_list; /* Event satisfied list pointer */
REG_5 TX_THREAD *last_satisfied; /* Last satisfied pointer */
TX_THREAD *suspended_list; /* Temporary copy of suspend list*/
ULONG suspended_count; /* Number of suspended threads */
ULONG current_event_flags; /* Current event flags */
UINT get_option; /* Suspended thread's get option */
/* Disable interrupts to remove the semaphore from the created list. */
TX_DISABLE
/* Log this kernel call. */
TX_EL_EVENT_FLAGS_SET_INSERT
/* Determine how to set this group's event flags. */
if (set_option & TX_EVENT_FLAGS_AND_MASK)
{
/* "AND" the flags into the current events of the group. */
group_ptr -> tx_event_flags_current =
group_ptr -> tx_event_flags_current & flags_to_set;
/* There is no need to check for any suspended threads since no
new bits are set. */
TX_RESTORE
return(TX_SUCCESS);
}
else
{
/* "OR" the flags into the current events of the group. */
group_ptr -> tx_event_flags_current =
group_ptr -> tx_event_flags_current | flags_to_set;
}
/* Determine if there are any threads suspended on the event flag group. */
if (group_ptr -> tx_event_flags_suspension_list)
{
/* Determine if there is just a single thread waiting on the event
flag group. */
if (group_ptr -> tx_event_flags_suspended_count == 1)
{
/* Single thread waiting for event flags. Bypass the multiple thread
logic. */
/* Setup thread pointer. */
thread_ptr = group_ptr -> tx_event_flags_suspension_list;
/* Determine if this thread's get event flag request has been met. */
if (thread_ptr -> tx_suspend_option & TX_EVENT_FLAGS_AND_MASK)
{
/* All flags must be present to satisfy request. */
if ((group_ptr -> tx_event_flags_current & thread_ptr -> tx_suspend_info) ==
thread_ptr -> tx_suspend_info)
/* Yes, all the events are present. */
status = TX_SUCCESS;
else
/* No, not all the events are present. */
status = TX_NO_EVENTS;
}
else
{
/* Any of the events will satisfy the request. */
if (group_ptr -> tx_event_flags_current & thread_ptr -> tx_suspend_info)
/* Yes, one or more of the requested events are set. */
status = TX_SUCCESS;
else
/* No, none of the events are currently set. */
status = TX_NO_EVENTS;
}
/* Was the suspended thread's event request satisfied? */
if (status == TX_SUCCESS)
{
/* Yes, resume the thread and apply any event flag
clearing. */
/* Return the actual event flags that satisfied the request. */
*((ULONG *) thread_ptr -> tx_additional_suspend_info) =
group_ptr -> tx_event_flags_current;
/* Determine whether or not clearing needs to take place. */
if (thread_ptr -> tx_suspend_option & TX_EVENT_FLAGS_CLEAR_MASK)
{
/* Yes, clear the flags that satisfied this request. */
group_ptr -> tx_event_flags_current =
group_ptr -> tx_event_flags_current & ~(thread_ptr -> tx_suspend_info);
}
/* Clear the suspension information in the event flag group. */
group_ptr -> tx_event_flags_suspension_list = TX_NULL;
group_ptr -> tx_event_flags_suspended_count = 0;
/* Clear cleanup routine to avoid timeout. */
thread_ptr -> tx_suspend_cleanup = TX_NULL;
/* Temporarily disable preemption. */
_tx_thread_preempt_disable++;
/* Restore interrupts. */
TX_RESTORE
/* Deactivate the timeout timer if necessary. */
if (thread_ptr -> tx_thread_timer.tx_list_head)
{
/* Deactivate the thread's timeout timer. */
_tx_timer_deactivate(&(thread_ptr -> tx_thread_timer));
}
else
{
/* Clear the remaining time to ensure timer doesn't get activated. */
thread_ptr -> tx_thread_timer.tx_remaining_ticks = 0;
}
/* Put return status into the thread control block. */
thread_ptr -> tx_suspend_status = TX_SUCCESS;
/* Resume thread. */
if (_tx_thread_resume(thread_ptr))
/* Preemption is required, transfer control back to
system. */
_tx_thread_system_return();
/* Return successful status. */
return(TX_SUCCESS);
}
else
{
/* Flags of single suspended thread were not satisfied. */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -