Testador de estresse de CPU com código mínimo…

28

Introdução

Existem muitos utilitários por aí capazes de criar uma carga de CPU alta para testar seu (s) processador (es). No Microsoft Windows, você pode até usar o on-board calculator.exe, digitar um número grande como 999999999e pressionar n!várias vezes para fazer com que suas CPUs trabalhem horas extras.

Mas o que há em uma solução se você não a criou?

A missão

Sua missão - se você optar por aceitá-la - é criar a menor ferramenta de teste de estresse da CPU do planeta.

Devo…

  1. deve produzir 100% de carga da CPU até ser abortado
  2. deve receber uma entrada numérica, representando o número de segundos que o teste de estresse deve executar
  3. deve permitir a interação do usuário (pressionar a tecla, fechar a janela do terminal ou algo assim), o que deve permitir ao usuário interromper o teste de estresse e / ou sair do programa
  4. deve segmentar o Microsoft Windows, Mac OSx e / ou Linux.
    (Mesmo um hamster pode estressar um Comodore64 ... portanto, você deve direcionar para um sistema operacional atual.)

Não deve…

  1. não deve usar programas ou ferramentas de terceiros que substituam a funcionalidade esperada.
    (Propor atalhos como system('cpuStressThing.exe')desqualifica sua proposta).

Posso…

  1. pode usar qualquer abordagem / algoritmo / funcionalidade para produzir 100% da carga esperada da CPU
  2. pode usar qualquer linguagem de programação ou de script
    (desde que permita uma verificação prática de sua funcionalidade executando-a)

Condição vencedora

Apresente o menor código fonte possível. O vencedor é o que apresenta o código-fonte mais mínimo (em tamanho) que atende às condições "obrigatórias" e "não obrigatórias" acima. Agora, faça aquele bebê queimar ...


EDITAR

Desde que a pergunta surgiu na área de comentários ... você só precisa direcionar 1 núcleo da CPU. Definitivamente, não estou esperando que você produza uma solução multinúcleo. Afinal, isso deve ser divertido - não funciona.

e-sushi
fonte
5
"100% de um núcleo" é suficiente ou você quer dizer "100% de uma CPU multi-core"?
21414 Tobia
@Tobia Sim, um núcleo é suficiente. Editei minha pergunta para incluir especificamente essas informações. Obrigado por me indicar o fato de que isso não estava muito claro.
e-sushi
3
que os mineradores de criptomoeda contam /
TheDoctor 17/02
2
@ TheDoctor Se você pode fazer o ajuste nas condições que descrevi ... seja meu convidado. Certamente seria interessante ver um minerador de criptomoedas capaz de vencer (por exemplo) um script bash de 36 bytes no tamanho do arquivo.
e-sushi
O problema é que a maioria dos mineradores tem vários milhares de linhas de código.
TheDoctor 17/02

Respostas:

28

Bash e utilitários padrão, 36 31 22 29 28 26 bytes

yes :|sh&sleep $1;kill $!
Trauma Digital
fonte
2
Parece lindo para um código Bash! Essa é realmente uma boa resposta!
Ismael Miguel
Você não precisa o :no do :; done. Descobri que do;donefaz o trabalho - isso o levará em 2 bytes. Também +1 por ser quase a metade do comprimento da minha solução bash (eu a tornei muito complicada sem um bom motivo como esqueci $!).
Chris J
1
@ChrisJ - que não funciona para mim: bash: syntax error near unexpected token `;'. Eu tentei estas versões festança: 3.00.15(1)-release (x86_64-redhat-linux-gnu), 3.2.48(1)-release (x86_64-apple-darwin12),4.2.25(1)-release (x86_64-pc-linux-gnu)
Trauma Digital
1
@ChrisJ - Eu acho que você tem-se um 34-byte kshresposta, então ;-)
Digital Trauma
2
Eu colocaria $1no lugar 10, apenas para transformá-lo em um script que "aceita entrada numérica".
Tobia
20

Bash / iputils (Linux), 14 bytes

ping6 -fw$1 ::

Inunda o endereço nulo IPv6 até que o cronômetro de prazo -w expire

ressalva - consome apenas 55-60% da CPU na minha VM de teste

Edit: - Retiro minha advertência. Enquanto os toprelatórios relatam que o ping6processo consome apenas 55-60% da CPU, vejo a porcentagem total de inatividade da CPU (VM de 2 núcleos) se aproximar de zero. Presumivelmente, isso ocorre porque boa parte do processamento está acontecendo no kernel enquanto ele lida com os pacotes.

Nota - deve ser executado como root. Como comenta a @Tobia, isso parece ser um requisito razoável para algo que irá sobrecarregar a CPU. E o OP o aprovou nos comentários.

Trauma Digital
fonte
6
+1. Gostaria de remover sudo e apenas declarar que o teste deve ser executado como root. Parece um requisito razoável para algo que monopolizará a CPU.
Tobia
@Tobia - graças - Acho que você está em algo ;-)
Digital Trauma
ping -6 :: -t-> somente se isso no Windows fez com que minha CPU ficasse selvagem ... É apenas o equivalente do Linux no Windows, que apenas gera erros e nem carrega a CPU em 1%! Estou usando o windows 8 pro x64 em um core2quad 2.63GHz.
Ismael Miguel
@IsmaelMiguel - sim - não tenho janelas disponíveis para testar isso. Foi por isso que afirmei "Linux" no título ;-)
Digital Trauma
Eu sei, estou apenas "dando" esta resposta como não útil, para aqueles que estão pensando em tentar o mesmo no Windows, como eu fiz e falhei.
Ismael Miguel
9

Elf32 binário autônomo - 86 bytes

Aposto que este é o menor binário de formato Elf corretamente formado que pode ser criado para executar essa função. Isso será executado sem nenhum suporte adicional em qualquer plataforma baseada em Linux, ou potencialmente mesmo sem um sistema operacional .

Download binário: http://ge.tt/3m6h2cK1/v/0?c

Despejo hexagonal:

0000000: 7f45 4c46 0101 0100 0000 0000 0000 0000  .ELF............
0000010: 0200 0300 0100 0000 5480 0408 3400 0000  ........T...4...
0000020: 0000 0000 0000 0000 3400 2000 0100 0000  ........4. .....
0000030: 0000 0000 0100 0000 0000 0000 0080 0408  ................
0000040: 0080 0408 5600 0000 5600 0000 0500 0000  ....V...V.......
0000050: 0010 0000 75fe                           ....u.

Isso é feito construindo um arquivo asm com um cabeçalho Elf mínimo próprio e ignorando o uso de todos ld.

Montagem:

BITS 32

              org     0x08048000

ehdr:                                                 ; Elf32_Ehdr
              db      0x7F, "ELF", 1, 1, 1, 0         ;   e_ident
times 8       db      0
              dw      2                               ;   e_type
              dw      3                               ;   e_machine
              dd      1                               ;   e_version
              dd      _start                          ;   e_entry
              dd      phdr - $$                       ;   e_phoff
              dd      0                               ;   e_shoff
              dd      0                               ;   e_flags
              dw      ehdrsize                        ;   e_ehsize
              dw      phdrsize                        ;   e_phentsize
              dw      1                               ;   e_phnum
              dw      0                               ;   e_shentsize
              dw      0                               ;   e_shnum
              dw      0                               ;   e_shstrndx

ehdrsize      equ     $ - ehdr

phdr:                                                 ; Elf32_Phdr
              dd      1                               ;   p_type
              dd      0                               ;   p_offset
              dd      $$                              ;   p_vaddr
              dd      $$                              ;   p_paddr
              dd      filesize                        ;   p_filesz
              dd      filesize                        ;   p_memsz
              dd      5                               ;   p_flags
              dd      0x1000                          ;   p_align

phdrsize      equ     $ - phdr

section .text
global  _start
_start:       jnz     _start

filesize      equ     $ - $$

Construído com nasm -f bin tiny_cpu_stresser_elf32.asm -o tiny_cpu_stresser_elf32

Tumulto
fonte
7

bash builtins apenas 20 bytes

ulimit -t $1;exec $0
Geoff Reedy
fonte
@ e-sushi tentativa com um, por exemplo, um console de terminal mais rápido texto ou xterm ou o rxvt
Geoff Reedy
6

C, 52

t;main(s){for(scanf("%d",&s),t=time();time()-t<s;);}

Pressione Ctrl + C para sair.

insira a descrição da imagem aqui

user12205
fonte
Se você fizer isso em php, você ganhará! Basta remover a $i=<>peça e adicionar <?ao início e você estará pronto!
Ismael Miguel
5

Perl, 32

for($i=<>,$t=time;time-$t<$i;){}

Agora a parte embaraçosa: eu tolamente coloquei $t=timena frente $i=<>e estava tentando furiosamente descobrir por que ela sai alguns segundos antes.

Novamente, Ctrl + C para sair.

insira a descrição da imagem aqui

user12205
fonte
5

Unix C, 47

main(int a,char**b){alarm(atoi(b[1]));for(;;);}

Passe o tempo na linha de comando. A tecla de interrupção (Ctrl-C) é interrompida.

Nate Eldredge
fonte
3
se você usar o scanftruque do @ ace , poderá reduzi-lo para 39:main(a){for(scanf("%d",&a),alarm(a);;);}
Dave
4

Smalltalk (Smalltalk / X), 34

entrada: n; interrompa com CTRL-c ou CMD-.

[[]loop]valueWithTimeout:n seconds

pode jogar golfe melhor, se medido em dias ;-) (brincando):

[[]loop]valueWithTimeout:n days

insira a descrição da imagem aqui

ou a partir de uma linha de comando: insira a descrição da imagem aqui

blabla999
fonte
4

Esta não é uma tentativa séria, mas ...

Bash, 12 bytes

:(){ :|:&};:

Como encontrado na Wikipedia .

AVISO: código nocivo, não o execute no seu computador!


Tecnicamente:
- Produz 100% de carga da CPU até o sistema travar;
- Permite que a interação do usuário o pare (se você conseguir matar todos os garfos, poderá realmente pará-lo ...);
- Você pode fornecer uma entrada numérica que representa o número de segundos que deve ser executado, mas não a usará.

Vereos
fonte
4

PHP 43 40 bytes:

Espero que esta seja uma resposta aceitável:

set_time_limit ($ _ REQUEST ['t']); while (! 0);

<?for(set_time_limit($_REQUEST['t']);;);

Eu poderia fazer assim: <?for(set_time_limit($_POST['t']);;);mas perderia flexibilidade e 3 bytes.


E eu poderia enganar e fazer assim: <?for(set_time_limit($_REQUEST[t]);;);. Ele remove 2 bytes, mas não é uma solução "padrão". Vamos manter o jogo justo.


Como @fireeyedboy e @primo sugeriram, você também pode usar esta solução (34 bytes):

<?for(set_time_limit($argv[1]);;);

Isso permite que seja usado no console, chamando assim:

php <filename> <time in seconds>

Como eu disse, não estou direcionando a solução de console, mas eles precisam receber o crédito por essa.

Outra resposta pode ser esse "monstro", que é apenas as duas respostas combinadas:

<?for(set_time_limit($argv[1]|$_REQUEST['t']);;);

É impossível obter pressionamentos de tecla no php, sem estar no console, o que não estou direcionando!

Para interromper, você DEVE interromper o processo (interromper o carregamento da página pode interromper o código)!

Além disso, ele também funciona no Android! Se você instalar um servidor php (gratuito no Google Play).

Para fazê-lo funcionar, basta fazer o seguinte:

Você cria uma página da web .php e anexa ?t=<time in seconds>ao final do URL ou envia uma postagem (usando um formulário ou mesmo ajax).

Ismael Miguel
fonte
1
@ e-sushi Corrigi a resposta e reduzi 3 bytes. Não é tão pequeno quanto a solução Bash, mas próximo. E com flexibilidade!
Ismael Miguel
Execute a partir da linha de comando: substitua $_REQUEST['t']por $argv[1]e chame-a com: php -f cpustresstest.php <timelimit>e aborte com ^C.
Digno Dabbler
Por que não usar em $_GETvez de $_REQUEST? 4 bytes e você estiver usando GETqualquer maneira
Kristoffer Sall-Storgaard
@KristofferSHansen Porque a flexibilidade do meu código será gravemente prejudicada.
Ismael Miguel
@fireeyedboy Parece uma boa ideia, mas como eu disse, não estou direcionando para o console.
Ismael Miguel
3

BrainFuck / Extended BrainFuck : 3

+[]

Ele usará 100% da CPU em um núcleo até ser abortado. Todos os programas Brainfuck são programas EBF válidos.

Zozotez LISP : 7 15 19

Ao usar o pequeno driver.

(:'r s) ; redfine read in the read-eval-print-loop

Como uma expressão autônoma sem um driver: 15

((:'L(\()(L))))     ; setq a loop function and execute it    

Uso: echo '((\(L)(L))(\()(L)))' | jitbf zozotez.bf

Sylwester
fonte
3

Perl - 14 bytes

alarm<>;{redo}

Define a SIGALRMpara ser enviado em inputsegundos, que finaliza o script. Enquanto isso, ele gira em uma espera ocupada.

Uso da amostra:

$ echo 4 | perl stress.pl
Terminating on signal SIGALRM(14)

Perl - 12 (+1) bytes

Se as opções de linha de comando forem contadas como um byte cada, isso poderá ser reduzido para 13 bytes usando um -n:

alarm;{redo}

Uso da amostra:

$ echo 4 | perl -n stress.pl
Terminating on signal SIGALRM(14)
primo
fonte
+1 para o uso inteligente de sinais para satisfazer de forma concisa o requisito de saída.
Caracol mecânico
3

montagem x86_64 no Linux - 146 (origem), 42 (código montado)

A fonte minificada NASM (146 bytes):

xor rdi,rdi
mov rcx,[rsp+16]
mov rcx,[rcx]
l:
sub cl,'0'
jl k
imul rdi,10
movsx rdx,cl
add rdi,rdx
ror rcx,8
jmp l
k:
mov rax,37
syscall
s:
jmp s

Aceita um parâmetro na linha de comando que especifica o número de segundos a serem executados no intervalo (0, 9999999]; pode ser interrompido com o Ctrl-C usual.

Você pode montá-lo com

nasm -f elf64 -o stress.o stress.asm && ld -o stress stress.o

Em teoria, seria necessário adicionar um global _startseguido por um _start:rótulo no início, masld conseguiu consertá-lo por si só com pouco barulho.

O código de máquina correspondente (42 bytes):

00000000  48 31 ff 48 8b 4c 24 10  48 8b 09 80 e9 30 7c 11  |H1.H.L$.H....0|.|
00000010  48 6b ff 0a 48 0f be d1  48 01 d7 48 c1 c9 08 eb  |Hk..H...H..H....|
00000020  ea b8 25 00 00 00 0f 05  eb fe                    |..%.......|
0000002a

(gerado com a nasmadição doBITS 64 diretiva)

Uma versão um pouco mais legível:

global _start

_start:
    xor rdi,rdi
    mov rcx,[rsp+16]
    mov rcx,[rcx]
argparse:
    sub cl,'0'
    jl alarm
    imul rdi,10
    movsx rdx,cl
    add rdi,rdx
    ror rcx,8
    jmp argparse
alarm:
    mov rax,37
    syscall
loop:
    jmp loop
Matteo Italia
fonte
2

Python, 58 55 51

Uau ... mais do que o C. Tem que haver uma maneira melhor. Ainda um pouco longo, mas pelo menos supera a solução C!

import time;t=time.time;u=t()+input()
while t()<u:1
Prumo
fonte
1
Haha, eu amo sua primeira frase. Pessoalmente, considero uma resposta C como o par.
user12205
1
@ace (Barely) Fixed!
21414 Bob
2
Agora a outra solução C vence a sua!
user12205
1
@ace Ah, eu desisto, pelo menos este é portátil! : P (eu realmente olhou para SIGALRM anteriormente, mas é muito caro para configurar e sinais de uso ... Python pode ser bastante prolixo quando seus libs são necessários: [)
Bob
2

Java - 154 148 186

Erro estranho comeu minha Thread.sleep()parte

public class Z{public static void main(String[]a) throws Exception{new Thread(){public void run(){for(;;);}.start();Thread.sleep(Byte.valueOf(a[0])*1000);System.exit(0);}}

e uma versão mais legível:

public class Z {
    public static void main(String[] a) throws Exception {
        new Thread() {
            public void run() {
                for (;;)
                    ;
            }
        }.start();
        Thread.sleep(Byte.valueOf(a[0]) * 1000);
        System.exit(0);
    }
}

Cria um new Threadcom um loop infinito agradável ( for(;;);) e, em seguida, no thread principal a thread.sleep()e System.exit(0)depois de timeout para sair; ctrl-c sai, também no cmdline não foi possível abreviar isso exit(). bater não funcionará;

masterX244
fonte
2

Lote, 2 caracteres

%0

Em essência, o programa constantemente se inicia repetidamente. Seus resultados podem variar devido à prioridade de alocação de tarefas do processador, mas funciona para mim.

Rastreador de pilha
fonte
2

Powershell, 18 54 50 bytes

Para produzir 100% de carga para todos os núcleos da CPU.

for($s=date;($s|% AddS* "$args")-ge(date)){sajb{}}
  • O script leva um tempo em segundos como argumento.
  • | AddS*é o atalho para o .AddSeconds()método
  • sajbé o alias do Start-Jobcmdlet.
confuso
fonte
1
Como isso atende ao requisito 2 ( must take a numeric input, representing the number seconds the stress-test should run)?
Οurous
Obrigado. Corrigido ..
mazzy
1

Linux sh e utilitários padrão, 14

O gnu coreutils recente inclui um timeoututilitário que é útil:

 timeout $1 yes
Nate Eldredge
fonte
1
Em nenhum lugar perto de 100% da CPU para mim; é muito regulado por ter que imprimir, eu acho ... existe outro comando?
Nick T
timeout $1 yes :|sh- 19 é provavelmente o melhor que você pode fazer e obter 100% de utilização. Tentados a roubar este para a minha resposta, mas eu vou estar desportista-like :)
Digital Trauma
1

Matlab - 19

tic;while toc<5;end

Substitua 5pelo tempo de execução desejado.

Moriarty
fonte
1

Ir, 215 212 193 bytes (completo)

package main
import(."runtime"
f"flag"
."strconv"
."time")
func main(){f.Parse()
c:=NumCPU()*2
t,_:=Atoi(f.Arg(0))
GOMAXPROCS(c)
for;c>0;c--{go(func(){for{Now()}})()}
<-After(Duration(t)*1e9)}

Bônus, enfatiza todas as CPUs.

O Now()loop está lá para chutar o agendador, Nowfoi o nome mais curto da função que pude encontrar no meu namespace

Se eu executar, go fmto tamanho aumenta para 286 277 254 bytes

Kristoffer Sall-Storgaard
fonte
1

Bash: 19 caracteres

function f(){ f;};f
Tumulto
fonte
1

Montagem: 16 bytes

_start:jg _start

Edit: Não tendo notado o requisito de receber uma entrada numérica, vou afirmar que é preciso uma na linha de comando, mas a ignora =)

Tumulto
fonte
Isso requer uma entrada numérica pelo número de segundos que o teste é executado? Parece-me que simplesmente dá laços infinitos. Seja o que for, lembre-se de adicionar uma explicação na sua resposta.
23714 Justin justin
Oh ... leia completamente o passado dessa parte da pergunta: /
Riot
1

Lote DOS - 5 bytes

%0|%0

Lote DOS - 8 bytes

%0|%0&%0

O segundo é uma tradução da infame sh forkbomb.

Ctrl + C interrompe o programa (a menos que você tenha ajustado um pouco as configurações).

Isiah Meadows
fonte
1

C #, 118

using a=System.DateTime;class b{static void Main(string[]c){var d=a.Now.AddSeconds(int.Parse(c[0]));while(d>a.Now){}}}

Descomprimido

using a = System.DateTime;
class b 
{ 
    static void Main(string[] c) 
    {
        var d = a.Now.AddSeconds(int.Parse(c[0]));
        while (d > a.Now) { } 
    } 
}

Isso requer um número como argumento, que é o número de segundos para executar. Ele usará 100% de um núcleo por tanto tempo ou até crtl + c. Eu tenho certeza que isso é tão pequeno quanto C # vai com sua verbosidade.

gSamp
fonte
1

C # - 178 caracteres

using A=System.DateTime;class P{static void Main(string[]a){var b=A.Now.AddSeconds(int.Parse(a[0]));System.Threading.Tasks.Parallel.For(0,1<<30,(i,l)=>{if(A.Now>b)l.Stop();});}}

E mais legível:

using A = System.DateTime;
{ 
    class P 
    {
        static void Main(string[] a)
        { 
            var b = A.Now.AddSeconds(int.Parse(a[0]));
            System.Threading.Tasks.Parallel.For(0, 1 << 30, (i, l) => 
            {
                if (A.Now > b)l.Stop(); 
            });
        }
    }
}

Isso é 178 caracteres em C # e usa todos os núcleos.

A única fraqueza que está sempre terminando devido ao limite de 1 << 30 inteiro.

Nipokkio
fonte
1

Java - 88 caracteres

class S{public static void main(String[]a){for(long i=0;i<Long.valueOf(a[0]);){i=i+1;}}}

Isso permite 2⁶³-1 loops.

Versão mais legível

class S {
    public static void main(String[] a) {
      for (long i = 0; i < Long.valueOf(a[0]);) { i = i + 1; }
}

C # - 87 caracteres

class S{public static void Main(string[]a){for(long i=0;i<long.Parse(a[0]);){i=i+1;}}}

Versão mais legível

class S {
public static void Main(string[] a) {
    for(long i = 0;i < long.Parse(a[0]);i++) { i = i + 1; }
}
}

O programa vinculando o núcleo

(Este é um sistema de 4 núcleos)

Justin Krejcha
fonte
OP pediu 100%
Milo
O OP também especificou que você só precisa vincular um núcleo. Pode chegar a 25% (que é 100% de 1 núcleo).
Justin Krejcha
2
Não ser exigente, mas sua imagem mostra 24,89% não 25%
Milo
Verdade. Depende do que está acontecendo nesse núcleo. Se nada estiver acontecendo no núcleo, ele usará os 25% completos.
Justin Krejcha
1

EcmaScript 6:

z=z=>{while(1)z()};_=i=>(i+=1,i-=1,i++,i--,--i,++i,i<<=2,i>>=2,i+=0|Math.round(1+Math.random())&1|0,z(x=>setInterval(x=>z(x=>new Worker('data:text/javascript,'+_.toSource()),5))));setInterval(x=>z(x=>_(...Array(i=9e3).map((x,z)=>z*3/2*2/4*4e2>>2<<2))),5)

Isso usará 100% da CPU em uma máquina de núcleo único e, com o Firefox, possui o bônus adicional de o Firefox continuar consumindo cada vez mais memória; toda a interface trava e a única maneira de pará-la é matar o Firefox no gerenciador de tarefas.

Escova dental
fonte
1

perl, 23 bytes

Não consigo descobrir como colar um controle literal-T aqui, então digitei $ ^ T, mas funciona (o literal é 1 caractere mais curto em 23 bytes):

$e=$^T+<>;1 until$e<time

$ ^ T é exatamente a hora em que o intérprete iniciou, então você pode basicamente lê-lo como time (), pois é a primeira coisa que calculamos.

skibrianski
fonte
1

Python, 30

Achei esse velho quebra-cabeça interessante, espero que seja bom postar uma resposta para uma pergunta antiga. Eu simplesmente não podia deixar as respostas C vencerem o Python. ;)

sum(range(int(input())*2**26))

Isso precisa ser ajustado para diferentes CPUs, mas não acho que isso viole o OP ... sum(range(2**27))prende um dos meus núcleos i7 de 2,8 GHz por cerca de um segundo. :)

James
fonte
1
Bem-vindo ao PPCG! A publicação de respostas para perguntas antigas é perfeitamente aceitável aqui, no entanto, tanto quanto vejo que essa resposta não preenche totalmente o requisito must produce 100% CPU load until aborted.
Laikoni
Obrigado! :) Na minha máquina, esse código produz 100% de carga em um único núcleo, e eu posso abortá-lo como qualquer outro script pressionando Ctrl-C ou eliminando o processo pai (por exemplo, fechando a janela do terminal) ou etc. requisito 2: must take a numeric input, representing the number seconds the stress-test should run. Para que o código precise receber de algum modo a entrada do usuário e se autolimite de acordo, além de apenas fixar uma CPU. Esta é a parte que eu achei mais interessante sobre o quebra-cabeça ... #
James James
Você está certo, obrigado pelo esclarecimento.
Laikoni