¿Recursos para aprender a programar en código máquina? [cerrado]


24

Soy un estudiante, recién empezado a programar y adorarlo, desde Java a C ++ y hasta C. Me moví hacia atrás a los barebones y pensé en ir más abajo a la Asamblea.

Pero, para mi sorpresa, mucha gente dijo que no es tan rápido como C y que no sirve de nada. Sugirieron aprender ya sea cómo programar un núcleo o escribir un compilador de C. Mi sueño es aprender a programar en binario (código de máquina) o tal vez programar bare metal (programar microcontrolador físicamente) o escribir biografías o cargadores de arranque o algo por el estilo.

Lo único que escuché después de tanta investigación es que un editor hexadecimal es lo más parecido al lenguaje de máquina que pude encontrar en esta época. ¿Hay otras cosas que desconozco? ¿Hay algún recurso para aprender a programar en código máquina? Preferiblemente en un microcontrolador / microprocesador de 8 bits.

Esta pregunta es similar a la mía, pero primero me interesa el aprendizaje práctico y luego comprender la teoría.


2
¿Cuál es exactamente el problema aquí? Si está preguntando si es posible codificar en código de máquina, entonces la respuesta es probablemente "sí". Si está solicitando tutoriales, entonces a) deje claro que esa es su pregunta, pero b) no es una pregunta constructiva.
ChrisF

66
¿No es C suficiente bere metal?
Tom Squires

66
Yo program bare metalcada vez que patear el cuadro de servidor. Funciona de maravillas!
yannis

77
¿Alguna vez consideró ir aún más abajo? Hackea
SK-logic

3
@ SK-logic, sí, la programación del código de máquina sería insufrible después de aproximadamente 1 hora. Tienes razón, una idea mejor y más productiva es llegar a la implementación de la CPU. También hay versiones virtuales del 6502 ( visual6502.org ), así como personas que tienen o aspiran a construir CPU utilizando lógica discreta moderna ( bradrodriguez.com/papers/piscedu2.htm )
Angelo

Respuestas:


27

Las personas no programan en código máquina (a menos que sean masoquistas). Utilizan (o desarrollan) herramientas para generar código de máquina (compilador o ensamblador, incluidas herramientas de desarrollo cruzado), o quizás bibliotecas que generan código de máquina (LLVM, libjit, GNU lightning, ...). Por lo tanto, los recursos sobre generación de código de máquina, compilación, optimizadores y microarquitecturas también son relevantes.

Y muy a menudo, un buen compilador optimizador genera un mejor código de máquina que el que podría hacer. Probablemente no podrá escribir un código de ensamblador de 200 líneas mejor que un buen optimizador.

Si desea comprender el código de la máquina, primero aprenda el ensamblaje. Está muy cerca del código de máquina. Úselo sabiamente, solo para cosas que no puede codificar en C (o en algún lenguaje de nivel superior, como Ocaml, Haskell, Common Lisp, Scala). Una buena manera es a menudo usar asminstrucciones (especialmente la función de ensamblaje extendido GCC ) dentro de una función C. Leer el código de ensamblaje (generado por gcc -S -O2 -fverbose-asm) también puede ser útil.

La Guía de ensamblaje de Linux es algo bueno para leer.

La arquitectura del conjunto de instrucciones del procesador actual (es decir, el conjunto de instrucciones que entiende el chip) es bastante compleja. Los más comunes son x86 (una PC típica en modo de 32 bits), X86-64 (una PC de escritorio en modo de 64 bits), ARM (teléfonos inteligentes, ...), PowerPC , etc. Todos son bastante complejos (por razones históricas y económicas razones). Quizás aprender primero un conjunto de instrucciones hipotéticas como, por ejemplo, el MMIX de Knuth es más simple.


8
"La gente no programa en C (...). Usan lenguajes modernos, tal vez con el backend de C"
Abyx

Definitivamente estoy de acuerdo. Y mi proyecto de trabajo actual (MELT, ver gcc-melt.org ) es un DSL traducido a C.
Basile Starynkevitch


66
¿Qué pasa con aquellos que quieren crear y ensamblar? Hay razones para aprender el código de la máquina, aunque no son tan comunes.
Jetti

Diría que está aprendiendo una arquitectura de conjunto de instrucciones (usando la mnemotecnia de ensamblaje). Raramente se aprende explícitamente la codificación exacta de la instrucción (por ejemplo, que NOP es 0x90). Es necesario que lo sepa al escribir un ensamblador o un generador de código de máquina. (Del mismo modo, rara vez necesita aprender de memoria la codificación UTF8 de Unicode).
Basile Starynkevitch

13

Como se indicó anteriormente, aprenda la Asamblea .

Un lenguaje ensamblador es un lenguaje de programación de bajo nivel para computadoras, microprocesadores, microcontroladores y otros dispositivos programables. Implementa una representación simbólica de los códigos de máquina y otras constantes necesarias para programar una arquitectura de CPU dada.

Entonces Asamblea es a symbolic representation of machine code.

Ahora puede preguntar "Ok, entonces, ¿cómo aprendo todo eso?" Estoy tan contento de que hayas preguntado:

  1. Comprende lo que es. Es de muy bajo nivel y le dará una comprensión muy profunda de una computadora. Es posible que desee comenzar con Wikipedia y luego leer este breve pasaje .
  2. ¡Aprenderlo! Las mejores lecturas son probablemente El arte del lenguaje ensamblador y el lenguaje ensamblador paso a paso: programación con Linux
  3. ¡Obtén codificación!

Estaba leyendo este otro hilo y creo que me topé con esto: programmers.stackexchange.com/a/82573/43388 ¿ algo de esa naturaleza podría encontrar un tutorial? Pero, primero necesito aprender el ensamblaje para facilitar la transición.
AceofSpades

1
Gracias, supongo que necesito aprender a ensamblar a pedido popular. +1
AceofSpades

8

Le sugiero que reconsidere su objetivo y he aquí por qué:

Aprendí por primera vez el lenguaje ensamblador 6502 en el microordenador BBC (Modelo B, 32K). Tenía una implementación BASIC increíble que incluía un ensamblador de macros. Los teníamos en la escuela, así que escribí todo tipo de programas traviesos que harían cosas como la manipulación directa del búfer de pantalla para hacer que Lemming caminara por cada pantalla, alrededor de la sala (estaban conectados en red) si las máquinas no se hubieran utilizado durante 10 minutos . Resultó en risas entre mis amigos de Year 7.

Cuando obtuve un Commodore 64 en casa, aprendí que tenía una CPU 6510 que también ejecutaba el lenguaje ensamblador 6502 pero con algunos extras interesantes. Tuve que comprar un ensamblador (vino en un cartucho ) e invocar los programas a través de BASIC. Con grandes visiones de escribir un juego superventas, finalmente logré crear varias demostraciones que registraban el hardware de la pantalla de video en interrupciones para hacer interesantes efectos de barra de colores que animaban a la música de chip funky. Impresionante, pero no tan útil.

Luego obtuve un Acorn Archimedes A310 que tenía una CPU ARM2, así que utilicé la misma impresionante implementación BÁSICA con ensamblador de macros incorporado que el BBC Micro (mismo patrimonio). Logré armar un par de juegos para los que un amigo artístico proporcionó gráficos, además de algunas demostraciones trippy basadas en sinusoides. Ambos fueron un trabajo difícil de programar y un código incorrecto podría derribar la máquina (disparar accidentalmente el registro de reinicio de hardware, etc.), perdiendo todo si no hubiera guardado (¡en disquete!).

En la Universidad me presentaron C ++ y, por lo tanto, C. pude usarlo para programar Sun / Solaris y algunas otras computadoras mainframe grandes. No tengo ni idea de qué arquitecturas de CPU ejecutaban estas máquinas: nunca tuve que usar ensamblador o leer el código de la máquina, ya que las herramientas C ++ me dieron la potencia que necesitaba para producir aplicaciones profesionales.

Después de Uni, trabajé en Windows y en varios sabores de Unix. C y C ++ funcionaron en todas estas máquinas y, finalmente, Java también.

Luego trabajé en Windows y Dreamcast usando C ++ con DirectX con una cadena de herramientas integral para la depuración.

Luego tomé un trabajo trabajando con chipsets basados ​​en ARM para televisores inteligentes (en 2000). Aunque mi experiencia con ARM2 puede haber sido relevante aquí, el trabajo se basó en C. Descubrí que todo lo relacionado con el hardware que había hecho en Arquímedes también se podía hacer en C usando operaciones sencillas de giro de bits. Parte de mi función era migrar la base de código a Windows, Playstation 2, Linux, otros conjuntos de chips de TV y móviles. Todas estas plataformas estaban disponibles con un compilador de C (a menudo GCC) y algún nivel de API para escribir en la máquina subyacente: el mundo incrustado rara vez es un O / S del núcleo. Nunca necesité saber el código de máquina completo para ninguna plataforma en particular más allá de escribir un cargador de arranque y un mini BIOS, los cuales saltaron al código C en la primera oportunidad disponible (después de configurar vectores de trampa,

El siguiente trabajo fue trabajar con C ++, C # y JavaScript en Windows. Sin código de máquina

El trabajo actual es trabajar con C ++, JavaScript, Python, LUA, HTML y otros lenguajes en varias plataformas. No tengo idea de qué código de máquina ejecutan estas plataformas, ni necesito saberlo: el compilador traduce nuestro código a lo que sea necesario. Si falla, detecto el error en un depurador o mediante diagnósticos de tiempo de ejecución (excepciones, señales, etc.).

Por diversión, desarrollo aplicaciones de iOS en el poco tiempo libre que tengo en casa. Utiliza Objective-C y una API que funciona en múltiples conjuntos de chips. Aparentemente están basados ​​en ARM, pero nunca he visto ningún código de máquina en mi desarrollo.

Si bien es un ejercicio fascinante para aprender el lenguaje ensamblador, ahora hay herramientas e idiomas de un nivel mucho más alto que le permiten ser un orden de magnitud (o dos) más productivo.

La cantidad de oportunidades de trabajo disponibles para un sorprendente programador de lenguaje ensamblador / código de máquina es minúscula en comparación con algo como JavaScript, Java, C #, C ++ u ObjC.

Te aconsejo que hagas de este un pasatiempo / interés secundario en lugar de un objetivo principal.


66
Es un hobby Me interesa cómo funcionan las cosas y, si es posible, aprender a manipularlas a un nivel muy básico. +1
AceofSpades

6

¿Mi sugerencia? Aprenda MIPS y aprenda a construir un procesador MIPS (simple). En realidad es más fácil de lo que parece.

La ventaja de MIPS sobre algunas de las otras arquitecturas es la simplicidad. No quedará atrapado en una tonelada de pequeños detalles, pero aún así aprenderá todas las grandes ideas que necesita para escribir código en otras arquitecturas.

Casualmente, este fue el proyecto final para mi (tercera) clase de introducción de CS. Si lo desea, puede leer la tarea y navegar a través de las conferencias como videos o diapositivas .

Entre otras cosas, nos hicimos cubierta de cómo el código MIPS se convirtió en binario; Incluso tuvimos que decodificar un código de máquina (muy simple) en los exámenes.

Incluso si no desea cubrir todo, la mayoría de las conferencias fueron impartidas por uno de los profesores favoritos de los estudiantes y son divertidas de ver por sí mismas.


Muchas gracias por los enlaces y explicando desde dónde debería comenzar. +1
AceofSpades

6

Soy un estudiante, recién empezado a programar y adorarlo, desde Java a C ++ y hasta C. Me moví hacia atrás a los barebones y pensé en ir más abajo a la Asamblea.

Excelente camino a seguir. Mi salto (¿caer?) De C a Asamblea y más abajo fue un curso universitario de Organización y Diseño de Computadoras , basado en el libro del mismo nombre.

Recomiendo encarecidamente este libro para los primeros capítulos sobre el ensamblaje básico de MIPS, hasta la arquitectura de canalización y memoria. Aún mejor sería tomar un curso sobre el mismo tema, o encontrar algunas conferencias en línea.

También vea el simulador MARS MIPS para ensuciarse las manos al escribir.


4

Si desea comprender cómo funciona la máquina por completo, ¿por qué no va al nivel más bajo posible y avanza hasta donde está (por ejemplo, C, C ++)?

Con eso quiero decir: ¿por qué no construyes tu propio sumador de 4 bits con transistores en un circuito (solo busca en Google si estás buscando instrucciones / tutoriales)?

Después de eso, construya una computadora pequeña con algo de RAM, y luego comience a aprender Assembly y escriba un programa o dos con ella.


Si el afiche original construye una computadora desde cero, tendrá que definir (no solo aprender) su propio ensamblaje.
Basile Starynkevitch

@daniels Entiendo el razonamiento al aprender a sumar de bits, que es cierto bajo nivel. +1
AceofSpades

Una alternativa a la construcción de una computadora desde cero podría ser aprender un procesador antiguo (y su lenguaje ensamblador) como el Z80 o 6502 que todavía es lo suficientemente simple como para ser entendido. Supongo que incluso hay emuladores con los que puedes jugar.
Giorgio

@AceofSpades Una excelente manera de construir fácilmente CPU y componentes de CPU (por ejemplo, un sumador) es con redstone en Minecraft, lo recomendaría. Comencé a trabajar en algunas máquinas simples en Minecraft, y ha mejorado mucho mi comprensión de la teoría y la lógica detrás de las computadoras.
Aaron

1

Tengo un conjunto de instrucciones que se hizo para esto, un simulador y algunos tutoriales sobre los conceptos básicos de una instrucción o concepto por lección. Simplemente escriba el programa, ejecútelo y luego aprenda lo que hace, pase a la siguiente lección.

http://www.github.com/dwelch67/lsasim

También tengo simuladores para algunos conjuntos de instrucciones convencionales. Cualquiera o todos los cuales son buenos para usar para aprender asm (si realmente siente que tiene que aprender x86, aprenda al final y use un simulador como el que he bifurcado, primero 8088/86 y luego avance). Aprender contra un simulador tiene ventajas y desventajas, un profesional importante, especialmente al comenzar, es que no se cuelga nada y tiene una gran visibilidad. Saltar de cabeza en una plataforma integrada, un microcontrolador, etc. para aprender un nuevo conjunto de instrucciones, tiene que superar los obstáculos de no poder ver lo que está sucediendo, lo que lleva a una larga lista de formas de fallar ...


1

Code by Charles Petzold es una muy buena introducción al tema y describe el proceso de construcción de una computadora que incluye cómo construir sumadores, contadores y matrices RAM e introduce el código de máquina y el lenguaje ensamblador y su relación con los lenguajes de nivel superior. También es una gran lectura sobre la historia de la informática.

Y acabo de leer esta pregunta en electronics.stackexchange que también podría ser útil


Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.