FreeRTOS Semaphore | FreeRTOS Ten

Table of contents

illustrate:

1. Semaphore

1.1. Introduction to semaphores

1.2. Semaphore characteristics

2. Binary semaphore

2.1. Introduction to binary semaphores

2.2. Obtain and release binary semaphore functions

2.3. Binary semaphore usage process and related API functions

2.4. Create a binary semaphore function to understand

2.5. Understanding the release of binary semaphore

2.6. Obtain understanding of binary semaphore

3. Counting semaphore

3.1. Introduction to counting semaphores

3.2. Applicable occasions for counting semaphores

3.3. Create a counting semaphore function

3.4. Get the current numerical size function of the semaphore

3.5. Release and acquisition of counting semaphore

4. Priority flipping

4.1. What is priority flipping?

4.2. Reasons for priority flipping

4.3. Solve priority flipping

5. Mutually exclusive semaphore

5.1. What is a mutually exclusive semaphore?

5.2. What is priority inheritance?


illustrate:

About the content:

1) The following contents are mostly conceptual understanding and step analysis

2) There is no personal sample code yet. The official sample code of FreeRTOS is used.

3) If you want to transplant the code for testing, please look elsewhere. There is no personal sample code for testing in the following content.

About others:

1) Operating system: win 10

2) Platform: keil 5 mdk

3) Language: c language

4) Board: STM32 series transplanted to FreeRTOS

1. Semaphore

1.1. Introduction to semaphores

        1) Semaphores are a mechanism to solve synchronization problems and can achieve orderly access to shared resources.

        2) The number of semaphore resources represents the number of shared resources (called a count value, a count value greater than 0 indicates that there are semaphore resources)

        3) Releasing the semaphore means giving up shared resources, and the count value is +1 (because there are too many vacancies in the shared resources)

        4) Obtaining the semaphore indicates occupying shared resources, and the count value is -1 (because there are fewer vacancies in the shared resources)

        5) The calculated value of the semaphore is limited: limit the maximum value. When the maximum value is limited to 1-->it is a binary semaphore; if the maximum value is not 1-->it is a counting semaphore.

1.2. Semaphore characteristics

        1) It only stores the count value and cannot store other data; to create a semaphore, you only need to allocate the semaphore structure

        2) When releasing the semaphore, it cannot be blocked and the count value is +1. When the count value reaches the maximum value, failure is returned.

        3) Get the semaphore, the count value is -1, when there are no resources, you can block

       

2. Binary semaphore

2.1. Introduction to binary semaphores

        1) The essence of a binary semaphore is a queue with a queue length of 1, so the queue can only exist in two situations: empty or full. This is the meaning of binary value.

        2) Binary semaphores are usually used for mutual exclusion access or task synchronization. They are similar to mutual exclusion semaphores, but binary semaphores may cause priority flipping problems, so binary semaphores are mostly used for task synchronization.

2.2. Obtain and release binary semaphore functions

        1) Release the binary semaphore function: xSemaphoreGive (in task), xSemaphoreGiveFromISR (in interrupt)

        2) Get the binary semaphore function: xSemaphoreTake (in task), xSemaphoreTakeFromISR (in interrupt)

        3) Give is equivalent to setting the flag to "full" --> equivalent to 1, and Take is equivalent to setting the flag to "empty" --> equivalent to 0

2.3. Binary semaphore usage process and related API functions

        1) First create a binary semaphore --> release the binary semaphore --> obtain the binary signal

        2) Related API functions, as shown in Figure 1 below:

 figure 1

2.4. Create a binary semaphore function to understand

Function name: SemaphoreHandle_t xSemaphoreCreateBinary (void)

Or use the create queue function and substitute different parameters, as shown in Figure 2 below:

figure 2

return value:

The return value is NULL, which means: creation failed

The return value is, other values, indicating: the handle of the binary signal is returned successfully when created.

2.5. Understanding the release of binary semaphore

Function name: BaseType_t xSemaphoreGive(xSemaphore)

parameter:

xSemaphore, meaning: the semaphore handle to be obtained

2.6. Obtain understanding of binary semaphore

Function name: BaseType_t xSemaphoreTake(xSemaphore, xBlockTime)

parameter:

xSemaphore, meaning: the semaphore handle to be obtained

xBlockTime, meaning: blocking time

return value:

pdTRUE, meaning: Obtaining the semaphore successfully

pdFALSE, meaning: timeout, failure to obtain semaphore

3. Counting semaphore

3.1. Introduction to counting semaphores

        A counting semaphore is equivalent to a queue with a queue length greater than 1, so a counting semaphore can accommodate multiple resources, which is determined when the counting semaphore is created.

3.2. Applicable occasions for counting semaphores

        1) Event counting: When each event occurs, the event processing function releases the counting semaphore (count value + 1), and other tasks will obtain the counting semaphore (count value - 1). This situation is usually when creating Set initial value to 0;

        2) Resource management: The semaphore represents the number of effective resources. The task must first obtain the semaphore (semaphore count value - 1) before it can obtain resource control. When the count value is 0, it means that there are no available resources. When the task has used up the resources Afterwards, the semaphore must be released (count value + 1). When the semaphore is created, the count value should be greater than the maximum number of resources.

3.3. Create a counting semaphore function

Function name: xSemaphoreCreateCounting(uxMaxCount, uxlnitalCount)

3.4. Get the current numerical size function of the semaphore

Function name: xSemaphoreGetCount(xSemaphore)

3.5. Release and acquisition of counting semaphore

        The same binary semaphore, no further explanation.

        

4. Priority flipping

4.1. What is priority flipping?

        High-priority tasks are executed slowly, and low-priority tasks are executed first. Priority flipping is very common in preemptive kernels, but priority flipping is not allowed in real-time operating systems, because priority flipping will destroy the expected allowed order of tasks, which may lead to unknown serious consequences.

4.2. Reasons for priority flipping

        1) Suppose there are three tasks A, B, and C. Task A has the highest priority (among ABC tasks, the same below), task B has the middle priority, and task C has the lowest priority; both task A and task C are binary values. The semaphore is applied for; Task B performs other functions (such as printing information)

        2) Task C is created first, so C runs first (task A is just ready at this time, and task B is not ready at this time). Task A also applies for a binary semaphore, but task C is already occupied at this time, and task A cannot apply for it. , can only be blocked and wait; at this time, task B is ready. Because task B does not apply for a binary semaphore and has a higher priority than task C, task B preempts task C; at this time, task A will take priority. level > task B priority, but task B runs first;

        3) High-priority tasks are blocked by low-priority tasks, causing high-priority tasks to be delayed in scheduling. But other medium-priority tasks can grab CPU resources. From the phenomenon, it seems that medium-priority tasks have higher priority than high-priority tasks.

4.3. Solve priority flipping

        1) Priority inheritance (mutually exclusive semaphore)

        2) Priority ceiling

5. Mutually exclusive semaphore

5.1. What is a mutually exclusive semaphore?

        A mutually exclusive semaphore is actually a binary semaphore with priority inheritance. A binary semaphore is most suitable for synchronization applications. Mutually exclusive semaphores are suitable for applications that require mutually exclusive access.

5.2. What is priority inheritance?

        When a mutex semaphore is being held by a low-priority task, if a high-priority task also attempts to obtain the mutex semaphore, the high-priority task will be blocked. However, this high-priority task will have its priority raised to the same priority as itself.

important point:

        1) Mutex semaphores cannot be used in interrupt service functions. Reasons: 1. Mutex semaphores have a task priority inheritance mechanism, but interrupts are not tasks and have no task priorities, so mutex semaphores can only be used for tasks. , cannot be used in interrupt service functions; 2. Interrupt service functions cannot set the blocking time to enter the blocking state because they have to wait for the mutually exclusive semaphore.

        2) When creating a mutually exclusive semaphore, the semaphore will be actively released once.

Guess you like

Origin blog.csdn.net/qq_57663276/article/details/128942339