Initial fork

This commit is contained in:
Ricardo Mazeto 2020-01-15 12:30:50 -07:00
commit 7917b6f5d9
4 changed files with 370 additions and 0 deletions

89
README.md Normal file
View File

@ -0,0 +1,89 @@
# Cook
## A bash replacement for make
Cook is supposed to be a simple build tool. As simple as possible. Cook is just a bash script sitting on your path waiting to cook you some delicious software. When you run cook, it searches the current working directory for a file called cookbook. If the cookbook file is found, cook executes the cookbook. If cook can't find the cookbook, it returns an error. You can also tell cook which cookbook to read, with the `-f <cookbook>` option. Or get a brand new free cookbook template with the `-n <language>` option, which makes cook look for a template cookbook on the configuration directory, "~/.config/cook" by default.
Before executing your cookbook, cook makes available to your cookbook two bash functions, **contains** and **check**.
contains <word> $@
Contains takes two arguments, **word** and $@. $@ is the list of arguments that cook was called with. Contains returns true, 0 in bash, if cook was called with that word as an argument. Here's an example of how it is supposed to be used:
contains gcc && CC=gcc
Which reads, if cook was called with the argument "gcc", let the variable CC be gcc.
The other function is check. It takes at least two arguments. The first is the name of the file to be compiled with the other arguments. Example:
check bin a.c b.c c.c
check returns true if the file bin don't exist or if it is older than any of the other files. check also sets a variable called DEPS, for dependencies, to be used in your compilation command. Therefore check is supposed to be used on your cookbooks like this:
check bin a.c b.c c.c \
&& $CC -o bin $DEPS
Cook covers these make cababilities:
- Build and install a package without
knowing the details of how that is done.
- Figure out automatically which files it
needs to update, based on which source files
have changed.
- PLUS: You can use your favorite indentaion style.
TODO list:
- figure out the order of dependencies.
- implement the "-o file" make capability,
which pretends that the file has changed, even though
it has changed. This is useful when you
add a new macro to a header file.
- Run checks in parallel.
## Recipe
Run **`cook -n [c|scheme|forth]`** and
get a free template cookbook of your choice on your cwd!
## Install
There's no install command available yet.
cp cook.sh /usr/local/bin/cook
gzip -c cook.1 > cook.1.gz
cp cook.1.gz /usr/share/man/man1/
mkdir ~/.config/cook
cp cookbooks/* ~/.config/cook
## LICENCE
This is free and unencumbered software released into the public domain.
Anyone is free to copy, modify, publish, use, compile, sell, or
distribute this software, either in source code form or as a compiled
binary, for any purpose, commercial or non-commercial, and by any
means.
In jurisdictions that recognize copyright laws, the author or authors
of this software dedicate any and all copyright interest in the
software to the public domain. We make this dedication for the benefit
of the public at large and to the detriment of our heirs and
successors. We intend this dedication to be an overt act of
relinquishment in perpetuity of all present and future rights to this
software under copyright law.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR
OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
OTHER DEALINGS IN THE SOFTWARE.
For more information, please refer to <http://unlicense.org/>

111
cook.1 Normal file
View File

@ -0,0 +1,111 @@
.Dd Apr 8, 2018
.Dt cook 1
.Os
.Sh NAME
cook
.Nd bash make
.Sh SYNOPSIS
Usage: cook
.Op Ar -f file
.Op Ar -n template
.Sh DESCRIPTION
.Nm cook
is a easy to use, tiny, minimalistic, intuitive, simple, vegan, gluten-free, and non-compatible with make, bash replacement for the make tool.
.Nm
Doesn't force you to use a specific indentation style on your compilation recipes, neither require you to learn a new syntax, you only need a little familiarity with bash to make full use of
.Nm .
And if if you aren't familiar with bash, there's a
\fIBASH\fR
section below with all the information you will need to get you started with
.Nm .
The first thing
.Nm
does when you run it, is search for a file called recipe on the current working directory. If the recipe file is not called recipe, you can tell cook which file to use with the -f flag.
If there's no recipe files on the current working directory, you can run
.Nm
\fI-n template\fR, where
\fItemplate\fR
is a file located at $HOME/.config/cook/. If cook finds the template file on the config directory, it will copy the file on the current working directory.
.Pp
.Nm
is nothing but a ordinary bash script with a handful of useful bash functions to automatize your compiling process. So far,
.Nm
contains only 2 functions. Once
.Nm
finds the recipe file, it will execute the recipe within the
.Nm
environment, making it's function available to your recipe. The cook functions are:
.Pp
.Nm contains
.Ar word argarr
Checks if argarr contains the given word. word should not contain any space, and argarr is usually $@, which is the whole list of arguments that
.Nm
was called with. $@ is the same as argv is in C. This is useful to set variables. You can call
.Nm
with different arguments to compile your program with different compilers, or set your #defines, etc.
.Nm check
.Ar bin src [src...]
checks if dependencies need to be recompiled. check takes at least two arguments. The first is the file that depends on the subsequent file(s). If at least one of the source files is older than the first file, the check returns true, 0 in bash, and the next command on the chain is executed.
.Sh RECIPE
A cook recipe is just a bash script. Here's an example of a recipe for a c program. If you don't understand how it is supposed to work or you're unfamiliar with bash, take a look at the \fIBASH\fR section of this manual.
# Compilation variables
CC="clang"
OUTDIR="bin"
OUTPUT="line_clg"
SRCDIR="src"
OBJDIR="obj"
MANDIR="/usr/share/man/man1"
CFLAGS="-Wall -Wpedantic -Werror -Os -g"
LIBS="-lm"
INSDIR="/usr/local/bin"
FPERMS="755"
# if cook was called with the arguments gcc or
# tcc, change the variable CC.
contains "gcc" $@ && CC=gcc && OUTPUT=line_gcc
contains "tcc" $@ && CC=tcc && OUTPUT=line_tcc
check $OUTDIR/$OUTPUT src/line.c &&\\
$CC $CFLAGS -o $OUTDIR/$OUTPUT $DEPS $LIBS
.Sh BASH
The only thing you need to know to start cooking, is how to declare variables in bash, and how to use conditional expressions. You can put any number of space characters before your variable declaration, but you can't put spaces between the variable name and the value.
# You cannot do this
CC = gcc
# but you can do this
CC=gcc
# and this, for alignment purposes
CC=gcc
In bash you can link a chain of commands, where each command is executed only if the previous command returns true, success, which is 0 in bash. You link this chain of commands with '&&'. Example:
check bin src1.c src2.c && $CC -o bin src1.c src2.c
These chains can get pretty long pretty fast, and a new line in bash tells bash to start executing the command. But you can "escape" this execution with a back-slash, like this:
check bin src1.c src2.c \\
&& $CC -o bin src1.c src2.c
And that's it! That's all you need to know to start cooking your programs.
Be aware that it is your responsability to declare your recipes in the right order.
.Sh ENVIRONMENT
.Pp
.Nm
Doesn't make use of environment variables yet.
.Sh BUGS
There's probably a couple of bugs here and there since this the 0.1 version. If you find a bug feel free to report it as an issue on the official github repository, or send me a patch via email.
.Sh AUTHOR
.An Ricardo Mazeto Aq Mt maz@cock.li
.Sh HOME
.Em https://cook.github.io

77
cook.sh Executable file
View File

@ -0,0 +1,77 @@
#!/bin/sh
# for convenience
alias ?=test
# Global list of dependencies
DEPS=""
CFGDIR="$HOME/.config/cook"
# The bash function check returns true, 0,
# when recompilation is needed.
# it also sets a variable called DEPS.
# DEPS is a useful variable that holds a list of
# all dependencies, so you can write
# check bin src1.c src2.c src3.c && $CC -o bin $DEPS
# Usage: check executable bar.c foo.c lib.c etc.c
check(){
# resets the DEPS list
DEPS=""
# at 1st, assume we don't need to recompile
ret=1
# if the 1st file don't even exist, return true
# in this case, we don't return 0 yet, because
# we need to set the DEPS variable
? ! -f "$1" && ret=0
# for each given argument
for file in $@;{
# skip 1st arg, because the 1st arg
# is the very object file to be compiled
? "$file" == "$1" && continue
# appends to DEPS.
DEPS="$DEPS $file"
# if the file doesn't exists, print err.
? ! -f "$file" && echo -e \
"\x1b[33;41m" \
"$file doesn\'t exist" \
"\x1b[0m" && break
# but if it is newer than the 1st arg return 0
? "$file" -nt "$1" && ret=0 && break;
}
return $ret
}
# The function contains returns true, 0 in bash,
# if the argsarray contains the word.
# usage: contains word argsarray
# this is probably not the best way to do it,
# but its the way I know, and it works.
contains(){
echo "$(echo $@ | cut -c $((${#1}+2))-)" |\
grep "$1" > /dev/null && return 0
return 1
}
# handles cook -f file
[[ "$#" == "2" ]] &&\
[[ "$1" == "-f" ]] &&\
[[ -e "$2" ]] &&\
. "$2" &&\
exit 0
# handles cook -n template
[[ "$#" == "2" ]] &&\
[[ "$1" == "-n" ]] &&\
[[ -e "$CFGDIR/$2" ]] &&\
cp "$CFGDIR/$2" "cookbook" &&\
exit 0
# handles cook [args]
[[ -e "./cookbook" ]] &&\
echo "running ./cookbook" &&\
. "./cookbook" $@ &&\
exit 0
# handles everything else
echo -en "usage:\n\tcook [-f cookbook] [-n template]\n" &&\
exit 0

93
cookbooks/c Normal file
View File

@ -0,0 +1,93 @@
# If the user called **bake** with the argument **help**, it's pretty convenient and it is a good practice to explain how to compile your program, which flags he can turn on and/or off for plugins, macros, etc.
contains "help" $@ && echo -en \
"Put your help text here\n" \
"Ex.:\n\n" \
"My super useful program v0.1\n\n" \
" Build with:\n" \
" bake program [FEATURES] [TESTSET]\n\n" \
&& exit 0
### clear
contains "clear" $@ && echo -en \
"Put cleaning commands here\n"\
"Ex.:\n\n"\
" test \$(ls bin | wc -l) -ne 0 &&\\ \n"\
" rm -rfv bin/* && exit 0\n\n"\
&& exit 0
### Uninstall
# ERROR. Unfortunetely the grep inside dep match the 'install'
# on "uninstall", so "uninstall" comes 1st here.
# This s a minor fix to a minor *bug*.
contains "uninstall" $@ &&\
echo -en \
"Put your uninstall commands here\n"\
"ex.:\n\n"\
" chmod \$MOD \$BINDIR/\$PROG &&\\ \n"\
" rm \$INSDIR/\$PROG &&\\ \n"\
" rm \$MANDIR/\$MAN &&\\ \n"\
" exit 0\n" &&\
exit 0
### Install
contains "install" $@ &&\
echo -en \
"Put your install commands here\n"\
"ex.:\n\n"\
" chmod \$MOD \$BINDIR/\$PROG &&\\ \n"\
" cp -i \$BINDIR/\$PROG \$INSDIR/\$PROG &&\\ \n"\
" cp -i \$DOCDIR/\$MAN \$MANDIR/\$MAN &&\\ \n"\
" exit 0\n" &&\
exit 0
### Stops before compilation
contains "stop" $@ && exit 0
### Variables
CC="" # c compiler
OUTDIR="" # output directory
OUTPUT="" # the final executable(s)
SRCDIR="" # source directory
ASMDIR="" # assembly directory
OBJDIR="" # object directory
MANDIR="" # usually "/usr/share/man/man1"
CFLAGS="" # pretty self-explanatory
LIBS="" # libraries to link
INSDIR="" # usually "/usr/local/bin" or "/bin/"
FPERMS="" # usually 755
ASM="" # list of assembly files
OBJ="" # list of object code files
SRC="main.src
foo.src
bar.src
class.src"
### Compile source to assembly
for s in $SRC; do
asm=$(echo $s | sed "s/\.c/\.a/g")
$ASM="$ASM $asm" # append to ASM
check $ASMDIR/$a $s &&\
$CC -S $CFLAGS -o $ASMDIR/$asm $s $LIBS
done
### Compile assembly to object files
for a in $ASM; do
obj=$(echo $a | sed "s/\.a/\.o/g")
$OBJ="$OBJ $obj" # append to ASM
check $OBJDIR/$obj $a &&\
$CC -c $CFLAGS -o $OBJDIR/$obj $a $LIBS
done
### Compile executable
check $OUTDIR/$OUTPUT $OBJ &&\
$CC $CFLAGS -o $OUTDIR/$OUTPUT $OBJ $LIBS
### Run
contains "run" $@ &&\
$OUTDIR/$OUTPUT > img/line.ff &&\
ff2png < img/line.ff > img/line.png &&\
fbi -a -f "xos4 Terminus-18" img/line.png 2> /dev/null