Introducción

Introducción

Después de toda esa teoría y conversación, comencemos construyendo el código escrito a través de las últimas nueve partes de esta serie. Esta parte de nuestra serie podría servirle incluso si aprendió C en otro lugar, o si cree que su lado práctico del desarrollo C necesita un poco de fuerza. Veremos cómo instalar el software necesario, lo que dice el software y, lo más importante, cómo transformar su código en ceros y otros. Antes de comenzar, es posible que desee echar un vistazo a nuestros artículos más recientes sobre cómo personalizar su entorno de desarrollo:

  • Introducción al editor VIM
  • Introducción a los emacs
  • Personalización de VIM para el desarrollo
  • Personalización de emacs para el desarrollo

Construyendo su programa

Recuerda la primera parte de nuestra serie de desarrollo C? Allí describimos el proceso básico que tiene lugar cuando compila su programa. Pero a menos que trabaje en el desarrollo del compilador o en algunas otras cosas realmente de bajo nivel, no le interesará cuántas instrucciones de JMP tiene el archivo de ensamblador generado, si alguna. Solo querrá saber cómo ser lo más eficiente posible. De esto se trata esta parte del artículo, pero solo estamos rascando la superficie, debido a la extensividad del tema. Pero un programador de C de nivel de entrada sabrá después de leer esto todo lo necesario para funcionar de manera eficiente.

Las herramientas

Además de saber exactamente lo que desea lograr, debe estar familiarizado con las herramientas para lograr lo que desea. Y hay mucho más en las herramientas de desarrollo de Linux que el GCC, aunque solo sería suficiente para compilar programas, pero sería una tarea tediosa a medida que aumenta el tamaño de su proyecto. Es por eso que se han creado otros instrumentos, y veremos aquí lo que son y cómo obtenerlos. Ya lo sugerí que leíste el manual de GCC, así que solo supondré que lo hiciste.

hacer

Imagine que tiene un proyecto de múltiples archivos, con muchos archivos de origen, las obras. Ahora imagine que tiene que modificar un archivo (algo menor) y agregar algún código a otro archivo de origen. Sería doloroso reconstruir todo el proyecto debido a eso. He aquí por qué se creó la marca: según las marcas de tiempo de archivo, detecta qué archivos deben ser reconstruidos para llegar a los resultados deseados (ejecutables, archivos de objetos ...), nombrados objetivos. Si el concepto todavía se ve turbio, no se preocupe: después de explicar un makfile y los conceptos generales, todo parecerá más fácil, aunque los conceptos avanzados pueden inducir el dolor de cabeza.

Make tiene este nombre exacto en todas las plataformas en las que trabajé, que son bastante distribuciones de Linux, *BSD y Solaris. Entonces, independientemente del administrador de paquetes que esté utilizando (si lo hay), ya sea apt*, yum, zypper, pacman o emerge, solo use el comando de instalación respectivo y haga como argumento y eso es todo. Otro enfoque sería, en distribuciones con los administradores de paquetes que tienen soporte de grupo, para instalar todo el grupo/patrón de desarrollo C/C ++. Hablando de idiomas, quería desacreditar un mito aquí, que dice Makefiles (el conjunto de reglas que realizan debe seguir para alcanzar el objetivo) solo es utilizado por los desarrolladores de C/C ++. Equivocado. Cualquier idioma con un compilador/intérprete capaz de invocarse desde el shell puede usar las instalaciones de make. De hecho, cualquier proyecto que necesite actualización basada en la dependencia puede usar hacer. Entonces, una definición actualizada de un archivo de make sería Un archivo que describe las relaciones y dependencias entre los archivos de un proyecto, con el propósito de definir lo que debe actualizarse/recompilar en caso de que cambie uno o más archivos en la cadena de dependencia. Comprender cómo hacer obras es esencial para cualquier desarrollador de C que trabaje bajo Linux o Unix: sí, las ofertas de unix comercial también hacen, aunque probablemente alguna versión que difiere de GNU, que es nuestro tema. "Versión diferente" significa más que números, significa que un BSD Makefile es incompatible con un GNU Makefile. Así que asegúrese de haber instalado GNU si no está en una caja de Linux.

En la primera parte de este artículo, y algunos posteriores, usamos y hablamos sobre partes de Yest, un pequeño programa que muestra la fecha de ayer por defecto, pero hace muchas cosas ingeniosas/relacionadas con el tiempo. Después de trabajar con el autor, Kimball Hawkins, nació un pequeño Makefile, que es con lo que trabajaremos.

Primero, veamos algunos conceptos básicos sobre The MakFile. El nombre canónico debe ser GnumakeFile, pero si no existe dicho archivo, busca nombres como Makefile y Makefile, en ese orden, o eso dice la página manual. Por cierto, por supuesto que deberías leerlo y leerlo nuevamente, luego leerlo un poco más. No es tan grande como el de GCC y puedes aprender muchos trucos útiles que serán útiles más tarde. Sin embargo, el nombre más utilizado en la práctica es MakeFile, y nunca he visto ninguna fuente con un archivo llamado GnumakeFile, es decir la verdad. Si, por varias razones, necesita especificar otro nombre, use Make's -F, como este:

 $ make -f mymakefile

Aquí está el File de Yest, que puede usar para compilar e instalar dicho programa, porque aún no está cargado de SourceForge. Aunque es solo un programa de dos archivos, la fuente y la página de manejo, ya se volverá a ser útil.

# MakeFile para compilar e instalar el yest Uname: = $ (shell uname -s) cc = gcc cflags = -wall cp = cp rm = rm rmflags = -f gzip = gzip versión = yest -2.7.0.5 Yest: ifeq ($ (Uname), Sunos) $ (CC) -Dsunos $ (CFLAGS) -O Yest $ (Versión).C demás $ (CC) $ (CFLAGS) -O Yest $ (Versión).C terminara si Todos: Instalación de Yest Maninstall Instalar: Maninstall $ (CP) Yest/USR/Local/Bin Maninstall: $ (CP) $ (Versión).Man1 antiest.1 $ (GZIP) Yest.1 $ (CP) Yest.1.GZ/USR/Share/Man/Man1/Clean: $ (RM) $ (RMFlags) Yest.1.GZ Deinstall: $ (RM) $ (RMFlags)/usr/local/bin/yest/usr/share/man/man1/yest1.GZ 

Si observa cuidadosamente el código anterior, ya observará y aprenderá varias cosas. Los comentarios comienzan con los hash, y dado que Makefiles puede volverse bastante críptico, es mejor que comente sus Makefiles. En segundo lugar, puede declarar sus propias variables, y luego puede hacer un buen uso de ellas. Luego viene la parte esencial: objetivos. Esas palabras seguidas por un colon se llaman objetivos, y uno las usa como hacer [-f name de makfile] Target_name. Si alguna vez instaló desde la fuente, probablemente escribió 'hacer instalar'. Bueno, 'Instalar' es uno de los objetivos en el archivo Makefile, y otros objetivos de uso común incluyen 'Limpio', 'Deinstall' o 'All'. Otra cosa más importante es que el primer objetivo siempre se ejecuta de forma predeterminada si no se especifica ningún objetivo. En nuestro caso, si escribiera 'hacer', ese habría sido el equivalente de 'hacer yest', como puede ver, lo que significa una compilación condicional (si estamos en Solaris/Sunos necesitamos una bandera de GCC adicional) y la creación de un ejecutable llamado 'yest'. Los objetivos como 'All' en nuestro ejemplo no están haciendo nada por sí mismos, solo dígale a hacer que dependan de otros archivos/objetivos para estar al día. Mira la sintaxis, a saber, cosas como espacios y pestañas, como hacer es bastante pretencioso sobre cosas como esta.

Aquí hay un breve makefile para un proyecto que tiene dos archivos de origen. Los nombres de archivo son src1.C y Src2.c y el nombre del ejecutable debe ser ejecutado. Simple, correcto?

EXEC: SRC1.O SRC2.o GCC -O EXEC SRC1.O SRC2.O SRC1.O: SRC1.C GCC -C SRC1.C SRC2.O: SRC2.C GCC -C SRC2.C

El único objetivo prácticamente utilizado, que también es el valor predeterminado, es 'ejecutivo'. Él depende en src1.O y Src2.o, que, a su vez, depende de los respectivos .Archivos C. Entonces, si modifica, digamos, src2.C, todo lo que tienes que hacer es ejecutar hacer de nuevo, lo que notará que src2.C es más nuevo que el resto y procede en consecuencia. Hay mucho más que hacer que cubierto aquí, pero no hay más espacio. Como siempre, se recomienda un autoestudio, pero si solo necesita funcionalidad básica, lo anterior le servirá bien.

El script de configuración

Por lo general, no es solo 'hacer && hacer instalación', porque antes de que exista esos dos existe un paso que genera el archivo de making, especialmente útil cuando se trata de proyectos más grandes. Básicamente, dicho script verifica que tiene los componentes necesarios para la compilación instalada, pero también toma varios argumentos que lo ayudan a cambiar el destino de los archivos instalados y otras opciones (e.gramo. Soporte QT4 o GTK3, soporte de archivo PDF o CBR, etc.). Veamos a corto plazo de qué se tratan esos scripts de configuración.

No suele escribir el script de configuración a mano. Utiliza AutoConf y Automake para esto. Como implican los nombres, lo que hacen es generar scripts y makingfiles, respectivamente. Por ejemplo, en nuestro ejemplo anterior con el programa Yest, en realidad podríamos usar un script de configuración que detecte el entorno del sistema operativo y cambie algunas variables, y después de todo eso genera un archivo maken. Hemos visto que el yest makefile verifica si estamos ejecutando en Sunos, y si lo estamos, agrega una bandera del compilador. Lo expandiría para verificar si estamos trabajando en un sistema BSD y, de ser así, invoca Gmake (GNU Make) en lugar de la marca nativa que es, como dijimos, incompatible con GNU Makefiles. Ambas cosas se hacen usando Autoconf: escribimos un pequeño configurar.en Archivo en el que le dicemos a AutoConf qué necesitamos verificar, y generalmente querrá verificar más que la plataforma del sistema operativo. Tal vez el usuario no tenga un compilador instalado, ni una marca, ni bibliotecas de desarrollo que sean importantes en tiempo de compilación, etc. Por ejemplo, una línea que verificaría la existencia del tiempo.H en las ubicaciones de encabezado estándar del sistema se verían así:

 Ac_check_headers (tiempo.h)

Le recomendamos que comience con una aplicación no demasiado grande, verifique el contenido de Tarball de origen y lea la configuración.en y/o configurar.archivos de CA. Para tarballs que los tienen, makfile.AM también es una buena forma de ver cómo se ve un archivo de automago. Hay algunos buenos libros sobre el asunto, y uno de ellos es la "gestión de proyectos con GNU" de Robert Mecklenburg.

Consejos de GCC y banderas de línea de comandos habituales

Sé que el manual de GCC es grande y sé que muchos de ustedes ni siquiera lo han leído. Me enorgullece leerlo todo (todo lo que pertenece al hardware de IA de todos modos) y debo confesar que me duele la cabeza después. Por otra parte, hay algunas opciones que debes saber, a pesar de que aprenderás más a medida que avanza.

Ya se ha encontrado con la bandera -o, que le dice a GCC qué saliente resultante y -c, eso le dice a GCC que no ejecute el enlazador, produciendo así lo que el ensamblador escupe, a saber, los archivos de objetos. Hablando de eso, hay opciones que controlan las etapas en las que el CCG debe detener la ejecución. Entonces, para detenerse antes de la etapa de ensamblaje, después de la compilación per se, use -s. En la misma línea, -e debe usarse si desea detener el GCC justo después del preprocesamiento.

Es una buena práctica seguir un estándar, si no es por uniformidad, pero para buenos hábitos de programación. Si está en el período formativo como desarrollador C, elija un estándar (ver más abajo) y sígalo. El lenguaje C se estandarizó primero después de que Kernighan y Ritchie (RIP) publicaron "El lenguaje de programación C" en 1978. Era un estándar no formal, pero en breve se llamó K&R y respetado. Pero ahora es obsoleto y no se recomienda. Más tarde, en los años 80 y 90, ANSI e ISO desarrollaron un estándar oficial, C89, seguido de C99 y C11. GCC también admite otros estándares, como GNUxx, donde xx puede ser 89 o 99, como ejemplos. Consulte el manual para obtener más detalles, y la opción es '-std =', "imponida" por '-pedantic'.

Las opciones relacionadas con las advertencias comienzan con "-W", como '-wall' (le dice a GCC que habilite todos los errores, aunque no todos están habilitados) o '-werror' (trate las advertencias como errores, siempre recomendadas). Puede aprobar argumentos suplementarios a los programas que ayudan con los pasos intermediarios, como el preprocesador, el ensamblador o el enlazador. Por ejemplo, aquí le mostramos cómo pasar una opción al enlazador:

 $ GCC [otras opciones ...] -wl,opción [Otro conjunto de opciones ...]

De manera similar e intuitiva, puede usar 'WA', para el ensamblador y 'wp', para el preprocesador. Tome nota de la coma y el espacio en blanco que le dice al compilador que la parte del preprocesador/ensamblador/enlazador ha terminado. Otras familias útiles de opciones incluyen '-g' y amigos para la depuración, '-o' y amigos para la optimización o '-idirectorio' - Sin espacio en blanco - para agregar una ubicación que contiene encabezado.

Conclusión

Le recomiendo que se tome su tiempo para leer este artículo, jugar con los ejemplos, luego escribir el suyo, aumentando la complejidad a medida que avanza.

Esto es lo que puede esperar a continuación:

  • I. C Desarrollo en Linux - Introducción
  • II. Comparación entre C y otros lenguajes de programación
  • III. Tipos, operadores, variables
  • IV. Control de flujo
  • V. Funciones
  • VI. Punteros y matrices
  • VII. Estructuras
  • VIII. E/S básica
  • Ix. Estilo de codificación y recomendaciones
  • X. Construyendo un programa
  • Xi. Embalaje para Debian y Fedora
  • Xii. Obtener un paquete en los repositorios oficiales de Debian

Tutoriales de Linux relacionados:

  • Cosas para instalar en Ubuntu 20.04
  • Una introducción a la automatización, herramientas y técnicas de Linux
  • Cosas que hacer después de instalar Ubuntu 20.04 fossa focal Linux
  • Instale Arch Linux en VMware Workstation
  • Tutorial de depuración de GDB para principiantes
  • Bash Regex avanzado con ejemplos
  • Sistema colgado de Linux? Cómo escapar a la línea de comando y ..
  • Manipulación de Big Data para la diversión y las ganancias Parte 1
  • Expresiones regulares de Python con ejemplos
  • Bash Loops con ejemplos