logo elektroda
logo elektroda
X
logo elektroda

ESP32 FreeRTOS: Connecting edp_http_client to UART with uart_echo Example

dondu 1944 32
ADVERTISEMENT
Treść została przetłumaczona polish » english Zobacz oryginalną wersję tematu
  • #1 17981210
    dondu
    Moderator on vacation ...
    Hi.

    I'm dabbling in ESP32 and starting to adopt FreeRTOS. My goal is to connect the edp_http_client examples to the UART. I am attaching the whole project below.

    For now, I've created a simple program based on uart_echo to see how to call several different processes (cutting out everything that involves uart). In other words, I used the uart_echo example template to test FreeRTOS.

    Unfortunately I had already fallen down on implementing the first process:

    Code: C / C++
    Log in, to see the code
    .

    The above program resets itself after a single correct execution as can be seen in this log:

    Code: HTML, XML
    Log in, to see the code
    .

    In the third from the end line you can see that my_task executed correctly once, but then there was a reboot due to:

    Code: HTML, XML
    Log in, to see the code
    .

    What am I doing wrong?
  • ADVERTISEMENT
  • Helpful post
    #2 17981248
    khoam
    Level 42  
    dondu wrote:
    What am I doing wrong?
    .
    In the FreeRTOS documentation it states: " Tasks are normally implemented as an infinite loop, and must never attempt to return or exit from their implementing function. "
    Your my_task () function should therefore look like this, for example:
    Code: C / C++
    Log in, to see the code
    .
    Source .
  • Helpful post
    #3 17981260
    Anonymous
    Level 1  
  • #4 17981686
    dondu
    Moderator on vacation ...
    After your comments, I added a delete shuffle and added a second task. Both increase the global variable while I moved the loop to the app_main() function:

    Code: C / C++
    Log in, to see the code
    .

    The result is:

    Quote:
    I (10441) RTOS_LOG: b=300
    I (10441) RTOS_LOG: c=300
    I (10541) RTOS_LOG: b=302
    I (10541) RTOS_LOG: c=302
    I (10641) RTOS_LOG: b=304
    I (10641) RTOS_LOG: c=304
    I (10741) RTOS_LOG: b=306
    I (10741) RTOS_LOG: c=306
    I (10841) RTOS_LOG: b=308
    I (10841) RTOS_LOG: c=308
    I (10941) RTOS_LOG: b=310
    I (10941) RTOS_LOG: c=310
    .
    Why is it that although the variable length is global the results are every 2?
  • ADVERTISEMENT
  • #5 17981783
    khoam
    Level 42  
    Below is the solution to the problem, and now read about semaphores and accessing global variables from FreeRTOS tasks :) .
    Code: C / C++
    Log in, to see the code
    .
  • ADVERTISEMENT
  • #6 17981879
    Anonymous
    Level 1  
  • #7 17981917
    khoam
    Level 42  
    stmx wrote:
    I don't know what the app_main is , but if it's something you prefer from the main after schedular starts - then it's wrong. After schedular starts in min there should be nothing because this code should not execute.
    .
    Another "I don't know, but I'll comment" style statement. Please refer to the ESP-IDF documentation, where it is described how the app_main is constructed.

    stmx wrote:
    In further shuffle they can exit via return. This cannot be the case.
    .
    This can be the case and is correct. The task is deleted. Please take a look at the example from the FreeRTOS documentation: https://www.freertos.org/implementing-a-FreeRTOS-task.html

    stmx wrote:
    I see that you are trying to invent your own RTOS governed by its own laws.
    .
    stmx wrote:
    Nobody does it that way anyway.

    Please keep these kinds of puppyish remarks to the participants https://www.kickstarter.com/projects/16738888...enerator-debugger-multimeter-and-muc/comments

    Added after 1 [hour] 14 [minutes]:

    stmx wrote:
    Additionally, deleting shuffles does not release the memory used by the task. This has to be done "manually" (of course if the task allocated something dynamically)
    .
    And if it does not allocate (as in the case of the code shown in post #4) then this (releasing memory) is done automatically during the Idle task.

    Added after 1 [minute]:

    stmx wrote:
    Tape deletion itself is optional in freeRTOS
    .
    That is, you may or may not do this depending on what you want to do e.g. in the case of ESP32 such a restart is required to reassign a task to another core.

    Added after 50 [seconds]:

    stmx wrote:
    In this case you must ensure that only one thread has exclusive access to the variable.
    .
    This is why the mutex was used in the code in post #5 - xSemaphoreCreateMutex().

    Added after 1 [hour] 9 [minutes]: .

    An alternative way to use a mutex in this case is to use the atomic type atomic_int :
    Code: C / C++
    Log in, to see the code
    .
  • ADVERTISEMENT
  • #8 17982242
    dondu
    Moderator on vacation ...
    Is everything OK now?

    Code: C / C++
    Log in, to see the code
    .

    The result is correct because my_task runs every second and my_task_2 runs every 5 seconds:

    Code: HTML, XML
    Log in, to see the code
    .
  • #9 17982270
    khoam
    Level 42  
    dondu wrote:
    The result is correct because my_task runs every second and my_task_2 runs every 5 seconds:
    .
    So the code should also be correct ;) .
    You have changed the strategy: you no longer create shuffles in app_main every time, i.e. in the "normal" way :) .
    In the function assigned to tasks, vTaskDelete(NULL) is redundant at the moment, unless you exit the while(1) loop with e.g. some break.
  • #10 17982304
    dondu
    Moderator on vacation ...
    khoam wrote:
    Code should also be therefore correct ;)
    .
    I meant whether it complies with FreeRTOS rules :) .

    khoam wrote:
    Delete(NULL) is currently redundant, unless you exit the while(1) loop with e.g. some break.

    Yes, yes, I read the link you pointed to vTaskDelete().

    If I needed one task to pause the other for a while, what would need to be done?
  • #11 17982328
    Anonymous
    Level 1  
  • Helpful post
    #12 17982329
    khoam
    Level 42  
    dondu wrote:
    If I needed one task to suspend the work of another for a while, what would need to be done?
    .
    Simply via vTaskSuspend() : https://www.freertos.org/a00130.html

    More "elegantly" by using xTaskNotifyGive() and ulTaskNotifyTake(), but this is a bit more difficult:
    https://www.freertos.org/RTOS-task-notifications.html

    dondu wrote:
    What I meant was whether FreeRTOS compliant
    .
    I don't want to answer that question, because there are as many "rules" in the Forum as there are participants :)
  • #13 17982353
    Anonymous
    Level 1  
  • #14 17982381
    dondu
    Moderator on vacation ...
    I reworked app_main() adding a handle when creating my_task_2 and in my_task I added pausing my_task_2 and restarting it.

    Code: C / C++
    Log in, to see the code
    .

    Result correct:

    Code: HTML, XML
    Log in, to see the code
    .

    The next step is to integrate the UARTU and WiFi client.
  • #15 17982383
    khoam
    Level 42  
    stmx wrote:
    this won't work because the task you want to stop has to block itself while waiting for notifications
    .
    That's why I wrote about using ulTaskNotifyTake() - please quote in full and read with understanding.

    Added after 2 [minutes]:

    dondu wrote:
    Result correct:
    .
    It is OK.
  • #16 17982387
    Anonymous
    Level 1  
  • #17 17982391
    khoam
    Level 42  
    stmx wrote:
    Tell me how you stop another notification task elegantly?
    .
    I won't directly stop another task with a notification, but I can cause the target task, upon receiving such a notification, to "pause" itself for a period of time specified in the notification sent - this is what the Author of the thread asked about in post #10.

    Added after 23 [minutes]: .

    I think it won't be long before the Author of the thread himself starts using notifications to determine the shuffle stop time, as soon as he faces the fact that the xTaskAbortDelay() function is not implemented in the FreeRTOS version for ESP32.
  • #18 17982542
    Anonymous
    Level 1  
  • #19 17982690
    khoam
    Level 42  
    stmx wrote:
    I don't think that's what it's about though .
    .
    Exactly what it is about, but the way of interpretation remains divergent and let it stay that way.
  • #20 17982782
    dondu
    Moderator on vacation ...
    Thanks to your help, currently:
    - one task receives data from UART1 while showing what it has received on the same UART,
    - a second task sends data to the database via http request using the POST method, showing one by one what it does in the monitor,
    - the third test increments the variable by 1 and shows its value also in the monitor.
    I deactivate the other two tasks for the duration of the http request service.

    Now I need to add timekeeping. With FreeRTOS, can xTaskGetTickCount() be used for this task, or something else?

    PS. I have changed the topic title as it no longer corresponds to its content :) .
  • #22 17982790
    Anonymous
    Level 1  
  • #23 17982793
    dondu
    Moderator on vacation ...
    Yes, of course I know there are timers in ESP32, but for now I'm concentrating on getting to know FreeRTOS hence the reason I'm asking about it.
    I'm currently using xTaskGetTickCount(), but will familiarise myself with what you've provided.
  • #24 17982808
    Anonymous
    Level 1  
  • #25 17982820
    dondu
    Moderator on vacation ...
    For the time being, I want to count down time intervals of about 15 minutes. This is needed because every such time the data is to be sent to the database. I wrote "approximately" because the tolerance can be as short as ±1 minute.
  • #26 17982825
    khoam
    Level 42  
    stmx wrote:
    This callback, in turn, must notify the task.
    .
    The soft timer does not need to notify task. Only the timer handler is passed in the callback, and the action it further calls does not have to be related to the FreeRTOS task.

    Added after 1 [minute]: .

    dondu wrote:
    For now I want to count down time intervals of about 15 minutes. This is needed because every such time the data is to be sent to the database
    .
    It all depends on what you want to happen after this countdown of the set time. If you want to send some data to the database, the callback in the soft timer will be appropriate.
  • #27 17982863
    Anonymous
    Level 1  
  • #28 17982869
    khoam
    Level 42  
    stmx wrote:
    If it is supposed to be just waiting and so to speak there is no unblock vTaskDelay( xDelay );
    .
    The callback in the soft timer can also unblock the task by sending an appropriate notification.
  • #29 17982871
    dondu
    Moderator on vacation ...
    Around the clock measurements are taken and averaged, and sent to the base every 15 minutes.
    I will also use Software Timers to get to know them :) .
  • #30 17982912
    Anonymous
    Level 1  

Topic summary

The discussion revolves around integrating the edp_http_client with UART on the ESP32 platform using FreeRTOS. The user initially faced challenges in task management and synchronization while implementing a simple program based on the uart_echo example. Responses highlighted the importance of maintaining tasks in an infinite loop, using vTaskDelete for task cleanup, and employing semaphores for safe access to shared variables. The user successfully created multiple tasks that increment a global variable and log its value, while also managing task suspension and resumption. The conversation also touched on using FreeRTOS software timers for timekeeping and data transmission intervals, with suggestions to utilize queues for task synchronization.
Summary generated by the language model.
ADVERTISEMENT