Klammerset: the @@@klammerset construct, its search path, and const correctness
The @@@klammerset system command formally declares a klammerset — a named, logically related group of klammer definitions — with an operative, idempotent declaration (:requires and :files load in order at the declaration point, relative to the declaring file). A bare symbol given to ktext -k, kdesc --input, or :requires resolves to x/x.k on the search path: the document's directory, then KLAMMERTEXT_KLAMMERSETS, then KLAMMERTEXT_HOME; kdesc --klammerset lists the available sets. sks/sks.k is the first declared klammerset, so `-k sks` loads the SKS by name. The engine's lookup classes were renamed *_set → *_registry to keep the two concepts apart, and the whole C++ tree now follows standard const-correctness conventions. tst/ gains klammerset_test.sh (18 cases). (from dev 64b1abf23e56)
This commit is contained in:
@@ -41,7 +41,7 @@ are regenerated on each release — patches cannot be merged directly.
|
|||||||
Report problems (or send patches) to the author; accepted changes are
|
Report problems (or send patches) to the author; accepted changes are
|
||||||
applied to the development tree and appear in a following snapshot.
|
applied to the development tree and appear in a following snapshot.
|
||||||
|
|
||||||
This snapshot was assembled from development commit `15b822f06ee0`.
|
This snapshot was assembled from development commit `64b1abf23e56`.
|
||||||
|
|
||||||
## License
|
## License
|
||||||
|
|
||||||
|
|||||||
@@ -5,7 +5,8 @@
|
|||||||
#include "font_store.h"
|
#include "font_store.h"
|
||||||
#include "ktype.h"
|
#include "ktype.h"
|
||||||
#include "log.h"
|
#include "log.h"
|
||||||
#include "argtype_set.h"
|
#include "argtype_registry.h"
|
||||||
|
#include "klammerset_registry.h"
|
||||||
#include "character.h"
|
#include "character.h"
|
||||||
#include "show.h"
|
#include "show.h"
|
||||||
#include "util.h"
|
#include "util.h"
|
||||||
@@ -32,6 +33,37 @@ static void font_usage()
|
|||||||
"and then in the default font set.\n";
|
"and then in the default font set.\n";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void klammerset_usage()
|
||||||
|
{
|
||||||
|
std::cout <<
|
||||||
|
"Klammerset commands:\n"
|
||||||
|
" --klammerset List the klammersets on the search path\n"
|
||||||
|
" --klammerset list The same\n"
|
||||||
|
" --klammerset help This description\n"
|
||||||
|
"\n"
|
||||||
|
"A klammerset symbol x names the declaration file x/x.k, searched for in:\n"
|
||||||
|
"the current directory (for ktext, the input document's directory), the\n"
|
||||||
|
"KLAMMERTEXT_KLAMMERSETS directories (colon-separated; default\n"
|
||||||
|
"$HOME/.klammertext/klammersets), and $KLAMMERTEXT_HOME. The first hit\n"
|
||||||
|
"wins, so a document-local klammerset shadows an installed one, which\n"
|
||||||
|
"shadows a distributed one.\n";
|
||||||
|
}
|
||||||
|
|
||||||
|
static void klammerset_command(const strings_t& words)
|
||||||
|
{
|
||||||
|
std::string verb = words.empty() ? "list" : words[0];
|
||||||
|
if (verb == "list") {
|
||||||
|
std::cout << boldblack << "Klammersets\n" << black
|
||||||
|
<< describe_klammerset_search(fs::current_path().string());
|
||||||
|
} else if (verb == "help") {
|
||||||
|
klammerset_usage();
|
||||||
|
} else {
|
||||||
|
std::cout << "Unrecognized klammerset command: --klammerset "
|
||||||
|
<< join(words, " ") << "\n\n";
|
||||||
|
klammerset_usage();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static void font_command(const strings_t& words)
|
static void font_command(const strings_t& words)
|
||||||
{
|
{
|
||||||
std::string verb = words.empty() ? "list" : words[0];
|
std::string verb = words.empty() ? "list" : words[0];
|
||||||
@@ -70,13 +102,14 @@ int main(int argc, char* argv[])
|
|||||||
args.flag("targets", "Show targets defined by the input file");
|
args.flag("targets", "Show targets defined by the input file");
|
||||||
args.flag("klammers", "Show klammers defined by the input file");
|
args.flag("klammers", "Show klammers defined by the input file");
|
||||||
args.var("font", "List installed fonts. Enter \"--font help\" for font maintenance commands.");
|
args.var("font", "List installed fonts. Enter \"--font help\" for font maintenance commands.");
|
||||||
|
args.var("klammerset", "List the klammersets on the search path. Enter \"--klammerset help\" for details.");
|
||||||
args.opt("v", "'verbosity'", "n", "0", "'verbosity'");
|
args.opt("v", "'verbosity'", "n", "0", "'verbosity'");
|
||||||
|
|
||||||
if (show_usage(argc, argv)) {
|
if (show_usage(argc, argv)) {
|
||||||
args.usage(file_basename(argv[0]));
|
args.usage(file_basename(argv[0]));
|
||||||
exit(1);
|
exit(1);
|
||||||
}
|
}
|
||||||
auto p = [&](std::string name) { return args.get(name) == "true"; };
|
auto p = [&](const std::string& name) { return args.get(name) == "true"; };
|
||||||
|
|
||||||
args.parse(argc, argv);
|
args.parse(argc, argv);
|
||||||
verbose_level = stoi(args.get("v"));
|
verbose_level = stoi(args.get("v"));
|
||||||
@@ -90,7 +123,7 @@ int main(int argc, char* argv[])
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (p("a")) {
|
if (p("a")) {
|
||||||
Argtype_set argtypes;
|
Argtype_registry argtypes;
|
||||||
std::cout << boldblack << "\nStandard klammer argument types\n" << black;
|
std::cout << boldblack << "\nStandard klammer argument types\n" << black;
|
||||||
std::cout << argtypes.describe() << "\n";
|
std::cout << argtypes.describe() << "\n";
|
||||||
}
|
}
|
||||||
@@ -116,6 +149,19 @@ int main(int argc, char* argv[])
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// The --klammerset subcommands operate on the search path
|
||||||
|
// (filesystem enumeration) and load no klammer set.
|
||||||
|
if (args.given("klammerset")) {
|
||||||
|
strings_t words {};
|
||||||
|
for (const std::string& w : args.as_vector("klammerset")) {
|
||||||
|
if (!w.empty()) {
|
||||||
|
words.push_back(w);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
klammerset_command(words);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
Machine M;
|
Machine M;
|
||||||
|
|
||||||
strings_t input_filenames = resolve_filename_list(args.get("input"));
|
strings_t input_filenames = resolve_filename_list(args.get("input"));
|
||||||
@@ -124,6 +170,13 @@ int main(int argc, char* argv[])
|
|||||||
M.read(fs::path(M.m_state.value("KLAMMERTEXT_HOME") + "/sks/sks.k"));
|
M.read(fs::path(M.m_state.value("KLAMMERTEXT_HOME") + "/sks/sks.k"));
|
||||||
} else {
|
} else {
|
||||||
for (auto fname : input_filenames) {
|
for (auto fname : input_filenames) {
|
||||||
|
if (is_klammerset_symbol(fname)) {
|
||||||
|
// A bare symbol resolves on the klammerset search
|
||||||
|
// path; kdesc has no input document, so the local
|
||||||
|
// stage is the cwd.
|
||||||
|
fname = resolve_klammerset_symbol(
|
||||||
|
fname, fs::current_path().string(), Locator()).string();
|
||||||
|
}
|
||||||
std::cout << "Read " << fname << "\n";
|
std::cout << "Read " << fname << "\n";
|
||||||
M.read(fs::path(absolute_pathname(fname)));
|
M.read(fs::path(absolute_pathname(fname)));
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -45,7 +45,7 @@ int main(int argc, char* argv[])
|
|||||||
args.usage(file_basename(argv[0]));
|
args.usage(file_basename(argv[0]));
|
||||||
exit(1);
|
exit(1);
|
||||||
}
|
}
|
||||||
auto p = [&](std::string name) { return args.get(name) == "true"; };
|
auto p = [&](const std::string& name) { return args.get(name) == "true"; };
|
||||||
|
|
||||||
args.parse(argc, argv);
|
args.parse(argc, argv);
|
||||||
verbose_level = args.as_int("v");
|
verbose_level = args.as_int("v");
|
||||||
|
|||||||
@@ -7,7 +7,8 @@
|
|||||||
#include "util.h"
|
#include "util.h"
|
||||||
#include "machine.h"
|
#include "machine.h"
|
||||||
#include "show.h"
|
#include "show.h"
|
||||||
#include "target_set.h"
|
#include "target_registry.h"
|
||||||
|
#include "klammerset_registry.h"
|
||||||
|
|
||||||
int main(int argc, char* argv[])
|
int main(int argc, char* argv[])
|
||||||
{
|
{
|
||||||
@@ -17,10 +18,10 @@ int main(int argc, char* argv[])
|
|||||||
args.req("filenames", "Input files in Klammertext format. ", "'list'");
|
args.req("filenames", "Input files in Klammertext format. ", "'list'");
|
||||||
args.opt("s", "Text processed before input files.", "input-string", "", "'text'");
|
args.opt("s", "Text processed before input files.", "input-string", "", "'text'");
|
||||||
args.opt("t","Output target; default is general (unspecified)", "target",
|
args.opt("t","Output target; default is general (unspecified)", "target",
|
||||||
Target_set::general_name, "'word'");
|
Target_registry::general_name, "'word'");
|
||||||
args.opt("o", "Output basename; meaning and default defined by target.", "basename",
|
args.opt("o", "Output basename; meaning and default defined by target.", "basename",
|
||||||
"", "'word'");
|
"", "'word'");
|
||||||
args.opt("k", "File containing the klammerset definition; default is the Standard Klammer Set. With a value of \"none\", no klammerset is loaded.",
|
args.opt("k", "Klammerset symbol (resolved on the klammerset search path) or the pathname of a klammerset definition file; default is the Standard Klammer Set. With a value of \"none\", no klammerset is loaded.",
|
||||||
"pathname", "", "'word'");
|
"pathname", "", "'word'");
|
||||||
args.flag("d", "Display the output to the screen, rather than writing files.");
|
args.flag("d", "Display the output to the screen, rather than writing files.");
|
||||||
args.flag("m", "Show the Klammermachine state at the beginning of processing.");
|
args.flag("m", "Show the Klammermachine state at the beginning of processing.");
|
||||||
@@ -83,6 +84,12 @@ int main(int argc, char* argv[])
|
|||||||
if (klammerset_filename != "none") {
|
if (klammerset_filename != "none") {
|
||||||
if (klammerset_filename.empty()) {
|
if (klammerset_filename.empty()) {
|
||||||
klammerset_filename = M.m_state.value("KLAMMERTEXT_HOME") + "/sks/sks.k";
|
klammerset_filename = M.m_state.value("KLAMMERTEXT_HOME") + "/sks/sks.k";
|
||||||
|
} else if (is_klammerset_symbol(klammerset_filename)) {
|
||||||
|
// A bare symbol resolves on the klammerset search path;
|
||||||
|
// the local stage is the input document's directory (the
|
||||||
|
// cwd when the input is a string).
|
||||||
|
klammerset_filename = resolve_klammerset_symbol(
|
||||||
|
klammerset_filename, M.m_state.value("K_input_dir"), Locator()).string();
|
||||||
}
|
}
|
||||||
K::log(1, "Reading klammerset filename: " + klammerset_filename);
|
K::log(1, "Reading klammerset filename: " + klammerset_filename);
|
||||||
M.read(fs::path(klammerset_filename));
|
M.read(fs::path(klammerset_filename));
|
||||||
|
|||||||
@@ -151,6 +151,35 @@ in the package folder (its name is shown at **Preferences → Settings** under
|
|||||||
`color_scheme`), choosing a light or dark source file to match the ground. The
|
`color_scheme`), choosing a light or dark source file to match the ground. The
|
||||||
exact values are in each file's header comment.
|
exact values are in each file's header comment.
|
||||||
|
|
||||||
|
## Sublime Merge
|
||||||
|
|
||||||
|
Sublime Merge reads the same `Packages` directory as Sublime Text, so the
|
||||||
|
package installed above needs no separate installation: `.kt` and `.k` files
|
||||||
|
are syntax-highlighted in Merge's diffs, and an edit to the syntax file is
|
||||||
|
picked up live, exactly as in the editor.
|
||||||
|
|
||||||
|
Only the syntax file crosses over. Merge has no Python plugin host — it
|
||||||
|
ships no `plugin_host` binary — so none of this package's code runs there:
|
||||||
|
|
||||||
|
| File | In Sublime Merge |
|
||||||
|
|------|------------------|
|
||||||
|
| `Klammertext.sublime-syntax` | Works. Delimiters and removed text are colored in diffs. |
|
||||||
|
| `Klammertext.py`, `Klammertext_indent.py`, `Klammertext_align.py` | Do not run: no plugin host. |
|
||||||
|
| `Default.sublime-keymap` | Inactive — it binds plugin commands. |
|
||||||
|
| `Comments.tmPreferences` | Inactive — Merge does not edit text. |
|
||||||
|
| `Breakers` / `Celeste` / `Mariana` / `Monokai` / `Sixteen` `.sublime-color-scheme` | Not used. They override Sublime Text's built-in schemes by name; Merge has its own. |
|
||||||
|
|
||||||
|
So delimiter matching — **Ctrl+M** and the live highlight of the matching
|
||||||
|
delimiter — is a Sublime Text feature only. Merge colors the delimiters but
|
||||||
|
cannot match them: matching is context-sensitive code, not a syntax rule
|
||||||
|
(which is why it is a plugin in the first place). Merge's built-in bracket
|
||||||
|
matching does not stand in for it either; that matches literal `(`, `[`, `{`
|
||||||
|
characters, not `@name ... name@` runs.
|
||||||
|
|
||||||
|
Merge colors the Klammertext scopes with its own scheme, so the hues differ
|
||||||
|
from the editor's — the token classes are distinguished, but the package's
|
||||||
|
five color schemes do not apply.
|
||||||
|
|
||||||
## Keeping literal klammers in sync
|
## Keeping literal klammers in sync
|
||||||
|
|
||||||
Klammers whose content is verbatim (`@code ... code@`) are listed in the
|
Klammers whose content is verbatim (`@code ... code@`) are listed in the
|
||||||
|
|||||||
@@ -8,9 +8,9 @@ include $(K)/env/makefile.env
|
|||||||
|
|
||||||
# Source files
|
# Source files
|
||||||
BASENAMES := util error locator file argv character ktype katom katom_list \
|
BASENAMES := util error locator file argv character ktype katom katom_list \
|
||||||
log show command argument argument_set argtype argtype_set \
|
log show command argument argument_set argtype argtype_registry \
|
||||||
state eval eval_python eval_cpp klammer klammer_set deftype \
|
state eval eval_python eval_cpp klammer klammer_registry klammerset klammerset_registry deftype \
|
||||||
target target_set machine font_store
|
target target_registry machine font_store
|
||||||
|
|
||||||
SOURCES := $(addsuffix .cpp,$(BASENAMES))
|
SOURCES := $(addsuffix .cpp,$(BASENAMES))
|
||||||
OBJECTS := $(addsuffix .o,$(BASENAMES))
|
OBJECTS := $(addsuffix .o,$(BASENAMES))
|
||||||
|
|||||||
@@ -6,9 +6,10 @@
|
|||||||
#include "error.h"
|
#include "error.h"
|
||||||
#include "util.h"
|
#include "util.h"
|
||||||
|
|
||||||
Argtype::Argtype(std::string name, std::string desc, std::string symbolic_pattern, std::string pattern,
|
Argtype::Argtype(const std::string& name, const std::string& desc, const std::string& symbolic_pattern,
|
||||||
std::string default_value, std::string alone_value,
|
const std::string& pattern,
|
||||||
std::string python_cast, modify_string_f python_format,
|
const std::string& default_value, const std::string& alone_value,
|
||||||
|
const std::string& python_cast, const modify_string_f& python_format,
|
||||||
const Locator& loc)
|
const Locator& loc)
|
||||||
: m_name(name)
|
: m_name(name)
|
||||||
, m_desc(desc)
|
, m_desc(desc)
|
||||||
|
|||||||
@@ -25,9 +25,10 @@ public:
|
|||||||
, m_loc()
|
, m_loc()
|
||||||
{};
|
{};
|
||||||
|
|
||||||
Argtype(std::string name, std::string desc, std::string symbolic_pattern, std::string pattern,
|
Argtype(const std::string& name, const std::string& desc, const std::string& symbolic_pattern,
|
||||||
std::string default_value, std::string alone_value,
|
const std::string& pattern,
|
||||||
std::string python_cast, modify_string_f python_format,
|
const std::string& default_value, const std::string& alone_value,
|
||||||
|
const std::string& python_cast, const modify_string_f& python_format,
|
||||||
const Locator& loc);
|
const Locator& loc);
|
||||||
|
|
||||||
std::string python_value(const std::string& var_name, std::vector<std::string> value, size_t name_size);
|
std::string python_value(const std::string& var_name, std::vector<std::string> value, size_t name_size);
|
||||||
|
|||||||
@@ -3,7 +3,7 @@
|
|||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
#include <numeric>
|
#include <numeric>
|
||||||
|
|
||||||
#include "argtype_set.h"
|
#include "argtype_registry.h"
|
||||||
#include "error.h"
|
#include "error.h"
|
||||||
#include "show.h"
|
#include "show.h"
|
||||||
#include "log.h"
|
#include "log.h"
|
||||||
@@ -11,13 +11,13 @@
|
|||||||
#include "character.h"
|
#include "character.h"
|
||||||
#include "katom.h"
|
#include "katom.h"
|
||||||
|
|
||||||
Parameter_set& Argtype_set::parameters()
|
Parameter_set& Argtype_registry::parameters()
|
||||||
{
|
{
|
||||||
static Parameter_set instance("name | desc :pattern .* :python_cast str :default :alone");
|
static Parameter_set instance("name | desc :pattern .* :python_cast str :default :alone");
|
||||||
return instance;
|
return instance;
|
||||||
}
|
}
|
||||||
|
|
||||||
Argtype_set::Argtype_set()
|
Argtype_registry::Argtype_registry()
|
||||||
{
|
{
|
||||||
(void)(void)K::log(2);
|
(void)(void)K::log(2);
|
||||||
Locator loc = current_locator();
|
Locator loc = current_locator();
|
||||||
@@ -33,7 +33,7 @@ Argtype_set::Argtype_set()
|
|||||||
m_types["bool"].m_alone = "true";
|
m_types["bool"].m_alone = "true";
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string Argtype_set::replace_symbols(const std::string& pattern, const Locator& loc)
|
std::string Argtype_registry::replace_symbols(const std::string& pattern, const Locator& loc)
|
||||||
{
|
{
|
||||||
std::smatch match {};
|
std::smatch match {};
|
||||||
std::regex symbol_pat(R"('(\w+)')");
|
std::regex symbol_pat(R"('(\w+)')");
|
||||||
@@ -54,7 +54,7 @@ std::string Argtype_set::replace_symbols(const std::string& pattern, const Locat
|
|||||||
return expanded;
|
return expanded;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Argtype_set::check_for_existing_definition(
|
void Argtype_registry::check_for_existing_definition(
|
||||||
const std::string& name, const Locator& loc)
|
const std::string& name, const Locator& loc)
|
||||||
{
|
{
|
||||||
if (count(m_names.begin(), m_names.end(), name) > 0) {
|
if (count(m_names.begin(), m_names.end(), name) > 0) {
|
||||||
@@ -65,7 +65,7 @@ void Argtype_set::check_for_existing_definition(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void Argtype_set::add(const std::string& name, const std::string& desc,
|
void Argtype_registry::add(const std::string& name, const std::string& desc,
|
||||||
const std::string& pattern, const std::string& default_value,
|
const std::string& pattern, const std::string& default_value,
|
||||||
const std::string& alone_value,
|
const std::string& alone_value,
|
||||||
const std::string& python_cast, modify_string_f python_format,
|
const std::string& python_cast, modify_string_f python_format,
|
||||||
@@ -130,15 +130,15 @@ void Argtype_set::add(const std::string& name, const std::string& desc,
|
|||||||
m_names.push_back(name);
|
m_names.push_back(name);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Argtype_set::add(std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end, std::vector<Katom>& katoms)
|
void Argtype_registry::add(std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end, std::vector<Katom>& katoms)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
auto [positional, optional, rest] =
|
auto [positional, optional, rest] =
|
||||||
argument_split(begin + 1, end - 1); //, Argtype_set::parameters.m_positional.size());
|
argument_split(begin + 1, end - 1); //, Argtype_registry::parameters.m_positional.size());
|
||||||
|
|
||||||
check_for_existing_definition(positional[0][0].m_text, begin->m_loc);
|
check_for_existing_definition(positional[0][0].m_text, begin->m_loc);
|
||||||
|
|
||||||
auto values = Argtype_set::parameters().value_map(positional, optional, rest, begin->m_loc);
|
auto values = Argtype_registry::parameters().value_map(positional, optional, rest, begin->m_loc);
|
||||||
|
|
||||||
// std::for_each(begin, end+1, [](Katom& k) { k.m_type = katom_t::replaced; });
|
// std::for_each(begin, end+1, [](Katom& k) { k.m_type = katom_t::replaced; });
|
||||||
|
|
||||||
@@ -151,7 +151,7 @@ void Argtype_set::add(std::vector<Katom>::iterator begin, std::vector<Katom>::it
|
|||||||
ignore_whitespace(next_iter, katoms);
|
ignore_whitespace(next_iter, katoms);
|
||||||
}
|
}
|
||||||
|
|
||||||
Argtype Argtype_set::get(const std::string& name, const Locator& loc) const
|
Argtype Argtype_registry::get(const std::string& name, const Locator& loc) const
|
||||||
{
|
{
|
||||||
if (is_not_in(name, m_names)) {
|
if (is_not_in(name, m_names)) {
|
||||||
std::stringstream msg {};
|
std::stringstream msg {};
|
||||||
@@ -162,7 +162,7 @@ Argtype Argtype_set::get(const std::string& name, const Locator& loc) const
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
std::string Argtype_set::eval(
|
std::string Argtype_registry::eval(
|
||||||
const std::string& value, const std::string& type_name, const Locator& loc)
|
const std::string& value, const std::string& type_name, const Locator& loc)
|
||||||
{
|
{
|
||||||
std::regex re = m_types[type_name].m_regex;
|
std::regex re = m_types[type_name].m_regex;
|
||||||
@@ -193,7 +193,7 @@ static std::string values_note(const Argtype& type)
|
|||||||
return note.str();
|
return note.str();
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string Argtype_set::describe(bool long_form, int indent_width) const
|
std::string Argtype_registry::describe(bool long_form, int indent_width) const
|
||||||
{
|
{
|
||||||
std::string indent(' ', indent_width);
|
std::string indent(' ', indent_width);
|
||||||
std::size_t name_width = std::accumulate(
|
std::size_t name_width = std::accumulate(
|
||||||
@@ -8,12 +8,12 @@
|
|||||||
#include "katom.h"
|
#include "katom.h"
|
||||||
#include "argument_set.h"
|
#include "argument_set.h"
|
||||||
|
|
||||||
class Argtype_set
|
class Argtype_registry
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
static Parameter_set& parameters();
|
static Parameter_set& parameters();
|
||||||
|
|
||||||
Argtype_set();
|
Argtype_registry();
|
||||||
|
|
||||||
std::string replace_symbols(const std::string& pattern, const Locator& loc);
|
std::string replace_symbols(const std::string& pattern, const Locator& loc);
|
||||||
void check_for_existing_definition(const std::string& name, const Locator& loc);
|
void check_for_existing_definition(const std::string& name, const Locator& loc);
|
||||||
@@ -29,7 +29,7 @@ public:
|
|||||||
std::string eval(const std::string& value, const std::string& type_name, const Locator& loc);
|
std::string eval(const std::string& value, const std::string& type_name, const Locator& loc);
|
||||||
std::string describe(bool long_form=false, int indent_width=4) const;
|
std::string describe(bool long_form=false, int indent_width=4) const;
|
||||||
|
|
||||||
inline bool is_defined(std::string name) {
|
inline bool is_defined(const std::string& name) const {
|
||||||
return count(m_names.begin(), m_names.end(), name) > 0;
|
return count(m_names.begin(), m_names.end(), name) > 0;
|
||||||
}
|
}
|
||||||
std::vector<std::string> m_names {};
|
std::vector<std::string> m_names {};
|
||||||
@@ -1,8 +1,8 @@
|
|||||||
#include "argument.h"
|
#include "argument.h"
|
||||||
#include "argtype.h"
|
#include "argtype.h"
|
||||||
|
|
||||||
Parameter::Parameter(const std::string& name, Argtype argtype, const Locator& loc,
|
Parameter::Parameter(const std::string& name, const Argtype& argtype, const Locator& loc,
|
||||||
bool optional, std::string default_value)
|
bool optional, const std::string& default_value)
|
||||||
: m_name(name)
|
: m_name(name)
|
||||||
, m_argtype(argtype)
|
, m_argtype(argtype)
|
||||||
, m_optional(optional)
|
, m_optional(optional)
|
||||||
|
|||||||
@@ -19,11 +19,10 @@ public:
|
|||||||
, m_target()
|
, m_target()
|
||||||
{};
|
{};
|
||||||
|
|
||||||
Parameter(const std::string& name, Argtype argtype, const Locator& loc,
|
Parameter(const std::string& name, const Argtype& argtype, const Locator& loc,
|
||||||
bool optional=false, std::string default_value = "");
|
bool optional=false, const std::string& default_value = "");
|
||||||
~Parameter() = default;
|
~Parameter() = default;
|
||||||
|
|
||||||
std::string python_value(std::string value);
|
|
||||||
bool undefined() const { return m_name == "_default"; };
|
bool undefined() const { return m_name == "_default"; };
|
||||||
|
|
||||||
std::string m_name {};
|
std::string m_name {};
|
||||||
|
|||||||
@@ -5,7 +5,7 @@
|
|||||||
#include "show.h"
|
#include "show.h"
|
||||||
#include "log.h"
|
#include "log.h"
|
||||||
#include "katom.h"
|
#include "katom.h"
|
||||||
#include "argtype_set.h"
|
#include "argtype_registry.h"
|
||||||
#include "argument_set.h"
|
#include "argument_set.h"
|
||||||
#include "util.h"
|
#include "util.h"
|
||||||
|
|
||||||
@@ -36,7 +36,7 @@ std::regex parameter_regex(bool optional=false)
|
|||||||
// rest(2): the base type is copied, its type parameter set, and its
|
// rest(2): the base type is copied, its type parameter set, and its
|
||||||
// display name extended, so kdesc signatures show rows.rest(2).
|
// display name extended, so kdesc signatures show rows.rest(2).
|
||||||
static Argtype resolve_argtype(
|
static Argtype resolve_argtype(
|
||||||
const std::string& type_text, const Argtype_set& argtypes, const Locator& loc)
|
const std::string& type_text, const Argtype_registry& argtypes, const Locator& loc)
|
||||||
{
|
{
|
||||||
static const std::regex parameterized(R"((\w+)\((\d+)\))");
|
static const std::regex parameterized(R"((\w+)\((\d+)\))");
|
||||||
std::smatch match {};
|
std::smatch match {};
|
||||||
@@ -58,7 +58,7 @@ static bool is_rest(const Argtype& argtype)
|
|||||||
Parameter_set::Parameter_set(const std::string parameter_string)
|
Parameter_set::Parameter_set(const std::string parameter_string)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
Argtype_set argtypes {};
|
Argtype_registry argtypes {};
|
||||||
parse_parameters(
|
parse_parameters(
|
||||||
katomize(line_split(parameter_string), Locator().str()),
|
katomize(line_split(parameter_string), Locator().str()),
|
||||||
argtypes);
|
argtypes);
|
||||||
@@ -69,11 +69,11 @@ Parameter_set::Parameter_set(const std::vector<Katom>& katoms)
|
|||||||
: m_katoms(katoms)
|
: m_katoms(katoms)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
Argtype_set argtypes {};
|
Argtype_registry argtypes {};
|
||||||
parse_parameters(m_katoms, argtypes);
|
parse_parameters(m_katoms, argtypes);
|
||||||
}
|
}
|
||||||
|
|
||||||
Parameter_set::Parameter_set(const std::vector<Katom>& katoms, const Argtype_set& argtypes)
|
Parameter_set::Parameter_set(const std::vector<Katom>& katoms, const Argtype_registry& argtypes)
|
||||||
: m_katoms(katoms)
|
: m_katoms(katoms)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
@@ -82,7 +82,7 @@ Parameter_set::Parameter_set(const std::vector<Katom>& katoms, const Argtype_set
|
|||||||
|
|
||||||
// Parameter parsing
|
// Parameter parsing
|
||||||
|
|
||||||
Parameter parse_positional_parameter(const katom_list& katoms, const Argtype_set& argtypes)
|
Parameter parse_positional_parameter(const katom_list& katoms, const Argtype_registry& argtypes)
|
||||||
{
|
{
|
||||||
// (void)K::log(3, katoms);
|
// (void)K::log(3, katoms);
|
||||||
if (katoms.size() > 1) {
|
if (katoms.size() > 1) {
|
||||||
@@ -110,7 +110,7 @@ Parameter parse_positional_parameter(const katom_list& katoms, const Argtype_set
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
Parameter parse_optional_parameter(const katom_list& katoms, const Argtype_set& argtypes)
|
Parameter parse_optional_parameter(const katom_list& katoms, const Argtype_registry& argtypes)
|
||||||
{
|
{
|
||||||
//(void)K::log(3);
|
//(void)K::log(3);
|
||||||
Katom k = katoms[0];
|
Katom k = katoms[0];
|
||||||
@@ -242,7 +242,7 @@ parameter_split(katom_list::const_iterator kbegin, katom_list::const_iterator ke
|
|||||||
return {positional, optional};
|
return {positional, optional};
|
||||||
}
|
}
|
||||||
|
|
||||||
void Parameter_set::parse_parameters(const katom_list& katoms, const Argtype_set& argtypes)
|
void Parameter_set::parse_parameters(const katom_list& katoms, const Argtype_registry& argtypes)
|
||||||
{
|
{
|
||||||
(void)K::log(3, trim(katoms));
|
(void)K::log(3, trim(katoms));
|
||||||
if (katoms.empty()) {
|
if (katoms.empty()) {
|
||||||
@@ -274,10 +274,10 @@ void Parameter_set::parse_parameters(const katom_list& katoms, const Argtype_set
|
|||||||
}
|
}
|
||||||
|
|
||||||
void describe_arguments(
|
void describe_arguments(
|
||||||
std::string label,
|
const std::string& label,
|
||||||
std::vector<std::vector<Katom>> positional,
|
const std::vector<std::vector<Katom>>& positional,
|
||||||
std::vector<std::vector<Katom>> optional,
|
const std::vector<std::vector<Katom>>& optional,
|
||||||
std::vector<Katom> rest)
|
const std::vector<Katom>& rest)
|
||||||
{
|
{
|
||||||
std::cout << label << ":\n"
|
std::cout << label << ":\n"
|
||||||
<< " positional: " << positional << "\n"
|
<< " positional: " << positional << "\n"
|
||||||
|
|||||||
@@ -7,7 +7,7 @@
|
|||||||
#include "argument.h"
|
#include "argument.h"
|
||||||
#include "locator.h"
|
#include "locator.h"
|
||||||
|
|
||||||
class Argtype_set;
|
class Argtype_registry;
|
||||||
|
|
||||||
std::tuple<std::vector<std::vector<Katom>>,std::vector<std::vector<Katom>>,std::vector<Katom>>
|
std::tuple<std::vector<std::vector<Katom>>,std::vector<std::vector<Katom>>,std::vector<Katom>>
|
||||||
argument_split(std::vector<Katom>::const_iterator kbegin, std::vector<Katom>::const_iterator kend,
|
argument_split(std::vector<Katom>::const_iterator kbegin, std::vector<Katom>::const_iterator kend,
|
||||||
@@ -20,9 +20,9 @@ public:
|
|||||||
~Parameter_set() = default;
|
~Parameter_set() = default;
|
||||||
Parameter_set(const std::string parameter_string);
|
Parameter_set(const std::string parameter_string);
|
||||||
Parameter_set(const std::vector<Katom>& katoms);
|
Parameter_set(const std::vector<Katom>& katoms);
|
||||||
Parameter_set(const std::vector<Katom>& katoms, const Argtype_set& argtypes);
|
Parameter_set(const std::vector<Katom>& katoms, const Argtype_registry& argtypes);
|
||||||
|
|
||||||
void parse_parameters(const std::vector<Katom>& katoms, const Argtype_set& argtypes);
|
void parse_parameters(const std::vector<Katom>& katoms, const Argtype_registry& argtypes);
|
||||||
void describe_parameters();
|
void describe_parameters();
|
||||||
|
|
||||||
void check_positional(
|
void check_positional(
|
||||||
@@ -40,7 +40,7 @@ public:
|
|||||||
bool empty() const { return m_katoms.size() == 0; };
|
bool empty() const { return m_katoms.size() == 0; };
|
||||||
|
|
||||||
std::vector<Katom> m_katoms {};
|
std::vector<Katom> m_katoms {};
|
||||||
//Argtype_set m_argtypes {};
|
//Argtype_registry m_argtypes {};
|
||||||
std::vector<Parameter> m_positional {};
|
std::vector<Parameter> m_positional {};
|
||||||
std::vector<Parameter> m_optional {};
|
std::vector<Parameter> m_optional {};
|
||||||
std::vector<std::string> m_optional_names {};
|
std::vector<std::string> m_optional_names {};
|
||||||
@@ -56,10 +56,10 @@ bool operator==(Parameter_set lhs, Parameter_set rhs);
|
|||||||
using Argument_set = Parameter_set;
|
using Argument_set = Parameter_set;
|
||||||
|
|
||||||
void describe_arguments(
|
void describe_arguments(
|
||||||
std::string label,
|
const std::string& label,
|
||||||
std::vector<std::vector<Katom>> positional,
|
const std::vector<std::vector<Katom>>& positional,
|
||||||
std::vector<std::vector<Katom>> optional,
|
const std::vector<std::vector<Katom>>& optional,
|
||||||
std::vector<Katom> rest);
|
const std::vector<Katom>& rest);
|
||||||
|
|
||||||
std::string replace_arguments(
|
std::string replace_arguments(
|
||||||
const std::map<std::string, std::string>& values,
|
const std::map<std::string, std::string>& values,
|
||||||
|
|||||||
@@ -227,7 +227,7 @@ void Argv::usage(const std::string& command)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void Argv::check_flags_and_options(std::string command, strings_t& words)
|
void Argv::check_flags_and_options(const std::string& command, strings_t& words)
|
||||||
{
|
{
|
||||||
std::vector<std::string> not_defined {};
|
std::vector<std::string> not_defined {};
|
||||||
for (auto word : words) {
|
for (auto word : words) {
|
||||||
@@ -334,10 +334,10 @@ void Argv::parse_optional(strings_t& words, string_map& named_args)
|
|||||||
// std::cout << "\n";
|
// std::cout << "\n";
|
||||||
}
|
}
|
||||||
|
|
||||||
void Argv::parse_positional(std::string command, //strings_t words,
|
void Argv::parse_positional(const std::string& command, //strings_t words,
|
||||||
std::string pos_args, string_map& named_args)
|
std::string pos_args, string_map& named_args)
|
||||||
{
|
{
|
||||||
for (std::string req : m_req_names) {
|
for (const std::string& req : m_req_names) {
|
||||||
auto arg = m_args[req];
|
auto arg = m_args[req];
|
||||||
auto [substring, rest, found] = regex_split_prefix(arg.m_rgx, pos_args);
|
auto [substring, rest, found] = regex_split_prefix(arg.m_rgx, pos_args);
|
||||||
if (!found) {
|
if (!found) {
|
||||||
|
|||||||
@@ -62,7 +62,7 @@ public:
|
|||||||
|
|
||||||
void update_width(Arg arg);
|
void update_width(Arg arg);
|
||||||
|
|
||||||
void check_flags_and_options(std::string command, std::vector<std::string>& words);
|
void check_flags_and_options(const std::string& command, std::vector<std::string>& words);
|
||||||
void parse_flags(std::vector<std::string>& words, std::map<std::string, std::string>& named_args);
|
void parse_flags(std::vector<std::string>& words, std::map<std::string, std::string>& named_args);
|
||||||
void parse_optional(std::vector<std::string>& words, std::map<std::string, std::string>& named_args);
|
void parse_optional(std::vector<std::string>& words, std::map<std::string, std::string>& named_args);
|
||||||
void parse_vars(std::vector<std::string>& words, std::map<std::string, std::string>& named_args);
|
void parse_vars(std::vector<std::string>& words, std::map<std::string, std::string>& named_args);
|
||||||
@@ -72,7 +72,7 @@ public:
|
|||||||
bool given(const std::string& name) { return m_given.contains(name); };
|
bool given(const std::string& name) { return m_given.contains(name); };
|
||||||
|
|
||||||
void parse_positional(
|
void parse_positional(
|
||||||
std::string command, // std::vector<std::string> words,
|
const std::string& command, // std::vector<std::string> words,
|
||||||
std::string pos_args, std::map<std::string, std::string>& named_args);
|
std::string pos_args, std::map<std::string, std::string>& named_args);
|
||||||
|
|
||||||
std::map<std::string, std::string> classify_arguments(int argc, char* argv[], bool full_parse=true);
|
std::map<std::string, std::string> classify_arguments(int argc, char* argv[], bool full_parse=true);
|
||||||
@@ -96,11 +96,11 @@ public:
|
|||||||
void describe();
|
void describe();
|
||||||
// void describe(Argv original);
|
// void describe(Argv original);
|
||||||
|
|
||||||
bool is_flag(std::string name) {
|
bool is_flag(const std::string& name) const {
|
||||||
return std::ranges::count(m_flag_names, name) > 0;
|
return std::ranges::count(m_flag_names, name) > 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool is_opt(std::string name) {
|
bool is_opt(const std::string& name) const {
|
||||||
return std::ranges::count(m_opt_names, name) > 0;
|
return std::ranges::count(m_opt_names, name) > 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1 +1 @@
|
|||||||
BASENAMES := util error locator file argv character ktype katom katom_list log show command argument argument_set argtype argtype_set state eval eval_python eval_cpp klammer klammer_set target target_set machine
|
BASENAMES := util error locator file argv character ktype katom katom_list log show command argument argument_set argtype argtype_registry state eval eval_python eval_cpp klammer klammer_registry klammerset klammerset_registry target target_registry machine
|
||||||
|
|||||||
11
mac/error.h
11
mac/error.h
@@ -10,8 +10,8 @@ inline std::string command_pathname { "Pathname of command executed on the comma
|
|||||||
|
|
||||||
class Error : std::exception {
|
class Error : std::exception {
|
||||||
public:
|
public:
|
||||||
Error(std::string error_type, std::string description,
|
Error(const std::string& error_type, const std::string& description,
|
||||||
Locator locator = Locator(), bool do_justify = true)
|
const Locator& locator = Locator(), bool do_justify = true)
|
||||||
: m_type(error_type)
|
: m_type(error_type)
|
||||||
, m_desc(description)
|
, m_desc(description)
|
||||||
, m_loc(locator)
|
, m_loc(locator)
|
||||||
@@ -48,6 +48,13 @@ public:
|
|||||||
: Error("target", description, locator, do_justify) {};
|
: Error("target", description, locator, do_justify) {};
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class Klammerset_error : public Error {
|
||||||
|
public:
|
||||||
|
explicit Klammerset_error(
|
||||||
|
const std::string& description, const Locator& locator=Locator(), bool do_justify=true)
|
||||||
|
: Error("klammerset", description, locator, do_justify) {};
|
||||||
|
};
|
||||||
|
|
||||||
class Definition_error : public Error {
|
class Definition_error : public Error {
|
||||||
public:
|
public:
|
||||||
explicit Definition_error(
|
explicit Definition_error(
|
||||||
|
|||||||
@@ -14,7 +14,7 @@ enum class eval_t {
|
|||||||
class Eval
|
class Eval
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
explicit Eval(Machine& machine, Locator loc)
|
explicit Eval(Machine& machine, const Locator& loc)
|
||||||
: m_machine(machine),
|
: m_machine(machine),
|
||||||
m_loc(loc)
|
m_loc(loc)
|
||||||
{};
|
{};
|
||||||
|
|||||||
@@ -7,14 +7,14 @@
|
|||||||
#include "file.h"
|
#include "file.h"
|
||||||
#include "show.h"
|
#include "show.h"
|
||||||
|
|
||||||
Eval_cpp::Eval_cpp(Machine& machine, Locator loc)
|
Eval_cpp::Eval_cpp(Machine& machine, const Locator& loc)
|
||||||
: m_machine(machine)
|
: m_machine(machine)
|
||||||
, m_loc(loc)
|
, m_loc(loc)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string Eval_cpp::eval(fs::path library_path, std::string function_name)
|
std::string Eval_cpp::eval(const fs::path& library_path, const std::string& function_name)
|
||||||
{
|
{
|
||||||
(void)K::log(3, library_path, function_name);
|
(void)K::log(3, library_path, function_name);
|
||||||
// msg() << "library path: " << library_path.string().c_str() << "\n";
|
// msg() << "library path: " << library_path.string().c_str() << "\n";
|
||||||
|
|||||||
@@ -7,12 +7,12 @@
|
|||||||
class Eval_cpp
|
class Eval_cpp
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
explicit Eval_cpp(Machine& machine, Locator loc);
|
explicit Eval_cpp(Machine& machine, const Locator& loc);
|
||||||
Eval_cpp(const Eval_cpp&) = delete;
|
Eval_cpp(const Eval_cpp&) = delete;
|
||||||
Eval_cpp& operator=(const Eval_cpp&) = delete;
|
Eval_cpp& operator=(const Eval_cpp&) = delete;
|
||||||
//~Eval_cpp();
|
//~Eval_cpp();
|
||||||
|
|
||||||
std::string eval(fs::path library_path, std::string function_name);
|
std::string eval(const fs::path& library_path, const std::string& function_name);
|
||||||
|
|
||||||
Machine m_machine {};
|
Machine m_machine {};
|
||||||
Locator m_loc;
|
Locator m_loc;
|
||||||
|
|||||||
@@ -5,7 +5,7 @@
|
|||||||
|
|
||||||
std::regex Eval_python::statement_delimiter("\\s*;\\s*");
|
std::regex Eval_python::statement_delimiter("\\s*;\\s*");
|
||||||
|
|
||||||
Eval_python::Eval_python(Machine& machine, Locator loc)
|
Eval_python::Eval_python(Machine& machine, const Locator& loc)
|
||||||
: m_machine(machine)
|
: m_machine(machine)
|
||||||
, m_loc(loc)
|
, m_loc(loc)
|
||||||
, m_globals(nullptr)
|
, m_globals(nullptr)
|
||||||
@@ -93,7 +93,7 @@ strings_t Eval_python::parse_modules(std::string code)
|
|||||||
return modules;
|
return modules;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Eval_python::import_module(std::string module_name, bool verify)
|
void Eval_python::import_module(const std::string& module_name, bool verify)
|
||||||
{
|
{
|
||||||
(void)K::log(3, module_name);
|
(void)K::log(3, module_name);
|
||||||
|
|
||||||
@@ -176,12 +176,12 @@ std::string Eval_python::get_result(PyObject* result_object)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string Eval_python::eval_expression(std::string expression, bool import_modules)
|
std::string Eval_python::eval_expression(const std::string& expression, bool import_modules)
|
||||||
{
|
{
|
||||||
(void)K::log(3, expression);
|
(void)K::log(3, expression);
|
||||||
// msg() << "expression: " << expression << "\n";
|
// msg() << "expression: " << expression << "\n";
|
||||||
if (import_modules && expression.find('.') != std::string::npos) {
|
if (import_modules && expression.find('.') != std::string::npos) {
|
||||||
for (auto m : parse_modules(expression)) {
|
for (const auto& m : parse_modules(expression)) {
|
||||||
import_module(m);
|
import_module(m);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -191,7 +191,7 @@ std::string Eval_python::eval_expression(std::string expression, bool import_mod
|
|||||||
Py_eval_input, m_globals, m_locals));
|
Py_eval_input, m_globals, m_locals));
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string Eval_python::eval_statements(std::string script)
|
std::string Eval_python::eval_statements(const std::string& script)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
strings_t statements = regex_split(script, statement_delimiter);
|
strings_t statements = regex_split(script, statement_delimiter);
|
||||||
|
|||||||
@@ -9,16 +9,16 @@ class Eval_python
|
|||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
static std::regex statement_delimiter;
|
static std::regex statement_delimiter;
|
||||||
explicit Eval_python(Machine& machine, Locator loc);
|
explicit Eval_python(Machine& machine, const Locator& loc);
|
||||||
Eval_python(const Eval_python&) = delete;
|
Eval_python(const Eval_python&) = delete;
|
||||||
Eval_python& operator=(const Eval_python&) = delete;
|
Eval_python& operator=(const Eval_python&) = delete;
|
||||||
~Eval_python();
|
~Eval_python();
|
||||||
void add_module_path(const std::string& path);
|
void add_module_path(const std::string& path);
|
||||||
std::vector<std::string> parse_modules(std::string code);
|
std::vector<std::string> parse_modules(std::string code);
|
||||||
void import_module(std::string module_name, bool verify = true);
|
void import_module(const std::string& module_name, bool verify = true);
|
||||||
std::string get_result(PyObject* result_object);
|
std::string get_result(PyObject* result_object);
|
||||||
std::string eval_expression(std::string expression, bool import_modules = true);
|
std::string eval_expression(const std::string& expression, bool import_modules = true);
|
||||||
std::string eval_statements(std::string script);
|
std::string eval_statements(const std::string& script);
|
||||||
std::string eval(std::string code);
|
std::string eval(std::string code);
|
||||||
//std::string eval_katom_list(const katom_iter& begin, const katom_iter& end);
|
//std::string eval_katom_list(const katom_iter& begin, const katom_iter& end);
|
||||||
std::string eval_katom_list(
|
std::string eval_katom_list(
|
||||||
|
|||||||
13
mac/file.cpp
13
mac/file.cpp
@@ -440,7 +440,7 @@ strings_t get_sks_directories(const std::string& s, bool include_argument)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string cache_directory(std::string subdirectory, std::string parent_directory)
|
std::string cache_directory(const std::string& subdirectory, std::string parent_directory)
|
||||||
{
|
{
|
||||||
if (parent_directory.empty()) {
|
if (parent_directory.empty()) {
|
||||||
// /dev/shm is a fast RAM-backed tmpfs on Linux; it does not exist on
|
// /dev/shm is a fast RAM-backed tmpfs on Linux; it does not exist on
|
||||||
@@ -475,7 +475,7 @@ bool in_modification_order(std::string filename1, std::string filename2)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void write_to_cache(std::string cache_dir, std::string basename, std::string text)
|
void write_to_cache(const std::string& cache_dir, const std::string& basename, const std::string& text)
|
||||||
{
|
{
|
||||||
if (!file_exists(cache_dir)) {
|
if (!file_exists(cache_dir)) {
|
||||||
//std::cout << "Creating cache directory: " << cache_dir << "\n";
|
//std::cout << "Creating cache directory: " << cache_dir << "\n";
|
||||||
@@ -486,14 +486,14 @@ void write_to_cache(std::string cache_dir, std::string basename, std::string tex
|
|||||||
string_to_file(output_filename, text);
|
string_to_file(output_filename, text);
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string read_from_cache(std::string cache_dir, std::string basename)
|
std::string read_from_cache(const std::string& cache_dir, const std::string& basename)
|
||||||
{
|
{
|
||||||
std::string input_filename = cache_dir + "/" + basename;
|
std::string input_filename = cache_dir + "/" + basename;
|
||||||
// msg() << "Reading file from cache: " << input_filename << "\n";
|
// msg() << "Reading file from cache: " << input_filename << "\n";
|
||||||
return string_from_file(input_filename);
|
return string_from_file(input_filename);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool cache_requires_update(std::string cache_dir, std::string file_to_cache, std::string basename)
|
bool cache_requires_update(const std::string& cache_dir, const std::string& file_to_cache, const std::string& basename)
|
||||||
{
|
{
|
||||||
std::string cache_filename = cache_dir + "/" + basename;
|
std::string cache_filename = cache_dir + "/" + basename;
|
||||||
return !in_modification_order(file_to_cache, cache_filename);
|
return !in_modification_order(file_to_cache, cache_filename);
|
||||||
@@ -662,11 +662,12 @@ void copy_file_stream(const fs::path& src, const fs::path& dst)
|
|||||||
}
|
}
|
||||||
|
|
||||||
void copy_preserving_basename(
|
void copy_preserving_basename(
|
||||||
strings_t filenames, std::string output_directory, std::string link_directory)
|
const strings_t& filenames, const std::string& output_directory,
|
||||||
|
const std::string& link_directory)
|
||||||
{
|
{
|
||||||
fs::path outdir(output_directory + "/" + link_directory);
|
fs::path outdir(output_directory + "/" + link_directory);
|
||||||
fs::create_directories(outdir);
|
fs::create_directories(outdir);
|
||||||
for (std::string filename : filenames) {
|
for (const std::string& filename : filenames) {
|
||||||
fs::path pname(filename);
|
fs::path pname(filename);
|
||||||
auto out_path = outdir / pname.filename();
|
auto out_path = outdir / pname.filename();
|
||||||
// Preserve the previous copy_options::update_existing behavior: skip
|
// Preserve the previous copy_options::update_existing behavior: skip
|
||||||
|
|||||||
11
mac/file.h
11
mac/file.h
@@ -45,12 +45,12 @@ fs::path klammertext_filename(
|
|||||||
const std::string& basename, bool error_if_missing=true, bool make_directory_if_missing=false);
|
const std::string& basename, bool error_if_missing=true, bool make_directory_if_missing=false);
|
||||||
std::vector<std::string> sks_dirs();
|
std::vector<std::string> sks_dirs();
|
||||||
std::vector<std::string> get_sks_directories(const std::string& s, bool include_argument=true);
|
std::vector<std::string> get_sks_directories(const std::string& s, bool include_argument=true);
|
||||||
std::string cache_directory(std::string subdirectory, std::string parent_directory="");
|
std::string cache_directory(const std::string& subdirectory, std::string parent_directory="");
|
||||||
std::time_t to_time_t(const fs::file_time_type& ftime);
|
std::time_t to_time_t(const fs::file_time_type& ftime);
|
||||||
bool in_modification_order(std::string filename1, std::string filename2);
|
bool in_modification_order(std::string filename1, std::string filename2);
|
||||||
void write_to_cache(std::string cache_dir, std::string basename, std::string text);
|
void write_to_cache(const std::string& cache_dir, const std::string& basename, const std::string& text);
|
||||||
std::string read_from_cache(std::string cache_dir, std::string basename);
|
std::string read_from_cache(const std::string& cache_dir, const std::string& basename);
|
||||||
bool cache_requires_update(std::string cache_dir, std::string file_to_cache, std::string basename);
|
bool cache_requires_update(const std::string& cache_dir, const std::string& file_to_cache, const std::string& basename);
|
||||||
|
|
||||||
std::vector<fs::path> pathnames_with_extension(
|
std::vector<fs::path> pathnames_with_extension(
|
||||||
const fs::path& dir, const std::string extension
|
const fs::path& dir, const std::string extension
|
||||||
@@ -73,6 +73,7 @@ bool files_differ(const fs::path& p1,
|
|||||||
void copy_file_stream(const fs::path& src, const fs::path& dst);
|
void copy_file_stream(const fs::path& src, const fs::path& dst);
|
||||||
|
|
||||||
void copy_preserving_basename(
|
void copy_preserving_basename(
|
||||||
std::vector<std::string> filenames, std::string output_directory, std::string link_directory);
|
const std::vector<std::string>& filenames, const std::string& output_directory,
|
||||||
|
const std::string& link_directory);
|
||||||
|
|
||||||
fs::path resolve_relative_to(const fs::path& relative, const fs::path& base=std::filesystem::current_path());
|
fs::path resolve_relative_to(const fs::path& relative, const fs::path& base=std::filesystem::current_path());
|
||||||
|
|||||||
@@ -36,7 +36,7 @@ static std::string lower_extension(const fs::path& path)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
std::string name_to_dirname(std::string name)
|
std::string name_to_dirname(const std::string& name)
|
||||||
{
|
{
|
||||||
std::string result {};
|
std::string result {};
|
||||||
for (char c : name) {
|
for (char c : name) {
|
||||||
@@ -206,7 +206,7 @@ static void extract_font_metrics(Resolved_font& font)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Resolved_font resolve_font(std::string family_name)
|
Resolved_font resolve_font(const std::string& family_name)
|
||||||
{
|
{
|
||||||
if (family_name.empty())
|
if (family_name.empty())
|
||||||
return {};
|
return {};
|
||||||
|
|||||||
@@ -19,7 +19,7 @@ struct Resolved_font {
|
|||||||
float capheight_ratio = 0.0f; // cap-height / unitsPerEm from OS/2 table
|
float capheight_ratio = 0.0f; // cap-height / unitsPerEm from OS/2 table
|
||||||
};
|
};
|
||||||
|
|
||||||
std::string name_to_dirname(std::string name);
|
std::string name_to_dirname(const std::string& name);
|
||||||
// Directories searched for installed fonts (KLAMMERTEXT_FONTS, default
|
// Directories searched for installed fonts (KLAMMERTEXT_FONTS, default
|
||||||
// ~/.klammertext/fonts); the default font set is searched after them.
|
// ~/.klammertext/fonts); the default font set is searched after them.
|
||||||
std::vector<std::string> installed_font_dirs();
|
std::vector<std::string> installed_font_dirs();
|
||||||
@@ -27,7 +27,7 @@ std::vector<std::string> installed_font_dirs();
|
|||||||
std::string default_font_dir();
|
std::string default_font_dir();
|
||||||
// Every installable font family found across those directories.
|
// Every installable font family found across those directories.
|
||||||
std::vector<std::string> available_font_families();
|
std::vector<std::string> available_font_families();
|
||||||
Resolved_font resolve_font(std::string family_name);
|
Resolved_font resolve_font(const std::string& family_name);
|
||||||
void install_resolved_font(const Resolved_font& font, std::string output_dir);
|
void install_resolved_font(const Resolved_font& font, std::string output_dir);
|
||||||
|
|
||||||
// One font file classified by its internal metadata (name table, OS/2).
|
// One font file classified by its internal metadata (name table, OS/2).
|
||||||
|
|||||||
@@ -281,7 +281,7 @@ katom_list trim(const katom_list& katoms, bool trim_inactive)
|
|||||||
return trim(result, trim_types);
|
return trim(result, trim_types);
|
||||||
}
|
}
|
||||||
|
|
||||||
strings_t line_split(std::string s)
|
strings_t line_split(const std::string& s)
|
||||||
{
|
{
|
||||||
std::istringstream is(s);
|
std::istringstream is(s);
|
||||||
strings_t result {};
|
strings_t result {};
|
||||||
@@ -293,7 +293,7 @@ strings_t line_split(std::string s)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::pair<std::string, strings_t> line_split(fs::path pathname)
|
std::pair<std::string, strings_t> line_split(const fs::path& pathname)
|
||||||
{
|
{
|
||||||
std::string source {};
|
std::string source {};
|
||||||
strings_t lines {};
|
strings_t lines {};
|
||||||
|
|||||||
@@ -99,8 +99,8 @@ std::vector<Katom> trim(const std::vector<Katom>& katoms, bool trim_inactive = f
|
|||||||
|
|
||||||
std::vector<std::vector<Katom>> bar_split(std::vector<Katom>::iterator kbegin, std::vector<Katom>::iterator kend);
|
std::vector<std::vector<Katom>> bar_split(std::vector<Katom>::iterator kbegin, std::vector<Katom>::iterator kend);
|
||||||
|
|
||||||
std::vector<std::string> line_split(std::string s);
|
std::vector<std::string> line_split(const std::string& s);
|
||||||
std::pair<std::string, std::vector<std::string>> line_split(fs::path pathname);
|
std::pair<std::string, std::vector<std::string>> line_split(const fs::path& pathname);
|
||||||
std::vector<Katom> katomize(const std::vector<std::string>& lines, const std::string& source_desc);
|
std::vector<Katom> katomize(const std::vector<std::string>& lines, const std::string& source_desc);
|
||||||
|
|
||||||
void warn_unparsed_katoms(std::vector<Katom>& katoms, bool warn = true);
|
void warn_unparsed_katoms(std::vector<Katom>& katoms, bool warn = true);
|
||||||
|
|||||||
@@ -181,10 +181,10 @@ void check_named_katom_span(const Katom& begin, const Katom& end)
|
|||||||
|
|
||||||
spans_t find_spans(
|
spans_t find_spans(
|
||||||
katom_iter begin, katom_iter end,
|
katom_iter begin, katom_iter end,
|
||||||
std::function<bool(const Katom&)> level_inc,
|
const std::function<bool(const Katom&)>& level_inc,
|
||||||
std::function<bool(const Katom&)> level_dec,
|
const std::function<bool(const Katom&)>& level_dec,
|
||||||
bool error_exit,
|
bool error_exit,
|
||||||
std::string name)
|
const std::string& name)
|
||||||
{
|
{
|
||||||
(void)K::log(4, name);
|
(void)K::log(4, name);
|
||||||
bool _dbg = false;
|
bool _dbg = false;
|
||||||
@@ -245,10 +245,10 @@ spans_t find_spans(
|
|||||||
|
|
||||||
spans_t find_spans(
|
spans_t find_spans(
|
||||||
katom_list& katoms,
|
katom_list& katoms,
|
||||||
std::function<bool(const Katom&)> level_inc,
|
const std::function<bool(const Katom&)>& level_inc,
|
||||||
std::function<bool(const Katom&)> level_dec,
|
const std::function<bool(const Katom&)>& level_dec,
|
||||||
bool error_exit,
|
bool error_exit,
|
||||||
std::string name)
|
const std::string& name)
|
||||||
{
|
{
|
||||||
return find_spans(katoms.begin(), katoms.end(), level_inc, level_dec, error_exit, name);
|
return find_spans(katoms.begin(), katoms.end(), level_inc, level_dec, error_exit, name);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -23,17 +23,17 @@ find_katom(const std::vector<Katom>::iterator begin, const std::vector<Katom>::i
|
|||||||
|
|
||||||
std::vector<std::pair<Katom, Katom>>
|
std::vector<std::pair<Katom, Katom>>
|
||||||
find_spans(std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end,
|
find_spans(std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end,
|
||||||
std::function<bool(const Katom&)> level_inc,
|
const std::function<bool(const Katom&)>& level_inc,
|
||||||
std::function<bool(const Katom&)> level_dec,
|
const std::function<bool(const Katom&)>& level_dec,
|
||||||
bool error_exit,
|
bool error_exit,
|
||||||
std::string name);
|
const std::string& name);
|
||||||
|
|
||||||
std::vector<std::pair<Katom, Katom>>
|
std::vector<std::pair<Katom, Katom>>
|
||||||
find_spans(std::vector<Katom>& katoms,
|
find_spans(std::vector<Katom>& katoms,
|
||||||
std::function<bool(const Katom&)> level_inc,
|
const std::function<bool(const Katom&)>& level_inc,
|
||||||
std::function<bool(const Katom&)> level_dec,
|
const std::function<bool(const Katom&)>& level_dec,
|
||||||
bool error_exit=true,
|
bool error_exit=true,
|
||||||
std::string name="all");
|
const std::string& name="all");
|
||||||
|
|
||||||
|
|
||||||
void describe_spans(const std::vector<Katom>& katoms);
|
void describe_spans(const std::vector<Katom>& katoms);
|
||||||
|
|||||||
@@ -13,7 +13,7 @@ using namespace std::literals;
|
|||||||
std::regex Klammer::name_re = std::regex(R"((\w+)(?:\.(\w+))?)");
|
std::regex Klammer::name_re = std::regex(R"((\w+)(?:\.(\w+))?)");
|
||||||
|
|
||||||
std::tuple<std::string, std::string>
|
std::tuple<std::string, std::string>
|
||||||
parse_name(Target_set targets, Katom name_katom)
|
parse_name(const Target_registry& targets, const Katom& name_katom)
|
||||||
{
|
{
|
||||||
std::string name_with_target = trim_char(name_katom.m_text, '@');
|
std::string name_with_target = trim_char(name_katom.m_text, '@');
|
||||||
std::smatch match {};
|
std::smatch match {};
|
||||||
@@ -29,7 +29,7 @@ parse_name(Target_set targets, Katom name_katom)
|
|||||||
std::string klammer_name = match[1];
|
std::string klammer_name = match[1];
|
||||||
std::string target_name = match[2];
|
std::string target_name = match[2];
|
||||||
if (target_name.empty()) {
|
if (target_name.empty()) {
|
||||||
target_name = Target_set::general_name;
|
target_name = Target_registry::general_name;
|
||||||
}
|
}
|
||||||
if (!targets.has(target_name)) {
|
if (!targets.has(target_name)) {
|
||||||
throw Target_error(
|
throw Target_error(
|
||||||
@@ -41,7 +41,7 @@ parse_name(Target_set targets, Katom name_katom)
|
|||||||
}
|
}
|
||||||
|
|
||||||
std::tuple<Katom, Parameter_set, katom_list, Locator>
|
std::tuple<Katom, Parameter_set, katom_list, Locator>
|
||||||
parse_definition_katoms(std::string klammer_name, Argtype_set argtypes, katom_iter& begin, katom_iter& end)
|
parse_definition_katoms(const std::string& klammer_name, const Argtype_registry& argtypes, katom_iter& begin, katom_iter& end)
|
||||||
{
|
{
|
||||||
(void)K::log(3, *begin, *(end - 1));
|
(void)K::log(3, *begin, *(end - 1));
|
||||||
katom_iter deftype = std::find_if(
|
katom_iter deftype = std::find_if(
|
||||||
@@ -84,7 +84,7 @@ parse_definition_katoms(std::string klammer_name, Argtype_set argtypes, katom_it
|
|||||||
}
|
}
|
||||||
|
|
||||||
void Klammer::add_target_definition(
|
void Klammer::add_target_definition(
|
||||||
std::string target_name, Argtype_set argtypes, katom_iter begin, katom_iter end)
|
const std::string& target_name, const Argtype_registry& argtypes, katom_iter begin, katom_iter end)
|
||||||
{
|
{
|
||||||
(void)K::log(3, *begin, *(end-1));
|
(void)K::log(3, *begin, *(end-1));
|
||||||
auto [deftype, parameters, body, loc] =
|
auto [deftype, parameters, body, loc] =
|
||||||
@@ -95,7 +95,7 @@ void Klammer::add_target_definition(
|
|||||||
std::regex variable_re(R"(\*(\w+)\*)");
|
std::regex variable_re(R"(\*(\w+)\*)");
|
||||||
int i = 0;
|
int i = 0;
|
||||||
variable_map_t varmap {};
|
variable_map_t varmap {};
|
||||||
for (auto k : body) {
|
for (const auto& k : body) {
|
||||||
std::smatch match {};
|
std::smatch match {};
|
||||||
std::string txt = k.m_text;
|
std::string txt = k.m_text;
|
||||||
while (std::regex_search(txt, match, variable_re) &&
|
while (std::regex_search(txt, match, variable_re) &&
|
||||||
@@ -127,23 +127,23 @@ void Klammer::remove_target_definition(const std::string& target_name)
|
|||||||
|
|
||||||
// Rationalize multiple definitions
|
// Rationalize multiple definitions
|
||||||
|
|
||||||
std::string error_list(std::string label, auto components, std::string after="")
|
std::string error_list(const std::string& label, const auto& components, const std::string& after="")
|
||||||
{
|
{
|
||||||
std::stringstream ss {};
|
std::stringstream ss {};
|
||||||
ss << label << ":\n";
|
ss << label << ":\n";
|
||||||
for (auto c : components) {
|
for (const auto& c : components) {
|
||||||
ss << " " << c.loc.desc() << "\n";
|
ss << " " << c.loc.desc() << "\n";
|
||||||
}
|
}
|
||||||
ss << after;
|
ss << after;
|
||||||
return ss.str();
|
return ss.str();
|
||||||
}
|
}
|
||||||
|
|
||||||
auto Klammer::target_defs(std::vector<std::string> target_names)
|
auto Klammer::target_defs(const std::vector<std::string>& target_names)
|
||||||
{
|
{
|
||||||
std::vector<Klammer::components> defs {};
|
std::vector<Klammer::components> defs {};
|
||||||
for (auto target : target_names) {
|
for (const auto& target : target_names) {
|
||||||
auto target_defs = collect_if(
|
auto target_defs = collect_if(
|
||||||
m_defs, [target](const auto& def) { return def.target == target; });
|
m_defs, [&target](const auto& def) { return def.target == target; });
|
||||||
defs.insert(defs.end(), target_defs.begin(), target_defs.end());
|
defs.insert(defs.end(), target_defs.begin(), target_defs.end());
|
||||||
}
|
}
|
||||||
return defs;
|
return defs;
|
||||||
@@ -173,7 +173,7 @@ void Klammer::disallow_instances() //Klammer::components declaration)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Klammer::copy_to_instances(Target_set targets)
|
bool Klammer::copy_to_instances(const Target_registry& targets)
|
||||||
{
|
{
|
||||||
auto instances = instance_defs();
|
auto instances = instance_defs();
|
||||||
if (!instances.empty()) {
|
if (!instances.empty()) {
|
||||||
@@ -202,19 +202,20 @@ bool Klammer::copy_to_instances(Target_set targets)
|
|||||||
}
|
}
|
||||||
|
|
||||||
void Klammer::copy_components(
|
void Klammer::copy_components(
|
||||||
Parameter_set parameters, std::vector<Klammer::components> cs, Target_set targets)
|
const Parameter_set& parameters, const std::vector<Klammer::components>& cs,
|
||||||
|
const Target_registry& targets)
|
||||||
{
|
{
|
||||||
(void)K::log(4);
|
(void)K::log(4);
|
||||||
for (auto target_name : targets.m_names) {
|
for (const auto& target_name : targets.m_names) {
|
||||||
if (target_name == Target_set::declare_name ||
|
if (target_name == Target_registry::declare_name ||
|
||||||
target_name == Target_set::general_name) {
|
target_name == Target_registry::general_name) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
m_parameters = parameters;
|
m_parameters = parameters;
|
||||||
}
|
}
|
||||||
for (auto c : cs) {
|
for (const auto& c : cs) {
|
||||||
m_body[c.target] = c.body;
|
m_body[c.target] = c.body;
|
||||||
m_body_generic[c.target] = (c.target == Target_set::general_name);
|
m_body_generic[c.target] = (c.target == Target_registry::general_name);
|
||||||
m_varmap[c.target] = c.varmap;
|
m_varmap[c.target] = c.varmap;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -223,7 +224,7 @@ void Klammer::copy_components(
|
|||||||
|
|
||||||
void Klammer::check_for_multiple_general_klammers()
|
void Klammer::check_for_multiple_general_klammers()
|
||||||
{
|
{
|
||||||
auto general_klammers = target_defs({Target_set::general_name});
|
auto general_klammers = target_defs({Target_registry::general_name});
|
||||||
if (general_klammers.size() > 1) {
|
if (general_klammers.size() > 1) {
|
||||||
throw Definition_error(
|
throw Definition_error(
|
||||||
error_list(
|
error_list(
|
||||||
@@ -235,11 +236,11 @@ void Klammer::check_for_multiple_general_klammers()
|
|||||||
|
|
||||||
void Klammer::check_for_declaration_and_definitions()
|
void Klammer::check_for_declaration_and_definitions()
|
||||||
{
|
{
|
||||||
auto declares = target_defs({Target_set::declare_name});
|
auto declares = target_defs({Target_registry::declare_name});
|
||||||
if (!declares.empty()) {
|
if (!declares.empty()) {
|
||||||
std::vector<Klammer::components> definitions {};
|
std::vector<Klammer::components> definitions {};
|
||||||
for (auto def : m_defs) {
|
for (const auto& def : m_defs) {
|
||||||
if (def.target != Target_set::declare_name) {
|
if (def.target != Target_registry::declare_name) {
|
||||||
if (def.deftype == katom_t::klammer_definition ||
|
if (def.deftype == katom_t::klammer_definition ||
|
||||||
def.deftype == katom_t::klammer_default) {
|
def.deftype == katom_t::klammer_default) {
|
||||||
msg() << def << "\n";
|
msg() << def << "\n";
|
||||||
@@ -261,11 +262,11 @@ void Klammer::check_for_declaration_and_definitions()
|
|||||||
|
|
||||||
// If a general definition exists, use it for targets not defined, but check signatures
|
// If a general definition exists, use it for targets not defined, but check signatures
|
||||||
|
|
||||||
void Klammer::copy_general_klammer_to_undefined(Target_set targets)
|
void Klammer::copy_general_klammer_to_undefined(const Target_registry& targets)
|
||||||
{
|
{
|
||||||
(void)K::log(4);
|
(void)K::log(4);
|
||||||
auto general_klammers = target_defs({Target_set::general_name});
|
auto general_klammers = target_defs({Target_registry::general_name});
|
||||||
auto declares = target_defs({Target_set::declare_name});
|
auto declares = target_defs({Target_registry::declare_name});
|
||||||
|
|
||||||
// Check matching signatures (though this case already handled)
|
// Check matching signatures (though this case already handled)
|
||||||
if (general_klammers.size() == 1) {
|
if (general_klammers.size() == 1) {
|
||||||
@@ -279,13 +280,13 @@ void Klammer::copy_general_klammer_to_undefined(Target_set targets)
|
|||||||
m_parameters.m_katoms[0].m_loc, false);
|
m_parameters.m_katoms[0].m_loc, false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
auto [target, deftype, parameters, body, varmap, loc] = general_klammers[0];
|
const auto& [target, deftype, parameters, body, varmap, loc] = general_klammers[0];
|
||||||
if (m_parameters.m_katoms.empty()) {
|
if (m_parameters.m_katoms.empty()) {
|
||||||
m_parameters = parameters;
|
m_parameters = parameters;
|
||||||
}
|
}
|
||||||
for (auto target_name : targets.m_names) {
|
for (const auto& target_name : targets.m_names) {
|
||||||
// std::cout << "General copy, considering " << target_name << "\n";
|
// std::cout << "General copy, considering " << target_name << "\n";
|
||||||
if (m_body.count(target_name) == 0 && target_name != Target_set::declare_name) {
|
if (m_body.count(target_name) == 0 && target_name != Target_registry::declare_name) {
|
||||||
// std::cout << " Copying to " << target_name << "\n";
|
// std::cout << " Copying to " << target_name << "\n";
|
||||||
m_body[target_name] = body;
|
m_body[target_name] = body;
|
||||||
m_body_generic[target_name] = true; // general body -> writer content
|
m_body_generic[target_name] = true; // general body -> writer content
|
||||||
@@ -298,7 +299,7 @@ void Klammer::copy_general_klammer_to_undefined(Target_set targets)
|
|||||||
|
|
||||||
// Three declaration cases: none, one, many
|
// Three declaration cases: none, one, many
|
||||||
|
|
||||||
void Klammer::no_declarations(Target_set targets)
|
void Klammer::no_declarations(const Target_registry& targets)
|
||||||
{
|
{
|
||||||
(void)K::log(4);
|
(void)K::log(4);
|
||||||
// std::cout << boldblack << "No declarations\n" << black;
|
// std::cout << boldblack << "No declarations\n" << black;
|
||||||
@@ -308,7 +309,7 @@ void Klammer::no_declarations(Target_set targets)
|
|||||||
std::vector<std::string> target_names = targets.applicable();
|
std::vector<std::string> target_names = targets.applicable();
|
||||||
std::vector<Parameter_set> all_parameter_sets {};
|
std::vector<Parameter_set> all_parameter_sets {};
|
||||||
// Are all parameters the same?
|
// Are all parameters the same?
|
||||||
for (auto def : m_defs) {
|
for (const auto& def : m_defs) {
|
||||||
if (std::ranges::find(target_names, def.target) != target_names.end()) {
|
if (std::ranges::find(target_names, def.target) != target_names.end()) {
|
||||||
// std::cout << " Found: " << def.target << "\n";
|
// std::cout << " Found: " << def.target << "\n";
|
||||||
all_parameter_sets.push_back(def.parameters);
|
all_parameter_sets.push_back(def.parameters);
|
||||||
@@ -332,7 +333,7 @@ void Klammer::no_declarations(Target_set targets)
|
|||||||
copy_general_klammer_to_undefined(targets);
|
copy_general_klammer_to_undefined(targets);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Klammer::one_declaration(Target_set targets, Klammer::components declare)
|
void Klammer::one_declaration(const Target_registry& targets, const Klammer::components& declare)
|
||||||
{
|
{
|
||||||
(void)K::log(4);
|
(void)K::log(4);
|
||||||
// std::cout << boldblack << "One declaration\n" << black;
|
// std::cout << boldblack << "One declaration\n" << black;
|
||||||
@@ -342,7 +343,7 @@ void Klammer::one_declaration(Target_set targets, Klammer::components declare)
|
|||||||
copy_general_klammer_to_undefined(targets);
|
copy_general_klammer_to_undefined(targets);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Klammer::many_declarations(std::vector<Klammer::components> declares)
|
void Klammer::many_declarations(const std::vector<Klammer::components>& declares)
|
||||||
{
|
{
|
||||||
(void)K::log(4);
|
(void)K::log(4);
|
||||||
// std::cout << boldblack << "Many declarations\n" << black;
|
// std::cout << boldblack << "Many declarations\n" << black;
|
||||||
@@ -353,10 +354,10 @@ void Klammer::many_declarations(std::vector<Klammer::components> declares)
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
void Klammer::rationalize(Target_set targets)
|
void Klammer::rationalize(const Target_registry& targets)
|
||||||
{
|
{
|
||||||
(void)K::log(3, m_name);
|
(void)K::log(3, m_name);
|
||||||
auto declares = target_defs({Target_set::declare_name});
|
auto declares = target_defs({Target_registry::declare_name});
|
||||||
auto declare_count = declares.size();
|
auto declare_count = declares.size();
|
||||||
if (declare_count == 0) {
|
if (declare_count == 0) {
|
||||||
disallow_instances();
|
disallow_instances();
|
||||||
@@ -371,7 +372,7 @@ void Klammer::rationalize(Target_set targets)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
std::string klammer_name_from_katom(std::string s, Locator loc)
|
std::string klammer_name_from_katom(const std::string& s, const Locator& loc)
|
||||||
{
|
{
|
||||||
std::regex rgx(R"(@(\w+).*)");
|
std::regex rgx(R"(@(\w+).*)");
|
||||||
std::smatch match {};
|
std::smatch match {};
|
||||||
@@ -389,11 +390,11 @@ void label(const std::string& s)
|
|||||||
std::cout << std::right << std::setw(w) << std::setfill(' ') << s << ": ";
|
std::cout << std::right << std::setw(w) << std::setfill(' ') << s << ": ";
|
||||||
}
|
}
|
||||||
|
|
||||||
void show_args(const std::string& label_text, std::vector<Argument> arguments)
|
void show_args(const std::string& label_text, const std::vector<Argument>& arguments)
|
||||||
{
|
{
|
||||||
if (!arguments.empty()) {
|
if (!arguments.empty()) {
|
||||||
label(label_text);
|
label(label_text);
|
||||||
for (auto a : arguments) {
|
for (const auto& a : arguments) {
|
||||||
std::cout << a << " ";
|
std::cout << a << " ";
|
||||||
}
|
}
|
||||||
std::cout << '\n';
|
std::cout << '\n';
|
||||||
@@ -403,7 +404,7 @@ void show_args(const std::string& label_text, std::vector<Argument> arguments)
|
|||||||
strings_t Klammer::get_target_names() const
|
strings_t Klammer::get_target_names() const
|
||||||
{
|
{
|
||||||
strings_t names {};
|
strings_t names {};
|
||||||
for (auto [target, body] : m_body) {
|
for (const auto& [target, body] : m_body) {
|
||||||
std::stringstream ss {};
|
std::stringstream ss {};
|
||||||
// ss << name << target.m_loc.m_line;
|
// ss << name << target.m_loc.m_line;
|
||||||
ss << target;
|
ss << target;
|
||||||
@@ -422,12 +423,12 @@ strings_t Klammer::get_locations()
|
|||||||
return {};
|
return {};
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string Klammer::signature_text()
|
std::string Klammer::signature_text() const
|
||||||
{
|
{
|
||||||
std::string result {};
|
std::string result {};
|
||||||
bool has_pos = false;
|
bool has_pos = false;
|
||||||
bool has_opt = false;
|
bool has_opt = false;
|
||||||
for (auto pos : m_parameters.m_positional) {
|
for (const auto& pos : m_parameters.m_positional) {
|
||||||
result += pos.m_name;
|
result += pos.m_name;
|
||||||
std::string type = pos.m_argtype.m_name;
|
std::string type = pos.m_argtype.m_name;
|
||||||
if (type != default_argtype) {
|
if (type != default_argtype) {
|
||||||
@@ -442,7 +443,7 @@ std::string Klammer::signature_text()
|
|||||||
if (opt_count <= 3 && !has_pos) {
|
if (opt_count <= 3 && !has_pos) {
|
||||||
result += " ";
|
result += " ";
|
||||||
}
|
}
|
||||||
for (auto opt : m_parameters.m_optional) {
|
for (const auto& opt : m_parameters.m_optional) {
|
||||||
if (opt_count > 3) {
|
if (opt_count > 3) {
|
||||||
result += "\n :" + opt.m_name;
|
result += "\n :" + opt.m_name;
|
||||||
} else {
|
} else {
|
||||||
@@ -473,18 +474,18 @@ std::string Klammer::signature_text()
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
std::string Klammer::description_text()
|
std::string Klammer::description_text() const
|
||||||
{
|
{
|
||||||
std::string result = " [" + m_name + ": no description]";
|
std::string result = " [" + m_name + ": no description]";
|
||||||
if (m_body.contains("k")) {
|
if (m_body.contains("k")) {
|
||||||
result = to_string(m_body["k"], true);
|
result = to_string(m_body.at("k"), true);
|
||||||
result = justify(result, 80, 1);
|
result = justify(result, 80, 1);
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
std::string Klammer::describe(int margin)
|
std::string Klammer::describe(int margin) const
|
||||||
{
|
{
|
||||||
std::string result {};
|
std::string result {};
|
||||||
result += "@" + m_name + signature_text() + description_text();
|
result += "@" + m_name + signature_text() + description_text();
|
||||||
|
|||||||
@@ -4,7 +4,7 @@
|
|||||||
|
|
||||||
#include "deftype.h"
|
#include "deftype.h"
|
||||||
#include "argument_set.h"
|
#include "argument_set.h"
|
||||||
#include "target_set.h"
|
#include "target_registry.h"
|
||||||
#include "locator.h"
|
#include "locator.h"
|
||||||
|
|
||||||
class Klammer
|
class Klammer
|
||||||
@@ -31,37 +31,38 @@ public:
|
|||||||
// target-name -> [variable -> index]
|
// target-name -> [variable -> index]
|
||||||
|
|
||||||
void add_target_definition(
|
void add_target_definition(
|
||||||
std::string target_name, Argtype_set argtypes,
|
const std::string& target_name, const Argtype_registry& argtypes,
|
||||||
std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end);
|
std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end);
|
||||||
void remove_target_definition(const std::string& target_name);
|
void remove_target_definition(const std::string& target_name);
|
||||||
|
|
||||||
auto target_defs(std::vector<std::string> target_names);
|
auto target_defs(const std::vector<std::string>& target_names);
|
||||||
auto instance_defs();
|
auto instance_defs();
|
||||||
void disallow_instances(); //Klammer::components declaration);
|
void disallow_instances(); //Klammer::components declaration);
|
||||||
bool copy_to_instances(Target_set targets);
|
bool copy_to_instances(const Target_registry& targets);
|
||||||
void copy_components(
|
void copy_components(
|
||||||
Parameter_set parameters, std::vector<Klammer::components> cs, Target_set targets);
|
const Parameter_set& parameters, const std::vector<Klammer::components>& cs,
|
||||||
|
const Target_registry& targets);
|
||||||
void check_for_multiple_general_klammers();
|
void check_for_multiple_general_klammers();
|
||||||
void check_for_declaration_and_definitions();
|
void check_for_declaration_and_definitions();
|
||||||
void copy_general_klammer_to_undefined(Target_set targets);
|
void copy_general_klammer_to_undefined(const Target_registry& targets);
|
||||||
void no_declarations(Target_set targets);
|
void no_declarations(const Target_registry& targets);
|
||||||
void one_declaration(Target_set targets, Klammer::components declare);
|
void one_declaration(const Target_registry& targets, const Klammer::components& declare);
|
||||||
void many_declarations(std::vector<Klammer::components> declares);
|
void many_declarations(const std::vector<Klammer::components>& declares);
|
||||||
void rationalize(Target_set target);
|
void rationalize(const Target_registry& targets);
|
||||||
/*
|
/*
|
||||||
void add_description(const std::string& desc, Katom definition_type);
|
void add_description(const std::string& desc, Katom definition_type);
|
||||||
|
|
||||||
auto user_defs();
|
auto user_defs();
|
||||||
auto klammer_defines_parameters();
|
auto klammer_defines_parameters();
|
||||||
auto klammer_uses_parameters();
|
auto klammer_uses_parameters();
|
||||||
void check_for_target_errors(Target_set targets);
|
void check_for_target_errors(Target_registry targets);
|
||||||
bool explicit_parameters_match();
|
bool explicit_parameters_match();
|
||||||
void copy_components(Klammer::components cs, Target_set targets);
|
void copy_components(Klammer::components cs, Target_registry targets);
|
||||||
*/
|
*/
|
||||||
|
|
||||||
std::string signature_text();
|
std::string signature_text() const;
|
||||||
std::string description_text();
|
std::string description_text() const;
|
||||||
std::string describe(int margin=0);
|
std::string describe(int margin=0) const;
|
||||||
|
|
||||||
bool has_literal_param() const {
|
bool has_literal_param() const {
|
||||||
for (const auto& p : m_parameters.m_positional)
|
for (const auto& p : m_parameters.m_positional)
|
||||||
@@ -91,18 +92,18 @@ public:
|
|||||||
std::map<std::string, bool> m_body_generic {};
|
std::map<std::string, bool> m_body_generic {};
|
||||||
};
|
};
|
||||||
|
|
||||||
std::string klammer_name_from_katom(std::string s, Locator loc);
|
std::string klammer_name_from_katom(const std::string& s, const Locator& loc);
|
||||||
|
|
||||||
std::tuple<std::string,std::string>
|
std::tuple<std::string,std::string>
|
||||||
parse_name(Target_set targets, Katom name_katom);
|
parse_name(const Target_registry& targets, const Katom& name_katom);
|
||||||
|
|
||||||
std::tuple<Katom, Parameter_set, std::vector<Katom>, Locator>
|
std::tuple<Katom, Parameter_set, std::vector<Katom>, Locator>
|
||||||
parse_definition_katoms(Argtype_set argtypes, //Target_set targets,
|
parse_definition_katoms(const std::string& klammer_name, const Argtype_registry& argtypes,
|
||||||
std::vector<Katom>::iterator& begin, std::vector<Katom>::iterator& end);
|
std::vector<Katom>::iterator& begin, std::vector<Katom>::iterator& end);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
klammer_definition_args parse_klammer_definition_katoms(
|
klammer_definition_args parse_klammer_definition_katoms(
|
||||||
katom_list& katoms, Argtype_set& argtypes);
|
katom_list& katoms, Argtype_registry& argtypes);
|
||||||
|
|
||||||
void check_for_undefined_arguments(
|
void check_for_undefined_arguments(
|
||||||
std::string name, Parameters parameters, katom_list body_katoms, Locator loc);
|
std::string name, Parameters parameters, katom_list body_katoms, Locator loc);
|
||||||
|
|||||||
@@ -1,18 +1,18 @@
|
|||||||
#include "klammer.h"
|
#include "klammer.h"
|
||||||
#include "klammer_set.h"
|
#include "klammer_registry.h"
|
||||||
#include "show.h"
|
#include "show.h"
|
||||||
#include "util.h"
|
#include "util.h"
|
||||||
#include "log.h"
|
#include "log.h"
|
||||||
#include "error.h"
|
#include "error.h"
|
||||||
|
|
||||||
/*
|
/*
|
||||||
bool Klammer_set::has(std::string name, std::string target)
|
bool Klammer_registry::has(std::string name, std::string target)
|
||||||
{
|
{
|
||||||
return m_klammers.count(name) > 0;
|
return m_klammers.count(name) > 0;
|
||||||
}
|
}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
void Klammer_set::add(Argtype_set argtypes, Target_set& targets, katom_iter begin, katom_iter end, katom_list& katoms)
|
void Klammer_registry::add(const Argtype_registry& argtypes, const Target_registry& targets, katom_iter begin, katom_iter end, katom_list& katoms)
|
||||||
{
|
{
|
||||||
(void)K::log(3, *begin, *(end - 1));
|
(void)K::log(3, *begin, *(end - 1));
|
||||||
restore_initial_type(begin, end);
|
restore_initial_type(begin, end);
|
||||||
@@ -62,7 +62,7 @@ void Klammer_set::add(Argtype_set argtypes, Target_set& targets, katom_iter begi
|
|||||||
// This add's target:
|
// This add's target:
|
||||||
Target target = targets.get(target_name, begin->m_loc);
|
Target target = targets.get(target_name, begin->m_loc);
|
||||||
if (!target.m_provides.empty()) {
|
if (!target.m_provides.empty()) {
|
||||||
for (auto provide_name : target.m_provides) {
|
for (const auto& provide_name : target.m_provides) {
|
||||||
if (m_klammers[klammer_name].m_defloc.count(provide_name) > 0) {
|
if (m_klammers[klammer_name].m_defloc.count(provide_name) > 0) {
|
||||||
m_klammers[klammer_name].remove_target_definition(provide_name);
|
m_klammers[klammer_name].remove_target_definition(provide_name);
|
||||||
}
|
}
|
||||||
@@ -80,30 +80,30 @@ void Klammer_set::add(Argtype_set argtypes, Target_set& targets, katom_iter begi
|
|||||||
ignore_whitespace(next_iter, katoms);
|
ignore_whitespace(next_iter, katoms);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Klammer_set::rationalize(Target_set targets)
|
void Klammer_registry::rationalize(const Target_registry& targets)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
for (auto k : m_klammers) {
|
for (auto& [name, klammer] : m_klammers) {
|
||||||
m_klammers[k.first].rationalize(targets);
|
klammer.rationalize(targets);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
bool Klammer_set::has(std::string name, std::string target)
|
bool Klammer_registry::has(std::string name, std::string target)
|
||||||
{
|
{
|
||||||
return m_klammers.count(name) > 0;
|
return m_klammers.count(name) > 0;
|
||||||
}
|
}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
void Klammer_set::check_klammer(std::string name, std::string target, Locator loc)
|
void Klammer_registry::check_klammer(const std::string& name, const std::string& target, const Locator& loc) const
|
||||||
{
|
{
|
||||||
if (m_klammers.count(name) == 0) {
|
if (m_klammers.count(name) == 0) {
|
||||||
throw Definition_error("The klammer " + q_(name) + " is not defined for an unspecified target", loc);
|
throw Definition_error("The klammer " + q_(name) + " is not defined for an unspecified target", loc);
|
||||||
}
|
}
|
||||||
Klammer k = m_klammers[name];
|
const Klammer& k = m_klammers.at(name);
|
||||||
if (k.m_defloc.count(target) == 0) {
|
if (k.m_defloc.count(target) == 0) {
|
||||||
std::string desc;
|
std::string desc;
|
||||||
if (target == Target_set::general_name) {
|
if (target == Target_registry::general_name) {
|
||||||
desc = "an unspecified target";
|
desc = "an unspecified target";
|
||||||
} else {
|
} else {
|
||||||
desc = "target " + q_(target);
|
desc = "target " + q_(target);
|
||||||
@@ -113,7 +113,7 @@ void Klammer_set::check_klammer(std::string name, std::string target, Locator lo
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
const std::vector<Katom>* Klammer_set::constant_body(const std::string& name) const
|
const std::vector<Katom>* Klammer_registry::constant_body(const std::string& name) const
|
||||||
{
|
{
|
||||||
auto it = m_klammers.find(name);
|
auto it = m_klammers.find(name);
|
||||||
if (it == m_klammers.end()) return nullptr;
|
if (it == m_klammers.end()) return nullptr;
|
||||||
@@ -126,14 +126,14 @@ const std::vector<Katom>* Klammer_set::constant_body(const std::string& name) co
|
|||||||
if (!d.parameters.empty()) return nullptr;
|
if (!d.parameters.empty()) return nullptr;
|
||||||
}
|
}
|
||||||
for (const auto& d : k.m_defs) {
|
for (const auto& d : k.m_defs) {
|
||||||
if (d.target == Target_set::general_name && d.parameters.empty()) {
|
if (d.target == Target_registry::general_name && d.parameters.empty()) {
|
||||||
return &d.body;
|
return &d.body;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
int max_length(std::map<std::string, Klammer> ss)
|
int max_length(const std::map<std::string, Klammer>& ss)
|
||||||
{
|
{
|
||||||
size_t result = 0;
|
size_t result = 0;
|
||||||
for_each(ss.begin(), ss.end(),
|
for_each(ss.begin(), ss.end(),
|
||||||
@@ -141,19 +141,19 @@ int max_length(std::map<std::string, Klammer> ss)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string Klammer_set::instance_list(int margin) const
|
std::string Klammer_registry::instance_list(int margin) const
|
||||||
{
|
{
|
||||||
std::stringstream ss {};
|
std::stringstream ss {};
|
||||||
std::string tab(margin, ' ');
|
std::string tab(margin, ' ');
|
||||||
auto name_width = max_length(m_klammers);
|
auto name_width = max_length(m_klammers);
|
||||||
for (auto [name, k] : m_klammers) {
|
for (const auto& [name, k] : m_klammers) {
|
||||||
ss << tab << std::setfill(' ') << std::setw(name_width) << name
|
ss << tab << std::setfill(' ') << std::setw(name_width) << name
|
||||||
<< sp_arrow << k << "\n";
|
<< sp_arrow << k << "\n";
|
||||||
}
|
}
|
||||||
return ss.str();
|
return ss.str();
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string Klammer_set::describe(int margin) const
|
std::string Klammer_registry::describe(int margin) const
|
||||||
{
|
{
|
||||||
/*
|
/*
|
||||||
strings_t names {};
|
strings_t names {};
|
||||||
@@ -161,7 +161,7 @@ std::string Klammer_set::describe(int margin) const
|
|||||||
strings_t locations {};
|
strings_t locations {};
|
||||||
*/
|
*/
|
||||||
std::string result;
|
std::string result;
|
||||||
for (auto [name, k] : m_klammers) {
|
for (const auto& [name, k] : m_klammers) {
|
||||||
result += k.describe(margin) + "\n";
|
result += k.describe(margin) + "\n";
|
||||||
/*
|
/*
|
||||||
names.push_back(name);
|
names.push_back(name);
|
||||||
@@ -1,16 +1,16 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include "klammer.h"
|
#include "klammer.h"
|
||||||
#include "target_set.h"
|
#include "target_registry.h"
|
||||||
|
|
||||||
class Klammer_set
|
class Klammer_registry
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
Klammer_set() = default;
|
Klammer_registry() = default;
|
||||||
void add(Argtype_set argtypes, Target_set& targets,
|
void add(const Argtype_registry& argtypes, const Target_registry& targets,
|
||||||
std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end, std::vector<Katom>& katoms);
|
std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end, std::vector<Katom>& katoms);
|
||||||
void rationalize(Target_set targets);
|
void rationalize(const Target_registry& targets);
|
||||||
void check_klammer(std::string name, std::string target, Locator loc);
|
void check_klammer(const std::string& name, const std::string& target, const Locator& loc) const;
|
||||||
const std::vector<Katom>* constant_body(const std::string& name) const;
|
const std::vector<Katom>* constant_body(const std::string& name) const;
|
||||||
std::string instance_list(int margin) const;
|
std::string instance_list(int margin) const;
|
||||||
std::string describe(int margin=0) const;
|
std::string describe(int margin=0) const;
|
||||||
8
mac/klammerset.cpp
Normal file
8
mac/klammerset.cpp
Normal file
@@ -0,0 +1,8 @@
|
|||||||
|
#include "klammerset.h"
|
||||||
|
|
||||||
|
Klammerset::Klammerset(const std::string& symbol, const std::string& desc, const Locator& loc)
|
||||||
|
: m_symbol(symbol)
|
||||||
|
, m_desc(desc)
|
||||||
|
, m_loc(loc)
|
||||||
|
{
|
||||||
|
}
|
||||||
28
mac/klammerset.h
Normal file
28
mac/klammerset.h
Normal file
@@ -0,0 +1,28 @@
|
|||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <string>
|
||||||
|
#include <vector>
|
||||||
|
|
||||||
|
#include "locator.h"
|
||||||
|
|
||||||
|
// A Klammerset is the formal construct declared by the @@@klammerset system
|
||||||
|
// command: a named, logically related group of klammer definitions loaded
|
||||||
|
// together. The instance holds metadata and the file list only -- the
|
||||||
|
// klammers themselves live in the Machine's Klammer_registry (one flat,
|
||||||
|
// additive namespace; the definition modes govern collisions). Membership
|
||||||
|
// is provenance, not containment.
|
||||||
|
class Klammerset
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
Klammerset() = default;
|
||||||
|
Klammerset(const std::string& symbol, const std::string& desc, const Locator& loc);
|
||||||
|
|
||||||
|
std::string m_symbol {}; // registry key and command-line name (e.g. "sks")
|
||||||
|
std::string m_desc {}; // the logical relationship that makes this a set
|
||||||
|
std::string m_name {}; // display name (e.g. "Standard Klammer Set")
|
||||||
|
std::string m_author {};
|
||||||
|
std::string m_date {}; // last update; a date serves as the version
|
||||||
|
std::vector<std::string> m_requires {}; // klammerset declaration files, loaded first
|
||||||
|
std::vector<std::string> m_files {}; // definition files, loaded in list order
|
||||||
|
Locator m_loc {}; // the declaring file; relative names resolve against it
|
||||||
|
};
|
||||||
225
mac/klammerset_registry.cpp
Normal file
225
mac/klammerset_registry.cpp
Normal file
@@ -0,0 +1,225 @@
|
|||||||
|
#include <cctype>
|
||||||
|
#include <cstdlib>
|
||||||
|
#include <iomanip>
|
||||||
|
#include <sstream>
|
||||||
|
|
||||||
|
#include "klammerset_registry.h"
|
||||||
|
#include "error.h"
|
||||||
|
#include "file.h"
|
||||||
|
#include "log.h"
|
||||||
|
#include "util.h"
|
||||||
|
#include "show.h"
|
||||||
|
#include "katom.h"
|
||||||
|
|
||||||
|
Klammerset_registry::Klammerset_registry()
|
||||||
|
: m_parameters(Parameter_set("symbol | desc :name :author :date :requires :files"))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void Klammerset_registry::add(Klammerset klammerset)
|
||||||
|
{
|
||||||
|
(void)K::log(3, klammerset.m_symbol);
|
||||||
|
m_klammersets[klammerset.m_symbol] = klammerset;
|
||||||
|
m_symbols.push_back(klammerset.m_symbol);
|
||||||
|
}
|
||||||
|
|
||||||
|
std::optional<Klammerset> Klammerset_registry::add(
|
||||||
|
std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end, std::vector<Katom>& katoms)
|
||||||
|
{
|
||||||
|
(void)K::log(3, *begin, *(end - 1));
|
||||||
|
auto [positional, optional, rest] =
|
||||||
|
argument_split(begin + 1, end - 1, m_parameters.m_positional.size());
|
||||||
|
auto values = m_parameters.value_map(positional, optional, rest, begin->m_loc);
|
||||||
|
|
||||||
|
modify_type(katom_t::replaced, begin, end);
|
||||||
|
auto next_iter = end;
|
||||||
|
ignore_whitespace(next_iter, katoms);
|
||||||
|
|
||||||
|
std::string symbol = values["symbol"];
|
||||||
|
check_symbol(symbol, begin->m_loc);
|
||||||
|
if (has(symbol)) {
|
||||||
|
(void)K::log(2, "Klammerset \"" + symbol + "\" is already loaded; declaration skipped");
|
||||||
|
return std::nullopt;
|
||||||
|
}
|
||||||
|
|
||||||
|
// The filename lists follow the standard conventions (spaces allowed,
|
||||||
|
// standalone "/" separator). The existence rescue tests names against
|
||||||
|
// the declaring file's directory, where relative names are later
|
||||||
|
// resolved by Machine::load_klammerset_files.
|
||||||
|
fs::path declaring(begin->m_loc.m_filename);
|
||||||
|
std::string base_dir =
|
||||||
|
fs::exists(declaring) ? declaring.parent_path().string() : "";
|
||||||
|
|
||||||
|
Klammerset klammerset(symbol, values["desc"], begin->m_loc);
|
||||||
|
klammerset.m_name = values["name"];
|
||||||
|
klammerset.m_author = values["author"];
|
||||||
|
klammerset.m_date = values["date"];
|
||||||
|
klammerset.m_requires = resolve_filename_list(values["requires"], base_dir);
|
||||||
|
klammerset.m_files = resolve_filename_list(values["files"], base_dir);
|
||||||
|
add(klammerset);
|
||||||
|
return klammerset;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Klammerset_registry::check_symbol(const std::string& symbol, const Locator& loc) const
|
||||||
|
{
|
||||||
|
bool valid = !symbol.empty() && std::isalpha(static_cast<unsigned char>(symbol[0]));
|
||||||
|
for (char c : symbol) {
|
||||||
|
if (!std::isalnum(static_cast<unsigned char>(c)) && c != '_') {
|
||||||
|
valid = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!valid) {
|
||||||
|
throw Klammerset_error(
|
||||||
|
"The klammerset symbol \"" + symbol + "\" is not valid. A symbol begins "
|
||||||
|
"with a letter and contains only letters, digits, and underscores.",
|
||||||
|
loc);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
bool Klammerset_registry::has(const std::string& symbol) const
|
||||||
|
{
|
||||||
|
return m_klammersets.count(symbol) > 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
Klammerset Klammerset_registry::get(const std::string& symbol, const Locator& loc) const
|
||||||
|
{
|
||||||
|
if (has(symbol)) {
|
||||||
|
return m_klammersets.at(symbol);
|
||||||
|
} else {
|
||||||
|
throw Klammerset_error("Klammerset " + symbol + " does not exist", loc);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// --- The klammerset search path ---
|
||||||
|
|
||||||
|
bool is_klammerset_symbol(const std::string& name)
|
||||||
|
{
|
||||||
|
if (name.empty() || !std::isalpha(static_cast<unsigned char>(name[0]))) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
for (char c : name) {
|
||||||
|
if (!std::isalnum(static_cast<unsigned char>(c)) && c != '_') {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::vector<std::string> klammerset_search_dirs(const std::string& local_dir)
|
||||||
|
{
|
||||||
|
std::vector<std::string> result {};
|
||||||
|
// A repeated directory (e.g. the local stage already IS
|
||||||
|
// $KLAMMERTEXT_HOME) adds nothing and clutters error messages.
|
||||||
|
auto push_unique = [&result](const std::string& dir) {
|
||||||
|
std::string canonical = fs::weakly_canonical(dir).string();
|
||||||
|
if (!is_in(canonical, result)) {
|
||||||
|
result.push_back(canonical);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
if (!local_dir.empty()) {
|
||||||
|
push_unique(local_dir);
|
||||||
|
}
|
||||||
|
std::string paths {};
|
||||||
|
const char* env = std::getenv("KLAMMERTEXT_KLAMMERSETS");
|
||||||
|
if (env && *env) {
|
||||||
|
paths = env;
|
||||||
|
} else if (const char* home = std::getenv("HOME"); home && *home) {
|
||||||
|
paths = std::string(home) + "/.klammertext/klammersets";
|
||||||
|
}
|
||||||
|
std::stringstream ss(paths);
|
||||||
|
std::string dir;
|
||||||
|
while (std::getline(ss, dir, ':')) {
|
||||||
|
if (!dir.empty()) {
|
||||||
|
push_unique(dir);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (const char* kthome = std::getenv(klammertext_home_var.c_str()); kthome && *kthome) {
|
||||||
|
push_unique(kthome);
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
fs::path resolve_klammerset_symbol(
|
||||||
|
const std::string& symbol, const std::string& local_dir, const Locator& loc)
|
||||||
|
{
|
||||||
|
std::vector<std::string> dirs = klammerset_search_dirs(local_dir);
|
||||||
|
for (const std::string& dir : dirs) {
|
||||||
|
fs::path candidate = fs::path(dir) / symbol / (symbol + ".k");
|
||||||
|
if (fs::exists(candidate) && fs::is_regular_file(candidate)) {
|
||||||
|
return fs::weakly_canonical(candidate);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
throw Klammerset_error(
|
||||||
|
"The klammerset \"" + symbol + "\" was not found. A symbol x names the "
|
||||||
|
"declaration file x/x.k in one of the search directories: "
|
||||||
|
+ join(dirs, ", ")
|
||||||
|
+ ". Enter \"kdesc --klammerset\" to list the available klammersets.",
|
||||||
|
loc);
|
||||||
|
}
|
||||||
|
|
||||||
|
std::string describe_klammerset_search(const std::string& local_dir, int margin)
|
||||||
|
{
|
||||||
|
std::string tab(margin, ' ');
|
||||||
|
std::stringstream ss {};
|
||||||
|
std::map<std::string, std::string> first_hit {};
|
||||||
|
for (const std::string& dir : klammerset_search_dirs(local_dir)) {
|
||||||
|
if (!fs::is_directory(dir)) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
for (const auto& entry : fs::directory_iterator(dir)) {
|
||||||
|
if (!entry.is_directory()) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
std::string symbol = entry.path().filename().string();
|
||||||
|
fs::path declaration = entry.path() / (symbol + ".k");
|
||||||
|
if (!is_klammerset_symbol(symbol) || !fs::is_regular_file(declaration)) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
ss << tab << symbol << sp_arrow << declaration.string();
|
||||||
|
if (first_hit.count(symbol)) {
|
||||||
|
ss << " (shadowed by " << first_hit[symbol] << ")";
|
||||||
|
} else {
|
||||||
|
first_hit[symbol] = declaration.string();
|
||||||
|
}
|
||||||
|
ss << "\n";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (first_hit.empty()) {
|
||||||
|
ss << tab << "(no klammersets found)\n";
|
||||||
|
}
|
||||||
|
return ss.str();
|
||||||
|
}
|
||||||
|
|
||||||
|
std::string Klammerset_registry::describe(int margin, bool long_format) const
|
||||||
|
{
|
||||||
|
std::string tab(margin, ' ');
|
||||||
|
std::stringstream ss {};
|
||||||
|
std::vector<std::string> descs {};
|
||||||
|
for (const std::string& symbol : m_symbols) {
|
||||||
|
descs.push_back(m_klammersets.at(symbol).m_desc);
|
||||||
|
}
|
||||||
|
auto symbol_width = max_length(m_symbols);
|
||||||
|
auto desc_width = max_length(descs);
|
||||||
|
for (const std::string& symbol : m_symbols) {
|
||||||
|
const Klammerset& ks = m_klammersets.at(symbol);
|
||||||
|
if (long_format) {
|
||||||
|
ss << tab << std::setfill(' ') << std::setw(symbol_width) << std::left << symbol << " "
|
||||||
|
<< std::setw(desc_width) << std::left << ks.m_desc << " "
|
||||||
|
<< ks.m_loc.str() << "\n";
|
||||||
|
if (!ks.m_name.empty())
|
||||||
|
ss << tab << std::string(symbol_width, ' ') << " name: " << ks.m_name << "\n";
|
||||||
|
if (!ks.m_author.empty())
|
||||||
|
ss << tab << std::string(symbol_width, ' ') << " author: " << ks.m_author << "\n";
|
||||||
|
if (!ks.m_date.empty())
|
||||||
|
ss << tab << std::string(symbol_width, ' ') << " date: " << ks.m_date << "\n";
|
||||||
|
if (!ks.m_requires.empty())
|
||||||
|
ss << tab << std::string(symbol_width, ' ') << " requires: " << join(ks.m_requires, " / ") << "\n";
|
||||||
|
if (!ks.m_files.empty())
|
||||||
|
ss << tab << std::string(symbol_width, ' ') << " files: " << join(ks.m_files, " / ") << "\n";
|
||||||
|
} else {
|
||||||
|
ss << tab << std::setfill(' ') << std::setw(symbol_width) << std::left << symbol
|
||||||
|
<< sp_arrow << ks << "\n";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return ss.str();
|
||||||
|
}
|
||||||
63
mac/klammerset_registry.h
Normal file
63
mac/klammerset_registry.h
Normal file
@@ -0,0 +1,63 @@
|
|||||||
|
#pragma once
|
||||||
|
#include <map>
|
||||||
|
#include <optional>
|
||||||
|
#include <string>
|
||||||
|
|
||||||
|
#include "klammerset.h"
|
||||||
|
#include "argument_set.h"
|
||||||
|
#include "katom.h"
|
||||||
|
|
||||||
|
class Klammerset_registry
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
Klammerset_registry();
|
||||||
|
|
||||||
|
void add(Klammerset klammerset);
|
||||||
|
// Parse a @@@klammerset span. Returns the new Klammerset so the
|
||||||
|
// Machine can load its files, or nullopt when the symbol is already
|
||||||
|
// registered: a klammerset is loaded once, and a repeated declaration
|
||||||
|
// (typically reached through :requires) is skipped, not an error.
|
||||||
|
std::optional<Klammerset> add(std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end, std::vector<Katom>& katoms);
|
||||||
|
void check_symbol(const std::string& symbol, const Locator& loc) const;
|
||||||
|
|
||||||
|
bool has(const std::string& symbol) const;
|
||||||
|
Klammerset get(const std::string& symbol, const Locator& loc) const;
|
||||||
|
|
||||||
|
std::string describe(int margin=2, bool long_format=false) const;
|
||||||
|
|
||||||
|
std::map<std::string, Klammerset> m_klammersets {};
|
||||||
|
std::vector<std::string> m_symbols {};
|
||||||
|
Parameter_set m_parameters {};
|
||||||
|
};
|
||||||
|
|
||||||
|
// --- The klammerset search path (symbol -> declaration file) ---
|
||||||
|
|
||||||
|
// A bare identifier (letters, digits, underscores; starts with a letter)
|
||||||
|
// names a klammerset symbol; anything else -- a path component, an
|
||||||
|
// extension, a space -- is a filename used as given.
|
||||||
|
bool is_klammerset_symbol(const std::string& name);
|
||||||
|
|
||||||
|
// The directories searched for a klammerset symbol, most specific first:
|
||||||
|
// 1. local_dir -- the directory of whatever names the symbol: the input
|
||||||
|
// document's directory (ktext -k), the declaring file's directory
|
||||||
|
// (:requires), or the cwd when there is no document
|
||||||
|
// 2. the KLAMMERTEXT_KLAMMERSETS directories (colon-separated; default
|
||||||
|
// ~/.klammertext/klammersets), in listed order
|
||||||
|
// 3. $KLAMMERTEXT_HOME (the distribution's sets, e.g. sks/sks.k)
|
||||||
|
// A symbol x resolves to the first <dir>/x/x.k found, so a document-local
|
||||||
|
// set shadows an installed one, which shadows a distributed one. (This is
|
||||||
|
// deliberately the OPPOSITE order from the @eval module path, which puts
|
||||||
|
// the SKS directories first: a stray util.py next to a document shadowing
|
||||||
|
// an SKS module is an everyday accident, while a directory named sks/
|
||||||
|
// holding an sks.k next to a manuscript is not.)
|
||||||
|
std::vector<std::string> klammerset_search_dirs(const std::string& local_dir);
|
||||||
|
|
||||||
|
// Resolve a symbol to its declaration file; first hit wins. Throws a
|
||||||
|
// Klammerset_error naming the searched directories when nothing matches.
|
||||||
|
fs::path resolve_klammerset_symbol(
|
||||||
|
const std::string& symbol, const std::string& local_dir, const Locator& loc);
|
||||||
|
|
||||||
|
// The symbols available on the search path, with provenance; a symbol
|
||||||
|
// found again in a later directory is marked as shadowed. For
|
||||||
|
// kdesc --klammerset.
|
||||||
|
std::string describe_klammerset_search(const std::string& local_dir, int margin=2);
|
||||||
@@ -28,7 +28,7 @@ std::string abbreviate_location(
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
Locator::Locator(fs::path filename, int line, int chr)
|
Locator::Locator(const fs::path& filename, int line, int chr)
|
||||||
: m_filename(filename)
|
: m_filename(filename)
|
||||||
, m_line(line)
|
, m_line(line)
|
||||||
, m_chr(chr)
|
, m_chr(chr)
|
||||||
|
|||||||
@@ -23,7 +23,7 @@ public:
|
|||||||
, m_line(int(location.line()))
|
, m_line(int(location.line()))
|
||||||
, m_chr(int(location.column()))
|
, m_chr(int(location.column()))
|
||||||
{};
|
{};
|
||||||
Locator(fs::path filename, int line, int chr);
|
Locator(const fs::path& filename, int line, int chr);
|
||||||
std::string str(bool relative = false) const;
|
std::string str(bool relative = false) const;
|
||||||
std::string desc(bool relative = false) const;
|
std::string desc(bool relative = false) const;
|
||||||
std::string abbrev(bool include_chr=true) const;
|
std::string abbrev(bool include_chr=true) const;
|
||||||
|
|||||||
100
mac/machine.cpp
100
mac/machine.cpp
@@ -9,10 +9,10 @@
|
|||||||
#include "eval.h"
|
#include "eval.h"
|
||||||
|
|
||||||
Machine::Machine()
|
Machine::Machine()
|
||||||
: m_argtypes(Argtype_set())
|
: m_argtypes(Argtype_registry())
|
||||||
, m_state(State())
|
, m_state(State())
|
||||||
, m_targets(Target_set())
|
, m_targets(Target_registry())
|
||||||
, m_klammers(Klammer_set())
|
, m_klammers(Klammer_registry())
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
m_state.add_environment_frame();
|
m_state.add_environment_frame();
|
||||||
@@ -352,20 +352,80 @@ void Machine::extract_machine_definitions()
|
|||||||
if (m_katoms.empty()) {
|
if (m_katoms.empty()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
for (const auto& [op, cl] : find_spans(m_katoms, begin_machine_def, end_machine_def, true, command_name)) {
|
// A @@@klammerset declaration inserts its files' katoms into the stream
|
||||||
auto [begin, end] = find_span_katoms(m_katoms, op, cl);
|
// at the declaration point, invalidating the span list, so the scan
|
||||||
//std::string name = trim_char(begin->m_text, '@');
|
// restarts. Processed spans are marked replaced and are never found
|
||||||
std::string name = begin->m_text;
|
// again, which also bounds the restarts.
|
||||||
if (name == "@@@target") {
|
bool rescan = true;
|
||||||
m_targets.add(begin, end, m_katoms);
|
while (rescan) {
|
||||||
} else if (name == "@@@argtype") {
|
rescan = false;
|
||||||
m_argtypes.add(begin, end, m_katoms);
|
for (const auto& [op, cl] : find_spans(m_katoms, begin_machine_def, end_machine_def, true, command_name)) {
|
||||||
} else if (name == "@@@state") {
|
auto [begin, end] = find_span_katoms(m_katoms, op, cl);
|
||||||
m_state.parse_state_katoms(begin, end, m_katoms);
|
//std::string name = trim_char(begin->m_text, '@');
|
||||||
|
std::string name = begin->m_text;
|
||||||
|
if (name == "@@@target") {
|
||||||
|
m_targets.add(begin, end, m_katoms);
|
||||||
|
} else if (name == "@@@argtype") {
|
||||||
|
m_argtypes.add(begin, end, m_katoms);
|
||||||
|
} else if (name == "@@@state") {
|
||||||
|
m_state.parse_state_katoms(begin, end, m_katoms);
|
||||||
|
} else if (name == "@@@klammerset") {
|
||||||
|
if (auto klammerset = m_klammersets.add(begin, end, m_katoms)) {
|
||||||
|
load_klammerset_files(*klammerset, end);
|
||||||
|
rescan = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Machine::load_klammerset_files(const Klammerset& klammerset, katom_iter insert_at)
|
||||||
|
{
|
||||||
|
(void)K::log(2, "Loading klammerset \"" + klammerset.m_symbol + "\"");
|
||||||
|
// Relative names resolve against the declaring file's directory, never
|
||||||
|
// the cwd. :requires files are read before the set's own files; each
|
||||||
|
// holds its own @@@klammerset declaration, whose already-loaded guard
|
||||||
|
// makes repeated requirements a no-op.
|
||||||
|
fs::path declaring(klammerset.m_loc.m_filename);
|
||||||
|
fs::path base = fs::exists(declaring) ? declaring : fs::current_path();
|
||||||
|
std::string base_dir = (is_directory(base) ? base : base.parent_path()).string();
|
||||||
|
|
||||||
|
// A :requires entry may be a bare symbol, resolved on the klammerset
|
||||||
|
// search path with the declaring directory as the local stage; :files
|
||||||
|
// entries are always filenames (this set's own definition files).
|
||||||
|
std::vector<std::string> filenames {};
|
||||||
|
for (const auto& required : klammerset.m_requires) {
|
||||||
|
if (is_klammerset_symbol(required)) {
|
||||||
|
filenames.push_back(
|
||||||
|
resolve_klammerset_symbol(required, base_dir, klammerset.m_loc).string());
|
||||||
|
} else {
|
||||||
|
filenames.push_back(required);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
filenames.insert(filenames.end(), klammerset.m_files.begin(), klammerset.m_files.end());
|
||||||
|
|
||||||
|
// Collect all files into one list and insert once: insert_at is
|
||||||
|
// invalidated by the first insertion into m_katoms.
|
||||||
|
katom_list loaded {};
|
||||||
|
for (const auto& filename : filenames) {
|
||||||
|
fs::path pathname = resolve_relative_to(filename, base);
|
||||||
|
if (!fs::exists(pathname)) {
|
||||||
|
throw Klammerset_error(
|
||||||
|
"Klammerset \"" + klammerset.m_symbol + "\" lists the file \"" + filename
|
||||||
|
+ "\", which does not exist (resolved to \"" + pathname.string() + "\")",
|
||||||
|
klammerset.m_loc);
|
||||||
|
}
|
||||||
|
pathname = fs::canonical(pathname);
|
||||||
|
m_state.add_search_dir(pathname.parent_path().string());
|
||||||
|
std::string text = trim_right(string_from_file(pathname.string()));
|
||||||
|
katom_list ks = katomize(line_split(text), pathname);
|
||||||
|
process_katoms(ks, pathname);
|
||||||
|
loaded.insert(loaded.end(), ks.begin(), ks.end());
|
||||||
|
}
|
||||||
|
m_katoms.insert(insert_at, loaded.begin(), loaded.end());
|
||||||
|
}
|
||||||
|
|
||||||
void Machine::extract_klammer_definitions(katom_list katoms)
|
void Machine::extract_klammer_definitions(katom_list katoms)
|
||||||
{
|
{
|
||||||
fmsg() << katoms << "\n";
|
fmsg() << katoms << "\n";
|
||||||
@@ -489,12 +549,12 @@ katom_list Machine::apply_klammer(
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Machine::apply_klammer_set(
|
void Machine::apply_klammer_registry(
|
||||||
Klammer_set& klammer_set, katom_list& katoms, const std::string& target, katom_iter begin, katom_iter end)
|
Klammer_registry& klammer_registry, katom_list& katoms, const std::string& target, katom_iter begin, katom_iter end)
|
||||||
{
|
{
|
||||||
(void)K::log(3, "Klammer");
|
(void)K::log(3, "Klammer");
|
||||||
std::string name = trim_char(begin->m_text, '@');
|
std::string name = trim_char(begin->m_text, '@');
|
||||||
katom_list applied_katoms = apply_klammer(klammer_set.m_klammers[name], target, begin, end);
|
katom_list applied_katoms = apply_klammer(klammer_registry.m_klammers[name], target, begin, end);
|
||||||
for (auto& k : applied_katoms) {
|
for (auto& k : applied_katoms) {
|
||||||
if (k.m_type == katom_t::bar || k.m_type == katom_t::double_bar || k.m_type == katom_t::option_name) {
|
if (k.m_type == katom_t::bar || k.m_type == katom_t::double_bar || k.m_type == katom_t::option_name) {
|
||||||
k.m_type = katom_t::text;
|
k.m_type = katom_t::text;
|
||||||
@@ -504,16 +564,16 @@ void Machine::apply_klammer_set(
|
|||||||
}
|
}
|
||||||
|
|
||||||
void Machine::apply(
|
void Machine::apply(
|
||||||
Klammer_set& klammer_set, katom_list& katoms, const std::string& target)
|
Klammer_registry& klammer_registry, katom_list& katoms, const std::string& target)
|
||||||
{
|
{
|
||||||
(void)K::log(3, "Klammer_set");
|
(void)K::log(3, "Klammer_registry");
|
||||||
for (const auto& [op, cl] : find_spans(
|
for (const auto& [op, cl] : find_spans(
|
||||||
katoms, begin_klammer_apply, end_klammer_apply, true, command_name)) {
|
katoms, begin_klammer_apply, end_klammer_apply, true, command_name)) {
|
||||||
auto [begin, end] = find_span_katoms(katoms, op, cl);
|
auto [begin, end] = find_span_katoms(katoms, op, cl);
|
||||||
klammer_set.check_klammer(
|
klammer_registry.check_klammer(
|
||||||
klammer_name_from_katom(begin->m_text, begin->m_loc),
|
klammer_name_from_katom(begin->m_text, begin->m_loc),
|
||||||
target, begin->m_loc);
|
target, begin->m_loc);
|
||||||
apply_klammer_set(klammer_set, katoms, target, begin, end);
|
apply_klammer_registry(klammer_registry, katoms, target, begin, end);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -4,9 +4,10 @@
|
|||||||
|
|
||||||
// #include "source.h"
|
// #include "source.h"
|
||||||
#include "katom_list.h"
|
#include "katom_list.h"
|
||||||
#include "klammer_set.h"
|
#include "klammer_registry.h"
|
||||||
#include "target_set.h"
|
#include "klammerset_registry.h"
|
||||||
#include "argtype_set.h"
|
#include "target_registry.h"
|
||||||
|
#include "argtype_registry.h"
|
||||||
#include "state.h"
|
#include "state.h"
|
||||||
|
|
||||||
#include "error.h"
|
#include "error.h"
|
||||||
@@ -20,11 +21,12 @@ public:
|
|||||||
Machine();
|
Machine();
|
||||||
|
|
||||||
// Copy constructor
|
// Copy constructor
|
||||||
Machine(const Machine& other)
|
Machine(const Machine& other)
|
||||||
: m_argtypes(other.m_argtypes)
|
: m_argtypes(other.m_argtypes)
|
||||||
, m_state(other.m_state)
|
, m_state(other.m_state)
|
||||||
, m_targets(other.m_targets)
|
, m_targets(other.m_targets)
|
||||||
, m_klammers(other.m_klammers)
|
, m_klammers(other.m_klammers)
|
||||||
|
, m_klammersets(other.m_klammersets)
|
||||||
, m_result(other.m_result)
|
, m_result(other.m_result)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
@@ -35,6 +37,7 @@ public:
|
|||||||
m_state = other.m_state;
|
m_state = other.m_state;
|
||||||
m_targets = other.m_targets;
|
m_targets = other.m_targets;
|
||||||
m_klammers = other.m_klammers;
|
m_klammers = other.m_klammers;
|
||||||
|
m_klammersets = other.m_klammersets;
|
||||||
m_result = other.m_result;
|
m_result = other.m_result;
|
||||||
}
|
}
|
||||||
return *this;
|
return *this;
|
||||||
@@ -65,6 +68,7 @@ public:
|
|||||||
bool klammers=true, bool eval=true, bool cond=true, bool read=true);
|
bool klammers=true, bool eval=true, bool cond=true, bool read=true);
|
||||||
|
|
||||||
void expand_constant_klammers(katom_list& katoms, const Katom& op, const Katom& cl);
|
void expand_constant_klammers(katom_list& katoms, const Katom& op, const Katom& cl);
|
||||||
|
void load_klammerset_files(const Klammerset& klammerset, katom_iter insert_at);
|
||||||
void extract_machine_definitions();
|
void extract_machine_definitions();
|
||||||
void extract_klammer_definitions();
|
void extract_klammer_definitions();
|
||||||
void extract_klammer_definitions(katom_list katoms);
|
void extract_klammer_definitions(katom_list katoms);
|
||||||
@@ -72,18 +76,19 @@ public:
|
|||||||
|
|
||||||
katom_list apply_klammer(Klammer& klammer, const std::string& target, katom_iter arguments_begin, katom_iter arguments_end);
|
katom_list apply_klammer(Klammer& klammer, const std::string& target, katom_iter arguments_begin, katom_iter arguments_end);
|
||||||
|
|
||||||
void apply_klammer_set(Klammer_set& klammer_set,
|
void apply_klammer_registry(Klammer_registry& klammer_registry,
|
||||||
katom_list& katoms, const std::string& target, katom_iter begin, katom_iter end);
|
katom_list& katoms, const std::string& target, katom_iter begin, katom_iter end);
|
||||||
|
|
||||||
void apply(Klammer_set& klammer_set, katom_list& katoms, const std::string& target);
|
void apply(Klammer_registry& klammer_registry, katom_list& katoms, const std::string& target);
|
||||||
|
|
||||||
std::string run_phase_functions();
|
std::string run_phase_functions();
|
||||||
std::string apply(const std::string& target_name, bool final_processing=true, bool escape_characters=true);
|
std::string apply(const std::string& target_name, bool final_processing=true, bool escape_characters=true);
|
||||||
|
|
||||||
Argtype_set m_argtypes {};
|
Argtype_registry m_argtypes {};
|
||||||
State m_state {};
|
State m_state {};
|
||||||
Target_set m_targets {};
|
Target_registry m_targets {};
|
||||||
Klammer_set m_klammers {};
|
Klammer_registry m_klammers {};
|
||||||
|
Klammerset_registry m_klammersets {};
|
||||||
input_sources_t m_sources {};
|
input_sources_t m_sources {};
|
||||||
std::string m_result {};
|
std::string m_result {};
|
||||||
std::vector<Katom> m_katoms {};
|
std::vector<Katom> m_katoms {};
|
||||||
|
|||||||
58
mac/show.cpp
58
mac/show.cpp
@@ -461,12 +461,12 @@ std::ostream& operator<<(std::ostream& os, const Klammer::components& kc)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// Klammer_set
|
// Klammer_registry
|
||||||
|
|
||||||
std::ostream& operator<<(std::ostream& os, const Klammer_set& ks)
|
std::ostream& operator<<(std::ostream& os, const Klammer_registry& ks)
|
||||||
{
|
{
|
||||||
for (auto klam : ks.m_klammers) {
|
for (const auto& klam : ks.m_klammers) {
|
||||||
for (auto [k,v] : klam.second.m_defloc) {
|
for (const auto& [k,v] : klam.second.m_defloc) {
|
||||||
os << " " << k << sp_arrow << v << "\n";
|
os << " " << k << sp_arrow << v << "\n";
|
||||||
}
|
}
|
||||||
//klam.second.m_defloc.str() << "\n";
|
//klam.second.m_defloc.str() << "\n";
|
||||||
@@ -485,30 +485,62 @@ void show_arrow_pair(std::ostream& os, std::pair<std::string,std::string> transf
|
|||||||
std::ostream& operator<<(std::ostream& os, const Target& t)
|
std::ostream& operator<<(std::ostream& os, const Target& t)
|
||||||
{
|
{
|
||||||
os << "<\U0001D517" << broken_bar << t.m_name << broken_bar << t.m_desc << broken_bar;
|
os << "<\U0001D517" << broken_bar << t.m_name << broken_bar << t.m_desc << broken_bar;
|
||||||
for (auto i : t.m_includes) {
|
for (const auto& i : t.m_includes) {
|
||||||
os << i << right_arrow << t.m_name << broken_bar;
|
os << i << right_arrow << t.m_name << broken_bar;
|
||||||
}
|
}
|
||||||
for (auto p : t.m_provides) {
|
for (const auto& p : t.m_provides) {
|
||||||
os << t.m_name << right_arrow << p << broken_bar;
|
os << t.m_name << right_arrow << p << broken_bar;
|
||||||
}
|
}
|
||||||
os << ">";
|
os << ">";
|
||||||
return os;
|
return os;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Target_set
|
// Target_registry
|
||||||
|
|
||||||
std::ostream& operator<<(std::ostream& os, const Target_set& ts)
|
std::ostream& operator<<(std::ostream& os, const Target_registry& ts)
|
||||||
{
|
{
|
||||||
size_t width = 0;
|
size_t width = 0;
|
||||||
for (auto t : ts.m_targets) {
|
for (const auto& t : ts.m_targets) {
|
||||||
width = std::max(width, t.first.size());
|
width = std::max(width, t.first.size());
|
||||||
}
|
}
|
||||||
for (auto [name, target] : ts.m_targets) {
|
for (const auto& [name, target] : ts.m_targets) {
|
||||||
os << std::setw(width) << name << sp_arrow << target << "\n";
|
os << std::setw(width) << name << sp_arrow << target << "\n";
|
||||||
}
|
}
|
||||||
return os;
|
return os;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Klammerset
|
||||||
|
|
||||||
|
std::ostream& operator<<(std::ostream& os, const Klammerset& ks)
|
||||||
|
{
|
||||||
|
os << "<\U0001D516" << broken_bar << ks.m_symbol << broken_bar << ks.m_desc;
|
||||||
|
if (!ks.m_date.empty()) {
|
||||||
|
os << broken_bar << ks.m_date;
|
||||||
|
}
|
||||||
|
if (!ks.m_requires.empty()) {
|
||||||
|
os << broken_bar << "requires " << join(ks.m_requires, " / ");
|
||||||
|
}
|
||||||
|
if (!ks.m_files.empty()) {
|
||||||
|
os << broken_bar << join(ks.m_files, " / ");
|
||||||
|
}
|
||||||
|
os << ">";
|
||||||
|
return os;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Klammerset_registry
|
||||||
|
|
||||||
|
std::ostream& operator<<(std::ostream& os, const Klammerset_registry& kr)
|
||||||
|
{
|
||||||
|
size_t width = 0;
|
||||||
|
for (const auto& k : kr.m_klammersets) {
|
||||||
|
width = std::max(width, k.first.size());
|
||||||
|
}
|
||||||
|
for (const auto& [symbol, klammerset] : kr.m_klammersets) {
|
||||||
|
os << std::setw(width) << symbol << sp_arrow << klammerset << "\n";
|
||||||
|
}
|
||||||
|
return os;
|
||||||
|
}
|
||||||
|
|
||||||
// Machine
|
// Machine
|
||||||
|
|
||||||
|
|
||||||
@@ -537,6 +569,7 @@ std::ostream& operator<<(std::ostream& os, const Machine& m)
|
|||||||
std::string argtypes_desc = m.m_argtypes.describe(false, 8);
|
std::string argtypes_desc = m.m_argtypes.describe(false, 8);
|
||||||
std::string state_desc = m.m_state.describe(false, 3);
|
std::string state_desc = m.m_state.describe(false, 3);
|
||||||
std::string targets_desc = m.m_targets.describe(4);
|
std::string targets_desc = m.m_targets.describe(4);
|
||||||
|
std::string klammersets_desc = m.m_klammersets.describe(4);
|
||||||
std::string klammer_desc = m.m_klammers.describe(2);
|
std::string klammer_desc = m.m_klammers.describe(2);
|
||||||
std::string source_desc = describe_sources(m);
|
std::string source_desc = describe_sources(m);
|
||||||
|
|
||||||
@@ -544,12 +577,13 @@ std::ostream& operator<<(std::ostream& os, const Machine& m)
|
|||||||
<< label("Sources", m.m_sources.size()) << source_desc << "\n"
|
<< label("Sources", m.m_sources.size()) << source_desc << "\n"
|
||||||
<< label("Argtypes", m.m_argtypes.m_names.size()) << argtypes_desc << "\n"
|
<< label("Argtypes", m.m_argtypes.m_names.size()) << argtypes_desc << "\n"
|
||||||
<< label("Targets", m.m_targets.m_names.size()) << targets_desc << "\n"
|
<< label("Targets", m.m_targets.m_names.size()) << targets_desc << "\n"
|
||||||
|
<< label("Klammersets", m.m_klammersets.m_symbols.size()) << klammersets_desc << "\n"
|
||||||
<< label("Klammers", m.m_klammers.m_klammers.size()) << klammer_desc << "\n"
|
<< label("Klammers", m.m_klammers.m_klammers.size()) << klammer_desc << "\n"
|
||||||
<< label("State", m.m_state.m_frames.size()) << state_desc;
|
<< label("State", m.m_state.m_frames.size()) << state_desc;
|
||||||
return os;
|
return os;
|
||||||
}
|
}
|
||||||
|
|
||||||
void modify_stream(std::string name)
|
void modify_stream(const std::string& name)
|
||||||
{
|
{
|
||||||
if (name == "all") std::cout << kall;
|
if (name == "all") std::cout << kall;
|
||||||
if (name == "type") std::cout << ktype;
|
if (name == "type") std::cout << ktype;
|
||||||
|
|||||||
21
mac/show.h
21
mac/show.h
@@ -8,9 +8,10 @@
|
|||||||
#include "argtype.h"
|
#include "argtype.h"
|
||||||
#include "argument.h"
|
#include "argument.h"
|
||||||
#include "klammer.h"
|
#include "klammer.h"
|
||||||
#include "klammer_set.h"
|
#include "klammer_registry.h"
|
||||||
|
#include "klammerset_registry.h"
|
||||||
#include "state.h"
|
#include "state.h"
|
||||||
#include "target_set.h"
|
#include "target_registry.h"
|
||||||
#include "machine.h"
|
#include "machine.h"
|
||||||
#include "file.h"
|
#include "file.h"
|
||||||
|
|
||||||
@@ -143,16 +144,22 @@ std::ostream& operator<<(std::ostream& os, const Klammer::variable_map_t& vm);
|
|||||||
// Klammer::components
|
// Klammer::components
|
||||||
std::ostream& operator<<(std::ostream& os, const Klammer::components& kc);
|
std::ostream& operator<<(std::ostream& os, const Klammer::components& kc);
|
||||||
|
|
||||||
// Klammer_set
|
// Klammer_registry
|
||||||
std::ostream& operator<<(std::ostream& os, const Klammer_set& ks);
|
std::ostream& operator<<(std::ostream& os, const Klammer_registry& ks);
|
||||||
|
|
||||||
// Target
|
// Target
|
||||||
std::ostream& operator<<(std::ostream& os, const Target& t);
|
std::ostream& operator<<(std::ostream& os, const Target& t);
|
||||||
|
|
||||||
// Target_set
|
// Target_registry
|
||||||
std::ostream& operator<<(std::ostream& os, const Target_set& ts);
|
std::ostream& operator<<(std::ostream& os, const Target_registry& ts);
|
||||||
|
|
||||||
|
// Klammerset
|
||||||
|
std::ostream& operator<<(std::ostream& os, const Klammerset& ks);
|
||||||
|
|
||||||
|
// Klammerset_registry
|
||||||
|
std::ostream& operator<<(std::ostream& os, const Klammerset_registry& kr);
|
||||||
|
|
||||||
// Machine
|
// Machine
|
||||||
std::ostream& operator<<(std::ostream& os, const Machine& m);
|
std::ostream& operator<<(std::ostream& os, const Machine& m);
|
||||||
|
|
||||||
void modify_stream(std::string name);
|
void modify_stream(const std::string& name);
|
||||||
|
|||||||
@@ -10,7 +10,7 @@
|
|||||||
|
|
||||||
int State::class_id = 0;
|
int State::class_id = 0;
|
||||||
|
|
||||||
bool Var::defined()
|
bool Var::defined() const
|
||||||
{
|
{
|
||||||
return !m_name.empty();
|
return !m_name.empty();
|
||||||
}
|
}
|
||||||
@@ -24,18 +24,19 @@ std::vector<std::string> Frame::names() const
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Frame::set(std::string name, std::string value,
|
void Frame::set(const std::string& name, const std::string& value,
|
||||||
std::string delim, std::string desc, Locator loc, Argtype argtype)
|
const std::string& delim, const std::string& desc, const Locator& loc,
|
||||||
|
const Argtype& argtype)
|
||||||
{
|
{
|
||||||
Var v(name, value, delim, desc, loc, argtype);
|
Var v(name, value, delim, desc, loc, argtype);
|
||||||
m_vars[name] = v;
|
m_vars[name] = v;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::pair<Var, bool> Frame::get(std::string name)
|
std::pair<Var, bool> Frame::get(const std::string& name) const
|
||||||
{
|
{
|
||||||
std::pair<Var, bool> result {Var(), false};
|
std::pair<Var, bool> result {Var(), false};
|
||||||
if (m_vars.contains(name)) {
|
if (m_vars.contains(name)) {
|
||||||
result = {m_vars[name], true};
|
result = {m_vars.at(name), true};
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
@@ -43,7 +44,7 @@ std::pair<Var, bool> Frame::get(std::string name)
|
|||||||
// State
|
// State
|
||||||
|
|
||||||
|
|
||||||
void State::open_frame(std::string name)
|
void State::open_frame(const std::string& name)
|
||||||
{
|
{
|
||||||
Frame f(name);
|
Frame f(name);
|
||||||
// m_frames.push_back(f);
|
// m_frames.push_back(f);
|
||||||
@@ -58,19 +59,20 @@ void State::close_frame()
|
|||||||
}
|
}
|
||||||
// Preserve altered machine state:
|
// Preserve altered machine state:
|
||||||
string_map machine_state {};
|
string_map machine_state {};
|
||||||
for (auto [name, var] : m_frames[0].m_vars) {
|
for (const auto& [name, var] : m_frames[0].m_vars) {
|
||||||
if (contains(name, "K_")) {
|
if (contains(name, "K_")) {
|
||||||
machine_state[name] = var.m_value;
|
machine_state[name] = var.m_value;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
m_frames.erase(m_frames.begin());
|
m_frames.erase(m_frames.begin());
|
||||||
for (auto [name, value] : machine_state) {
|
for (const auto& [name, value] : machine_state) {
|
||||||
set(name, value, true);
|
set(name, value, true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void State::set(std::string name, std::string value, bool update,
|
void State::set(const std::string& name, const std::string& value, bool update,
|
||||||
std::string delim, std::string desc, Locator loc, Argtype argtype)
|
const std::string& delim, const std::string& desc, const Locator& loc,
|
||||||
|
const Argtype& argtype)
|
||||||
{
|
{
|
||||||
if (m_frames.empty()) {
|
if (m_frames.empty()) {
|
||||||
std::stringstream ss {};
|
std::stringstream ss {};
|
||||||
@@ -89,9 +91,9 @@ void State::set(std::string name, std::string value, bool update,
|
|||||||
m_frames[0].set(name, value, delim, desc, loc, argtype);
|
m_frames[0].set(name, value, delim, desc, loc, argtype);
|
||||||
}
|
}
|
||||||
|
|
||||||
void State::set(std::map<std::string, std::string> varmap)
|
void State::set(const std::map<std::string, std::string>& varmap)
|
||||||
{
|
{
|
||||||
for (auto [k, v] : varmap) {
|
for (const auto& [k, v] : varmap) {
|
||||||
set(k, v);
|
set(k, v);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -107,7 +109,7 @@ void State::set(const std::map<std::string, std::string>& varmap,
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void State::replace(std::string name, std::string value, bool error_if_not_defined)
|
void State::replace(const std::string& name, const std::string& value, bool error_if_not_defined)
|
||||||
{
|
{
|
||||||
if (error_if_not_defined && !get(name).defined()) {
|
if (error_if_not_defined && !get(name).defined()) {
|
||||||
std::stringstream ss {};
|
std::stringstream ss {};
|
||||||
@@ -120,14 +122,14 @@ void State::replace(std::string name, std::string value, bool error_if_not_defin
|
|||||||
void State::add_environment_frame()
|
void State::add_environment_frame()
|
||||||
{
|
{
|
||||||
open_frame(klammerstate::shell_environment_name);
|
open_frame(klammerstate::shell_environment_name);
|
||||||
for (auto [name, value] : environment_variables()) {
|
for (const auto& [name, value] : environment_variables()) {
|
||||||
set(name, value);
|
set(name, value);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Var State::get(std::string name, bool error_if_not_defined, Locator loc)
|
Var State::get(const std::string& name, bool error_if_not_defined, const Locator& loc) const
|
||||||
{
|
{
|
||||||
for (auto f : m_frames) {
|
for (const auto& f : m_frames) {
|
||||||
auto [result, found] = f.get(name);
|
auto [result, found] = f.get(name);
|
||||||
if (found) {
|
if (found) {
|
||||||
return result;
|
return result;
|
||||||
@@ -141,12 +143,12 @@ Var State::get(std::string name, bool error_if_not_defined, Locator loc)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string State::value(std::string name, bool error_if_not_defined, Locator loc)
|
std::string State::value(const std::string& name, bool error_if_not_defined, const Locator& loc) const
|
||||||
{
|
{
|
||||||
return get(name, error_if_not_defined, loc).m_value;
|
return get(name, error_if_not_defined, loc).m_value;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string State::subst(std::string text, bool quote_values)
|
std::string State::subst(const std::string& text, bool quote_values) const
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
std::string result = text;
|
std::string result = text;
|
||||||
@@ -198,7 +200,8 @@ void State::subst(katom_iter begin, katom_iter end)
|
|||||||
}
|
}
|
||||||
|
|
||||||
void prohibit_change_of_description(
|
void prohibit_change_of_description(
|
||||||
std::string name, bool defined, std::string old_desc, std::string new_desc, Locator old_loc, Locator loc)
|
const std::string& name, bool defined, const std::string& old_desc,
|
||||||
|
const std::string& new_desc, const Locator& old_loc, const Locator& loc)
|
||||||
{
|
{
|
||||||
if (defined && !old_desc.empty() && !new_desc.empty()) {
|
if (defined && !old_desc.empty() && !new_desc.empty()) {
|
||||||
std::stringstream ss {};
|
std::stringstream ss {};
|
||||||
@@ -216,7 +219,7 @@ void prohibit_change_of_description(
|
|||||||
|
|
||||||
// Parameter_set m_parameters = Parameter_set("name :value :append :replace :delim :desc");
|
// Parameter_set m_parameters = Parameter_set("name :value :append :replace :delim :desc");
|
||||||
|
|
||||||
void State::parse_state_katoms(katom_iter begin, katom_iter end, katom_list katoms)
|
void State::parse_state_katoms(katom_iter begin, katom_iter end, katom_list& katoms)
|
||||||
{
|
{
|
||||||
(void)K::log(3, *begin, *(end-1));
|
(void)K::log(3, *begin, *(end-1));
|
||||||
// std::cout << "parse_katoms: " << std::pair(begin + 1, end - 1) << "\n";
|
// std::cout << "parse_katoms: " << std::pair(begin + 1, end - 1) << "\n";
|
||||||
@@ -246,11 +249,11 @@ void State::parse_state_katoms(katom_iter begin, katom_iter end, katom_list kato
|
|||||||
ignore_whitespace(next_iter, katoms);
|
ignore_whitespace(next_iter, katoms);
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<std::string> State::all_names()
|
std::vector<std::string> State::all_names() const
|
||||||
{
|
{
|
||||||
std::vector<std::string> result {};
|
std::vector<std::string> result {};
|
||||||
for (Frame f : m_frames) {
|
for (const Frame& f : m_frames) {
|
||||||
for (auto [name, var] : f.m_vars) {
|
for (const auto& [name, var] : f.m_vars) {
|
||||||
// std::cout << "Name: " << name << "\n";
|
// std::cout << "Name: " << name << "\n";
|
||||||
result.push_back(name);
|
result.push_back(name);
|
||||||
}
|
}
|
||||||
@@ -282,7 +285,7 @@ std::string State::python_code()
|
|||||||
// the file whose @eval names it is found regardless of the cwd.
|
// the file whose @eval names it is found regardless of the cwd.
|
||||||
python_dirs.insert(python_dirs.end(),
|
python_dirs.insert(python_dirs.end(),
|
||||||
m_search_dirs.begin(), m_search_dirs.end());
|
m_search_dirs.begin(), m_search_dirs.end());
|
||||||
for (auto d : python_dirs) {
|
for (const auto& d : python_dirs) {
|
||||||
auto python_files = pathnames_with_extension(d, "py");
|
auto python_files = pathnames_with_extension(d, "py");
|
||||||
if (!python_files.empty()) {
|
if (!python_files.empty()) {
|
||||||
ss << "sys.path.append('" << d << "')\n";
|
ss << "sys.path.append('" << d << "')\n";
|
||||||
@@ -308,12 +311,12 @@ std::string State::describe(bool show_environment, int margin_size) const
|
|||||||
std::string margin(margin_size, ' ');
|
std::string margin(margin_size, ' ');
|
||||||
int i = m_frames.size() - 1;
|
int i = m_frames.size() - 1;
|
||||||
std::stringstream ss {};
|
std::stringstream ss {};
|
||||||
for (auto f : m_frames) {
|
for (const auto& f : m_frames) {
|
||||||
int width = max_key_length(f.m_vars);
|
int width = max_key_length(f.m_vars);
|
||||||
ss << margin << "Frame " << i-- << ": " << f.m_name << "\n";
|
ss << margin << "Frame " << i-- << ": " << f.m_name << "\n";
|
||||||
if ((f.m_name != klammerstate::shell_environment_name) ||
|
if ((f.m_name != klammerstate::shell_environment_name) ||
|
||||||
(show_environment && f.m_name == klammerstate::shell_environment_name)) {
|
(show_environment && f.m_name == klammerstate::shell_environment_name)) {
|
||||||
for (auto [key, value] : f.m_vars) {
|
for (const auto& [key, value] : f.m_vars) {
|
||||||
std::string print_value = value.m_value;
|
std::string print_value = value.m_value;
|
||||||
if (print_value == klammerstate::no_value) {
|
if (print_value == klammerstate::no_value) {
|
||||||
print_value = "<no-value>";
|
print_value = "<no-value>";
|
||||||
|
|||||||
40
mac/state.h
40
mac/state.h
@@ -14,9 +14,9 @@ class Var
|
|||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
Var() = default;
|
Var() = default;
|
||||||
Var(std::string name, std::string value=klammerstate::no_value,
|
Var(const std::string& name, const std::string& value=klammerstate::no_value,
|
||||||
std::string delim=":", std::string desc="", Locator loc=Locator(),
|
const std::string& delim=":", const std::string& desc="", const Locator& loc=Locator(),
|
||||||
Argtype argtype=Argtype())
|
const Argtype& argtype=Argtype())
|
||||||
: m_name(name)
|
: m_name(name)
|
||||||
, m_value(value)
|
, m_value(value)
|
||||||
, m_delim(delim)
|
, m_delim(delim)
|
||||||
@@ -24,7 +24,7 @@ public:
|
|||||||
, m_loc(loc)
|
, m_loc(loc)
|
||||||
, m_argtype(argtype)
|
, m_argtype(argtype)
|
||||||
{};
|
{};
|
||||||
bool defined();
|
bool defined() const;
|
||||||
|
|
||||||
std::string m_name {};
|
std::string m_name {};
|
||||||
std::string m_value {};
|
std::string m_value {};
|
||||||
@@ -41,15 +41,15 @@ inline std::string shell_environment_name = "Shell environment";
|
|||||||
class Frame
|
class Frame
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
Frame(std::string name)
|
Frame(const std::string& name)
|
||||||
: m_name(name)
|
: m_name(name)
|
||||||
{};
|
{};
|
||||||
|
|
||||||
std::vector<std::string> names() const;
|
std::vector<std::string> names() const;
|
||||||
void set(std::string name, std::string value,
|
void set(const std::string& name, const std::string& value,
|
||||||
std::string delim=":", std::string desc="", Locator loc=Locator(),
|
const std::string& delim=":", const std::string& desc="", const Locator& loc=Locator(),
|
||||||
Argtype argtype=Argtype());
|
const Argtype& argtype=Argtype());
|
||||||
std::pair<Var, bool> get(std::string name);
|
std::pair<Var, bool> get(const std::string& name) const;
|
||||||
|
|
||||||
std::string m_name {};
|
std::string m_name {};
|
||||||
std::map<std::string, Var> m_vars {};
|
std::map<std::string, Var> m_vars {};
|
||||||
@@ -59,24 +59,24 @@ class State
|
|||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
static int class_id;
|
static int class_id;
|
||||||
void open_frame(std::string name);
|
void open_frame(const std::string& name);
|
||||||
void close_frame();
|
void close_frame();
|
||||||
void set(std::string name, std::string value, bool update=false,
|
void set(const std::string& name, const std::string& value, bool update=false,
|
||||||
std::string delim=" ", std::string desc="", Locator loc=Locator(),
|
const std::string& delim=" ", const std::string& desc="", const Locator& loc=Locator(),
|
||||||
Argtype argtype=Argtype());
|
const Argtype& argtype=Argtype());
|
||||||
void set(std::map<std::string, std::string> varmap);
|
void set(const std::map<std::string, std::string>& varmap);
|
||||||
void set(const std::map<std::string, std::string>& varmap,
|
void set(const std::map<std::string, std::string>& varmap,
|
||||||
const Parameter_set& parameters);
|
const Parameter_set& parameters);
|
||||||
void replace(std::string name, std::string value, bool error_if_not_defined=true);
|
void replace(const std::string& name, const std::string& value, bool error_if_not_defined=true);
|
||||||
void add_environment_frame();
|
void add_environment_frame();
|
||||||
Var get(std::string name, bool error_if_not_defined=false, Locator loc=Locator());
|
Var get(const std::string& name, bool error_if_not_defined=false, const Locator& loc=Locator()) const;
|
||||||
std::string value(std::string name, bool error_if_not_defined=true, Locator loc=Locator());
|
std::string value(const std::string& name, bool error_if_not_defined=true, const Locator& loc=Locator()) const;
|
||||||
|
|
||||||
std::string subst(std::string text, bool quote_values=false);
|
std::string subst(const std::string& text, bool quote_values=false) const;
|
||||||
void subst(std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end);
|
void subst(std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end);
|
||||||
|
|
||||||
void parse_state_katoms(std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end, katom_list katoms);
|
void parse_state_katoms(std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end, katom_list& katoms);
|
||||||
std::vector<std::string> all_names();
|
std::vector<std::string> all_names() const;
|
||||||
void add_search_dir(const std::string& dir);
|
void add_search_dir(const std::string& dir);
|
||||||
std::string python_code();
|
std::string python_code();
|
||||||
std::string describe(bool show_environment=false, int margin_size=2) const;
|
std::string describe(bool show_environment=false, int margin_size=2) const;
|
||||||
|
|||||||
@@ -7,32 +7,32 @@
|
|||||||
//#include "text.h"
|
//#include "text.h"
|
||||||
#include "util.h"
|
#include "util.h"
|
||||||
|
|
||||||
void Target::add_transform(std::string original, std::string transformed)
|
void Target::add_transform(const std::string& original, const std::string& transformed)
|
||||||
{
|
{
|
||||||
m_transforms.push_back({original, transformed});
|
m_transforms.push_back({original, transformed});
|
||||||
}
|
}
|
||||||
|
|
||||||
void Target::add_transforms(std::string transforms)
|
void Target::add_transforms(const std::string& transforms)
|
||||||
{
|
{
|
||||||
add_transforms(parse_transforms(transforms));
|
add_transforms(parse_transforms(transforms));
|
||||||
}
|
}
|
||||||
|
|
||||||
void Target::add_transforms(string_pairs transforms)
|
void Target::add_transforms(const string_pairs& transforms)
|
||||||
{
|
{
|
||||||
for (auto [old_str, new_str] : transforms) {
|
for (const auto& [old_str, new_str] : transforms) {
|
||||||
add_transform(old_str, new_str);
|
add_transform(old_str, new_str);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void Target::transform(katom_list& katoms)
|
void Target::transform(katom_list& katoms) const
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
std::for_each(
|
std::for_each(
|
||||||
katoms.begin(), katoms.end(),
|
katoms.begin(), katoms.end(),
|
||||||
[this] (Katom& k) {
|
[this] (Katom& k) {
|
||||||
// std::cout << "transform: " << k << "\n";
|
// std::cout << "transform: " << k << "\n";
|
||||||
if (k.m_type != katom_t::literal) {
|
if (k.m_type != katom_t::literal) {
|
||||||
for (auto [a, b] : this->m_transforms) {
|
for (const auto& [a, b] : this->m_transforms) {
|
||||||
// std::cout << " " << a << right_arrow << b << "\n";
|
// std::cout << " " << a << right_arrow << b << "\n";
|
||||||
k.m_text = string_replace(k.m_text, a, b);
|
k.m_text = string_replace(k.m_text, a, b);
|
||||||
}
|
}
|
||||||
@@ -41,7 +41,7 @@ void Target::transform(katom_list& katoms)
|
|||||||
}
|
}
|
||||||
|
|
||||||
std::vector<std::pair<std::string, std::string>>
|
std::vector<std::pair<std::string, std::string>>
|
||||||
parse_transforms(std::string transform_string)
|
parse_transforms(const std::string& transform_string)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
if (trim(transform_string).empty()) return {};
|
if (trim(transform_string).empty()) return {};
|
||||||
@@ -59,7 +59,7 @@ parse_transforms(std::string transform_string)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Target::add_escapes(std::string escape_spec)
|
void Target::add_escapes(const std::string& escape_spec)
|
||||||
{
|
{
|
||||||
auto words = word_split(escape_spec);
|
auto words = word_split(escape_spec);
|
||||||
for (size_t i = 0; i + 1 < words.size(); i += 2) {
|
for (size_t i = 0; i + 1 < words.size(); i += 2) {
|
||||||
@@ -142,9 +142,9 @@ std::string hide_structural_characters(const std::string& s)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Target::add_after_apply(std::string function_specs)
|
void Target::add_after_apply(const std::string& function_specs)
|
||||||
{
|
{
|
||||||
for (auto f : regex_split(function_specs, std::regex(R"(\s+;\s+)"), true)) {
|
for (const auto& f : regex_split(function_specs, std::regex(R"(\s+;\s+)"), true)) {
|
||||||
// msg() << "Add " << m_name << " after-apply: " << f << "\n";
|
// msg() << "Add " << m_name << " after-apply: " << f << "\n";
|
||||||
m_after_apply.push_back(f);
|
m_after_apply.push_back(f);
|
||||||
}
|
}
|
||||||
|
|||||||
20
mac/target.h
20
mac/target.h
@@ -11,25 +11,25 @@ class Target
|
|||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
Target() = default;
|
Target() = default;
|
||||||
// Target(std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end, Argtype_set argtypes);
|
// Target(std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end, Argtype_registry argtypes);
|
||||||
Target(std::string name, std::string desc, Locator loc)
|
Target(const std::string& name, const std::string& desc, const Locator& loc)
|
||||||
: m_name(name)
|
: m_name(name)
|
||||||
, m_desc(desc)
|
, m_desc(desc)
|
||||||
, m_loc(loc)
|
, m_loc(loc)
|
||||||
{};
|
{};
|
||||||
|
|
||||||
void add_transform(std::string original, std::string transformed);
|
void add_transform(const std::string& original, const std::string& transformed);
|
||||||
void add_transforms(std::string transforms);
|
void add_transforms(const std::string& transforms);
|
||||||
void add_transforms(std::vector<std::pair<std::string, std::string>> transforms);
|
void add_transforms(const std::vector<std::pair<std::string, std::string>>& transforms);
|
||||||
void transform(std::vector<Katom>& katoms);
|
void transform(std::vector<Katom>& katoms) const;
|
||||||
|
|
||||||
void add_escapes(std::string escape_spec);
|
void add_escapes(const std::string& escape_spec);
|
||||||
std::string escape_text(std::string text) const;
|
std::string escape_text(std::string text) const;
|
||||||
std::string unescape_text(std::string text) const;
|
std::string unescape_text(std::string text) const;
|
||||||
std::string resolve_escapes(std::string text) const;
|
std::string resolve_escapes(std::string text) const;
|
||||||
static std::string escape_marker(const std::string& ch);
|
static std::string escape_marker(const std::string& ch);
|
||||||
|
|
||||||
void add_after_apply(std::string function_specs);
|
void add_after_apply(const std::string& function_specs);
|
||||||
|
|
||||||
std::string m_name {};
|
std::string m_name {};
|
||||||
std::string m_desc {};
|
std::string m_desc {};
|
||||||
@@ -40,13 +40,13 @@ public:
|
|||||||
Locator m_loc {};
|
Locator m_loc {};
|
||||||
std::vector<std::pair<std::string, std::string>> m_transforms {};
|
std::vector<std::pair<std::string, std::string>> m_transforms {};
|
||||||
std::vector<std::pair<std::string, std::string>> m_escapes {};
|
std::vector<std::pair<std::string, std::string>> m_escapes {};
|
||||||
// Argtype_set m_argtypes {};
|
// Argtype_registry m_argtypes {};
|
||||||
|
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
std::vector<std::pair<std::string, std::string>>
|
std::vector<std::pair<std::string, std::string>>
|
||||||
parse_transforms(std::string transform_string);
|
parse_transforms(const std::string& transform_string);
|
||||||
|
|
||||||
// Decode every KTESC<hex>KTESC marker in text back to its original
|
// Decode every KTESC<hex>KTESC marker in text back to its original
|
||||||
// characters. Used for the final output (after target-declared escapes have
|
// characters. Used for the final output (after target-declared escapes have
|
||||||
|
|||||||
@@ -1,8 +1,7 @@
|
|||||||
#include <sstream>
|
#include <sstream>
|
||||||
#include <iterator>
|
#include <iterator>
|
||||||
#include <algorithm>
|
|
||||||
|
|
||||||
#include "target_set.h"
|
#include "target_registry.h"
|
||||||
#include "error.h"
|
#include "error.h"
|
||||||
#include "log.h"
|
#include "log.h"
|
||||||
#include "util.h"
|
#include "util.h"
|
||||||
@@ -10,10 +9,10 @@
|
|||||||
#include "log.h"
|
#include "log.h"
|
||||||
#include "katom.h"
|
#include "katom.h"
|
||||||
|
|
||||||
std::string Target_set::declare_name = "k";
|
std::string Target_registry::declare_name = "k";
|
||||||
std::string Target_set::general_name = "*";
|
std::string Target_registry::general_name = "*";
|
||||||
|
|
||||||
Target_set::Target_set()
|
Target_registry::Target_registry()
|
||||||
: m_parameters(Parameter_set("name | desc :after_apply :after_write :includes :escape | transforms.rest"))
|
: m_parameters(Parameter_set("name | desc :after_apply :after_write :includes :escape | transforms.rest"))
|
||||||
{
|
{
|
||||||
Target k(declare_name, "Description of parameters and klammer result", Locator());
|
Target k(declare_name, "Description of parameters and klammer result", Locator());
|
||||||
@@ -22,16 +21,15 @@ Target_set::Target_set()
|
|||||||
add(general);
|
add(general);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Target_set::add(Target target)
|
void Target_registry::add(Target target)
|
||||||
{
|
{
|
||||||
(void)K::log(3, target);
|
(void)K::log(3, target);
|
||||||
check_for_previous_definition(target.m_name, target.m_loc);
|
check_for_previous_definition(target.m_name, target.m_loc);
|
||||||
m_targets[target.m_name] = target;
|
m_targets[target.m_name] = target;
|
||||||
m_names.push_back(target.m_name);
|
m_names.push_back(target.m_name);
|
||||||
m_descs.push_back(target.m_desc);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void Target_set::add(std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end, std::vector<Katom>& katoms)
|
void Target_registry::add(std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end, std::vector<Katom>& katoms)
|
||||||
{
|
{
|
||||||
(void)K::log(3, *begin, *(end - 1));
|
(void)K::log(3, *begin, *(end - 1));
|
||||||
auto [positional, optional, rest] =
|
auto [positional, optional, rest] =
|
||||||
@@ -40,14 +38,10 @@ void Target_set::add(std::vector<Katom>::iterator begin, std::vector<Katom>::ite
|
|||||||
|
|
||||||
//std::cout << ktype << "Transformed: " << kreplaced << std::pair(begin, end) << "\n";
|
//std::cout << ktype << "Transformed: " << kreplaced << std::pair(begin, end) << "\n";
|
||||||
//std::cout << values << "\n";
|
//std::cout << values << "\n";
|
||||||
check_for_previous_definition(values["name"], begin->m_loc);
|
|
||||||
Target target(values["name"], values["desc"], begin->m_loc);
|
Target target(values["name"], values["desc"], begin->m_loc);
|
||||||
target.add_transforms(values["transforms"]);
|
target.add_transforms(values["transforms"]);
|
||||||
target.add_escapes(values["escape"]);
|
target.add_escapes(values["escape"]);
|
||||||
target.add_after_apply(values["after_apply"]);
|
target.add_after_apply(values["after_apply"]);
|
||||||
// for (auto included_target : word_split(values["includes"])) {
|
|
||||||
// msg() << "Include: " << included_target << "\n";
|
|
||||||
// }
|
|
||||||
target.m_includes = word_split(values["includes"]);
|
target.m_includes = word_split(values["includes"]);
|
||||||
// Inherit escapes from included targets
|
// Inherit escapes from included targets
|
||||||
for (const auto& included : target.m_includes) {
|
for (const auto& included : target.m_includes) {
|
||||||
@@ -57,15 +51,13 @@ void Target_set::add(std::vector<Katom>::iterator begin, std::vector<Katom>::ite
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
m_targets[target.m_name] = target;
|
// Registration (and the previous-definition check) goes through
|
||||||
m_names.push_back(target.m_name);
|
// add(Target) -- the single registration path.
|
||||||
|
add(target);
|
||||||
|
|
||||||
for (auto [name, defined_target] : m_targets) {
|
for (auto& [name, defined_target] : m_targets) {
|
||||||
// msg() << name << sp_arrow << defined_target << "\n";
|
|
||||||
if (is_in(name, target.m_includes)) {
|
if (is_in(name, target.m_includes)) {
|
||||||
defined_target.m_provides.push_back(target.m_name);
|
defined_target.m_provides.push_back(target.m_name);
|
||||||
// msg() << " " << name << " provides " << target.m_name << "\n " << defined_target.m_provides << "\n";
|
|
||||||
m_targets[name] = defined_target;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -76,56 +68,62 @@ void Target_set::add(std::vector<Katom>::iterator begin, std::vector<Katom>::ite
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void Target_set::check_for_previous_definition(std::string name, Locator loc)
|
void Target_registry::check_for_previous_definition(const std::string& name, const Locator& loc) const
|
||||||
{
|
{
|
||||||
if (has(name)) {
|
if (has(name)) {
|
||||||
Target current = m_targets[name];
|
const Target& current = m_targets.at(name);
|
||||||
throw Target_error("Target \"" + name + "\" is already defined:\n " + current.m_loc.desc(),
|
throw Target_error("Target \"" + name + "\" is already defined:\n " + current.m_loc.desc(),
|
||||||
loc, false);
|
loc, false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Target_set::has(std::string target_name)
|
bool Target_registry::has(const std::string& target_name) const
|
||||||
{
|
{
|
||||||
return std::ranges::find(m_names, target_name) != m_names.end();
|
// Membership comes from the map; m_names exists only to preserve
|
||||||
|
// definition order for describe().
|
||||||
|
return m_targets.count(target_name) > 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
Target Target_set::get(std::string target_name, Locator loc)
|
Target Target_registry::get(const std::string& target_name, const Locator& loc) const
|
||||||
{
|
{
|
||||||
if (has(target_name) || target_name == Target_set::general_name) {
|
if (has(target_name) || target_name == Target_registry::general_name) {
|
||||||
return m_targets.at(target_name);
|
return m_targets.at(target_name);
|
||||||
} else {
|
} else {
|
||||||
throw Target_error("Target " + target_name + " does not exist", loc);
|
throw Target_error("Target " + target_name + " does not exist", loc);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void Target_set::transform(std::string target_name, katom_list& katoms)
|
void Target_registry::transform(const std::string& target_name, katom_list& katoms) const
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
m_targets[target_name].transform(katoms);
|
m_targets.at(target_name).transform(katoms);
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<std::string> Target_set::user_defined()
|
std::vector<std::string> Target_registry::user_defined() const
|
||||||
{
|
{
|
||||||
return collect_if(
|
return collect_if(
|
||||||
m_names, [](auto name) {
|
m_names, [](const auto& name) {
|
||||||
return name != Target_set::declare_name && name != Target_set::general_name; });
|
return name != Target_registry::declare_name && name != Target_registry::general_name; });
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<std::string> Target_set::applicable()
|
std::vector<std::string> Target_registry::applicable() const
|
||||||
{
|
{
|
||||||
return collect_if(
|
return collect_if(
|
||||||
m_names, [](auto name) {
|
m_names, [](const auto& name) {
|
||||||
return name != Target_set::declare_name; });
|
return name != Target_registry::declare_name; });
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string Target_set::describe(int margin, bool long_format) const
|
std::string Target_registry::describe(int margin, bool long_format) const
|
||||||
{
|
{
|
||||||
std::string tab(margin, ' ');
|
std::string tab(margin, ' ');
|
||||||
std::stringstream ss {};
|
std::stringstream ss {};
|
||||||
|
std::vector<std::string> descs {};
|
||||||
|
for (const std::string& name : m_names) {
|
||||||
|
descs.push_back(m_targets.at(name).m_desc);
|
||||||
|
}
|
||||||
auto name_width = max_length(m_names);
|
auto name_width = max_length(m_names);
|
||||||
auto desc_width = max_length(m_descs);
|
auto desc_width = max_length(descs);
|
||||||
for (const std::string& name : m_names) {
|
for (const std::string& name : m_names) {
|
||||||
const Target& t = m_targets.at(name);
|
const Target& t = m_targets.at(name);
|
||||||
if (long_format) {
|
if (long_format) {
|
||||||
@@ -6,17 +6,17 @@
|
|||||||
#include "argument_set.h"
|
#include "argument_set.h"
|
||||||
#include "katom.h"
|
#include "katom.h"
|
||||||
|
|
||||||
class Target_set
|
class Target_registry
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
static std::string declare_name;
|
static std::string declare_name;
|
||||||
static std::string general_name;
|
static std::string general_name;
|
||||||
|
|
||||||
Target_set();
|
Target_registry();
|
||||||
|
|
||||||
void add(Target target);
|
void add(Target target);
|
||||||
void add(std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end, std::vector<Katom>& katoms);
|
void add(std::vector<Katom>::iterator begin, std::vector<Katom>::iterator end, std::vector<Katom>& katoms);
|
||||||
void check_for_previous_definition(std::string name, Locator loc);
|
void check_for_previous_definition(const std::string& name, const Locator& loc) const;
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -27,19 +27,18 @@ public:
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
|
|
||||||
bool has(std::string target_name);
|
bool has(const std::string& target_name) const;
|
||||||
Target get(std::string target_name, Locator loc);
|
Target get(const std::string& target_name, const Locator& loc) const;
|
||||||
void transform(std::string target_name, std::vector<Katom>& katoms);
|
void transform(const std::string& target_name, std::vector<Katom>& katoms) const;
|
||||||
|
|
||||||
std::vector<std::string> user_defined();
|
std::vector<std::string> user_defined() const;
|
||||||
std::vector<std::string> applicable();
|
std::vector<std::string> applicable() const;
|
||||||
|
|
||||||
std::string describe(int margin=2, bool long_format=false) const;
|
std::string describe(int margin=2, bool long_format=false) const;
|
||||||
|
|
||||||
//Argtype_set m_argtypes {};
|
//Argtype_registry m_argtypes {};
|
||||||
std::map<std::string, Target> m_targets {};
|
std::map<std::string, Target> m_targets {};
|
||||||
std::vector<std::string> m_names {};
|
std::vector<std::string> m_names {};
|
||||||
std::vector<std::string> m_descs {};
|
|
||||||
Parameter_set m_parameters {};
|
Parameter_set m_parameters {};
|
||||||
|
|
||||||
|
|
||||||
@@ -51,7 +50,7 @@ public:
|
|||||||
|
|
||||||
|
|
||||||
//Parameter_set m_parameters =
|
//Parameter_set m_parameters =
|
||||||
// Parameter_set(katomize({"name :desc | transforms.rest"}, "target_set"));
|
// Parameter_set(katomize({"name :desc | transforms.rest"}, "target_registry"));
|
||||||
|
|
||||||
/*
|
/*
|
||||||
// Targets(Statevar_set& statevars);
|
// Targets(Statevar_set& statevars);
|
||||||
25
mac/util.cpp
25
mac/util.cpp
@@ -111,7 +111,7 @@ std::string regex_escape(const std::string& s)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
strings_t regex_split(std::string s, std::regex re, bool trim_parts)
|
strings_t regex_split(const std::string& s, const std::regex& re, bool trim_parts)
|
||||||
{
|
{
|
||||||
strings_t result = {};
|
strings_t result = {};
|
||||||
if (s.size() == 0) {
|
if (s.size() == 0) {
|
||||||
@@ -134,17 +134,17 @@ strings_t word_split(const std::string& s)
|
|||||||
return regex_split(s, std::regex("\\s+"));
|
return regex_split(s, std::regex("\\s+"));
|
||||||
}
|
}
|
||||||
|
|
||||||
bool is_in(std::string s, strings_t v)
|
bool is_in(const std::string& s, const strings_t& v)
|
||||||
{
|
{
|
||||||
return find(v.begin(), v.end(), s) != v.end();
|
return find(v.begin(), v.end(), s) != v.end();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool is_not_in(std::string s, strings_t v)
|
bool is_not_in(const std::string& s, const strings_t& v)
|
||||||
{
|
{
|
||||||
return find(v.begin(), v.end(), s) == v.end();
|
return find(v.begin(), v.end(), s) == v.end();
|
||||||
}
|
}
|
||||||
|
|
||||||
strings_t find_all(std::string str, std::regex pattern, int match_group)
|
strings_t find_all(const std::string& str, const std::regex& pattern, int match_group)
|
||||||
{
|
{
|
||||||
std::sregex_iterator end {};
|
std::sregex_iterator end {};
|
||||||
strings_t result;
|
strings_t result;
|
||||||
@@ -153,7 +153,7 @@ strings_t find_all(std::string str, std::regex pattern, int match_group)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
strings_t find_all(std::string str, std::string pattern, int match_group)
|
strings_t find_all(const std::string& str, const std::string& pattern, int match_group)
|
||||||
{
|
{
|
||||||
return find_all(str, std::regex(pattern), match_group);
|
return find_all(str, std::regex(pattern), match_group);
|
||||||
}
|
}
|
||||||
@@ -168,7 +168,7 @@ strings_t split_into_paragraphs(const std::string& s)
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string add_margin(std::string s, unsigned int margin_size)
|
std::string add_margin(const std::string& s, unsigned int margin_size)
|
||||||
{
|
{
|
||||||
auto margin = std::string(margin_size, ' ');
|
auto margin = std::string(margin_size, ' ');
|
||||||
return trim_right(
|
return trim_right(
|
||||||
@@ -297,7 +297,7 @@ std::string to_be(int count, bool present)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
int max_length(strings_t ss)
|
int max_length(const strings_t& ss)
|
||||||
{
|
{
|
||||||
size_t result = 0;
|
size_t result = 0;
|
||||||
for_each(ss.begin(), ss.end(),
|
for_each(ss.begin(), ss.end(),
|
||||||
@@ -349,7 +349,7 @@ std::vector<std::pair<std::string, std::string>> environment_variables(bool allo
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string replace_environment_variables(std::string str)
|
std::string replace_environment_variables(const std::string& str)
|
||||||
{
|
{
|
||||||
if (str.find('{') == std::string::npos || str.find('}') == std::string::npos) {
|
if (str.find('{') == std::string::npos || str.find('}') == std::string::npos) {
|
||||||
return str;
|
return str;
|
||||||
@@ -398,10 +398,10 @@ std::string abbrev(const std::string& s, unsigned int max_length, bool remove_ne
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
void remove_element(std::vector<std::string>& ss, std::string removed)
|
void remove_element(std::vector<std::string>& ss, const std::string& removed)
|
||||||
{
|
{
|
||||||
ss.erase(std::remove_if(ss.begin(), ss.end(),
|
ss.erase(std::remove_if(ss.begin(), ss.end(),
|
||||||
[&removed](std::string s) { return s == removed; }),
|
[&removed](const std::string& s) { return s == removed; }),
|
||||||
ss.end());
|
ss.end());
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -428,7 +428,7 @@ std::string display_string(const std::string& s, unsigned int width, bool replac
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::pair<std::string,std::string> extract_parameter_type(std::string parameter_name)
|
std::pair<std::string,std::string> extract_parameter_type(const std::string& parameter_name)
|
||||||
{
|
{
|
||||||
std::regex name_pat { R"((\w+)\.(\w+))" };
|
std::regex name_pat { R"((\w+)\.(\w+))" };
|
||||||
std::smatch match {};
|
std::smatch match {};
|
||||||
@@ -487,7 +487,8 @@ std::string get_env_var(const std::string& var) {
|
|||||||
return val ? std::string(val) : "";
|
return val ? std::string(val) : "";
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string freplace(const std::string src, std::regex pattern, std::function<std::string(std::smatch)> func)
|
std::string freplace(const std::string& src, const std::regex& pattern,
|
||||||
|
const std::function<std::string(std::smatch)>& func)
|
||||||
{
|
{
|
||||||
std::string result {};
|
std::string result {};
|
||||||
std::smatch match;
|
std::smatch match;
|
||||||
|
|||||||
29
mac/util.h
29
mac/util.h
@@ -36,13 +36,13 @@ std::string string_replace(const std::string& source, const std::string& old_str
|
|||||||
std::string regex_escape(const std::string& s);
|
std::string regex_escape(const std::string& s);
|
||||||
bool contains(const std::string& str, const std::string& substr);
|
bool contains(const std::string& str, const std::string& substr);
|
||||||
bool contains(const std::vector<std::string>& strings, const std::string& element);
|
bool contains(const std::vector<std::string>& strings, const std::string& element);
|
||||||
std::vector<std::string> regex_split(std::string s, std::regex re, bool trim_parts=true);
|
std::vector<std::string> regex_split(const std::string& s, const std::regex& re, bool trim_parts=true);
|
||||||
std::vector<std::string> word_split(const std::string& s);
|
std::vector<std::string> word_split(const std::string& s);
|
||||||
bool is_in(std::string s, std::vector<std::string> v);
|
bool is_in(const std::string& s, const std::vector<std::string>& v);
|
||||||
bool is_not_in(std::string s, std::vector<std::string> v);
|
bool is_not_in(const std::string& s, const std::vector<std::string>& v);
|
||||||
std::vector<std::string> find_all(std::string str, std::regex pattern, int match_group=0);
|
std::vector<std::string> find_all(const std::string& str, const std::regex& pattern, int match_group=0);
|
||||||
std::vector<std::string> find_all(std::string str, std::string pattern, int match_group=0);
|
std::vector<std::string> find_all(const std::string& str, const std::string& pattern, int match_group=0);
|
||||||
std::string add_margin(std::string s, unsigned int margin_size);
|
std::string add_margin(const std::string& s, unsigned int margin_size);
|
||||||
std::string justify(const std::string& input_text, unsigned int text_width=80, unsigned int margin_width=0);
|
std::string justify(const std::string& input_text, unsigned int text_width=80, unsigned int margin_width=0);
|
||||||
std::string join(const std::vector<std::string>& ss, const std::string& separator = " ");
|
std::string join(const std::vector<std::string>& ss, const std::string& separator = " ");
|
||||||
std::string join(int argc, char* array[], const std::string& separator = " ");
|
std::string join(int argc, char* array[], const std::string& separator = " ");
|
||||||
@@ -50,26 +50,27 @@ std::string argv_to_string(int argc, char* argv[]);
|
|||||||
std::string plural(const std::string& word, int count);
|
std::string plural(const std::string& word, int count);
|
||||||
std::string plural(const std::string& word, const std::vector<std::string>& things);
|
std::string plural(const std::string& word, const std::vector<std::string>& things);
|
||||||
std::string to_be(int count, bool present = true);
|
std::string to_be(int count, bool present = true);
|
||||||
int max_length(std::vector<std::string> ss);
|
int max_length(const std::vector<std::string>& ss);
|
||||||
std::vector<std::pair<std::string, std::string>> environment_variables(bool allow_empty_definitions=true);
|
std::vector<std::pair<std::string, std::string>> environment_variables(bool allow_empty_definitions=true);
|
||||||
std::string replace_environment_variables(std::string str);
|
std::string replace_environment_variables(const std::string& str);
|
||||||
std::string abbrev(const std::string& s, unsigned int max_length=65, bool remove_newlines=true);
|
std::string abbrev(const std::string& s, unsigned int max_length=65, bool remove_newlines=true);
|
||||||
void remove_element(std::vector<std::string>& ss, std::string removed);
|
void remove_element(std::vector<std::string>& ss, const std::string& removed);
|
||||||
void remove_duplicates(std::vector<std::string>& ss);
|
void remove_duplicates(std::vector<std::string>& ss);
|
||||||
std::string display_string(const std::string& s, unsigned int width=40, bool replace_newlines=true);
|
std::string display_string(const std::string& s, unsigned int width=40, bool replace_newlines=true);
|
||||||
std::pair<std::string,std::string> extract_parameter_type(std::string parameter_name);
|
std::pair<std::string,std::string> extract_parameter_type(const std::string& parameter_name);
|
||||||
std::tuple<std::string, std::string, bool> regex_split_prefix(const std::regex& pattern, const std::string& text);
|
std::tuple<std::string, std::string, bool> regex_split_prefix(const std::regex& pattern, const std::string& text);
|
||||||
std::vector<std::string> dlist_split(const std::string& s);
|
std::vector<std::string> dlist_split(const std::string& s);
|
||||||
std::string get_env_var(const std::string& var);
|
std::string get_env_var(const std::string& var);
|
||||||
std::string freplace(const std::string src, std::regex pattern, std::function<std::string(std::smatch)> func);
|
std::string freplace(const std::string& src, const std::regex& pattern,
|
||||||
|
const std::function<std::string(std::smatch)>& func);
|
||||||
std::string exec(const char* cmd);
|
std::string exec(const char* cmd);
|
||||||
|
|
||||||
inline std::string q_(std::string s)
|
inline std::string q_(const std::string& s)
|
||||||
{
|
{
|
||||||
return "\"" + s + "\"";
|
return "\"" + s + "\"";
|
||||||
}
|
}
|
||||||
|
|
||||||
inline std::string qq_(std::string s)
|
inline std::string qq_(const std::string& s)
|
||||||
{
|
{
|
||||||
if (s.find('\n') == std::string::npos) {
|
if (s.find('\n') == std::string::npos) {
|
||||||
return "\"" + s + "\"";
|
return "\"" + s + "\"";
|
||||||
@@ -97,7 +98,7 @@ bool all_equal(const std::vector<T>& v) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
template <typename T>
|
template <typename T>
|
||||||
int max_key_length(std::map<std::string, T> map)
|
int max_key_length(const std::map<std::string, T>& map)
|
||||||
{
|
{
|
||||||
size_t result = 0;
|
size_t result = 0;
|
||||||
for_each(map.begin(), map.end(),
|
for_each(map.begin(), map.end(),
|
||||||
|
|||||||
@@ -11,7 +11,7 @@
|
|||||||
#include "log.h"
|
#include "log.h"
|
||||||
#include "file.h"
|
#include "file.h"
|
||||||
|
|
||||||
bool strbool(std::string s, Locator loc)
|
bool strbool(const std::string& s, const Locator& loc)
|
||||||
{
|
{
|
||||||
std::vector<std::string> values = {"false", "False", "0", "true", "True", "1"};
|
std::vector<std::string> values = {"false", "False", "0", "true", "True", "1"};
|
||||||
if (is_not_in(s, values)) {
|
if (is_not_in(s, values)) {
|
||||||
@@ -136,7 +136,7 @@ void Document_class::save_string_input_as_file()
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
fs::path parse_input_filename(std::string s, std::string input_dir)
|
fs::path parse_input_filename(const std::string& s, const std::string& input_dir)
|
||||||
{
|
{
|
||||||
fs::path p(s);
|
fs::path p(s);
|
||||||
if (p.extension() != ".kt") {
|
if (p.extension() != ".kt") {
|
||||||
@@ -160,13 +160,13 @@ fs::path parse_input_filename(std::string s, std::string input_dir)
|
|||||||
return p;
|
return p;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Document_class::write(std::string filename, std::string contents)
|
void Document_class::write(const std::string& filename, const std::string& contents)
|
||||||
{
|
{
|
||||||
write_file(filename, contents, write_files);
|
write_file(filename, contents, write_files);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void write_file(std::string filename, std::string contents, bool write_p)
|
void write_file(const std::string& filename, const std::string& contents, bool write_p)
|
||||||
{
|
{
|
||||||
if (write_p) {
|
if (write_p) {
|
||||||
string_to_file(filename, contents);
|
string_to_file(filename, contents);
|
||||||
@@ -177,14 +177,14 @@ void write_file(std::string filename, std::string contents, bool write_p)
|
|||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
void output_msg(std::string msg)
|
void output_msg(const std::string& msg)
|
||||||
{
|
{
|
||||||
std::cout << red;
|
std::cout << red;
|
||||||
(void)K::log(1, msg);
|
(void)K::log(1, msg);
|
||||||
std::cout << black;
|
std::cout << black;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Document_class::create_directory(std::string directory)
|
void Document_class::create_directory(const std::string& directory)
|
||||||
{
|
{
|
||||||
if (write_files) {
|
if (write_files) {
|
||||||
fs::create_directories(directory);
|
fs::create_directories(directory);
|
||||||
|
|||||||
@@ -16,7 +16,7 @@ inline std::map<std::string, int> html_tags {
|
|||||||
|
|
||||||
using string_pairs_t = std::vector<std::pair<std::string,std::string>>;
|
using string_pairs_t = std::vector<std::pair<std::string,std::string>>;
|
||||||
|
|
||||||
std::string unescape_newlines(std::string s);
|
std::string unescape_newlines(const std::string& s);
|
||||||
|
|
||||||
enum class docstruct_t {
|
enum class docstruct_t {
|
||||||
plain,
|
plain,
|
||||||
@@ -24,7 +24,7 @@ enum class docstruct_t {
|
|||||||
book
|
book
|
||||||
};
|
};
|
||||||
|
|
||||||
inline docstruct_t docstruct(std::string name)
|
inline docstruct_t docstruct(const std::string& name)
|
||||||
{
|
{
|
||||||
if (name == "plain") {
|
if (name == "plain") {
|
||||||
return docstruct_t::plain;
|
return docstruct_t::plain;
|
||||||
@@ -43,41 +43,41 @@ public:
|
|||||||
void save_string_input_as_file();
|
void save_string_input_as_file();
|
||||||
|
|
||||||
//void create_directory(std::string directory);
|
//void create_directory(std::string directory);
|
||||||
void write(std::string filename, std::string contents);
|
void write(const std::string& filename, const std::string& contents);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
strings_t get_css_files(
|
strings_t get_css_files(
|
||||||
std::string output_dir,
|
const std::string& output_dir,
|
||||||
std::string css_text, strings_t css_files, bool write_file);
|
const std::string& css_text, const strings_t& css_files, bool write_file);
|
||||||
*/
|
*/
|
||||||
|
|
||||||
strings_t get_js_files(
|
strings_t get_js_files(
|
||||||
bool nav, bool include_sks_js,
|
bool nav, bool include_sks_js,
|
||||||
std::string pages_basenames_filename); // , std::string output_dir, bool write_file);
|
const std::string& pages_basenames_filename); // , const std::string& output_dir, bool write_file);
|
||||||
|
|
||||||
argmap m_args {};
|
argmap m_args {};
|
||||||
void write_basenames_js_file(std::string filename, std::vector<std::string> basenames);
|
void write_basenames_js_file(const std::string& filename, const std::vector<std::string>& basenames);
|
||||||
std::string create_html_output_directories();
|
std::string create_html_output_directories();
|
||||||
std::string create_tex_output_directories();
|
std::string create_tex_output_directories();
|
||||||
|
|
||||||
std::pair<std::vector<std::string>, std::vector<std::string>>
|
std::pair<std::vector<std::string>, std::vector<std::string>>
|
||||||
html_auxiliary_files(std::string output_directory, std::string pages_basename_filename,
|
html_auxiliary_files(const std::string& output_directory, const std::string& pages_basename_filename,
|
||||||
std::vector<std::string> custom_css_files);
|
const std::vector<std::string>& custom_css_files);
|
||||||
|
|
||||||
|
|
||||||
void process_input_files();
|
void process_input_files();
|
||||||
std::vector<Heading> insert_section_numbers(std::string marker="___NUM___", bool add_to_toc=true);
|
std::vector<Heading> insert_section_numbers(const std::string& marker="___NUM___", bool add_to_toc=true);
|
||||||
void insert_html_caption_numbers();
|
void insert_html_caption_numbers();
|
||||||
std::vector<std::tuple<std::string, std::string, std::string>> reference_list(std::string target_marker);
|
std::vector<std::tuple<std::string, std::string, std::string>> reference_list(const std::string& target_marker);
|
||||||
std::map<std::string, std::string> id_to_caption_number();
|
std::map<std::string, std::string> id_to_caption_number();
|
||||||
std::map<std::string, std::vector<std::pair<std::string, std::string>>> html_references();
|
std::map<std::string, std::vector<std::pair<std::string, std::string>>> html_references();
|
||||||
void resolve_html_references();
|
void resolve_html_references();
|
||||||
std::string single_page_toc();
|
std::string single_page_toc();
|
||||||
elements_t page(std::string body, std::string output_dir, int max_level);
|
elements_t page(const std::string& body, const std::string& output_dir, int max_level);
|
||||||
|
|
||||||
std::string make_single_html_page(std::string output_directory);
|
std::string make_single_html_page(const std::string& output_directory);
|
||||||
std::string make_html_navigation_structure(
|
std::string make_html_navigation_structure(
|
||||||
std::string output_directory, std::vector<Heading> headings);
|
const std::string& output_directory, std::vector<Heading> headings);
|
||||||
std::string html();
|
std::string html();
|
||||||
std::string tex();
|
std::string tex();
|
||||||
std::string make_help_page();
|
std::string make_help_page();
|
||||||
@@ -167,13 +167,13 @@ public:
|
|||||||
std::string m_cache_dir {};
|
std::string m_cache_dir {};
|
||||||
};
|
};
|
||||||
|
|
||||||
fs::path parse_input_filename(std::string s, std::string input_dir);
|
fs::path parse_input_filename(const std::string& s, const std::string& input_dir);
|
||||||
void write_file(std::string filename, std::string contents, bool write_files);
|
void write_file(const std::string& filename, const std::string& contents, bool write_files);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
std::vector<std::string> combine_files(
|
std::vector<std::string> combine_files(
|
||||||
std::vector<std::string> filenames, std::string output_filename,
|
const std::vector<std::string>& filenames, const std::string& output_filename,
|
||||||
std::string prolog="", std::string epilog="",
|
const std::string& prolog="", const std::string& epilog="",
|
||||||
bool write_file_p=true,
|
bool write_file_p=true,
|
||||||
std::function <std::string(std::string)> processor=nullptr);
|
std::function <std::string(std::string)> processor=nullptr);
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -10,7 +10,7 @@
|
|||||||
#include "show.h"
|
#include "show.h"
|
||||||
#include "file.h"
|
#include "file.h"
|
||||||
|
|
||||||
std::string unescape_newlines(std::string s)
|
std::string unescape_newlines(const std::string& s)
|
||||||
{
|
{
|
||||||
return string_replace(s, " ___NL___ ", "\n");
|
return string_replace(s, " ___NL___ ", "\n");
|
||||||
|
|
||||||
@@ -44,7 +44,7 @@ std::string insert_missing_ids(std::smatch match)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string insert_ids(std::string html_text)
|
std::string insert_ids(const std::string& html_text)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
std::string result = html_text;
|
std::string result = html_text;
|
||||||
@@ -154,7 +154,7 @@ std::string Document_class::font_definitions()
|
|||||||
return ss.str();
|
return ss.str();
|
||||||
}
|
}
|
||||||
|
|
||||||
void Document_class::write_basenames_js_file(std::string filename, std::vector<std::string> basenames)
|
void Document_class::write_basenames_js_file(const std::string& filename, const std::vector<std::string>& basenames)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
std::string tab(" ");
|
std::string tab(" ");
|
||||||
@@ -202,7 +202,7 @@ std::string Document_class::create_html_output_directories()
|
|||||||
return output_directory;
|
return output_directory;
|
||||||
}
|
}
|
||||||
|
|
||||||
strings_t get_css_files(strings_t custom_css_files)
|
strings_t get_css_files(const strings_t& custom_css_files)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
strings_t result = sks_files_of_type("css");
|
strings_t result = sks_files_of_type("css");
|
||||||
@@ -223,7 +223,7 @@ std::vector<std::string> js_basenames(bool nav)
|
|||||||
|
|
||||||
strings_t Document_class::get_js_files(
|
strings_t Document_class::get_js_files(
|
||||||
bool nav, bool include_sks_js,
|
bool nav, bool include_sks_js,
|
||||||
std::string pages_basenames_filename)
|
const std::string& pages_basenames_filename)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
strings_t result {};
|
strings_t result {};
|
||||||
@@ -244,13 +244,13 @@ strings_t Document_class::get_js_files(
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
strings_t link_filenames(strings_t& full_filenames, std::string page_dir)
|
strings_t link_filenames(strings_t& full_filenames, const std::string& page_dir)
|
||||||
{
|
{
|
||||||
strings_t result {};
|
strings_t result {};
|
||||||
fs::path page_dir_path(page_dir);
|
fs::path page_dir_path(page_dir);
|
||||||
// int i = 0;
|
// int i = 0;
|
||||||
std::transform(full_filenames.begin(), full_filenames.end(), std::back_inserter(result),
|
std::transform(full_filenames.begin(), full_filenames.end(), std::back_inserter(result),
|
||||||
[&](std::string f) {
|
[&](const std::string& f) {
|
||||||
fs::path full(f);
|
fs::path full(f);
|
||||||
//msg() << i << full << " " << full.filename() << "\n";
|
//msg() << i << full << " " << full.filename() << "\n";
|
||||||
fs::path path(page_dir_path / full.filename());
|
fs::path path(page_dir_path / full.filename());
|
||||||
@@ -260,8 +260,8 @@ strings_t link_filenames(strings_t& full_filenames, std::string page_dir)
|
|||||||
}
|
}
|
||||||
|
|
||||||
std::pair<std::vector<std::string>, std::vector<std::string>>
|
std::pair<std::vector<std::string>, std::vector<std::string>>
|
||||||
Document_class::html_auxiliary_files(std::string output_directory, std::string pages_basenames_filename,
|
Document_class::html_auxiliary_files(const std::string& output_directory, const std::string& pages_basenames_filename,
|
||||||
std::vector<std::string> custom_css_files)
|
const std::vector<std::string>& custom_css_files)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
strings_t all_css_files = custom_css_files;
|
strings_t all_css_files = custom_css_files;
|
||||||
@@ -352,7 +352,7 @@ std::string increment_level(int level, std::vector<int> &levels)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
std::string extract_id(std::string attr)
|
std::string extract_id(const std::string& attr)
|
||||||
{
|
{
|
||||||
std::smatch match {};
|
std::smatch match {};
|
||||||
if (!std::regex_match(attr, match, id_attr_rgx)) {
|
if (!std::regex_match(attr, match, id_attr_rgx)) {
|
||||||
@@ -362,7 +362,7 @@ std::string extract_id(std::string attr)
|
|||||||
}
|
}
|
||||||
|
|
||||||
std::vector<Heading>
|
std::vector<Heading>
|
||||||
Document_class::insert_section_numbers(std::string marker, bool add_to_toc)
|
Document_class::insert_section_numbers(const std::string& marker, bool add_to_toc)
|
||||||
{
|
{
|
||||||
std::vector<int> levels(9, 0);
|
std::vector<int> levels(9, 0);
|
||||||
std::smatch match {};
|
std::smatch match {};
|
||||||
@@ -407,7 +407,7 @@ Document_class::insert_section_numbers(std::string marker, bool add_to_toc)
|
|||||||
return headings;
|
return headings;
|
||||||
}
|
}
|
||||||
|
|
||||||
int get_caption_number(std::map<std::string, int>& numbers, std::string label)
|
int get_caption_number(std::map<std::string, int>& numbers, const std::string& label)
|
||||||
{
|
{
|
||||||
int result;
|
int result;
|
||||||
if (numbers.count(label) == 0) {
|
if (numbers.count(label) == 0) {
|
||||||
@@ -470,7 +470,7 @@ void Document_class::insert_html_caption_numbers()
|
|||||||
|
|
||||||
|
|
||||||
std::vector<std::tuple<std::string, std::string, std::string>>
|
std::vector<std::tuple<std::string, std::string, std::string>>
|
||||||
Document_class::reference_list(std::string target_marker)
|
Document_class::reference_list(const std::string& target_marker)
|
||||||
{
|
{
|
||||||
std::regex reference_rgx("__REF__");
|
std::regex reference_rgx("__REF__");
|
||||||
std::regex target_rgx("<div id=\"(.*?)\" data-label=\"(.*?)\" class=\"caption_");
|
std::regex target_rgx("<div id=\"(.*?)\" data-label=\"(.*?)\" class=\"caption_");
|
||||||
@@ -519,7 +519,7 @@ std::map<std::string, std::string> Document_class::id_to_caption_number()
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
std::pair<int, int> offset_spec_to_count(std::string spec)
|
std::pair<int, int> offset_spec_to_count(const std::string& spec)
|
||||||
{
|
{
|
||||||
std::regex rgx(R"((\w+)\s*(\d*))");
|
std::regex rgx(R"((\w+)\s*(\d*))");
|
||||||
std::smatch match {};
|
std::smatch match {};
|
||||||
@@ -637,7 +637,7 @@ std::string Document_class::single_page_toc()
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
elements_t Document_class::page(std::string body_text, std::string output_dir, int max_level)
|
elements_t Document_class::page(const std::string& body_text, const std::string& output_dir, int max_level)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
std::string toc {}; // Calculate
|
std::string toc {}; // Calculate
|
||||||
@@ -674,7 +674,7 @@ elements_t Document_class::page(std::string body_text, std::string output_dir, i
|
|||||||
return page;
|
return page;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string Document_class::make_single_html_page(std::string output_directory)
|
std::string Document_class::make_single_html_page(const std::string& output_directory)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
std::stringstream ss {};;
|
std::stringstream ss {};;
|
||||||
@@ -694,7 +694,7 @@ std::string Document_class::make_single_html_page(std::string output_directory)
|
|||||||
}
|
}
|
||||||
|
|
||||||
std::string Document_class::make_html_navigation_structure(
|
std::string Document_class::make_html_navigation_structure(
|
||||||
std::string output_directory, std::vector<Heading> headings)
|
const std::string& output_directory, std::vector<Heading> headings)
|
||||||
{
|
{
|
||||||
msg() << "Navigation format\n";
|
msg() << "Navigation format\n";
|
||||||
std::vector<std::string> pages_basenames {};
|
std::vector<std::string> pages_basenames {};
|
||||||
|
|||||||
@@ -40,7 +40,7 @@ int unnumbered_id = 0;
|
|||||||
|
|
||||||
/*
|
/*
|
||||||
std::tuple<std::string, std::vector<Heading>, std::vector<unsigned int>, unsigned int>
|
std::tuple<std::string, std::vector<Heading>, std::vector<unsigned int>, unsigned int>
|
||||||
add_section_numbers(std::string s, std::string basename, std::vector<unsigned int> levels, unsigned int initial_id,
|
add_section_numbers(const std::string& s, const std::string& basename, std::vector<unsigned int> levels, unsigned int initial_id,
|
||||||
std::map<std::string, std::string>& section_id_map)
|
std::map<std::string, std::string>& section_id_map)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
@@ -155,7 +155,7 @@ std::string make_html_table_of_contents(std::vector<Heading> headings)
|
|||||||
}
|
}
|
||||||
|
|
||||||
std::string toc_link_attrs(
|
std::string toc_link_attrs(
|
||||||
std::string section, std::string title, std::string filename, std::string target, int level)
|
const std::string& section, const std::string& title, const std::string& filename, const std::string& target, int level)
|
||||||
{
|
{
|
||||||
std::string basename = file_basename(filename);
|
std::string basename = file_basename(filename);
|
||||||
std::stringstream ss {};
|
std::stringstream ss {};
|
||||||
@@ -259,7 +259,7 @@ make_navigation_table_of_contents(std::vector<Heading> headings)
|
|||||||
}
|
}
|
||||||
|
|
||||||
void show_table_of_contents(
|
void show_table_of_contents(
|
||||||
std::string kt_root_filename, std::string title, std::vector<Heading> headings)
|
const std::string& kt_root_filename, const std::string& title, std::vector<Heading> headings)
|
||||||
{
|
{
|
||||||
long unsigned int width = kt_root_filename.size();
|
long unsigned int width = kt_root_filename.size();
|
||||||
for (Heading h : headings) {
|
for (Heading h : headings) {
|
||||||
@@ -285,7 +285,7 @@ void show_table_of_contents(
|
|||||||
}
|
}
|
||||||
|
|
||||||
std::string cache_table_of_contents(
|
std::string cache_table_of_contents(
|
||||||
std::string kt_root_filename, std::string title, std::vector<Heading> headings)
|
const std::string& kt_root_filename, const std::string& title, std::vector<Heading> headings)
|
||||||
{
|
{
|
||||||
long unsigned int width = kt_root_filename.size();
|
long unsigned int width = kt_root_filename.size();
|
||||||
for (Heading h : headings) {
|
for (Heading h : headings) {
|
||||||
|
|||||||
@@ -8,8 +8,8 @@ const std::string link_delimiter { "%" };
|
|||||||
|
|
||||||
class Heading {
|
class Heading {
|
||||||
public:
|
public:
|
||||||
Heading(int level, std::string filename, std::string section, std::string id,
|
Heading(int level, const std::string& filename, const std::string& section, const std::string& id,
|
||||||
std::string number, std::string title)
|
const std::string& number, const std::string& title)
|
||||||
: m_level(level), m_filename(filename), m_section(section), m_id(id),
|
: m_level(level), m_filename(filename), m_section(section), m_id(id),
|
||||||
m_number(number), m_title(title)
|
m_number(number), m_title(title)
|
||||||
{};
|
{};
|
||||||
@@ -25,7 +25,7 @@ std::ostream& operator<<(std::ostream& os, const Heading h);
|
|||||||
|
|
||||||
/*
|
/*
|
||||||
std::tuple<std::string, std::vector<Heading>, std::vector<unsigned int>, unsigned int>
|
std::tuple<std::string, std::vector<Heading>, std::vector<unsigned int>, unsigned int>
|
||||||
add_section_numbers(std::string s, std::string basename, std::vector<unsigned int> levels, unsigned int initial_id,
|
add_section_numbers(const std::string& s, const std::string& basename, std::vector<unsigned int> levels, unsigned int initial_id,
|
||||||
std::map<std::string, std::string>& section_id_map);
|
std::map<std::string, std::string>& section_id_map);
|
||||||
*/
|
*/
|
||||||
|
|
||||||
@@ -35,7 +35,7 @@ std::pair<int, std::string>
|
|||||||
make_navigation_table_of_contents(std::vector<Heading> headings);
|
make_navigation_table_of_contents(std::vector<Heading> headings);
|
||||||
|
|
||||||
void show_table_of_contents(
|
void show_table_of_contents(
|
||||||
std::string kt_filename, std::string title, std::vector<Heading> headings);
|
const std::string& kt_filename, const std::string& title, std::vector<Heading> headings);
|
||||||
|
|
||||||
std::string cache_table_of_contents(
|
std::string cache_table_of_contents(
|
||||||
std::string kt_root_filename, std::string title, std::vector<Heading> headings);
|
const std::string& kt_root_filename, const std::string& title, std::vector<Heading> headings);
|
||||||
|
|||||||
@@ -29,7 +29,7 @@ std::ostream& operator<<(std::ostream& os, const numbered_elements& line_states)
|
|||||||
return os;
|
return os;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string add_latex_caption_numbers(std::string latex_text)
|
std::string add_latex_caption_numbers(const std::string& latex_text)
|
||||||
{
|
{
|
||||||
std::string caption_delimiter { "__CAPTION__" }; // But also in kutil.py
|
std::string caption_delimiter { "__CAPTION__" }; // But also in kutil.py
|
||||||
std::regex caption_delimiter_rgx(caption_delimiter);
|
std::regex caption_delimiter_rgx(caption_delimiter);
|
||||||
@@ -74,7 +74,7 @@ std::string add_latex_caption_numbers(std::string latex_text)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
numbered_elements latex_line_states(std::vector<std::string> lines)
|
numbered_elements latex_line_states(const std::vector<std::string>& lines)
|
||||||
{
|
{
|
||||||
// \hypertarget{Reference-Figure-0}{}\label{Label-Reference-Figure-0}
|
// \hypertarget{Reference-Figure-0}{}\label{Label-Reference-Figure-0}
|
||||||
std::regex element_container_rgx(BS + R"(hypertarget\{(Reference-(\w+)-\d+)\}.*)");
|
std::regex element_container_rgx(BS + R"(hypertarget\{(Reference-(\w+)-\d+)\}.*)");
|
||||||
@@ -96,9 +96,9 @@ numbered_elements latex_line_states(std::vector<std::string> lines)
|
|||||||
return states;
|
return states;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string find_target(std::string target,
|
std::string find_target(const std::string& target,
|
||||||
std::vector<std::string>& lines, int start, numbered_elements states,
|
const std::vector<std::string>& lines, int start, const numbered_elements& states,
|
||||||
std::string target_type, int target_count, std::string direction)
|
const std::string& target_type, int target_count, const std::string& direction)
|
||||||
{
|
{
|
||||||
// msg() << "find_target: " << target_type << " target_count: " << target_count
|
// msg() << "find_target: " << target_type << " target_count: " << target_count
|
||||||
// << " direction: " << direction << "\n";
|
// << " direction: " << direction << "\n";
|
||||||
@@ -137,7 +137,7 @@ std::string find_target(std::string target,
|
|||||||
}
|
}
|
||||||
|
|
||||||
std::string resolve_caption_references(
|
std::string resolve_caption_references(
|
||||||
std::string target, std::vector<std::string> lines, numbered_elements states)
|
const std::string& target, const std::vector<std::string>& lines, numbered_elements states)
|
||||||
{
|
{
|
||||||
//auto lines = regex_split(text, std::regex(R"(\n)"), false);
|
//auto lines = regex_split(text, std::regex(R"(\n)"), false);
|
||||||
// numbered_elements states = line_states(lines);
|
// numbered_elements states = line_states(lines);
|
||||||
|
|||||||
@@ -11,12 +11,12 @@ using numbered_element_spec = std::tuple<std::string, std::string, std::string>;
|
|||||||
//using numbered_elements = std::vector<std::vector<numbered_element_spec>>;
|
//using numbered_elements = std::vector<std::vector<numbered_element_spec>>;
|
||||||
using numbered_elements = std::vector<numbered_element_spec>;
|
using numbered_elements = std::vector<numbered_element_spec>;
|
||||||
|
|
||||||
numbered_elements html_line_states(std::vector<std::string> lines);
|
numbered_elements html_line_states(const std::vector<std::string>& lines);
|
||||||
numbered_elements latex_line_states(std::vector<std::string> lines);
|
numbered_elements latex_line_states(const std::vector<std::string>& lines);
|
||||||
|
|
||||||
std::pair<std::string, int> add_html_caption_numbers(std::string html_text, int& chapter_number);
|
std::pair<std::string, int> add_html_caption_numbers(const std::string& html_text, int& chapter_number);
|
||||||
std::string add_latex_caption_numbers(std::string text);
|
std::string add_latex_caption_numbers(const std::string& text);
|
||||||
|
|
||||||
std::string resolve_caption_references(
|
std::string resolve_caption_references(
|
||||||
std::string target, std::vector<std::string> lines, numbered_elements states);
|
const std::string& target, const std::vector<std::string>& lines, numbered_elements states);
|
||||||
|
|
||||||
|
|||||||
@@ -5,7 +5,7 @@
|
|||||||
#include "klammer_base.h"
|
#include "klammer_base.h"
|
||||||
#include "show.h"
|
#include "show.h"
|
||||||
|
|
||||||
std::string Klammer_base::get(std::string name)
|
std::string Klammer_base::get(const std::string& name)
|
||||||
{
|
{
|
||||||
//std::cout << "GET " << name << "\n";
|
//std::cout << "GET " << name << "\n";
|
||||||
std::string result = m_machine.m_state.value(name);
|
std::string result = m_machine.m_state.value(name);
|
||||||
@@ -49,7 +49,7 @@ std::string Klammer_base::result()
|
|||||||
throw Target_error("Unknown target: " + target);
|
throw Target_error("Unknown target: " + target);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Klammer_base::show(std::string klammer_name)
|
void Klammer_base::show(const std::string& klammer_name)
|
||||||
{
|
{
|
||||||
std::cout << "Arguments of klammer \"" << klammer_name << "\"\n"
|
std::cout << "Arguments of klammer \"" << klammer_name << "\"\n"
|
||||||
<< m_machine.m_state.describe() << "\n";
|
<< m_machine.m_state.describe() << "\n";
|
||||||
|
|||||||
@@ -18,14 +18,14 @@ public:
|
|||||||
{};
|
{};
|
||||||
virtual ~Klammer_base() {};
|
virtual ~Klammer_base() {};
|
||||||
|
|
||||||
std::string get(std::string);
|
std::string get(const std::string& name);
|
||||||
std::string get(const char* name);
|
std::string get(const char* name);
|
||||||
virtual std::string html();
|
virtual std::string html();
|
||||||
virtual std::string tex();
|
virtual std::string tex();
|
||||||
virtual std::string txt();
|
virtual std::string txt();
|
||||||
|
|
||||||
std::string result();
|
std::string result();
|
||||||
void show(std::string klammer_name);
|
void show(const std::string& klammer_name);
|
||||||
|
|
||||||
Machine m_machine;
|
Machine m_machine;
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -10,7 +10,7 @@
|
|||||||
|
|
||||||
#include <filesystem>
|
#include <filesystem>
|
||||||
|
|
||||||
std::string read_file(std::string filename)
|
std::string read_file(const std::string& filename)
|
||||||
{
|
{
|
||||||
std::ifstream stream {};
|
std::ifstream stream {};
|
||||||
std::ostringstream buffer {};
|
std::ostringstream buffer {};
|
||||||
@@ -36,7 +36,7 @@ std::string klammertext_dir()
|
|||||||
return kdir;
|
return kdir;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool in_subset(std::string base, std::vector<std::string> subset)
|
bool in_subset(const std::string& base, const std::vector<std::string>& subset)
|
||||||
{
|
{
|
||||||
return subset.empty() ||
|
return subset.empty() ||
|
||||||
(std::find(subset.begin(), subset.end(), base) != subset.end());
|
(std::find(subset.begin(), subset.end(), base) != subset.end());
|
||||||
@@ -44,7 +44,7 @@ bool in_subset(std::string base, std::vector<std::string> subset)
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
std::vector<std::string> sks_files_of_type(std::string extension, std::vector<std::string> subset)
|
std::vector<std::string> sks_files_of_type(const std::string& extension, const std::vector<std::string>& subset)
|
||||||
{
|
{
|
||||||
bool dbg = false;
|
bool dbg = false;
|
||||||
std::string kdir = klammertext_dir();
|
std::string kdir = klammertext_dir();
|
||||||
@@ -85,7 +85,7 @@ std::vector<std::string> sks_files_of_type(std::string extension, std::vector<st
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string find_kt_file(std::string filename)
|
std::string find_kt_file(const std::string& filename)
|
||||||
{
|
{
|
||||||
std::string result {};
|
std::string result {};
|
||||||
std::vector<std::string> prefix {"", "kt/"};
|
std::vector<std::string> prefix {"", "kt/"};
|
||||||
@@ -117,7 +117,7 @@ std::string find_kt_file(std::string filename)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
std::string caption_marker(std::string name, std::string caption, std::string delimiter)
|
std::string caption_marker(const std::string& name, const std::string& caption, const std::string& delimiter)
|
||||||
{
|
{
|
||||||
std::string result {caption};
|
std::string result {caption};
|
||||||
if (caption.size() > 0) {
|
if (caption.size() > 0) {
|
||||||
@@ -128,7 +128,7 @@ std::string caption_marker(std::string name, std::string caption, std::string de
|
|||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
std::string process(Machine& M, std::string target, fs::path source_filename,
|
std::string process(Machine& M, const std::string& target, const fs::path& source_filename,
|
||||||
bool post_process, bool unescape_chars)
|
bool post_process, bool unescape_chars)
|
||||||
{
|
{
|
||||||
// Text text(source_filename, false, false);
|
// Text text(source_filename, false, false);
|
||||||
@@ -144,7 +144,7 @@ std::string process(Machine& M, std::string target, fs::path source_filename,
|
|||||||
return processed;
|
return processed;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string process(Machine& M, std::string target, std::string source_text,
|
std::string process(Machine& M, const std::string& target, const std::string& source_text,
|
||||||
bool post_process, bool unescape_chars)
|
bool post_process, bool unescape_chars)
|
||||||
{
|
{
|
||||||
Text text(source_text, false, false);
|
Text text(source_text, false, false);
|
||||||
@@ -157,8 +157,8 @@ std::string process(Machine& M, std::string target, std::string source_text,
|
|||||||
return processed;
|
return processed;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string process(Machine& M, std::string target,
|
std::string process(Machine& M, const std::string& target,
|
||||||
std::string source_text, fs::path source_filename,
|
const std::string& source_text, const fs::path& source_filename,
|
||||||
bool post_process, bool unescape_chars)
|
bool post_process, bool unescape_chars)
|
||||||
{
|
{
|
||||||
Text text({source_text}, {source_filename}, false, false);
|
Text text({source_text}, {source_filename}, false, false);
|
||||||
|
|||||||
@@ -12,24 +12,24 @@ std::vector<std::string> sks_basenames { // removed "book"
|
|||||||
|
|
||||||
const std::string caption_delimiter = "__CAPTION__";
|
const std::string caption_delimiter = "__CAPTION__";
|
||||||
|
|
||||||
std::string read_file(std::string filename);
|
std::string read_file(const std::string& filename);
|
||||||
|
|
||||||
std::string klammertext_dir();
|
std::string klammertext_dir();
|
||||||
|
|
||||||
std::vector<std::string> old_sks_files_of_type(std::string extension);
|
std::vector<std::string> old_sks_files_of_type(const std::string& extension);
|
||||||
std::vector<std::string> sks_files_of_type(std::string extension, std::vector<std::string> subset={});
|
std::vector<std::string> sks_files_of_type(const std::string& extension, const std::vector<std::string>& subset={});
|
||||||
|
|
||||||
std::string caption_marker(std::string name, std::string caption, std::string delimiter=" – ");
|
std::string caption_marker(const std::string& name, const std::string& caption, const std::string& delimiter=" – ");
|
||||||
|
|
||||||
std::string find_kt_file(std::string filename);
|
std::string find_kt_file(const std::string& filename);
|
||||||
|
|
||||||
std::string process(Machine& M, std::string target, std::string source_text,
|
std::string process(Machine& M, const std::string& target, const std::string& source_text,
|
||||||
bool post_process=false, bool unescape_chars=false);
|
bool post_process=false, bool unescape_chars=false);
|
||||||
|
|
||||||
std::string process(Machine& M, std::string target, fs::path source_filename,
|
std::string process(Machine& M, const std::string& target, const fs::path& source_filename,
|
||||||
bool post_process=false, bool unescape_chars=false);
|
bool post_process=false, bool unescape_chars=false);
|
||||||
|
|
||||||
std::string process(Machine& M, std::string target,
|
std::string process(Machine& M, const std::string& target,
|
||||||
std::string source_text, fs::path source_filename,
|
const std::string& source_text, const fs::path& source_filename,
|
||||||
bool post_process, bool unescape_chars);
|
bool post_process, bool unescape_chars);
|
||||||
|
|
||||||
|
|||||||
23
sks/sks.k
23
sks/sks.k
@@ -1,15 +1,10 @@
|
|||||||
# Standard Klammer Set
|
# Standard Klammer Set
|
||||||
@read kutil/kutil.k @
|
@@@klammerset sks | Document production: formatting, structure, and layout for the html, tex, pdf, and txt targets
|
||||||
@read target/target.k @
|
:name Standard Klammer Set
|
||||||
@read font/font.k @
|
:author Andy Kopra
|
||||||
@read section/section.k @
|
:date 2026-07-30
|
||||||
@read image/image.k @
|
:files kutil/kutil.k target/target.k font/font.k section/section.k
|
||||||
@read code/code.k @
|
image/image.k code/code.k list/list.k link/link.k
|
||||||
@read list/list.k @
|
table/table.k date/date.k block/block.k color/color.k
|
||||||
@read link/link.k @
|
document/document.k book/book.k
|
||||||
@read table/table.k @
|
@@@
|
||||||
@read date/date.k @
|
|
||||||
@read block/block.k @
|
|
||||||
@read color/color.k @
|
|
||||||
@read document/document.k @
|
|
||||||
@read book/book.k @
|
|
||||||
|
|||||||
@@ -132,7 +132,7 @@ std::string to_string(elements_t e)
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
bool HTML::void_element(std::string tag) const
|
bool HTML::void_element(const std::string& tag) const
|
||||||
{
|
{
|
||||||
if (tag == "!DOCTYPE")
|
if (tag == "!DOCTYPE")
|
||||||
return true;
|
return true;
|
||||||
@@ -141,7 +141,7 @@ bool HTML::void_element(std::string tag) const
|
|||||||
(m_void_tags.begin(), m_void_tags.end(), tag) != m_void_tags.end();
|
(m_void_tags.begin(), m_void_tags.end(), tag) != m_void_tags.end();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool HTML::empty_element(std::string tag) const
|
bool HTML::empty_element(const std::string& tag) const
|
||||||
{
|
{
|
||||||
if (tag == preamble_tag)
|
if (tag == preamble_tag)
|
||||||
return true;
|
return true;
|
||||||
@@ -151,13 +151,13 @@ bool HTML::empty_element(std::string tag) const
|
|||||||
}
|
}
|
||||||
|
|
||||||
//HTML& HTML::attr(std::string name, std::variant<int, float, std::string> value)
|
//HTML& HTML::attr(std::string name, std::variant<int, float, std::string> value)
|
||||||
HTML& HTML::attr(std::string name, attr_t value)
|
HTML& HTML::attr(const std::string& name, attr_t value)
|
||||||
{
|
{
|
||||||
m_attrs.push_back({name, value});
|
m_attrs.push_back({name, value});
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
|
|
||||||
HTML& HTML::attrs(std::string s)
|
HTML& HTML::attrs(const std::string& s)
|
||||||
{
|
{
|
||||||
static const std::regex attr_rgx(R"((\w+)\s*=\s*\"(.*?)\")");
|
static const std::regex attr_rgx(R"((\w+)\s*=\s*\"(.*?)\")");
|
||||||
auto attrs_begin = std::sregex_iterator(s.begin(), s.end(), attr_rgx);
|
auto attrs_begin = std::sregex_iterator(s.begin(), s.end(), attr_rgx);
|
||||||
@@ -177,25 +177,25 @@ HTML& HTML::attrs(std::string s)
|
|||||||
|
|
||||||
namespace html {
|
namespace html {
|
||||||
|
|
||||||
HTML elt(std::string tag)
|
HTML elt(const std::string& tag)
|
||||||
{
|
{
|
||||||
HTML h(tag);
|
HTML h(tag);
|
||||||
return h;
|
return h;
|
||||||
}
|
}
|
||||||
|
|
||||||
HTML elt(std::string tag, std::string text)
|
HTML elt(const std::string& tag, const std::string& text)
|
||||||
{
|
{
|
||||||
HTML h(tag, trim(text));
|
HTML h(tag, trim(text));
|
||||||
return h;
|
return h;
|
||||||
}
|
}
|
||||||
|
|
||||||
HTML elt(std::string tag, elements_t elements)
|
HTML elt(const std::string& tag, elements_t elements)
|
||||||
{
|
{
|
||||||
HTML h(tag, elements);
|
HTML h(tag, elements);
|
||||||
return h;
|
return h;
|
||||||
}
|
}
|
||||||
|
|
||||||
HTML elt(std::string tag, HTML e, elements_t elts)
|
HTML elt(const std::string& tag, HTML e, elements_t elts)
|
||||||
{
|
{
|
||||||
elements_t elements = {e};
|
elements_t elements = {e};
|
||||||
elements.insert(elements.end(), elts.begin(), elts.end());
|
elements.insert(elements.end(), elts.begin(), elts.end());
|
||||||
@@ -242,7 +242,7 @@ namespace html {
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
elements_t local_font_elements(strings_t fontnames)
|
elements_t local_font_elements(const strings_t& fontnames)
|
||||||
{
|
{
|
||||||
elements_t result {};
|
elements_t result {};
|
||||||
for (auto name : fontnames) {
|
for (auto name : fontnames) {
|
||||||
@@ -254,7 +254,7 @@ namespace html {
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
elements_t javascript(std::string output_dir, strings_t js_filenames)
|
elements_t javascript(const std::string& output_dir, const strings_t& js_filenames)
|
||||||
{
|
{
|
||||||
//elements_t result { jquery_elements() };
|
//elements_t result { jquery_elements() };
|
||||||
elements_t result {};
|
elements_t result {};
|
||||||
@@ -276,10 +276,10 @@ namespace html {
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
HTML head(std::string title,
|
HTML head(const std::string& title,
|
||||||
std::string css,
|
const std::string& css,
|
||||||
strings_t css_filenames,
|
const strings_t& css_filenames,
|
||||||
strings_t local_fonts)
|
const strings_t& local_fonts)
|
||||||
{
|
{
|
||||||
elements_t elts = meta_elements();
|
elements_t elts = meta_elements();
|
||||||
// msg() << "ELTS sks: " << elts << "\n";
|
// msg() << "ELTS sks: " << elts << "\n";
|
||||||
@@ -317,8 +317,8 @@ namespace html {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
HTML button(std::string id, std::string name,
|
HTML button(const std::string& id, const std::string& name,
|
||||||
std::string attrib="", std::string value="")
|
const std::string& attrib="", const std::string& value="")
|
||||||
{
|
{
|
||||||
std::vector<std::string> hidden = {"Clear", "Back"};
|
std::vector<std::string> hidden = {"Clear", "Back"};
|
||||||
HTML result = elt("span", string_replace(name, " ", " ")).id(id).cls("navb");
|
HTML result = elt("span", string_replace(name, " ", " ")).id(id).cls("navb");
|
||||||
@@ -449,7 +449,7 @@ namespace html {
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
elements_t status(std::string date, std::string version, std::string copyright)
|
elements_t status(const std::string& date, const std::string& version, const std::string& copyright)
|
||||||
{
|
{
|
||||||
elements_t result {};
|
elements_t result {};
|
||||||
if (!date.empty()) {
|
if (!date.empty()) {
|
||||||
@@ -465,21 +465,21 @@ namespace html {
|
|||||||
}
|
}
|
||||||
|
|
||||||
elements_t page(
|
elements_t page(
|
||||||
std::string title,
|
const std::string& title,
|
||||||
std::string page_title,
|
std::string page_title,
|
||||||
std::string output_dir,
|
const std::string& output_dir,
|
||||||
std::string nav,
|
const std::string& nav,
|
||||||
int max_level,
|
int max_level,
|
||||||
std::string toc,
|
const std::string& toc,
|
||||||
std::string text,
|
const std::string& text,
|
||||||
std::string date,
|
const std::string& date,
|
||||||
std::string version,
|
const std::string& version,
|
||||||
std::string copyright,
|
const std::string& copyright,
|
||||||
std::string css,
|
const std::string& css,
|
||||||
strings_t css_filenames,
|
const strings_t& css_filenames,
|
||||||
strings_t js_filenames,
|
const strings_t& js_filenames,
|
||||||
strings_t local_fonts,
|
const strings_t& local_fonts,
|
||||||
std::string logo)
|
const std::string& logo)
|
||||||
{
|
{
|
||||||
if (page_title.empty())
|
if (page_title.empty())
|
||||||
page_title = title;
|
page_title = title;
|
||||||
@@ -540,7 +540,7 @@ namespace html {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void add_title(elements_t& body, std::string title, std::string logo)
|
void add_title(elements_t& body, const std::string& title, const std::string& logo)
|
||||||
{
|
{
|
||||||
// No title bar at all when there is nothing to put in it (an
|
// No title bar at all when there is nothing to put in it (an
|
||||||
// untitled document); a logo alone still gets the bar.
|
// untitled document); a logo alone still gets the bar.
|
||||||
@@ -561,7 +561,7 @@ namespace html {
|
|||||||
body.push_back(navigation(max_level));
|
body.push_back(navigation(max_level));
|
||||||
}
|
}
|
||||||
|
|
||||||
void add_text(elements_t& body, std::string text, std::string toc, bool text_only)
|
void add_text(elements_t& body, const std::string& text, const std::string& toc, bool text_only)
|
||||||
{
|
{
|
||||||
if (text_only) {
|
if (text_only) {
|
||||||
elements_t content {};
|
elements_t content {};
|
||||||
@@ -580,7 +580,7 @@ namespace html {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void add_status_bar(
|
void add_status_bar(
|
||||||
elements_t& body, std::string date, std::string version, std::string copyright)
|
elements_t& body, const std::string& date, const std::string& version, const std::string& copyright)
|
||||||
{
|
{
|
||||||
elements_t status_elements = status(date, version, copyright);
|
elements_t status_elements = status(date, version, copyright);
|
||||||
if (!empty(status_elements)) {
|
if (!empty(status_elements)) {
|
||||||
@@ -593,7 +593,7 @@ namespace html {
|
|||||||
body.push_back(elt("div", "").attr("id", "pagecache"));
|
body.push_back(elt("div", "").attr("id", "pagecache"));
|
||||||
}
|
}
|
||||||
|
|
||||||
void add_js_links(elements_t& body, strings_t js_filenames, std::string output_dir)
|
void add_js_links(elements_t& body, const strings_t& js_filenames, const std::string& output_dir)
|
||||||
{
|
{
|
||||||
if (!js_filenames.empty()) {
|
if (!js_filenames.empty()) {
|
||||||
auto js_elements { javascript(output_dir, js_filenames) };
|
auto js_elements { javascript(output_dir, js_filenames) };
|
||||||
@@ -603,8 +603,8 @@ namespace html {
|
|||||||
|
|
||||||
elements_t make_page(
|
elements_t make_page(
|
||||||
elements_t body,
|
elements_t body,
|
||||||
std::string page_title, std::string css,
|
std::string page_title, const std::string& css,
|
||||||
strings_t css_filenames, strings_t local_fonts)
|
const strings_t& css_filenames, const strings_t& local_fonts)
|
||||||
{
|
{
|
||||||
elements_t page { preamble() };
|
elements_t page { preamble() };
|
||||||
page.push_back(
|
page.push_back(
|
||||||
@@ -615,7 +615,7 @@ namespace html {
|
|||||||
return page;
|
return page;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool tag_is_block_element(std::string tag)
|
bool tag_is_block_element(const std::string& tag)
|
||||||
{
|
{
|
||||||
auto location = std::find(block_elements.begin(), block_elements.end(), tag);
|
auto location = std::find(block_elements.begin(), block_elements.end(), tag);
|
||||||
return location != block_elements.end();
|
return location != block_elements.end();
|
||||||
@@ -635,7 +635,7 @@ namespace html {
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string make_paragraphs(std::string html_text)
|
std::string make_paragraphs(const std::string& html_text)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
std::string result {};
|
std::string result {};
|
||||||
@@ -654,7 +654,7 @@ namespace html {
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string minimize_css(std::string src)
|
std::string minimize_css(const std::string& src)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
std::string result = src;
|
std::string result = src;
|
||||||
@@ -668,7 +668,7 @@ namespace html {
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string minimize_js(std::string src)
|
std::string minimize_js(const std::string& src)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
return src;
|
return src;
|
||||||
|
|||||||
@@ -32,24 +32,24 @@ public:
|
|||||||
operator std::string() {
|
operator std::string() {
|
||||||
std::stringstream ss {}; ss << *this; return ss.str(); };
|
std::stringstream ss {}; ss << *this; return ss.str(); };
|
||||||
|
|
||||||
HTML(std::string tag) :
|
HTML(const std::string& tag) :
|
||||||
m_tag(tag) {};
|
m_tag(tag) {};
|
||||||
|
|
||||||
HTML(std::string tag, std::string text) :
|
HTML(const std::string& tag, const std::string& text) :
|
||||||
m_tag(tag), m_text({text}) {};
|
m_tag(tag), m_text({text}) {};
|
||||||
|
|
||||||
HTML(std::string tag, elements_t elements) :
|
HTML(const std::string& tag, elements_t elements) :
|
||||||
m_tag(tag), m_elements(elements) {};
|
m_tag(tag), m_elements(elements) {};
|
||||||
|
|
||||||
HTML& attr(std::string name, attr_t value);
|
HTML& attr(const std::string& name, attr_t value);
|
||||||
HTML& attrs(std::string s);
|
HTML& attrs(const std::string& s);
|
||||||
|
|
||||||
HTML& cls(std::string name) { return attr("class", name); };
|
HTML& cls(const std::string& name) { return attr("class", name); };
|
||||||
HTML& sty(std::string css) { return attr("style", css); };
|
HTML& sty(const std::string& css) { return attr("style", css); };
|
||||||
HTML& id(std::string id) { return attr("id", id); };
|
HTML& id(const std::string& id) { return attr("id", id); };
|
||||||
|
|
||||||
bool void_element(std::string tag) const;
|
bool void_element(const std::string& tag) const;
|
||||||
bool empty_element(std::string tag) const;
|
bool empty_element(const std::string& tag) const;
|
||||||
friend std::ostream& operator<<(std::ostream& os, const HTML& h);
|
friend std::ostream& operator<<(std::ostream& os, const HTML& h);
|
||||||
friend std::ostream& operator<<(std::ostream& os, const std::vector<HTML>& hv);
|
friend std::ostream& operator<<(std::ostream& os, const std::vector<HTML>& hv);
|
||||||
|
|
||||||
@@ -68,48 +68,48 @@ private:
|
|||||||
};
|
};
|
||||||
|
|
||||||
namespace html {
|
namespace html {
|
||||||
HTML elt(std::string tag);
|
HTML elt(const std::string& tag);
|
||||||
HTML elt(std::string tag, std::string text);
|
HTML elt(const std::string& tag, const std::string& text);
|
||||||
HTML elt(std::string tag, elements_t elements);
|
HTML elt(const std::string& tag, elements_t elements);
|
||||||
HTML elt(std::string tag, HTML e, elements_t elts);
|
HTML elt(const std::string& tag, HTML e, elements_t elts);
|
||||||
|
|
||||||
//HTML preamble();
|
//HTML preamble();
|
||||||
//HTML head(strings_t css_filenames, strings_t js_filenames);
|
//HTML head(strings_t css_filenames, strings_t js_filenames);
|
||||||
|
|
||||||
elements_t page(
|
elements_t page(
|
||||||
std::string title,
|
const std::string& title,
|
||||||
std::string page_title,
|
std::string page_title,
|
||||||
std::string output_dir,
|
const std::string& output_dir,
|
||||||
std::string nav,
|
const std::string& nav,
|
||||||
int max_level,
|
int max_level,
|
||||||
std::string toc,
|
const std::string& toc,
|
||||||
std::string text,
|
const std::string& text,
|
||||||
std::string date,
|
const std::string& date,
|
||||||
std::string version,
|
const std::string& version,
|
||||||
std::string copyright,
|
const std::string& copyright,
|
||||||
std::string css,
|
const std::string& css,
|
||||||
strings_t css_filenames = {},
|
strings_t css_filenames = {},
|
||||||
strings_t js_filenames = {},
|
strings_t js_filenames = {},
|
||||||
strings_t local_fonts = {},
|
strings_t local_fonts = {},
|
||||||
std::string logo = {});
|
std::string logo = {});
|
||||||
|
|
||||||
void add_title(elements_t& body, std::string title, std::string logo="");
|
void add_title(elements_t& body, const std::string& title, const std::string& logo="");
|
||||||
void add_title(elements_t& body, std::string title, std::string logo);
|
void add_title(elements_t& body, const std::string& title, const std::string& logo);
|
||||||
void add_nav(elements_t& body, int max_level);
|
void add_nav(elements_t& body, int max_level);
|
||||||
void add_text(elements_t& body, std::string text, std::string toc_text, bool text_only);
|
void add_text(elements_t& body, const std::string& text, const std::string& toc_text, bool text_only);
|
||||||
void add_bottom_spacer(elements_t& body);
|
void add_bottom_spacer(elements_t& body);
|
||||||
void add_status_bar(elements_t& body, std::string date, std::string version, std::string copyright);
|
void add_status_bar(elements_t& body, const std::string& date, const std::string& version, const std::string& copyright);
|
||||||
void add_page_cache(elements_t& body);
|
void add_page_cache(elements_t& body);
|
||||||
void add_js_links(elements_t& body, std::vector<std::string> js_filenames, std::string output_dir);
|
void add_js_links(elements_t& body, const std::vector<std::string>& js_filenames, const std::string& output_dir);
|
||||||
elements_t make_page(
|
elements_t make_page(
|
||||||
elements_t body,
|
elements_t body,
|
||||||
std::string page_title, std::string css,
|
std::string page_title, const std::string& css,
|
||||||
std::vector<std::string> css_filenames,
|
const std::vector<std::string>& css_filenames,
|
||||||
std::vector<std::string> local_fonts);
|
const std::vector<std::string>& local_fonts);
|
||||||
|
|
||||||
bool tag_is_block_element(std::string tag);
|
bool tag_is_block_element(const std::string& tag);
|
||||||
std::string make_paragraphs(std::string html_text);
|
std::string make_paragraphs(const std::string& html_text);
|
||||||
std::string minimize_css(std::string src);
|
std::string minimize_css(const std::string& src);
|
||||||
std::string minimize_js(std::string src);
|
std::string minimize_js(const std::string& src);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -33,7 +33,7 @@ namespace latex {
|
|||||||
|
|
||||||
|
|
||||||
std::string title_line(
|
std::string title_line(
|
||||||
std::string text, std::string font="1.3", std::string vskip="4pt",
|
const std::string& text, const std::string& font="1.3", const std::string& vskip="4pt",
|
||||||
bool vskip_if_missing=false)
|
bool vskip_if_missing=false)
|
||||||
{
|
{
|
||||||
std::stringstream ss {};
|
std::stringstream ss {};
|
||||||
@@ -48,8 +48,8 @@ namespace latex {
|
|||||||
}
|
}
|
||||||
|
|
||||||
std::string default_cover(
|
std::string default_cover(
|
||||||
std::string title, std::string subtitle,
|
const std::string& title, const std::string& subtitle,
|
||||||
std::string author, std::string date, std::string version)
|
const std::string& author, const std::string& date, const std::string& version)
|
||||||
{
|
{
|
||||||
std::string test = trim(title + subtitle + author + date + version);
|
std::string test = trim(title + subtitle + author + date + version);
|
||||||
std::stringstream ss {};
|
std::stringstream ss {};
|
||||||
@@ -65,8 +65,8 @@ namespace latex {
|
|||||||
}
|
}
|
||||||
|
|
||||||
std::string nonbook_title(
|
std::string nonbook_title(
|
||||||
std::string title, std::string subtitle,
|
const std::string& title, const std::string& subtitle,
|
||||||
std::string author, std::string date, std::string version)
|
const std::string& author, const std::string& date, const std::string& version)
|
||||||
{
|
{
|
||||||
std::string test = trim(title + subtitle + author + date + version);
|
std::string test = trim(title + subtitle + author + date + version);
|
||||||
std::stringstream ss {};
|
std::stringstream ss {};
|
||||||
@@ -86,7 +86,7 @@ namespace latex {
|
|||||||
return ss.str();
|
return ss.str();
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string pagenumber(int n, std::string style="arabic")
|
std::string pagenumber(int n, const std::string& style="arabic")
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
std::stringstream ss {};
|
std::stringstream ss {};
|
||||||
@@ -94,7 +94,7 @@ namespace latex {
|
|||||||
return ss.str();
|
return ss.str();
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string book_verso_page(std::string copyright)
|
std::string book_verso_page(const std::string& copyright)
|
||||||
{
|
{
|
||||||
(void)K::log(3);
|
(void)K::log(3);
|
||||||
std::stringstream ss {};
|
std::stringstream ss {};
|
||||||
@@ -111,7 +111,7 @@ namespace latex {
|
|||||||
return ss.str();
|
return ss.str();
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string font_command(std::string command, const Resolved_font& font, float scale)
|
std::string font_command(const std::string& command, const Resolved_font& font, float scale)
|
||||||
{
|
{
|
||||||
std::stringstream ss {};
|
std::stringstream ss {};
|
||||||
if (font.family_name.empty())
|
if (font.family_name.empty())
|
||||||
@@ -150,23 +150,23 @@ namespace latex {
|
|||||||
return ss.str();
|
return ss.str();
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string page(std::string structure,
|
std::string page(const std::string& structure,
|
||||||
std::string title,
|
const std::string& title,
|
||||||
std::string subtitle,
|
const std::string& subtitle,
|
||||||
std::string authors,
|
const std::string& authors,
|
||||||
std::string date,
|
const std::string& date,
|
||||||
std::string version,
|
const std::string& version,
|
||||||
std::string copyright,
|
const std::string& copyright,
|
||||||
std::string bottom,
|
const std::string& bottom,
|
||||||
std::string prolog,
|
const std::string& prolog,
|
||||||
std::string paper_size,
|
const std::string& paper_size,
|
||||||
bool two_column,
|
bool two_column,
|
||||||
float leading,
|
float leading,
|
||||||
int pointsize,
|
int pointsize,
|
||||||
bool ragged_right,
|
bool ragged_right,
|
||||||
std::string cover,
|
const std::string& cover,
|
||||||
bool landscape,
|
bool landscape,
|
||||||
std::string body,
|
const std::string& body,
|
||||||
Resolved_font serif_font,
|
Resolved_font serif_font,
|
||||||
Resolved_font sans_font,
|
Resolved_font sans_font,
|
||||||
Resolved_font mono_font,
|
Resolved_font mono_font,
|
||||||
|
|||||||
@@ -6,23 +6,23 @@
|
|||||||
|
|
||||||
namespace latex {
|
namespace latex {
|
||||||
|
|
||||||
std::string page(std::string structure,
|
std::string page(const std::string& structure,
|
||||||
std::string title,
|
const std::string& title,
|
||||||
std::string subtitle,
|
const std::string& subtitle,
|
||||||
std::string authors,
|
const std::string& authors,
|
||||||
std::string date,
|
const std::string& date,
|
||||||
std::string version,
|
const std::string& version,
|
||||||
std::string copyright,
|
const std::string& copyright,
|
||||||
std::string bottom,
|
const std::string& bottom,
|
||||||
std::string prolog,
|
const std::string& prolog,
|
||||||
std::string paper_size,
|
const std::string& paper_size,
|
||||||
bool two_column,
|
bool two_column,
|
||||||
float leading,
|
float leading,
|
||||||
int pointsize,
|
int pointsize,
|
||||||
bool ragged_right,
|
bool ragged_right,
|
||||||
std::string cover,
|
const std::string& cover,
|
||||||
bool landscape,
|
bool landscape,
|
||||||
std::string body,
|
const std::string& body,
|
||||||
Resolved_font serif_font = {},
|
Resolved_font serif_font = {},
|
||||||
Resolved_font sans_font = {},
|
Resolved_font sans_font = {},
|
||||||
Resolved_font mono_font = {},
|
Resolved_font mono_font = {},
|
||||||
|
|||||||
@@ -3,7 +3,7 @@ The targets in the SKS use the LaTeX convention for converting ASCII
|
|||||||
characters into standard typographical characters. This is done
|
characters into standard typographical characters. This is done
|
||||||
by LaTeX by default; other targets must use the transforms parameter
|
by LaTeX by default; other targets must use the transforms parameter
|
||||||
of Parameter_set, as defined for the m_parameters variable of the
|
of Parameter_set, as defined for the m_parameters variable of the
|
||||||
Target_set class. (See file target_set.cpp.)
|
Target_registry class. (See file target_registry.cpp.)
|
||||||
|
|
||||||
The LaTeX transformations supported by the SKS are:
|
The LaTeX transformations supported by the SKS are:
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
# Klammertext distribution test suite (subset).
|
# Klammertext distribution test suite (subset).
|
||||||
#
|
#
|
||||||
# Runs the seven shell regression suites:
|
# Runs the eight shell regression suites:
|
||||||
# cond_test.sh — @cond argument delimitation
|
# cond_test.sh — @cond argument delimitation
|
||||||
# deftype_test.sh — the four klammer definition modes + redefinition table
|
# deftype_test.sh — the four klammer definition modes + redefinition table
|
||||||
# escape_test.sh — target character escaping and quoted specials
|
# escape_test.sh — target character escaping and quoted specials
|
||||||
@@ -8,6 +8,7 @@
|
|||||||
# alone_test.sh — an optional argument's three values (default, the
|
# alone_test.sh — an optional argument's three values (default, the
|
||||||
# argument type's :alone value, a written value)
|
# argument type's :alone value, a written value)
|
||||||
# modulepath_test.sh — @eval finds modules beside the file that names them
|
# modulepath_test.sh — @eval finds modules beside the file that names them
|
||||||
|
# klammerset_test.sh — the @@@klammerset system command and its search path
|
||||||
# editor_test.sh — editor support (doc/edit): indentation and table
|
# editor_test.sh — editor support (doc/edit): indentation and table
|
||||||
# alignment; needs python3, uses Emacs when installed
|
# alignment; needs python3, uses Emacs when installed
|
||||||
#
|
#
|
||||||
@@ -21,4 +22,5 @@ test:
|
|||||||
./filename_test.sh
|
./filename_test.sh
|
||||||
./alone_test.sh
|
./alone_test.sh
|
||||||
./modulepath_test.sh
|
./modulepath_test.sh
|
||||||
|
./klammerset_test.sh
|
||||||
./editor_test.sh
|
./editor_test.sh
|
||||||
|
|||||||
@@ -17,7 +17,7 @@
|
|||||||
# combinations. This test pins down every entry of that table plus the basic
|
# combinations. This test pins down every entry of that table plus the basic
|
||||||
# behavior of each mode, none of which tst/klammer_test.cpp currently covers.
|
# behavior of each mode, none of which tst/klammer_test.cpp currently covers.
|
||||||
#
|
#
|
||||||
# {replace,warn,message} semantics (mac/klammer_set.cpp):
|
# {replace,warn,message} semantics (mac/klammer_registry.cpp):
|
||||||
# !replace && message -> Definition_error (nonzero exit)
|
# !replace && message -> Definition_error (nonzero exit)
|
||||||
# !replace && empty -> silently keep the existing definition
|
# !replace && empty -> silently keep the existing definition
|
||||||
# replace && warn -> emit a warning, then replace
|
# replace && warn -> emit a warning, then replace
|
||||||
|
|||||||
1
tst/klammerset/bad_file.k
Normal file
1
tst/klammerset/bad_file.k
Normal file
@@ -0,0 +1 @@
|
|||||||
|
@@@klammerset broken | Lists a file that does not exist :files missing.k @@@
|
||||||
1
tst/klammerset/base.k
Normal file
1
tst/klammerset/base.k
Normal file
@@ -0,0 +1 @@
|
|||||||
|
@@@target fix | Fixture target @@@
|
||||||
11
tst/klammerset/decl.k
Normal file
11
tst/klammerset/decl.k
Normal file
@@ -0,0 +1,11 @@
|
|||||||
|
# Engine-tier fixture: a klammerset with metadata, a dependency, an ordered
|
||||||
|
# file list (klammers.k uses the target defined in base.k), and a trailing
|
||||||
|
# definition that must load after the files (program order).
|
||||||
|
@@@klammerset kit | Engine-test klammerset
|
||||||
|
:name Klammerset Integration Test
|
||||||
|
:author Klammertext tests
|
||||||
|
:date 2026-07-30
|
||||||
|
:requires util.k
|
||||||
|
:files base.k / klammers.k
|
||||||
|
@@@
|
||||||
|
@@after : AFTER @@
|
||||||
1
tst/klammerset/decl2.k
Normal file
1
tst/klammerset/decl2.k
Normal file
@@ -0,0 +1 @@
|
|||||||
|
@@@klammerset kit | Duplicate declaration of kit :files dup_only.k @@@
|
||||||
1
tst/klammerset/dup_only.k
Normal file
1
tst/klammerset/dup_only.k
Normal file
@@ -0,0 +1 @@
|
|||||||
|
@@only_dup : DUP @@
|
||||||
1
tst/klammerset/klammers.k
Normal file
1
tst/klammerset/klammers.k
Normal file
@@ -0,0 +1 @@
|
|||||||
|
@@greet.fix name : Hello *name* @@
|
||||||
1
tst/klammerset/space name.k
Normal file
1
tst/klammerset/space name.k
Normal file
@@ -0,0 +1 @@
|
|||||||
|
@@spacey.fix : SPACEY @@
|
||||||
1
tst/klammerset/spacey.k
Normal file
1
tst/klammerset/spacey.k
Normal file
@@ -0,0 +1 @@
|
|||||||
|
@@@klammerset sp | Spacey filename in the list :files base.k / space name.k @@@
|
||||||
2
tst/klammerset/util.k
Normal file
2
tst/klammerset/util.k
Normal file
@@ -0,0 +1,2 @@
|
|||||||
|
@@@klammerset util | Utility klammers for engine tests :date 2026-07-30 @@@
|
||||||
|
@@dash : -- @@
|
||||||
1
tst/klammerset/wrapper.k
Normal file
1
tst/klammerset/wrapper.k
Normal file
@@ -0,0 +1 @@
|
|||||||
|
@@@klammerset wrap | Wrapper requiring kit twice :requires decl.k / decl2.k @@@
|
||||||
284
tst/klammerset_test.sh
Executable file
284
tst/klammerset_test.sh
Executable file
@@ -0,0 +1,284 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
#
|
||||||
|
# klammerset_test.sh — Regression tests for the @@@klammerset system command.
|
||||||
|
#
|
||||||
|
# @@@klammerset declares a Klammerset: a named, logically related group of
|
||||||
|
# klammer definitions. The declaration is operative — processing it reads
|
||||||
|
# the :requires files and then the :files, in list order, at the point of the
|
||||||
|
# declaration; relative names resolve against the declaring file's directory,
|
||||||
|
# never the cwd. A repeated declaration of an already-registered symbol is
|
||||||
|
# skipped (loaded once), which is what makes :requires idempotent. The
|
||||||
|
# klammers themselves live in the Machine's flat Klammer_registry; the
|
||||||
|
# Klammerset holds metadata and the file list only.
|
||||||
|
#
|
||||||
|
# Engine tier: no SKS. Fixtures live in tst/klammerset/ and define their own
|
||||||
|
# target ("fix") inline.
|
||||||
|
#
|
||||||
|
# Usage: ./klammerset_test.sh
|
||||||
|
# Exit code: 0 if all tests pass, 1 otherwise.
|
||||||
|
|
||||||
|
PASS=0
|
||||||
|
FAIL=0
|
||||||
|
KTEXT=ktext
|
||||||
|
K=${KLAMMERTEXT_HOME:?KLAMMERTEXT_HOME must be set}
|
||||||
|
FIX=$K/tst/klammerset
|
||||||
|
|
||||||
|
red=$'\033[31m'
|
||||||
|
green=$'\033[32m'
|
||||||
|
bold=$'\033[1m'
|
||||||
|
reset=$'\033[0m'
|
||||||
|
|
||||||
|
# strip leading/trailing blank lines and surrounding whitespace
|
||||||
|
trim() { awk '{ sub(/[ \t\r]+$/, "") } { line[NR]=$0 } END { f=1; while (f<=NR && line[f]=="") f++; l=NR; while (l>=1 && line[l]=="") l--; for (i=f;i<=l;i++) print line[i] }'; }
|
||||||
|
|
||||||
|
# check_eq TEST_NAME EXPECTED KTEXT_ARGS...
|
||||||
|
# Runs ktext, expects exit status 0, and compares trimmed stdout to EXPECTED.
|
||||||
|
check_eq() {
|
||||||
|
local test_name="$1"
|
||||||
|
local expected="$2"
|
||||||
|
shift 2
|
||||||
|
|
||||||
|
local output status
|
||||||
|
output=$("$KTEXT" "$@" 2>/tmp/klammerset_test_err.$$)
|
||||||
|
status=$?
|
||||||
|
output=$(printf '%s' "$output" | trim)
|
||||||
|
|
||||||
|
if [ $status -ne 0 ]; then
|
||||||
|
echo "${red}FAIL${reset} $test_name — ktext exited $status"
|
||||||
|
echo " stderr: $(head -3 /tmp/klammerset_test_err.$$)"
|
||||||
|
FAIL=$((FAIL + 1))
|
||||||
|
return
|
||||||
|
fi
|
||||||
|
if [ "$output" = "$expected" ]; then
|
||||||
|
echo "${green}PASS${reset} $test_name"
|
||||||
|
PASS=$((PASS + 1))
|
||||||
|
else
|
||||||
|
echo "${red}FAIL${reset} $test_name"
|
||||||
|
echo " expected: [$expected]"
|
||||||
|
echo " got: [$output]"
|
||||||
|
FAIL=$((FAIL + 1))
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# check_contains TEST_NAME SUBSTRING KTEXT_ARGS...
|
||||||
|
# Runs ktext, expects exit status 0, and checks that the combined output
|
||||||
|
# contains SUBSTRING.
|
||||||
|
check_contains() {
|
||||||
|
local test_name="$1"
|
||||||
|
local needle="$2"
|
||||||
|
shift 2
|
||||||
|
|
||||||
|
local output status
|
||||||
|
output=$("$KTEXT" "$@" 2>&1)
|
||||||
|
status=$?
|
||||||
|
|
||||||
|
if [ $status -ne 0 ]; then
|
||||||
|
echo "${red}FAIL${reset} $test_name — ktext exited $status"
|
||||||
|
echo " output: $(echo "$output" | head -3)"
|
||||||
|
FAIL=$((FAIL + 1))
|
||||||
|
return
|
||||||
|
fi
|
||||||
|
if printf '%s' "$output" | grep -qF "$needle"; then
|
||||||
|
echo "${green}PASS${reset} $test_name"
|
||||||
|
PASS=$((PASS + 1))
|
||||||
|
else
|
||||||
|
echo "${red}FAIL${reset} $test_name"
|
||||||
|
echo " expected output to contain: [$needle]"
|
||||||
|
echo " got: $(echo "$output" | head -5)"
|
||||||
|
FAIL=$((FAIL + 1))
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
# check_fails TEST_NAME SUBSTRING KTEXT_ARGS...
|
||||||
|
# Runs ktext, expects a NONZERO exit status, and checks that the combined
|
||||||
|
# output contains SUBSTRING.
|
||||||
|
check_fails() {
|
||||||
|
local test_name="$1"
|
||||||
|
local needle="$2"
|
||||||
|
shift 2
|
||||||
|
|
||||||
|
local output status
|
||||||
|
output=$("$KTEXT" "$@" 2>&1)
|
||||||
|
status=$?
|
||||||
|
|
||||||
|
if [ $status -eq 0 ]; then
|
||||||
|
echo "${red}FAIL${reset} $test_name — expected an error, ktext exited 0"
|
||||||
|
FAIL=$((FAIL + 1))
|
||||||
|
return
|
||||||
|
fi
|
||||||
|
if printf '%s' "$output" | grep -qF "$needle"; then
|
||||||
|
echo "${green}PASS${reset} $test_name"
|
||||||
|
PASS=$((PASS + 1))
|
||||||
|
else
|
||||||
|
echo "${red}FAIL${reset} $test_name"
|
||||||
|
echo " expected error output to contain: [$needle]"
|
||||||
|
echo " got: $(echo "$output" | head -5)"
|
||||||
|
FAIL=$((FAIL + 1))
|
||||||
|
fi
|
||||||
|
}
|
||||||
|
|
||||||
|
echo "${bold}@@@klammerset tests${reset}"
|
||||||
|
echo "======================="
|
||||||
|
echo
|
||||||
|
|
||||||
|
# --- Loading ---------------------------------------------------------------
|
||||||
|
|
||||||
|
# 1. :files load in list order: klammers.k defines @greet for the target
|
||||||
|
# that base.k declares, so base.k must have been read first.
|
||||||
|
check_eq "1. :files load in order (target before klammer)" \
|
||||||
|
"Hello World" \
|
||||||
|
-k "$FIX/decl.k" -s '@greet World @' -t fix
|
||||||
|
|
||||||
|
# 2. :requires loads the dependency before the set's own files.
|
||||||
|
check_eq "2. :requires loads the dependency" \
|
||||||
|
"--" \
|
||||||
|
-k "$FIX/decl.k" -s '@dash@' -t fix
|
||||||
|
|
||||||
|
# 3. Program order: a definition AFTER the declaration in the declaring file
|
||||||
|
# is available (there is no :text argument; the declaring file's own
|
||||||
|
# content plays that role).
|
||||||
|
check_eq "3. trailing definition in the declaring file" \
|
||||||
|
"AFTER" \
|
||||||
|
-k "$FIX/decl.k" -s '@after@' -t fix
|
||||||
|
|
||||||
|
# 4. Relative :files names resolve against the DECLARING file's directory,
|
||||||
|
# not the cwd (run from an unrelated directory).
|
||||||
|
output=$( (cd /tmp && "$KTEXT" -k "$FIX/decl.k" -s '@greet Elsewhere @' -t fix) 2>/dev/null | trim )
|
||||||
|
if [ "$output" = "Hello Elsewhere" ]; then
|
||||||
|
echo "${green}PASS${reset} 4. :files resolve against the declaring file's directory"
|
||||||
|
PASS=$((PASS + 1))
|
||||||
|
else
|
||||||
|
echo "${red}FAIL${reset} 4. :files resolve against the declaring file's directory"
|
||||||
|
echo " expected: [Hello Elsewhere]"
|
||||||
|
echo " got: [$output]"
|
||||||
|
FAIL=$((FAIL + 1))
|
||||||
|
fi
|
||||||
|
|
||||||
|
# 5. A filename with a space in the :files list (standalone "/" separator).
|
||||||
|
check_eq "5. spacey filename in :files" \
|
||||||
|
"SPACEY" \
|
||||||
|
-k "$FIX/spacey.k" -s '@spacey@' -t fix
|
||||||
|
|
||||||
|
# --- The already-loaded guard ------------------------------------------------
|
||||||
|
|
||||||
|
# 6. A second declaration of an already-registered symbol is skipped, not an
|
||||||
|
# error: wrapper.k requires decl.k (registers "kit") and then decl2.k
|
||||||
|
# (re-declares "kit"); the wrapper still loads and kit's klammers work.
|
||||||
|
check_eq "6. duplicate declaration is skipped, not an error" \
|
||||||
|
"Hello Again" \
|
||||||
|
-k "$FIX/wrapper.k" -s '@greet Again @' -t fix
|
||||||
|
|
||||||
|
# 7. ...and the skipped declaration's files are NOT loaded.
|
||||||
|
check_fails "7. skipped declaration loads none of its files" \
|
||||||
|
"only_dup" \
|
||||||
|
-k "$FIX/wrapper.k" -s '@only_dup@' -t fix
|
||||||
|
|
||||||
|
# --- Introspection -----------------------------------------------------------
|
||||||
|
|
||||||
|
# 8. -m lists the registered klammersets.
|
||||||
|
check_contains "8. -m shows the klammerset symbol" \
|
||||||
|
"kit" \
|
||||||
|
-k "$FIX/decl.k" -s 'x' -t fix -m
|
||||||
|
|
||||||
|
check_contains "9. -m shows the required klammerset too" \
|
||||||
|
"Utility klammers for engine tests" \
|
||||||
|
-k "$FIX/decl.k" -s 'x' -t fix -m
|
||||||
|
|
||||||
|
# --- Errors --------------------------------------------------------------------
|
||||||
|
|
||||||
|
# 10. A listed file that does not exist is a clean klammerset error.
|
||||||
|
check_fails "10. missing file in :files" \
|
||||||
|
"missing.k" \
|
||||||
|
-k "$FIX/bad_file.k" -s 'x' -t fix
|
||||||
|
|
||||||
|
# 11. A symbol must be an identifier (starts with a letter; letters, digits,
|
||||||
|
# underscores).
|
||||||
|
check_fails "11. invalid symbol rejected" \
|
||||||
|
"not valid" \
|
||||||
|
-k none -s '@@@klammerset 9bad | Bad symbol @@@' -d
|
||||||
|
|
||||||
|
# --- The search path (symbol -> <dir>/<symbol>/<symbol>.k) -------------------
|
||||||
|
|
||||||
|
# Runtime fixtures: a document directory holding a local klammerset, and a
|
||||||
|
# separate directory serving as a KLAMMERTEXT_KLAMMERSETS stage.
|
||||||
|
DOCDIR=$(mktemp -d /tmp/klammerset_doc.XXXXXX)
|
||||||
|
ENVDIR=$(mktemp -d /tmp/klammerset_env.XXXXXX)
|
||||||
|
trap 'rm -rf "$DOCDIR" "$ENVDIR" /tmp/klammerset_test_err.$$' EXIT
|
||||||
|
|
||||||
|
mkdir -p "$DOCDIR/locset" "$ENVDIR/envset" "$ENVDIR/locset"
|
||||||
|
printf '@@@klammerset locset | Document-local set @@@\n@@@target fixL | Fixture @@@\n@@local_k.fixL : LOCAL @@\n' \
|
||||||
|
> "$DOCDIR/locset/locset.k"
|
||||||
|
printf '@local_k@\n' > "$DOCDIR/doc.kt"
|
||||||
|
printf '@@@klammerset envset | Installed set @@@\n@@@target fixE | Fixture @@@\n@@env_k.fixE : ENV @@\n' \
|
||||||
|
> "$ENVDIR/envset/envset.k"
|
||||||
|
printf '@@@klammerset locset | Shadow candidate @@@\n@@@target fixL | Fixture @@@\n@@local_k.fixL : ENV-SHADOWED @@\n' \
|
||||||
|
> "$ENVDIR/locset/locset.k"
|
||||||
|
|
||||||
|
# 12. Stage 1 for a file input: the document's directory.
|
||||||
|
check_eq "12. symbol resolves in the document's directory" \
|
||||||
|
"LOCAL" \
|
||||||
|
"$DOCDIR/doc.kt" -k locset -t fixL -d
|
||||||
|
|
||||||
|
# 13. Stage 1 for string input: the cwd stands in for the document.
|
||||||
|
output=$( (cd "$DOCDIR" && "$KTEXT" -s '@local_k@' -k locset -t fixL) 2>/dev/null | trim )
|
||||||
|
if [ "$output" = "LOCAL" ]; then
|
||||||
|
echo "${green}PASS${reset} 13. cwd stands in for the document (string input)"
|
||||||
|
PASS=$((PASS + 1))
|
||||||
|
else
|
||||||
|
echo "${red}FAIL${reset} 13. cwd stands in for the document (string input)"
|
||||||
|
echo " expected: [LOCAL] got: [$output]"
|
||||||
|
FAIL=$((FAIL + 1))
|
||||||
|
fi
|
||||||
|
|
||||||
|
# 14. Stage 2: the KLAMMERTEXT_KLAMMERSETS directories.
|
||||||
|
output=$(KLAMMERTEXT_KLAMMERSETS=$ENVDIR "$KTEXT" -s '@env_k@' -k envset -t fixE 2>/dev/null | trim)
|
||||||
|
if [ "$output" = "ENV" ]; then
|
||||||
|
echo "${green}PASS${reset} 14. symbol resolves in KLAMMERTEXT_KLAMMERSETS"
|
||||||
|
PASS=$((PASS + 1))
|
||||||
|
else
|
||||||
|
echo "${red}FAIL${reset} 14. symbol resolves in KLAMMERTEXT_KLAMMERSETS"
|
||||||
|
echo " expected: [ENV] got: [$output]"
|
||||||
|
FAIL=$((FAIL + 1))
|
||||||
|
fi
|
||||||
|
|
||||||
|
# 15. Shadowing: the document-local set wins over the installed one.
|
||||||
|
output=$(KLAMMERTEXT_KLAMMERSETS=$ENVDIR "$KTEXT" "$DOCDIR/doc.kt" -k locset -t fixL -d 2>/dev/null | trim)
|
||||||
|
if [ "$output" = "LOCAL" ]; then
|
||||||
|
echo "${green}PASS${reset} 15. document-local set shadows the installed one"
|
||||||
|
PASS=$((PASS + 1))
|
||||||
|
else
|
||||||
|
echo "${red}FAIL${reset} 15. document-local set shadows the installed one"
|
||||||
|
echo " expected: [LOCAL] got: [$output]"
|
||||||
|
FAIL=$((FAIL + 1))
|
||||||
|
fi
|
||||||
|
|
||||||
|
# 16. :requires by symbol, resolved with the declaring directory as the
|
||||||
|
# local stage (the required set sits inside the declaring set's dir).
|
||||||
|
mkdir -p "$DOCDIR/kit2/locset"
|
||||||
|
cp "$DOCDIR/locset/locset.k" "$DOCDIR/kit2/locset/locset.k"
|
||||||
|
printf '@@@klammerset kit2 | Requires by symbol :requires locset @@@\n' > "$DOCDIR/kit2/kit2.k"
|
||||||
|
check_eq "16. :requires accepts a symbol (declaring-dir stage)" \
|
||||||
|
"LOCAL" \
|
||||||
|
-k "$DOCDIR/kit2/kit2.k" -s '@local_k@' -t fixL
|
||||||
|
|
||||||
|
# 17. Stage 3: $KLAMMERTEXT_HOME — the kdesc listing enumerates sks
|
||||||
|
# (sks/sks.k already satisfies the <symbol>/<symbol>.k convention).
|
||||||
|
output=$(kdesc --klammerset 2>/dev/null)
|
||||||
|
if printf '%s' "$output" | grep -q 'sks/sks\.k'; then
|
||||||
|
echo "${green}PASS${reset} 17. kdesc --klammerset lists sks from KLAMMERTEXT_HOME"
|
||||||
|
PASS=$((PASS + 1))
|
||||||
|
else
|
||||||
|
echo "${red}FAIL${reset} 17. kdesc --klammerset lists sks from KLAMMERTEXT_HOME"
|
||||||
|
echo " got: $(echo "$output" | head -3)"
|
||||||
|
FAIL=$((FAIL + 1))
|
||||||
|
fi
|
||||||
|
|
||||||
|
# 18. An unknown symbol is a clean error naming the search directories.
|
||||||
|
check_fails "18. unknown symbol names the search path" \
|
||||||
|
"was not found" \
|
||||||
|
-s 'x' -k nosuchset -d
|
||||||
|
|
||||||
|
echo
|
||||||
|
echo "======================="
|
||||||
|
echo "Results: ${green}$PASS passed${reset}, $([ $FAIL -gt 0 ] && echo "${red}$FAIL failed${reset}" || echo "0 failed")"
|
||||||
|
[ $FAIL -eq 0 ]
|
||||||
Reference in New Issue
Block a user