{"id":1119,"date":"2020-11-03T17:41:00","date_gmt":"2020-11-03T17:41:00","guid":{"rendered":"http:\/\/visiorob.com.br\/?p=1119"},"modified":"2022-09-04T14:11:41","modified_gmt":"2022-09-04T14:11:41","slug":"rtos-progamacao-de-tempo-real-para-sistemas-embarcados","status":"publish","type":"post","link":"https:\/\/visiorob.com.br\/index.php\/2020\/11\/03\/rtos-progamacao-de-tempo-real-para-sistemas-embarcados\/","title":{"rendered":"RTOS- Progama\u00e7\u00e3o de tempo real para sistemas embarcados"},"content":{"rendered":"\n<p>Rtos:  sistema multi-tarefas para sistemas embarcados<br>Quando se torna interessante o uso de freeRtos ?  <br>         O sistema operacinal  de tempo real, se torna uma solu\u00e7\u00e3o quando sofremos com a necessidade de se ter multi-tarefas em embarcados, devido necessidade de se ter diversos sensores e atuadores trabalhando em tarefas especificas. Assim, o controle se torna algo dif\u00edcil de se realizar simult\u00e2neamente ,deixando a programa\u00e7\u00e3o e sincroniza\u00e7\u00e3o complexa. Dessa forma, fazendo o uso do sistema operacional de tempo real vantajosa.<br>O que \u00e9 um sistema operacional ?<br>Funciona como um conjunto de softwares que criam um ambiente multi-tarefas e tamb\u00e9m \u00e9 uma abstra\u00e7\u00e3o entre software e hardware, com gerenciamento de recursos internos. Os principais itens de um sistema operacional s\u00e3o :<br>Kernel : N\u00facleo do sistema operacional, sendo uma camada de adstra\u00e7\u00e3o entre os software e hardware para o gerenciamento de mem\u00f3ria e gerenciamento de processos<br>Scheduler:  \u00c9 software  do sistema que decide quais tarefas ser\u00e3o executadas. Por prioridade ou em caso de prioridade iguais o software tenta dividir o tempo entre as tarefas.<br>Tarefas: S\u00e3o pequenos programas. Cada tarefa pode desempenhar algo totalmente diferente das outras ou iguais com partilha de recursos. S\u00e3o nos programas que iremos dividir nosso c\u00f3digo em partes, deixando que o scheduler as execute com todas as devidas import\u00e2ncias.<br>Qual a finalidade dos RTOS?<br> Tendo  em vista que nos RTOS o tempo de resposta \u00e9 mais importante do que a capacidade de executar diversas tarefas simultaneamente. Mesmo que n\u00e3o seja imediato o \u201c\u2019 real-time\u201d, deve ser previs\u00edvel dependendo da forma que seu sistema funciona.  As tarefas tem tempos extipulados  para serem executas, logo chamadas de \u201cTime Critical\u201d. Logo, sendo indispens\u00e1vel para os embarcados, que necessitam fazer tarefas simult\u00e2neas sem que uma atrase a outra.<br><\/p>\n\n\n\n<p>Esbo\u00e7ando alguns recursos<\/p>\n\n\n\n<p>&nbsp;Fun\u00e7\u00e3o das \u201ctaks\u201d(tarefas):<\/p>\n\n\n\n<p>As taks do freeRTOS, s\u00e3o equivalente aos programas de um computador, aonde dentro da fun\u00e7\u00e3o main() tem um loop infinito que pede op\u00e7\u00f5es ao usu\u00e1rio, respondendo a cada op\u00e7\u00e3o com a execu\u00e7\u00e3o de um trecho de c\u00f3digo espec\u00edfico, e depois voltando a uma nova intera\u00e7\u00e3o do loop. Logo, e poss\u00edvel chegar que , embora tenha varias op\u00e7\u00f5es do que fazer, apenas uma delas e feitas por vez, em um sequ\u00eancia de instru\u00e7\u00f5es. A fun\u00e7\u00e3o da task tem o aspecto de uma fun\u00e7\u00e3o main(), com um loop infinito em seu n\u00facleo, evidenciando que ela executa sem precisar se importar em cooperar com as outras fun\u00e7\u00f5es e tarefas que possam existir. Ser\u00e1 o pr\u00f3prio sistema operacional que tratar\u00e1 de parar momentaneamente a execu\u00e7\u00e3o do c\u00f3digo da task para dar chance a outra task.<\/p>\n\n\n\n<p>Sem\u00e1foro( semaphore):<\/p>\n\n\n\n<p>Como j\u00e1 expecifica&nbsp; o pr\u00f3prio nome, os sem\u00e1foros coordenam a execu\u00e7\u00e3o entre as task. Sem que haja necessariamente mais dados associados. Necessitando apenas o contexto associado pelo programador ao sem\u00e1foro.<\/p>\n\n\n\n<p>Tipo de sem\u00e1foro:<\/p>\n\n\n\n<p>&nbsp;De exclus\u00e3o m\u00fatua, chamado de mutex, ele age com o contexto de que so uma das tasks pode agir esta ocorrendo. E que todas as demais que pretendem atuar naquele contexto est\u00e3o exclu\u00eddas, como em um cruzamento de ruas com sem\u00e1foro.<\/p>\n\n\n\n<p>temos os sem\u00e1foros de contadores, que permite que diversas tasks e pontos do c\u00f3digo possam alocar o sem\u00e1foro, decrementando um valor at\u00e9 que chegue a zero, quando n\u00e3o ser\u00e1 mais poss\u00edvel aloc\u00e1-lo.<\/p>\n\n\n\n<p>Temporiza\u00e7\u00e3o:<\/p>\n\n\n\n<p>&nbsp;&nbsp;Alem do c\u00f3digo executar as tasks, pode-se utilizar fun\u00e7\u00f5es que s\u00e3o executadas de tempo em tempos, sem um loop interno apartir do m\u00f3dulo timer. Este m\u00f3dulo coloca as fun\u00e7\u00f5es definidas em um fila e as executa em intervalos regulares ou em uma \u00fanica vez, ap\u00f3 uma temporiza\u00e7\u00e3o.<\/p>\n\n\n\n<p>&nbsp;Logo,&nbsp; para controlar o timeout \u00e9 necess\u00e1rio apenas ativar um chamada de determinada fun\u00e7\u00e3o a cada x segundos, por exemplo.<\/p>\n\n\n\n<p>&nbsp;Usando um exemplo que vem na biblioteca do freeRTOS no Arduino.<\/p>\n\n\n\n<p>Nome do exemplo: Blink_AnalogRead<\/p>\n\n\n\n<p>Como encontrar: abrir o&nbsp; IDE Arduino depois de instalado( se estiver usando Windows 10 da para baixar pela Microsoft store) depois de ter baixado o arquivo do freeRTOS e colocado na pasta libraries do Arduino. Basta apenas, abrir o Arduino IDE ir em arquivos, exemplos, ir at\u00e9 exemplos de bibliotecas personalizadas, e abrir o exemplo aqui proposto.<\/p>\n\n\n\n<p>#include &lt;Arduino_FreeRTOS.h&gt;<\/p>\n\n\n\n<p>void TaskBlink( void *pvParameters );<\/p>\n\n\n\n<p>void TaskAnalogRead( void *pvParameters );<\/p>\n\n\n\n<p>void setup() {<\/p>\n\n\n\n<p>&nbsp; Serial.begin(9600);<\/p>\n\n\n\n<p>&nbsp; while (!Serial) {<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; ;<\/p>\n\n\n\n<p>&nbsp; }<\/p>\n\n\n\n<p>&nbsp; xTaskCreate(<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; TaskBlink<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; ,&nbsp; &#8220;Blink&#8221;&nbsp;&nbsp;<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; ,&nbsp; 128&nbsp;<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; ,&nbsp; NULL<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; ,&nbsp; 2&nbsp;<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; ,&nbsp; NULL );<\/p>\n\n\n\n<p>&nbsp; xTaskCreate(<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; TaskAnalogRead<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; ,&nbsp; &#8220;AnalogRead&#8221;<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; ,&nbsp; 128<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; ,&nbsp; NULL<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; ,&nbsp; 1&nbsp;<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; ,&nbsp; NULL );<\/p>\n\n\n\n<p>}<\/p>\n\n\n\n<p>void loop()<\/p>\n\n\n\n<p>{<\/p>\n\n\n\n<p>}<\/p>\n\n\n\n<p>void TaskBlink(void *pvParameters)<\/p>\n\n\n\n<p>{<\/p>\n\n\n\n<p>&nbsp; (void) pvParameters;<\/p>\n\n\n\n<p>&nbsp; pinMode(LED_BUILTIN, OUTPUT);<\/p>\n\n\n\n<p>&nbsp; for (;;)<\/p>\n\n\n\n<p>&nbsp; {<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; digitalWrite(LED_BUILTIN, HIGH);&nbsp;<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; vTaskDelay( 1000 \/ portTICK_PERIOD_MS );<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; digitalWrite(LED_BUILTIN, LOW);&nbsp;&nbsp;&nbsp;<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; vTaskDelay( 1000 \/ portTICK_PERIOD_MS );<\/p>\n\n\n\n<p>&nbsp; }<\/p>\n\n\n\n<p>}<\/p>\n\n\n\n<p>void TaskAnalogRead(void *pvParameters)&nbsp; \/\/ This is a task.<\/p>\n\n\n\n<p>{<\/p>\n\n\n\n<p>&nbsp; (void) pvParameters;<\/p>\n\n\n\n<p>&nbsp; for (;;)<\/p>\n\n\n\n<p>&nbsp; {<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; int sensorValue = analogRead(A0);<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; Serial.println(sensorValue);<\/p>\n\n\n\n<p>&nbsp;&nbsp;&nbsp; vTaskDelay(1);<\/p>\n\n\n\n<p>&nbsp; }<\/p>\n\n\n\n<p>}<\/p>\n\n\n\n<p>Ap\u00f3s tiras alguns coment\u00e1rios apenas para simplificar a demonstra\u00e7\u00e3o e esbo\u00e7ar mais ou menos o que deve se achar l\u00e1 no Arduino.<\/p>\n\n\n\n<p>&nbsp;Algumas analizes desse software:&nbsp; &nbsp;Na primeira linha vemos o #include &lt;Arduino_FreeRTOS.h&gt;, que \u00e9 a header padr\u00e3o para freeRTOS, comando padr\u00e3o m\u00ednimo para o uso do rtos no Arduino, com ele pode se ter as defini\u00e7\u00f5es mais b\u00e1sicas, que permitem a cria\u00e7\u00e3o e funcionamento das tasks. Se for necess\u00e1rio utilizar outros recursos, ser\u00e1 necess\u00e1rio usar os arquivos header necess\u00e1rios para a sua necessidade especifica.<\/p>\n\n\n\n<p>Logo ap\u00f3s vem os prot\u00f3tipos das fun\u00e7\u00f5es tasks( que cria as tasks):<\/p>\n\n\n\n<p>TaskBlink( void *pvParameters );<\/p>\n\n\n\n<p>TaskAnalogRead( void *pvParameters );<\/p>\n\n\n\n<p>Seus nomes s\u00e3o sugestivos para suas a\u00e7\u00f5es, sempre retornam void e recebem um ponteiro gen\u00e9rico para void.<\/p>\n\n\n\n<p>Seguindo a ordem , vem a parte de cria\u00e7\u00e3o das tasks na fun\u00e7\u00e3o setup(), s\u00e3o criadas duas&nbsp; tasks usando a fun\u00e7\u00e3o xTaskCreate, cada uma atribui alguns par\u00e2metros, com destaque para a primeira que \u00e9 o nome da fun\u00e7\u00e3o task<\/p>\n\n\n\n<p>&nbsp;Logo ap\u00f3s, se encontra a fun\u00e7\u00e3o loop vazia, onde poderia estar o c\u00f3digo de piscar o led( l\u00ea uma entrada anal\u00f3gica), esta vazia. Justamente porque agora as opera\u00e7\u00f5es ficar\u00e3o principalmente nas taks e quando necess\u00e1rio nas interrup\u00e7\u00f5es.<\/p>\n\n\n\n<p>A seguir, temos uma inicializa\u00e7\u00e3o no pino ,linha 75 do programa no Arduino, referente as primeiras linhas das task, j\u00e1 que o pino \u00e9 assunto dela e s\u00f3 ela ir\u00e1 us\u00e1-lo. Esse c\u00f3digo roda apenas uma vez. Entre as linhas 77 e 83 existe o loop que pisca o led, primeiro acende , espera, apaga e volta a acender. Agora, olhando a segunda fun\u00e7\u00e3o task come\u00e7a na linha 86 indo ate a 107, na linha 102 temos a leitura da entrada anal\u00f3gica para a vari\u00e1vel sensorValue que \u00e9 colocada dentro do loop, na 104 o valor \u00e9 enviado para o serial, notasse que aqui n\u00e3o foi necess\u00e1rio usar um sem\u00e1foro pois apenas uma task envia coisas para o serial. Se voc\u00ea usar um recurso com apenas uma task, ok sem problemas, mas se usa-lo em v\u00e1rios lugares ir\u00e1 precisar controlar o acesso a ele.<\/p>\n\n\n\n<p>&nbsp;Se quiser rodar o programa no arduino utilizar um led com o catodo ligado ao GND e um resistor de &nbsp;10k\u03a9 no anodo ao pino 12<\/p>\n\n\n\n<p>Acesse as publica\u00e7\u00f5es do grupo VISIOROB no Instagram \/<a href=\"https:\/\/www.instagram.com\/visiorob\/\">https:\/\/www.instagram.com\/visiorob\/<\/a>. N\u00e3o se esque\u00e7a as outras mat\u00e9rias dispon\u00edveis no blog \/<a href=\"https:\/\/visiorob.com.br\/index.php\/grupo-visiorob\/\">https:\/\/visiorob.com.br\/index.php\/grupo-visiorob\/<\/a>. <\/p>\n\n\n\n<figure class=\"wp-block-image size-large\"><img loading=\"lazy\" decoding=\"async\" width=\"750\" height=\"749\" src=\"https:\/\/visiorob.com.br\/wp-content\/uploads\/2020\/11\/WhatsApp-Image-2020-11-03-at-14.39.26.jpeg\" alt=\"\" class=\"wp-image-1288\" srcset=\"https:\/\/visiorob.com.br\/wp-content\/uploads\/2020\/11\/WhatsApp-Image-2020-11-03-at-14.39.26.jpeg 750w, https:\/\/visiorob.com.br\/wp-content\/uploads\/2020\/11\/WhatsApp-Image-2020-11-03-at-14.39.26-300x300.jpeg 300w, https:\/\/visiorob.com.br\/wp-content\/uploads\/2020\/11\/WhatsApp-Image-2020-11-03-at-14.39.26-150x150.jpeg 150w\" sizes=\"auto, (max-width: 750px) 100vw, 750px\" \/><\/figure>\n\n\n\n<p>Para ficar por dentro de tudo que acontece! Enfim, nos vemos na pr\u00f3xima.<\/p>\n","protected":false},"excerpt":{"rendered":"<div class=\"mh-excerpt\"><p>Rtos: sistema multi-tarefas para sistemas embarcadosQuando se torna interessante o uso de freeRtos ? O sistema operacinal de tempo real, se torna uma solu\u00e7\u00e3o quando <a class=\"mh-excerpt-more\" href=\"https:\/\/visiorob.com.br\/index.php\/2020\/11\/03\/rtos-progamacao-de-tempo-real-para-sistemas-embarcados\/\" title=\"RTOS- Progama\u00e7\u00e3o de tempo real para sistemas embarcados\">[&#8230;]<\/a><\/p>\n<\/div>","protected":false},"author":24,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"om_disable_all_campaigns":false,"_monsterinsights_skip_tracking":false,"_monsterinsights_sitenote_active":false,"_monsterinsights_sitenote_note":"","_monsterinsights_sitenote_category":0,"footnotes":""},"categories":[1],"tags":[],"class_list":["post-1119","post","type-post","status-publish","format-standard","hentry","category-uncategorized"],"aioseo_notices":[],"_links":{"self":[{"href":"https:\/\/visiorob.com.br\/index.php\/wp-json\/wp\/v2\/posts\/1119","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/visiorob.com.br\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/visiorob.com.br\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/visiorob.com.br\/index.php\/wp-json\/wp\/v2\/users\/24"}],"replies":[{"embeddable":true,"href":"https:\/\/visiorob.com.br\/index.php\/wp-json\/wp\/v2\/comments?post=1119"}],"version-history":[{"count":4,"href":"https:\/\/visiorob.com.br\/index.php\/wp-json\/wp\/v2\/posts\/1119\/revisions"}],"predecessor-version":[{"id":1289,"href":"https:\/\/visiorob.com.br\/index.php\/wp-json\/wp\/v2\/posts\/1119\/revisions\/1289"}],"wp:attachment":[{"href":"https:\/\/visiorob.com.br\/index.php\/wp-json\/wp\/v2\/media?parent=1119"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/visiorob.com.br\/index.php\/wp-json\/wp\/v2\/categories?post=1119"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/visiorob.com.br\/index.php\/wp-json\/wp\/v2\/tags?post=1119"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}