From cca2c345f9b16b88e1fc4e9ea598cf2f7ed8653a Mon Sep 17 00:00:00 2001 From: Carlos Maniero Date: Mon, 24 Apr 2023 22:33:52 -0300 Subject: cli: Create a CLI to generate an executable from pipa code. This commit introduces a full-featured CLI that allows you to compile a file, set the gas and linker path, and define the executable output. Signed-off-by: Carlos Maniero Reviewed-by: Johnny Richard Link: https://lists.sr.ht/~johnnyrichard/pipalang-devel/patches/40642 --- pipa | 160 ++++++++++++++++++++++++++++++++++++++++++++++++ test/integration_test.c | 7 +-- 2 files changed, 162 insertions(+), 5 deletions(-) create mode 100755 pipa diff --git a/pipa b/pipa new file mode 100755 index 0000000..d197ade --- /dev/null +++ b/pipa @@ -0,0 +1,160 @@ +#!/bin/sh +# Copyright (C) 2023 Carlos Maniero +# +# This program is free software: you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation, either version 3 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see . + +AS="as" +LD="ld" +SCRIPT_DIR=$(dirname "$0") +PIPAC_PATH="$SCRIPT_DIR/pipac" +SILENT=0 + +ERROR_PREFIX="[ERROR]" +WELCOME_MESSAGE="Welcome to Pipa Compiler" +PIPA_LOGO="" +COMPILING_MESSAGE="Compiling:" +BUILT_MESSAGE="Built:" +COMPILATION_ERROR_MESSAGE="Compilation error:" + +if [ -t 1 ] && [ "$(tput colors)" -ge 8 ]; then + ERROR_PREFIX="\033[31m$ERROR_PREFIX\033[0m" + PIPA_LOGO="🪁" + WELCOME_MESSAGE="\033[1m$PIPA_LOGO $WELCOME_MESSAGE\033[0m" + COMPILING_MESSAGE="\033[1m$PIPA_LOGO $COMPILING_MESSAGE\033[0m" + BUILT_MESSAGE="\033[1m✅ $BUILT_MESSAGE\033[0m" +fi + +check_deps() { + if [ ! -e "$PIPAC_PATH" ]; then + printf "$ERROR_PREFIX pipac not found at $PIPAC_PATH. Consider running make command.\n" + exit 1 + fi + if [ ! -e "$AS" ] && ! which "$AS" >/dev/null; then + printf "$ERROR_PREFIX $AS not found.\n\n" + printf "Install it or provide the path with --as \n" + exit 1 + fi + if [ ! -e "$LD" ] && ! which "$LD" >/dev/null; then + printf "$ERROR_PREFIX $LD not found.\n\n" + printf "Install it or provide the path with --ld \n" + exit 1 + fi +} + +print_help() { + printf "$WELCOME_MESSAGE\n" + printf "Usage:\n" + printf "$0 [options] Compile filename.pipa\n\n" + printf "Options:\n" + printf -- "--as The path of gas compiler. Default: as\n" + printf -- "--help Prints this prompt.\n" + printf -- "--ld The path of linker compiler. Default: ld\n" + printf -- "--out The executable name. Default: filename without extension.\n" + printf -- "--silent Hide logs. Errors are sill displayed.\n" + exit 0 +} + +# FIXME: Allow the filename to came before the options +while [ $# -gt 0 ]; do + case "$1" in + --silent) + SILENT=1 + shift 1 + ;; + --as) + if [ ! -n "$2" ]; then + printf "$ERROR_PREFIX no argument passed for --as\n" >&2 + exit 1 + fi + AS="$2" + shift 2 + ;; + --ld) + if [ ! -n "$2" ]; then + printf "$ERROR_PREFIX no argument passed for --ld\n" >&2 + exit 1 + fi + LD="$2" + shift 2 + ;; + --out) + if [ ! -n "$2" ]; then + printf "$ERROR_PREFIX no argument passed for --out\n" >&2 + exit 1 + fi + OUT="$2" + shift 2 + ;; + --help) + print_help + ;; + *) + break + ;; + esac +done + +check_deps + +FILE_NAME="$1" + +log() { + if [ "$SILENT" -eq 0 ]; then + printf "$1\n" + fi +} + +cleanup() { + rm -f "$OUT.s" + rm -f "$OUT.o" +} + +if [ ! -n "$FILE_NAME" ]; then + printf "$ERROR_PREFIX no input file.\n" >&2 + exit 1 +fi + +if [ ! -e "$FILE_NAME" ]; then + printf "$ERROR_PREFIX filename not found.\n" >&2 + exit 1 +fi + +log "$COMPILING_MESSAGE $FILE_NAME" + +if ! [ -n "${OUT+x}" ]; then + OUT="${FILE_NAME%.*}" +fi + + +if ! $PIPAC_PATH "$FILE_NAME" > "$OUT.s"; then + printf "$ERROR_PREFIX $COMPILATION_ERROR_MESSAGE unable to generate assembly.\n" + cleanup + exit 1 +fi + +if ! $AS -o "$OUT.o" "$OUT.s" --64; then + printf "$ERROR_PREFIX $COMPILATION_ERROR_MESSAGE unable to compile gas.\n" + cleanup + exit 1 +fi + +if ! $LD -o "$OUT" "$OUT.o"; then + printf "$ERROR_PREFIX $COMPILATION_ERROR_MESSAGE unable to link the application.\n" + cleanup + exit 1 +fi + +cleanup + +log "$BUILT_MESSAGE $OUT" diff --git a/test/integration_test.c b/test/integration_test.c index 0ef3f5d..b6c0f36 100644 --- a/test/integration_test.c +++ b/test/integration_test.c @@ -22,15 +22,12 @@ void assert_exit_status(char* filename, int expected_exit_status) { - char command[255] = "../pipac "; + char command[255] = "../pipa --silent --out /tmp/pipa_program "; strcat(command, filename); - strcat(command, " > /tmp/pipa_example.s"); system(command); - system("as -o /tmp/pipa_example.o /tmp/pipa_example.s --64"); - system("ld -o /tmp/pipa_example /tmp/pipa_example.o"); - int status = system("/tmp/pipa_example"); + int status = system("/tmp/pipa_program"); if (WIFEXITED(status)) { int exit_status = WEXITSTATUS(status); -- cgit v1.2.3