ÍNDICE DE CONTEÚDO
- Primeiros Passos com o ESP32 e o NuttX
- Blink LED no ESP32 com o RTOS NuttX
- LVGL no ESP32 com o RTOS Apache NuttX
- Interpretador LUA com NuttX
- Executando NuttX em um ESP32 emulado com QEMU
- NuttX: Criando (ou Copiando!) uma Aplicação para o NuttX
- NuttX: Usando o Simulador para Testes e Debugging de Aplicações
Este artigo compõe a série Primeiros Passos com o ESP32 e o Apache NuttX. Uma série cujo objetivo é apresentar um overview do Sistema Operacional de Tempo Real Apache NuttX e prover instruções para utilizar o Apache NuttX no ESP32.
Caso você esteja iniciando no universo Apache NuttX, é recomendada a leitura deste artigo, no qual Sara Monteiro explica o processo de preparação do ambiente de desenvolvimento e descreve os passos necessários para compilar o Apache NuttX e fazer o upload do firmware para a memória Flash do ESP32.
Neste artigo, como o repositório oficial do QEMU não tem suporte ao ESP32, compilaremos o fork da Espressif do QEMU, configurar o NuttX para funcionar com o emulador e compilar um exemplo para demonstração. Vale notar que, apesar de existir uma variação do QEMU com suporte ao ESP32 desenvolvida pela Espressif, a empresa não oferece suporte oficial ao QEMU.
O que é QEMU ?
QEMU (de Quick EMUlator) é um software open source criado por Fabrice Bellard para a criação de ambientes de virtualização e emulação.
Seminário Linux Embarcado 2024: Evento Presencial em São Paulo
Participe do Seminário Linux Embarcado 2024 em São Paulo. Conhecimento técnico, palestras, workshops e oportunidade de networking com profissionais experientes.
Em emulações, seu principal objetivo é executar sistemas operacionais e aplicações desenvolvidas para outra plataforma de hardware. Por exemplo, executar um software criado para a plataforma ARM em um computador baseado em x86.
Já em virtualizações, o QEMU emula dispositivos e instruções privilegiadas utilizando módulos de kernel (KQEMU ou KVM) e o ambiente de máquina virtual provido pelo sistema operacional. É tipicamente utilizado para executar o sistema Windows em computadores utilizando Linux.
Caso deseje saber mais, visite a página oficial do projeto.
Por quê utilizar QEMU ?
Uma das principais vantagens da utilização do QEMU é a possibilidade de testar um software sendo desenvolvido sem precisar adquirir o hardware necessário para executá-lo.
Além disso, outras vantagens incluem a depuração de problemas sem precisar de um conversor JTAG/Serial e a possibilidade de emulação com mais memória que no módulo físico correspondente.
Instalação
Pré-requisitos
Assumiremos aqui que o ambiente de desenvolvimento com Apache NuttX já esteja configurado conforme o passo a passo descrito no primeiro artigo da série utilizando o sistema Ubuntu 20.04 LTS. Além disso, assegure-se de que os repositórios nuttx e nuttx-apps estejam atualizados.
1 2 3 4 |
cd ~/nuttxspace/nuttx git pull origin master cd ~/nuttxspace/apps git pull origin master |
Primeiramente, precisamos instalar alguns pacotes necessários para a compilação do QEMU:
1 |
sudo apt install git libglib2.0-dev libfdt-dev libpixman-1-dev zlib1g-dev ninja-build libgcrypt-dev python3 |
Agora podemos prosseguir com o download do fork da aplicação QEMU. Nesse tutorial, clonaremos o repositório na pasta esp-qemu dentro do diretório home do usuário:
1 |
git clone https://github.com/espressif/qemu ~/esp-qemu |
Com esses passos, temos tudo o que precisamos para a compilação do QEMU com suporte a processadores com arquitetura Xtensa.
Compilação
Com os arquivos preparados para a configuração e compilação, podemos configurar o sistema de compilação para selecionar as funcionalidades necessárias para o funcionamento do ESP32 (caso deseje saber mais sobre as opções de configurações disponíveis, execute ./configure --help
dentro da pasta esp-qemu):
1 2 3 4 5 6 7 |
cd ~/esp-qemu ./configure --target-list=xtensa-softmmu \ --enable-gcrypt \ --enable-debug --enable-sanitizers \ --disable-strip --disable-user \ --disable-capstone --disable-vnc \ --disable-sdl --disable-gtk |
Após o processo de configuração ser concluído, podemos compilar a aplicação para gerar o executável do QEMU com suporte ao ESP32:
1 |
ninja -C build |
Após concluída esta etapa, será gerado o executável qemu-system-xtensa
na pasta build. Com o QEMU instalado, precisamos configurar nosso sistema NuttX para funcionar em conjunto com o QEMU.
Configuração do RTOS NuttX
Agora precisamos configurar a nossa aplicação para ter suporte ao QEMU. Como o emulador requer que as partições da memória estejam em um arquivo só, precisamos habilitar a configuração de fusão dos arquivos binários em apenas um.
Primeiramente, garanta que não exista nenhuma configuração aplicada no sistema NuttX:
1 2 |
cd ~/nuttxspace/nuttx make distclean |
Em seguida, podemos selecionar uma aplicação para ser compilada. Utilizaremos a aplicação NuttShell como exemplo a ser emulado.
1 |
./tools/configure.sh esp32-devkitc:nsh |
Para a execução no emulador QEMU, precisamos alterar algumas opções de configuração. Acesse o menu de configuração:
1 |
make menuconfig |
Dentro do menu, navegue para Board Selection e selecione a opção ESP32 binary image for QEMU. Salve e saia do menu.
Iremos, agora, gerar a imagem do sistema NuttX com a aplicação NuttShell para ser executada no emulador:
1 |
make ESPTOOL_BINDIR=../esp-bins -j |
Caso os passos tenham sido seguidos corretamente, a mensagem Generated: nuttx.merged.bin (QEMU compatible)
deverá ser exibida no fim da compilação.
Execução de Aplicações
Para executarmos nossa aplicação, precisamos voltar na pasta onde se encontra nosso executável do QEMU e rodá-lo com as configurações corretas para o ESP32:
1 2 3 4 |
cd ~/esp-qemu/build ./qemu-system-xtensa -nographic \ -machine esp32 \ -drive file=~/nuttxspace/nuttx/nuttx.merged.bin,if=mtd,format=raw |
Caso tudo tenha ocorrido com sucesso, a aplicação será executada no terminal em um ESP32 emulado pelo QEMU:
Para encerrar a aplicação, aperte Ctrl-A e em seguida a tecla X.
Depuração usando GDB
Podemos também executar o emulador com o servidor do GDB ativo para podermos fazer debug no programa sendo executado. Para isso, precisamos primeiro instalar o GDB para o ESP32:
1 2 3 4 5 6 |
sudo apt install python2.7 libpython2.7-dev wget -qO- https://github.com/espressif/binutils-gdb/releases/download/esp-gdb-v12.1_20221002/xtensa-esp-elf-gdb-12.1_20221002-x86_64-linux-gnu.tar.gz | tar -xvz sudo mv xtensa-esp-elf-gdb/ /opt/xtensa/ echo "export PATH=\$PATH:/opt/xtensa/xtensa-esp-elf-gdb/bin" >> ~/.bashrc echo "export QEMU_XTENSA_CORE_REGS_ONLY=1" >> ~/.bashrc source ~/.bashrc |
Agora podemos executar o QEMU esperando por uma conexão do GDB para debug:
1 2 3 |
./qemu-system-xtensa -nographic -s -S \ -machine esp32 \ -drive file=~/nuttxspace/nuttx/nuttx.merged.bin,if=mtd,format=raw |
A emulação não será iniciada até uma conexão do GDB ser realizada. Para isso, executamos em um outro terminal o seguinte comando para executar o debugger:
1 2 3 4 |
xtensa-esp32-elf-gdb ~/nuttxspace/nuttx/nuttx \ -ex "target remote :1234" \ -ex "monitor system_reset" \ -ex "tb app_main" |
Com o GDB conectado, é possível adicionar breakpoints e watches para debug. Para continuar a emulação, basta executar o comando continue ou c.
Para uma depuração mais a fundo, não se esqueça de habilitar as opções de debug desejadas no menuconfig do NuttX.
Considerações Finais
Nesse tutorial você viu como instalar e utilizar o QEMU, executar o sistema NuttX em um ESP32 emulado e utilizar ferramentas de depuração no mesmo.
Para saber mais sobre as limitações de emular o ESP32 utilizando o QEMU ou possui alguma dúvida, acesse a wiki do fork.
Referências
Site Oficial QEMU: https://www.qemu.org/
Wiki QEMU Espressif: https://github.com/espressif/qemu/wiki
Documentação ESP-IDF: https://docs.espressif.com/projects/esp-idf/en/latest/esp32/api-guides/tools/idf-tools.html
Documentação NuttX: https://nuttx.apache.org/docs/latest/index.html
Bacana! Funcionou tranquilo.
Isso também me lembrou a possibilidade de emular esp32 com nuttx também no picsimlab (qemu-fork integrado).
Tutorial perfeito Lucas! Parabens, me ajudou bastante aqui!