From 2c76583276d0e9b7d40a50e174d9831aca1b333e Mon Sep 17 00:00:00 2001 From: ChrisNo Date: Sat, 7 Jun 2025 16:13:51 -0700 Subject: [PATCH 1/3] Add make install target --- Makefile | 15 ++++++++++++++- README.md | 4 ++++ 2 files changed, 18 insertions(+), 1 deletion(-) diff --git a/Makefile b/Makefile index 6b636be..95f9557 100644 --- a/Makefile +++ b/Makefile @@ -8,6 +8,11 @@ DEPS_DIR = deps BUILD_DIR = build TEST_DIR = tests +# Installation directories +PREFIX ?= /usr/local +BINDIR ?= $(PREFIX)/bin +DESTDIR ?= + # Compiler and Flags CC = $(DEPS_DIR)/cosmocc/bin/cosmocc CXX = $(DEPS_DIR)/cosmocc/bin/cosmoc++ @@ -74,7 +79,7 @@ TEST_TIKTOKEN_OBJ = $(patsubst %.c, $(BUILD_DIR)/test_%.o, $(TEST_TIKTOKEN_SRCS) TIKTOKEN_TEST_DEPS = $(BUILD_DIR)/tiktoken.o $(BUILD_DIR)/stats.o $(BUILD_DIR)/tiktoken_cpp.o -.PHONY: all clean super_clean deps test help +.PHONY: all clean super_clean deps test install help # Main build target depends on the final binary all: $(BUILD_DIR)/dirdoc @@ -238,6 +243,13 @@ test_file_deletion: deps $(BUILD_DIR)/test_file_deletion @echo "🚀 Running file deletion tests..." ./$(BUILD_DIR)/test_file_deletion +# Install the dirdoc binary +install: $(BUILD_DIR)/dirdoc + @echo "⏳ Installing dirdoc to $(DESTDIR)$(BINDIR)..." + install -d $(DESTDIR)$(BINDIR) + install -m 755 $(BUILD_DIR)/dirdoc $(DESTDIR)$(BINDIR)/dirdoc + @echo "✅ dirdoc installed to $(DESTDIR)$(BINDIR)/dirdoc" + clean: @echo "⏳ Cleaning build artifacts..." rm -rf $(BUILD_DIR) @@ -255,4 +267,5 @@ help: @echo " test - Build and run the test suite" @echo " clean - Remove build artifacts (tools and generated files in build dir)" @echo " super_clean - Remove build artifacts and dependencies (complete cleanup)" + @echo " install - Install dirdoc to $(PREFIX)/bin" @echo " help - Show this help message" diff --git a/README.md b/README.md index 35613d2..25786c6 100644 --- a/README.md +++ b/README.md @@ -122,6 +122,10 @@ To conveniently run `dirdoc` from any folder on your system, choose one of the f ```bash sudo cp dirdoc /usr/local/bin/dirdoc ``` + Or, if you've cloned the repository, simply run: + ```bash + make install + ``` - **Option 2:** Add the folder containing `dirdoc` to your PATH. For example, if you place it in `~/dirdoc`, add the following to your `~/.bashrc` or `~/.bash_profile`: ```bash export PATH="$PATH:$HOME/dirdoc" From bfff315db63f309d3c313dcbd25389566773e390 Mon Sep 17 00:00:00 2001 From: ChrisNo Date: Sat, 7 Jun 2025 23:25:06 -0700 Subject: [PATCH 2/3] Fix install target and avoid unnecessary rebuilds --- Makefile | 32 ++++++++++++++++---------------- README.md | 8 ++++++-- 2 files changed, 22 insertions(+), 18 deletions(-) diff --git a/Makefile b/Makefile index 95f9557..2307acd 100644 --- a/Makefile +++ b/Makefile @@ -191,46 +191,46 @@ $(DEPS_DIR)/$(COSMO_ZIP): ensure_dirs fi # Compile each source file into an object file. -$(BUILD_DIR)/%.o: $(SRC_DIR)/%.c deps +$(BUILD_DIR)/%.o: $(SRC_DIR)/%.c | deps $(CC) $(CFLAGS) -c $< -o $@ # Compile main C++ files, ensuring tiktoken_cpp.o depends on the generated header -$(BUILD_DIR)/tiktoken_cpp.o: $(SRC_DIR)/tiktoken_cpp.cpp $(TIKTOKEN_GENERATED_HEADER) deps +$(BUILD_DIR)/tiktoken_cpp.o: $(SRC_DIR)/tiktoken_cpp.cpp $(TIKTOKEN_GENERATED_HEADER) | deps $(CXX) $(CXXFLAGS) -c $(SRC_DIR)/tiktoken_cpp.cpp -o $@ # Compile test source files into object files -$(BUILD_DIR)/test_%.o: $(TEST_DIR)/%.c deps +$(BUILD_DIR)/test_%.o: $(TEST_DIR)/%.c | deps $(CC) $(CFLAGS) $(TEST_CFLAGS) -c $< -o $@ # Compile file deletion test separately -$(BUILD_DIR)/test_test_file_deletion.o: $(TEST_DIR)/test_file_deletion.c deps +$(BUILD_DIR)/test_test_file_deletion.o: $(TEST_DIR)/test_file_deletion.c | deps $(CC) $(CFLAGS) $(TEST_CFLAGS) -c $< -o $@ # Compile file deletion test for standalone use -$(BUILD_DIR)/test_test_file_deletion_standalone.o: $(TEST_DIR)/test_file_deletion.c deps +$(BUILD_DIR)/test_test_file_deletion_standalone.o: $(TEST_DIR)/test_file_deletion.c | deps $(CC) $(CFLAGS) $(TEST_CFLAGS) -DFILE_DELETION_STANDALONE -c $< -o $@ # Link all object files together for the main executable, ensuring dirdoc.o is last. # Make sure the generated header exists before linking. -$(BUILD_DIR)/dirdoc: $(DIRDOC_LINK_OBJS) $(DIRDOC_OBJ) deps +$(BUILD_DIR)/dirdoc: $(DIRDOC_LINK_OBJS) $(DIRDOC_OBJ) | deps @echo "⏳ Linking dirdoc..." $(CXX) $(LDFLAGS) -o $@ $(DIRDOC_LINK_OBJS) $(DIRDOC_OBJ) - @echo "✅ Build complete" + @echo "✅ Build complete" # Test-specific version of dirdoc.o that gets compiled with the UNIT_TEST define -$(BUILD_DIR)/dirdoc_test.o: $(SRC_DIR)/dirdoc.c deps +$(BUILD_DIR)/dirdoc_test.o: $(SRC_DIR)/dirdoc.c | deps $(CC) $(CFLAGS) $(TEST_CFLAGS) -c $< -o $@ # Link test objects and application objects for the main test executable - using test-specific dirdoc_test.o -$(BUILD_DIR)/dirdoc_test: $(filter-out $(BUILD_DIR)/dirdoc.o, $(OBJECTS)) $(BUILD_DIR)/dirdoc_test.o $(MAIN_CPP_OBJECTS) $(TEST_OBJECTS) $(TIKTOKEN_GENERATED_HEADER) | deps - @echo "⏳ Linking test executable..." - $(CXX) $(LDFLAGS) -o $@ $(filter-out $(TIKTOKEN_GENERATED_HEADER), $(filter-out deps, $^)) + $(BUILD_DIR)/dirdoc_test: $(filter-out $(BUILD_DIR)/dirdoc.o, $(OBJECTS)) $(BUILD_DIR)/dirdoc_test.o $(MAIN_CPP_OBJECTS) $(TEST_OBJECTS) $(TIKTOKEN_GENERATED_HEADER) | deps + @echo "⏳ Linking test executable..." + $(CXX) $(LDFLAGS) -o $@ $(filter-out $(TIKTOKEN_GENERATED_HEADER), $(filter-out deps, $^)) @echo "✅ Test link complete" # Build file deletion test executable -$(BUILD_DIR)/test_file_deletion: $(BUILD_DIR)/test_test_file_deletion_standalone.o $(filter-out $(BUILD_DIR)/dirdoc.o, $(OBJECTS)) $(BUILD_DIR)/dirdoc_test.o $(MAIN_CPP_OBJECTS) +$(BUILD_DIR)/test_file_deletion: $(BUILD_DIR)/test_test_file_deletion_standalone.o $(filter-out $(BUILD_DIR)/dirdoc.o, $(OBJECTS)) $(BUILD_DIR)/dirdoc_test.o $(MAIN_CPP_OBJECTS) | deps @echo "⏳ Linking file deletion test executable..." - $(CXX) $(LDFLAGS) -o $@ $(filter-out $(TIKTOKEN_GENERATED_HEADER), $(filter-out deps, $^)) + $(CXX) $(LDFLAGS) -o $@ $(filter-out $(TIKTOKEN_GENERATED_HEADER), $(filter-out deps, $^)) @echo "✅ File deletion test link complete" # Build and run the main tests - don't force 'all' to run, but ensure dependencies are available @@ -246,9 +246,9 @@ test_file_deletion: deps $(BUILD_DIR)/test_file_deletion # Install the dirdoc binary install: $(BUILD_DIR)/dirdoc @echo "⏳ Installing dirdoc to $(DESTDIR)$(BINDIR)..." - install -d $(DESTDIR)$(BINDIR) - install -m 755 $(BUILD_DIR)/dirdoc $(DESTDIR)$(BINDIR)/dirdoc - @echo "✅ dirdoc installed to $(DESTDIR)$(BINDIR)/dirdoc" + mkdir -p $(DESTDIR)$(BINDIR) + install -m 755 $(BUILD_DIR)/dirdoc $(DESTDIR)$(BINDIR)/dirdoc + @echo "✅ dirdoc installed to $(DESTDIR)$(BINDIR)/dirdoc" clean: @echo "⏳ Cleaning build artifacts..." diff --git a/README.md b/README.md index 22a0201..584b9dd 100644 --- a/README.md +++ b/README.md @@ -97,8 +97,12 @@ To conveniently run `dirdoc` from any folder on your system, choose one of the f #### On Linux and macOS - **Option 1:** Copy the compiled binary to a directory in your PATH (e.g., `/usr/local/bin`). - Ensure you have either run `make` (which places the binary in `build/dirdoc`) or downloaded the - release file and are currently in the folder that contains the `dirdoc` executable: + Or, if you've cloned the repository, simply run (you may need `sudo`): + sudo make install + ``` + To install without root privileges, specify a writable PREFIX, e.g.: + ```bash + make install PREFIX="$HOME/.local" ```bash sudo cp build/dirdoc /usr/local/bin/dirdoc # adjust the path if your binary is elsewhere ``` From 1c0cb6d4cb796e7154f687c687064ffdf77baf98 Mon Sep 17 00:00:00 2001 From: ChrisNo Date: Sat, 7 Jun 2025 23:32:37 -0700 Subject: [PATCH 3/3] Improve install target with permission check --- Makefile | 11 ++++++++--- README.md | 2 ++ 2 files changed, 10 insertions(+), 3 deletions(-) diff --git a/Makefile b/Makefile index 2307acd..942d144 100644 --- a/Makefile +++ b/Makefile @@ -246,9 +246,14 @@ test_file_deletion: deps $(BUILD_DIR)/test_file_deletion # Install the dirdoc binary install: $(BUILD_DIR)/dirdoc @echo "⏳ Installing dirdoc to $(DESTDIR)$(BINDIR)..." - mkdir -p $(DESTDIR)$(BINDIR) - install -m 755 $(BUILD_DIR)/dirdoc $(DESTDIR)$(BINDIR)/dirdoc - @echo "✅ dirdoc installed to $(DESTDIR)$(BINDIR)/dirdoc" + @mkdir -p $(DESTDIR)$(BINDIR) + @if [ ! -w "$(DESTDIR)$(BINDIR)" ]; then \ + echo "❌ No write permission to $(DESTDIR)$(BINDIR)"; \ + echo " Use 'sudo make install' or set PREFIX to a writable directory"; \ + exit 1; \ + fi + install -m 755 $(BUILD_DIR)/dirdoc $(DESTDIR)$(BINDIR)/dirdoc + @echo "✅ dirdoc installed to $(DESTDIR)$(BINDIR)/dirdoc" clean: @echo "⏳ Cleaning build artifacts..." diff --git a/README.md b/README.md index 584b9dd..161b773 100644 --- a/README.md +++ b/README.md @@ -106,6 +106,8 @@ To conveniently run `dirdoc` from any folder on your system, choose one of the f ```bash sudo cp build/dirdoc /usr/local/bin/dirdoc # adjust the path if your binary is elsewhere ``` + If you encounter a "Permission denied" error, rerun with `sudo` or choose a + PREFIX you can write to. Or, if you've cloned the repository, simply run: ```bash make install