Previously I have used make purely for building large C, C++ based code bases. But recently I find myself writing a lot of one off scripts for automating tasks could be anything from checking for status of a test run to things like creating embeddings for some social media posts that I have downloaded. Point being there are so many different scripts and tasks that I automate that eventually in a week or so I forget exactly all the ways to invoke a particular script and various env variables and inputs it needs. This is where Makefiles shine for me now. Creating a make file to run the scripts achieves both the documentation as well as automating the invocation of the scripts.
Make is a system that has evolved from a simple and intuitive concept (declarative file to express build dependencies in order to automate build order resolution) into something of an art form for environment configuration, conditional compilation, etc.
Just like how there is a "JavaScript - the Good Parts" book, and one for C++, Make gives me the feeling that it also needs one.
I built this guide because I could never quite wrap my head around Makefiles. They seemed awash with hidden rules and esoteric symbols, and asking simple questions didn’t yield simple answers.
Related, if you don't want an entire build system, but just want some command runner with less baggage than make, there's just.
I really like just, BUT, it misses one of the more useful features of Makefiles/Taskfiles, that is to NOT run a task if its work is already complete (checksum,timestamp etc.).
We use this quite a lot to keep dev loops nice and fast (skipping lots of unnecessary work).
Yeah, I think those of us who aren't looking to compile C or C++ are better served by it. The C++ crowd also seems to be moving to other build systems like Cmake and Bazel. I can't comment on those, but it seems like Kids These Days have a better chance of saying "no thanks" when offered to learn makefile.
And then later us greybeards can go "why back in my day you had to deal with makefiles, and blah blah blah"
Yeah, these days I'd expect just to be available in repos, and make to actually not be installed unless the machine is used for C development. So at that point when picking something to install, and you just need a command runner, it makes more sense to go for just than to pick make and have to deal with all the extra baggage and pitfalls.
If you work in academia in high performance computing, or in tech in big companies, you very often find more hassle and constraints on not having sudo and no to install things. So knowing your makefile will run on anything from wsl and Mac to a server in prod is valuable.
I have had to work on a legacy c++ where just getting all its old dependencies (some from the 90s ) to build was an infuriating and frustrating experience. It is never just make files, it's autotools, automake, configure scripts, cmake (which is a bad language and should feel bad) and making sure all the versions line up.
Really made me appreciate cargo and modern built in build systems.
It's an unstable feature rn, but I really like the script runner pattern with uv so I can just throw some python snippets with dependencies into the file.
Using make as a glorified script and then complaining that it doesn't work well is something that some people really love to do for some reason. "make" is built to construct a graph of files on disk that depend on each other, and then traverse that graph to update the files that need updating. The virtual targets in the task-runner scenario break that. I guess "just" is better at this use case? Can you use a script?
just is actually very close to make, even according to its own documentation.
It is better at being a task runner (its dependencies are between tasks, not files, so things like .PHONY are applied by default), and that extends to things like supporting scripts in ways that are probably easier than make, but just is actually closer to make than I'd have guessed from hearing others talk about it.
MAKEFILES ARE NOT SCRIPTS. THEY ARE DECLARATIVE, NOT IMPERATIVE.
I see so many "Makefile tutorials" that try to explain Make as an imperative set of recipes. It is not. It is like SQL. You tell Make "I want this", and then it figures out how to do it.
Make was written at an unfortunate time in Progamming Language history: the 1970s. It is an attempt at a 4th-generation language, which realized after the fact was a bad way to try and categorize languages.
A great Makefile has as few explicit rules as possible, and ideally no commands.
Haha, funny read. I'm new to Make. They use it in my current workplace. We work in Go, not C. Each project has a make file, but mainly consists of commands calling just one other command.
I did not like Makefiles. I actually wrote a ruby-class that handles generation of Makefiles for me. It is far from perfect, but for trivial things it does work fine.
Whenever I have to edit a raw Makefile, I feel as if I am sent back to the early 1980s or even late 1970s.
We then had GNU configure - that's also annoying but has some convenience, e. g. ./configure --help (why does cmake and meson not have this, did the authors not understand why --help is useful to have).
Admittedly both cmake and meson/ninja (or cmake+ninja) are better than both Makefile and GNU configure; meson is IMO currently the best. But that mileage may vary, of course. Makefiles are at the least also simple. Ugly, but simple. That's worth something too.
This is really nice, but it assumes GNU make. It should start teaching with standard make for all those people who might find themselves working on a mid-90s Unix workstation. That's still a thing that happens, right?
I was going to say maybe macOS uses some kind of BSD Make, but it looks like Apple Developer Tools installs GNU Make after all.
That said, it's a good thing to be mindful of. I've caused and encountered my fair share of bugs by mistakenly trying to use GNU shell utility features in a script that had to run on macOS without GNU coreutils installed (and vice versa). I feel like not enough people are aware that even POSIX-compliant shell utilities can have nonstandard features that don't necessarily work cross platform.
it looks like Apple Developer Tools installs GNU Make after all.
Yep.
But it's GNU make 3.8.1 from 2006, so it's probably among the projects Apple will eventually replace with something featuring a different license once they have a chance. (For example, they recently replaced rsync.)
So, to your point, once that happens, you'll have a fairly large developer user base whose default make isn't GNU, so projects will either have to say "first, install make via Homebrew", or they'll have to adapt.
Oh yeah, and even the version thing can be an pain. I always have to install a modern Bash version on a new Mac to make sure my scripts will work. I don't use Make deeply enough to know what GNU has added since 2006 but I'm sure that's caused a few people some pain.
They also ship an ancient bash, allegedly because they're fine with GPL2 but not GPL3. I'd guess the reason is the same for shipping 20 year old GNU make.
But it is kinda weird that they haven't replaced it with BSD make in those decades. I'd really also expect them to drop bash—zsh is their interactive shell, and debian shows you can make do with dash. Instead their users get GNU tools from decades ago, which can be surprising for everyone who expects some modern feature or bugfix to be present.
Right. They changed the default from tcsh to bash (because nobody liked tcsh), then to zsh (because they didn't want GPL3). They'll probably eventually deprecate, then delete it, as they've done with e.g. built-in Perl.
Hrm, personally I find the yaml-based syntax of go-task to be another kind of convoluted, but I expect it might feel more natural for people who are very comfortable with github workflow specifications?
Together with an editor that supports JSON schemas, editing YAML is actually pretty comfortable. And Makefiles should honestly be read far more often than written, and there's zero question in my mind that a Taskfile is easier to read and understand than a Makefile.
Yeah, I work with yaml-language-server and yamllint and whatnot, and I'm not going to start defending makefile as a task runner system, but those aren't the only two options. Like I mentioned in another comment, I find justfiles to be pretty good. IMO the makefile syntax is generally readable, and the justfile syntax improves on it.
I'm not gonna claim one is clearly superior to the other for everything, but I think for people more used to makefiles, the justfile will feel like an improvement, while for people more used to github actions, the taskfile will feel familiar.
Props for the effort of documenting it, but regarding the title, just no, don't learn makefiles, and especially don't write them. Just let make die and replace it whenever you have the chance, with anything really. There's plenty of alternatives today.
Annoying tabby syntax, cryptic symbols, a chickensink of obscure features, poor handling of environment variables, several existing dialects, plenty of historical baggage... You'd have to actively try* to create an alternative to make that's as bad as make. It's not even all that great at doing the one thing it's supposed to do: properly figuring out what needs updating.
* ok, I guess you could just base it off yaml and let yaml do the rest
All that work, and yet it doesn't do what all proper build systems do well: rebuild the targets when the command to generate them changes. With this, you can edit the Makefile to change the build flags and it won't rebuild accordingly.
Make is a simplistic command runner with basic dependency rules. You can build some sort of build system on top of it with great effort, but this isn't it. Please, use specialized domain tools instead of using a general purpose tool badly to ensure your builds are correct. Fast and wrong is useless.
Ever since I learned (some of, the useful parts for simple setups) Make, my projects get a Makefile for simple running and often also for setting up dependencies, for example in Python venv and so on. I feel bad, if I have to remember or memorize how to run a project. Make enables me to go into a project directory and run it. And I take great care to make it runnable on different devices, so that I can git clone on my laptop and run the same thing as on my computer. That includes making sure, that things are actually reproducible. And that includes lock files, and/or things like Guix package manager. All neatly done in the Makefile so that I don't have to think about it, when I do anything ordinary in the project.
Many developers are not aware of solutions to reproducibility issues, or don't know how to solve them. Many developers also don't know Make and think it is only for compiling C projects.
There is, of course, also https://www.microsoft.com/en-us/research/wp-content/uploads/2016/03/hadrian.pdf (not really about make, just puns off of the title of Miller 2004)
Almost every target in a Makefile today is a phony, in other words Makefiles are used for anything but the original purpose. They are still kinda neat IMO.
But I use it in a couple apps at work, and it's an awesome way of making sure tasks A and B are complete before you launch C and D...stuff like that, configured in a text file...love it.
Interesting. I started a new Go project yesterday and Claude recommended make. I asked it if that was still the best choice in 2025 and it seemed to think so. Even after compiling things for 25+ years on *nix systems I’ve never learned it. Saved this to go through later.
That's actually not bad to be honest. Like most people I've ended up with "my" makefile that I copy and paste between projects and I dare not change it that much if I can possibly avoid it. make problems tend to become intractable quickly. When it was introduced the concept of "opinionated build system" and why this is better didn't exist so I'm not going to blame it for its faults,
Although i like the story about how its designer kept the absurd tab sensitivity because he didn't want to upset his dozen users. Don't break userspace!
Well, make is quite opinionated, there's this bunch of default rules and behavior specified.
Rules that may be so engrained now, maybe young folks don't always appreciate the posix/unix standards certainly aren't how things have to work at all. I'm not advocating departing from them now - you'll probably just cause yourself pain because they ARE engrained and network effects matter - just it's all just path-dependent history in the end, some stuff some humans in our timeline decided years ago.
e.g. Like sure, .o meaning object file is pretty normal, and then standard make having builtin spec-defined defaults for .o and stuff in turn pretty normal. But it's not some rule embedded in the physical laws of the universe. Definitely were systems in the 1980s using .obj for object file not .o, before things settled down (*). Use of .o an opinionated decision being made for you by a previous generations' convention-over-configuration. ;-)
I was quite surprised to see the unix standards change some of it recently - bunch of Fortran related stuff seems to have vanished from latest posix/unix standards. Fortran actually still fairly big+important if niche in Scientific/Engineering HPC (that also usually uses linux/unix-likes), would have thought they'd leave it in.
https://pubs.opengroup.org/onlinepubs/9799919799/utilities/make.html - The Open Group Base Specifications Issue 8 / IEEE Std 1003.1-2024 :
The default rules and macro values for make shall achieve results that are the same as if the following were used, except that where a result includes the literal value of a macro, this value may differ. Implementations that do not support the C-Language Development Utilities option may omit CC, CFLAGS, YACC, YFLAGS, LEX, LFLAGS, LDFLAGS, and the .c, .y, and .l inference rules. Implementations may provide additional macros and rules.
https://pubs.opengroup.org/onlinepubs/9699919799/utilities/make.html - The Open Group Base Specifications Issue 7, 2018 edition IEEE Std 1003.1-2017 (Revision of IEEE Std 1003.1-2008)
The default rules for make shall achieve results that are the same as if the following were used. Implementations that do not support the C-Language Development Utilities option may omit CC, CFLAGS, YACC, YFLAGS, LEX, LFLAGS, LDFLAGS, and the .c, .y, and .l inference rules. Implementations that do not support FORTRAN may omit FC, FFLAGS, and the .f inference rules. Implementations may provide additional macros and rules.
The compiler is called metacc, and it accepts several types of files. It assumes that filenames ending in .c represent C source programs. The compiler then compiles these .c files and places the reSUlting object program in the current directory with the same filename, but ending with .obj. The suffix .obj denotes an object file. The compiler assumes that files ending in .asm are assembly source programs. You can use the assembler to assemble these and produce an object file (ending with .obj) in the current directory
pingedbyte@reddit
Previously I have used make purely for building large C, C++ based code bases. But recently I find myself writing a lot of one off scripts for automating tasks could be anything from checking for status of a test run to things like creating embeddings for some social media posts that I have downloaded. Point being there are so many different scripts and tasks that I automate that eventually in a week or so I forget exactly all the ways to invoke a particular script and various env variables and inputs it needs. This is where Makefiles shine for me now. Creating a make file to run the scripts achieves both the documentation as well as automating the invocation of the scripts.
Oxidopamine@reddit
Wish I could unlearn makefiles
solarview@reddit
Why, if you don’t mind me asking?
munchbunny@reddit
Make is a system that has evolved from a simple and intuitive concept (declarative file to express build dependencies in order to automate build order resolution) into something of an art form for environment configuration, conditional compilation, etc.
Just like how there is a "JavaScript - the Good Parts" book, and one for C++, Make gives me the feeling that it also needs one.
fragbot2@reddit
People cargo cult Makefiles and often never understand what they’re doing as they don’t do them frequently enough to become competent with them.
If you take the time to understand them, they are far more capable and maintainable than people realize (gmake in particular).
ZelphirKalt@reddit
With Makefiles it is important to know where to stop, definitely.
realvolker1@reddit
The entire contents of my typical
build.sh
:syklemil@reddit
Related, if you don't want an entire build system, but just want some command runner with less baggage than make, there's just.
seanamos-1@reddit
I really like just, BUT, it misses one of the more useful features of Makefiles/Taskfiles, that is to NOT run a task if its work is already complete (checksum,timestamp etc.).
We use this quite a lot to keep dev loops nice and fast (skipping lots of unnecessary work).
MiigPT@reddit
You might want to look into mise, I like it quite a bit
seanamos-1@reddit
Thanks, not heard of it before and it seems to cover all the bases. Time for a POC!
bowersbros@reddit
Just is honestly amazing, sine moving to it, it's stopped me having to google how to do things like arguments etc
syklemil@reddit
Yeah, I think those of us who aren't looking to compile C or C++ are better served by it. The C++ crowd also seems to be moving to other build systems like Cmake and Bazel. I can't comment on those, but it seems like Kids These Days have a better chance of saying "no thanks" when offered to learn makefile.
And then later us greybeards can go "why back in my day you had to deal with makefiles, and blah blah blah"
BiteFancy9628@reddit
I just stick with make because it exists everywhere. But I guess just has gained enough traction you can find it in most distro packages repos.
syklemil@reddit
Yeah, these days I'd expect
just
to be available in repos, andmake
to actually not be installed unless the machine is used for C development. So at that point when picking something to install, and you just need a command runner, it makes more sense to go forjust
than to pickmake
and have to deal with all the extra baggage and pitfalls.BiteFancy9628@reddit
If you work in academia in high performance computing, or in tech in big companies, you very often find more hassle and constraints on not having sudo and no to install things. So knowing your makefile will run on anything from wsl and Mac to a server in prod is valuable.
tempest_@reddit
I have had to work on a legacy c++ where just getting all its old dependencies (some from the 90s ) to build was an infuriating and frustrating experience. It is never just make files, it's autotools, automake, configure scripts, cmake (which is a bad language and should feel bad) and making sure all the versions line up.
Really made me appreciate cargo and modern built in build systems.
Middlewarian@reddit
I'm building an on-line C++ code generator. To the best of my knowledge other languages don't have on-line code generators.
Halkcyon@reddit
It's an unstable feature rn, but I really like the script runner pattern with uv so I can just throw some python snippets with dependencies into the file.
dima55@reddit
Using make as a glorified script and then complaining that it doesn't work well is something that some people really love to do for some reason. "make" is built to construct a graph of files on disk that depend on each other, and then traverse that graph to update the files that need updating. The virtual targets in the task-runner scenario break that. I guess "just" is better at this use case? Can you use a script?
mpyne@reddit
just is actually very close to make, even according to its own documentation.
It is better at being a task runner (its dependencies are between tasks, not files, so things like
.PHONY
are applied by default), and that extends to things like supporting scripts in ways that are probably easier than make, but just is actually closer to make than I'd have guessed from hearing others talk about it.husky_whisperer@reddit
I feel the same way about Dockerfile and docker-compose.yaml.
this_knee@reddit
Pleasantly surprised that this is the top comment for this. It’s a great tool.
heptadecagram@reddit
No. No no no.
MAKEFILES ARE NOT SCRIPTS. THEY ARE DECLARATIVE, NOT IMPERATIVE.
I see so many "Makefile tutorials" that try to explain Make as an imperative set of recipes. It is not. It is like SQL. You tell Make "I want this", and then it figures out how to do it.
Make was written at an unfortunate time in Progamming Language history: the 1970s. It is an attempt at a 4th-generation language, which realized after the fact was a bad way to try and categorize languages.
A great Makefile has as few explicit rules as possible, and ideally no commands.
Effective Use of Make
gomsim@reddit
Haha, funny read. I'm new to Make. They use it in my current workplace. We work in Go, not C. Each project has a make file, but mainly consists of commands calling just one other command.
shevy-java@reddit
I did not like Makefiles. I actually wrote a ruby-class that handles generation of Makefiles for me. It is far from perfect, but for trivial things it does work fine.
Whenever I have to edit a raw Makefile, I feel as if I am sent back to the early 1980s or even late 1970s.
We then had GNU configure - that's also annoying but has some convenience, e. g. ./configure --help (why does cmake and meson not have this, did the authors not understand why --help is useful to have).
Admittedly both cmake and meson/ninja (or cmake+ninja) are better than both Makefile and GNU configure; meson is IMO currently the best. But that mileage may vary, of course. Makefiles are at the least also simple. Ugly, but simple. That's worth something too.
MC68328@reddit
This is really nice, but it assumes GNU make. It should start teaching with standard make for all those people who might find themselves working on a mid-90s Unix workstation. That's still a thing that happens, right?
valarauca14@reddit
30 year old build system lol
i_hate_shitposting@reddit
I was going to say maybe macOS uses some kind of BSD Make, but it looks like Apple Developer Tools installs GNU Make after all.
That said, it's a good thing to be mindful of. I've caused and encountered my fair share of bugs by mistakenly trying to use GNU shell utility features in a script that had to run on macOS without GNU coreutils installed (and vice versa). I feel like not enough people are aware that even POSIX-compliant shell utilities can have nonstandard features that don't necessarily work cross platform.
chucker23n@reddit
Yep.
But it's GNU make 3.8.1 from 2006, so it's probably among the projects Apple will eventually replace with something featuring a different license once they have a chance. (For example, they recently replaced rsync.)
So, to your point, once that happens, you'll have a fairly large developer user base whose default
make
isn't GNU, so projects will either have to say "first, installmake
via Homebrew", or they'll have to adapt.i_hate_shitposting@reddit
Oh yeah, and even the version thing can be an pain. I always have to install a modern Bash version on a new Mac to make sure my scripts will work. I don't use Make deeply enough to know what GNU has added since 2006 but I'm sure that's caused a few people some pain.
syklemil@reddit
They also ship an ancient bash, allegedly because they're fine with GPL2 but not GPL3. I'd guess the reason is the same for shipping 20 year old GNU make.
But it is kinda weird that they haven't replaced it with BSD make in those decades. I'd really also expect them to drop bash—zsh is their interactive shell, and debian shows you can make do with dash. Instead their users get GNU tools from decades ago, which can be surprising for everyone who expects some modern feature or bugfix to be present.
chucker23n@reddit
Right. They changed the default from tcsh to bash (because nobody liked tcsh), then to zsh (because they didn't want GPL3). They'll probably eventually deprecate, then delete it, as they've done with e.g. built-in Perl.
RoomyRoots@reddit
BSDs are still a thing. I though Alpine defaulted to non-Gnu but looks like it does use Gnu Make
hw999@reddit
make is a bit convoluted, i think go-task is a much better alternative.
syklemil@reddit
Hrm, personally I find the yaml-based syntax of go-task to be another kind of convoluted, but I expect it might feel more natural for people who are very comfortable with github workflow specifications?
r1veRRR@reddit
Together with an editor that supports JSON schemas, editing YAML is actually pretty comfortable. And Makefiles should honestly be read far more often than written, and there's zero question in my mind that a Taskfile is easier to read and understand than a Makefile.
syklemil@reddit
Yeah, I work with yaml-language-server and yamllint and whatnot, and I'm not going to start defending makefile as a task runner system, but those aren't the only two options. Like I mentioned in another comment, I find justfiles to be pretty good. IMO the makefile syntax is generally readable, and the justfile syntax improves on it.
I'm not gonna claim one is clearly superior to the other for everything, but I think for people more used to makefiles, the justfile will feel like an improvement, while for people more used to github actions, the taskfile will feel familiar.
silveryRain@reddit
Props for the effort of documenting it, but regarding the title, just no, don't learn makefiles, and especially don't write them. Just let make die and replace it whenever you have the chance, with anything really. There's plenty of alternatives today.
Annoying tabby syntax, cryptic symbols, a chickensink of obscure features, poor handling of environment variables, several existing dialects, plenty of historical baggage... You'd have to actively try* to create an alternative to make that's as bad as make. It's not even all that great at doing the one thing it's supposed to do: properly figuring out what needs updating.
* ok, I guess you could just base it off yaml and let yaml do the rest
OrphisFlo@reddit
All that work, and yet it doesn't do what all proper build systems do well: rebuild the targets when the command to generate them changes. With this, you can edit the Makefile to change the build flags and it won't rebuild accordingly.
Make is a simplistic command runner with basic dependency rules. You can build some sort of build system on top of it with great effort, but this isn't it. Please, use specialized domain tools instead of using a general purpose tool badly to ensure your builds are correct. Fast and wrong is useless.
brotatowolf@reddit
Oh hell no
ZelphirKalt@reddit
Ever since I learned (some of, the useful parts for simple setups) Make, my projects get a Makefile for simple running and often also for setting up dependencies, for example in Python venv and so on. I feel bad, if I have to remember or memorize how to run a project. Make enables me to go into a project directory and run it. And I take great care to make it runnable on different devices, so that I can git clone on my laptop and run the same thing as on my computer. That includes making sure, that things are actually reproducible. And that includes lock files, and/or things like Guix package manager. All neatly done in the Makefile so that I don't have to think about it, when I do anything ordinary in the project.
Many developers are not aware of solutions to reproducibility issues, or don't know how to solve them. Many developers also don't know Make and think it is only for compiling C projects.
jivedudebe@reddit
Yeah no
skinnybuddha@reddit
First read this, https://accu.org/journals/overload/14/71/miller_2004/
legobmw99@reddit
There is, of course, also https://www.microsoft.com/en-us/research/wp-content/uploads/2016/03/hadrian.pdf (not really about make, just puns off of the title of Miller 2004)
skinnybuddha@reddit
That's the real answer. There are better solutions now.
kintar1900@reddit
There's a typo in the article title. It has the word "Recursive" in front of "Makefiles Considered Harmful".
burtgummer45@reddit
Don't go programmers normally just use make?
krsnik93@reddit
Almost every target in a Makefile today is a phony, in other words Makefiles are used for anything but the original purpose. They are still kinda neat IMO.
captain_obvious_here@reddit
Make is an amazing and extremely reliable tool. I wish I had more occasions to use it :/
kintar1900@reddit
Be careful or you'll end up being REQUIRED to use it, then you'll learn the error of that wish.
captain_obvious_here@reddit
Nah, that probably won't happen in 2025 or later.
But I use it in a couple apps at work, and it's an awesome way of making sure tasks A and B are complete before you launch C and D...stuff like that, configured in a text file...love it.
rusmo@reddit
No thanks.
Apterygiformes@reddit
learn nix
TheCritFisher@reddit
Nix isn't bad, but it's better with devenv. The language is weird, but once you're used to it, it's a very nice experience.
RoomyRoots@reddit
The C++ of Make, lol
Apterygiformes@reddit
Maybe more like the Haskell of Make, but fixes the works on my machine dilemma
RoomyRoots@reddit
That would be Guix.
Somepotato@reddit
Not enough people know about Premake. Would recommend for generating build files.
GatitoAnonimo@reddit
Interesting. I started a new Go project yesterday and Claude recommended make. I asked it if that was still the best choice in 2025 and it seemed to think so. Even after compiling things for 25+ years on *nix systems I’ve never learned it. Saved this to go through later.
GoTheFuckToBed@reddit
I use bash
Atlos@reddit
AI is really good at generating makefiles. I’ve started using them again now that I don’t have to remember the syntax much.
Advanced-Essay6417@reddit
That's actually not bad to be honest. Like most people I've ended up with "my" makefile that I copy and paste between projects and I dare not change it that much if I can possibly avoid it. make problems tend to become intractable quickly. When it was introduced the concept of "opinionated build system" and why this is better didn't exist so I'm not going to blame it for its faults,
Although i like the story about how its designer kept the absurd tab sensitivity because he didn't want to upset his dozen users. Don't break userspace!
GwanTheSwans@reddit
Well,
make
is quite opinionated, there's this bunch of default rules and behavior specified.Rules that may be so engrained now, maybe young folks don't always appreciate the posix/unix standards certainly aren't how things have to work at all. I'm not advocating departing from them now - you'll probably just cause yourself pain because they ARE engrained and network effects matter - just it's all just path-dependent history in the end, some stuff some humans in our timeline decided years ago.
e.g. Like sure,
.o
meaning object file is pretty normal, and then standardmake
having builtin spec-defined defaults for.o
and stuff in turn pretty normal. But it's not some rule embedded in the physical laws of the universe. Definitely were systems in the 1980s using.obj
for object file not.o
, before things settled down (*). Use of.o
an opinionated decision being made for you by a previous generations' convention-over-configuration. ;-)I was quite surprised to see the unix standards change some of it recently - bunch of Fortran related stuff seems to have vanished from latest posix/unix standards. Fortran actually still fairly big+important if niche in Scientific/Engineering HPC (that also usually uses linux/unix-likes), would have thought they'd leave it in.
https://pubs.opengroup.org/onlinepubs/9799919799/utilities/make.html - The Open Group Base Specifications Issue 8 / IEEE Std 1003.1-2024 :
https://pubs.opengroup.org/onlinepubs/9699919799/utilities/make.html - The Open Group Base Specifications Issue 7, 2018 edition IEEE Std 1003.1-2017 (Revision of IEEE Std 1003.1-2008)
(*) e.g. early Greenhills C cross-compiler (PDF) on Sun for Amiga use, 1985 -
Linguistic-mystic@reddit
My every makefile starts with
.RECIPEPREFIX = /
so I don’t ever have to type the deplorable Tab characterDGolden@reddit
Honestly
make
is fairly okay except for the bloody hard tabs.I admit I sometimes use
.RECIPEPREFIX
(though not= /
as such, typically= >
, probably just because it's used in the example usage in the GNU make manual) but it remains a GNU-ism - never added to the Unix/Posix standard formake
to date.And of course bearing in mind the classic "Recursive Make Considered Harmful" rant. https://aegis.sourceforge.net/auug97.pdf