From 18103df342375bd2f69f23bff12ae1198ae0d11f Mon Sep 17 00:00:00 2001 From: soup Date: Sat, 14 Dec 2024 16:50:56 -0500 Subject: [PATCH] Initial commit --- .gitignore | 2 ++ .gitmodules | 3 ++ Makefile | 16 ++++++++++ compile_commands.json | 21 +++++++++++++ deps/tree-sitter-c | 1 + flake.lock | 58 ++++++++++++++++++++++++++++++++++ flake.nix | 24 ++++++++++++++ src/gen_enum.tsq | 5 +++ src/main.c | 73 +++++++++++++++++++++++++++++++++++++++++++ 9 files changed, 203 insertions(+) create mode 100644 .gitignore create mode 100644 .gitmodules create mode 100644 Makefile create mode 100644 compile_commands.json create mode 160000 deps/tree-sitter-c create mode 100644 flake.lock create mode 100644 flake.nix create mode 100644 src/gen_enum.tsq create mode 100644 src/main.c diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..bc95448 --- /dev/null +++ b/.gitignore @@ -0,0 +1,2 @@ +.cache/ +build/ diff --git a/.gitmodules b/.gitmodules new file mode 100644 index 0000000..e468ce8 --- /dev/null +++ b/.gitmodules @@ -0,0 +1,3 @@ +[submodule "deps/tree-sitter-c"] + path = deps/tree-sitter-c + url = https://github.com/tree-sitter/tree-sitter-c diff --git a/Makefile b/Makefile new file mode 100644 index 0000000..b590bb4 --- /dev/null +++ b/Makefile @@ -0,0 +1,16 @@ +CC := gcc -g -Og -std=c23 -Wall -Wextra -Wpedantic -Isrc -ltree-sitter + +build/bin/cgen: src/main.c | build/.build-dirs + $(CC) deps/tree-sitter-c/src/parser.c $^ -o build/bin/cgen + +.PHONY: run +run: build/bin/cgen + build/bin/cgen + +build/.build-dirs: Makefile + mkdir -p build/bin + touch build/.build-dirs + +.PHONY: clean +clean: + rm -rf build diff --git a/compile_commands.json b/compile_commands.json new file mode 100644 index 0000000..22b4777 --- /dev/null +++ b/compile_commands.json @@ -0,0 +1,21 @@ +[ + { + "arguments": [ + "/nix/store/1ciadcliylyyi9vx21id9vi1p1mayjn8-gcc-wrapper-14.2.0/bin/gcc", + "-c", + "-g", + "-Og", + "-std=c23", + "-Wall", + "-Wextra", + "-Wpedantic", + "-Isrc", + "-o", + "build/bin/cgen", + "src/main.c" + ], + "directory": "/home/n/src/cgen", + "file": "/home/n/src/cgen/src/main.c", + "output": "/home/n/src/cgen/build/bin/cgen" + } +] diff --git a/deps/tree-sitter-c b/deps/tree-sitter-c new file mode 160000 index 0000000..e8841a6 --- /dev/null +++ b/deps/tree-sitter-c @@ -0,0 +1 @@ +Subproject commit e8841a6a9431b7365ac9055688429e1deb8db90f diff --git a/flake.lock b/flake.lock new file mode 100644 index 0000000..6d4ff59 --- /dev/null +++ b/flake.lock @@ -0,0 +1,58 @@ +{ + "nodes": { + "flake-utils": { + "inputs": { + "systems": "systems" + }, + "locked": { + "lastModified": 1731533236, + "narHash": "sha256-l0KFg5HjrsfsO/JpG+r7fRrqm12kzFHyUHqHCVpMMbI=", + "owner": "numtide", + "repo": "flake-utils", + "rev": "11707dc2f618dd54ca8739b309ec4fc024de578b", + "type": "github" + }, + "original": { + "owner": "numtide", + "repo": "flake-utils", + "type": "github" + } + }, + "nixpkgs": { + "locked": { + "lastModified": 1733550349, + "narHash": "sha256-NcGumB4Lr6KSDq+nIqXtNA8QwAQKDSZT7N9OTGWbTrs=", + "path": "/nix/store/sqmn1ky3k66661h32djyjvsr8l99330z-source", + "rev": "e2605d0744c2417b09f8bf850dfca42fcf537d34", + "type": "path" + }, + "original": { + "id": "nixpkgs", + "type": "indirect" + } + }, + "root": { + "inputs": { + "flake-utils": "flake-utils", + "nixpkgs": "nixpkgs" + } + }, + "systems": { + "locked": { + "lastModified": 1681028828, + "narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=", + "owner": "nix-systems", + "repo": "default", + "rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e", + "type": "github" + }, + "original": { + "owner": "nix-systems", + "repo": "default", + "type": "github" + } + } + }, + "root": "root", + "version": 7 +} diff --git a/flake.nix b/flake.nix new file mode 100644 index 0000000..ba7dbbb --- /dev/null +++ b/flake.nix @@ -0,0 +1,24 @@ +{ + inputs.nixpkgs.url = "nixpkgs"; + inputs.flake-utils.url = "github:numtide/flake-utils"; + + outputs = inputs: + (inputs.flake-utils.lib.eachDefaultSystem (system: + let + pkgs = inputs.nixpkgs.legacyPackages.${system}; + in { + devShells.default = + pkgs.mkShell { + packages = with pkgs; [ + gdb + gcc15 + valgrind + strace + llvmPackages_17.clang-tools + bear + tree-sitter + ]; + }; + } + )); +} diff --git a/src/gen_enum.tsq b/src/gen_enum.tsq new file mode 100644 index 0000000..70b870c --- /dev/null +++ b/src/gen_enum.tsq @@ -0,0 +1,5 @@ +(enum_specifier + name: (type_identifier)? @enum_name + body: (enumerator_list + (enumerator + name: (identifier) @enum_variant)?)) diff --git a/src/main.c b/src/main.c new file mode 100644 index 0000000..aafb7d6 --- /dev/null +++ b/src/main.c @@ -0,0 +1,73 @@ +#include +#include +#include +#include + +#include + +TSLanguage const *tree_sitter_c(void); + +char const *USAGE = "\ +cgen \ +"; + +size_t read_stdin(char *buf, size_t buf_cap) { + char *at = buf; + char *end = buf + buf_cap; + + for (; at < end; ++at) { + if ((*at = fgetc(stdin)) == EOF) { + break; + } + } + if (at < end) { *at = '\0'; } + + return at - buf; +} + +char const gen_enum_query_str[] = { + #embed "./gen_enum.tsq", '\0' +}; +void gen_enum_strs() { + size_t buf_cap = 2 << 16; + char *buf = calloc(buf_cap, sizeof(*buf)); + size_t buf_len = read_stdin(buf, buf_cap); + + TSParser *parser = ts_parser_new(); + TSLanguage const *lang_c = tree_sitter_c(); + ts_parser_set_language(parser, lang_c); + + TSTree *tree = ts_parser_parse_string(parser, nullptr, buf, buf_len); + TSNode root_node = ts_tree_root_node(tree); + + char *string = ts_node_string(root_node); + printf("%s\n", string); + + uint32_t err_offset = 0; + TSQueryError err = {}; + TSQuery *query = ts_query_new( + lang_c, + gen_enum_query_str, + strlen(gen_enum_query_str), + &err_offset, + &err + ); + if (err != TSQueryErrorNone) { + printf("query error %d near: %s\n", err, gen_enum_query_str + err_offset); + assert(false); + } +} + +int main(int argc, char **argv) { + if (argc != 2) { + printf("%s", USAGE); + exit(1); + } + + char const *mode = argv[1]; + if (!strcmp(mode, "enum-strs")) { + gen_enum_strs(); + } + + return 0; +}