0% acharam este documento útil (0 voto)
298 visualizações371 páginas

Embedded Linux Slides PDF

Enviado por

rogerberaldi
Direitos autorais
© © All Rights Reserved
Levamos muito a sério os direitos de conteúdo. Se você suspeita que este conteúdo é seu, reivindique-o aqui.
Formatos disponíveis
Baixe no formato PDF, TXT ou leia on-line no Scribd
0% acharam este documento útil (0 voto)
298 visualizações371 páginas

Embedded Linux Slides PDF

Enviado por

rogerberaldi
Direitos autorais
© © All Rights Reserved
Levamos muito a sério os direitos de conteúdo. Se você suspeita que este conteúdo é seu, reivindique-o aqui.
Formatos disponíveis
Baixe no formato PDF, TXT ou leia on-line no Scribd
Você está na página 1/ 371

Linux embarcado

Embedded Labworks

Por Sergio Prado. São Paulo, Março de 2019


® Copyright Embedded Labworks 2004-2019. All rights reserved.
Embedded Labworks

SOBRE ESTE DOCUMENTO


✗ Este documento é baseado no material de treinamento
disponibilizado pela Bootlin em:
https://bootlin.com/training/embedded-linux/
✗ Este documento é disponibilizado sob a Licença Creative
Commons BY-SA 3.0.
http://creativecommons.org/licenses/by-sa/3.0/legalcode

✗ Os fontes deste documento estão disponíveis em:


http://e-labworks.com/treinamentos/linux/source
Embedded Labworks

SOBRE O INSTRUTOR
✗ Sergio Prado tem mais de 20 anos de experiência em desenvolvimento de software
para sistemas embarcados, atuando principalmente em projetos com Linux
embarcado, Android embarcado e sistemas operacionais de tempo real.

✗ É sócio da Embedded Labworks, onde atua com consultoria, treinamento e


desenvolvimento de software para sistemas embarcados.
https://e-labworks.com

✗ É ativo na comunidade de sistemas embarcados no Brasil, sendo um dos criadores do


site Embarcados, administrador do grupo sis_embarcados no Google Groups, além de
manter um blog pessoal sobre assuntos da área.
https://sergioprado.org

✗ É colaborador de alguns projetos de software livre, incluindo o Buildroot e o kernel


Linux.
Embedded Labworks

AGENDA DO TREINAMENTO
✗ DIA 1: Introdução e arquitetura de sistemas com Linux embarcado,
toolchain, bootloader e kernel.

✗ DIA 2: Rootfs, módulos do kernel, sistemas de arquivo e


ferramentas de build de sistemas Linux.

✗ DIA 3: Desenvolvimento de aplicações, licenças de software,


aplicações gráficas, ferramentas de desenvolvimento, depuração
de sistemas Linux.
Embedded Labworks

PRÉ-REQUISITOS
✗ Usuário nível básico de distribuições GNU/Linux.

✗ Terminal de comandos (ls, cp, cat, grep, find, vi, etc).

✗ Conhecimentos básicos em linguagem C/C++.

✗ Conhecimento básicos de hardware e sistemas embarcados (GPIO,


PWM, I2C, SPI, etc).
Embedded Labworks

AMBIENTE DE LABORATÓRIO
/opt/labs/ Ambiente de laboratório
dl/ Aplicações e pacotes open-source
que serão usados durante as
atividades de laboratório
docs/ Documentação
guides/ Guias de consulta (shell, vi, etc)
hardware/ Documentação do hardware
training/ Slides e atividades de laboratório
videos/ Vídeos
ex/ Exercícios de laboratório
tools/ Ferramentas de uso geral
Embedded Labworks

ORIENTAÇÕES GERAIS
✗ Pergunte...

✗ Expresse seu ponto de vista...

✗ Troque experiências...

✗ Ajude...

✗ Participe!
Embedded Labworks

Linux embarcado

Introdução
Embedded Labworks

OS 3 MARCOS
✗ 1970: Engenheiros da Bell Labs, liderados por Ken Thompson e
Dennis Ritchie, criam o sistema operacional UNIX.

✗ 1983: Richard Stallman, projeto GNU e o conceito de software livre.


Começa o desenvolvimento do gcc, gdb, glibc e outras ferramentas
importantes.

✗ 1991: Linus Torvalds, projeto do kernel Linux, um sistema


operacional UNIX-like. Em conjunto com o projeto GNU, nasce o
sistema operacional GNU/Linux.
Embedded Labworks

Em 1991...

”I'm doing a (free) operating system (just a


hobby, won't be big and professional like
gnu) for 386(486) AT clones. This has been
brewing since april, and is starting to get
ready. I'd like any feedback on things
people like/dislike in minix, as my OS
resembles it somewhat (same physical
layout of the file-system (due to practical
reasons) among other things).”
Embedded Labworks

MAIS DE 25 ANOS DEPOIS...


Embedded Labworks

VÍDEO (OS 20 ANOS DO LINUX)


Embedded Labworks

O KERNEL
✗ Linux é um kernel!
https://www.kernel.org/

✗ As distribuições Linux (Ubuntu, Fedora, Debian, Slackware, etc)


integram o kernel Linux com diversas bibliotecas e aplicações.

✗ O correto é chamar estas distribuições de sistemas operacionais


GNU/Linux.

✗ Linux embarcado é o uso do kernel Linux e de diversos outros


componentes de software em sistemas embarcados.
Embedded Labworks

PRINCIPAIS CARACTERÍSTICAS
✗ Código aberto e livre de royalties.

✗ Portável: suporte para 24 diferentes arquiteturas (versão 4.19).

✗ Escalável: o mesmo kernel roda em roteadores, relógios, celulares,


servidores e supercomputadores!

✗ Estável: capaz de rodar por muito tempo sem precisar de um único


reboot.

✗ Recursos ”infinitos” disponíveis na Internet.


Embedded Labworks

REUSO DE COMPONENTES
✗ Uma das principais vantagens do uso do Linux em sistemas embarcados:
reuso de componentes!

✗ A comunidade open-source já fornece implementações prontas para as


principais funcionalidades dos projetos: suporte a hardware, protocolos
de rede, bibliotecas gráficas, criptografia, etc.

✗ Suporte a hardware. Ex: Linux foi o primeiro kernel a suportar os


padrões USB 2.0, USB 3.0, Bluetooth, etc.

✗ Desenvolvimento rápido baseado em componentes prontos.

✗ Foco no seu produto, core business, time-to-market!


Embedded Labworks

BAIXO CUSTO
✗ Sem royalties: use e abuse de software livre!

✗ Se sua aplicação usa apenas software livre, incluindo as


ferramentas de desenvolvimento, seu custo de software é zero! Seu
único custo será a aquisição de know-how.

✗ Permite que você possa investir mais no hardware e em


treinamento para sua equipe!
Embedded Labworks

CONTROLE TOTAL
✗ Trabalhando com software livre, você tem o código-fonte de todos
os componentes do seu sistema.

✗ Liberdade para modificar, otimizar, depurar, melhorar.

✗ Não fica preso à prioridade que fornecedores ou terceiros darão ao


seu projeto.

✗ Total controle do software do seu projeto!


Embedded Labworks

QUALIDADE
✗ Muitos componentes open source são usados em milhares de
sistemas ao redor do mundo.

✗ Normalmente a qualidade é bem melhor que a de softwares


proprietários (muitas pessoas olhando o mesmo problema!).

✗ Permite uma base sólida para seu projeto.

✗ É claro, nem todo software aberto é de boa qualidade, portanto


tome cuidado. Procure sempre aqueles mais usados em outros
projetos e com uma comunidade mais ativa.
Embedded Labworks

SUPORTE DA COMUNIDADE
✗ Componentes open-source são desenvolvidos por uma comunidade
de desenvolvedores e usuários.

✗ As comunidades podem te fornecer suporte de alta qualidade. Você


tem contato inclusive com os principais desenvolvedores dos
projetos.

✗ Em muitos casos o suporte é melhor comparado ao suporte


prestado por empresas comerciais, mas você precisa saber como
usar corretamente o suporte da comunidade.

✗ Permite você resolver os problemas mais rapidamente!


Embedded Labworks

MITOS
✗ Mito 1: ”Linux is Free”.
✗ Linux não é grátis, Linux é livre! Do 2o. parágrafo da GPL: ”When we
speak of free software, we are refering to freedom, not price”.

✗ Mito 2: ”Não consigo proteger a propriedade intelectual do meu


produto”.
✗ Consegue sim, basta tomar alguns cuidados com licenças de
software!
Embedded Labworks

Linux embarcado

Arquitetura básica
Embedded Labworks

ARQUITETURA BÁSICA

Aplicação Aplicação

Biblioteca Biblioteca

Toolchain Biblioteca C

Linux kernel

Bootloader

Hardware
Embedded Labworks

COMPONENTES DO SISTEMA
✗ Hardware: seu produto!

✗ Bootloader: responsável pela inicialização básica do hardware,


carregamento e execução do kernel Linux.

✗ Kernel Linux: Núcleo do sistema operacional. Gerencia CPU, memória e I/O,


exportando serviços para as bibliotecas e aplicações.

✗ Rootfs: sistema de arquivos principal.


✗ Biblioteca C: interface entre o kernel e as aplicações do usuário.
✗ Bibliotecas e aplicações do usuário.

✗ Toolchain: conjunto de ferramentas para gerar os binários do sistema.


Embedded Labworks

HARDWARE

Aplicação Aplicação

Biblioteca Biblioteca

Toolchain Biblioteca C

Linux kernel

Bootloader

Hardware
Embedded Labworks

HARDWARE
Embedded Labworks

CPU
✗ Suporta mais de 20 arquiteturas diferentes (x86, ia64, ARM, ARM64,
PowerPC, MIPS, RISC-V, MicroBlaze, ARC, etc).

✗ 32/64 bits: não foi feito para microcontroladores de 8 e 16 bits!

✗ Originalmente projetado para CPUs com MMU (Memory Management Unit).

✗ O projeto uClinux foi criado para utilizar o Linux em sistemas sem MMU.
https://en.wikipedia.org/wiki/MClinux

✗ Boa parte do uClinux já foi integrado à árvore oficial do kernel,


possibilitando o uso do Linux mainline em diversas CPUs sem MMU
(m68k, ARM 7, ARM Cortex M3/M4, H8/300 da Hitachi, ADI Blackfin, etc).
Embedded Labworks

MEMÓRIA RAM E ARMAZENAMENTO


✗ Um sistema Linux bem básico pode funcionar com 8MB de RAM (ou
até menos!), mas o ideal para começar é em torno de 32MB.

✗ Suporta armazenamento em memória flash NAND e NOR, disco


rígido, cartão SD/MMC, etc.

✗ Um sistema bem básico pode funcionar com 2M de armazenamento


(ou até menos!).
Embedded Labworks

COMUNICAÇÃO
✗ O Linux suporta muitos barramentos comuns em sistemas
embarcados: I2C, SPI, CAN, 1-wire, SDIO, USB, etc.

✗ E também os principais protocolos de rede: Ethernet, Wi-Fi,


Bluetooth, CAN, IPv4, IPv6, TCP, UDP, etc.

✗ Se o barramento ou protocolo não possuir restrições de licença, é


bem provável que esteja implementado no kernel.
Embedded Labworks

CRITÉRIOS PARA SELEÇÃO


✗ Certifique-se de que o hardware seja suportado pelo kernel Linux e
por um bootloader open-source.

✗ Suporte nas versões oficiais dos projetos (bootloader e kernel) é


melhor: maior qualidade e novas versões disponíveis.

✗ A diferença entre uma plataforma suportada na árvore oficial do


kernel e outra plataforma não suportada de forma oficial pode
trazer grandes consequências em termos de custo e tempo de
desenvolvimento!
Embedded Labworks

TOOLCHAIN

Aplicação Aplicação

Biblioteca Biblioteca

Toolchain Biblioteca C

Linux kernel

Bootloader

Hardware
Embedded Labworks

TOOLCHAIN
✗ Conjunto de ferramentas de programação usadas para gerar
determinado produto, seja um software ou mesmo um sistema
completo.

✗ Quando a plataforma de desenvolvimento (host) é diferente da


plataforma alvo (target), chamamos o toolchain de cross-compiling
toolchain.
Embedded Labworks

TOOLCHAIN (cont.)

Código-fonte
Host
Toolchain nativo Cross-compiling toolchain
x86

Binário x86 Binário ARM Target


x86 ARM
Embedded Labworks

COMPONENTES DO TOOLCHAIN
✗ Compilador (gcc).

✗ Assembler e Linker (binutils).

✗ Biblioteca C padrão (glibc, uclibc-ng, musl, etc).

✗ Arquivos de cabeçalho do kernel.

✗ Depurador (gdb).
Embedded Labworks

TOOLCHAINS PRONTOS
✗ Linaro (ARM):
https://wiki.linaro.org/WorkingGroups/ToolChain

✗ Sourcery Codebench (ARM, MIPS, PPC):


https://www.mentor.com/embedded-software/sourcery-tools/sourcery-codebench

✗ Bootlin (ARM, MIPS, PPC, x86, etc):


https://toolchains.bootlin.com/

✗ Scratchbox (ARM e x86):


http://www.scratchbox.org/
Embedded Labworks

FERRAMENTAS OPEN SOURCE


✗ Crosstool-ng:
https://crosstool-ng.github.io

✗ Buildroot:
https://buildroot.org/

✗ Yocto Project:
https://www.yoctoproject.org/
Embedded Labworks

SISTEMA LINUX EMBARCADO

Aplicação Aplicação

Biblioteca Biblioteca

Toolchain Biblioteca C

Linux kernel

Bootloader

Hardware
Embedded Labworks

SISTEMA LINUX EMBARCADO (NA FLASH)


Bootloader

Kernel

Rootfs

Memória flash
Embedded Labworks

BOOTLOADER

Aplicação Aplicação

Biblioteca Biblioteca

Toolchain Biblioteca C

Linux kernel

Bootloader

Hardware
Embedded Labworks

BOOTLOADER
✗ O bootloader tem basicamente duas responsabilidades:
✗ Inicializar o hardware.
✗ Carregar e executar o sistema operacional.

✗ Normalmente, o bootloader provê outras funcionalidades para


facilitar o desenvolvimento do sistema, incluindo:
✗ Passagem de parâmetros para o kernel.
✗ Rotinas de diagnóstico de hardware.
✗ Ler e escrever em dispositivos de armazenamento (memória flash,
cartão SD, etc).
✗ Boot pela rede.
Embedded Labworks

PRINCIPAIS BOOTLOADERS
✗ x86:
✗ LILO
✗ Grub
✗ Syslinux

✗ ARM, MIPS, PPC e outras arquiteturas:


✗ U-Boot
✗ Barebox
✗ Redboot
Embedded Labworks

KERNEL

Aplicação Aplicação

Biblioteca Biblioteca

Toolchain Biblioteca C

Linux kernel

Bootloader

Hardware
Embedded Labworks

ALGUMAS CARACTERÍSTICAS DO KERNEL


✗ Gerenciar a execução dos processos e controlar o acesso à
memória e a dispositivos de I/O.

✗ Conceito de kernel space x user space.

✗ Interface de user space com kernel space via chamadas do sistema


(system calls).

✗ Acesso ao hardware via arquivos de dispositivo.

✗ Gerenciamento dinâmico de módulos do kernel.


Embedded Labworks

EXEMPLO DE SYSTEM CALL


Embedded Labworks

ROOTFS

Aplicação Aplicação

Biblioteca Biblioteca

Toolchain Biblioteca C

Linux kernel

Bootloader

Hardware
Embedded Labworks

COMPONENTES BÁSICOS
✗ Biblioteca do sistema (glibc, uClibc-ng, musl, dietlibc, etc).

✗ Mecanismo de inicialização (sysvinit, systemd, etc).

✗ Bibliotecas e aplicações.
Embedded Labworks

APLICAÇÕES PARA EMBARCADOS


✗ Dropbear: cliente e servidor SSH (~110K).

✗ Lighttpd: servidor web (~200K).

✗ SDL: biblioteca gráfica (~1,4MB).

✗ SQLite: Banco de dados relacional (~250KB).


Embedded Labworks

BUSYBOX
✗ Pacote que combina versões mais leves de ferramentas UNIX em
um único binário, otimizado por tamanho.

✗ Geralmente as ferramentas são mais limitadas em termos de


funcionalidades quando comparadas às originais.

✗ É considerado o canivete suíço de sistemas embarcados com Linux!


Embedded Labworks

BUSYBOX – TUDO ISSO EM ~1MB!


addgroup, adduser, adjtimex, ar, arp, arping, ash, awk, basename, bbconfig, bbsh, brctl, bunzip2, busybox,
bzcat, bzip2, cal, cat, catv, chat, chattr, chcon, chgrp, chmod, chown, chpasswd, chpst, chroot, chrt, chvt,
cksum, clear, cmp, comm, cp, cpio, crond, crontab, cryptpw, cttyhack, cut, date, dc, dd, deallocvt, delgroup,
deluser, depmod, devfsd, df, dhcprelay, diff, dirname, dmesg, dnsd, dos2unix, dpkg, dpkg_deb, du,
dumpkmap, dumpleases, e2fsck, echo, ed, egrep, eject, env, envdir, envuidgid, ether_wake, expand, expr,
fakeidentd, false, fbset, fbsplash, fdflush, fdformat, fdisk, fetchmail, fgrep, find, findfs, fold, free, freeramdisk,
fsck, fsck_minix, ftpget, ftpput, fuser, getenforce, getopt, getsebool, getty, grep, gunzip, gzip, halt, hd,
hdparm, head, hexdump, hostid, hostname, httpd, hush, hwclock, id, ifconfig, ifdown, ifenslave, ifup, inetd,
init, inotifyd, insmod, install, ip, ipaddr, ipcalc, ipcrm, ipcs, iplink, iproute, iprule, iptunnel, kbd_mode, kill,
killall, killall5, klogd, lash, last, length, less, linux32, linux64, linuxrc, ln, load_policy, loadfont, loadkmap,
logger, login, logname, logread, losetup, lpd, lpq, lpr, ls, lsattr, lsmod, lzmacat, makedevs, man,
matchpathcon, md5sum, mdev, mesg, microcom, mkdir, mke2fs, mkfifo, mkfs_minix, mknod, mkswap,
mktemp, modprobe, more, mount, mountpoint, msh, mt, mv, nameif, nc, netstat, nice, nmeter, nohup,
nslookup, od, openvt, parse, passwd, patch, pgrep, pidof, ping, ping6, pipe_progress, pivot_root, pkill,
poweroff, printenv, printf, ps, pscan, pwd, raidautorun, rdate, rdev, readahead, readlink, readprofile, realpath,
reboot, renice, reset, resize, restorecon, rm, rmdir, rmmod, route, rpm, rpm2cpio, rtcwake, run_parts, runcon,
runlevel, runsv, runsvdir, rx, script, sed, selinuxenabled, sendmail, seq, sestatus, setarch, setconsole,
setenforce, setfiles, setfont, setkeycodes, setlogcons, setsebool, setsid, setuidgid, sh, sha1sum, showkey,
slattach, sleep, softlimit, sort, split, start_stop_daemon, stat, strings, stty, su, sulogin, sum, sv, svlogd,
swapoff, swapon, switch_root, sync, sysctl, syslogd, tac, tail, tar, taskset, tcpsvd, tee, telnet, telnetd, test,
tftp, tftpd, time, top, touch, tr, traceroute, true, tty, ttysize, tune2fs, udhcpc, udhcpd, udpsvd, umount,
uname, uncompress, unexpand, uniq, unix2dos, unlzma, unzip, uptime, usleep, uudecode, uuencode,
vconfig, vi, vlock, watch, watchdog, wc, wget, which, who, whoami, xargs, yes, zcat, zcip
Embedded Labworks

SISTEMA LINUX

“Desenvolver um sistema Linux embarcado


é como brincar de Lego!”
Embedded Labworks

BUILD SYSTEM
✗ Um build system é capaz de:
✗ Gerar o toolchain.
✗ Compilar e gerar a imagem do bootloader.
✗ Configurar, compilar e gerar a imagem do kernel.
✗ Compilar bibliotecas e aplicações, e gerar a imagem final do rootfs.
Embedded Labworks

ALGUNS BUILD SYSTEMS


✗ Proprietários:
✗ Monta Vista.
✗ Wind River.
✗ TimeSys.

✗ Open source:
✗ Buildroot.
✗ OpenEmbedded/Yocto Project.
✗ OpenWrt.
✗ PTXdist.
Embedded Labworks

OS 3 PAPÉIS DO DESENVOLVEDOR
✗ Desenvolvedor de aplicações: desenvolve aplicações Linux.

✗ Integrador: Integra todos os componentes (bootloader, kernel,


bibliotecas e aplicações) em um sistema Linux embarcado.

✗ Desenvolvedor de BSP (Board Support Package): porta o kernel e o


bootloader, desenvolve drivers para os dispositivos de hardware do
produto, etc.

Nosso foco neste treinamento: integrador e


desenvolvedor de aplicações!
Embedded Labworks

VAMOS COMEÇAR?
Embedded Labworks

Linux embarcado

Kit de desenvolvimento
Embedded Labworks

TORADEX
✗ A Toradex é uma empresa Suíça que projeta e desenvolve
computadores em módulo ou sistemas em módulo juntamente com
placas base e acessórios compatíveis para o mercado de sistemas
embarcados.

✗ Possui uma linha grande de módulos baseados nos SoCs NVIDIA


Tegra, NXP i.MX e NXP Vybrid.

✗ Possui um escritório em Valinhos/SP com suporte e estoque local.


Embedded Labworks

HENSYS
✗ A HENSYS é uma empresa brasileira, focada em desenvolvimento de hardware
de alta qualidade, oferecendo serviços de engenharia para customização de
produtos e também desenvolvimento de firmware para sistemas embarcados.

✗ Com atuação nos mercados agrícola, laboratorial, médico e industrial, possui


grande know-how no desenvolvimento de soluções com conectividade IoT.

✗ Possui fábrica própria com linha de montagem SMT automatizada e montagem


PTH para a industrialização de placas que possuam ou não a necessidade de
conformidade com a norma RoHS Lead Free (sem chumbo).
Embedded Labworks

COLIBRI IMX6DL
✗ System-on-module (SOM) da Toradex.

✗ Baseado no SOC i.MX6 DualLite da NXP,


um ARM Cortex-A9 rodando a até
996MHz.

✗ 512MB de memória RAM.

✗ 4GB de armazenamento interno (eMMC


NAND Flash).

✗ Conector no padrão SODIMM200


(memória DDR1).
Embedded Labworks

PLACA BASE ASTER


✗ Placa base compatível com todos os
módulos Colibri da Toradex.

✗ Alimentação via USB, que também provê


uma interface USB/serial.

✗ Interfaces USB Host, Ethernet, display RGB,


VGA e leitor de cartão SD.

✗ Conectores compatíveis com o Arduino


(shields) e a Raspberry Pi (capes).

✗ Barramento de 40 pinos que exporta o


acesso à diversas interfaces de I/O do SoC
(I2C, SPI, UART, GPIO, etc).
Embedded Labworks

PLACA DE EXPANSÃO IPÊ CAPE


✗ Placa desenvolvida pela Hensys em
parceria com a Toradex e a Embedded
Labworks.

✗ 1 chave, 1 botão e 2 leds conectados a


GPIOs.

✗ Trimmer conectado a um canal A/D.

✗ Buzzer conectado a um canal PWM.

✗ Expansor de GPIO MCP23S08 conectado


a um display de 7 segmentos.
Embedded Labworks

PLACA DE EXPANSÃO IPÊ CAPE (cont.)


✗ Sensor de umidade e temperatura
(SI7006).

✗ IMU (Inertial Measurement Unit) com


acelerômetro, giroscópio e compasso
(MPU-9250).

✗ Chip de criptografia ST33TPM12I2C.

✗ Microcontrolador STM32F103 conectado


ao processador via I2C e UART, com
dois leds acessíveis pelo usuário.
Embedded Labworks

REFERÊNCIAS E DOCUMENTAÇÃO
✗ A documentação do hardware está disponível no ambiente de
laboratório do treinamento em /opt/labs/docs/hardware:

SOC_imx6sdl_datasheet.pdf: datasheet do SOC.

SOM_colibri_imx6_datasheet.pdf: datasheet do SOM.

BASEBOARD_aster_datasheet.pdf: datasheet da placa base.

BASEBOARD_aster_schematics_v1.1b.pdf: esquemático da placa base.

CAPE_ipe_v1.3.pdf: esquemático da placa de expansão.

✗ Recursos na internet:
https://www.toradex.com/community/
https://community.nxp.com/
Embedded Labworks

LABORATÓRIO

Conectando e testando o target


Embedded Labworks

Linux embarcado

Toolchain
Embedded Labworks

O QUE SÃO TOOLCHAINS?


✗ Ao pé da letra, e traduzindo literalmente, toolchain é uma "corrente
de ferramentas". Na prática, é um conjunto de ferramentas de
compilação.

✗ Você se lembra do processo de compilação de um programa em C?


Ele envolve normalmente as seguintes etapas: pré-processamento,
compilação, montagem (assembler) e linkagem.

✗ Cada uma destas etapas é executada por uma ferramenta (pré-


processador, compilador, assembler e linker), e todas elas fazem
parte do toolchain.
Embedded Labworks

TIPOS DE TOOLCHAIN
✗ As ferramentas de desenvolvimento normalmente disponíveis em um
desktop GNU/Linux são chamadas de toolchain nativo.

✗ Este toolchain roda na sua máquina e compila código para ser executado
na sua máquina (normalmente x86 ou x86-64).

✗ Em um sistema embarcado normalmente é mais complicado (às vezes


até impossível) usar um toolchain nativo, porque precisamos de bastante
espaço em disco, capacidade de processamento, memória, etc.

✗ Portanto, para esta tarefa o melhor é usar um toolchain de compilação


cruzada (cross-compiling toolchain), que roda na sua plataforma de
desenvolvimento mas gera código para a plataforma alvo.
Embedded Labworks

TIPOS DE TOOLCHAIN (cont.)

Código-fonte
Host
Toolchain nativo Cross-compiling toolchain
x86

Binário x86 Binário ARM Target


x86 ARM
Embedded Labworks

COMPONENTES DO TOOLCHAIN

Compilador (GCC) Biblioteca C padrão

Binutils Headers do kernel

Debugger (GDB)

Toolchain
Embedded Labworks

COMPILADOR GCC
✗ O GCC (GNU Compiler Collection) é o compilador do projeto GNU.
https://gcc.gnu.org/

✗ Compatível com diversas linguagens de programação, incluindo C,


C++, Objective-C, Fortran, Ada, Go e D.

✗ Pode gerar código para diversas arquiteturas, incluindo ARM, AVR,


Blackfin, MIPS, PowerPC, x86, etc.

✗ O Clang do projeto LLVM é seu principal concorrente.


https://clang.llvm.org/
Embedded Labworks

BINUTILS
✗ Binutils é um conjunto de ferramentas para manipular arquivos
binários para uma arquitetura específica.
https://www.gnu.org/software/binutils/

✗ Algumas das principais ferramentas disponibilizadas pelo binutils:


✗ as: assembler.
✗ ld: linker.
✗ ar, ranlib: gerar bibliotecas estáticas (*.a).
✗ objdump, readelf, size, nm, strings: inspecionar binários.
✗ strip: remover partes não utilizadas do binário para diminuir seu
tamanho.
Embedded Labworks

BIBLIOTECA C
✗ O que é a biblioteca C?
✗ Interface entre as aplicações e o kernel. Aplicações
✗ API para o desenvolvimento de aplicações.
Biblioteca C
✗ O toolchain depende da biblioteca C, já que
ele irá linká-la com sua aplicação para
gerar os binários para a arquitetura-alvo.
Kernel
✗ Diversas bibliotecas C estão disponíveis:
glibc, uClibc-ng, musl, dietlibc, etc.
Embedded Labworks

GLIBC
✗ Biblioteca C do projeto GNU (licença LGPL).
https://www.gnu.org/software/libc/

✗ Usada em boa parte dos sistemas GNU/Linux (desktop e servidor).

✗ Projetada com foco em performance e portabilidade.

✗ Dependendo do sistema, pode não ser uma boa escolha, já que possui um
consumo considerável de espaço em disco/flash e memória RAM.

✗ Durante um tempo, existiu uma variante chamada eglibc (embedded glibc)


compatível com a glibc e com foco em sistemas embarcados.
✗ O projeto foi descontinuado porque todas as alterações feitas na eglibc já foram
integradas à glibc.
Embedded Labworks

UCLIBC-NG
✗ A uClibc-ng é mais leve e projetada para sistemas embarcados (licença LGPL).
https://uclibc-ng.org/

✗ É uma evolução (fork) da uClibc (microcontroller C library), criada originalmente


para suportar o uClinux.

✗ Altamente configurável, possui um foco maior na economia de recursos,


principalmente no espaço ocupado em disco/flash.

✗ Enquanto que um build mínimo da glibc pode ocupar em torno de 2MB, um build
da uClibc pode ocupar apenas 500KB!

✗ Alguns recursos podem não estar disponíveis na uClibc-ng (operações de ponto


flutuante, funções de tempo-real, etc).
Embedded Labworks

MUSL
✗ A musl é uma outra opção de biblioteca C para sistemas
embarcados.
https://www.musl-libc.org

✗ Leve, rápida e escrita do zero, o projeto iniciou quando o


desenvolvimento da uClibc ficou estagnado por um tempo.

✗ Liberada sob uma licença permissiva (MIT).

✗ Pode ser uma boa opção para criar binários linkados


estaticamente.
Embedded Labworks

COMPARANDO

“Hello World” compilado para ARM

Tipo de compilação glibc uClibc-ng musl

Linkagem dinâmica 8196 7268 7296

Linkagem estática
541752 139656 17212
Not stripped

Linkagem estática
414896 87676 9084
Stripped
Embedded Labworks

KERNEL HEADERS
✗ Sabemos que o toolchain depende da biblioteca C do sistema.

✗ E a biblioteca C, por sua vez, depende do kernel! Por que?


✗ Chamadas de sistema.
✗ Definições de constantes.
✗ Estruturas de dados.

✗ Por isso, para compilar a biblioteca C, o toolchain precisa dos


arquivos de cabeçalho do kernel.
Embedded Labworks

KERNEL HEADERS (EXEMPLOS)


✗ Números das chamadas de sistema em <asm/unistd.h>:
#define __NR_exit 1
#define __NR_fork 2
#define __NR_read 3


Definições de constantes em <asm-generic/fcntl.h>:
#define O_RDWR 00000002

✗ Estruturas de dados em <asm/stat.h>:


struct stat {
unsigned long st_dev;
unsigned long st_ino;
[...]
};
Embedded Labworks

ESCOLHENDO O TOOLCHAIN
✗ Existem basicamente duas soluções para selecionar o toolchain
para um projeto com Linux embarcado:
1. Utilizar um toolchain pronto, fornecido por uma empresa ou
disponibilizado pela comunidade.
2. Utilizar uma ferramenta para configurar e gerar um toolchain
customizado de acordo com as suas necessidades.
Embedded Labworks

UTILIZANDO UM TOOLCHAIN PRONTO


✗ Utilizar um toolchain pronto é uma opção:
✗ Vantagem: simples e conveniente.
✗ Desvantagem: inflexível, você não consegue otimizar o toolchain de acordo
com as suas necessidades.

✗ Possíveis escolhas:
✗ Toolchain fornecido pelo fabricante do hardware (NXP, Toradex, etc).
✗ Toolchain fornecido por empresas especializadas (Mentor Graphics, etc).
✗ Toolchain fornecido pela comunidade (Linaro, Buildroot, etc).

✗ Uma referência bem completa de toolchains em:


https://elinux.org/Toolchains
Embedded Labworks

INSTALANDO E USANDO
✗ Basta seguir o procedimento do fornecedor da solução.

✗ Normalmente, estes são os passos:


✗ Baixar e descompactar o toolchain em um diretório na sua máquina.
✗ Adicionar no PATH o diretório onde se encontram os binários:
$ export PATH=/path/to/toolchain/bin/:$PATH
✗ Compilar sua aplicação usando o toolchain:
$ PREFIX-gcc teste.c -o teste

✗ O PREFIX depende da configuração do toolchain, e permite diferenciar


toolchains nativos de toolchains de compilação cruzada.
$ arm-linux-gcc teste.c -o teste
Embedded Labworks

LABORATÓRIO

Usando um toolchain pré-compilado


Embedded Labworks

GERANDO SEU PRÓPRIO TOOLCHAIN


✗ Gerar um toolchain manualmente é uma tarefa difícil e dolorosa!
✗ É necessário estar familiarizado com o gcc.
✗ Muitos componentes para configurar e compilar.
✗ Existem depêndencias entre as versões dos componentes.
✗ Algumas plataformas necessitam que sejam aplicados patches em
alguns componentes antes de compilar.

✗ Ótimo site para os aventureiros:


http://www.linuxfromscratch.org/
Embedded Labworks

USANDO FERRAMENTAS
✗ Existem ferramentas que automatizam o processo de geração de
toolchains.

✗ Você não precisa se preocupar com o processo de geração do


toolchain, dependências, patches, etc.

✗ E por outro lado, estas ferramentas oferecem a flexibilidade de


configuração e seleção dos componentes do toolchain e de suas
versões.
Embedded Labworks

ALGUMAS FERRAMENTAS
✗ Crosstool-NG (suporta glibc, uClibc-ng, musl):
https://crosstool-ng.github.io/

✗ Buildroot (suporta glibc, uClibc-ng, musl):


https://buildroot.org/

✗ OpenEmbedded/Yocto Project (suporta glibc, musl):


https://www.yoctoproject.org
Embedded Labworks

CROSSTOOL-NG
✗ O crosstool-NG é a principal ferramenta de código-aberto
específica para a criação de toolchains.
https://crosstool-ng.github.io/

✗ Capaz de gerar toolchains para diferentes arquiteturas de


hardware, incluindo x86, x86-64, MIPS, ARM e PPC.

✗ Capaz de gerar toolchains bare metal e com suporte ao Linux.

✗ Possui a mesma interface de configuração do kernel Linux.


Embedded Labworks

CROSSTOOL-NG (cont.)
Embedded Labworks

LABORATÓRIO

Gerando um toolchain
Embedded Labworks

Linux embarcado

Bootloader
Embedded Labworks

BOOTLOADER
✗ O bootloader é o código responsável por:
✗ Inicializar o hardware (CPU, GPIO, controladora de RAM, etc).
✗ Carregar outro binário (normalmente o sistema operacional) de um
dispositivo de armazenamento para a RAM.
✗ Passar o controle da CPU para este binário.
Embedded Labworks

FUNCIONALIDADES DO BOOTLOADER
✗ Além destas funcionalidades básicas, a maioria dos bootloaders
possui uma interface de linha de comandos com diversas opções,
incluindo:
✗ Rotinas de diagnóstico de hardware.
✗ Manipulação das memórias RAM e flash.
✗ Comunicação via rede e serial.
✗ Suporte à variáveis de ambiente e execução de scripts.
✗ Passagem de parâmetros para o sistema operacional.
Embedded Labworks

BOOTLOADERS NO X86 BIOS


em ROM

✗ Plataformas x86 normalmente vem acompanhadas de uma


memória não-volátil, a BIOS.
Estágio 1
512 bytes
✗ Um programa na BIOS é executado no boot do equipamento, do disco
que faz a inicialização básica do hardware, carrega para a
memória e executa os primeiros 512 bytes do dispositivo de
boot. Estes 512 bytes também são chamados de MBR.
Estágio 2
✗ A MBR é o bootloader de 1o. estágio, que é o responsável por do disco
carregar um bootloader de 2o. estágio do disco para a RAM.

✗ O bootloader de 2o. estágio é mais completo, entende SO


sistemas de arquivo, consegue ler o sistema operacional do do disco
disco, carregar para a memória e executar.
Embedded Labworks

BOOTLOADERS NO X86 (cont.)


✗ LILO, já foi bastante utilizado, mas caiu em desuso.
https://wiki.debian.org/LILO

✗ GRUB, Grand Unified Bootloader, é o mais poderoso e o padrão


atualmente em desktops e servidores.
https://www.gnu.org/software/grub/

✗ Syslinux, mais utilizado em boot pela rede e por mídias removíveis.


https://www.syslinux.org/
Embedded Labworks

BOOT EM ARM
O SoC tem um código de boot em uma ROM interna, responsável
ROM Code
por carregar um bootloader de 1o. estágio (SPL) para uma
memória RAM interna (SRAM ou IRAM).

O SPL (Secundary Program Loader) é responsável por inicializar


SPL o hardware (CPU, DRAM, GPIOs, etc) e carregar um bootloader
de 2o. estágio para a RAM.

É um bootloader mais completo e normalmente suporta


Bootloader
sistemas de arquivo, interface USB e protocolo TCP/IP.
Responsável por carregar e executar o kernel Linux.

Linux Kernel É executado da memória RAM e assume o controle do sistema


(a partir daqui, o bootloader não existe mais).
Embedded Labworks

i.MX28 (NXP)
Código de boot em ROM iniciado quando o i.MX28 é resetado. Lê
ROM Code
as chaves de seleção do modo de boot para identificar a fonte
do boot (USB, SD/MMC, NAND, I2C, SPI, JTAG).

O SPL trabalha com o conceito de boot stream, um conjunto de


Bootlets bootlets, que são pequenos executáveis para extender o
bootloader, como o “power_prep” (configura PM) e o
“boot_prep” (configura a memória SDRAM e carrega o U-Boot).

Inicializa alguns dispositivos de hardware (rede, USB, etc).


U-Boot
Carrega a imagem do kernel na RAM e passa o controle para
ele.

Linux Kernel Roda da RAM. Assume o controle do sistema (a partir daqui, o


bootloader não existe mais).
Embedded Labworks

OMAP3530/AM35x (Texas Instruments)


Procura por imagens de boot na NAND, UART, USB e MMC, e
ROM Code
carrega para a SRAM (64KB). GPIOs podem mudar a ordem da
busca.

Roda da SRAM. Inicializa a controladora da SDRAM, NAND ou


X-Loader
MMC, e carrega o bootloader de 2o. estágio para a RAM.

Roda da RAM. Inicializa alguns dispositivos de hardware (rede,


U-Boot USB, etc). Carrega a imagem do kernel na RAM e passa o
controle para ele.

Linux Kernel Roda da RAM. Assume o controle do sistema (a partir daqui, o


bootloader não existe mais).
Embedded Labworks

LPC3250 (NXP)
Tenta o boot pela porta serial (modo de serviço), SPI,
ROM Code
barramento externo e flash NAND, carregando o código para a
SRAM (56KB).

Kickstart roda da SRAM, inicializa hardware e carrega o stage 1


Kickstart/S1L loader, um bootloader completo que possui diversas funções
para configurar o hardware. O S1L carrega o bootloader de 2o.
estágio para a RAM.

Roda da RAM. Inicializa alguns dispositivos de hardware (rede,


U-Boot
USB, etc). Carrega a imagem do kernel na RAM e passa o
controle para ele.

Linux Kernel Roda da RAM. Assume o controle do sistema (a partir daqui, o


bootloader não existe mais).
Embedded Labworks

AT91 (ATMEL)
Procura por imagens de boot em diversos dispositivos de
ROM Code
armazenamento, e carrega para a SRAM (4KB).

Roda da SRAM. Inicializa a controladora da DRAM e carrega o


AT91Bootstrap bootloader de 2o. estágio para a RAM.

Roda da RAM. Inicializa alguns dispositivos de hardware (rede,


U-Boot USB, etc). Carrega a imagem do kernel na RAM e passa o
controle para ele.

Linux Kernel Roda da RAM. Assume o controle do sistema (a partir daqui, o


bootloader não existe mais).
Embedded Labworks

i.MX5/i.MX6 (NXP)
Código de boot em ROM é iniciado no reset. Lê o registrador
ROM Code BOOT_MODE ou um conjunto de GPIOs para determinar o
dispositivo de boot (NOR/NAND, cartão SD/MMC, SATA, etc).

U-Boot SPL Uma versão mínima do U-Boot que irá inicializar o hardware
(clock, SDRAM, etc) e carregar o U-Boot completo para a RAM.

Inicializa alguns dispositivos de hardware (rede, USB, etc).


U-Boot
Carrega a imagem do kernel na RAM e passa o controle para
ele.

Linux Kernel Roda da RAM. Assume o controle do sistema (a partir daqui, o


bootloader não existe mais).
Embedded Labworks

A31 (ALLWINNER)
Código de boot em ROM é iniciado no reset. Verifica as
ROM Code interfaces de boot suportadas (NAND, SD Card, USB) para
carregar o SPL para a memória RAM interna do chip.

U-Boot SPL Uma versão mínima do U-Boot que irá inicializar o hardware
(clock, SDRAM, etc) e carregar o U-Boot completo para a RAM.

Inicializa alguns dispositivos de hardware (rede, USB, etc).


U-Boot
Carrega a imagem do kernel na RAM e passa o controle para
ele.

Linux Kernel Roda da RAM. Assume o controle do sistema (a partir daqui, o


bootloader não existe mais).
Embedded Labworks

BOOTLOADERS EM LINUX EMBARCADO


✗ O bootloader de 1o. estágio (SPL) é totalmente dependente do
hardware e cada plataforma pode ter o seu. Nosso foco é no
bootloader de 2o. estágio.

✗ Existem alguns bootloaders de código-aberto que suportam o


kernel Linux. Os dois mais conhecidos e utilizados são:
✗ U-Boot: bastante popular em ARM, mas também utilizado em outras
arquiteturas como MIPS, PPC e até x86.
https://www.denx.de/wiki/U-Boot
✗ Barebox: sucessor do U-Boot, código melhor estruturado e
desenvolvimento ativo, mas ainda com pouco suporte a hardware.
https://www.barebox.org/
Embedded Labworks

U-BOOT
✗ Bootloader open-source mais utilizado atualmente (licença GPLv2).
https://www.denx.de/wiki/U-Boot

✗ Suporta uma grande variedade de CPUs, incluindo PPC, ARM, MIPS,


Coldfire, x86, etc.

✗ Desde 2008, segue um intervalo fixo de release, onde a cada dois ou


três meses uma versão é liberada (as versões são nomeadas com o
formato YYYY.MM).

✗ Documentação disponível em:


https://www.denx.de/wiki/U-Boot/Documentation
Embedded Labworks

FUNCIONALIDADES DO U-BOOT
✗ Exibir informações do hardware (memória, periféricos, etc).

✗ Manipular a RAM (ler, escrever, comparar, testar, etc).

✗ Manipular memórias flash (ler, escrever, apagar, etc).

✗ Boot via memória flash.

✗ Boot via rede (bootp, tftp, dhcp, etc).


Embedded Labworks

FUNCIONALIDADES DO U-BOOT (cont.)


✗ Boot por interfaces SD/MMC ou USB.

✗ Entende sistemas de arquivo (fat, ext2/3, ext4, ubifs, jffs2, etc).

✗ Configuração por variáveis de ambiente e suporte à scripts.

✗ Executa código bare-metal.

✗ Carrega e executa imagens do kernel Linux.


Embedded Labworks

BAIXANDO O U-BOOT
✗ É responsabilidade do fabricante do hardware disponibilizar o código-fonte do
U-Boot (porte) para a sua plataforma.

✗ O fabricante pode fazer isso e enviar o código para a árvore principal do projeto
(mainline). Neste caso, os fontes podem ser baixados no site do projeto em:
https://www.denx.de/wiki/U-Boot

✗ Mas nem sempre o fabricante faz isso! Neste caso, o fabricante irá
disponibilizar os fontes em um outro local, provavelmente no seu site junto com
o BSP (Board Support Package) da plataforma.

✗ Portanto, consulte a documentação da sua plataforma para saber como e onde


baixar os fontes do U-Boot.
Embedded Labworks

CÓDIGO-FONTE DO U-BOOT
$ ls
api configs dts Kconfig post
arch defconfig env lib README
board disk examples Licenses scripts
cmd doc fs MAINTAINERS spl
common Documentation include Makefile test
config.mk drivers Kbuild net tools
Embedded Labworks

CONFIGURANDO O U-BOOT
✗ O U-Boot suporta diversas arquiteturas de CPU e plataformas de
hardware. Antes de compilar o U-Boot, você precisa configurá-lo
para a sua plataforma de hardware:
$ make <board_config>

✗ Substitua <board_config> pelo nome da sua plataforma de


hardware. Por exemplo, para configurar o U-Boot para o módulo
Colibri i.MX6 da Toradex:
$ make colibri_imx6_defconfig
Embedded Labworks

CONFIGURANDO O U-BOOT (cont.)


✗ Os arquivos de configuração das plataformas de hardware suportadas
pelo U-Boot estão disponíveis no diretório configs/.
$ ls configs/
10m50_defconfig
3c120_defconfig
A10-OLinuXino-Lime_defconfig
A10s-OLinuXino-M_defconfig
[...]

✗ As versões mais atuais do U-Boot também possibilitam alterar a


configuração através da ferramenta menuconfig:
$ make menuconfig
Embedded Labworks

COMPILANDO O U-BOOT
✗ Para compilar o U-Boot, basta executar o comando make passando
o prefixo do toolchain:
$ make CROSS_COMPILE=arm-linux-

✗ No final, será gerada a imagem do U-Boot para ser gravada no


target.
$ ls -l u-boot.img
-rw-rw-r-- 1 sprado sprado 323812 Mar 12 20:13 u-boot.img
Embedded Labworks

GRAVANDO O U-BOOT
✗ O processo de gravação do U-Boot pode ser feito de diferentes
formas, dependendo do target:
✗ Se o target puder iniciar por uma mídia removível (cartão SD,
pendrive, HD, etc), basta conectar o dispositivo removível na sua
máquina de desenvolvimento e gravar o U-Boot.
✗ Se o dispositivo utilizar armazenamento interno como flash NAND ou
eMMC, podem existir algumas opções, incluindo:
✗ O ROM code pode ter um monitor de boot que se comunica via
serial ou USB com uma ferramenta de gravação no PC.
✗ Interface JTAG.
Embedded Labworks

U-BOOT PROMPT
U-Boot 2018.07-g74ce0cd-dirty (Mar 04 2019 - 08:24:27 -0300)

CPU: Freescale i.MX6DL rev1.2 at 792 MHz


Reset cause: POR
I2C: ready
DRAM: 512 MiB
PMIC: device id: 0x10, revision id: 0x11
Loading Environment from MMC... OK
auto-detected panel vga-rgb
Display: vga-rgb (640x480)
In: serial_mxc
Out: serial_mxc
Err: serial_mxc
Model: Toradex Colibri iMX6 DualLite 512MB
Net: using PHY at 0
Warning: FEC (eth0) using random MAC address - 06:31:72:11:ed:a0

Hit any key to stop autoboot: 0

Colibri iMX6 >


Embedded Labworks

COMANDOS DO U-BOOT
✗ O U-Boot possui diversos comandos para manipular o hardware e o
processo de boot.

✗ Uma lista dos comandos existentes pode ser exibida com o


comando help.
> help

✗ A documentação completa dos comandos está disponível no


manual do U-Boot no site do projeto:
https://www.denx.de/wiki/DULG/Manual
Embedded Labworks

COMANDOS DO U-BOOT (cont.)


> version
U-Boot 2018.07-g74ce0cd-dirty (Mar 04 2019 - 08:24:27 -0300)

arm-linux-gcc (crosstool-NG crosstool-ng-1.23.0) 6.3.1


20170109
GNU ld (crosstool-NG crosstool-ng-1.23.0) 2.28

> bdinfo
arch_number = 0x00000000
boot_params = 0x10000100
DRAM bank = 0x00000000
-> start = 0x10000000
-> size = 0x20000000
eth0name = FEC
ethaddr = (not set)
current eth = FEC
ip_addr = 192.168.0.2
baudrate = 115200 bps
...
Embedded Labworks

COMANDOS DO U-BOOT (cont.)


> mmc info
Device: FSL_SDHC
Manufacturer ID: 3
OEM: 5344
Name: SU04G
Bus Speed: 50000000
Mode : SD High Speed (50MHz)
Rd Block Len: 512
SD version 3.0
High Capacity: Yes
Capacity: 3.7 GiB
Bus Width: 4-bit
Erase Group Size: 512 Bytes

> gpio set 9


gpio: pin 9 (gpio 9) value is 1
Warning: value of pin is still 0
Embedded Labworks

VARIÁVEIS DE AMBIENTE
✗ A configuração do bootloader e do processo de boot é feita através
de variáveis de ambiente do U-Boot.

✗ O comando printenv é capaz de imprimir o conteúdo de uma


variável ou exibir todas as variáveis existentes.

✗ Uma variável pode ser criada ou alterada com o comando setenv.

✗ Por padrão, as variáveis são armazenadas em memória. O comando


saveenv pode ser utilizado para salvar as variáveis de forma
persistente em um dispositivo de armazenamento (flash, cartão SD,
eMMC, etc).
Embedded Labworks

VARIÁVEIS DE AMBIENTE (cont.)


> printenv
arch=arm
baudrate=115200
board=colibri_imx6
board_name=colibri_imx6
board_rev=0000
boot_file=uImage
[...]

> setenv teste 1

> printenv teste


teste=1

> saveenv
Saving Environment to MMC... Writing to MMC(0)... OK
Embedded Labworks

LABORATÓRIO

Compilando e gravando o U-Boot


Embedded Labworks

Linux embarcado

Kernel Linux
Embedded Labworks

VISÃO GERAL
Aplicação Aplicação

Biblioteca Biblioteca Aplicação User space

Biblioteca C

Chamadas de sistema Notificação de eventos


Exportação de informações

Kernel

Gerenciamento do hardware Notificação de eventos

Hardware
Embedded Labworks

HISTÓRICO
✗ O kernel é um dos componentes do sistema operacional, que requer
bibliotecas e aplicações para prover funcionalidades aos usuários.

✗ Criado em 1991 pelo estudante finlandês Linus Torvalds, começou


a ser usado rapidamente como sistema operacional em projetos de
software livre.

✗ Linus Torvalds foi capaz de criar uma comunidade grande e


dinâmica de desenvolvedores e usuários ao redor do projeto.

✗ Atualmente, centenas de pessoas e empresas contribuem com o


projeto.
Embedded Labworks

COLABORAÇÃO
Embedded Labworks

ESTATÍSTICAS
✗ Estatísticas da versão 4.17:
✗ 64 dias de desenvolvimento.
✗ 1.696 desenvolvedores.
✗ 13.453 commits.
✗ 690.000 linhas adicionadas.
✗ 869.000 linhas removidas.
✗ Aproximadamente 9 commits por hora.
✗ Aproximadamente 17 linhas alteradas por minuto!
Embedded Labworks

ARQUITETURA
Embedded Labworks

GERENCIAMENTO DE PROCESSOS
✗ Um processo é um programa em execução, que possui um identificador (PID)
e está associado a um conjunto de recursos como arquivos abertos,
mapeamento de memória, etc.

✗ Um processo contém uma ou mais linhas de execução, chamadas de threads.

✗ Cada thread possui um contador de programa, uma região de stack e uma


cópia dos registradores da CPU.

✗ Sob o ponto de vista do escalonador, o kernel Linux não diferencia processos


e threads.

✗ Por este motivo, o Linux escalona threads e não processos!


Embedded Labworks

GERENCIAMENTO DE PROCESSOS (cont.)


✗ O Linux é um sistema multitasking preemptivo.

✗ Possui o conceito de classes de escalonamento, onde cada classe


possui um algoritmo que decide qual processo deve ser executado,
quando e por quanto tempo.

✗ O escalonador padrão do Linux é chamado de CFS (Completely Fair


Scheduler), onde cada tarefa recebe uma "porcentagem justa" da CPU.

✗ No CFS, a fatia de uso da CPU atribuída a cada tarefa é variável e


pode ser influenciada pelo usuário através da configuração de nice
do processo.
Embedded Labworks

GERENCIAMENTO DE PROCESSOS (cont.)


✗ O kernel Linux possui também dois escalonadores de tempo real (FIFO e RR),
que tem prioridade sobre o CFS.

✗ Mesmo assim, o Linux não pode ser considerado um sistema operacional


determinístico (em alguns trechos de código a latência para atender um
pedido de interrupção pode ser muito grande e difícil de mensurar).

✗ Existe um conjunto de patches chamado PREEMPT_RT que pode ser aplicado


ao kernel para melhorar este cenário de alta latência, permitindo o uso do
kernel em sistemas soft real-time.

✗ Uma opção para o uso do Linux em aplicações hard real-time é a utilização


de um kernel de tempo real em conjunto com o Linux (RTLinux, RTAI,
Xenomai).
Embedded Labworks

GERENCIAMENTO DE MEMÓRIA
✗ O Linux trabalha com o mecanismo de memória virtual para
gerenciar a memória do sistema.

✗ Em um sistema com memória virtual, todo o acesso à memória do


sistema é realizado através de endereços virtuais, que são
convertidos (por hardware) para endereços físicos durante o
acesso à memória do sistema.

✗ A MMU (Memory Management Unit) é o hardware que implementa o


mecanismo de memória virtual, gerenciando a memória do sistema
e fazendo a conversão entre endereços de memória físicos e
virtuais.
Embedded Labworks

MMU

Endereço Endereço
virtual físico
CPU MMU Memória
Embedded Labworks

VANTAGENS DA MMU
✗ Um sistema com MMU é capaz de prover:
✗ Maior endereçamento de memória para os processos. Em uma
arquitetura de 32 bits, os processos podem ter acesso a um
endereçamento linear de até 3G de memória virtual.
✗ SWAP: se faltar memória física, possibilita salvar e recuperar
páginas de memória do disco.
✗ Gerenciamento dinâmico da memória do processo (stack, heap, etc).
✗ Compartilhamento: os processos podem compartilhar memória
(código, dados, etc), usado por exemplo em mecanismos de IPC.
✗ Proteção: cada processo só enxerga seu espaço de endereçamento,
onde um acesso inválido gera uma exceção.
Embedded Labworks

SISTEMA DE ARQUIVO VIRTUAL


✗ O Linux é fortemente baseado em arquivos (quase tudo no sistema
é representado por um arquivo).

✗ O kernel possui uma camada chamada VFS (Virtual Filesystem) que


abstrai o acesso aos arquivos, possibilitando que rotinas de acesso
ao arquivo (open, read, write, close, etc) sejam mapeadas para
diferentes destinos.
Embedded Labworks

SISTEMA DE ARQUIVO VIRTUAL (cont.)


✗ Exemplo 1: acessando um arquivo físico em um dispositivo de
armazenamento (copiando um arquivo do HD para um pendrive):
$ cp /usr/sbin/app /mnt/pendrive/

✗ Exemplo 2: acessando um arquivo virtual (listando a estatística de


uso de memória do sistema):
$ cat /proc/meminfo

✗ Exemplo 3: acessando um dispositivo de hardware (escrevendo na


porta serial):
$ echo "Teste" > /dev/ttyS0
Embedded Labworks

VERSIONAMENTO
✗ Antes da versão 2.6:
✗ Uma árvore de versões estáveis (1.0, 2.0, 2.2, 2.4).
✗ Uma árvore de versões de desenvolvimento (2.1, 2.3, 2.5).

✗ A partir de 2003, apenas uma árvore: 2.6.X.

✗ Em 2011, a versão mudou para 3.0.

✗ Em 2015, a versão mudou para 4.0.

✗ Em 2019, a versão mudou para 5.0.


Embedded Labworks

CICLO DE RELEASE
✗ Processo de desenvolvimento a cada 3 meses aproximadamente.
✗ Merge window: 2 semanas (até sair X.Y-rc1).
✗ Bug fixing: 6 a 10 semanas (X.Y-rc2, X.Y-rc3, etc).

✗ Em aproximadamente 3 meses é liberado o release final X.Y.

✗ Para acompanhar as mudanças no kernel:


https://kernelnewbies.org/LinuxChanges
https://lwn.net/
Embedded Labworks

FONTES DO KERNEL
✗ A versão oficial do código-fonte do kernel encontra-se em:
https://www.kernel.org/

✗ Baixando os fontes por http:


$ wget https://cdn.kernel.org/pub/linux/kernel/v5.x/linux-5.0.tar.xz
$ tar xfv linux-5.0.tar.xz

✗ Baixando os fontes pelo git:


$ git clone git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
Embedded Labworks

FONTES DO KERNEL (cont.)


✗ Muitas comunidades e fabricantes de hardware podem manter
versões alternativas do kernel:
✗ Fabricantes de hardware podem manter versões específicas do
kernel com suporte às suas plataformas de referência (BSP).
✗ Comunidades podem manter versões do kernel voltadas à
arquiteturas específicas (ARM, MIPS, PPC), sub-sistemas (USB, PCI,
network), sistemas de tempo-real, etc.

✗ Portanto, consulte a documentação da sua plataforma para saber


como e onde baixar os fontes do Linux.
Embedded Labworks

FONTES DO KERNEL (cont.)


$ ls
arch Documentation ipc MAINTAINERS samples
block drivers Kbuild Makefile scripts
certs firmware Kconfig mm security
COPYING fs kernel Module.symvers sound
CREDITS include lib net tools
crypto init LICENSES README usr
Embedded Labworks

TAMANHO DOS FONTES DO KERNEL


✗ Fontes do kernel 4.19:
✗ Tamanho total: 1,1GB
✗ Arquivos: ~61.000
✗ Linhas de código-fonte: ~17.000.000

✗ Porque os fontes são tão grandes? Milhares de drivers de


dispositivo, diversos protocolos de rede, suporte a diferentes
arquiteturas e plataformas.

✗ O núcleo do kernel é bem pequeno, menos de 2% do código total!


Embedded Labworks

LICENÇA
✗ Todo o código-fonte do kernel Linux é software livre e liberado sob
a licença GPLv2.

✗ Isso significa que:


✗ Quando você receber ou comprar um equipamento com Linux
embarcado, você tem o direito de requisitar os fontes, alterá-los e
redistribuí-los!
✗ Quando você produzir um equipamento com Linux embarcado, você
precisa liberar os fontes do kernel sob as mesmas condições, sem
restrições.
Embedded Labworks

LICENÇA (cont.)
✗ Mas e os módulos do kernel?

✗ Os módulos do kernels são uma área cinza: é um trabalho derivado


do kernel ou não?
✗ A opinião geral da comunidade é de que drivers de código fechado
são ruins. Veja “Kernel Driver Statement” no link abaixo:
http://j.mp/fbyuuH
✗ Sob um ponto de vista legal, cada driver é provavelmente um caso
diferente. Ex: Nvidia.
✗ É realmente útil manter um driver proprietário?
Embedded Labworks

VANTAGENS DE DRIVERS GPL


✗ Você não precisa escrever um driver do zero, podendo reusar o
código de outros drivers.

✗ Com drivers abertos você tem suporte da comunidade, com mais


pessoas revisando e colaborando com seu driver.

✗ Você pode integrar o seu driver na árvore oficial do kernel, e não se


preocupar com qualquer alteração em APIs internas do Linux.
Custo zero de manutenção e melhorias no driver!

✗ Os usuários e a comunidade tem uma visão positiva da empresa.


Embedded Labworks

CONFIGURANDO O KERNEL
✗ O kernel possui centenas de drivers de dispositivo, diversos
protocolos de rede e muitos outros itens de configuração.

✗ Mas o kernel é bem modular, a maioria das opções pode ser


habilitada ou desabilitada conforme a necessidade.

✗ O processo de configuração serve para você configurar o kernel para


ser compilado para o seu sistema e plataforma de hardware.

✗ O conjunto de opções que você irá habilitar depende:


✗ Do seu hardware (device drivers, etc).
✗ Das funcionalidades (protocolos de rede, sistemas de arquivo, etc).
Embedded Labworks

CONFIGURAÇÃO
✗ As configurações são salvas em um arquivo chamado .config no diretório
principal dos fontes do kernel, e possuem o formato key=value. Exemplo:
CONFIG_ARM=y

✗ Dificilmente você vai precisar editar o arquivo .config manualmente.


Existem ferramentas de interface gráfica para configurar o kernel e gerar o
arquivo de configuração automaticamente:
$ make menuconfig
$ make gconfig
$ make xconfig
$ make nconfig
Embedded Labworks

make xconfig
Embedded Labworks

make gconfig
Embedded Labworks

make nconfig
Embedded Labworks

make menuconfig
Embedded Labworks

CONFIGURANDO O KERNEL (cont.)


✗ O kernel é um binário único, resultado do processo de linkagem de
todos os arquivos-objeto das funcionalidades que você habilitou,
incluindo os device drivers.

✗ O kernel permite que algumas funcionalidades possam ser


habilitadas e compiladas de duas formas:
✗ Estática ou built-in: a funcionalidade selecionada é linkada
estaticamente à imagem final do kernel.
✗ Dinâmica ou módulo: é gerado um módulo daquela funcionalidade
(arquivo com extensão .ko). Este módulo não é incluído na imagem final
do kernel. Ele deve ser adicionado ao sistema de arquivos e pode ser
carregado dinamicamente (em tempo de execução), conforme a
necessidade.
Embedded Labworks

OPÇÕES DE CONFIGURAÇÃO
✗ Opções booleanas (verdadeiro/falso):
[ ] → Opção desabilitada
[*] → Opção habilitada

✗ Opções de 3 estados:
< > → Opção desabilitada
<*> → Opção habilitada (built-in)
<M> → Opção habilitada (módulo)

✗ Números inteiros. Ex: (17) Kernel log buffer size

✗ Strings. Ex: (iso8859-1) Default iocharset for FAT


Embedded Labworks

DEPENDÊNCIAS
✗ Na configuração do kernel, podem existir dependências entre
funcionalidades:
✗ Exemplo 1: o driver de um dispositivo I2C só pode ser habilitado se o
barramento I2C for habilitado.
✗ Exemplo 2: o framework de porta serial do kernel (serial core) é
habilitado automaticamente quando um driver de UART é habilitado.

✗ As ferramentas de configuração do kernel são capazes de


gerenciar as dependências entre as opções de configuração e
habilitar automaticamente uma funcionalidade se necessário.
Embedded Labworks

CONFIGURAÇÃO POR ARQUITETURA


✗ Toda a configuração do kernel é dependente da arquitetura da CPU.

✗ Por padrão, o kernel considera uma compilação nativa, então irá usar a
arquitetura da máquina de desenvolvimento no comando abaixo:
$ make menuconfig

✗ Para configurar para ARM por exemplo, você precisa especificar a


arquitetura:
$ make ARCH=arm menuconfig

✗ Ao invés de passar a variável ARCH na chamada do make, você pode também


definí-la como variável de ambiente ou alterar o arquivo Makefile do
diretório principal do kernel.
Embedded Labworks

CONFIGURAÇÕES PRÉ-DEFINIDAS
✗ Arquivos de configuração pré-definidos para diversas plataformas estão
disponíveis em arch/<arch>/configs/.

✗ O uso de arquivos pré-configurados é a forma padrão de configurar o kernel


Linux para uma plataforma específica. Por exemplo, para carregar a
configuração padrão do módulo Colibri i.MX6 da Toradex:
$ make ARCH=arm imx_v6_v7_defconfig

✗ Para salvar um arquivo de configuração, podemos criar uma cópia com o


comando savedefconfig e depois salvá-la no diretório de configs do
kernel:
$ make ARCH=arm savedefconfig
$ cp defconfig arch/<arch>/configs/myconfig_defconfig
Embedded Labworks

VALIDANDO O ARQUIVO DE CONFIGURAÇÃO


✗ O parâmetro oldconfig valida a consistência de um arquivo de
configuração do kernel:
$ make ARCH=arm oldconfig

✗ Ele avisa e configura automaticamente parâmetros e dependências


que antes não existiam.

✗ Deve ser usado sempre que:


✗ O arquivo .config for alterado manualmente.
✗ O arquivo .config for reutilizado em diferentes versões do kernel.
Embedded Labworks

COMPILANDO O KERNEL
✗ Depois de configurado, para compilar nativamente basta executar:
$ make

✗ Para compilar de forma cruzada, é necessário indicar a arquitetura


e o prefixo do toolchain:
$ make ARCH=arm CROSS_COMPILE=arm-linux-

✗ O comando acima irá gerar uma imagem genérica para ARM. Se


você quiser gerar uma imagem específica, deve adicionar ao fim do
comando o nome da imagem:
$ make ARCH=arm CROSS_COMPILE=arm-linux- zImage
Embedded Labworks

COMPILANDO O KERNEL (cont.)


✗ Ao fim do processo de compilação, serão geradas as seguintes
imagens:
✗ vmlinux: imagem no formato ELF gerada na raiz do código-fonte, que
não é inicializável mas pode ser utilizada para depuração.
✗ Em arch/<arch>/boot/:
✗ Image: imagem final do kernel, bootável e descomprimida.
✗ *Image: imagem bootável e comprimida do kernel (bzImage para
x86, zImage para ARM, etc).
✗ uImage: imagem do kernel para o U-Boot (opcional).
Embedded Labworks

INSTALANDO O KERNEL
✗ Para instalar o kernel, basta executar o comando abaixo:
$ make INSTALL_PATH=<install_dir> install

✗ Este comando irá instalar os seguintes arquivos no diretório passado


(ou no diretório /boot por padrão):
✗ vmlinuz-<version> (imagem do kernel comprimida)
✗ System.map-<version> (tabela de símbolos do kernel)
✗ config-<version> (arquivo de configuração do kernel)

✗ Não é comum o uso deste comando em sistemas embarcados, já que


normalmente gravamos o kernel em um endereço específico do
dispositivo de armazenamento (cartão SD, memória flash, etc).
Embedded Labworks

DEVICE TREE
✗ Muitas plataformas possuem dispositivos de hardware que não podem
ser identificados dinamicamente pelo kernel.

✗ Nestes casos, é necessário um mecanismo para comunicar ao kernel


informações sobre os dispositivos de hardware presentes no sistema.

✗ A forma antiga de resolver este problema era descrevendo o


hardware através de estruturas de dados, o que deixava o código-
fonte do kernel mais confuso e difícil de manter.

✗ Atualmente, a maioria das plataformas (incluindo ARM) suportam o


mecanismo de device tree.
Embedded Labworks

DEVICE TREE (cont.)


✗ O device tree é uma estrutura de dados capaz de descrever a
topologia e a configuração do hardware presente no sistema.

✗ Na prática, o device tree é um arquivo texto com extensão .dts


que descreve hierarquicamente o hardware através de nós e
propriedades.

✗ Atualmente, o device tree é suportado por diversas arquiteturas,


incluindo ARM, PowerPC, OpenRISC, ARC e Microblaze.
Embedded Labworks

LISTAGEM DEVICE TREE


✗ Cada placa suportada pelo kernel possui um arquivo de especificação do
device tree, disponível no código-fonte em arch/<arch>/boot/dts:
$ ls arch/arm/boot/dts/
aks-cdu.dts
alphascale-asm9260-devkit.dts
alphascale-asm9260.dtsi
alpine-db.dts
alpine.dtsi
am335x-baltos.dtsi
am335x-baltos-ir2110.dts
am335x-baltos-ir3220.dts
[...]
Embedded Labworks

COMPILANDO O DEVICE TREE


✗ Uma ferramenta chamada Device Tree Compiler ( dtc), disponível em
scripts/dtc/, é responsável por compilar o device tree.

✗ Para compilar o device tree de todas as placas habilitadas na


configuração do kernel:
$ make ARCH=arm CROSS_COMPILE=arm-linux- dtbs

✗ Para compilar o device tree de uma placa específica:


$ make ARCH=arm CROSS_COMPILE=arm-linux- imx6dl-colibri-aster.dtb

✗ Os arquivos DTB são gerados em arch/<arch>/boot/dts.


Embedded Labworks

BOOT COM DEVICE TREE


✗ Durante o processo de boot, o bootloader é o responsável por
passar o device tree para o kernel.

✗ Exemplo para o U-Boot:


> bootz ${kernel_addr_r} - ${fdt_addr_r}

✗ Caso o bootloader não seja capaz de passar o device tree para o


kernel, é possível indicar ao kernel que o DTB está integrado à sua
imagem habilitando a opção CONFIG_ARM_APPENDED_DTB, e depois
gerando uma imagem com o DTB integrado:
$ cat zImage board.dtb > zImage_dtb
Embedded Labworks

LIMPANDO A COMPILAÇÃO
✗ Remove todos os arquivos gerados (imagens, arquivos-objeto, etc).
$ make ARCH=arm clean

✗ Remove todos os arquivos de gerados e arquivos de configuração


(usado quando pretende-se mudar de plataforma).
$ make ARCH=arm mrproper

✗ Além dos arquivos gerados e arquivos de configuração, remove


também arquivos de backup (bom para gerar patches).
$ make ARCH=arm distclean
Embedded Labworks

LINHA DE COMANDOS DO KERNEL


✗ Ao ser carregado, o kernel pode receber um conjunto de
parâmetros. Chamamos esses parâmetros de linha de comandos do
kernel (kernel command line).

✗ A linha de comandos do kernel pode ser passada de duas formas:


✗ Pelo bootloader.
✗ Através da opção CONFIG_CMDLINE no menu de configuração do
kernel.

✗ Esta linha de comandos é uma string com diversas opções no


formato chave=valor.
Embedded Labworks

LINHA DE COMANDOS DO KERNEL (cont.)


console=ttymxc0 root=/dev/mmcblk0p1 rootfstype=ext4

✗ Onde:
✗ console = dispositivo serial que será utilizado como console.
✗ root = partição onde se encontra o sistema de arquivos (rootfs).
✗ rootfstype = tipo do sistema de arquivos.

✗ Existem dezenas opções, todas documentadas no código-fonte do


kernel:
$ ls Documentation/admin-guide/kernel-parameters.txt
Embedded Labworks

LABORATÓRIO

Compilando e gravando o kernel Linux


Embedded Labworks

Linux embarcado

Rootfs
Embedded Labworks

SISTEMAS DE ARQUIVO
✗ Sistemas de arquivo são usados para organizar dados, de forma
hierárquica, em diretórios e arquivos disponíveis em dispositivos
de armazenamento (locais ou remotos).

✗ Em sistemas Unix, aplicações e usuários enxergam apenas uma


hierarquia única e global de arquivos e diretórios, que podem ser
compostos por diferentes sistemas de arquivo.

✗ Um ou mais sistemas de arquivo são montados em locais


específicos nesta hierarquia de diretórios.
Embedded Labworks

SISTEMAS DE ARQUIVO (cont.)


✗ Quando um sistema de arquivo é montado em um diretório, este
diretório é chamado de ponto de montagem ou mount point, e o
conteúdo deste diretório irá refletir o conteúdo armazenado no
dispositivo de armazenamento.

✗ Isso permite que aplicações acessem diretórios e arquivos


facilmente independentemente da localização ou do tipo do
dispositivo de armazemanento.

✗ Tudo o que as aplicações enxergam são arquivos e diretórios!


Embedded Labworks

O COMANDO MOUNT
✗ O comando mount permite montar um sistema de arquivo:
$ mount -t type device mountpoint

✗ Onde:
✗ -t type é opcional e identifica o tipo do sistema de arquivo (fat, ext4,
jffs2, etc).
✗ device é o dispositivo de armazenamento, ou local na rede, onde
estão armazenados os dados.
✗ mountpoint é o diretório onde os arquivos serão acessados, também
chamado de ponto de montagem.
Embedded Labworks

O COMANDO UMOUNT
✗ O comando umount permite desmontar um sistema de arquivo:
$ umount <dispositivo ou ponto de montagem>

✗ Quando trabalhamos com dispositivos removíveis, é necessário


executar o umount antes de remover o dispositivo, já que o Linux
por padrão mantém em cache as alterações realizadas no
dispositivo para melhorar a performance, e o umount garante que
estas alterações sejam realizadas antes da remoção do
dispositivo.
Embedded Labworks

MONTANDO UM SISTEMA DE ARQUIVO


✗ Criando o diretório (ponto de montagem):
$ mkdir /mnt/usbkey

✗ Montando um pendrive:
$ mount -t vfat /dev/sda1 /mnt/usbkey

✗ Listando o conteúdo do pendrive:


$ ls /mnt/usbkey
docs prog.c picture.png movie.avi

✗ Desmontando o dispositivo USB:


$ umount /mnt/usbkey
Embedded Labworks

SISTEMA DE ARQUIVO ROOT


✗ Um sistema de arquivo específico é montado na raiz principal da
hierarquia, identificado pelo /.

✗ Este sistema de arquivo é chamado de root ou rootfs.

✗ Como ele é o primeiro sistema de arquivo a ser montado, não tem


como fazê-lo com o comando mount, já que o mesmo ainda não
está disponível. Lembre-se: ainda não existe nenhum sistema de
arquivo montado!

✗ Por isso, o responsável por esta tarefa é o kernel, de acordo com a


opção root na linha de comandos do kernel.
Embedded Labworks

SISTEMA DE ARQUIVO ROOT (cont.)


✗ Se você não passar a opção root na linha de comandos, o kernel
entra em pânico!
Please append a correct "root=" boot option
Kernel panic - not syncing: VFS: Unable to mount
root fs on unknown block(0,0)

✗ Passando a opção root para o kernel:


... console=ttyS2,115200n8 root=/dev/sda2 ...
Embedded Labworks

LOCALIDADES DO ROOTFS
✗ O rootfs pode ser montado de diferentes localidades:
✗ Da partição de um HD.
✗ Da partição de um pendrive.
✗ Da partição de um cartão SD.
✗ Da partição de uma memória flash NAND.
✗ Pela rede, através do protocolo NFS.
✗ Da memória, pré-carregado pelo bootloader.

✗ É nossa a decisão de como iniciar o sistema, e assim configurar


corretamente a opção root do kernel.
Embedded Labworks

MONTANDO O ROOTFS
✗ Partição de um HD ou pendrive USB:

root=/dev/sdXY, onde X é uma letra que indica o dispositivo e Y é
o número da partição.
✗ Exemplo: root=/dev/sdb2

✗ Partição de um cartão SD:



root=/dev/mmcblkXpY, onde X é um número de identificação do
dispositivo, e Y é o número da partição.
✗ Exemplo: root=/dev/mmcblk0p2
Embedded Labworks

MONTANDO O ROOTFS (cont.)


✗ Partição de uma memória flash NAND:

root=/dev/mtdblockX, onde X é o número da partição.
✗ Exemplo: root=/dev/mtdblock3
Embedded Labworks

MONTANDO O ROOTFS VIA REDE


✗ Uma vez que sua rede esteja funcionando, o rootfs pode estar na
sua máquina de desenvolvimento e ser exportado via protocolo NFS
(Network File System).

Host Target
Servidor NFS Cliente NFS

✗ Muito mais fácil e rápido de atualizar o rootfs sem precisar gravar


na flash e reiniciar o equipamento.

✗ Possibilidade de ter um rootfs bem grande, podendo incluir


ferramentas e binários que não caberiam na flash do equipamento.
Embedded Labworks

MONTANDO O ROOTFS EM MEMÓRIA


✗ Também é possível ter uma imagem de rootfs integrada à imagem
do kernel, sendo por consequência carregada em memória junto
com o kernel.

✗ Este mecanismo é chamado de initramfs.

Kernel Initramfs
(cpio archive)

Imagem do kernel (uImage, zImage, bzImage, etc)


Embedded Labworks

INITRAMFS
✗ Vantagens:
✗ Pode ser usado como um passo intermediário para montar o
verdadeiro rootfs (mecanismo comum em desktops e servidores).
✗ O boot é mais rápido e as aplicações iniciam mais rapidamente.
✗ É mais seguro pois impede alterações persistentes no rootfs.
✗ Pode ser utilizado para implementar um mecanismo de update de
firmware.

✗ Desvantagens:
✗ Como o initramfs é montado em RAM, o armazenamento é volátil
(perde as informações ao reiniciar).
Embedded Labworks

ORGANIZAÇÃO DO ROOTFS
✗ A organização do rootfs no Linux é padronizada pelo Filesystem
Hierarcy Standard.
http://www.pathname.com/fhs/

✗ A maioria dos sistemas Linux estão de acordo com este padrão


porque:
✗ As aplicações esperam este formato.
✗ Facilita o trabalho de usuários e desenvolvedores quando precisam
trabalhar com diferentes sistemas Linux.
Embedded Labworks

DIRETÓRIOS MAIS IMPORTANTES


/bin Programas básicos do sistema
/sbin Aplicações de administração do sistema
/boot Imagens de boot (bootloader, kernel, etc)
/etc Arquivos de configuração
/home Diretório de arquivos dos usuários
/root Home do usuário root
/lib Bibliotecas básicas do sistema
/media Ponto de montagem para mídias removíveis
/mnt Ponto de montagem temporário
Embedded Labworks

DIRETÓRIOS MAIS IMPORTANTES (cont.)


/dev Arquivos de dispositivo
/sys Ponto de montagem do sistema de
arquivo virtual sysfs
/proc Ponto de montagem do sistema de
arquivo virtual proc
/tmp Arquivos temporários
/usr Aplicações e arquivos compartilhados
/usr/bin Aplicações básicas dos usuários
/usr/lib Bibliotecas dos usuários
/usr/sbin Aplicações de administração dos usuários
/var Arquivos de dados (logs, banco de
dados, arquivos temporários, etc)
Embedded Labworks

ARQUIVOS DE DISPOSITIVO
✗ Um conceito muito importante do mundo Unix: boa parte dos
”objetos do sistema” são representados como arquivos, permitindo
que as aplicações manipulem estes objetos usando uma API
comum (open, read, write, close, etc).

✗ Da mesma forma, os dispositivos de hardware também são


representados no Linux através de arquivos, chamados de arquivos
de dispositivo e disponíveis no diretório /dev.
Embedded Labworks

INFORMAÇÕES DOS DISPOSITIVOS


✗ Internamente, cada arquivo de dispositivo está associado à três
informações básicas:
✗ Major number: indica a categoria do dispositivo.
✗ Minor number: indica o número do dispositivo.
✗ Tipo do dispositivo:
✗ Dispositivos de bloco: composto por blocos de dados de tamanho
fixo, endereçáveis e de acesso aleatório, que podem ser lidos
e/ou escritos. Exemplos: HD, pendrive, etc.
✗ Dispositivo de caractere: possibilita o acesso sequencial de bytes,
sem começo, sem fim e sem tamanho! Exemplos: portal serial,
placa de som, etc.
Embedded Labworks

EXEMPLOS
✗ Exemplos de arquivos de dispositivo:
$ ls -la /dev/ttyS* /dev/sda1
brw-rw---- 1 root disk 8, 1 2012-01-25 06:54 /dev/sda1
crw-rw---- 1 root dialout 4, 64 2012-01-25 06:54 /dev/ttyS0
crw-rw---- 1 root dialout 4, 65 2012-01-25 06:54 /dev/ttyS1
crw-rw---- 1 root dialout 4, 66 2012-01-25 06:54 /dev/ttyS2
crw-rw---- 1 root dialout 4, 67 2012-01-25 06:54 /dev/ttyS3

✗ Escrevendo ”Hello” na porta serial:


int fd;
fd = open(“/dev/ttyS0”, O_RDWR);
write(fd, “Hello”, 5);
close(fd);
Embedded Labworks

CRIANDO ARQUIVOS DE DISPOSITIVO


✗ Para sistemas mais simples, os arquivos de dispositivo podem ser
criados manualmente com o comando mknod (é necessário
privilégios de root):
$ mknod /dev/<device> [c|b] major minor

✗ Para sistemas mais complexos, existem mecanismos para


adicionar e remover arquivos de dispositivo dinamicamente:
✗ udev
✗ mdev
✗ devtmpfs
Embedded Labworks

PROCFS
✗ O sistema de arquivo virtual procfs exporta (normalmente para o
diretório /proc) um conjunto de informações do kernel, incluindo
estatísticas dos processos, memória e uso de I/O.

✗ O procfs também possibilita ajustar parâmetros do kernel em


tempo de execução.

✗ Muitas aplicações, como os comandos ps e top, utilizam o /proc


para exibir informações dos processos em execução.
Embedded Labworks

PROCFS (cont.)
✗ Montando o procfs:
$ mount -t proc none /proc

✗ Mais informações na documentação do kernel:


$ ls Documentation/filesystems/proc.txt
Embedded Labworks

SYSFS
✗ O sistema de arquivo virtual sysfs exporta (normalmente para o
diretório /sys) informações de drivers e dispositivos de hardware
conectados ao sistema.

✗ Usado por aplicações que querem ler informações dos dispositivos


de hardware conectados ao sistema. Ex: udev, lsusb, etc.

✗ Pode ser usado também para parametrizar ou configurar


determinado hardware.
Embedded Labworks

SYSFS (cont.)
✗ Montando o sysfs:
$ mount -t sysfs none /sys

✗ Mais informações na documentação do kernel:


$ ls Documentation/filesystems/sysfs.txt
Embedded Labworks

A INICIALIZAÇÃO
✗ Após montar o rootfs, o kernel irá tentar executar uma aplicação
de inicialização, também chamado de processo init.

✗ O processo init pode ser passado como parâmetro na linha de


comandos do kernel:
init=/sbin/init

✗ Se o parâmetro init não for passado, o kernel tenta executar os


seguintes binários, nesta ordem: /sbin/init, /etc/init,
/bin/init e /bin/sh.
Embedded Labworks

A INICIALIZAÇÃO (cont.)
✗ Se nenhum destes programas de inicialização for encontrado, o
kernel entra em pânico!
Kernel panic - not syncing: No init found.

✗ Assim que executado, o processo init é o responsável pela


inicialização do restante do sistema.
Embedded Labworks

VISÃO GERAL DO BOOT


Bootloader
Carrega o kernel para a RAM e inicia

Kernel
Monta o rootfs indicado por ”root=”
Inicia a aplicação ”init”

init
Inicia outros serviços e aplicações

Shell Outras aplicações

Rootfs
Embedded Labworks

MECANISMOS DE INICIALIZAÇÃO
✗ Depois que o kernel chamou a aplicação init, é responsabilidade do
rootfs o restante da inicialização do sistema.

✗ Existem diferentes mecanismos de inicialização no Linux, como


systemd, upstart, openrc e sysvinit (System V Init).

✗ Devido à simplicidade de uso e utilização em soluções mais


simples, vamos estudar no treinamento o sysvinit.
Embedded Labworks

SYSTEM V INIT
✗ O sysvinit possui basicamente os seguintes componentes:
✗ Aplicação init (o pai de todos os processos).
✗ Arquivo de configuração /etc/inittab.
✗ Scripts de inicialização em /etc/init.d/ ou /etc/rc.d/.
Embedded Labworks

/etc/inittab
# Startup the system
null::sysinit:/bin/mount -t proc proc /proc
null::sysinit:/bin/mount -t sysfs sysfs /sys

# now run any rc scripts


::sysinit:/etc/init.d/rcS

# Put a getty on the serial port


ttySAC0::respawn:/sbin/getty -L ttySAC0 115200 vt100

# Stuff to do for the 3-finger salute


::ctrlaltdel:/sbin/reboot

# Stuff to do before rebooting


null::shutdown:/usr/bin/killall syslogd
Embedded Labworks

/etc/init.d/rcS
#!/bin/sh

for i in /etc/init.d/S??*; do

case "$i" in

*.sh)
. $i
;;

*)
$i start
;;

esac

done
Embedded Labworks

/etc/init.d/
$ ls -l /etc/init.d/
total 8
-rwxr-xr-x 1 root root 408 2011-08-31 08:44 rcS
-rwxr-xr-x 1 root root 478 2011-09-08 15:02 S01logging
-rwxr-xr-x 1 root root 1365 2011-08-31 08:44 S20urandom
-rwxr-xr-x 1 root root 282 2011-08-31 08:44 S40network
-rwxr-xr-x 1 root root 1092 2011-09-08 16:05 S50dropbear
-rwxr-xr-x 1 root root 73 2011-09-13 14:50 S60leds
Embedded Labworks

CRIANDO UM ROOTFS BÁSICO


✗ Um sistema Linux precisa de um conjunto básico de programas
para funcionar (init, shell, cat, top, ps, grep, find, etc).

✗ Normalmente estes programas são fornecidos em diferentes


projetos, sendo trabalhoso compilar e integrar manualmente todos
estes componentes no rootfs.

✗ O Busybox é uma solução alternativa, trazendo uma quantidade


grande e comum de programas usados em sistemas Linux, com
tamanho reduzido, perfeito para sistemas embarcados!
https://busybox.net/
Embedded Labworks

APLICAÇÕES DISPONÍVEIS NO BUSYBOX


addgroup, adduser, adjtimex, ar, arp, arping, ash, awk, basename, bbconfig, bbsh, brctl, bunzip2, busybox,
bzcat, bzip2, cal, cat, catv, chat, chattr, chcon, chgrp, chmod, chown, chpasswd, chpst, chroot, chrt, chvt,
cksum, clear, cmp, comm, cp, cpio, crond, crontab, cryptpw, cttyhack, cut, date, dc, dd, deallocvt, delgroup,
deluser, depmod, devfsd, df, dhcprelay, diff, dirname, dmesg, dnsd, dos2unix, dpkg, dpkg_deb, du,
dumpkmap, dumpleases, e2fsck, echo, ed, egrep, eject, env, envdir, envuidgid, ether_wake, expand, expr,
fakeidentd, false, fbset, fbsplash, fdflush, fdformat, fdisk, fetchmail, fgrep, find, findfs, fold, free, freeramdisk,
fsck, fsck_minix, ftpget, ftpput, fuser, getenforce, getopt, getsebool, getty, grep, gunzip, gzip, halt, hd,
hdparm, head, hexdump, hostid, hostname, httpd, hush, hwclock, id, ifconfig, ifdown, ifenslave, ifup, inetd,
init, inotifyd, insmod, install, ip, ipaddr, ipcalc, ipcrm, ipcs, iplink, iproute, iprule, iptunnel, kbd_mode, kill,
killall, killall5, klogd, lash, last, length, less, linux32, linux64, linuxrc, ln, load_policy, loadfont, loadkmap,
logger, login, logname, logread, losetup, lpd, lpq, lpr, ls, lsattr, lsmod, lzmacat, makedevs, man,
matchpathcon, md5sum, mdev, mesg, microcom, mkdir, mke2fs, mkfifo, mkfs_minix, mknod, mkswap,
mktemp, modprobe, more, mount, mountpoint, msh, mt, mv, nameif, nc, netstat, nice, nmeter, nohup,
nslookup, od, openvt, parse, passwd, patch, pgrep, pidof, ping, ping6, pipe_progress, pivot_root, pkill,
poweroff, printenv, printf, ps, pscan, pwd, raidautorun, rdate, rdev, readahead, readlink, readprofile, realpath,
reboot, renice, reset, resize, restorecon, rm, rmdir, rmmod, route, rpm, rpm2cpio, rtcwake, run_parts, runcon,
runlevel, runsv, runsvdir, rx, script, sed, selinuxenabled, sendmail, seq, sestatus, setarch, setconsole,
setenforce, setfiles, setfont, setkeycodes, setlogcons, setsebool, setsid, setuidgid, sh, sha1sum, showkey,
slattach, sleep, softlimit, sort, split, start_stop_daemon, stat, strings, stty, su, sulogin, sum, sv, svlogd,
swapoff, swapon, switch_root, sync, sysctl, syslogd, tac, tail, tar, taskset, tcpsvd, tee, telnet, telnetd, test,
tftp, tftpd, time, top, touch, tr, traceroute, true, tty, ttysize, tune2fs, udhcpc, udhcpd, udpsvd, umount,
uname, uncompress, unexpand, uniq, unix2dos, unlzma, unzip, uptime, usleep, uudecode, uuencode,
vconfig, vi, vlock, watch, watchdog, wc, wget, which, who, whoami, xargs, yes, zcat, zcip
Embedded Labworks

LABORATÓRIO

Criando um rootfs para o target


Embedded Labworks

Linux embarcado

Módulos do kernel
Embedded Labworks

KERNEL MONOLÍTICO E MICROKERNEL


✗ Kernel monolítico: o sistema operacional inteiro roda em kernel
space, com total acesso aos recursos da máquina (CPU, memória e
I/O), e provê para as aplicações (userspace) uma interface de
comunicação através de chamadas de sistema (system calls).

✗ Microkernel: apenas o núcleo do kernel roda em kernelspace


(gerenciamento de memória, escalonador). O restante roda em
userspace, incluindo sistemas de arquivos, device drivers,
protocolos de rede, etc!
Embedded Labworks

MONOLÍTICO X MICROKERNEL
Embedded Labworks

O KERNEL LINUX
✗ O Linux é um kernel monolítico.

✗ Mas internamente o Linux é bem modular. Cada funcionalidade é


abstraída em um módulo, com uma interface de comunicação bem
definida. Por isso, permite um sistema de configuração onde você
pode facilmente adicionar ou remover determinada funcionalidade.

✗ E o Linux permite que você adicione dinamicamente “pedaços de


código do kernel” em tempo de execução!

✗ Chamamos esses “pedaços de código” de módulos do kernel.


Embedded Labworks

VANTAGENS DOS MÓDULOS


✗ Ajuda a manter a imagem do kernel bem pequena.

✗ Só consome recursos (CPU, memória, I/O) enquanto estiver carregado.

✗ O tempo de boot do kernel fica menor.

✗ Possibilita desenvolver e testar um código do kernel (ex: device


driver) sem precisar reiniciar o target.

✗ Cuidado: módulos rodam em kernel space. Uma vez carregados, eles


tem total controle do sistema! Por isso só podem ser carregados
como root.
Embedded Labworks

COMPILANDO OS MÓDULOS
✗ Para compilar os módulos nativamente, basta executar o comando
abaixo na raiz do código-fonte do kernel:
$ make modules

✗ Para compilar os módulos de forma cruzada, é necessário passar a


arquitetura e o prefixo do toolchain:
$ make ARCH=arm CROSS_COMPILE=arm-linux- modules
Embedded Labworks

INSTALANDO OS MÓDULOS
✗ Para instalar os módulos nativamente, basta executar o comando
abaixo:
$ make modules_install

✗ No caso de um ambiente de compilação cruzada, os módulos


devem ser instalados no rootfs do target.

✗ Para isso, podemos usar o parâmetro INSTALL_MOD_PATH no


comando de instalação:
$ make ARCH=<arch> INSTALL_MOD_PATH=<dir> modules_install
Embedded Labworks

INSTALANDO OS MÓDULOS (cont.)


✗ Os módulos são instalados em /lib/modules/<kernel-version>/
por padrão:
# ls /lib/modules/4.19.17/
build modules.builtin.bin modules.softdep
kernel modules.dep modules.symbols
modules.alias modules.dep.bin modules.symbols.bin
modules.alias.bin modules.devname source
modules.builtin modules.order
Embedded Labworks

INSTALANDO OS MÓDULOS (cont.)


✗ Os arquivos dos módulos estarão dentro do diretório kernel/:
# tree /lib/modules/4.19.17/kernel
└── drivers
└── iio
├── buffer
│ ├── industrialio-triggered-buffer.ko
│ └── kfifo_buf.ko
├── imu
│ └── inv_mpu6050
│ ├── inv-mpu6050-i2c.ko
│ └── inv-mpu6050.ko
└── industrialio.ko
Embedded Labworks

DEPENDÊNCIAS DOS MÓDULOS


✗ Alguns módulos podem depender de outros módulos. Por exemplo,
o módulo usb_storage.ko depende do módulo usbcore.ko.

✗ Isso significa que, para carregar o módulo usb_storage.ko, é


necessário carregar antes o módulo usbcore.ko.

✗ As dependências entre os módulos ficam descritas no arquivo


/lib/modules/<kernel-version>/modules.dep.

✗ Este arquivo é gerado automaticamente quando os módulos são


instalados, através de uma ferramenta chamada depmod.
Embedded Labworks

DEPENDÊNCIAS DOS MÓDULOS (cont.)


# cat /lib/modules/4.19.17/modules.dep
kernel/drivers/iio/buffer/industrialio-triggered-buffer.ko: ker
nel/drivers/iio/buffer/kfifo_buf.ko kernel/drivers/iio/industri
alio.ko
kernel/drivers/iio/buffer/kfifo_buf.ko: kernel/drivers/iio/indu
strialio.ko
kernel/drivers/iio/imu/inv_mpu6050/inv-mpu6050.ko: kernel/drive
rs/iio/buffer/industrialio-triggered-buffer.ko kernel/drivers/i
io/buffer/kfifo_buf.ko kernel/drivers/iio/industrialio.ko
kernel/drivers/iio/imu/inv_mpu6050/inv-mpu6050-i2c.ko: kernel/d
rivers/iio/imu/inv_mpu6050/inv-mpu6050.ko kernel/drivers/iio/bu
ffer/industrialio-triggered-buffer.ko kernel/drivers/iio/buffer
/kfifo_buf.ko kernel/drivers/iio/industrialio.ko
kernel/drivers/iio/industrialio.ko:
Embedded Labworks

CARREGANDO UM MÓDULO
✗ O comando insmod carrega apenas o módulo passado, sem
verificar suas dependências. É necessário passar o caminho
completo do módulo.
# insmod /lib/modules/4.19.17/kernel/drivers/iio/industrialio.ko

✗ O comando modprobe carrega um módulo e todas as suas


dependências. Deve-se passar apenas o nome do módulo, sem a
extensão .ko e sem seu caminho completo.
# modprobe industrialio
Embedded Labworks

DESCARREGANDO UM MÓDULO
✗ O comando rmmod descarrega apenas o módulo passado, sem
descarregar suas dependências. Funciona apenas se o módulo não
estiver mais em uso. Deve-se passar apenas o nome do módulo,
sem a extensão .ko e sem seu caminho completo.
# rmmod industrialio

✗ O comando modprobe descarrega um módulo e todas as suas


dependências (que não estão sendo usadas). Deve-se passar
apenas o nome do módulo, sem a extensão .ko e sem seu caminho
completo.
# modprobe -r industrialio
Embedded Labworks

LISTANDO INFORMAÇÕES DOS MÓDULOS


✗ O comando modinfo lê os metadados de um módulo, como sua
descrição, parâmetros, licença e dependências. Deve-se passar
apenas o nome do módulo, sem a extensão .ko e sem seu caminho
completo.
# modinfo industrialio

✗ O comando lsmod lista todos os módulos carregados.


# lsmod
Embedded Labworks

MODINFO
# modinfo industrialio
filename: /lib/modules/4.19.17/kernel/drivers/iio/industrialio.ko
license: GPL
description: Industrial I/O core
author: Jonathan Cameron <jic23@kernel.org>
srcversion: 9C0B01D46E2B110B4619BFE
depends:
intree: Y
name: industrialio
vermagic: 4.19.17 SMP mod_unload modversions ARMv6 p2v8
Embedded Labworks

LSMOD
# lsmod
Module Size Used by
inv_mpu6050_i2c 16384 0
inv_mpu6050 20480 2 inv_mpu6050_i2c
industrialio_trigge 16384 1 inv_mpu6050
kfifo_buf 16384 1 industrialio_triggered_buffer
industrialio 69632 3 inv_mpu6050,industrialio_triggere...
Embedded Labworks

PASSANDO PARÂMETROS
✗ Passando parâmetros ao carregar o módulo:
# modprobe <module> param=value

✗ Passando parâmetros para um módulo via arquivo de configuração


(/etc/modprobe.conf ou /etc/modprobe.d/):
options <module> param=value

✗ Passando um parâmetro via linha de comandos do kernel:


<module>.param=value
Embedded Labworks

LABORATÓRIO

Trabalhando com módulos do kernel


Embedded Labworks

Linux embarcado

Tipos de sistemas de arquivo


Embedded Labworks

SISTEMAS DE ARQUIVO
✗ Um sistema de arquivo é uma representação dos dados salvos em
um dispositivo de armazenamento.

✗ Exemplos de sistemas de arquivo: FAT, NTFS, EXT4, UBIFS, etc.

✗ Existem diferentes tipos de sistemas de arquivo para atender


diferentes necessidades, incluindo:
✗ Performance.
✗ Segurança.
✗ Economia de espaço.
✗ Características físicas do dispositivo de armazenamento.
Embedded Labworks

DISPOSITIVOS DE ARMAZENAMENTO
✗ No Linux, os dispositivos de armazenamento são classificados em dois
tipos: dispositivos de bloco e memórias flash.

✗ Isso porque, dentro do kernel, eles são manipulados por sub-sistemas


diferentes:
✗ Dispositivos de bloco podem ser lidos ou escritos normalmente sem a
necessidade de apagar antes, e ”virtualmente” não possuem limites de
escrita. Exemplos: HD SATA, pendrive, SSD, etc.
✗ Memórias flash trabalham em blocos e para serem escritas precisam ser
apagadas antes. Exemplos: flash NAND, flash NOR, etc.

✗ Por este motivo, vamos estudar estes dois sub-sistemas


separadamente.
Embedded Labworks

DISPOSITIVOS DE BLOCO
✗ Uma lista com todos os dispositivos de bloco disponíveis no
sistema pode ser obtido em /proc/partitions:
$ cat /proc/partitions
major minor #blocks name

8 0 312571224 sda
8 1 303903744 sda1
8 2 1 sda2
8 5 8665088 sda3
Embedded Labworks

SISTEMAS DE ARQUIVO TRADICIONAIS


✗ Existem sistemas de arquivo específicos para dispositivos de bloco.

✗ Um dos primeiros foi o tradicional sistema de arquivos ext2,


presente no Linux desde praticamente as primeiras versões.

✗ É um sistema de arquivo bem estável, mas com um grande


problema: pode deixar o sistema em um estado inconsistente se for
interrompido durante uma operação em disco.

✗ O ext2 foi usado durante um bom tempo no Linux (quase 10 anos).


Então começaram a aparecer alguns sistemas de arquivo com uma
característica especial chamada de journaling.
Embedded Labworks

JOURNALING
Aplicação
✗ Um sistema de arquivo com journal
foi projetado para manter a User space Escreve no arquivo
consistência dos dados mesmo Kernel space
após um crash do sistema ou um
Escreve uma
reboot inesperado. entrada no journal

✗ Todas as alterações são salvas em


Escreve no arquivo
um journal (uma espécie de log)
antes de serem aplicadas no
arquivo.
Limpa entrada no
journal
Embedded Labworks

JOURNALING (cont.)

Reboot
✗ Devido ao mecanismo de
journaling, o sistema de
arquivo nunca fica em um
Journal
vazio?
estado inconsistente
Não
(corrompido).
Descarta entradas
incompletas no
journal ✗ Os últimos dados salvos,
Sim
no entanto, podem ser
perdidos.
Executa
journal

Sistema de arquivo OK
Embedded Labworks

SISTEMAS DE ARQUIVO COM JOURNALING


✗ O ext3 foi o padrão para sistemas de arquivo com journal durante um
bom tempo. Ele é basicamente o ext2 com a funcionalidade de journaling.

✗ O ext4 é a nova geração com muitas melhorias, sendo o sistema de


arquivo padrão das distribuições Linux atuais.

✗ O btrfs (também chamado de ”ButterFS”) é a próxima geração e visa


substituir o ext4. Já está em uso por algumas distribuições Linux.

✗ Existem muitos outros sistemas de arquivo com journaling, incluindo


reiserFS, JFS e XFS, que possuem aplicações específicas, como por
exemplo trabalhar com arquivos muito pequenos ou com carga de
trabalho muito alta.
Embedded Labworks

DISPOSITIVOS DE BLOCO COM FLASH


✗ Alguns dispositivos de bloco possuem memória flash, porém aparecem no
sistema como um dispositivo de bloco comum (ex: pendrive, cartão SD, eMMC,
SSD, etc).

✗ Isso porque estes dispositivos possuem uma controladora chamada FTL (Flash
Translation Layer) que converte a flash em um disco para o sistema operacional.

✗ Para estes casos, é importante evitar ao máximo escritas desnecessárias no


dispositivo para aumentar a vida útil da flash. Por exemplo, uma partição
formatada com ext4 pode gerar escritas desnecessárias devido ao journaling.

✗ Para estes casos, podemos utilizar o F2FS (Flash-Friendly File System), um novo
sistema de arquivo criado pela Samsung que leva em consideração as
características e limitações da memória flash do dispositivo.
Embedded Labworks

QUAL ESCOLHER?
✗ Na prática, você utilizará por padrão o ext4 em dispositivos de
bloco (talvez o ext4 seja substituído pelo btrfs em alguns anos).

✗ Para dispositivos de bloco que possuem memória flash, você pode


querer desabilitar o journaling do ext4 ou avaliar o uso do F2FS.

✗ Você só usará vfat e ntfs se quiser interoperabilidade com


sistemas Windows.

✗ Outros sistemas de arquivo como o reiserFS, o JFS e o XFS são


usados normalmente em servidores, e tem pouca aplicação em
Linux embarcado.
Embedded Labworks

SISTEMAS DE ARQUIVO COMPRIMIDOS


✗ Sistemas embarcados possuem normalmente poucos recursos de
armazenamento. Por este motivo, você pode querer usar um sistema de
arquivo que comprima os dados, deixando o tamanho da imagem do
sistema de arquivo menor, e ocupando menos espaço no dispositivo de
armazenamento.

✗ Um sistema de arquivo comprimido, como o próprio nome diz, armazena


os dados de forma comprimida no dispositivo de armazenamento.

✗ Como algoritmos para escrever de forma comprimida são bem mais


complicados de implementar sem afetar a performance e a
confiabilidade do sistema, boa parte dos sistemas de arquivo
comprimidos são de apenas leitura.
Embedded Labworks

CRAMFS
✗ O CramFS (Compressed ROM Filesystem) é um exemplo de sistema
de arquivo comprimido de apenas leitura, desenvolvido
especialmente para sistemas embarcados ou dispositivos com
baixa capacidade de armazenamento.
https://www.kernel.org/doc/Documentation/filesystems/cramfs.txt

✗ Os dados são comprimidos com a biblioteca zlib, suportando


arquivos de até 16M, e com tamanho máximo da imagem de até
256MB.

✗ Você só vai precisar do CramFS se seu kernel for muito antigo


(anterior à versão 2.6.29).
Embedded Labworks

SQUASHFS
✗ O SquashFS é uma espécie de sucessor do CramFS, visando atingir os
mesmos objetivos, mas com melhor compressão, melhor performance
de leitura e suporte a arquivos e sistemas maiores.
https://www.kernel.org/doc/Documentation/filesystems/squashfs.txt

✗ Gera uma imagem de sistema de arquivo 3 a 5 vezes menor que o ext3/4.


https://elinux.org/Squash_Fs_Comparisons

✗ Muito usado em sistemas embarcados para partições que podem ser


apenas de leitura (kernel, rootfs, etc).

✗ Usado também em distribuições que rodam direto de um pendrive ou


CD/DVD (Live CD).
Embedded Labworks

SISTEMAS DE ARQUIVO VOLÁTEIS


✗ Quando trabalhamos com Linux embarcado, às vezes precisamos
criar arquivos temporários, armazenar informações de processos
em execução, fazer log, etc.

✗ Fazer isso em um dispositivo de armazenamento pode ser muito


custoso, já que envolve operações de I/O e pode consumir a vida
útil do dispositivo no caso de memórias flash.

✗ São nestes casos que usamos sistemas de arquivo voláteis.


Embedded Labworks

SISTEMAS DE ARQUIVO VOLÁTEIS (cont.)


✗ Com um sistema de arquivo volátil, você consegue manter um
diretório do sistema montado em RAM. Ou seja, tudo o que você
escrever neste diretório, vai para a memória RAM!

✗ Consequentemente, você irá perder estas informações no boot do


equipamento. Mas é a solução perfeita para armazenar dados e
arquivos temporários.

✗ O sistema de arquivo volátil padrão no Linux atualmente é o tmpfs.


Embedded Labworks

TMPFS
✗ O tmpfs é um sistema de arquivo útil para armazenar dados
temporários em RAM (arquivos temporários, logs, etc).

✗ Não gasta muita RAM, cresce e diminui automaticamente conforme


o uso (configurável durante a montagem).

✗ Como montar o tmpfs:


$ mount -t tmpfs tmp /tmp

✗ Para mais informações, veja a documentação no kernel:


$ ls Documentation/filesystems/tmpfs.txt
Embedded Labworks

MISTURANDO TUDO
✗ Você pode dividir seu dispositivo de bloco em
partições: squashfs
rootfs

Dispositivo de Bloco
✗ Uma partição squashfs para o rootfs (kernel, comprimido
binários, etc). Salva espaço, e por ser apenas
leitura, fica protegido de alterações acidentais no
sistema de arquivos.
✗ Uma partição ext4 para leitura e escrita de dados ext4
dados e
do usuário e de configuração. configuração
✗ Dados temporários em RAM com o tmpfs.
tmpfs

RAM
dados
voláteis
Embedded Labworks

MEMÓRIAS FLASH
✗ Algumas limitações diferem as memórias flash de dispositivos de bloco
tradicionais como HDs.

✗ As memórias flash só podem ser apagadas em blocos. Estes blocos são


chamados de erase blocks, e podem variar de algumas dezenas para algumas
centenas de KB.

✗ Quando você apaga um bloco da flash, todos os bits assumem tipicamente o


valor 1. Com um bloco apagado, você pode escrever em qualquer posição da
flash.

✗ Porém, se você escrever 0 em qualquer um dos bits de qualquer posição da


flash, você só consegue fazê-lo voltar para 1 apagando todo o bloco
correspondente da flash!
Embedded Labworks

MEMÓRIAS FLASH (cont.)


✗ Outra limitação das memórias flash é a quantidade de vezes que
você pode apagar e escrever nela (program/erase cycles).

✗ Esta limitação, dependendo do modelo e do fabricante da flash,


pode variar entre 100.000 e 1.000.000 ciclos. Parece muito, mas
basta você deixar sua aplicação fazendo log em memória flash
para transformá-la em um peso de papel!

✗ É por este motivo que existe uma funcionalidade chamada wear


leveling, que minimiza este problema, e que pode ser
implementada por software ou diretamente em chips controladores
de flash.
Embedded Labworks

MEMÓRIAS FLASH (cont.)


✗ Mesmo assim, depois de certo tempo de uso da flash, um ou mais
blocos serão inutilizados.

✗ Por este motivo, existe uma técnica chamada de BBM (Bad Block
Management).

✗ Quando sai de fábrica, as memórias flash NAND já possuem


gravada nelas uma tabela de bad blocks.

✗ Toda camada de software que trabalha com memórias flash deve


ser capaz de ler e identificar estes bad blocks para não utilizar
regiões inválidas da flash.
Embedded Labworks

TIPOS DE MEMÓRIAS FLASH


✗ Além destas características especiais, existem basicamente dois
tipos de memória flash:
✗ Flash NOR: Acesso aleatório para leitura de dados (byte a byte),
velocidade alta para leitura mas lenta para apagar e escrever, baixa
densidade, menor durabilidade, alto custo por MB. Usada para
armazenar código, substituir ROM.
✗ Flash NAND: Acesso de leitura em blocos, velocidade baixa para leitura
mas alta para apagar e escrever, alta densidade, maior durabilidade,
baixo custo por MB. Usada para armazenar dados.

✗ É por causa de todas estas características e limitações das


memórias flash que existe um sub-sistema específico no kernel
chamado MTD para tratar memórias flash.
Embedded Labworks

MTD (MEMORY TECHNOLOGY DEVICES)

Interface com o sistema de arquivos


MTD User modules
ubifs jffs2 yaffs2

Char device Read-only block device Block device

MTD Chip drivers


NOR flash RAM chips
Block device Virtual memory

NAND flash DiskOnChip flash ROM chips Virtual devices

Hardware
Embedded Labworks

CAMADAS DO SUB-SISTEMA MTD


✗ A camada de baixo (MTD chip drivers) conversa diretamente com o
hardware, enquanto que a camada de cima (MTD user modules)
implementa os diferentes sistemas de arquivo e mecanismos de
acesso à memória flash.

✗ Cada memória tem o seu MTD chip driver para possibilitar o acesso
ao hardware da flash. Mas cada sistema pode usar um ou mais
MTD user modules.

✗ Cada um dos MTD user modules irá tratar de forma diferente a


flash. É neste contexto que as memórias flash também são
chamadas de dispositivos MTD.
Embedded Labworks

MTDCHAR
✗ O driver mtdchar implementa o módulo "char device" da flash. Ele cria
um dispositivo de caractere para cada partição de um dispositivo MTD
no sistema, normalmente chamado de /dev/mtdX, onde X é o número da
partição.

✗ Com este módulo, você tem acesso sequencial (byte a byte) ao conteúdo
da flash.

✗ Além disso, ele disponibiliza comandos ioctl() para você manipular a


flash (ler informações, apagar/gravar na flash, etc).

✗ A principal utilidade deste módulo é no gerenciamento da flash através


do pacote mtd-utils.
Embedded Labworks

MTD-UTILS
✗ O mtd-utils é um conjunto de ferramentas para manipular
dispositivos MTD:
✗ mtdinfo retorna informações detalhadas do dispositivo.
✗ flash_eraseall apaga todo o dispositivo.
✗ flashcp escreve em memórias flash NOR.
✗ nandwrite escreve um memórias flash NAND.
✗ mkfs.jffs2 e mkfs.ubifs cria os respectivos sistemas de arquivo na
flash.

✗ Para mais informações consulte o site do projeto:


http://www.linux-mtd.infradead.org/
Embedded Labworks

MTDBLOCK
✗ O driver mtdblock implementa o módulo "block device" da flash.

✗ Ele cria um dispositivo de bloco para cada partição de um dispositivo


MTD no sistema, normalmente nomeado /dev/mtdblockX, onde X é o
número da partição.

✗ Este módulo permite acesso de leitura/escrita por bloco, como se fosse


um disco, mas não gerencia bad blocks e também não trabalha com
wear leveling em escritas.

✗ Portanto, se você quiser um sistema de arquivo que trabalhe com todas


as limitações da flash, incluindo bad blocks e wear leveling, você vai
precisar de um sistema de arquivo específico para flash.
Embedded Labworks

JFFS2
✗ É um dos sistemas de arquivo para flash mais antigos ainda em
utilização.
http://www.linux-mtd.infradead.org/doc/jffs2.html

✗ Vantagens: compressão em tempo de execução (economiza espaço),


confiabilidade, wear leveling e algoritmo ECC.

✗ Desvantagens: não escala muito bem em memórias flash com


capacidades muito grandes. O kernel precisa varrer todo o sistema de
arquivo no momento da montagem.

✗ Habilitando no kernel a opção CONFIG_JFFS2_SUMMARY reduz


drasticamente este tempo de montagem.
Embedded Labworks

YAFFS2
✗ É um dos sucessores do JFFS2, com o objetivo de corrigir os
problemas de performance em memórias flash muito grandes.
https://yaffs.net/

✗ Vantagens: tempo de boot rápido, confiabilidade, wear leveling e


algoritmo ECC.

✗ Desvantagens: suporta apenas memória flash NAND, não comprime


os dados e não está integrado ao mainline do kernel.
Embedded Labworks

UBIFS
✗ Evolução do jffs2, dos mesmos desenvolvedores do mtd-utils,
disponível a partir do kernel 2.6.27.
http://www.linux-mtd.infradead.org/doc/ubifs.html

✗ Trabalha com volumes lógicos em cima de dispositivos MTD.

✗ Principal desvantagem é o overhead de metadados, por isso sua


utilização é aconselhada apenas em memórias flash maiores
(acima de 32M).

✗ Com a capacidade das memórias flash aumentando cada vez mais,


tem se tornado o sistema de arquivo padrão para dispositivos MTD.
Embedded Labworks

DICAS PARA TRABALHAR COM FLASH


✗ Não use a memória flash como região de swap!

✗ Não use a memória flash para armazenamento volátil como logs e


arquivos temporários (use tmpfs nestes casos).

✗ Monte o rootfs como apenas leitura, ou use o squashfs, quando possível.

✗ Utilizar a opção de montagem noatime para evitar escritas


desnecessárias na memória flash.

✗ Não use a opção de montagem sync (atualização escreve imediatamente


no sistema de arquivo).
Embedded Labworks

ESCOLHENDO O SISTEMA DE ARQUIVO

Dados Não Somente Não Bloco


Voláteis? Leitura? Dispositivo Tem flash?

Sim Sim
Não
MTD
Sim
squashfs ext4 ou f2fs

tmpfs ubifs ou jffs2 ext4


Embedded Labworks

LABORATÓRIO

Montando o rootfs do cartão SD


Embedded Labworks

Linux embarcado

Build system
Embedded Labworks

O DESAFIO: INTEGRAR TUDO ISSO

Aplicação Aplicação

Biblioteca Biblioteca

Toolchain Biblioteca C

Linux kernel

Bootloader

Hardware
Embedded Labworks

O DESAFIO: INTEGRAR TUDO ISSO (cont.)

u-boot.img zImage rootfs.img


Embedded Labworks

INTEGRANDO TUDO
✗ O que vimos até aqui foi um passo a passo de como desenvolver
um sistema Linux embarcado manualmente.

✗ Na prática, não precisamos desenvolver um sistema Linux


manualmente, ja que é uma atividade trabalhosa, demorada e
suscetível à erros.

✗ Portanto, temos normalmente duas possíveis soluções para


trabalhar no desenvolvimento de sistemas com Linux embarcado:
1. Usar uma distribuição Linux pronta.
2. Usar um sistema de build (build system).
Embedded Labworks

DISTRIBUIÇÃO PRONTA
✗ Existem diversas distribuições comerciais prontas para Linux
embarcado: MontaVista, Timesys Linux, Wind River Linux, etc.

✗ Existem também diversas soluções abertas, incluindo Android,


Debian, Fedora, Ubuntu, Tizen, Angstrom, Alpine Linux, etc.

✗ Vantagens do uso de uma distribuição pronta:


✗ Simplicidade de uso.
✗ Facilidade na instalação de novos pacotes.
✗ Framework de desenvolvimento pronto e funcional.
Embedded Labworks

DISTRIBUIÇÃO PRONTA (cont.)


✗ Desvantagens do uso de uma distribuição pronta:
✗ Falta flexibilidade (compatibilidade com a plataforma de hardware,
mecanismo de inicialização, framework de desenvolvimento, etc).
✗ Pode não estar otimizado para o target, consumindo muitos recursos
(CPU, memória) da máquina.
✗ Normalmente o rootfs é grande, ocupa muito espaço no dispositivo de
armazenamento.
✗ Tempo de boot normalmente alto.
✗ Difícil de levantar quais pacotes open source são usados.
✗ Requer tempo para customizar e deixar o sistema mais leve.
Embedded Labworks

BUILD SYSTEM
✗ O build system permite gerar um sistema Linux completo do zero.

✗ Ele automatiza o processo de geração dos diversos componentes


do sistema, incluindo toolchain, bootloader, kernel, bibliotecas e
aplicações.

✗ Normalmente já contém um conjunto grande de pacotes


configurados para serem habilitados e utilizados pelo seu sistema.

✗ E facilita o trabalho de adicionar novos pacotes se necessário.


Embedded Labworks

BUILD SYSTEM (cont.)


✗ Vantagens:
✗ Flexibilidade.
✗ O processo de build torna-se reproduzível, facilitando o trabalho de
recompilação, correção de problemas e adição de novas
funcionalidades.

✗ Desvantagens (?):
✗ Tempo adicional para aprender a usar e configurar a ferramenta para
a geração do sistema Linux customizado.
Embedded Labworks

FERRAMENTAS
✗ Buildroot, desenvolvido pela comunidade:
https://buildroot.org/

✗ PTXdist, desenvolvido pela empresa Pengutronix:


https://www.ptxdist.org/

✗ OpenWRT, com foco em dispositivos de rede.


https://openwrt.org/
Embedded Labworks

FERRAMENTAS (cont.)
✗ OpenEmbedded, mais flexível (e também mais complexo):
https://www.openembedded.org/

✗ Yocto Project (Poky), mais novo e baseado no OpenEmbedded:


https://www.yoctoproject.org/

✗ Sistemas comerciais (MontaVista, WindRiver, Timesys).


Embedded Labworks

BUILDROOT
✗ Desenvolvido pelos mesmos mantenedores da uClibc.

✗ Possibilita gerar o toolchain, o bootloader, o kernel e o rootfs com


muitas bibliotecas e aplicações disponíveis.

✗ Mais de 2.000 aplicações e bibliotecas integradas, de utilitários


básicos à bibliotecas mais elaboradas como X.org, Qt, Gtk, Webkit,
Gstreamer, etc.

✗ Desde a versão 2009.02 um novo release é liberado a cada 3


meses.
Embedded Labworks

BUILDROOT (cont.)
Embedded Labworks

YOCTO PROJECT
✗ Projeto patrocinado pela Linux Foundation que provê um conjunto de
ferramentas para auxiliar na criação de sistemas Linux para dispositivos
embarcados.
https://www.yoctoproject.org

✗ O sistema de build (Poky) usa uma ferramenta chamada bitbake que processa
um conjunto de arquivos chamados de receitas (recipes).

✗ O conjunto de receitas habilitadas define a distribuição Linux que será gerada.


As receitas podem ser organizadas em camadas (layers), possibilitando um
sistema bastante customizável através da reutilização de receitas.

✗ Capaz de gerar SDK de desenvolvimento, sistemas multiplataforma, suporte a


gerenciamento de pacotes, etc.
Embedded Labworks

YOCTO (cont.)
Embedded Labworks

QUAL USAR?
✗ Depende, cada sistema de build tem suas vantagens!

✗ Buildroot:
✗ Simples de usar.
✗ Ferramenta de configuração mais intuitiva.
✗ Compilação mais rápida.
✗ Ótima solução para projetos pequenos e médios.
Embedded Labworks

QUAL USAR? (cont.)


✗ Yocto:
✗ Mais flexível.
✗ Suporta a geração de sistemas multiplataforma.
✗ Suporta gerenciamento de pacotes.
✗ Permite geração de ferramentas de desenvolvimento como SDKs e emuladores.
✗ Ótimo para desenvolvimento de BSPs e outros projetos maiores.

✗ Pelo tempo de compilação menor e pela facilidade de uso, utilizaremos o


Buildroot no treinamento.

✗ De qualquer forma, vale a pena conhecer e estudar o Yocto, pois


dependendo do projeto ele pode ser a melhor solução.
Embedded Labworks

CONFIGURANDO O BUILDROOT
✗ Permite configurar, dentre outras opções:
✗ Arquitetura e modelo da CPU.
✗ Toolchain.
✗ Bootloader.
✗ Kernel.
✗ Bibliotecas e aplicações.
✗ Tipos das imagens do rootfs (ext2, jffs2, etc).

✗ Para configurar:
$ make menuconfig
Embedded Labworks

CONFIGURANDO O BUILDROOT
Embedded Labworks

COMPILANDO O BUILDROOT
✗ A configuração também fica armazenada no arquivo .config.

✗ Para compilar:
$ make

✗ No final do processo de compilação, as imagens estarão


disponíveis no diretório output/images/:
$ ls output/images/
rootfs.ext4 u-boot.img zImage
Embedded Labworks

LABORATÓRIO

Gerando um sistema Linux com o Buildroot


Embedded Labworks

Linux embarcado

Bibliotecas e aplicações
Embedded Labworks

BIBLIOTECAS E APLICAÇÕES
✗ Uma das grandes vantagens do Linux é a enorme quantidade de
bibliotecas e aplicações disponíveis.

✗ Estas bibliotecas e aplicações são normalmente disponibilizadas e


distribuídas gratuitamente, e devido à sua natureza de código
aberto, podem ser analisadas e modificadas de acordo com o
projeto.

✗ Entretanto, o uso eficiente destes componentes nem sempre é fácil.

✗ É necessário encontrar e escolher o componente mais apropriado


para compilar e integrar ao seu projeto.
Embedded Labworks

PROCURANDO COMPONENTES
✗ Pesquisar em sites de busca (Google).

✗ Perguntar à comunidade (fóruns, listas de discussão, etc).

✗ Pesquisar outros produtos com Linux embarcado e identificar seus


componentes.

✗ Procurar em sites que hospedam projetos de software livre.


https://github.com
https://bitbucket.org
https://sourceforge.net
Embedded Labworks

COMO ESCOLHER?
✗ Requisitos técnicos: o componente deve satisfazer os requisitos técnicos
do projeto. Mas não esqueça também de que você mesmo pode
implementar estas melhorias (e depois compartilhar!).

✗ Atividade do projeto: o projeto deve ser ativo, releases frequentes, fórum


movimentado. É importante ter a garantia de manutenção e suporte.

✗ Qualidade do software: analise a qualidade do código. Seu uso em


diversos sistemas e uma comunidade ativa em geral significam uma
qualidade relativamente boa.

✗ Licença: a licença pode ser um impeditivo para o uso de determinado


componente de código aberto.
Embedded Labworks

Linux embarcado

Pacotes open source


Embedded Labworks

LINGUAGENS DE SCRIPT
✗ Interpretadores das mais comuns linguagens estão disponíveis:
✗ Shell script
✗ Python
✗ Perl
✗ Lua
✗ Ruby
✗ PHP
Embedded Labworks

EDITORES DE TEXTO
✗ vi: editor de texto em Linux embarcado mais usado.

✗ nano: ótimo editor para os iniciantes.

✗ uemacs: versão reduzida do editor do projeto GNU (emacs).


Embedded Labworks

FERRAMENTAS DE REDE
✗ dropbear: implementação de um cliente e servidor SSH. Bom para
ter acesso remoto seguro e transferir arquivos.

✗ dnsmasq: servidor DNS e DHCP.

✗ iptables: ferramentas userspace para gerenciar o firewall.

✗ netsnmp: implementação do protocolo SNMP.

✗ openssl: biblioteca para conexões SLL e TLS.

✗ vsftpd: servidor SFTP.


Embedded Labworks

SERVIDORES WEB
✗ Busybox http server: servidor HTTP do Busybox, com suporte à CGI e
autenticação, ocupando apenas 9K de tamanho. Não suporta SSL.

✗ Boa: servidor HTTP simples e rápido. Trabalha com apenas uma thread de
execução, multiplexando o processamento de conexões simultâneas. Sem
suporte a controle de acesso e SSL.

✗ thttpd: servidor HTTP simples, rápido e portável, com suporte à CGI e


autenticação. Não suporta SSL.

✗ lighttpd: servidor HTTP mais completo, ótimo para gerenciar altas cargas,
rápido e seguro, com suporte a controle de acesso, CGI e SSL.

✗ Outras opções estão surgindo como o Monkey HTTP e o Nginx.


Embedded Labworks

MULTIMEDIA
✗ Gstreamer: framework multimídia, permite codificar e decodificar diversos
containers e formatos multimídia. Suporta codecs de hardware através de
plugins.

✗ FFmpeg: ferramenta completa para gravar, converter e tocar mídias.


Implementa a libavcodec, uma das mais usadas e famosas bibliotecas de
áudio e vídeo da atualidade.

✗ Mplayer: player multimídia (usa a libavcodec).

✗ Alsalib: biblioteca associada com o sistema de som no Linux.

✗ Outras bibliotecas e codecs como flac, libogg, libtheora, libvorbis, libmad,


libsndfile, speex, etc.
Embedded Labworks

BANCO DE DADOS
✗ SQLite: uma pequena biblioteca em C que implementa um
gerenciador de banco de dados relacional bem leve que pode ser
embarcado no seu projeto.
✗ É ”a escolha” de banco de dados em Linux embarcado.
✗ Pode ser usado como uma biblioteca normal.
✗ Pode ser até compilada estaticamente com uma aplicação
proprietária, já que o SQLite é liberado sob domínio público.
Embedded Labworks

OUTRAS BIBLIOTECAS E APLICAÇÕES


✗ Compressão e descompressão de arquivos.

✗ Criptografia.

✗ Manipulação do hardware.

✗ Comunicação entre processos.

✗ Tratamento de arquivos texto (XML, JSON, etc).

✗ Camada gráfica (veremos em detalhes mais adiante no treinamento).

✗ Etc!
Embedded Labworks

Linux embarcado

Licenças
Embedded Labworks

LICENÇAS
✗ Todo software sob uma licença de software livre dá aos usuários 4
liberdades básicas:
✗ Liberdade de executar (como quiser e para qualquer propósito).
✗ Liberdade de estudar e adaptar o código-fonte às suas necessidades.
✗ Liberdade de redistribuir cópias do código-fonte.
✗ Liberdade de distribuir cópias das suas versões modificadas.

✗ Veja o link abaixo para uma definição completa de software livre:


https://www.gnu.org/philosophy/free-sw.html
Embedded Labworks

LICENÇAS (cont.)
✗ As licenças de software livre possuem basicamente duas categorias:
✗ Licenças copyleft.
✗ Licenças non-copyleft (permissivas).

✗ Quando você modifica e distribui um software sob licença copyleft, você


precisa liberá-lo sob a mesma licença original.
✗ Mesma liberdade a novos usuários.
✗ Incentivo para você contribuir de volta à comunidade.

✗ Licenças non-copyleft não tem estes requisitos, e versões modificadas


podem ser mantidas proprietárias, sendo necessário apenas manter a
atribuição de autoria do projeto ao autor original.
Embedded Labworks

GPL
✗ GNU General Public Licence.

✗ Cobre mais da metade dos projetos de software livre, incluindo o


U-Boot, o Linux, o Busybox e muitas aplicações.

✗ É uma licença copyleft:


✗ Trabalhos derivados precisam ser liberados sob a mesma licença.
✗ Programas linkados com uma biblioteca GPL também são
considerados um trabalho derivado, e precisam ser liberados sob a
mesma licença.
Embedded Labworks

GPL (cont.)
✗ Boa parte dos projetos são cobertos pela GPLv2.

✗ Alguns softwares são cobertos pela GPLv3.


✗ Principal diferença: o usuário deve ser capaz de rodar versões
modificadas do programa no dispositivo (segundo a licença, caso seja
um dispositivo de consumo).
Embedded Labworks

LGPL
✗ GNU Lesser General Public Licence.

✗ Licença usada nas maioria das bibliotecas.

✗ É uma licença copyleft:


✗ Trabalhos derivados precisam ser liberados sob a mesma licença.
✗ Mas um programa linkado com uma biblioteca LGPL pode ser mantido
proprietário.
✗ Porém, o usuário deve ter a possibilidade de atualizar a biblioteca
independentemente da aplicação.
✗ A solução mais simples é através de linkagem dinâmica.
Embedded Labworks

CUIDADOS COM A GPL


✗ De forma geral, os seguintes cuidados devem ser tomados com
softwares de licença GPL em produtos comerciais:
✗ Não linkar um software proprietário com bibliotecas GPL.
✗ Não linkar estaticamente um software proprietário com bibliotecas
LGPL.
✗ Evitar o uso de aplicações e bibliotecas de licença GPLv3 e LGPLv3.

✗ Lembrando que não existe nenhuma obrigação se o seu software ou


produto não for distribuído!
Embedded Labworks

LICENÇAS NON-COPYLEFT
✗ Versões modificadas de um software sob licença non-copyleft
podem ser mantidas proprietárias, desde que seja mantida a
autoria da versão original.

✗ Também chamadas de licenças permissivas, existe uma grande


família de licenças non-copyleft relativamente similares em suas
características, dentre elas:
✗ Apache Licence
✗ BSD Licence
✗ MIT Licence
✗ X11 Licence
Embedded Labworks

LICENÇAS (EXEMPLOS)
✗ Você modificou o Linux, o Busybox, o U-Boot ou outro software GPL:
✗ Você precisa liberar o software com as modificações realizadas sob
a mesma licença, e estar pronto para distribuir o código-fonte para
seus clientes.

✗ Você modificou uma biblioteca qualquer sob a licença LGPL:


✗ Você precisa liberar as versões modificadas sob a mesma licença.
Embedded Labworks

LICENÇAS (EXEMPLOS)
✗ Você criou uma aplicação que utiliza uma biblioteca LGPL:
✗ Você pode manter sua aplicação proprietária desde que a linkagem
com a biblioteca seja dinâmica.

✗ Você fez modificações em um software non-copyleft:


✗ Você pode manter suas modificações proprietárias, mas precisa
atribuir o crédito aos autores do projeto original.
Embedded Labworks

APLICANDO LICENÇAS
✗ Não existe uma regra única para aplicar licenças em software open
source, já que cada licença possui sua própria “receita de bolo”. De
qualquer forma, um projeto open source possui normalmente:
✗ Uma indicação da licença utilizada e uma cópia completa desta
licença no site do projeto.
✗ Uma cópia completa da licença utilizada no diretório principal do
código-fonte do projeto. Normalmente este arquivo é nomeado como
LICENCE, LICENCE.TXT, COPYRIGHT ou COPYING.
✗ Um descritivo da licença utilizada no cabeçalho de cada arquivo-
fonte do projeto. O conteúdo deste descritivo depende da licença
utilizada.
Embedded Labworks

Linux embarcado

Compilando bibliotecas e aplicações


Embedded Labworks

MECANISMOS DE COMPILAÇÃO
✗ Todo software possui um sistema de build ou mecanismo de
compilação.

✗ Dentre os projetos de software livre, podemos destacar os


seguintes mecanismos de compilação:
✗ Makefile: processado pela ferramenta make do projeto GNU.
✗ Autotools: sistema de build de aplicações do projeto GNU.
✗ Cmake: sistema de build de aplicações mais novo e moderno, usado
em diversos projetos de software livre como o KDE e o MySQL.
✗ Qmake: Criado pela Trolltech e utilizando atualmente em alguns
projetos como o Qt.
Embedded Labworks

MAKE
✗ O make é uma ferramenta do projeto GNU bastante utilizada para
compilar aplicações e bibliotecas.
https://www.gnu.org/software/make/

✗ Ele interpreta arquivos normalmente chamados Makefile, que


contém as instruções a serem executadas durante o processo de
compilação.

✗ Para compilar uma aplicação ou biblioteca baseada em makefile,


basta executar o make (considerando-se que o arquivo Makefile
esteja no diretório corrente):
$ make
Embedded Labworks

MAKEFILE (EXEMPLO 1)
TOOLCHAIN:=/opt/labs/ex/09/buildroot/output/host/usr/bin/

CROSS_COMPILE:=arm-linux-

PATH:=${TOOLCHAIN}:${PATH}

all:
${CROSS_COMPILE}gcc teste.c -o teste

clean:
rm -Rf *.o teste
Embedded Labworks

MAKEFILE (EXEMPLO 2)
src = $(wildcard src/*.c) \
$(wildcard src/net/*.c) \
$(wildcard src/fs/*.c)

obj = $(src:.c=.o)

CC ?= gcc

LDFLAGS = -lpng -lm


CFLAGS = -Wall -Werror -O2

app: $(obj)
$(CC) -o $@ $^ $(LDFLAGS)

%.o: %.c
$(CC) $(CFLAGS) -o $@ -c $<

.PHONY: clean
clean:
rm -f $(obj) app
Embedded Labworks

LABORATÓRIO

Desenvolvendo aplicações com Makefile


Embedded Labworks

AUTOTOOLS
✗ Autotools é o nome dado ao sistema de build de aplicações do
projeto GNU, que contém um conjunto de ferramentas para auxiliar
na compilação de uma biblioteca ou aplicação.

✗ Seu objetivo é ser um sistema de build universal e multiplataforma.

✗ Através de um script de configuração, o autotools irá:


✗ Analisar e verificar se a plataforma-alvo possui os requisitos
necessários para compilar a biblioteca ou aplicação.
✗ Configurar a biblioteca ou aplicação, habilitando ou desabilitando
funcionalidades antes da compilação.
✗ Gerar o makefile para compilar a biblioteca ou aplicação.
Embedded Labworks

AUTOTOOLS (cont.)
✗ O autotools é composto pelas seguintes ferramentas:
✗ Autoconf: ferramenta responsável por gerar os scripts de configuração.
✗ Automake: ferramenta responsável por gerar os makefiles.
✗ Libtool: ferramenta responsável por compilar e criar de forma portável
as bibliotecas da aplicação.

✗ Na prática, para compilar um software baseado em autotools,


normalmente executamos os comandos abaixo:
$ ./configure
$ make
$ make install
Embedded Labworks

CROSS-COMPILANDO COM AUTOTOOLS


✗ Para compilar um software baseado em autotools para uma outra
plataforma, você precisará prestar atenção em alguns detalhes adicionais.

✗ No comando de configuração, você precisa passar o prefixo do toolchain na


opção --host.

✗ Nos casos em que o software a ser compilado não suportar a opção --


host, você pode passar informações sobre o toolchain em variáveis de
ambiente como CC, CFLAGS e LDFLAGS.

✗ No comando de instalação, você precisa indicar onde irá instalar o


software usando a variável DESTDIR, que deve estar apontando para o
diretório onde se encontra o rootfs do sistema.
Embedded Labworks

AUTOTOOLS (EXEMPLO)
$ ./configure --host=arm-linux --enable-debug --disable-nls
checking whether make sets $(MAKE)... yes
checking for arm-linux-strip... arm-linux-strip
checking for arm-linux-gcc... arm-linux-gcc
checking for C compiler default output file name... a.out
checking whether the C compiler works... yes
checking whether we are cross compiling... yes
checking for suffix of executables...
[...]
config.status: creating Makefile
config.status: creating m4/Makefile
config.status: creating lib/Makefile
[...]

$ make

$ make DESTDIR=/opt/labs/ex/06/rootfs install


Embedded Labworks

LABORATÓRIO

Compilando aplicações baseadas em autotools


Embedded Labworks

Linux embarcado

Bibliotecas gráficas
Embedded Labworks

FRAMEBUFFER
Toolkit Gráfico Window
Aplicação Aplicação (Qt, Gtk) Manager/
Aplicação
User

Aplicação Biblioteca Toolkit Servidor Gráfico


(SDL, DirectFB) Gráfico (Qt) (X/Wayland)

Framebuffer framework
/dev/fbX
Kernel
Framebuffer Framebuffer
driver driver

Controladora Controladora Hardware


VGA LCD
Embedded Labworks

INPUT
Aplicação Biblioteca Toolkit Servidor
gráfica gráfico gráfico
User

Input event driver (/dev/input/eventX)


Input framework

Input driver Input driver Input driver Input driver Input driver Kernel

Serio USB I2C GPIO USB

Teclado Mouse Touchscreen Teclado Joystick Hardware


PS2 Matricial
Embedded Labworks

SDL
✗ SDL (Simple Directmedia Layer) é uma biblioteca multimídia para
acesso de baixo nível em dispositivos de entrada (teclado, mouse,
joystick, etc) e saída (vídeo, áudio, etc).
https://www.libsdl.org/

✗ Suporta aceleração de hardware 3D via OpenGL e acesso ao


framebuffer para gráficos 2D.

✗ Usada basicamente para desenvolvimento de aplicações que


desejam acessar diretamente o hardware. Exemplos: jogos, mídia
players, etc.
Embedded Labworks

JOGO CIVILIZATION USANDO SDL


Embedded Labworks

LEFT FOR DEAD 2 TAMBÉM USA SDL


Embedded Labworks

DIRECTFB
✗ Biblioteca de baixo nível para trabalhar com interface gráfica.
https://github.com/deniskropp/DirectFB

✗ Pode ser utilizada para desenvolvimento de UI em aplicações


simples, ou como uma camada de baixo nível para bibliotecas
gráficas de mais alto nível.

✗ Manipula eventos de entrada como mouse, teclado, joystick, etc.

✗ Capacidade de trabalhar com aceleradores gráficos em diferentes


hardwares.
Embedded Labworks

MEDIACENTER USANDO DIRECTFB


Embedded Labworks

X.ORG KDRIVE
✗ Kdrive (antes Tiny-X) é a implementação do servidor X para
sistemas embarcados.
https://www.x.org

✗ Também trabalha diretamente sobre o framebuffer.

✗ Suporte total ao protocolo X11, e permite o uso de qualquer


aplicação ou biblioteca baseada no X11.

✗ O uso é feito normalmente com um Toolkit rodando por cima (Qt,


Gtk, EFL, WxEmbedded, etc).
Embedded Labworks

KDE USANDO KDRIVE


Embedded Labworks

Linux embarcado

Toolkits gráficos
Embedded Labworks

GTK
✗ Famoso toolkit usado no Gnome, disponibilizando uma API baseada
em widgets para o desenvolvimento de aplicações gráficas.
https://www.gtk.org/

✗ Pode usar o servidor X ou o DirectFB como backend gráfico.

✗ Não inclui um sistema de janelas.

✗ Em desktop é comum o Gnome como sistema de janelas. Em


sistemas embarcados, uma possibilidade é o Matchbox.
Embedded Labworks

EXEMPLOS DE USO DO GTK


OpenMoko

Maemo

Interface
proprietária
Embedded Labworks

Qt
✗ O Qt é um framework completo para o desenvolvimento de
aplicações multiplataforma desktop e mobile.
https://www.qt.io/

✗ Suporta inúmeras plataformas, incluindo os sistemas operacionais


GNU/Linux, Windows, MacOS, Android e iOS e as arquiteturas x86,
x86-64 e ARM.

✗ O acesso ao hardware (display, GPU, etc) é feito através de plugins,


suportando diversas interfaces como framebuffer (linuxfb), OpenGL
(eglfs), directfb (directfb), X11 (xcb), Wayland (wayland), VNC (vnc),
etc.
Embedded Labworks

Qt (cont.)
✗ Diversas aplicações e produtos famosos utilizam o Qt, incluindo as
smart TVs da LG e os softwares Autodesk Maya, Google Earth e
VirtualBox.
https://resources.qt.io/customer-stories-all

✗ É implementado em C++ mas possui bindings para outras


linguagens, incluindo Python, Go, Rust, PHP e Java.
Embedded Labworks

EXEMPLOS DE USO DO QT

Express GPS

OpenMoko Netflix Player


Embedded Labworks

HISTÓRICO DO QT
✗ 1990: começou a ser escrito pela Trolltech.

✗ 1995: primeiro release público do Qt (licenças GPLv2 e comercial).

✗ 2008: Nokia compra a Trolltech.

✗ 2009: Lançado o Qt Creator e o Qt 4.5 (licença LGPLv2).

✗ 2011: Digia compra da Nokia a licença comercial e os direitos do Qt.

✗ 2014: Digia cria a subsidiária "The Qt Company".

✗ 2016: Lançamento do Qt 5.7, onde a maioria do módulos é relicenciado para


LGPLv3.
Embedded Labworks

APIs
✗ O Qt possui uma API completa para o desenvolvimento de
aplicações, incluindo bibliotecas para trabalhar com arquivos,
threads, networking, banco de dados, multimedia, localização,
gráficos, etc.

✗ Possui uma API baseada em widgets para o desenvolvimento de


aplicações com interface gráfica.

✗ Através do módulo Qt Quick e da linguagem declarativa QML,


possibilita o desenvolvimento de aplicações gráficas ricas e
fluídas.
Embedded Labworks

QT QUICK
✗ Na mudança do Qt4 para o Qt5, houve um foco grande no
desenvolvimento de interfaces gráficas ricas através de um
módulo chamado Qt Quick, baseado em três principais
componentes:
✗ Uma linguagem declarativa chamada QML.
✗ Um interpretador Javascript.
✗ Elementos para o desenvolvimento de uma interface gráfica rica, com
bastante foco em animação e efeitos 3D.

✗ Apesar da grande quantidade de novos recursos, o Qt5 mantém


compatibilidade com as versões anteriores do Qt.
Embedded Labworks

EXEMPLOS QT QUICK
Embedded Labworks

LICENÇAS
✗ Até a versão 5.3, os principais módulos do Qt eram licenciados com
LGPLv2, uma licença bastante amigável do ponto de vista
comercial.

✗ A partir do Qt 5.4, os principais módulos do Qt foram aos poucos


relicenciados para LGPLv3, que pode ser uma barreira para
produtos comerciais. Para estes casos, pode ser necessário
adquirir uma licença comercial do Qt.

✗ Nas últimas versões do Qt, a maioria dos módulos tem licença


LGPLv3.
Embedded Labworks

LICENÇA (Qt v5.6)

Fonte: https://www.embeddeduse.com/2016/04/10/using-qt-5-6-and-later-under-lgpl/
Embedded Labworks

LICENÇA (Qt v5.7)

Fonte: https://www.embeddeduse.com/2016/04/10/using-qt-5-6-and-later-under-lgpl/
Embedded Labworks

QT CREATOR
✗ Ambiente de desenvolvimento integrado (IDE) completo para o Qt.
https://www.qt.io/download

✗ Disponível para Linux, Windows e MacOS.

✗ Suporta o desenvolvimento de aplicações em modo texto,


aplicações gráficas através de widgets e aplicações multimídia
ricas utilizando QML.

✗ Possibilita o desenvolvimento, testes e depuração remota em um


dispositivo com Linux embarcado.
Embedded Labworks

QT CREATOR (EDITOR)
Embedded Labworks

QT CREATOR (WIDGETS)
Embedded Labworks

QT CREATOR (QML)
Embedded Labworks

LABORATÓRIO

Desenvolvimento de aplicações em Qt
Embedded Labworks

Linux embarcado

Debugging
Embedded Labworks

GDB
✗ O GDB (GNU Debugger) é a ferramenta de depuração interativa
padrão do projeto GNU.
https://www.gnu.org/software/gdb/

✗ Está disponível para diversas arquiteturas de CPU, incluindo ARM,


x86, MIPS e PPC.

✗ A interface da ferramenta é via linha de comandos.

✗ Possui diversos frontends gráficos, incluindo o DDD e o Eclipse.


Embedded Labworks

DEBUG REMOTO
✗ Como no target temos o binário da aplicação em execução e no
host o código-fonte e as ferramentas de desenvolvimento, depurar
a aplicação no target envolve uma arquitetura cliente-servidor.

✗ No target, executamos a aplicação com o servidor GDB (gdbserver).

✗ No host, utilizamos o cliente GDB do toolchain para se conectar ao


servidor no target e controlar a execução da aplicação.
Embedded Labworks

DEBUG REMOTO (cont.)

Host Target

arm-linux-gdb gdbserver
Conexão
Serial ou
Ethernet

Binários e bibliotecas Binários e bibliotecas


com símbolos de sem símbolos de
debugging debugging
Embedded Labworks

DEBUG REMOTO (cont.)


✗ No target, inicie o servidor do GDB passando a aplicação a ser
depurada:
# gdbserver localhost:1234 /usr/sbin/main

✗ No host, execute o GDB do toolchain de compilação cruzada,


passando o binário da aplicação com símbolos de debugging:
$ arm-linux-gdb main

✗ E se conecte ao target pela rede:


(gdb) target remote 192.168.0.2:1234
Embedded Labworks

COMANDOS DO GDB
✗ Assim que se conectar ao servidor do GDB, coloque breakpoints
nos trechos de código de interesse.
(gdb) break main

✗ E execute a aplicação com o comando continue.


(gdb) continue

✗ Se acontecer um crash, a aplicação irá automaticamente parar a


execução na linha de código que gerou o problema.
Embedded Labworks

COMANDOS DO GDB (cont.)


✗ Ao parar em um breakpoint, utilize o comando next para executar a
próxima linha de código (step over):
(gdb) next

✗ Utilize o comando step para entrar em uma função (step into):


(gdb) step

✗ Utilize o comando print para imprimir o valor de uma variável:


(gdb) print i
Embedded Labworks

COMANDOS DO GDB (cont.)


✗ O comando backtrace pode ser utilizado para exibir a pilha de
chamadas de função da aplicação:
(gdb) backtrace

✗ Para encerrar o processo de depuração, desconecte-se do servidor


do GDB com o comando detach.
(gdb) detach

✗ Para sair do GDB, execute o comando quit.


(gdb) quit
Embedded Labworks

MODO TUI
✗ O modo tui do GDB irá abrir uma janela com o código-fonte da
aplicação, facilitando a visualização do processo de depuração:
$ arm-linux-gdb main --tui
Embedded Labworks

CORE DUMP
✗ Core dump é um arquivo que contém a imagem da memória de um
processo no momento da sua finalização.

✗ O core dump é gerado durante o processamento de alguns sinais,


incluindo SIGQUIT, SIGILL, SIGABRT, SIGFPE e SIGSEGV.

✗ Uma das situações mais comuns de geração do core dump é


quando uma aplicação encerra sua execução abruptamente devido
a um crash (acesso inválido à memória, divisão por zero, etc).

✗ O core dump pode ser utilizado em um debugger para inspecionar o


estado do processo no momento em que ele foi encerrado.
Embedded Labworks

CORE DUMP (cont.)


✗ Diversos requisitos precisam ser atendidos para que o arquivo de
core dump seja gerado, incluindo:
✗ O processo precisa de permissão para criar o arquivo de core dump.
✗ É necessário ter espaço suficiente no sistema de arquivos.
✗ A configuração de limite do tamanho do arquivo de core do processo
(RLIMIT_CORE) precisa estar configurada corretamente.

✗ A configuração do RLIMIT_CORE do processo é normalmente zero, o


que faz com que o arquivo de core dump não seja gerado por padrão.
Para alterar esta configuração, podemos utilizar o comando ulimit.
# ulimit -c unlimited
Embedded Labworks

CORE DUMP (cont.)


✗ Por padrão, o nome do arquivo de core dump é core, gerado no
mesmo diretório onde a aplicação foi executada.

✗ O nome do arquivo de core do processo pode ser alterado


escrevendo em /proc/sys/kernel/core_pattern.

✗ Mais informações estão disponíveis na página de manual do core.


$ man 5 core
Embedded Labworks

EXEMPLO: CORE DUMP


int main(int argc, const char *argv[])
{
int i;
char *c = 0;

for (i = 0; i < 10; i++) {


if (i == 5) {
*c = 10;
}
}

return 0;
}
Embedded Labworks

EXEMPLO: CORE DUMP (cont.)


# ulimit -c unlimited

# main
Segmentation fault (core dumped)

# ls -l core
-rw------- 1 root root 217088 Dec 6 2018 core
Embedded Labworks

EXEMPLO: CORE DUMP (cont.)


$ arm-linux-gdb -c core main
Core was generated by `main'.
Program terminated with signal SIGSEGV, Segmentation fault.
#0 0x000104b0 in main (argc=1, argv=0xbe96de64) at main.c:8
8 *c = 10;

(gdb) backtrace
#0 0x000104b0 in main (argc=1, argv=0xbe96de64) at main.c:8

(gdb) print c
$1 = 0x0
Embedded Labworks

VALGRIND
✗ O Valgring é um framework de instrumentação para se criar
ferramentas de análise dinâmica de aplicações.
http://valgrind.org/

✗ Atualmente, o Valgrind fornece ferramentas de análise de memória


e profiling de aplicações.

✗ Um dos principais usos do Valgring é na análise de alocação


dinâmica de memória e detecção de memory leak nas aplicações.
Embedded Labworks

APLICAÇÃO COM BUG


int txData(char *data)
{
unsigned char *ptr = NULL, *buf = NULL;
int size = strlen(data);

if ((ptr = buf = (unsigned char*)malloc(size + 3)) == NULL)


return(-1);

*ptr++ = STX;
strncpy(ptr, data, size);
ptr += size;
*ptr++ = ETX;

if (txSerial(buf, size + 3) == -1)


return(-2);

free(buf);

return 0;
}
Embedded Labworks

TESTANDO COM VALGRIND


$ valgrind ./leak
==3811== Memcheck, a memory error detector
==3811== Copyright (C) 2002-2009, and GNU GPL, by Julian Seward et al.
==3811== Using Valgrind-3.6.0.SVN-Debian and LibVEX; rerun with -h for
copyright info
==3811== Command: ./leak
==3811==
Erro ao enviar mensagem!
==3811==
==3811== HEAP SUMMARY:
==3811== in use at exit: 13 bytes in 1 blocks
==3811== total heap usage: 1 allocs, 0 frees, 13 bytes allocated
==3811==
==3811== LEAK SUMMARY:
==3811== definitely lost: 13 bytes in 1 blocks
==3811== indirectly lost: 0 bytes in 0 blocks
==3811== possibly lost: 0 bytes in 0 blocks
==3811== still reachable: 0 bytes in 0 blocks
==3811== suppressed: 0 bytes in 0 blocks
==3811== Rerun with --leak-check=full to see details of leaked memory
==3811==
==3811== For counts of detected and suppressed errors, rerun with: -v
==3811== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 13 from 8)
Embedded Labworks

STRACE
✗ O strace (system calls tracer) permite capturar todas as chamadas
de sistema realizadas pela aplicação.
https://strace.io/

✗ Bastante útil para depurar uma aplicação que fecha sem exibir
nenhuma mensagem de erro, ou então para fazer engenharia
reversa em uma aplicação a qual você tenha somente o binário.

✗ Disponível em sistemas GNU/Linux, e pode ser compilada para sua


plataforma alvo.
Embedded Labworks

EXEMPLO STRACE
$ strace cat Makefile
execve("/bin/cat", ["cat", "Makefile"], [/* 38 vars */]) = 0
brk(0) = 0x98b4000
access("/etc/ld.so.nohwcap", F_OK) = -1 ENOENT (No such file or directory)
mmap2(NULL, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) =
access("/etc/ld.so.preload", R_OK) = -1 ENOENT (No such file or directory)
open("/etc/ld.so.cache", O_RDONLY) = 3
fstat64(3, {st_mode=S_IFREG|0644, st_size=111585, ...}) = 0
mmap2(NULL, 111585, PROT_READ, MAP_PRIVATE, 3, 0) = 0xb7f69000
close(3) = 0
access("/etc/ld.so.nohwcap", F_OK) = -1 ENOENT (No such file or directory)
open("/lib/tls/i686/cmov/libc.so.6", O_RDONLY) = 3
fstat64(3, {st_mode=S_IFREG|0755, st_size=1442180, ...}) = 0
mprotect(0xb7f62000, 4096, PROT_NONE) = 0
mmap2(0xb7f63000, 12288, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|
MAP_DENYWRITE, 3, 0x15c) = 0xb7f63000
mmap2(0xb7f66000, 9840, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|
MAP_ANONYMOUS, -1, 0) = 0xb7f66000
close(3) = 0
...
Embedded Labworks

LTRACE
✗ O ltrace (library calls tracer) permite capturar todas as chamadas
de bibliotecas realizadas e sinais recebidos pela aplicação.
https://www.ltrace.org/

✗ Complementa o uso do strace, que não exibe as chamadas de


biblioteca.
Embedded Labworks

EXEMPLO LTRACE
$ ltrace nedit index.html
sscanf(0x8274af1, 0x8132618, 0x8248640, 0xbfaadfe8, 0) = 1
sprintf("const 0", "const %d", 0) = 7
strcmp("startScan", "const 0") = 1
strcmp("ScanDistance", "const 0") = -1
strcmp("const 200", "const 0") = 1
strcmp("$list_dialog_button", "const 0") = -1
strcmp("$shell_cmd_status", "const 0") = -1
strcmp("$read_status", "const 0") = -1
strcmp("$search_end", "const 0") = -1
strcmp("$string_dialog_button", "const 0") = -1
strcmp("$rangeset_list", "const 0") = -1
strcmp("$calltip_ID", "const 0") = -1
...
Embedded Labworks

SUMÁRIO LTRACE
$ ltrace -c cat /etc/resolv.conf
% time seconds usecs/call calls function
------ ----------- ----------- --------- --------------------
22.10 0.000795 795 1 setlocale
8.51 0.000306 153 2 read
7.81 0.000281 281 1 write
7.65 0.000275 137 2 __fxstat
6.84 0.000246 61 4 __freading
6.31 0.000227 113 2 fclose
4.39 0.000158 158 1 open
4.06 0.000146 146 1 close
3.92 0.000141 141 1 posix_fadvise
3.59 0.000129 64 2 fileno
3.56 0.000128 64 2 __fpending
...
------ ----------- ----------- --------- --------------------
100.00 0.003597 29 total
Embedded Labworks

LABORATÓRIO

Depurando aplicações com o GDB


Embedded Labworks

Linux embarcado

Ambiente de desenvolvimento de aplicações


Embedded Labworks

DESENVOLVENDO APLICAÇÕES
✗ Um sistema Linux embarcado é um sistema Linux normal, apenas com
um conjunto menor e mais enxuto de componentes.

✗ Em termos de desenvolvimento de aplicações, é o mesmo processo


comparado ao desenvolvimento para desktop, o que inclusive facilita os
testes.

✗ Você pode reusar aplicações e bibliotecas sem nenhuma adaptação na


maioria das vezes.

✗ Mas sempre leve em conta a limitação de recursos do seu equipamento


(capacidade de processamento, memória e armazenamento).
Embedded Labworks

LINGUAGEM DE PROGRAMAÇÃO
✗ A linguagem padrão para desenvolvimento de aplicações no nível do
sistema é a linguagem C. A biblioteca C padrão esta sempre presente em
sistemas Linux.

✗ C++ pode ser usada para o desenvolvimento de aplicações que requerem


um nível maior de abstração.

✗ Java também é uma possibilidade, mas leve em consideração o consumo


de recursos do dispositivo.

✗ Linguagens de script como Python e shell são muito úteis em determinadas


tarefas, e podem ajudar a diminuir o tempo de desenvolvimento, mas leve
em consideração questões como consumo de recursos e segurança.
Embedded Labworks

AMBIENTES DE DESENVOLVIMENTO
✗ Eclipse: Uma IDE completa baseada em plugins, ideal para
desenvolver outras IDEs. Roda em cima de uma JVM. Diversas
empresas de sistemas embarcados tem usado a plataforma
Eclipse para desenvolver IDEs para seus produtos. Ex: MontaVista
DevRocket, TimeSys TimeStorm, Windriver Workbench, TI Code
Composer, NXP MCUxpresso, etc.

✗ Kdevelop: uma IDE completa. Roda nativamente. Suporta diversas


linguagens incluindo C, C++ e Java.

✗ Outras opções: Geany, Code::Blocks, Netbeans, Sublime Text, Kate,


Atom, Visual Studio Code, vim, emacs, etc.
Embedded Labworks

CONTROLE DE VERSÃO
✗ CVS: Foi bastante popular, mas possui diversas deficiências e hoje
não é mais utilizado em novos projetos.

✗ Subversion: Também chamado de SVN, criado como substituto do


CVS, removendo diversas limitações e com melhor performance.

✗ Git: Sistema de controle de versão distribuído criado por Linus


Torvalds, se tornou o padrão para novos projetos open source.

✗ Mercurial: Trabalha da mesma forma que o Git e pode ser uma


opção alternativa para sistemas de controle de versão distribuído.
Embedded Labworks

LABORATÓRIO

Desenvolvendo e depurando com o Eclipse


Embedded Labworks

Linux Embarcado

E agora?
Embedded Labworks

RECURSOS ONLINE
✗ Site do kernel Linux:
https://www.kernel.org/

✗ Linux kernel mailing list:


https://lkml.org/

✗ Acompanhar as mudanças nas novas versões do kernel:


https://kernelnewbies.org/LinuxChanges

✗ Notícias e novidades sobre o desenvolvimento do kernel:


https://lwn.net/
Embedded Labworks

RECURSOS ONLINE (cont.)


✗ Linux Foundation (notícias, blog e vídeos):
https://www.linuxfoundation.org/

✗ Bootlin (documentos e vídeos):


https://bootlin.com/

✗ Revista eletrônica sobre Linux:


https://www.linuxjournal.com/

✗ Wiki dedicada a Linux embarcado:


https://elinux.org
Embedded Labworks

RECURSOS ONLINE (cont.)


✗ Site Embarcados:
https://www.embarcados.com.br/

✗ Grupo sis_embarcados:
https://groups.google.com/forum/#!forum/sis_embarcados

✗ Blog do Sergio Prado:


https://sergioprado.org/
Embedded Labworks

LIVRO SOFTWARE LIVRE

The Cathedral & The Bazaar


Eric S. Raymond
Embedded Labworks

LIVROS DESENVOLVIMENTO DE SOFTWARE


The Linux programming interface
Michael Kerrisk

The art of UNIX Programming


Eric S. Raymond
Embedded Labworks

LIVROS LINUX EMBARCADO

Embedded Linux Primer


Christopher Hallinan

Building Embedded Linux Systems


Karim Yaghmour & others
Embedded Labworks

LIVROS LINUX KERNEL

Linux Kernel in a Nutshell


Greg Kroah-Hartman

Linux Kernel Development


Robert Love
Embedded Labworks

LIVROS LINUX DEVICE DRIVERS


Essential Linux Device Drivers
Sreekrishnan Venkateswaran

Linux Device Drivers


Jonathan Corbet & others
Embedded Labworks

PERGUNTAS OU COMENTÁRIOS FINAIS?


OBRIGADO!
E-mail sergio.prado@e-labworks.com
Website http://e-labworks.com

Embedded Labworks

Por Sergio Prado. São Paulo, Março de 2019


® Copyright Embedded Labworks 2004-2019. All rights reserved.

Você também pode gostar

pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy