Usando apenas um núcleo da CPU

9

Preciso executar testes de desempenho para o meu programa simultâneo e meu requisito é que ele seja executado em apenas um núcleo da CPU. (Não quero threads de cooperação - quero sempre ter uma alternância de contexto).

Então, eu tenho duas perguntas:

  1. A melhor solução - Como assinar e reservar apenas um núcleo da CPU apenas para o meu programa (para forçar o SO a não usar esse núcleo da CPU). Eu acho que não é possível, mas talvez eu esteja errado ...

  2. Como configurar o linux (Fedora 24) para usar apenas um núcleo de CPU?

peter55555
fonte
Veja isso .
Kamil Maciorowski
1
Observe que as CPUs modernas podem mudar sua velocidade, dependendo de quantos núcleos estão em uso no total. Mesmo que você tenha certeza de que seu processo está usando apenas um único núcleo e nenhum outro processo está usando, a velocidade desse núcleo será diferente dependendo de como o sistema operacional usará os outros núcleos. Leve isso em consideração ao executar seus testes.
Liori 22/10/16
Você deve conseguir desativar os núcleos da CPU do BIOS, talvez seja mais confiável para os seus testes, já que @liori afirmou acima que o sistema operacional pode estar alterando a velocidade do núcleo.
Marcs
Que tal criar uma VM e atribuir apenas um núcleo a ela? Ah, acabei de ler o "para não usar este núcleo da CPU", então não importa ...
sakisk 27/10

Respostas:

26

No linux, a chamada do sistema para definir a afinidade da CPU para um processo é sched_setaffinity. Depois, há a tasksetferramenta para fazer isso na linha de comando.

Para que esse programa seja executado em apenas uma CPU, acho que você gostaria de algo como

taskset -c 1 ./myprogram

(defina qualquer número de CPU como argumento para o -ccomutador.)

Isso deve estar próximo o suficiente de um sistema de processador único, desde que seus outros processos não executem muito em comparação com o que você deseja medir ou que sejam programados para outras CPUs. Se você quiser dedicar uma CPU apenas a esse processo único e impedir que outros processos sejam executados nessa CPU, também será necessário definir sua afinidade.

Isso, eu não sei como fazer corretamente. Você precisaria definir a afinidade do processador initlogo no início do processo de inicialização para garantir que ela seja herdada para todos os processos no sistema. Como solução alternativa, você pode usar taskset -c -p 0 $PIDtodos os outros processos para forçá-los a executar apenas na CPU # 0.

systemd também temCPUAffinity= de controlar a afinidade nos arquivos da unidade e há um par de perguntas sobre como definir a afinidade padrão aqui na unix.SE, mas eu não encontrou qualquer com uma solução boa.

Embora o @Kamil Maciorowski tenha comentado e respondido a outra pergunta no superuser.com , a configuração isolcpus=1 na linha de comando do kernel deve "isolar essa CPU dos algoritmos gerais de agendamento", o que é algo que você pode querer.

ilkkachu
fonte
Isso não responde bem à pergunta. Embora o conjunto de tarefas (ou outros métodos de configuração da afinidade da tarefa) garanta que um processo seja executado apenas no conjunto especificado de núcleos, não garante que apenas esse processo seja executado nesses núcleos. Ou seja, o sistema operacional pode agendar outros processos para o núcleo em que você definiu a afinidade do processo. Na prática, esta é a resposta mais útil, mas esteja ciente das limitações e, em particular, esteja ciente de que ela não fornece o que você pede em 1) "reserve apenas um núcleo da CPU apenas para o meu programa (para forçar o SO a use este núcleo da CPU) "
James Greenhalgh 21/10
@ JamesGreenhalgh, mas encontrar uma maneira de definir a afinidade da CPU para cada processo responderia à pergunta. É possível definir uma afinidade de CPU padrão para novos processos, como uma opção do kernel (linha de cmd)? Isso entraria em vigor no início do processo de inicialização e afetaria todos os processos.
jpaugh
Na verdade, eu perdi a cláusula entre parênteses sobre impedir a execução de outros processos nessa CPU. Ou talvez eu pensasse que o maior problema seria garantir que o programa em questão fosse executado em apenas um núcleo, em vez de quatro, e que os outros processos pudessem ser considerados uma espécie de incômodo, o que não importaria muito comparado a isso. Mas admito que não tive uma resposta adequada para essa parte da pergunta, além do que Kamil comentou agora.
ilkkachu
@jpaugh, acho que mesmo assim você não seria capaz de se isolar completamente da possibilidade de outro processo ser executado no "seu" núcleo. Por exemplo, um que redefina sua própria afinidade, ou mesmo o próprio código do kernel, consumindo tempo não relacionado ao gerenciamento do seu processo. Mais uma vez, concordo plenamente que, na prática, essa resposta é o que a maioria faria para resolver a maior parte do problema, mas eu estaria realmente interessado em ler uma resposta para a parte final entre parênteses!
James Greenhalgh