From 0c13293f431f0e2379ea062db1abd04484f92ef2 Mon Sep 17 00:00:00 2001 From: E Date: Mon, 3 May 2021 11:24:35 -0400 Subject: [PATCH 1/4] tools: add a luacheckrc generator tools/make-luacheck-files.sh will generate a .luacheckrc with the following rules: - any rules set in the project header (.luacheck.head) - each mod is allowed to use a single global sharing its mod name - mod dependency information is parsed, and those mods' globals are permitted for read access --- .luacheck.head | 17 +++++++ tools/make-luacheck-files.sh | 95 ++++++++++++++++++++++++++++++++++++ 2 files changed, 112 insertions(+) create mode 100644 .luacheck.head create mode 100755 tools/make-luacheck-files.sh diff --git a/.luacheck.head b/.luacheck.head new file mode 100644 index 00000000..bf49be42 --- /dev/null +++ b/.luacheck.head @@ -0,0 +1,17 @@ +std = "min" + +read_globals = { + "ItemStack", + "dump", "dump2", + "vector", + "VoxelArea", + "minetest", + "PseudoRandom", + "PerlinNoise", + "PcgRandom", + + string = {fields = {"split", "trim"}}, + table = {fields = {"copy", "getn", "indexof", "insert_all"}}, + math = {fields = {"hypot", "round"}}, +} + diff --git a/tools/make-luacheck-files.sh b/tools/make-luacheck-files.sh new file mode 100755 index 00000000..fa954ff7 --- /dev/null +++ b/tools/make-luacheck-files.sh @@ -0,0 +1,95 @@ +#!/bin/sh +# +# make-luacheck-files.sh +# v1 - E - Initial version + +set -ue + +if [ ! -d "mods" ] || [ ! -r ".luacheck.head" ]; then + printf "error: this script needs to be run from the mineclonia project root\n" 1>&2 + exit 1 +fi + +# We need these to be explicitly NOT expanded. +# shellcheck disable=2016 +{ + # This creates a luacheckrc-compatible line from a mod (supplied on + # the command line with -v MOD="mod_name"), a directory (-v DIR="..."), + # and a list of dependencies (via STDIN). The `read_globals` section is + # skipped if there are no dependencies (-v EMPTY=1). + AWK_DEPS2LCHECK=' + BEGIN { + printf("files[\"" DIR "\"] = { globals = { \"" MOD "\" }"); + if (!EMPTY) { + printf(", read_globals = { "); + } + }; + + # Without a pattern, this will match on empty lines + # and mess up the entry. We clean up the extra commas + # later in the script. + /.+/{ + sub("?$", ""); + sub("\xd", ""); + printf("\"" $1 "\", "); + }; + + END { + if (!EMPTY) { + printf("}"); + } + printf(" }\n"); + };' + + # This takes any line that contains 'depends' and an equal sign + # and spits out each (comma-separated) entry on its own line. + SED_MODCONF2DEPS=' + /depends *=/{ + s/.*depends *=//; + s/, ?/\n/g; + p; + }' + + HEADER=' +------------------------------------------------------------------- +-- THIS FILE WAS AUTOGENERATED BY tools/make-luacheck-files.sh ! -- +-- DO NOT EDIT BY HAND. YOUR CHANGES WILL BE LOST NEXT RUN! -- +------------------------------------------------------------------- + +' +} + +find mods -type d -print | while read -r DIR; do + if [ -r "$DIR/depends.txt" ]; then + printf "found: %s (%s)\n" "$DIR" "depends.txt" 1>&2 + # depends.txt is a simple newline-delimited file, + # so we can just read it in. + DEPS="$(cat "$DIR/depends.txt")" + elif [ -r "$DIR/mod.conf" ]; then + printf "found: %s (%s)\n" "$DIR" "mod.conf" 1>&2 + # mod.conf needs some more help to get usable + # data out of it. + DEPS="$(sed -n -r -e "$SED_MODCONF2DEPS" "$DIR/mod.conf")" + else + # Empty dir, or not a mod dir. + continue + fi + + EMPTY=0 + if [ -z "$DEPS" ]; then + EMPTY=1 + fi + + # Get only the last chunk of the directory + # for the mod name. + MOD="${DIR##*/}" + + # Now we run through it through the formatter, + # and remove any rogue trailing commas. + { awk -v DIR="$DIR" -v EMPTY="$EMPTY" -v MOD="$MOD" -- "$AWK_DEPS2LCHECK" | sed -e "s/, }/ }/"; } <<-EOF + $DEPS + EOF +done > .luacheck.files + +# Put the final thing together with the warning header +{ printf "%s" "$HEADER"; cat .luacheck.head .luacheck.files; } > .luacheckrc From 02a8496b5f72e8ae0523f9aa7075f9d96ce56ee2 Mon Sep 17 00:00:00 2001 From: E Date: Mon, 3 May 2021 11:28:57 -0400 Subject: [PATCH 2/4] luacheck: include a generated luacheck config --- .luacheckrc | 163 ++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 163 insertions(+) create mode 100644 .luacheckrc diff --git a/.luacheckrc b/.luacheckrc new file mode 100644 index 00000000..6cd60584 --- /dev/null +++ b/.luacheckrc @@ -0,0 +1,163 @@ + +------------------------------------------------------------------- +-- THIS FILE WAS AUTOGENERATED BY tools/make-luacheck-files.sh ! -- +-- DO NOT EDIT BY HAND. YOUR CHANGES WILL BE LOST NEXT RUN! -- +------------------------------------------------------------------- + +std = "min" + +read_globals = { + "ItemStack", + "dump", "dump2", + "vector", + "VoxelArea", + "minetest", + "PseudoRandom", + "PerlinNoise", + "PcgRandom", + + string = {fields = {"split", "trim"}}, + table = {fields = {"copy", "getn", "indexof", "insert_all"}}, + math = {fields = {"hypot", "round"}}, +} + +files["mods/CORE/_mcl_autogroup"] = { globals = { "_mcl_autogroup" } } +files["mods/CORE/biomeinfo"] = { globals = { "biomeinfo" } } +files["mods/CORE/controls"] = { globals = { "controls" } } +files["mods/CORE/flowlib"] = { globals = { "flowlib" } } +files["mods/CORE/mcl_explosions"] = { globals = { "mcl_explosions" }, read_globals = { "mcl_particles", "mcl_fire" } } +files["mods/CORE/mcl_init"] = { globals = { "mcl_init" } } +files["mods/CORE/mcl_loot"] = { globals = { "mcl_loot" } } +files["mods/CORE/mcl_particles"] = { globals = { "mcl_particles" } } +files["mods/CORE/mcl_sounds"] = { globals = { "mcl_sounds" } } +files["mods/CORE/mcl_util"] = { globals = { "mcl_util" }, read_globals = { "mcl_init" } } +files["mods/CORE/mcl_worlds"] = { globals = { "mcl_worlds" }, read_globals = { "mcl_init" } } +files["mods/CORE/mcl_autogroup"] = { globals = { "mcl_autogroup" } } +files["mods/ENTITIES/drippingwater"] = { globals = { "drippingwater" }, read_globals = { "mcl_core" } } +files["mods/ENTITIES/mcl_boats"] = { globals = { "mcl_boats" }, read_globals = { "mcl_player", "mcl_core", "doc_identifier" } } +files["mods/ENTITIES/mcl_burning"] = { globals = { "mcl_burning" } } +files["mods/ENTITIES/mcl_falling_nodes"] = { globals = { "mcl_falling_nodes" } } +files["mods/ENTITIES/mcl_item_entity"] = { globals = { "mcl_item_entity" }, read_globals = { "flowlib", "mcl_enchanting" } } +files["mods/ENTITIES/mcl_minecarts"] = { globals = { "mcl_minecarts" }, read_globals = { "mcl_explosions", "mcl_core", "mcl_sounds", "mcl_player", "mcl_achievements", "mcl_chests", "mcl_furnaces", "mesecons_commandblock", "mcl_hoppers", "mcl_tnt", "mesecons", "doc_identifier" } } +files["mods/ENTITIES/mcl_mobs"] = { globals = { "mcl_mobs" }, read_globals = { "mcl_particles", "mcl_weather", "mcl_explosions", "mcl_hunger", "mcl_worlds", "invisibility", "lucky_block", "cmi", "doc_identifier", "mcl_armor", "mcl_portals", "mcl_experience" } } +files["mods/ENTITIES/mcl_paintings"] = { globals = { "mcl_paintings" } } +files["mods/ENTITIES/mobs_mc"] = { globals = { "mobs_mc" }, read_globals = { "mcl_init", "mcl_particles", "default", "mcl_mobs", "mcl_tnt", "mcl_bows", "mcl_throwing", "mcl_fishing", "bones", "mesecons_materials", "mobs_mc_gameconfig", "doc_items" } } +files["mods/ENTITIES/mobs_mc_gameconfig"] = { globals = { "mobs_mc_gameconfig" }, read_globals = { "mcl_init", "mcl_core" } } +files["mods/ENVIRONMENT/lightning"] = { globals = { "lightning" }, read_globals = { "mcl_fire", "mcl_death_messages" } } +files["mods/ENVIRONMENT/mcl_moon"] = { globals = { "mcl_moon" } } +files["mods/ENVIRONMENT/mcl_void_damage"] = { globals = { "mcl_void_damage" }, read_globals = { "mcl_worlds", "mcl_death_messages" } } +files["mods/ENVIRONMENT/mcl_weather"] = { globals = { "mcl_weather" }, read_globals = { "mcl_init", "mcl_worlds", "lightning" } } +files["mods/HELP/doc/doc"] = { globals = { "doc" }, read_globals = { "unified_inventory", "sfinv_buttons", "central_message", "inventory_plus" } } +files["mods/HELP/doc/doc_identifier"] = { globals = { "doc_identifier" }, read_globals = { "doc", "doc_items", "doc_basics", "mcl_core" } } +files["mods/HELP/doc/doc_items"] = { globals = { "doc_items" }, read_globals = { "doc" } } +files["mods/HELP/mcl_craftguide"] = { globals = { "mcl_craftguide" }, read_globals = { "mcl_core", "mcl_compass", "mcl_clock", "doc", "sfinv", "sfinv_buttons" } } +files["mods/HELP/mcl_doc"] = { globals = { "mcl_doc" }, read_globals = { "doc", "doc_items" } } +files["mods/HELP/mcl_doc_basics"] = { globals = { "mcl_doc_basics" }, read_globals = { "doc" } } +files["mods/HELP/mcl_tt"] = { globals = { "mcl_tt" }, read_globals = { "tt", "mcl_enchanting" } } +files["mods/HELP/tt"] = { globals = { "tt" } } +files["mods/HUD/awards"] = { globals = { "awards" }, read_globals = { "sfinv", "unified_inventory" } } +files["mods/HUD/hudbars"] = { globals = { "hudbars" } } +files["mods/HUD/mcl_achievements"] = { globals = { "mcl_achievements" }, read_globals = { "awards" } } +files["mods/HUD/mcl_base_textures"] = { globals = { "mcl_base_textures" } } +files["mods/HUD/mcl_death_messages"] = { globals = { "mcl_death_messages" } } +files["mods/HUD/mcl_formspec"] = { globals = { "mcl_formspec" } } +files["mods/HUD/mcl_formspec_prepend"] = { globals = { "mcl_formspec_prepend" }, read_globals = { "mcl_init" } } +files["mods/HUD/mcl_hbarmor"] = { globals = { "mcl_hbarmor" }, read_globals = { "hudbars", "mcl_armor" } } +files["mods/HUD/mcl_inventory"] = { globals = { "mcl_inventory" }, read_globals = { "mcl_init", "mcl_formspec", "mcl_player", "_mcl_autogroup", "mcl_armor", "mcl_brewing", "mcl_potions", "mcl_enchanting" } } +files["mods/HUD/show_wielded_item"] = { globals = { "show_wielded_item" }, read_globals = { "hudbars" } } +files["mods/ITEMS/REDSTONE/mcl_comparators"] = { globals = { "mcl_comparators" }, read_globals = { "mesecons", "mcl_sounds", "doc", "screwdriver" } } +files["mods/ITEMS/REDSTONE/mcl_dispensers"] = { globals = { "mcl_dispensers" }, read_globals = { "mcl_init", "mcl_formspec", "mesecons", "mcl_sounds", "mcl_tnt", "mcl_worlds", "mcl_core", "mcl_nether", "mcl_armor_stand", "mcl_armor", "doc", "screwdriver" } } +files["mods/ITEMS/REDSTONE/mcl_droppers"] = { globals = { "mcl_droppers" }, read_globals = { "mcl_init", "mcl_formspec", "mesecons", "mcl_util", "doc", "screwdriver" } } +files["mods/ITEMS/REDSTONE/mcl_observers"] = { globals = { "mcl_observers" }, read_globals = { "mesecons", "mcl_util" } } +files["mods/ITEMS/REDSTONE/mesecons"] = { globals = { "mesecons" }, read_globals = { "mcl_sounds", "mcl_core", "doc" } } +files["mods/ITEMS/REDSTONE/mesecons_alias"] = { globals = { "mesecons_alias" }, read_globals = { "mesecons" } } +files["mods/ITEMS/REDSTONE/mesecons_button"] = { globals = { "mesecons_button" }, read_globals = { "mesecons", "doc" } } +files["mods/ITEMS/REDSTONE/mesecons_commandblock"] = { globals = { "mesecons_commandblock" }, read_globals = { "mesecons", "doc", "doc_items" } } +files["mods/ITEMS/REDSTONE/mesecons_delayer"] = { globals = { "mesecons_delayer" }, read_globals = { "mesecons", "doc", "screwdriver" } } +files["mods/ITEMS/REDSTONE/mesecons_lightstone"] = { globals = { "mesecons_lightstone" }, read_globals = { "mesecons", "doc" } } +files["mods/ITEMS/REDSTONE/mesecons_mvps"] = { globals = { "mesecons_mvps" }, read_globals = { "mesecons" } } +files["mods/ITEMS/REDSTONE/mesecons_noteblock"] = { globals = { "mesecons_noteblock" }, read_globals = { "mesecons", "mcl_particles" } } +files["mods/ITEMS/REDSTONE/mesecons_pistons"] = { globals = { "mesecons_pistons" }, read_globals = { "mesecons", "mesecons_mvps", "mcl_mobitems", "doc", "screwdriver" } } +files["mods/ITEMS/REDSTONE/mesecons_pressureplates"] = { globals = { "mesecons_pressureplates" }, read_globals = { "mesecons", "doc" } } +files["mods/ITEMS/REDSTONE/mesecons_solarpanel"] = { globals = { "mesecons_solarpanel" }, read_globals = { "mesecons", "doc" } } +files["mods/ITEMS/REDSTONE/mesecons_torch"] = { globals = { "mesecons_torch" }, read_globals = { "mesecons", "mcl_torches", "doc" } } +files["mods/ITEMS/REDSTONE/mesecons_walllever"] = { globals = { "mesecons_walllever" }, read_globals = { "mesecons", "doc" } } +files["mods/ITEMS/REDSTONE/mesecons_wires"] = { globals = { "mesecons_wires" }, read_globals = { "mesecons", "doc" } } +files["mods/ITEMS/mcl_anvils"] = { globals = { "mcl_anvils" }, read_globals = { "mcl_init", "mcl_formspec", "mcl_sounds", "mcl_core", "screwdriver", "tt", "mcl_enchanting" } } +files["mods/ITEMS/mcl_armor"] = { globals = { "mcl_armor" }, read_globals = { "mcl_core", "mcl_player", "mcl_fire", "ethereal", "bakedclay", "mcl_enchanting" } } +files["mods/ITEMS/mcl_armor_stand"] = { globals = { "mcl_armor_stand" }, read_globals = { "mcl_armor", "mcl_core", "mcl_sounds", "mcl_stairs", "screwdriver" } } +files["mods/ITEMS/mcl_banners"] = { globals = { "mcl_banners" }, read_globals = { "mcl_sounds", "mcl_core", "mcl_wool", "mcl_cauldrons", "doc", "screwdriver" } } +files["mods/ITEMS/mcl_beds"] = { globals = { "mcl_beds" }, read_globals = { "playerphysics", "mcl_sounds", "mcl_worlds", "mcl_wool", "mcl_dye", "mcl_explosions", "mcl_weather", "mcl_spawn", "doc" } } +files["mods/ITEMS/mcl_books"] = { globals = { "mcl_books" }, read_globals = { "mcl_init", "mcl_core", "mcl_sounds", "mcl_mobitems", "mcl_dye" } } +files["mods/ITEMS/mcl_bows"] = { globals = { "mcl_bows" }, read_globals = { "controls", "awards", "mcl_achievements", "mcl_core", "mcl_mobitems", "playerphysics", "doc", "doc_identifier", "mesecons_button", "mcl_particles", "mcl_enchanting" } } +files["mods/ITEMS/mcl_brewing"] = { globals = { "mcl_brewing" }, read_globals = { "mcl_init", "mcl_formspec", "mcl_sounds", "mcl_potions", "mcl_mobitems", "mcl_core", "doc", "screwdriver" } } +files["mods/ITEMS/mcl_buckets"] = { globals = { "mcl_buckets" }, read_globals = { "mcl_worlds", "mcl_core", "mclx_core", "doc" } } +files["mods/ITEMS/mcl_cake"] = { globals = { "mcl_cake" }, read_globals = { "mcl_core", "mcl_sounds", "mcl_hunger", "mcl_buckets", "mcl_farming", "mcl_mobitems", "doc" } } +files["mods/ITEMS/mcl_cauldrons"] = { globals = { "mcl_cauldrons" }, read_globals = { "mcl_core", "mclx_core", "mcl_sounds", "doc" } } +files["mods/ITEMS/mcl_chests"] = { globals = { "mcl_chests" }, read_globals = { "mcl_init", "mcl_formspec", "mcl_core", "mcl_sounds", "mcl_end", "mesecons", "doc", "screwdriver" } } +files["mods/ITEMS/mcl_clock"] = { globals = { "mcl_clock" }, read_globals = { "mcl_init", "mcl_worlds", "mesecons", "doc" } } +files["mods/ITEMS/mcl_cocoas"] = { globals = { "mcl_cocoas" }, read_globals = { "mcl_sounds", "mcl_core", "doc" } } +files["mods/ITEMS/mcl_colorblocks"] = { globals = { "mcl_colorblocks" }, read_globals = { "mcl_core", "mcl_sounds", "mcl_dye", "doc", "screwdriver" } } +files["mods/ITEMS/mcl_compass"] = { globals = { "mcl_compass" }, read_globals = { "mcl_core", "mcl_worlds", "mesecons", "doc" } } +files["mods/ITEMS/mcl_core"] = { globals = { "mcl_core" }, read_globals = { "mcl_autogroup", "mcl_init", "mcl_sounds", "mcl_particles", "mcl_util", "mcl_worlds", "doc_items", "doc", "mcl_enchanting" } } +files["mods/ITEMS/mcl_crafting_table"] = { globals = { "mcl_crafting_table" }, read_globals = { "mcl_init", "mcl_formspec", "mcl_sounds" } } +files["mods/ITEMS/mcl_doors"] = { globals = { "mcl_doors" }, read_globals = { "mcl_core", "mcl_sounds", "doc?", "screwdriver?", "mesecons" } } +files["mods/ITEMS/mcl_dye"] = { globals = { "mcl_dye" }, read_globals = { "mcl_core", "mcl_flowers", "mcl_mobitems", "mcl_cocoas" } } +files["mods/ITEMS/mcl_enchanting"] = { globals = { "mcl_enchanting" }, read_globals = { "tt", "walkover", "mcl_sounds", "screwdriver" } } +files["mods/ITEMS/mcl_end"] = { globals = { "mcl_end" }, read_globals = { "mcl_sounds", "mcl_util", "doc_items", "mcl_worlds", "mcl_structures" } } +files["mods/ITEMS/mcl_farming"] = { globals = { "mcl_farming" }, read_globals = { "mcl_core", "mcl_sounds", "mcl_wool", "mcl_torches", "mcl_weather", "mcl_armor", "mobs_mc", "doc" } } +files["mods/ITEMS/mcl_fences"] = { globals = { "mcl_fences" }, read_globals = { "mcl_core", "mcl_sounds", "doc", "screwdriver" } } +files["mods/ITEMS/mcl_fire"] = { globals = { "mcl_fire" }, read_globals = { "mcl_core", "mcl_worlds", "mcl_sounds", "mcl_particles", "mcl_portals" } } +files["mods/ITEMS/mcl_fishing"] = { globals = { "mcl_fishing" }, read_globals = { "mcl_core", "mcl_sounds", "mcl_loot", "mcl_mobs", "mcl_enchanting" } } +files["mods/ITEMS/mcl_flowerpots"] = { globals = { "mcl_flowerpots" }, read_globals = { "mcl_core", "mcl_sounds", "mcl_farming", "mcl_flowers", "doc" } } +files["mods/ITEMS/mcl_flowers"] = { globals = { "mcl_flowers" }, read_globals = { "mcl_core", "mcl_util", "mcl_sounds", "screwdriver", "doc" } } +files["mods/ITEMS/mcl_furnaces"] = { globals = { "mcl_furnaces" }, read_globals = { "mcl_init", "mcl_formspec", "mcl_core", "mcl_sounds", "mcl_craftguide", "mcl_achievements", "mcl_particles", "doc", "screwdriver" } } +files["mods/ITEMS/mcl_heads"] = { globals = { "mcl_heads" }, read_globals = { "mcl_sounds", "mcl_armor", "screwdriver", "doc" } } +files["mods/ITEMS/mcl_hoppers"] = { globals = { "mcl_hoppers" }, read_globals = { "mcl_core", "mcl_formspec", "mcl_sounds", "mcl_util", "doc", "screwdriver" } } +files["mods/ITEMS/mcl_itemframes"] = { globals = { "mcl_itemframes" }, read_globals = { "mcl_core", "mcl_sounds", "screwdriver" } } +files["mods/ITEMS/mcl_jukebox"] = { globals = { "mcl_jukebox" }, read_globals = { "mcl_core", "mcl_sounds" } } +files["mods/ITEMS/mcl_maps"] = { globals = { "mcl_maps" } } +files["mods/ITEMS/mcl_mobitems"] = { globals = { "mcl_mobitems" }, read_globals = { "mcl_core", "mcl_hunger" } } +files["mods/ITEMS/mcl_mobspawners"] = { globals = { "mcl_mobspawners" }, read_globals = { "mcl_sounds", "mcl_mobs" } } +files["mods/ITEMS/mcl_monster_eggs"] = { globals = { "mcl_monster_eggs" }, read_globals = { "mcl_sounds", "mobs_mc" } } +files["mods/ITEMS/mcl_mushrooms"] = { globals = { "mcl_mushrooms" }, read_globals = { "mcl_sounds", "mcl_util", "doc" } } +files["mods/ITEMS/mcl_nether"] = { globals = { "mcl_nether" }, read_globals = { "mcl_core", "mcl_sounds", "mcl_util", "walkover", "mcl_death_messages", "doc_items", "doc", "screwdriver" } } +files["mods/ITEMS/mcl_ocean"] = { globals = { "mcl_ocean" }, read_globals = { "mcl_core", "mcl_sounds", "mcl_dye", "doc", "doc_items", "screwdriver" } } +files["mods/ITEMS/mcl_portals"] = { globals = { "mcl_portals" }, read_globals = { "mcl_init", "mcl_worlds", "mcl_core", "mcl_nether", "mcl_end", "mcl_particles", "mcl_spawn", "awards", "doc" } } +files["mods/ITEMS/mcl_potions"] = { globals = { "mcl_potions" }, read_globals = { "mcl_core", "mcl_farming", "mcl_mobitems", "mcl_fishing", "mcl_bows", "mcl_end", "mcl_weather", "playerphysics" } } +files["mods/ITEMS/mcl_signs"] = { globals = { "mcl_signs" }, read_globals = { "mcl_sounds", "mcl_core", "doc" } } +files["mods/ITEMS/mcl_sponges"] = { globals = { "mcl_sponges" }, read_globals = { "mcl_sounds", "mcl_core", "mclx_core" } } +files["mods/ITEMS/mcl_stairs"] = { globals = { "mcl_stairs" }, read_globals = { "mcl_core", "mcl_sounds", "mcl_nether", "mcl_end", "mcl_ocean" } } +files["mods/ITEMS/mcl_throwing"] = { globals = { "mcl_throwing" }, read_globals = { "mcl_core", "mcl_mobitems", "doc", "mcl_fishing" } } +files["mods/ITEMS/mcl_tnt"] = { globals = { "mcl_tnt" }, read_globals = { "mcl_explosions", "mcl_particles", "mcl_sounds", "mcl_mobitems", "mcl_death_messages", "doc_identifier", "mesecons" } } +files["mods/ITEMS/mcl_tools"] = { globals = { "mcl_tools" }, read_globals = { "mcl_sounds" } } +files["mods/ITEMS/mcl_torches"] = { globals = { "mcl_torches" }, read_globals = { "mcl_core", "mcl_sounds", "mcl_particles", "doc" } } +files["mods/ITEMS/mcl_totems"] = { globals = { "mcl_totems" }, read_globals = { "mobs_mc" } } +files["mods/ITEMS/mcl_walls"] = { globals = { "mcl_walls" }, read_globals = { "mcl_core", "mcl_end", "mcl_ocean", "mcl_nether", "mcl_sounds", "doc" } } +files["mods/ITEMS/mcl_wool"] = { globals = { "mcl_wool" }, read_globals = { "mcl_sounds", "doc" } } +files["mods/ITEMS/mclx_core"] = { globals = { "mclx_core" }, read_globals = { "mcl_core", "doc" } } +files["mods/ITEMS/mclx_fences"] = { globals = { "mclx_fences" }, read_globals = { "mcl_fences" } } +files["mods/ITEMS/mclx_stairs"] = { globals = { "mclx_stairs" }, read_globals = { "mcl_ocean", "mcl_core", "mcl_sounds", "mcl_nether", "mcl_end", "mcl_colorblocks", "mcl_stairs", "doc" } } +files["mods/ITEMS/xpanes"] = { globals = { "xpanes" }, read_globals = { "mcl_sounds", "mcl_core", "doc" } } +files["mods/MAPGEN/mcl_biomes"] = { globals = { "mcl_biomes" }, read_globals = { "mcl_init", "mcl_mapgen_core", "mcl_core", "mcl_worlds", "mcl_farming", "mcl_flowers", "mcl_end", "mcl_ocean" } } +files["mods/MAPGEN/mcl_dungeons"] = { globals = { "mcl_dungeons" }, read_globals = { "mcl_init", "mcl_core", "mcl_chests", "mcl_mobs", "mcl_mobspawners", "mcl_mapgen_core", "mobs_mc" } } +files["mods/MAPGEN/mcl_mapgen_core"] = { globals = { "mcl_mapgen_core" }, read_globals = { "mcl_init", "mcl_core", "biomeinfo", "mclx_core", "mcl_worlds", "mcl_cocoas", "mcl_sponges", "mcl_ocean", "mcl_stairs", "mcl_monster_eggs", "mcl_structures" } } +files["mods/MAPGEN/mcl_strongholds"] = { globals = { "mcl_strongholds" }, read_globals = { "mcl_init", "mcl_structures", "mcl_mapgen_core" } } +files["mods/MAPGEN/mcl_structures"] = { globals = { "mcl_structures" }, read_globals = { "mcl_loot" } } +files["mods/MAPGEN/mcl_villages"] = { globals = { "mcl_villages" }, read_globals = { "mcl_util", "mcl_mapgen_core", "mcl_structures", "mcl_core", "mcl_loot", "mcl_farming", "mobs_mc" } } +files["mods/MAPGEN/tsm_railcorridors"] = { globals = { "tsm_railcorridors" }, read_globals = { "mcl_init", "mcl_worlds", "mcl_core", "mcl_mapgen_core", "mcl_loot", "mcl_tnt", "mcl_farming", "mcl_mobspawners", "mcl_minecarts" } } +files["mods/MISC/findbiome"] = { globals = { "findbiome" }, read_globals = { "biomeinfo" } } +files["mods/MISC/mcl_commands"] = { globals = { "mcl_commands" }, read_globals = { "mcl_death_messages" } } +files["mods/MISC/mcl_temp_helper_recipes"] = { globals = { "mcl_temp_helper_recipes" }, read_globals = { "mcl_core", "mcl_mobitems", "mcl_end", "mcl_nether", "mcl_ocean", "mcl_stairs", "xpanes" } } +files["mods/MISC/mcl_wip"] = { globals = { "mcl_wip" }, read_globals = { "mcl_core", "mcl_fishing", "mcl_maps", "mcl_minecarts", "doc_identifier", "mobs_mc", "mcl_comparators", "mcl_minecarts", "mcl_paintings", "mcl_potions" } } +files["mods/PLAYER/mcl_death_drop"] = { globals = { "mcl_death_drop" }, read_globals = { "mcl_armor", "mcl_enchanting" } } +files["mods/PLAYER/mcl_hunger"] = { globals = { "mcl_hunger" }, read_globals = { "hudbars", "mcl_death_messages" } } +files["mods/PLAYER/mcl_meshhand"] = { globals = { "mcl_meshhand" }, read_globals = { "mcl_tools", "mcl_skins" } } +files["mods/PLAYER/mcl_player_init"] = { globals = { "mcl_player_init" } } +files["mods/PLAYER/mcl_playerinfo"] = { globals = { "mcl_playerinfo" }, read_globals = { "mcl_init", "mcl_core", "mcl_particles", "mcl_death_messages" } } +files["mods/PLAYER/mcl_playerplus"] = { globals = { "mcl_playerplus" }, read_globals = { "mcl_init", "mcl_core", "mcl_particles", "mcl_hunger", "mcl_death_messages", "playerphysics", "mcl_playerinfo", "mcl_weather", "mcl_spawn", "mcl_enchanting" } } +files["mods/PLAYER/mcl_skins"] = { globals = { "mcl_skins" }, read_globals = { "mcl_player", "mcl_inventory", "intllib", "mcl_armor" } } +files["mods/PLAYER/mcl_spawn"] = { globals = { "mcl_spawn" }, read_globals = { "mcl_init" } } +files["mods/PLAYER/mcl_sprint"] = { globals = { "mcl_sprint" }, read_globals = { "mcl_playerinfo", "playerphysics", "mcl_hunger" } } +files["mods/PLAYER/playerphysics"] = { globals = { "playerphysics" } } +files["mods/PLAYER/wieldview"] = { globals = { "wieldview" }, read_globals = { "mcl_armor" } } From b1fbbfdd352ff4e02d2b4373e516585a5abb9dd6 Mon Sep 17 00:00:00 2001 From: E Date: Mon, 3 May 2021 13:33:19 -0400 Subject: [PATCH 3/4] tools: remove inline scripting from make-luacheck-files - the awk script was moved to its own file (deps-to-luacheck.awk) with minor changes, including added commentary, slightly more rigorous error checking, and using a different separator model to avoid a second stage to remove trailing commas - SED_MODCONF2DEPS was moved to a containing function, and commented - the awk command itself is now easier on the eyes --- tools/deps-to-luacheck.awk | 41 +++++++++++++++++++++ tools/make-luacheck-files.sh | 70 +++++++++++++----------------------- 2 files changed, 65 insertions(+), 46 deletions(-) create mode 100644 tools/deps-to-luacheck.awk diff --git a/tools/deps-to-luacheck.awk b/tools/deps-to-luacheck.awk new file mode 100644 index 00000000..19aab14a --- /dev/null +++ b/tools/deps-to-luacheck.awk @@ -0,0 +1,41 @@ +BEGIN { + if (!DIR || !MOD) { + printf("error: DIR and MOD must be set.\n"); + _panic=1; + exit 1; + } + + printf("files[\"" DIR "\"] = { globals = { \"" MOD "\" }"); + + if (!EMPTY) { + printf(", read_globals = { "); + } +}; + +# Without a pattern, this will match on empty lines +# and mess up the entry. We clean up the extra commas +# later in the script. +/.+/{ + # Get rid of the optional (?) mark from + # depends.txt entries. + sub("?$", ""); + + # Some files have CRLF, so get rid of those + # too. + sub("\xd", ""); + + SEP=", "; + if (NR == 1) { + SEP=""; + } + printf(SEP "\"" $1 "\""); +}; + +END { + if (!_panic) { + if (!EMPTY) { + printf(" }"); + } + printf(" }\n"); + } +}; diff --git a/tools/make-luacheck-files.sh b/tools/make-luacheck-files.sh index fa954ff7..507d6e93 100755 --- a/tools/make-luacheck-files.sh +++ b/tools/make-luacheck-files.sh @@ -2,6 +2,7 @@ # # make-luacheck-files.sh # v1 - E - Initial version +# v2 - E - Remove (most) inline scripts set -ue @@ -10,53 +11,27 @@ if [ ! -d "mods" ] || [ ! -r ".luacheck.head" ]; then exit 1 fi -# We need these to be explicitly NOT expanded. -# shellcheck disable=2016 -{ - # This creates a luacheckrc-compatible line from a mod (supplied on - # the command line with -v MOD="mod_name"), a directory (-v DIR="..."), - # and a list of dependencies (via STDIN). The `read_globals` section is - # skipped if there are no dependencies (-v EMPTY=1). - AWK_DEPS2LCHECK=' - BEGIN { - printf("files[\"" DIR "\"] = { globals = { \"" MOD "\" }"); - if (!EMPTY) { - printf(", read_globals = { "); - } - }; - - # Without a pattern, this will match on empty lines - # and mess up the entry. We clean up the extra commas - # later in the script. - /.+/{ - sub("?$", ""); - sub("\xd", ""); - printf("\"" $1 "\", "); - }; - - END { - if (!EMPTY) { - printf("}"); - } - printf(" }\n"); - };' - - # This takes any line that contains 'depends' and an equal sign - # and spits out each (comma-separated) entry on its own line. - SED_MODCONF2DEPS=' - /depends *=/{ - s/.*depends *=//; - s/, ?/\n/g; - p; - }' - - HEADER=' +HEADER=' ------------------------------------------------------------------- -- THIS FILE WAS AUTOGENERATED BY tools/make-luacheck-files.sh ! -- -- DO NOT EDIT BY HAND. YOUR CHANGES WILL BE LOST NEXT RUN! -- ------------------------------------------------------------------- ' + +# This takes any line that contains 'depends' and an equal sign +# and spits out each (comma-separated) entry on its own line. +modconf2deps() { + sed -n -r -e ' + # Match any lines like "depends = asdfada" + /depends *=/{ + # Get rid of the "depends =" part + s/.*depends *=//; + # Convert commas to newlines + s/, */\n/g; + # Record the output + p; + }' } find mods -type d -print | while read -r DIR; do @@ -69,7 +44,7 @@ find mods -type d -print | while read -r DIR; do printf "found: %s (%s)\n" "$DIR" "mod.conf" 1>&2 # mod.conf needs some more help to get usable # data out of it. - DEPS="$(sed -n -r -e "$SED_MODCONF2DEPS" "$DIR/mod.conf")" + DEPS="$(modconf2deps < "$DIR/mod.conf")" else # Empty dir, or not a mod dir. continue @@ -84,10 +59,13 @@ find mods -type d -print | while read -r DIR; do # for the mod name. MOD="${DIR##*/}" - # Now we run through it through the formatter, - # and remove any rogue trailing commas. - { awk -v DIR="$DIR" -v EMPTY="$EMPTY" -v MOD="$MOD" -- "$AWK_DEPS2LCHECK" | sed -e "s/, }/ }/"; } <<-EOF - $DEPS + # Now we run through it through the formatter + awk \ + -v DIR="$DIR" \ + -v EMPTY="$EMPTY" \ + -v MOD="$MOD" \ + -f tools/deps-to-luacheck.awk <<-EOF + $DEPS EOF done > .luacheck.files From e14265ff8e815bfa487f4e0c7831083e20f36c62 Mon Sep 17 00:00:00 2001 From: E Date: Sun, 16 May 2021 17:13:46 -0400 Subject: [PATCH 4/4] luacheck: remove luacheck generator, generate rules in .luacheckrc --- .luacheck.head | 17 --- .luacheckrc | 231 +++++++++++++---------------------- tools/deps-to-luacheck.awk | 41 ------- tools/make-luacheck-files.sh | 73 ----------- 4 files changed, 85 insertions(+), 277 deletions(-) delete mode 100644 .luacheck.head delete mode 100644 tools/deps-to-luacheck.awk delete mode 100755 tools/make-luacheck-files.sh diff --git a/.luacheck.head b/.luacheck.head deleted file mode 100644 index bf49be42..00000000 --- a/.luacheck.head +++ /dev/null @@ -1,17 +0,0 @@ -std = "min" - -read_globals = { - "ItemStack", - "dump", "dump2", - "vector", - "VoxelArea", - "minetest", - "PseudoRandom", - "PerlinNoise", - "PcgRandom", - - string = {fields = {"split", "trim"}}, - table = {fields = {"copy", "getn", "indexof", "insert_all"}}, - math = {fields = {"hypot", "round"}}, -} - diff --git a/.luacheckrc b/.luacheckrc index 6cd60584..9970dac6 100644 --- a/.luacheckrc +++ b/.luacheckrc @@ -1,9 +1,3 @@ - -------------------------------------------------------------------- --- THIS FILE WAS AUTOGENERATED BY tools/make-luacheck-files.sh ! -- --- DO NOT EDIT BY HAND. YOUR CHANGES WILL BE LOST NEXT RUN! -- -------------------------------------------------------------------- - std = "min" read_globals = { @@ -21,143 +15,88 @@ read_globals = { math = {fields = {"hypot", "round"}}, } -files["mods/CORE/_mcl_autogroup"] = { globals = { "_mcl_autogroup" } } -files["mods/CORE/biomeinfo"] = { globals = { "biomeinfo" } } -files["mods/CORE/controls"] = { globals = { "controls" } } -files["mods/CORE/flowlib"] = { globals = { "flowlib" } } -files["mods/CORE/mcl_explosions"] = { globals = { "mcl_explosions" }, read_globals = { "mcl_particles", "mcl_fire" } } -files["mods/CORE/mcl_init"] = { globals = { "mcl_init" } } -files["mods/CORE/mcl_loot"] = { globals = { "mcl_loot" } } -files["mods/CORE/mcl_particles"] = { globals = { "mcl_particles" } } -files["mods/CORE/mcl_sounds"] = { globals = { "mcl_sounds" } } -files["mods/CORE/mcl_util"] = { globals = { "mcl_util" }, read_globals = { "mcl_init" } } -files["mods/CORE/mcl_worlds"] = { globals = { "mcl_worlds" }, read_globals = { "mcl_init" } } -files["mods/CORE/mcl_autogroup"] = { globals = { "mcl_autogroup" } } -files["mods/ENTITIES/drippingwater"] = { globals = { "drippingwater" }, read_globals = { "mcl_core" } } -files["mods/ENTITIES/mcl_boats"] = { globals = { "mcl_boats" }, read_globals = { "mcl_player", "mcl_core", "doc_identifier" } } -files["mods/ENTITIES/mcl_burning"] = { globals = { "mcl_burning" } } -files["mods/ENTITIES/mcl_falling_nodes"] = { globals = { "mcl_falling_nodes" } } -files["mods/ENTITIES/mcl_item_entity"] = { globals = { "mcl_item_entity" }, read_globals = { "flowlib", "mcl_enchanting" } } -files["mods/ENTITIES/mcl_minecarts"] = { globals = { "mcl_minecarts" }, read_globals = { "mcl_explosions", "mcl_core", "mcl_sounds", "mcl_player", "mcl_achievements", "mcl_chests", "mcl_furnaces", "mesecons_commandblock", "mcl_hoppers", "mcl_tnt", "mesecons", "doc_identifier" } } -files["mods/ENTITIES/mcl_mobs"] = { globals = { "mcl_mobs" }, read_globals = { "mcl_particles", "mcl_weather", "mcl_explosions", "mcl_hunger", "mcl_worlds", "invisibility", "lucky_block", "cmi", "doc_identifier", "mcl_armor", "mcl_portals", "mcl_experience" } } -files["mods/ENTITIES/mcl_paintings"] = { globals = { "mcl_paintings" } } -files["mods/ENTITIES/mobs_mc"] = { globals = { "mobs_mc" }, read_globals = { "mcl_init", "mcl_particles", "default", "mcl_mobs", "mcl_tnt", "mcl_bows", "mcl_throwing", "mcl_fishing", "bones", "mesecons_materials", "mobs_mc_gameconfig", "doc_items" } } -files["mods/ENTITIES/mobs_mc_gameconfig"] = { globals = { "mobs_mc_gameconfig" }, read_globals = { "mcl_init", "mcl_core" } } -files["mods/ENVIRONMENT/lightning"] = { globals = { "lightning" }, read_globals = { "mcl_fire", "mcl_death_messages" } } -files["mods/ENVIRONMENT/mcl_moon"] = { globals = { "mcl_moon" } } -files["mods/ENVIRONMENT/mcl_void_damage"] = { globals = { "mcl_void_damage" }, read_globals = { "mcl_worlds", "mcl_death_messages" } } -files["mods/ENVIRONMENT/mcl_weather"] = { globals = { "mcl_weather" }, read_globals = { "mcl_init", "mcl_worlds", "lightning" } } -files["mods/HELP/doc/doc"] = { globals = { "doc" }, read_globals = { "unified_inventory", "sfinv_buttons", "central_message", "inventory_plus" } } -files["mods/HELP/doc/doc_identifier"] = { globals = { "doc_identifier" }, read_globals = { "doc", "doc_items", "doc_basics", "mcl_core" } } -files["mods/HELP/doc/doc_items"] = { globals = { "doc_items" }, read_globals = { "doc" } } -files["mods/HELP/mcl_craftguide"] = { globals = { "mcl_craftguide" }, read_globals = { "mcl_core", "mcl_compass", "mcl_clock", "doc", "sfinv", "sfinv_buttons" } } -files["mods/HELP/mcl_doc"] = { globals = { "mcl_doc" }, read_globals = { "doc", "doc_items" } } -files["mods/HELP/mcl_doc_basics"] = { globals = { "mcl_doc_basics" }, read_globals = { "doc" } } -files["mods/HELP/mcl_tt"] = { globals = { "mcl_tt" }, read_globals = { "tt", "mcl_enchanting" } } -files["mods/HELP/tt"] = { globals = { "tt" } } -files["mods/HUD/awards"] = { globals = { "awards" }, read_globals = { "sfinv", "unified_inventory" } } -files["mods/HUD/hudbars"] = { globals = { "hudbars" } } -files["mods/HUD/mcl_achievements"] = { globals = { "mcl_achievements" }, read_globals = { "awards" } } -files["mods/HUD/mcl_base_textures"] = { globals = { "mcl_base_textures" } } -files["mods/HUD/mcl_death_messages"] = { globals = { "mcl_death_messages" } } -files["mods/HUD/mcl_formspec"] = { globals = { "mcl_formspec" } } -files["mods/HUD/mcl_formspec_prepend"] = { globals = { "mcl_formspec_prepend" }, read_globals = { "mcl_init" } } -files["mods/HUD/mcl_hbarmor"] = { globals = { "mcl_hbarmor" }, read_globals = { "hudbars", "mcl_armor" } } -files["mods/HUD/mcl_inventory"] = { globals = { "mcl_inventory" }, read_globals = { "mcl_init", "mcl_formspec", "mcl_player", "_mcl_autogroup", "mcl_armor", "mcl_brewing", "mcl_potions", "mcl_enchanting" } } -files["mods/HUD/show_wielded_item"] = { globals = { "show_wielded_item" }, read_globals = { "hudbars" } } -files["mods/ITEMS/REDSTONE/mcl_comparators"] = { globals = { "mcl_comparators" }, read_globals = { "mesecons", "mcl_sounds", "doc", "screwdriver" } } -files["mods/ITEMS/REDSTONE/mcl_dispensers"] = { globals = { "mcl_dispensers" }, read_globals = { "mcl_init", "mcl_formspec", "mesecons", "mcl_sounds", "mcl_tnt", "mcl_worlds", "mcl_core", "mcl_nether", "mcl_armor_stand", "mcl_armor", "doc", "screwdriver" } } -files["mods/ITEMS/REDSTONE/mcl_droppers"] = { globals = { "mcl_droppers" }, read_globals = { "mcl_init", "mcl_formspec", "mesecons", "mcl_util", "doc", "screwdriver" } } -files["mods/ITEMS/REDSTONE/mcl_observers"] = { globals = { "mcl_observers" }, read_globals = { "mesecons", "mcl_util" } } -files["mods/ITEMS/REDSTONE/mesecons"] = { globals = { "mesecons" }, read_globals = { "mcl_sounds", "mcl_core", "doc" } } -files["mods/ITEMS/REDSTONE/mesecons_alias"] = { globals = { "mesecons_alias" }, read_globals = { "mesecons" } } -files["mods/ITEMS/REDSTONE/mesecons_button"] = { globals = { "mesecons_button" }, read_globals = { "mesecons", "doc" } } -files["mods/ITEMS/REDSTONE/mesecons_commandblock"] = { globals = { "mesecons_commandblock" }, read_globals = { "mesecons", "doc", "doc_items" } } -files["mods/ITEMS/REDSTONE/mesecons_delayer"] = { globals = { "mesecons_delayer" }, read_globals = { "mesecons", "doc", "screwdriver" } } -files["mods/ITEMS/REDSTONE/mesecons_lightstone"] = { globals = { "mesecons_lightstone" }, read_globals = { "mesecons", "doc" } } -files["mods/ITEMS/REDSTONE/mesecons_mvps"] = { globals = { "mesecons_mvps" }, read_globals = { "mesecons" } } -files["mods/ITEMS/REDSTONE/mesecons_noteblock"] = { globals = { "mesecons_noteblock" }, read_globals = { "mesecons", "mcl_particles" } } -files["mods/ITEMS/REDSTONE/mesecons_pistons"] = { globals = { "mesecons_pistons" }, read_globals = { "mesecons", "mesecons_mvps", "mcl_mobitems", "doc", "screwdriver" } } -files["mods/ITEMS/REDSTONE/mesecons_pressureplates"] = { globals = { "mesecons_pressureplates" }, read_globals = { "mesecons", "doc" } } -files["mods/ITEMS/REDSTONE/mesecons_solarpanel"] = { globals = { "mesecons_solarpanel" }, read_globals = { "mesecons", "doc" } } -files["mods/ITEMS/REDSTONE/mesecons_torch"] = { globals = { "mesecons_torch" }, read_globals = { "mesecons", "mcl_torches", "doc" } } -files["mods/ITEMS/REDSTONE/mesecons_walllever"] = { globals = { "mesecons_walllever" }, read_globals = { "mesecons", "doc" } } -files["mods/ITEMS/REDSTONE/mesecons_wires"] = { globals = { "mesecons_wires" }, read_globals = { "mesecons", "doc" } } -files["mods/ITEMS/mcl_anvils"] = { globals = { "mcl_anvils" }, read_globals = { "mcl_init", "mcl_formspec", "mcl_sounds", "mcl_core", "screwdriver", "tt", "mcl_enchanting" } } -files["mods/ITEMS/mcl_armor"] = { globals = { "mcl_armor" }, read_globals = { "mcl_core", "mcl_player", "mcl_fire", "ethereal", "bakedclay", "mcl_enchanting" } } -files["mods/ITEMS/mcl_armor_stand"] = { globals = { "mcl_armor_stand" }, read_globals = { "mcl_armor", "mcl_core", "mcl_sounds", "mcl_stairs", "screwdriver" } } -files["mods/ITEMS/mcl_banners"] = { globals = { "mcl_banners" }, read_globals = { "mcl_sounds", "mcl_core", "mcl_wool", "mcl_cauldrons", "doc", "screwdriver" } } -files["mods/ITEMS/mcl_beds"] = { globals = { "mcl_beds" }, read_globals = { "playerphysics", "mcl_sounds", "mcl_worlds", "mcl_wool", "mcl_dye", "mcl_explosions", "mcl_weather", "mcl_spawn", "doc" } } -files["mods/ITEMS/mcl_books"] = { globals = { "mcl_books" }, read_globals = { "mcl_init", "mcl_core", "mcl_sounds", "mcl_mobitems", "mcl_dye" } } -files["mods/ITEMS/mcl_bows"] = { globals = { "mcl_bows" }, read_globals = { "controls", "awards", "mcl_achievements", "mcl_core", "mcl_mobitems", "playerphysics", "doc", "doc_identifier", "mesecons_button", "mcl_particles", "mcl_enchanting" } } -files["mods/ITEMS/mcl_brewing"] = { globals = { "mcl_brewing" }, read_globals = { "mcl_init", "mcl_formspec", "mcl_sounds", "mcl_potions", "mcl_mobitems", "mcl_core", "doc", "screwdriver" } } -files["mods/ITEMS/mcl_buckets"] = { globals = { "mcl_buckets" }, read_globals = { "mcl_worlds", "mcl_core", "mclx_core", "doc" } } -files["mods/ITEMS/mcl_cake"] = { globals = { "mcl_cake" }, read_globals = { "mcl_core", "mcl_sounds", "mcl_hunger", "mcl_buckets", "mcl_farming", "mcl_mobitems", "doc" } } -files["mods/ITEMS/mcl_cauldrons"] = { globals = { "mcl_cauldrons" }, read_globals = { "mcl_core", "mclx_core", "mcl_sounds", "doc" } } -files["mods/ITEMS/mcl_chests"] = { globals = { "mcl_chests" }, read_globals = { "mcl_init", "mcl_formspec", "mcl_core", "mcl_sounds", "mcl_end", "mesecons", "doc", "screwdriver" } } -files["mods/ITEMS/mcl_clock"] = { globals = { "mcl_clock" }, read_globals = { "mcl_init", "mcl_worlds", "mesecons", "doc" } } -files["mods/ITEMS/mcl_cocoas"] = { globals = { "mcl_cocoas" }, read_globals = { "mcl_sounds", "mcl_core", "doc" } } -files["mods/ITEMS/mcl_colorblocks"] = { globals = { "mcl_colorblocks" }, read_globals = { "mcl_core", "mcl_sounds", "mcl_dye", "doc", "screwdriver" } } -files["mods/ITEMS/mcl_compass"] = { globals = { "mcl_compass" }, read_globals = { "mcl_core", "mcl_worlds", "mesecons", "doc" } } -files["mods/ITEMS/mcl_core"] = { globals = { "mcl_core" }, read_globals = { "mcl_autogroup", "mcl_init", "mcl_sounds", "mcl_particles", "mcl_util", "mcl_worlds", "doc_items", "doc", "mcl_enchanting" } } -files["mods/ITEMS/mcl_crafting_table"] = { globals = { "mcl_crafting_table" }, read_globals = { "mcl_init", "mcl_formspec", "mcl_sounds" } } -files["mods/ITEMS/mcl_doors"] = { globals = { "mcl_doors" }, read_globals = { "mcl_core", "mcl_sounds", "doc?", "screwdriver?", "mesecons" } } -files["mods/ITEMS/mcl_dye"] = { globals = { "mcl_dye" }, read_globals = { "mcl_core", "mcl_flowers", "mcl_mobitems", "mcl_cocoas" } } -files["mods/ITEMS/mcl_enchanting"] = { globals = { "mcl_enchanting" }, read_globals = { "tt", "walkover", "mcl_sounds", "screwdriver" } } -files["mods/ITEMS/mcl_end"] = { globals = { "mcl_end" }, read_globals = { "mcl_sounds", "mcl_util", "doc_items", "mcl_worlds", "mcl_structures" } } -files["mods/ITEMS/mcl_farming"] = { globals = { "mcl_farming" }, read_globals = { "mcl_core", "mcl_sounds", "mcl_wool", "mcl_torches", "mcl_weather", "mcl_armor", "mobs_mc", "doc" } } -files["mods/ITEMS/mcl_fences"] = { globals = { "mcl_fences" }, read_globals = { "mcl_core", "mcl_sounds", "doc", "screwdriver" } } -files["mods/ITEMS/mcl_fire"] = { globals = { "mcl_fire" }, read_globals = { "mcl_core", "mcl_worlds", "mcl_sounds", "mcl_particles", "mcl_portals" } } -files["mods/ITEMS/mcl_fishing"] = { globals = { "mcl_fishing" }, read_globals = { "mcl_core", "mcl_sounds", "mcl_loot", "mcl_mobs", "mcl_enchanting" } } -files["mods/ITEMS/mcl_flowerpots"] = { globals = { "mcl_flowerpots" }, read_globals = { "mcl_core", "mcl_sounds", "mcl_farming", "mcl_flowers", "doc" } } -files["mods/ITEMS/mcl_flowers"] = { globals = { "mcl_flowers" }, read_globals = { "mcl_core", "mcl_util", "mcl_sounds", "screwdriver", "doc" } } -files["mods/ITEMS/mcl_furnaces"] = { globals = { "mcl_furnaces" }, read_globals = { "mcl_init", "mcl_formspec", "mcl_core", "mcl_sounds", "mcl_craftguide", "mcl_achievements", "mcl_particles", "doc", "screwdriver" } } -files["mods/ITEMS/mcl_heads"] = { globals = { "mcl_heads" }, read_globals = { "mcl_sounds", "mcl_armor", "screwdriver", "doc" } } -files["mods/ITEMS/mcl_hoppers"] = { globals = { "mcl_hoppers" }, read_globals = { "mcl_core", "mcl_formspec", "mcl_sounds", "mcl_util", "doc", "screwdriver" } } -files["mods/ITEMS/mcl_itemframes"] = { globals = { "mcl_itemframes" }, read_globals = { "mcl_core", "mcl_sounds", "screwdriver" } } -files["mods/ITEMS/mcl_jukebox"] = { globals = { "mcl_jukebox" }, read_globals = { "mcl_core", "mcl_sounds" } } -files["mods/ITEMS/mcl_maps"] = { globals = { "mcl_maps" } } -files["mods/ITEMS/mcl_mobitems"] = { globals = { "mcl_mobitems" }, read_globals = { "mcl_core", "mcl_hunger" } } -files["mods/ITEMS/mcl_mobspawners"] = { globals = { "mcl_mobspawners" }, read_globals = { "mcl_sounds", "mcl_mobs" } } -files["mods/ITEMS/mcl_monster_eggs"] = { globals = { "mcl_monster_eggs" }, read_globals = { "mcl_sounds", "mobs_mc" } } -files["mods/ITEMS/mcl_mushrooms"] = { globals = { "mcl_mushrooms" }, read_globals = { "mcl_sounds", "mcl_util", "doc" } } -files["mods/ITEMS/mcl_nether"] = { globals = { "mcl_nether" }, read_globals = { "mcl_core", "mcl_sounds", "mcl_util", "walkover", "mcl_death_messages", "doc_items", "doc", "screwdriver" } } -files["mods/ITEMS/mcl_ocean"] = { globals = { "mcl_ocean" }, read_globals = { "mcl_core", "mcl_sounds", "mcl_dye", "doc", "doc_items", "screwdriver" } } -files["mods/ITEMS/mcl_portals"] = { globals = { "mcl_portals" }, read_globals = { "mcl_init", "mcl_worlds", "mcl_core", "mcl_nether", "mcl_end", "mcl_particles", "mcl_spawn", "awards", "doc" } } -files["mods/ITEMS/mcl_potions"] = { globals = { "mcl_potions" }, read_globals = { "mcl_core", "mcl_farming", "mcl_mobitems", "mcl_fishing", "mcl_bows", "mcl_end", "mcl_weather", "playerphysics" } } -files["mods/ITEMS/mcl_signs"] = { globals = { "mcl_signs" }, read_globals = { "mcl_sounds", "mcl_core", "doc" } } -files["mods/ITEMS/mcl_sponges"] = { globals = { "mcl_sponges" }, read_globals = { "mcl_sounds", "mcl_core", "mclx_core" } } -files["mods/ITEMS/mcl_stairs"] = { globals = { "mcl_stairs" }, read_globals = { "mcl_core", "mcl_sounds", "mcl_nether", "mcl_end", "mcl_ocean" } } -files["mods/ITEMS/mcl_throwing"] = { globals = { "mcl_throwing" }, read_globals = { "mcl_core", "mcl_mobitems", "doc", "mcl_fishing" } } -files["mods/ITEMS/mcl_tnt"] = { globals = { "mcl_tnt" }, read_globals = { "mcl_explosions", "mcl_particles", "mcl_sounds", "mcl_mobitems", "mcl_death_messages", "doc_identifier", "mesecons" } } -files["mods/ITEMS/mcl_tools"] = { globals = { "mcl_tools" }, read_globals = { "mcl_sounds" } } -files["mods/ITEMS/mcl_torches"] = { globals = { "mcl_torches" }, read_globals = { "mcl_core", "mcl_sounds", "mcl_particles", "doc" } } -files["mods/ITEMS/mcl_totems"] = { globals = { "mcl_totems" }, read_globals = { "mobs_mc" } } -files["mods/ITEMS/mcl_walls"] = { globals = { "mcl_walls" }, read_globals = { "mcl_core", "mcl_end", "mcl_ocean", "mcl_nether", "mcl_sounds", "doc" } } -files["mods/ITEMS/mcl_wool"] = { globals = { "mcl_wool" }, read_globals = { "mcl_sounds", "doc" } } -files["mods/ITEMS/mclx_core"] = { globals = { "mclx_core" }, read_globals = { "mcl_core", "doc" } } -files["mods/ITEMS/mclx_fences"] = { globals = { "mclx_fences" }, read_globals = { "mcl_fences" } } -files["mods/ITEMS/mclx_stairs"] = { globals = { "mclx_stairs" }, read_globals = { "mcl_ocean", "mcl_core", "mcl_sounds", "mcl_nether", "mcl_end", "mcl_colorblocks", "mcl_stairs", "doc" } } -files["mods/ITEMS/xpanes"] = { globals = { "xpanes" }, read_globals = { "mcl_sounds", "mcl_core", "doc" } } -files["mods/MAPGEN/mcl_biomes"] = { globals = { "mcl_biomes" }, read_globals = { "mcl_init", "mcl_mapgen_core", "mcl_core", "mcl_worlds", "mcl_farming", "mcl_flowers", "mcl_end", "mcl_ocean" } } -files["mods/MAPGEN/mcl_dungeons"] = { globals = { "mcl_dungeons" }, read_globals = { "mcl_init", "mcl_core", "mcl_chests", "mcl_mobs", "mcl_mobspawners", "mcl_mapgen_core", "mobs_mc" } } -files["mods/MAPGEN/mcl_mapgen_core"] = { globals = { "mcl_mapgen_core" }, read_globals = { "mcl_init", "mcl_core", "biomeinfo", "mclx_core", "mcl_worlds", "mcl_cocoas", "mcl_sponges", "mcl_ocean", "mcl_stairs", "mcl_monster_eggs", "mcl_structures" } } -files["mods/MAPGEN/mcl_strongholds"] = { globals = { "mcl_strongholds" }, read_globals = { "mcl_init", "mcl_structures", "mcl_mapgen_core" } } -files["mods/MAPGEN/mcl_structures"] = { globals = { "mcl_structures" }, read_globals = { "mcl_loot" } } -files["mods/MAPGEN/mcl_villages"] = { globals = { "mcl_villages" }, read_globals = { "mcl_util", "mcl_mapgen_core", "mcl_structures", "mcl_core", "mcl_loot", "mcl_farming", "mobs_mc" } } -files["mods/MAPGEN/tsm_railcorridors"] = { globals = { "tsm_railcorridors" }, read_globals = { "mcl_init", "mcl_worlds", "mcl_core", "mcl_mapgen_core", "mcl_loot", "mcl_tnt", "mcl_farming", "mcl_mobspawners", "mcl_minecarts" } } -files["mods/MISC/findbiome"] = { globals = { "findbiome" }, read_globals = { "biomeinfo" } } -files["mods/MISC/mcl_commands"] = { globals = { "mcl_commands" }, read_globals = { "mcl_death_messages" } } -files["mods/MISC/mcl_temp_helper_recipes"] = { globals = { "mcl_temp_helper_recipes" }, read_globals = { "mcl_core", "mcl_mobitems", "mcl_end", "mcl_nether", "mcl_ocean", "mcl_stairs", "xpanes" } } -files["mods/MISC/mcl_wip"] = { globals = { "mcl_wip" }, read_globals = { "mcl_core", "mcl_fishing", "mcl_maps", "mcl_minecarts", "doc_identifier", "mobs_mc", "mcl_comparators", "mcl_minecarts", "mcl_paintings", "mcl_potions" } } -files["mods/PLAYER/mcl_death_drop"] = { globals = { "mcl_death_drop" }, read_globals = { "mcl_armor", "mcl_enchanting" } } -files["mods/PLAYER/mcl_hunger"] = { globals = { "mcl_hunger" }, read_globals = { "hudbars", "mcl_death_messages" } } -files["mods/PLAYER/mcl_meshhand"] = { globals = { "mcl_meshhand" }, read_globals = { "mcl_tools", "mcl_skins" } } -files["mods/PLAYER/mcl_player_init"] = { globals = { "mcl_player_init" } } -files["mods/PLAYER/mcl_playerinfo"] = { globals = { "mcl_playerinfo" }, read_globals = { "mcl_init", "mcl_core", "mcl_particles", "mcl_death_messages" } } -files["mods/PLAYER/mcl_playerplus"] = { globals = { "mcl_playerplus" }, read_globals = { "mcl_init", "mcl_core", "mcl_particles", "mcl_hunger", "mcl_death_messages", "playerphysics", "mcl_playerinfo", "mcl_weather", "mcl_spawn", "mcl_enchanting" } } -files["mods/PLAYER/mcl_skins"] = { globals = { "mcl_skins" }, read_globals = { "mcl_player", "mcl_inventory", "intllib", "mcl_armor" } } -files["mods/PLAYER/mcl_spawn"] = { globals = { "mcl_spawn" }, read_globals = { "mcl_init" } } -files["mods/PLAYER/mcl_sprint"] = { globals = { "mcl_sprint" }, read_globals = { "mcl_playerinfo", "playerphysics", "mcl_hunger" } } -files["mods/PLAYER/playerphysics"] = { globals = { "playerphysics" } } -files["mods/PLAYER/wieldview"] = { globals = { "wieldview" }, read_globals = { "mcl_armor" } } +-- A config option to allow r/w access to mods which contain +-- this one. It only avoids a couple warnings, and may not be +-- the behavior we want, so it's disabled by default. +local allow_parents=false + +local lfs = require "lfs" + +-- Seed the queue with the mods/ directory +local queue={ {"mods"} } + +local function check(dir) + -- Get the string of the directory path + local sdir=table.concat(dir, "/") + -- Save the top-level directory name as a + -- fallback in case there's no mod.conf, + -- or no name= directive. + local name=dir[#dir] + + -- Is there a mod.conf? + if lfs.attributes(sdir.."/mod.conf", "mode") == "file" then + local deps={} + for line in io.lines(sdir.."/mod.conf") do + -- Use name= if it's there + name=string.match(line, "name *= *([a-zA-Z0-9_]+)") or name + -- Get the dependency entries (if they're there) + local ents=string.match(line, "depends *=(.*)$") + if ents then + -- Split them in to the comma-separated names + for m in string.gmatch(ents, "([a-zA-Z0-9_]+),?") do + table.insert(deps, m) + end + end + end + + local glb={ name } + if allow_parents then + for _, v in pairs(dir) do + -- Skip ALL-CAPS names since those tend + -- to be collections of mods instead of + -- mods themselves. + if not string.match(v, "^[A-Z]+$") then + table.insert(glb, v) + end + end + end + + -- Tell Luacheck what the directory is allowed to do + files[sdir]={ + globals = glb, + read_globals = deps, + } + elseif lfs.attributes(sdir.."/init.lua", "mode") == "file" then + -- No mod.conf, but there's an init.lua here. + local glb={ name } + if allow_parents then + for _, v in pairs(dir) do + -- Again, skip ALL-CAPS. + if not string.match(v, "^[A-Z]+$") then + table.insert(glb, v) + end + end + end + + files[sdir]={ globals=glb } + end + + -- Queue any child directories + for d in lfs.dir(sdir) do + -- Skip hidden directories and parent/current directories. + if lfs.attributes(sdir.."/"..d, "mode") == "directory" and not string.match(d, "^%.") then + -- Copy dir in to nd (New Dir) + local nd={} + for k, v in pairs(dir) do + nd[k]=v + end + nd[#nd+1]=d + table.insert(queue, nd) + end + end +end + +while #queue > 0 do + -- Pop an entry and process it. + check(table.remove(queue, 1)) +end diff --git a/tools/deps-to-luacheck.awk b/tools/deps-to-luacheck.awk deleted file mode 100644 index 19aab14a..00000000 --- a/tools/deps-to-luacheck.awk +++ /dev/null @@ -1,41 +0,0 @@ -BEGIN { - if (!DIR || !MOD) { - printf("error: DIR and MOD must be set.\n"); - _panic=1; - exit 1; - } - - printf("files[\"" DIR "\"] = { globals = { \"" MOD "\" }"); - - if (!EMPTY) { - printf(", read_globals = { "); - } -}; - -# Without a pattern, this will match on empty lines -# and mess up the entry. We clean up the extra commas -# later in the script. -/.+/{ - # Get rid of the optional (?) mark from - # depends.txt entries. - sub("?$", ""); - - # Some files have CRLF, so get rid of those - # too. - sub("\xd", ""); - - SEP=", "; - if (NR == 1) { - SEP=""; - } - printf(SEP "\"" $1 "\""); -}; - -END { - if (!_panic) { - if (!EMPTY) { - printf(" }"); - } - printf(" }\n"); - } -}; diff --git a/tools/make-luacheck-files.sh b/tools/make-luacheck-files.sh deleted file mode 100755 index 507d6e93..00000000 --- a/tools/make-luacheck-files.sh +++ /dev/null @@ -1,73 +0,0 @@ -#!/bin/sh -# -# make-luacheck-files.sh -# v1 - E - Initial version -# v2 - E - Remove (most) inline scripts - -set -ue - -if [ ! -d "mods" ] || [ ! -r ".luacheck.head" ]; then - printf "error: this script needs to be run from the mineclonia project root\n" 1>&2 - exit 1 -fi - -HEADER=' -------------------------------------------------------------------- --- THIS FILE WAS AUTOGENERATED BY tools/make-luacheck-files.sh ! -- --- DO NOT EDIT BY HAND. YOUR CHANGES WILL BE LOST NEXT RUN! -- -------------------------------------------------------------------- - -' - -# This takes any line that contains 'depends' and an equal sign -# and spits out each (comma-separated) entry on its own line. -modconf2deps() { - sed -n -r -e ' - # Match any lines like "depends = asdfada" - /depends *=/{ - # Get rid of the "depends =" part - s/.*depends *=//; - # Convert commas to newlines - s/, */\n/g; - # Record the output - p; - }' -} - -find mods -type d -print | while read -r DIR; do - if [ -r "$DIR/depends.txt" ]; then - printf "found: %s (%s)\n" "$DIR" "depends.txt" 1>&2 - # depends.txt is a simple newline-delimited file, - # so we can just read it in. - DEPS="$(cat "$DIR/depends.txt")" - elif [ -r "$DIR/mod.conf" ]; then - printf "found: %s (%s)\n" "$DIR" "mod.conf" 1>&2 - # mod.conf needs some more help to get usable - # data out of it. - DEPS="$(modconf2deps < "$DIR/mod.conf")" - else - # Empty dir, or not a mod dir. - continue - fi - - EMPTY=0 - if [ -z "$DEPS" ]; then - EMPTY=1 - fi - - # Get only the last chunk of the directory - # for the mod name. - MOD="${DIR##*/}" - - # Now we run through it through the formatter - awk \ - -v DIR="$DIR" \ - -v EMPTY="$EMPTY" \ - -v MOD="$MOD" \ - -f tools/deps-to-luacheck.awk <<-EOF - $DEPS - EOF -done > .luacheck.files - -# Put the final thing together with the warning header -{ printf "%s" "$HEADER"; cat .luacheck.head .luacheck.files; } > .luacheckrc