function append(line) { if (doc) { doc = doc "\n" } doc = doc line } function eval(alias, target) { print alias "() { " target " \"${@}\"; }" } function output(name, type) { print "↙ " type print name print doc exit } function reset() { if (f == "") { doc = "" } } BEGIN { RE_ANY = "(.*)" RE_BEGIN = "^" RE_CONST = "([_A-Z][_0-9A-Z]*)" RE_SET = "=.*" RE_SPACE = "[[:space:]]" RE_VAR = "([_a-z][_0-9a-z]*)" RE_SPACES = RE_SPACE "*" RE_END = RE_SPACES "$" RE_FUNC = RE_SPACES "\\(" RE_SPACES "\\)" RE_SPACES "{" RE_ALIAS = RE_BEGIN "#=" RE_SPACES RE_VAR RE_END RE_BINARY = RE_BEGIN "#\\|" RE_SPACES RE_VAR RE_END RE_CLOSE = RE_BEGIN "}" RE_SPACES RE_END RE_COMMAND = RE_BEGIN "#/" RE_SPACES RE_VAR RE_END RE_CONSTANT = RE_BEGIN RE_CONST RE_SET RE_END RE_DOC = RE_BEGIN RE_SPACES "#" RE_SPACE RE_ANY RE_END RE_FUNCTION = RE_BEGIN RE_VAR RE_FUNC RE_END RE_MODULE = RE_BEGIN "#." RE_SPACES RE_ANY RE_END RE_SHEBANG = RE_BEGIN "#!" RE_SPACES RE_ANY RE_END RE_VARIABLE = RE_BEGIN RE_VAR RE_SET RE_END match_alias = 0 command = 0 f = "" reset() module = 0 } { if (action == "aliases") { if (match($0, RE_ALIAS, m)) { print m[1] } } else if (action == "binaries") { if (match($0, RE_BINARY, m)) { binaries[m[1]] = "" } } else if (action == "commands") { if (match($0, RE_COMMAND, m)) { print m[1] } } else if (action == "constants") { if (match($0, RE_CONSTANT, m)) { print m[1] } } else if (action == "functions") { if (match($0, RE_FUNCTION, m)) { print m[1] } } else if (action == "variables") { if (match($0, RE_VARIABLE, m)) { print m[1] } } else if (action == "aliases functions") { if (match($0, RE_ALIAS, m)) { append(m[1]) } else if (match($0, RE_FUNCTION, m)) { split(doc, array, "\n") for (item in array) { eval(array[item], m[1]) } reset() } else { reset() } } else if (action == "commands functions") { if (match($0, RE_COMMAND, m)) { append(m[1]) } else if (match($0, RE_FUNCTION, m)) { split(doc, array, "\n") for (item in array) { eval(array[item], m[1]) } reset() } else { reset() } } else if (action == "command function") { if (match($0, RE_COMMAND, m)) { append(m[1]) } else if (match($0, RE_FUNCTION, m)) { split(doc, array, "\n") for (item in array) { if (item == target) { print m[1] exit } } reset() } else { reset() } } else if (action == "doc") { # doc if (match($0, RE_SHEBANG, m)) { append("! " m[1]) } else if (match($0, RE_DOC, m)) { if (f) { append($0) } else { append(m[1]) } } else if (match($0, RE_ALIAS, m)) { append("= " m[1]) if (m[1] == target) { match_alias = 1 } } else if (match($0, RE_COMMAND, m)) { append("/ " m[1]) if (m[1] == target) { command = 1 } # set } else if (match($0, RE_CONSTANT, m)) { if (m[1] == target) { output(m[1], "constant") } else { reset() } } else if (match($0, RE_VARIABLE, m)) { if (m[1] == target) { output(m[1], "variable") } else { reset() } # others } else if (match($0, RE_MODULE, m)) { reset() if (m[1] == target) { module = 1 } } else if (match($0, RE_FUNCTION, m)) { f = m[1] } else if (match($0, RE_CLOSE, m)) { if (match_alias) { print "= " target output(f, "function") } else if (command) { print "/ " target output(f, "function") } else if (f == target) { output(f, "function") } else { f = "" reset() } } else { if (module) { output(target, "module") } else { reset() } } } } END { if (action == "binaries") { for (binary in binaries) { print binary } } }