Author Archives: ftonello

Easy way to get a priority of a process in Linux

So, I was researching online on how to get a priority of a Linux process (RT or not) and all asnwers used GNU top  or GNU ps , which is fine, but not on my embedded system that uses a simpler version of those tools from busy-box. Anyway, I know that procfs somehow shows that data, right. So with the help of man 5 proc  I wrote this small shell script that you can easily use to get the scheduling policy and its priority.

You can use as ./prio.sh PID .

I find this very useful on listing kernel thread priorities for PREEMPT_RT .

Enjoy.

 

QEMU para desenvolvimento do Linux Kernel

Este post é um complemento do artigo anterior: Introdução a módulos no Linux Kernel.

QEMU é software livre hypervisor do tipo 2 que faz virtualização de hardware. É uma ótima ferramenta de auxílio ao desenvolvimento do Linux, conforme eu postei no artigo anterior. Neste artigo eu gostaria de expandir um pouco como usar o QEMU para desenvolvimento de novas funcionalidades no Kernel que afetam o user-space. Neste caso é interessante ter mais do que o busy-box como ferramentas de user-space, pois várias ferramentas de desenvolvimento, daemons e outros programas  estariam faltando. Por isso vamos utilizar uma imagem QEMU com Arch-Linux instalado básico.

Criar imagem para o QEMU

Obviamente é necessário fazer o download do QEMU e da iso Arch-Linux na sua máquina.

O QEMU provê ferramentas para a criação de um disco virtual que o próprio entende. Para isso vamos então criar um disco de 2G de tamanho, por exemplo:

Agora vamos bootar com a iso Arch-Linux previamente baixada:

Onde <archlinux.iso> é o arquivo baixado enteriormente.

Siga as instruções básicas de instalação do Arch. No meu caso, o que eu fiz foi o seguinte:

  1. Criei uma partição no disco usando fdisk
  2. Formatei esta partição como ext4 usando mkfs.ext4
  3. Montei ela em /mnt com # mount /dev/sda1 /mnt
  4. Criei uma pasta de boot em /mnt/boot  que não será usada (vamos usar nossa versão do Kernel e não a do Arch)
  5. Rodei # pacstrap /mnt base
  6. Criei fstab com # genfstab -U /mnt >> /mnt/etc/fstab
  7. Fiz chroot # arch-chroot /mnt
  8. Configurei o Time Zone e Locale apenas. O resto não é necessário para o que vamos fazer.
  9. No meu caso eu também instalei vim, bluez e alsa, já que uso esses pacotes para desenvolvimento. # pacman -S vim bluez alsa gdb . Se isso não functionar, rode o dhcpcd  antes na interface de rede habilitada.
  10. # exit  e # umount /mnt

Pronto!

Rodando tudo

Agora é tudo muito simples. Como não vamos usar o Kernel que vem com o Arch, eu recomendo configurar seu Kernel com todos os módulos que você precisa como built-in. Isso é important, já que o udev  da distro não conseguirá rodar modprobe  nos módulos que vem no Arch.

Também usamos a flag -enable-kvm  no QEMU. Isso faz com que o mesmo não interprete as instruções x86_64 e sim o processador nativo, aumentando muito a performance da nossa máquina virtual.

Tudo isso é meio que auto explicativo. Mas algumas coisas interessantes aqui é o argumento -nographic  e o -append . Ambos são usados para o QEMU direcionar o output do console no terminal. -m  é a quantidade de memória RAM.

Dicas

QEMU é uma ferramente bem avançada com suporte a muitas coisas. É preciso ler sua documentação e tentar brincar um pouco com as configurações.

Mas posso dar alguns exemplos aqui que eu mesmo uso.

Acessar periféricos USB

Adicione as seguintes linhas na chamada

Óbvio que 0xAAAA e 0xBBBB devem ser os valores respectivos do seu aparelho. Você pode facilmente obtê-lo com lsusb .

Seu usuário precisará ter acesso privilegiado ao device node.

Pasta compartilhada

Por padrão o QEMU já roda com -net nic -net user . Mas como queremos compartilhar pastas entre o host e o guest, vamos usar uma opção de rodar o samba junto.

O QEMU irá rodar o samba já tudo configurado, e dentro do sistema guest (ArchLinux) você precisa montar uma pasta com o seguinte comando:

O IP é fixo pelo QEMU mesmo e o caminho do SMB também. Agora o ~/host  pode ser qualquer lugar, claro.

Outras dicas

  • Uma dica importante é usar # shutdown -h now  na máquina virtual para desligá-la.
  • Rode # stty -F /dev/ttyS0 cols <X> rows <Y>  para configurar o terminal do Linux para não limitar as linhas e colunas menores do que seu terminal é capaz, ficando muito chato de usar. Para conseguir os valores de X e Y, eu rodo o comando resize  existente no xterm do host.

Se tiver mais dicas, exemplos ou correções, por favor, poste nos comentários. Eu vou agregar todas as dicas e exemplos de comandos que forem úteis para desenvolvimento do Linux.


Permission is granted to copy, distribute and/or modify this document under the terms of the GNU Free Documentation License, Version 1.3 or any later version published by the Free Software Foundation; with no Invariant Sections, no Front-Cover Texts and no Back-Cover Texts.

MIDI over Bluetooth Low Energy on Linux finally accepted

I am very happy to say that MIDI over BLE on Linux will be part of the next BlueZ release! You can check both commits for this initial release.

In order to build you need alsa-lib dependency and run ./configure  with --enable-midi  option because it is disabled by default since it is an experimental feature yet.

Now you can run bluetoothd and just connect to a BLE device that advertises the MIDI Primary Service. Once done that, bluetoothd will load the MIDI driver and a new ALSA Sequencer client/port will be created for the device. You can check with aseqdump -l  command to list all available ports for subscription. Connect to your Synth and enjoy!

Okay, there might be one caveat on this whole thing. It is very important that Connection Interval property is set via the Connection Update Command from the peripheral, but some devices don’t do it! This is required by the BLE-MIDI spec, but apparently MacOS or iOS force a Connection Interval for their particular adapters on each platform when connected to a MIDI device (yes, clearly they don’t trust device manufactures and they now exactly the most optimal configuration for their specific adapters). And since most MIDI device users use those OSes, they don’t really care about setting the Connection Interval. That’s a shame, I know…

So, If you notice any drop of connection, bad latency and packet drops, force BlueZ do the same – enforce a Connection Interval. To do that you have to edit a file that is located in  /var/lib/bluetooth/[ADAPTER]/[DEVICE]/info  where [ADAPTER] and [DEVICE] is their respective addresses and restart bluetoothd. Add the following lines:

If these values doesn’t work well for you, you might need to try out different MinInterval and MaxInterval for your particular adapter. I know it sucks, but that’s the price to pay for non compliant devices. If that is the case, complain to the manufacturer!

Anyway, back to the good stuff.

There is still work to be done. It is missing the Peripheral role support that can be implemented as a bluetoothd plugin or, perhaps, as a dedicated program if the prior doesn’t meet the low-latency requirements. There is also a support missing in ALSA Sequencer for arbitrary event timestamp, which is required by BLE-MIDI.

I will continue maintaining my personal branch of BlueZ to support MIDI further developments, so feel free to drop a line there, open issues (or use BlueZ bugtracker), send pull-requets etc.

Thanks to ROLI Ltd. for supporting me on this project. Also, Ben Supper, Luiz Augusto von Dentz and Adam Goode for reviewing the patch set.

MIDI over BLE on Linux under review, finally!

I am very happy to say that I finally have a version good enough to be sent for peer-review on linux-bluetooth mainling list.

There will be other little reviews, obviously. But hopefully this patch will be accepted for next BlueZ version.

Please, I invite you to review and test. You can check the patch at linux-bluetooth and a video demo I made (below as well).

Important notes:

  • GATT client (GAP central role)
  • libmidi (MIDI parsing)
  • unit-tests

The GATT server (GAP Peripheral role) can easily be implemented using libmidi . Once this main patch is in mainline, then it will be interesting to start working on it.

As mentioned on my patch, I would like to send kudos to ROLI Ltd. which allowed my to work on this as part of my full-time job.

Linux v4.9 with more USB-MIDI improvements

I am very happy to say that finally all ROLI‘s patches for USB-MIDI gadget driver for the Seaboard GRAND has been accepted upstream and it will be part of v4.9 of the Linux Kernel. Those final patches ended up causing improvements on the core USB Gadget framework as well, fixing potential bugs and making it more robust.

Some changes:

  • Refactor of the MIDI state machine;
  • Properly clean buffers if USB’s endpoint gets disabled;
  • USB Request allocator function aligns OUT endpoints to wMaxPacketSize property;
  • Other things as well…

The patches can be seen on Felipe Balbi’s and Greg Kroah-Hartman’s branches at this moment, since the v4.9 merge window is not open yet.

As always I would like to send appreciations to the Linux community, which has been always very open and helpful.

Make sure to update your kernel to 4.9 when it is available and enjoy!

Bitbake’s PR Service as standalone server

bitbake support outside a OE-core or poky (yocto) environment is quite annoying. No distribution that I have used so far could write a decent package containing all dependencies and fixing PYTHONPATH problems in run-time.

Why I did need this? Because I wanted to run bitbake’s prserv as a standalone server in a build server. In order to do that I had to create an Arch package + systemd service file.

You can check out Arch support for bitbake in AUR. Also it might give a better understanding for other distributions as well.

Now for systemd, create a file /usr/lib/systemd/system/bitbake-prserv.service  and add the following content.

Make sure that the port is accessible via tcp on your firewall (39411 used here is just a random number). Also, you can notice that I couldn’t find a way to use $PRSERV_PORT  in PIDFile= option. If you know a better solution, please share with us.

SysEx support on MIDI over BLE for Linux

So, recently during a trip to Portugal, I implemented the SysEx support for the BlueZ MIDI profile. The implementation is rather simple, but it can be confusing because of multiple BLE packets that can be used to transfer this MIDI message. I tested with a Seaboard RISE that I have in hand.

If you are interested in contributing, please review the code and try to test if possible. I will be posting a clear road-map on what is missing and what is our goal.

I am happy to say that I will be able to dedicate more time to this project, so hopefully the initial stage of MIDI over BLE support will be done in a month.

 

USB-MIDI Gadget improvements on Linux

Here at ROLI we make heavy usage of Linux and its audio stack (ALSA). And one of our problems was the MIDI Gadget driver. The Linux USB Gadget MIDI driver has been neglected for few years now. It had several bugs, memory leaks and not very clean code-base. Why didn’t anyone care? Well, one of the reasons is that MIDI is a low speed and low throughput protocol, and the current driver was delivering just enough. But that is about to change because ROLI and others have been working on the Multidimensional Polyphonic Expression (MPE) MIDI specification, which increases dramatically the number of MIDI messages per second and per USB request. Thus problems started to arise.

Overall there were several patches that we upstreamed, including performance and memory-footprint improvements by pre-allocating IN USB requests, state machine refactor and fixing an annoying bug that caused the MIDI Streaming endpoint to freeze. There were also critical memory leaks fixes in ChipIdea’s UDC driver.

It is important to note that the Linux community was very helpful and open as always. Our threads created some helpful discussions and motivated others to contribute and improve the MIDI driver too.

So, update your kernel to v4.5 and enjoy a much better MIDI experience for your device on Linux.

PS: v4.6 and v4.7 will also have other improvements that were not merged yet.

BlueZ fork on github for MIDI over BLE

Since there are some people reaching me and showing interest in helping with the implementation of the MIDI over BLE profile on Linux, I created a fork repository of BlueZ on github so others can checkout the branch midi and help it out.

The idea is just to share the MIDI profile driver with others so we can concentrate the development efforts, then send patches to the mainline BlueZ. Once it gets integrated into mainline, I will drop this repository.

As mentioned on previous blog post, the work is still undergoing and incomplete.

So, please, checkout the repository and the profile driver.

MIDI over Bluetooth Low Energy on Linux

Two months ago I made a request for comments on the linux-bluetooth and linux-alsa lists to propose the implementation of the MIDI over Bluetooth Low Energy profile on Linux using BlueZ and ALSA.

The main goals of the project are:

  1. To be transparent to applications, i.e., use ALSA Sequencer interface (ideally also use ALSA RawMidi too[1]);
  2. Support Peripheral and Central Bluetooth GAP roles.

[1] The problem with this is that it requires a kernel module to create a rawmidi device.

MMA is almost done with the actual MIDI over BLE spec. But since it is very close to Apple’s one, we can actually start implementing it.

On the mailing list, BlueZ developers suggested to implement it using the GATT D-Bus API to read and write the MIDI I/O characteristic for the sake of simplicity of initial version. Although this recommendation is valid, it will probably not fit the low latency requirements for this type of application.

That is why I already started the implementation as a native BlueZ plug-in (using the new shared api’s) instead. I’ve also sent two patches to fix a bug on that new API, which still requires some more work.

What I’ve Got So Far

I have a simple BlueZ profile plug-in that setups up an ALSA Sequencer client and port, reads the MIDI I/O characteristics notifications and writes the MIDI messages to the Sequencer port. I have tested the Seaboard RISE with a Linux synthesizer that supports ALSA Sequencer and it seems to work pretty fine.

This initial version still lacks timestamp support, write support and central role support.

Considerations

I’ve noticed that the connection with the Seaboard RISE was very unstable. Every time the RISE would send high throughput messages, the connection would drop. Then I’ve noticed that the RISE doesn’t send the Connection Update Command to the host and then BlueZ would not update the connection state to be in a lower latency. But that doesn’t happen on a iOS and Mac OS system, but why?

To understand what was going on, I connected to an iThing device as a peripheral exporting the MIDI Service and dumped the Connection Update Command data. I noticed that the Mac OS forced the connection parameters (instead of listening to the peripheral to suggest it) as follows:

  • Minimum Connection Interval: 6
  • Maximum Connection Interval: 12
  • Connection Latency: 0
  • Supervision Timeout: 200

As BlueZ supports the setting up connection parameters, I just changed the info file and reconnected. That caused my connection to be much more stable, but still not perfect. Eventually the connection still drops. So, that is something I still need to figure out. Any suggestions on it will be helpful.

I want to finish the timestamp and write support before releasing it. The central role can be implemented after the release, since I think the most exciting feature right now is to support BLE MIDI devices.

If you are interested in contributing, send me an email, I can share what I have it so far.