sábado, 30 de novembro de 2013

Fair share user scheduling on Linux terminal servers


Linux terminal server, LTSP, xrdp, kernel, scheduler, cgroups.


The default Linux scheduling configuration divides CPU time on a per process basis. If a system accepts multiple interactive users, that is not the desired situation since a user that is running many processes will have a larger CPU share than the others. However, it is possible to configure fair share user scheduling on Linux using cgroups together with some scripting. That will distribute CPU time, as well as other resources, in a flexible user based manner. NFS I/O escapes the control groups mechanisms but we will provide a method for handling such situations. The motivation for this article is the need to ensure that, on a correctly configured server, a single user is unable to cause system wide performance degradation


Once up on a time there was a kernel option called FAIR_USER_SCHED that divided the CPU time slices on a per user basis. For some time, later on, that option was called just USER_SCHED. Eventually it got removed because its existence meant a lot of code to maintain. As a result, each google search about "fair share user scheduling" brings now up old discussion threads and college homework assignments. But as this option was removed a hot replacement called cgroups was ready to rock... well, sort of.

In system administration nothing is ever that simple. A kernel option that would automatically set the scheduler to work on a per user basis got replaced by a much more general process group approach that needs manual configuration and user space real time process classification to achieve the same effect. Less code to maintain in the kernel - lots of homemade scripts to be written worldwide and no documentation on how to do it properly. There is, however, a great thing in the new approach: it is not only the CPU that can be fairly shared. We can now control the scheduling of other resources such as I/O on block devices and network activity.

Resource sharing on terminal servers

There are different systems that can benefict from this such as mass hosting web servers running Apache with Suexec, large university development machines that take thousands of SSH logins and terminal servers. We will focus on terminal servers for this article.

The case for terminal servers is a rather trivial one, in terms of system administration efficiency. But configuration and maintenance require a deep understanding of many aspects of OS and network operations. Part of that will be the subject of a future article. For now, we would like to stress that when talking about terminal servers we don't mean the single application remote session running on a simplified desktop (or no desktop at all). Neither we mean a virtual remote single-user PC. We are talking about a complete remote desktop server where N users deal simultaneously with KDE, Firefox, Libreoffice, Gwenview, Gimp, Okular, arK, rdesktop and others, as if they had a local machine with all that software installed.

From time to time Linus Torvalds tells the media that one of the remaining challenges for the Linux kernel is desktop workloads. So, the greatest possible challenge must be having N desktop users on the same machine sharing the same Linux kernel. We will  now show you how to optimize the scheduling for fair sharing of CPU and block I/O. Everything described in this article was successfully tested on Ubuntu 12.04 LTS using XRDP as the remote desktop server.

Kernel control groups

Control groups, aka cgroups, are sets of processes to which the Linux kernel assigns specific resource shares. When you install cgroups on Ubuntu
apt-get install cgroup-bin libcgroup1 libpam-cgroup
you will get a default configuration where all the running processes belong to the same cgroup. That is a particular configuration where the kernel behaves just as if the cgroup feature was not enabled - since there is a single group it takes all the resources and shares them internally on a per-process basis. From that point on we can start building a custom configuration.

1. The first step is creating a cgroup for all users that will ever access the terminal server.

Essentialy, this is done using
getent group REMOTEUSERS
and pushing the list to the cgcreate command, that belongs to libcgroup.

There are some details related to the fact that the cgroups must be refreshed from time to time to keep the terminal server in sync with the list of users stored on the authentication server. Since there may be thousands of users and, in that case, we don't want to recreate the already existing cgroups, we will provide you a script that takes care of such details.

In case you find this over engineering we will refer you back to the Introduction where we warned that the "much more general group approach" needed "manual configuration...". "Generality comes at this price", must have thought the kernel team.

2. The second step is having PAM and the cgroup utilities classify the post login processes, for each user, into the right cgroup.

session required        pam_script.so
session optional        pam_cgroup.so
session sufficient      pam_winbind.so
session optional        pam_ck_connector.so nox11
@REMOTEUSERS             cpu,blkio     %U
root                              cpu,blkio     system
xrdp                             cpu,blkio     system
*                                   cpu,blkio     others
With this configuration users belonging to the group REMOTEUSERS will have an individual cgroup. On the other hand, users that are allowed to log in but don't belong to that group will compete for resources within a group called "others". Processes belonging to users root and xrdp will have a reserved share via a group called "system".

 3. The final step is allocating the available resources to the created groups.

That is achieved by using the cgset command on the existing cgroups. What we do in this case is giving each user cgroup the same CPU and I/O share while leaving a fixed share for the "system" and "others" cgroups.

Something like this:
for i in $USERLIST; do
  cgcreate -g cpu:/$i
  cgcreate -g blkio:/$i
  cgset -r blkio.weight=$USERBLKIO /$i

# other users that have processes running
if [ ! -e /sys/fs/cgroup/cpu/others ]; then
  cgcreate -g cpu:/others
  cgcreate -g blkio:/others
  cgset -r blkio.weight=$USERBLKIO /others

# for anything that runs as root and something else that cgrules.conf puts in thys group
if [ ! -e /sys/fs/cgroup/cpu/system ]; then
  cgcreate -g cpu:/system
  cgcreate -g blkio:/system
  # reserved for root ssh actions - default shares value is 1024
  cgset -r cpu.shares=$SYSCPU /system
  # default value is 500, max value is 1000
  cgset -r  blkio.weight=$SYSBLKIO /system
Note: if you are seeing pointless cgroup messages on the syslog add
to /etc/cgred.conf.

Automating setup and maintenance

To automate the synchronization between the terminal server and the authentication directory it connects to (be it Active Directory, LDAP or Samba...) we suggest this script. It makes cgroup management a much easier task and can be edited to suit your needs.

Testing the setup

After the the system is configured you should see one directory named as each user at /sys/fs/cgroup/cpu and /sys/fs/cgroup/blkio/. Inside each of those directories there will be a file called "tasks" that lists the processes of the corresponding user. You can compare the content of that file to the content of "ps -u USERNAME" and check that it matches. You can see that as another user logs in its processes are automatically inserted at both /sys/fs/cgroup/cpu/ANOTHERUSER/tasks and /sys/fs/cgroup/blkio/ANOTHERUSER/tasks.

You can query the properties of each cgroup with commands such as the following:
cgget system
cgget others
Once you are sure that group configuration and process classification are working you can run CPU and block I/O sharing tests.

Imagine that you have a single core VM. If a certain CPU intensive test process takes 1 minute to complete for user A while pushing the virtual CPU to 100%, two of the same processes running - one for user A and another for user B - shall take 2 minutes to complete. Each of the users will wait 2 minutes for the result. Now, what if user B decides to run 2 instances of the same process? The answer is easy: it would take a total of 3 minutes for all the processes to be ready. But here you will see the important difference: without our cgroup configuration both users would wait 3 minutes for all their processes to complete whereas with our configuration user A would wait 2 minutes and B would wait 3. That is, each user will get half of the CPU time regardless of the number of processes it runs. When user A's process is done, after 2 minutes, user B will get the whole CPU and finish the remaining work in a single minute. The evolution of CPU shares in time is summarized in the following table.

Without fair sharing
1st minute
2nd minute
3rd minute
With fair sharing
1st minute
2nd minute
3rd minute
We should stress that for this behaviour to be verifiable the test must fully occupy the available CPUs. On a single core machine it is easy to do it with a single test process. To perform this simple test on a multicore machine you need to run extra CPU intensive processes just to keep all but one cores at 100% thus enabling competition between test processes - cgroups have no effect if there is no resource scarcity.

To test block I/O resource sharing the procedure is similar. We suggest that you saturate disk read access by using dd to read through a large file. Running concurrent dd processes mustn't allow the owner of those processes to write at a higher rate. After preparing a couple of large files with
dd if=/dev/zero of=/tmp/zerofile1 bs=1024 count=4096000
cp -f /tmp/zerofile1 /tmp/zerofile2
cp -f /tmp/zerofile1 /tmp/zerofile3
one simple test would be executing something like
echo 3 > /proc/sys/vm/drop_caches

cgexec -g blkio:ONEUSER dd if=/tmp/zerofile1 of=/dev/null &
cgexec -g blkio:ANOTHERUSER dd if=/tmp/zerofile2 of=/dev/null &
cgexec -g blkio:ANOTHERUSER dd if=/tmp/zerofile3 of=/dev/null &
Just as with the CPU test you would conclude that ANOTHERUSER would not see an advantage in running 2 concurrent processes.

CPU and block I/O can be monitored with the atop utilty - use shift+d to sort by DSK activity and shift+c to sort by CPU usage. If you'd like to see CPU usage grouped per user you can use this script.

NFS - not fair shareable

If everything above is correctly setup you should have a system where, if pressure mounts, each user becomes bound to a certain amount of CPU and block I/O. Thus, the impact of misbehaviour or accidental misuse is limited.

Still, problems may arise if you are using NFS to store home directories. If you are doing that, probably due to having several terminal servers balanced across a large group of users, you should be aware that NFS usage is not fair shareable. This suggests a new funky acronym for NFS but that is purely accidental and we won't go further that way.

The problem is that NFS I/O does not count as block I/O - NFS is a network filesystem not a block device. Furthermore, network transfers on NFS are done as root so network related cgroups mechanisms can't be used either.

To mitigate this problem we developed a simple I/O governor that permanently monitors suspect processes - that must be defined in a case by case basis - and calms them down if they are taking too much I/O. By calming them down, we mean sending them SIGSTOP and, after a while, SIGCONT. What the governor actually does to an I/O intensive process, after leaving it alone for a certain configurable grace period, is put it to sleep for a decreasing fraction of its running time until its I/O activity reaches a specific pre-configured limit.

The usual suspects are processes that tend to saturate the I/O bandwidth to the physical storage by reading or writing at a very high rate causing large delays to the short reads and writes of other applications. For example, we wouldn't like that a user copying a 1GB folder to a shared network drive would degrade the startup time of Libreoffice or Firefox for all the others. But that could happen, since NFS is not fair shareable and that's precisely what the I/O governor avoids. The original idea came from this CPU governor (which we don't need since cgroups are doing the cpu governing job) and the working logic is probably not very different from the Process Lasso windows tool that we mentioned here.

We usually monitor kio_file processes which are responsible for handling file copy operations performed with Dolphin, on KDE. That, of course, needs to be adapted to the particular use of each terminal server. You can take a look at the governor here. Please note that it should be running at all times and depends on the helper script iolim.sh that you can find here.


Resource governing can be achieved on terminal servers by using a combination of the cgroups kernel feature and a couple of bash scripts. Performance loss situations, that could become stressful to the users, can be effectively avoided. Runaway processes that potentially consume too much CPU, block I/O or NFS I/O can be controlled automatically.

Here is how an 8 VCPU virtual machine, supported on 8 real CPU cores, handles 15 concurrent full desktop users with great performance. Note that we are in average delivering half a core and 400MB of RAM to each user with excellent performance. The number of users could still grow significantly without causing work delays.



sábado, 23 de novembro de 2013

Ali há link, ali há lata

Poderia, talvez, pensar-se que a tragi-comédia à volta das discussões sobre conteúdos digitais e pirataria estivesse já esgotada, em Portugal. Isso seria, vemos agora, uma ideia infantil já que é perfeitamente possível um assunto estar esgotado na substância mas não o estar, de todo, na irritância.

Que a palavra irritância não exista pouco nos importa. Aliás, não é líquido que não venha a tornar-se um substantivo precisamente aplicável ao dom dos que nada de substancial fazem para resolver um problema próprio, mas do qual recorrentemente se queixam.

Ao dom da irritância, dos tais, contrapõe-se a pertinência da blogger Jonasnuts que, com perspicácia, nos demonstra que os do costume se precipitaram, outra vez, nas conclusões e que o deputado Galamba está inocente, pelo menos deste crime e até prova em contrário.

Aproveitamos esta oportunidade para perguntar se "há link", não para o Porto-Sporting mas para algumas das obras que remetam vagamente para esta novela sem fim. Há link para o "The usual suspects"? Há link para o "2001 Odisseia no espaço"? (é especialmente relevante a cena do monolito). Há link  para o "O Império Contra Ataca"?

Neste caso, para evitar polémicas diremos explicitamente que só estamos interessados em links onde se possa fazer um pagamento do qual, como contrapartida, se obtenha o direito de visionar a obra ou de, da mesma, fazer download.

Posto este breve comentário remeter-nos-emos ao silêncio, sobre o assunto, até que "haja links" ou alguem nos acorde com uma overdose de piada. Galambagate, really? :-) Não será fácil fazer melhor.

terça-feira, 20 de agosto de 2013

Silly season: os atributos de um café Português

O café é uma ciência complexa. 

E não, isto não se trata de mais uma piada sobre Java. O café em Portugal é apreciado pela subtileza das suas configurações e pela pouca subtileza de alguns empregados de mesa. 

O café em Portugal é perfeitamente dominado por um serviço de mesa experiente mas potencialmente confuso para um programador desprovido de cafeína.

Aqui fica uma implementação rudimentar em Python.
# coding=utf-8

class Length:
        short, normal, long = range (3)

class Sweetner:
        sugar, sweetner = range (2)

class Mixer:
        spoon, cinnamon_stick = range (2)

class Type:
        normal, decaf = range (2)

class Coffee:
        "representation of a portuguese coffee"

        # the members are "semi private" - not meant to be accessed directly    
        def __init__(self, ctype = Type.normal , length = Length.normal , milk_spot = False , cup_preheating = False , sweetening = Sweetner.sugar ,  mixer_type = Mixer.spoon ):
                self.__type = ctype
                self.__length = length
                self.__milk_spot = milk_spot
                self.__cup_preheating = cup_preheating
                self.__sweetening = sweetening
                self.__mixer_type = mixer_type
                # homework: validate input and raise ValueError if it's wrong :-)

        # this function translates the internal representation of Coffee atrributes into an order that can be sent to the waiter
        def __str__(self):
                result = "Um %s %s %s %s %s %s" % ( self.get_type_pt(), self.get_length_pt(), self.get_milk_spot_pt(), self.get_cup_preheating_pt(), self.get_sweetening_pt(), self.get_mixer_type() )
                # clear redundant whitespace on return
                return ' '.join(result.split())+'.'

        def get_type_pt(self):
                if self.__type == Type.normal:
                        return "café"
                return "descafeinado"

        def get_length_pt(self):
                if self.__length == Length.short:
                        return "curto"
                if self.__length == Length.normal:
                        return ""
                if self.__length == Length.long:
                        return "cheio"
                return "erro"

        def get_milk_spot_pt(self):
                if self.__milk_spot == True:
                        return "pingado"
                return ""

        def get_cup_preheating_pt(self):
                if self.__cup_preheating == True:
                        return "em chávena escaldada"
                return ""

        def get_sweetening_pt(self):
                if self.__sweetening == Sweetner.sweetner:
                        return "com adoçante"
                return ""

        def get_mixer_type(self):
                if self.__mixer_type == Mixer.cinnamon_stick:
                        return "e pauzinho de canela"
                return ""

Enough said. Posto isto, há que fazer os pedidos. Experimentem estes.

# café default - for machos
cafe = Coffee()
print cafe

# ultrademanding customer
cafe = Coffee(Type.normal, Length.long, True, True, Sweetner.sweetner, Mixer.cinnamon_stick)
print cafe

# no comments
cafe = Coffee(Type.decaf, Length.normal, False, False, Sweetner.sweetner, Mixer.spoon)
print cafe


quinta-feira, 18 de abril de 2013

Random youtube goodness

We just found out that it is possible to disable the greatest Youtube annoyance of all time: autoplay. Yes, like with many other browsing annoyances... there is a script for that.

YousableTube is a script for the Greasemonkey extension that can disable autoplay (while keeping autobuffering!), allow for easy downloading in several formats and much more. It's just a click away, after installing Greasemonkey. We tested it using the Youtube HTML5 mode and worked great.

And since this is not enough, seems that many people use Youtube to play music at parties. That must feel very clumsy :-) even now that we know how to disable the dreadful autoplay feature. But hey, there's a web app for that!

Turnetubelist is as crossfader application that can search on youtube and manage a pair of playlists. I wouldn't call this an DJ application :-) but it certainly can improve ad-hoc parties.

quarta-feira, 10 de abril de 2013

1º de Abril atrasado

Nem houve tempo para completar a análise do "mercado" nacional de conteúdos digitais, agora com ao inclusão do Video Clube Online Optimus Clix, porque a Zon já se antecipou com uma oferta fortemente inovadora e concorrencial. Em Portugal, a inovação acontece a uma velocidade estonteante, com as empresas de telecomunicações a liderarem o progresso.

Mas é que é mesmo verdade. Parece que a Zon montou um vídeo clube online, no Facebook (que moderno!) e o inaugurou com um catálogo de dois (2) filmes. Ou pelo menos é o que têm garantido diversos media.

Uma visita rápida à página do vídeo clube conduz-nos a uma abundância nunca vista de filmes disponíveis "no Videoclube da tua TV". 

"Ah...então não era para alugar na Internet, ó chefe?!"

Bom, isso é do mais simples. Basta vascular as dezenas de posts que lá estão até encontrar um dos dois (2) que supostamente se podem alugar.

E depois é só dar um clique num URL to tipo "bit.ly" - estando logged in na sua conta do Facebook, é claro - sem medo do que possa acontecer a seguir. Afinal de contas isto é de confiança... é um clube da Zon...

Mas será mesmo?

É que na realidade não se vê qualquer referência à Zon na referida página. E na descrição do perfil lê-se

O serviço de Videoclube da TV está disponível nos diversos operadores de TV- ZON, MEO, Cabovisão, Optimus e Vodafone [...] Para mais informação sobre os termos deste serviço e preços aplicáveis, contacta o teu Operador de TV.
Alguém poderá garantir quem faz a gestão deste serviço?

Mas a Zon tem com certeza qualquer coisa a ver com isto. Ou pelo menos virá a ter no futuro. Para confirmar isso basta ler o Press Release oficial que data de Abril de 2103.

Em resumo, para aceder a este serviço futurista de 2103, que lhe permite alugar dois (2) filmes na Internet, basta fazer login com a sua conta do Facebook (se não tiver é favor ter), percorrer sequencialmente dezenas de posts, escolher um dos dois filmes - ou então o outro, clicar num link "bit.ly", aceitar o acesso a uma aplicação do Facebook, rezar para que não haja intromissões na sua privacidade e, se tudo correr bem, pagar e ver um filme (ou então o outro).

A revolução está ON. E com serviços online deste calibre a pirataria em breve estará OFF :-)

domingo, 7 de abril de 2013

Xorg, vesa, modelines, intel and 915resolution


This post is perhaps a bit too technical and probably too long, but it is important that certain things are google indexed, for the Linux community to work better. That has been helpful to us many times in the past, so we are glad to do our share.

The Intel Cedarview Xorg driver seems to be quite slow. It is outperformed by the Xorg Vesa driver, at least for basic operations. You can use any graphics mode (including wide modes such as 1920x1080) with the Vesa driver thanks to a small program called 915resolution. For multiple devices connected to different monitors you can use Vesa + 915resolution and control the display resolution using DHCP.

Intel's Cedarview mess

Seems that the Intel Cedarview chipset had a tough start on Linux devices. The stupidity of outsourcing the GPU to PowerVR, while not ensuring to have working drivers in time, caused many complaints (example) from users around the world. That meant lots of hardware working at the wrong resolution or with sub-optimal performance. And it happened even though the very same Intel employs a highly trained Linux driver team. That team, unfortunately, can't do anything for rebranded 3rd-party hardware, if no specifications are delivered.

At some point, Intel finally made official drivers available. The Xorg driver is called pvr and can be found here. But guess what the Release Notes say:

 * Poor 2D rendering performance through Xlib protocol. (#9 #125 #126)

Having tried the version that landed on Ubuntu 12.04 official repositories (apt-get install cedarview) I must say the Release Notes are right. The driver seems unusable, as dragging and maximizing windows is painfully slow. While this would embarassing enough for Intel, I must add something to the situation. Their driver is outperformed by the Vesa driver and, with an up to date kernel such as the default kernel from Ubuntu 12.04.2, the Modesetting driver. Yes, it's true. The late coming specific driver from Intel is beaten hands down by two generic Linux drivers, one of which is several years old.

I must say we haven't tried OpenGL, XV or VAAPI with Intel's pvr driver. Even if it worked and performed well, it would still be pointless since the user can't properly drag a window without waiting one second for each repaint.

So, as a company that's responsible for thousands of EUR of Intel related purchases every year, we would like to greet Intel with the famous words, Linus Torvalds has given NVIDIA, and kindly suggest that they use their own driver team to have proper drivers written in time.

The Vesa driver

The Vesa driver is a generic Xorg driver that uses one of the VESA graphics modes that are present in the graphics cards BIOS. This driver doesn't know how to program low level details of the card and doesn't accelerate any operations. However, given a powerful enough CPU the Vesa driver is more than acceptable for daily work.

But there is a problem: the official VESA modes are not suitable for current displays. None of the currently used wide modes is available in the cards BIOSes and the driver will ignore any modelines that are added to Xorg.conf.

To help with that, a utility called 915resolution that works with Intel's cards was created. An updated version that works with the Cedarview chipset can be found here.

To run any graphics mode using the Vesa driver, you just need to load it into the card BIOS before Xorg is started. Some examples:

[root@host ubuntupxe]#./915resolution -c Cedarview 3c 1920 1080 16 2576 1120

[root@host ubuntupxe]#./915resolution -c Cedarview  3c 1600 900 16 2112 934

[root@host ubuntupxe]#./915resolution -c Cedarview 3c 1600 900 16 1904 934

The first argument of 915resolution, 3c,  is the code of the standard mode that will be overwritten. You can see a list of modes using the -l flag.

The remaining arguments are X, Y, DEPTH, HTOTAL and VTOTAL. Even though HTOTAL and VTOTAL are said to be optional, they are in fact necessary for the picture to have the right size and placement on screen. You can find values for HTOTAL and VTOTAL generating a modeline with cvt, as in the following example

[root@host ubuntupxe]# cvt 1600 900 60

In this example, we requested a modeline for 1600x900 @ 60 Hz. The result is

# 1600x900 59.95 Hz (CVT 1.44M9) hsync: 55.99 kHz; pclk: 118.25 MHz
Modeline "1600x900_60.00"  118.25  1600 1696 1856 2112  900 903 908 934 -hsync +vsync

The values for HTOTAL and VTOTAL are always the 7th and 11th field (emphasis added above).

A generic xorg.conf for multiple devices

Once you ensure each of your devices has the best mode for its display made available using 915resolution, you only need a generic Xorg.conf. That file must contain  "vesa" as the graphics driver and a list of wide modes. In the example below, xorf.conf contains a set of wide modes all of which are ignored, except the one loaded into the card BIOS using 915resolution.

Section "Screen"
        Identifier "Screen0"
        Device     "Card0"
        Monitor    "Monitor0"
        DefaultDepth 24
        SubSection "Display"
                Modes      "1600x900" "1440x900" "1366x768" "1360x768"
                Viewport   0 0
                Depth     24
If you must support multiple identical Intel devices, connected to different monitors you can even send the resolution, colour depth, HOTAL and VTOTAL via a DHCP custom variable, to configure their resolutions centrally. Please note that although the mode that was written to the card BIOS is "selected" automatically (ie, the others are rejected) using the above xorg.conf example, not all combinations of colour depth and resolution are possible. It may happen that 1600x900@24 bpp is possible whereas the maximum bpp for 1920x1080 is 16.


Having the Vesa driver working at any resolution is due to the work of Steve Tomljenovic, author of the original 915resolution, and user vtaylor who posted a modified version at slitaz.org.

quinta-feira, 21 de fevereiro de 2013

Matar o direito de autor

Estando outra vez na agenda a questão recorrente da taxação dos dispositivos de armazenamento (taxa Canavilhas, #pl118, etc) publica-se aqui uma receita infalível para acabar com o direito de autor de uma vez por todas.

Aparentemente, esta receita é a que está a ser seguida.


representantes da indústria em estado de negação, advogados negociadores de copyright em slow motion, cidadãos activistas, cidadãos indiferentes, deputados, comentadores, bloggers e empresas de telecomunicações.


  1. Criar um mercado de telecomunicações em que o acesso em banda larga se generaliza, a preços relativamente competitivos
  2. Não disponibilizar neste mercado - onde tudo o resto funciona bem - uma oferta credível de acesso legal a conteúdos protegidos por direito de autor (ver este texto)
  3. Garantir que nos poucos serviços acessíveis os pagamentos não funcionam com métodos seguros (Multibanco, MBNET), resumindo-se a métodos inseguros (cartão de crédito de plástico) e que existem incompatibilidades QB entre sistemas operativos
  4. Lamentar recorrentemente as perdas "resultantes" da pirataria, sem no entanto investir na oferta legal, deixando que a pirataria comece a ser aceite em termos culturais
  5. Deixar passar vários anos nesta situação, até que a geração de piratas "filhos" se converta numa geração de piratas "pais", cidadãos adultos para quem piratear é perfeitamente normal
  6. Sobre o leite derramado reagir à bully com abusos aos direitos fundamentais dos consumidores (rootkit Sony, tratado ACTA, ...)
  7.  Tentar introduzir taxações indiscriminadas sobre dispositivos de armazenamento, taxas estas que, mesmo que não avancem, irão polarizar os cidadãos no sentido contrário e caso avancem irão convence-los de que os direitos de autor afinal são pagos a montante ( "agora sim, não há qualquer problema em piratear")
Está pronto e nem é preciso juntar mais água.

No fim, admirem-se quando os cidadãos revogarem, em termos práticos, o direito de autor e se indisponibilizarem de todo para pagar por conteúdos digitais.

domingo, 20 de janeiro de 2013

Essencial business applications for Android

There are so many applications for Android that it can be challenging to find the good ones out of the huge lot. Here is a short list for users that use Android devices mostly for work purposes:
  • LDAP Client - query an LDAP Address Book and add contacts to your Android Address Book
  • CardDav-Sync - synchronize your contacts with a CardDav compliant server (eg Zimbra); free and paid versions available.
  • AnDal Calendar Sync - synchronize you Calendar with a Caldav compliant server (eg Zimbra)
  • K-9 Mail - open source IMAP client that is better than the default email apps
  • OpenDocument Reader - it does what the name suggests
  • Opera Mobile - better than the default Android Browser
  • Connect Bot - local shell and ssh client
  • Nexus torch - simple flash light application that doesn't require permissions that make you wonder...

One handy service that I find not to be working right is delicious.com. After trying several applications none of those seemed to be working well and using the website directly is just not fast enough. Update: DeliciousDroid works great. Search Google Play for "deliciousdroid" (no spaces) or you won't find it!

If you are aware of other productivity-enhancing applications that don't require weird permissions please share in the comments section.