systemd, cpu por usuário e / ou limites de memória

5

Existe uma pergunta semelhante: Cgroups, limitam a memória por usuário , mas a solução não funciona em "moderno" sistemas, onde a hierarquia dos cgroups é gerenciado pelo systemd.

Solução simples - modelando user-UID.slice - não funciona, porque não é suportado, veja link .

Existe alguma maneira de obter o efeito desejado - gerenciar recursos de CPU e / ou memória por usuário?

UPD : manterei minha solução por causa do histórico, mas systemctl set-property deve ser chamado no momento do login, usando pam_exec , consulte link . Nesta abordagem, não há janela de tempo entre o login do usuário e a configuração de limites.

Minha solução . A interface org.freedesktop.login1.Manage do /org/freedesktop/login1 object emite UserNew(u uid, o object_path) signal. Eu escrevi um daemon simples que escuta o sinal e toda vez que ele é emitido, defina CPUAccounting=true para a fatia do usuário que acabou de ser logado.

    
por intelfx 18.09.2017 / 20:26

2 respostas

3

UPD : manterei minha solução por causa do histórico, mas systemctl set-property deve ser chamado no momento do login, usando pam_exec , consulte link . Nesta abordagem, não há janela de tempo entre o login do usuário e a configuração de limites.

Solução antiga

Aqui está um script muito simples que faz o trabalho

#!/bin/bash

STATE=1 # 1 -- waiting for signal; 2 -- reading UID

dbus-monitor --system "interface=org.freedesktop.login1.Manager,member=UserNew" |
while read line
do
    case $STATE in
    1) [[ $line =~ member=UserNew ]] && STATE=2 ;;
    2) read dbus_type ID <<< $line
       systemctl set-property user-$ID.slice CPUAccounting=true
       STATE=1
    ;;
    esac
done

Ele pode ser facilmente estendido para suportar limites de memória por usuário.

Testado em uma VM com 2 CPUs e 2 usuários. O primeiro usuário executa o comando dd if=/dev/zero of=/dev/null | dd if=/dev/zero of=/dev/null e o segundo executa apenas uma instância de dd . Sem esse script em execução, cada instância de dd usava cerca de 70% da CPU.

Em seguida, iniciei o script, reutilizei os usuários e executei novamente dd dos comandos. Desta vez, dois processos dd do primeiro usuário receberam apenas 50% da CPU cada e o processo do segundo usuário levou 100% da CPU. Além disso, systemd-cgtop mostrou que /user.slice/user-UID1.slice e /user.slice/user-UID2.slice tomam 100% do tempo de CPU cada, mas a primeira fatia tem 6 tarefas e a segunda apenas 5 tarefas.

Quando eu mato a tarefa dd do segundo usuário, o primeiro usuário começa a consumir 200% do tempo da CPU. Portanto, temos uma alocação justa de recursos sem restrições artificiais, como "cada usuário pode usar apenas um núcleo".

    
por 19.09.2017 / 20:05
0

O problema que você mencionou ainda está aberto, mas isso funciona para mim.

sudo systemctl edit --force user-1234.slice

Em seguida, digite e salve isto:

[Slice]
CPUQuota=10%

Não sei por que isso funciona.

    
por 19.01.2018 / 09:09