Por que os programas não são escritos no Assembly com mais frequência? [fechadas]


216

Parece ser uma opinião comum que a programação em assembly leva mais tempo e é mais difícil de programar do que em uma linguagem de nível superior, como C. Portanto, parece recomendável ou presumido que é melhor escrever em uma linguagem de nível superior por esses motivos. e por uma melhor portabilidade.

Recentemente, escrevi no assembly x86 e me ocorreu que talvez esses motivos não sejam realmente verdadeiros, exceto talvez a portabilidade. Talvez seja mais uma questão de familiaridade e saber escrever bem uma montagem. Notei também que a programação em assembly é bem diferente da programação em uma HLL. Talvez um programador de montagem bom e experiente possa escrever programas com a mesma facilidade e rapidez que um programador C experiente escrevendo em C.

Talvez seja porque a programação de montagem seja bem diferente das HLLs e, portanto, exija pensamentos, métodos e maneiras diferentes, o que faz parecer muito estranho programar para pessoas desconhecidas e, por isso, dá o nome errado ao escrever programas.

Se a portabilidade não é um problema, então realmente, o que C teria sobre um bom montador como o NASM?

Edit: Apenas para apontar. Quando você está escrevendo em montagem, não precisa escrever apenas nos códigos de instruções. Você pode usar macros e procedimentos e suas próprias convenções para fazer várias abstrações para tornar os programas mais modulares, mais fáceis de manter e mais fáceis de ler. É aqui que entra o conhecimento de como escrever uma boa montagem.


71
Escrever ? E a leitura de código? você (e outros) lerá o código muito mais do que você escreve
n °

81
Por que eu deveria aprender um novo idioma apenas porque meu programa deve ser executado em uma nova plataforma? Por que eu deveria construir meus programas para se adequar à idéia de quantos registros existem e o que você pode fazer com os processadores? Eu tento resolver problemas, não faço os lances dos computadores.
Joachim Sauer

8
Resumo do EDIT: Pode-se usar um compilador C.
Meinersbur

4
@ Simon Talvez eu tenha errado meus anos, mas estou surpreso por estarmos debatendo ASM vs "uma linguagem de alto nível como C" em 2010. Especificamente, a parte em que C é o exemplo de uma linguagem de alto nível
matt b

11
@ changelog: Não é assim que você soletra programação.reddit.com.
BoltClock

Respostas:


331

O ASM tem pouca legibilidade e não é realmente sustentável em comparação com idiomas de nível superior.

Além disso, há muito menos desenvolvedores ASM do que em outros idiomas mais populares, como C.

Além disso, se você usar um idioma de nível superior e novas instruções ASM estiverem disponíveis (SSE, por exemplo), você só precisará atualizar seu compilador e seu código antigo poderá facilmente usar as novas instruções.

E se a próxima CPU tiver o dobro de registros?

O inverso dessa pergunta seria: Que funcionalidade os compiladores fornecem?

Duvido que você possa / queira / deve otimizar seu ASM melhor do que gcc -O3pode.


10
O gcc não é tão bom em otimização, muito melhor que o humano médio, mas há muitos lugares em que os otimizadores não conseguem fazer um bom trabalho. Concordo com você, caso contrário.
old_timer

4
@dwelch Em casos muito raros, o gcc (ou muitos outros compiladores) não consegue otimizar adequadamente o C. compilado. Nesses casos, no entanto, você sempre pode escrever um número limitado de procedimentos no ASM e vincular apenas esses métodos durante a compilação.
precisa saber é o seguinte

@ Ben S: Eu editei inicialmente em "muitos" em vez de "muito" porque "muito" é usado apenas para objetos singulares. Como o objeto "much" é plural (desenvolvedores), "many" é a opção correta. Mas não vou editar sua resposta novamente se "muito" for o que você deseja.
Billy ONeal

1
Existem muitos casos em que um compilador não pode otimizar bem, mas muitas vezes um desenvolvedor ciente das limitações do otimizador pode otimizar seu código C sem recorrer à montagem.
Qwertie 23/04

1
No FWIW do meu trabalho diário, compilo nosso produto com gcc -g -O0, porque ser capaz de anexar gdb a ele em um sistema ativo e não enlouquecer devido a variáveis ​​otimizadas fora da existência, vale muito mais a pena. empresa do que seria deixar ociosos outros 4 bilhões de ciclos de CPU todos os dias (de um total de 3 trilhões). Triturar números inteiros simplesmente não é o gargalo com muita frequência.
Bernd Jendrissek

1930

Olá, eu sou um compilador.

Acabei de digitalizar milhares de linhas de código enquanto você estava lendo esta frase. Naveguei por milhões de possibilidades de otimizar uma única linha sua usando centenas de técnicas diferentes de otimização, com base em uma vasta quantidade de pesquisas acadêmicas nas quais você passaria anos. Não sentirei vergonha, nem mesmo uma ligeira pontada, quando converter um loop de três linhas em milhares de instruções apenas para torná-lo mais rápido. Não tenho vergonha de fazer grandes esforços de otimização ou de fazer os truques mais sujos. E se você não quiser, talvez por um dia ou dois, eu me comportarei e farei da maneira que você quiser. Posso transformar os métodos que estou usando quando quiser, sem alterar uma única linha do seu código. Eu posso até mostrar como seu código ficaria em assembly, em diferentes arquiteturas de processador e diferentes sistemas operacionais e em diferentes convenções de montagem, se desejar. Sim, tudo em segundos. Porque, você sabe, eu posso; e você sabe, você não pode.

PS Oh, a propósito, você não estava usando metade do código que escreveu. Fiz um favor e joguei fora.


99

Eu escrevi shedloads de assembler para os chips 6502, Z80, 6809 e 8086. Parei de fazê-lo assim que os compiladores C se tornaram disponíveis para as plataformas que eu estava abordando e imediatamente fiquei pelo menos 10x mais produtivo. A maioria dos bons programadores usa as ferramentas que utiliza por razões racionais.


72

Adoro programar em linguagem assembly, mas é preciso mais código para fazer a mesma coisa que em um idioma de alto nível, e há uma correlação direta entre linhas de código e bugs. (Isso foi explicado décadas atrás no The Mythical Man-Month .)

É possível pensar em C como 'montagem de alto nível', mas dê alguns passos acima e você estará em um mundo diferente. Em C #, você não pensa duas vezes em escrever isso:

foreach (string s in listOfStrings) { /* do stuff */ }

Seriam dezenas, talvez centenas de linhas de código em assembly, cada programador que o implementasse adotaria uma abordagem diferente e a próxima pessoa que chegasse teria que descobrir isso. Portanto, se você acredita (como muitos acreditam) que os programas são escritos principalmente para outras pessoas lerem, a montagem é menos legível do que a HLL típica.

Edit: eu acumulei uma biblioteca pessoal de código usada para tarefas comuns e macros para implementar estruturas de controle do tipo C. Mas eu bati na parede nos anos 90, quando as GUIs se tornaram a norma. Muito tempo estava sendo gasto em coisas rotineiras.

A última tarefa que tive onde o ASM era essencial foi, há alguns anos, escrever código para combater malware. Sem interface do usuário, por isso foram todas as partes divertidas sem o inchaço.


Você tem certeza sobre isso? I parecem leitura recordação no código completo que este não era o caso ...
jcolebrand

1
Tenho certeza de que há um ponto em que a vantagem de 'menos linhas' é superada pela desvantagem de 'otimização prematura'. Mas eu não vejo o Code Complete há séculos ...
egrunin

6
Um pouco irônico usar "otimização prematura" como um argumento para montagem ... (Eu provavelmente interpretam mal de você Mas eu ainda acho que é engraçado..)
Bernd Jendrissek

Você ainda pode chamar a função no assembler, por isso duvido que um loop foreach leve dezenas a centenas de linhas. Ou o que estou perdendo?
Sebastian Mach

@ phresnel: foreachtrabalha muito mais do que for- instancia e usa um iterador específico do tipo.
egrunin

15

Além das respostas de legibilidade, capacidade de manutenção, código mais curto e, portanto, menos bugs, além de ser muito mais fácil, adicionarei um motivo adicional:

velocidade do programa.

Sim, na montagem, você pode ajustar manualmente seu código para fazer uso de todos os ciclos anteriores e torná-lo o mais rápido possível fisicamente. No entanto, quem tem tempo? Se você escrever um programa C não totalmente estúpido, o compilador fará um ótimo trabalho de otimização para você. Provavelmente, faça pelo menos 95% das otimizações que você faria manualmente, sem precisar se preocupar em acompanhar nenhuma delas. Definitivamente, existe um tipo de regra 90/10 aqui, onde os últimos 5% das otimizações acabarão ocupando 95% do seu tempo. Então, por que se preocupar?


4
+1. Escrever código assembler e escrever código assembler rápido são duas coisas diferentes. Se você usa um bom compilador, obtém o código rápido do assembler gratuitamente.
Niki

você obtém código rápido de montador de graça apenas se souber usar o compilador, a maioria não usa otimização, a maioria das pessoas compila com opções de depuração e, como resultado, acaba com um montador lento mal executado. sim, em mais de 99% do tempo você não deve tocá-lo, basta tocar nos botões do compilador e não ajustar a saída diretamente.
precisa saber é o seguinte

se você se preocupa com as otimizações, deve fazê-lo no compilador ... Se você não se importa com otimizações, mas ainda está usando assembly, está apenas sendo bobo.
precisa saber é o seguinte

@dwelch: Eu acho que pode haver algumas crianças que não se incomodam em descobrir como suas ferramentas são usadas. Mas duvido que pessoas como elas jamais sejam capazes de escrever códigos de montadores rápidos.
Niki

13

Se um programa de produção médio tiver 100 mil linhas de código e cada linha tiver entre 8 e 12 instruções para montagem, isso representará 1 milhão de instruções para montagem.

Mesmo se você pudesse escrever tudo isso à mão a uma velocidade decente (lembre-se, é 8 vezes mais código do que precisa escrever), o que acontece se você quiser alterar algumas das funcionalidades? Compreender algo que você escreveu há algumas semanas atrás com essas 1 milhão de instruções é um pesadelo! Não há módulos, classes, design orientado a objetos, estruturas, nada. E a quantidade de código semelhante que você precisa escrever para as coisas mais simples é assustadora, na melhor das hipóteses.

Além disso, você não pode otimizar seu código quase tão bem quanto uma linguagem de alto nível. Onde C, por exemplo, executa um número insano de otimizações porque você descreve sua intenção, não apenas seu código, no assembler você escreve apenas código, o assembler não pode realmente executar nenhuma otimização digna de nota em seu código. O que você escreve é ​​o que obtém e, confie em mim, não pode otimizar com segurança 1 milhão de instruções que você corrige e corrige ao escrevê-las.


8

Bem, eu tenho escrito muita montagem "nos velhos tempos" e posso garantir que sou muito mais produtivo quando escrevo programas em uma linguagem de alto nível.


8
"Assembléia é latina".
Adriano Varoli Piazza

4
@ Adriano: exceto que existem muitos, muitos dialetos diferentes e dois não são parecidos.
Joachim Sauer

1
Claro, mas eu quis dizer que aprender a programar em qualquer um deles oferece uma visão sobre a arquitetura de uma máquina que ajuda em níveis mais altos. A menos que você lide com a memória paginada, nesse caso, você acaba com cicatrizes. Como ler Carmen 16 de Catulo.
Adriano Varoli Piazza

5
@Adriano "Assembléia é latina", nenhum asm é grunhido de homens das cavernas. Um grunhido por pedra 2grunts por veado, 3grunts por fogo - bom para coisas simples, mas difícil de administrar um império.
Martin Beckett

1
@ Martin: Você já tentou fazer aritmética complexa com algarismos romanos?
Adriano Varoli Piazza

6

Um nível razoável de competência de montador é uma habilidade útil, especialmente se você trabalha em qualquer tipo de nível de sistema ou programação incorporada, não tanto porque você precisa escrever tanto montador, mas porque às vezes é importante entender o que a caixa realmente está fazendo . Se você não tem um entendimento de baixo nível dos conceitos e problemas do assembler, isso pode ser muito difícil.

No entanto, quanto à realmente escrever muito código no assembler, há várias razões para isso não ser muito feito.

  • Simplesmente não há (quase) necessidade. Exceto por algo como a inicialização muito precoce do sistema e talvez alguns fragmentos de assembler ocultos em funções ou macros C, todos os códigos de nível muito baixo que podem ter sido escritos no assembler podem ser escritos em C ou C ++ sem dificuldade.

  • O código em linguagens de nível superior (mesmo C e C ++) condensa a funcionalidade em muito menos linhas, e há uma pesquisa considerável mostrando que o número de bugs se correlaciona com o número de linhas do código-fonte. Ou seja, o mesmo problema, resolvido no assembler e C, terá mais erros no assembler simplesmente porque é mais longo. O mesmo argumento motiva a mudança para linguagens de nível superior, como Perl, Python, etc.

  • Ao escrever no assembler, você precisa lidar com todos os aspectos do problema, desde o layout detalhado da memória, seleção de instruções, escolhas de algoritmos, gerenciamento de pilha, etc. Linguagens de nível mais alto tiram tudo isso de você, e é por isso que são muito mais densos termos de LOC.

Essencialmente, todos os itens acima estão relacionados ao nível de abstração disponível para você no assembler versus C ou em algum outro idioma. O Assembler obriga você a fazer todas as suas próprias abstrações e mantê-las através de sua própria autodisciplina, onde qualquer linguagem de nível intermediário como C, e especialmente as de nível superior, fornece abstrações prontas para uso, assim como as capacidade de criar novos com relativa facilidade.


6

Como desenvolvedor que passa a maior parte do tempo no mundo da programação embarcada, eu argumentaria que o assembly está longe de ser uma linguagem obsoleta / morta. Há um certo nível de codificação próximo ao metal (por exemplo, em drivers) que às vezes não pode ser expresso com precisão ou eficiência em um idioma de nível superior. Escrevemos quase todas as nossas rotinas de interface de hardware no assembler.

Dito isto, esse código de montagem é agrupado de forma que possa ser chamado a partir do código C e é tratado como uma biblioteca. Não escrevemos o programa inteiro em montagem por vários motivos. Primeiro e acima de tudo, é portabilidade; nossa base de código é usada em vários produtos que usam arquiteturas diferentes e queremos maximizar a quantidade de código que pode ser compartilhada entre eles. O segundo é a familiaridade do desenvolvedor. Simplificando, as escolas não ensinam montagem como costumavam fazer, e nossos desenvolvedores são muito mais produtivos em C do que em montagem. Além disso, temos uma grande variedade de "extras" (itens como bibliotecas, depuradores, ferramentas de análise estática etc.) disponíveis para o nosso código C que não estão disponíveis para o código da linguagem assembly. Mesmo se quiséssemos escrever um programa de montagem pura, não seria possível, porque várias bibliotecas críticas de hardware estão disponíveis apenas como C libs. Em certo sentido, é um problema de galinha / ovo. As pessoas são afastadas do assembly porque não existem tantas bibliotecas e ferramentas de desenvolvimento / depuração disponíveis, mas as bibliotecas / ferramentas não existem porque poucas pessoas usam o assembly para justificar o esforço para criá-las.

No final, há um tempo e um lugar para praticamente qualquer idioma. As pessoas usam o que estão mais familiarizadas e produtivas. Provavelmente sempre haverá um lugar no repertório de um programador para montagem, mas a maioria dos programadores descobrirá que pode escrever código em uma linguagem de nível superior que é quase tão eficiente em muito menos tempo.


6

Quando você está escrevendo em montagem, não precisa escrever apenas nos códigos de instruções. Você pode usar macros e procedimentos e suas próprias convenções para fazer várias abstrações para tornar os programas mais modulares, mais fáceis de manter e mais fáceis de ler.

Então, o que você está basicamente dizendo é que, com o uso qualificado de um assembler sofisticado, você pode tornar seu código ASM cada vez mais próximo de C (ou qualquer outra linguagem de baixo nível de sua própria invenção), até que você acabe tão produtivo quanto um programador em C.

Isso responde à sua pergunta? ;-)

Não digo isso à toa: programei usando exatamente esse montador e sistema. Melhor ainda, o assembler poderia direcionar um processador virtual, e um tradutor separado compilou a saída do assembler para uma plataforma de destino. É o que acontece com o FI da LLVM, mas em suas formas iniciais o pré-data em cerca de 10 anos. Portanto, havia portabilidade, além da capacidade de escrever rotinas para um montador de destino específico, quando necessário, para eficiência.

Escrever usando esse assembler era tão produtivo quanto C e, em comparação com o GCC-3 (que já existia na época em que eu estava envolvido), o assembler / tradutor produziu um código que era mais ou menos rápido e geralmente menor. O tamanho era realmente importante, e a empresa tinha poucos programadores e estava disposta a ensinar aos novos contratados um novo idioma antes que eles pudessem fazer algo útil. E nós tínhamos o apoio de que pessoas que não conheciam o montador (por exemplo, clientes) podiam escrever C e compilá-lo para o mesmo processador virtual, usando a mesma convenção de chamada e assim por diante, para que ele tivesse uma interface organizada. Então parecia uma vitória marginal.

Isso ocorreu com vários anos de trabalho na bolsa, desenvolvendo a tecnologia de montagem, bibliotecas e assim por diante. É certo que muito disso foi feito para torná-lo portátil, se ele tivesse como alvo apenas uma arquitetura, o montador que dançava e dançava seria muito mais fácil.

Em resumo: você pode não gostar de C, mas isso não significa que o esforço de usar C seja maior que o esforço de criar algo melhor.


5

A montagem não é portátil entre diferentes microprocessadores.


Isso não é exatamente verdade nos processadores modernos e nos programas assembler; você pode direcionar diferentes processadores da mesma forma que em C. Certamente não será capaz de usar o conjunto completo de instruções nesse caso, mas também não o escreverá. em C. Portabilidade não é a principal preocupação.
Blindy

6
Talvez você queira dizer arquitetura .
Ben S

2
@Blindy - Pode alvo diferentes processadores dentro da família x 86, mas não há dúvida nenhuma semelhança em instruções de montagem entre uma variante x 86 e um processador ARM ou um Z80 ou um 8051.
semaj

É verdade, mas também não é possível programar um z80 em c. Acho que estamos todos falando sobre processadores x86 / x64 normais aqui.
Blindy

1
Todo o mundo não é um x86. Nada sobre "microprocessadores diferentes" sugere que todos eles executam o mesmo conjunto de instruções.
Bernd Jendrissek

5

A mesma razão pela qual não vamos mais ao banheiro lá fora, ou por que não falamos latim ou aramaico.

A tecnologia aparece e torna as coisas mais fáceis e acessíveis.

EDIT - para deixar de ofender as pessoas, removi certas palavras.


4
Você ainda está ofendendo Luddites com a palavraTechnology
SeanJA

1
"Nós" não falamos latim?
húmido

Nem o latim nem o aramaico desapareceram porque foram substituídos por uma melhor tecnologia (isto é, um idioma mais fácil de aprender / aprender). De fato, o latim ainda está conosco em todos os lugares da Europa. Todas as línguas romanas são baseadas no latim. O (neo) aramaico moderno é falado por quase meio milhão de pessoas hoje. As razões pelas quais essas línguas não são mais predominantes são históricas (geopolíticas, para ser mais preciso), não tecnológicas. Mesmo motivo, o inglês é a língua franca das classes dominantes e científicas de nossa época - as pessoas do último império, os britânicos (e agora os norte-americanos) falam isso.
the Ritz

4

Por quê? Simples.

Compare isto:

        for (var i = 1; i <= 100; i++)
        {
            if (i % 3 == 0)
                Console.Write("Fizz");
            if (i % 5 == 0)
                Console.Write("Buzz");
            if (i % 3 != 0 && i % 5 != 0)
                Console.Write(i);
            Console.WriteLine();
        }

com

.locals init (
    [0] int32 i)
L_0000: ldc.i4.1 
L_0001: stloc.0 
L_0002: br.s L_003b
L_0004: ldloc.0 
L_0005: ldc.i4.3 
L_0006: rem 
L_0007: brtrue.s L_0013
L_0009: ldstr "Fizz"
L_000e: call void [mscorlib]System.Console::Write(string)
L_0013: ldloc.0 
L_0014: ldc.i4.5 
L_0015: rem 
L_0016: brtrue.s L_0022
L_0018: ldstr "Buzz"
L_001d: call void [mscorlib]System.Console::Write(string)
L_0022: ldloc.0 
L_0023: ldc.i4.3 
L_0024: rem 
L_0025: brfalse.s L_0032
L_0027: ldloc.0 
L_0028: ldc.i4.5 
L_0029: rem 
L_002a: brfalse.s L_0032
L_002c: ldloc.0 
L_002d: call void [mscorlib]System.Console::Write(int32)
L_0032: call void [mscorlib]System.Console::WriteLine()
L_0037: ldloc.0 
L_0038: ldc.i4.1 
L_0039: add 
L_003a: stloc.0 
L_003b: ldloc.0 
L_003c: ldc.i4.s 100
L_003e: ble.s L_0004
L_0040: ret 

Eles são idênticos em termos de recursos. O segundo nem é assembler, mas o .NET IL (Linguagem Intermediária, semelhante ao bytecode de Java). A segunda compilação transforma a IL em código nativo (ou seja, quase assembler), tornando-a ainda mais enigmática.


3

Eu acho que o ASM até x86 (_64) faz sentido nos casos em que você ganha muito utilizando instruções difíceis para um compilador otimizar. O x264, por exemplo, usa muito ASM para sua codificação, e os ganhos de velocidade são enormes.


2

Tenho certeza de que há muitas razões, mas duas razões rápidas em que consigo pensar são

  1. O código de montagem é definitivamente mais difícil de ler (tenho certeza de que é mais demorado escrever também)
  2. Quando você tem uma grande equipe de desenvolvedores trabalhando em um produto, é útil ter seu código dividido em blocos lógicos e protegido por interfaces.

1
Observe que você também pode separar a montagem em blocos lógicos.
Paul Williams

2

Uma das primeiras descobertas (você encontrará no Mythical Man-Month de Brooks , que é da experiência da década de 1960) foi que as pessoas eram mais ou menos tão produtivas em um idioma quanto em outro, em linhas de código depuradas por dia. Obviamente, isso não é universalmente verdade e pode quebrar quando for levado longe demais, mas geralmente era verdade nos idiomas de alto nível da época de Brooks.

Portanto, a maneira mais rápida de obter produtividade seria usar linguagens em que uma linha de código individual fizesse mais e, de fato, isso funcionaria, pelo menos para linguagens de complexidade como FORTRAN e COBOL, ou para dar um exemplo mais moderno C.


2

Portabilidade é sempre um problema - se não agora, pelo menos eventualmente. A indústria de programação gasta bilhões todos os anos para portar software antigo que, no momento em que foi escrito, "obviamente" não apresentava nenhum problema de portabilidade.


2
"Ele não precisará ser portado para outra arquitetura" soa muito para meus ouvidos, como "Ele não precisará de mais de dois dígitos para o ano".
precisa

Ou não podemos usar c # porque o Windows pode não estar disponível no próximo ano?
Martin Beckett

Por exemplo, os computadores MacIntosh da Apple, baseados nos processadores Motorola MC68000, PowerPC (IBM et all) e agora nos processadores x86 (IA-32 (e)) da Intel. Então, sim, a portabilidade é um problema para qualquer sistema usado por tempo suficiente, e qualquer programador que não tenha sido mordido por seu código com duração maior do que o esperado ainda não tem experiência.
Mctylr

@ Martin: Daqui a vinte anos, haverá muitos programas em C # que as pessoas desejam executar e, portanto, haverá uma maneira de compilar e executar programas em C #. Não há nada inerentemente consertado no C #, embora em vinte anos eu ficaria surpreso se ainda fosse tão popular quanto é agora. No entanto, em vinte anos, nossas CPUs serão significativamente diferentes. Um programa assembler escrito em 1990 pode muito bem funcionar hoje em dia, mas com certeza não será o ideal, e será executado mais lento do que compilado C.
David Thornley

Foi isso que eu quis dizer - eu tenho muito mais problemas de portabilidade porque uma estrutura de alto nível foi alterada de 6 meses atrás do que porque as instruções em um x86 foram alteradas - especialmente porque asm codificado manualmente tende a seguir os métodos mais simples.
Martin Beckett

2

Houve um ciclo vicioso quando o assembly se tornou menos comum: à medida que as linguagens de nível superior amadureciam, os conjuntos de instruções da linguagem assembly eram construídos menos para a conveniência do programador e mais para a conveniência dos compiladores.

Portanto, agora, realisticamente, pode ser muito difícil tomar as decisões corretas sobre, digamos, quais registros você deve usar ou quais instruções são um pouco mais eficientes. Os compiladores podem usar heurísticas para descobrir quais compensações provavelmente terão o melhor retorno. Provavelmente, podemos pensar em problemas menores e encontrar otimizações locais que podem superar nossos compiladores agora bastante sofisticados, mas as probabilidades são de que, em geral, um bom compilador fará um trabalho melhor na primeira tentativa do que provavelmente um bom programador. Eventualmente, como John Henry, podemos vencer a máquina, mas podemos nos queimar seriamente chegando lá.

Nossos problemas também agora são bem diferentes. Em 1986, eu estava tentando descobrir como obter um pouco mais de velocidade de pequenos programas que envolviam colocar algumas centenas de pixels na tela; Eu queria que a animação fosse menos espasmódica. Um argumento justo para a linguagem assembly. Agora, estou tentando descobrir como representar abstrações em torno da linguagem dos contratos e da política de serviço para hipotecas, e prefiro ler algo que se pareça com o idioma que os executivos falam. Diferentemente das macros LISP, as macros Assembly não impõem muita coisa no que diz respeito a regras, portanto, mesmo que você consiga algo razoavelmente próximo a uma DSL em um bom assembler, ele estará sujeito a todos os tipos de peculiaridades que ganharam ' me causa problemas se eu escrevi o mesmo código em Ruby, Boo, Lisp, C # ou até F #.

Se seus problemas são fáceis de expressar em linguagem assembly eficiente, no entanto, você terá mais poder.


2

O mesmo vale para o que os outros disseram.

Nos bons velhos tempos antes da invenção do C, quando os únicos idiomas de alto nível eram coisas como COBOL e FORTRAN, havia muitas coisas que simplesmente não eram possíveis sem o recurso ao assembler. Era a única maneira de obter toda a flexibilidade, poder acessar todos os dispositivos, etc. Mas então C foi inventado, e quase tudo o que era possível na montagem era possível em C. Escrevi muito pouca montagem desde então.

Dito isto, acho que é um exercício muito útil para novos programadores aprenderem a escrever no assembler. Não porque eles realmente usariam muito, mas porque então você entende o que realmente está acontecendo dentro do computador. Eu já vi muitos erros de programação e códigos ineficientes de programadores que claramente não têm idéia do que realmente está acontecendo com os bits e bytes e registradores.


Sim, local. Os anos de E / S de disco e fita do Fortran nos mainframes da IBM atrás eram quase inúteis, então escrevemos nossas próprias rotinas de E / S no 370 / Assembler e as chamamos do código Fortan IV. E escrever código de montagem me fez realmente entender a arquitetura subjacente. Não escrevo nenhum código de montagem há alguns anos e todas as pessoas mais jovens com quem trabalho nunca escreveram nenhum - mas eu gostaria que eles escrevessem, é tão educativo.
Simon Knights

2

Estou programando em montagem agora há cerca de um mês. Costumo escrever um trecho de código em C e depois compilá-lo na montagem para me ajudar. Talvez eu não esteja utilizando todo o poder de otimização do compilador C, mas parece que minha fonte C asm está incluindo operações desnecessárias. Então, estou começando a ver que a conversa de um bom compilador C que supera um bom codificador de montagem nem sempre é verdadeira.

Enfim, meus programas de montagem são tão rápidos. E quanto mais eu uso assembly, menos tempo leva para escrever meu código, porque realmente não é tão difícil. Também o comentário sobre montagem com pouca legibilidade não é verdadeiro. Se você rotular seus programas corretamente e fazer comentários quando houver necessidade de elaboração adicional, tudo estará pronto. De fato, de certa forma, a montagem é mais clara para o programador, porque eles estão vendo o que está acontecendo no nível do processador. Não conheço outros programadores, mas para mim gosto de saber o que está acontecendo, em vez de as coisas estarem em uma espécie de caixa preta.

Com isso dito, a vantagem real dos compiladores é que um compilador pode entender padrões e relacionamentos e depois codificá-los automaticamente nos locais apropriados na fonte. Um exemplo popular são as funções virtuais em C ++, que exigem que o compilador mapeie de maneira ideal os ponteiros de função. No entanto, um compilador está limitado a fazer o que o fabricante do compilador permite que ele faça. Isso leva os programadores às vezes a recorrer a fazer coisas bizarras com seu código, adicionando tempo de codificação, quando eles poderiam ter sido feitos trivialmente com assembly.

Pessoalmente, acho que o mercado suporta fortemente idiomas de alto nível. Se a linguagem assembly fosse a única linguagem existente hoje, seriam cerca de 70% menos pessoas programando e quem sabe onde estaria o mundo, provavelmente nos anos 90. Idiomas de nível superior atraem uma gama maior de pessoas. Isso permite que um maior suprimento de programadores construa a infraestrutura necessária em nosso mundo. Países em desenvolvimento como China e Índia se beneficiam muito de linguagens como Java. Esses países desenvolverão rapidamente sua infraestrutura de TI e as pessoas se tornarão mais interconectadas. Portanto, meu argumento é que as linguagens de alto nível são populares não porque produzem código superior, mas porque ajudam a atender à demanda nos mercados do mundo.


+1 para coisa de caixa preta. Sim, estamos usando caixas pretas, e não há como espiar nelas (muito fácil). Como o C # foreach realmente funciona? Quem sabe. A Microsoft disse que é perfeito. Então deve ser.
ern0

Além disso, não se esqueça que, com uma 'linguagem de alto nível', existem muitas outras coisas importantes no mundo real. C vem com as bibliotecas padrão (matemática, processamento de strings, E / S, etc.) e, em seguida, os pesos pesados ​​como Java vêm com vários outros pacotes e bibliotecas para conectividade, processamento de imagens, processamento de dados, desenvolvimento da Web etc. É uma pergunta de usar seu tempo para se concentrar em obter 1 tarefa detalhada com alto desempenho em uma plataforma (usando, portanto, montagem) versus gastar o mesmo tempo em obter uma tarefa muito maior em várias plataformas com o mínimo de erros.
JBX

1

Estou aprendendo montagem na comp org agora e, embora seja interessante, também é muito ineficiente escrever. Você precisa manter muitos detalhes em sua mente para fazer as coisas funcionarem, e também é mais lento escrever as mesmas coisas . Por exemplo, uma simples linha 6 para loop em C ++ pode ser igual a 18 linhas ou mais de montagem.

Pessoalmente, é muito divertido aprender como as coisas funcionam no nível do hardware, e isso me dá uma maior apreciação de como a computação funciona.


1

O que C tem sobre um bom montador de macros é o idioma C. Verificação de tipo. Construções de loop. Gerenciamento de pilha automático. (Quase) gerenciamento automático de variáveis. Técnicas de memória dinâmica em assembler são uma enorme dor no traseiro. Fazer uma lista vinculada corretamente é assustador, em comparação com C ou, melhor ainda, com a lista foo.insert (). E depuração - bem, não há contestação sobre o que é mais fácil de depurar. HLLs ganham as mãos lá em baixo.

Codifiquei quase metade da minha carreira em montador, o que torna muito fácil para mim pensar em montador. isso me ajuda a ver o que o compilador C está fazendo, o que novamente me ajuda a escrever o código que o compilador C pode manipular com eficiência. Uma rotina bem pensada, escrita em C, pode ser escrita para produzir exatamente o que você deseja no assembler com um pouco de trabalho - e é portátil! Eu já tive que reescrever algumas rotinas ASM mais antigas de volta ao C por razões de plataforma cruzada e isso não é divertido.

Não, continuarei com C e lidarei com a ligeira desaceleração ocasional no desempenho em relação ao tempo de produtividade que ganho com a HLL.


1

Só posso responder por que, pessoalmente, não escrevo programas em assembléias com mais frequência, e o principal motivo é que é mais entediante . Além disso, acho que é mais fácil entender as coisas sutilmente erradas sem perceber imediatamente. Por exemplo, você pode mudar a maneira como usa um registro em uma rotina, mas esquece de mudar isso em um só lugar. Vai ficar bem e você pode não perceber até muito mais tarde.

Dito isto, acho que ainda existem usos válidos para montagem. Por exemplo, eu tenho várias rotinas de montagem bastante otimizadas para processar grandes quantidades de dados, usando o SIMD e seguindo a abordagem paranóica "cada bit é sagrado" [citação V.Stob]. (Mas observe que as implementações ingênuas de assemblies geralmente são muito piores do que o compilador geraria para você.)


1

C é um montador de macro! E é o melhor!

Ele pode fazer quase tudo o que a montagem pode, pode ser portátil e, na maioria dos casos raros, em que não pode fazer algo, você ainda pode usar o código de montagem incorporado. Isso deixa apenas uma pequena fração dos programas que você absolutamente precisa escrever na montagem e nada além de montagem.

E as abstrações de nível mais alto e a portabilidade tornam mais valioso para a maioria das pessoas escrever software de sistema em C. E embora você possa não precisar de portabilidade agora, se você investir muito tempo e dinheiro escrevendo algum programa, talvez não queira se limitar no que você poderá usá-lo no futuro.


1

As pessoas parecem esquecer que também há outra direção.

Por que você está escrevendo no Assembler? Por que não escrever o programa em um idioma verdadeiramente de baixo nível?

Ao invés de

mov eax, 0x123
add eax, 0x456
push eax
call printInt

você poderia muito bem escrever

B823010000
0556040000
50 
FF15.....

Isso tem tantas vantagens, você sabe o tamanho exato do seu programa, pode reutilizar o valor das instruções como entrada para outras instruções e nem precisa de um montador para escrevê-las, pode usar qualquer editor de texto ...

E a razão pela qual você ainda prefere o Assembler sobre isso, é a razão pela qual outras pessoas preferem C ...


0

Porque é sempre assim: o tempo passa e as coisas boas também passam :(

Mas quando você escreve código ASM, é um sentimento totalmente diferente do que quando você codifica langs de alto nível, embora saiba que é muito menos produtivo. É como se você fosse um pintor: você é livre para desenhar o que quiser da maneira que quiser, sem absolutamente nenhuma restrição (bem, apenas pelos recursos da CPU) ... É por isso que eu adoro. É uma pena que essa linguagem desapareça. Mas enquanto alguém ainda se lembra e codifica, nunca morrerá!


Verdade. Por outro lado, há a humilhação que você experimenta quando o caixa e o supermercado se recusam a descontar seu cheque, dizendo com desdém: "Ah, você programa em um idioma de BAIXO NÍVEL".
Jay

0

$$$

Uma empresa contrata um desenvolvedor para ajudar a transformar o código em $$$. Quanto mais rápido o código útil puder ser produzido, mais rápido a empresa poderá transformar esse código em $$$.

Linguagens de nível superior geralmente são melhores para produzir volumes maiores de código útil. Isso não quer dizer que a assembléia não tenha seu lugar, pois há momentos e lugares em que nada mais fará.


0

A vantagem das HLLs é ainda maior quando você compara o assembly a uma linguagem de nível superior ao C, por exemplo, Java, Python ou Ruby. Por exemplo, esses idiomas têm coleta de lixo: não há necessidade de se preocupar quando liberar um pedaço de memória e não há vazamentos ou erros de memória devido à liberação muito cedo.


0

Como outros mencionados anteriormente, a razão para qualquer ferramenta existir é a eficiência com que ela pode funcionar. Como os HLLs podem realizar os mesmos trabalhos que muitas linhas de código asm, acho que é natural que o assembly seja substituído por outros idiomas. E para as brincadeiras próximas ao hardware - há montagem em linha em C e outras variantes conforme o idioma. O Dr. Paul Carter diz na Linguagem de Montagem do PC

"... uma melhor compreensão de como os computadores realmente funcionam em um nível mais baixo do que em linguagens de programação como Pascal. Ao obter uma compreensão mais profunda de como os computadores funcionam, o leitor geralmente pode ser muito mais produtivo desenvolvendo software em linguagens de nível superior, como C e C ++. Aprender a programar em linguagem assembly é uma excelente maneira de atingir esse objetivo ".

Temos introdução à montagem nos meus cursos da faculdade. Isso ajudará a limpar conceitos. No entanto, duvido que algum de nós escreva 90% do código na montagem. Quão relevante é hoje o conhecimento aprofundado da montagem?


-2

Ao folhear essas respostas, aposto que 9/10 dos respondentes nunca trabalharam com montagem.

Esta é uma pergunta antiga que surge de vez em quando e você obtém as mesmas respostas, principalmente desinformadas. Se não fosse pela portabilidade, eu ainda faria tudo em conjunto. Mesmo assim, eu codifico em C quase como fiz na montagem.


1
+1 mencionando pessoas sem nenhuma experiência em ASM e outro +1 em "codificação em C como ASM". Quando estou escrevendo aplicativos C ++ (sim, CPP, não C) para incorporados, estou codificando como se fosse asm, por exemplo, sem usar nenhum novo / malloc ().
ern0

Então você usa várias coisas como char buf [MAX_PATH], que cai quando alguém tem dados do tamanho MAX_PATH + n? ;)
paulm

1
@ paulm - Você quer dizer como C?
19413 Rob

1
Espero que os autores de montadores não evitem o uso de malloc (). Sim, no incorporado, você tem restrição de memória. Mas faça isso no Unix ou em outro desktop (ou mesmo na maioria dos sistemas operacionais móveis) e você estará restringindo desnecessariamente a si e a seus usuários. Além disso: quanto menos LOC você escreve, menor a chance de erro, o que significa que o código de nível superior provavelmente terá menos erros que o menor.
uliwitness

1
Só olhei porque eu estava desconfiado e, sim, com certeza posso dizer que os redditores e os HNers estão aqui.
19413 Rob
Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.