From 1b8c47a8b14f784f6605eee3a73713dbce6ca572 Mon Sep 17 00:00:00 2001 From: olpc user Date: Mon, 9 Dec 2019 20:38:22 -0800 Subject: changed level-0 allocation to use groups --- starts/meaning-vm/level-0/baseref.hpp | 4 +- starts/meaning-vm/level-0/concept.cpp | 1 + starts/meaning-vm/level-0/memorystore.cpp | 94 +++++++++++++++++++++++-------- starts/meaning-vm/level-0/memorystore.hpp | 37 +++++++++++- starts/meaning-vm/level-0/ref.cpp | 4 ++ starts/meaning-vm/level-1/baseref.hpp | 2 +- starts/meaning-vm/level-1/funcs.cpp | 23 ++++---- starts/meaning-vm/level-1/funcs.hpp | 2 +- starts/meaning-vm/level-1/memorystore.cpp | 33 ----------- starts/meaning-vm/level-1/memorystore.hpp | 14 ----- starts/meaning-vm/level-1/sugar.cpp | 9 ++- starts/meaning-vm/level0.cpp | 36 +++++------- starts/meaning-vm/level1.cpp | 6 ++ 13 files changed, 154 insertions(+), 111 deletions(-) delete mode 100644 starts/meaning-vm/level-1/memorystore.cpp delete mode 100644 starts/meaning-vm/level-1/memorystore.hpp diff --git a/starts/meaning-vm/level-0/baseref.hpp b/starts/meaning-vm/level-0/baseref.hpp index fbb7a28..69880c8 100644 --- a/starts/meaning-vm/level-0/baseref.hpp +++ b/starts/meaning-vm/level-0/baseref.hpp @@ -57,7 +57,7 @@ public: template T& vget(ref const & type) const { return p->vget(type.p); } template - void vset(ref const & type, T const & v) { p->set(type.p, level0::alloc(v)); } + void vset(ref const & type, T const & v) { p->set(type.p, level0::alloc(self, v)); } template T& val() { return p->val(); } @@ -100,7 +100,7 @@ private: bool operator!=(mutit const & other) const { return self.it != other.it; } val & operator*() { return *(val*)&self.it.operator*(); } - val & operator->() { return *(val*)&self.it.operator->(); } + val * operator->() { return (val*)self.it.operator->(); } private: It it; diff --git a/starts/meaning-vm/level-0/concept.cpp b/starts/meaning-vm/level-0/concept.cpp index 9bb772d..0661edd 100644 --- a/starts/meaning-vm/level-0/concept.cpp +++ b/starts/meaning-vm/level-0/concept.cpp @@ -12,6 +12,7 @@ concept* concept::id() void concept::link(concept* type, concept* target) { + if (type == 0 || target == 0) { throw null_reference(); } links.insert({type, target}); } diff --git a/starts/meaning-vm/level-0/memorystore.cpp b/starts/meaning-vm/level-0/memorystore.cpp index adae8b2..61f8ec0 100644 --- a/starts/meaning-vm/level-0/memorystore.cpp +++ b/starts/meaning-vm/level-0/memorystore.cpp @@ -8,21 +8,66 @@ namespace intellect { namespace level0 { -static auto & concepts() +static auto & index() { - static std::unordered_set> concepts; - return concepts; + static std::unordered_set> index; + return index; } -ref alloc(std::any data) { + +namespace concepts { + ref allocator() { static ref ret = new concept(); return ret; }; + ref allocates() { static ref ret = new concept(); return ret; }; + ref allocations() { static ref ret = new concept(); return ret; }; + ref level0allocations() { static ref ret = new concept(); return ret; }; +} + +struct init { init() +{ + concepts::allocator().link(concepts::allocator(), concepts::level0allocations()); + concepts::level0allocations().link(concepts::allocates(), concepts::allocator()); + index().insert(concepts::allocator()); + + concepts::allocates().link(concepts::allocator(), concepts::level0allocations()); + concepts::level0allocations().link(concepts::allocates(), concepts::allocates()); + index().insert(concepts::allocates()); + + concepts::allocations().link(concepts::allocator(), concepts::level0allocations()); + concepts::level0allocations().link(concepts::allocates(), concepts::allocations()); + index().insert(concepts::allocations()); + + concepts::level0allocations().link(concepts::allocator(), concepts::level0allocations()); + concepts::level0allocations().link(concepts::allocates(), concepts::level0allocations()); + index().insert(concepts::level0allocations()); +} } _init; + +ref alloc(ref source, std::any data) +{ concept * r = new concept(); r->data = data; - concepts().insert(r); + alloc((ref)r, source); + index().insert(r); return r; } -static concept* referenced(ref r) { - for (ref r2 : concepts()) { +void alloc(ref r, ref source) +{ + r.link(concepts::allocator(), source); + source.link(concepts::allocates(), r); +} + +void realloc(ref r, ref newsource) +{ + ref oldsource = r.get(concepts::allocator()); + alloc(r, newsource); + dealloc(r, oldsource); +} + +static concept* referenced(ref r, ref source) { + for (ref r2 : index()) { + if (r2 == source) { + continue; + } if (r2 == r) { continue; } @@ -38,28 +83,33 @@ static concept* referenced(ref r) { return 0; } -void dealloc(ref r) { - concept * referenced = intellect::level0::referenced(r); - if (referenced) { - throw still_referenced_by(r, referenced); +void dealloc(ref r, ref source) { + auto it = index().find(r); + if (it == index().end()) { throw no_such_concept(r); } + + source.unlink(concepts::allocates(), r); + r.unlink(concepts::allocator(), source); + if (r.linked(concepts::allocator())) { return; } + + index().erase(it); + + auto ours = r.getAll(concepts::allocates()); + for (auto allocation : ours) { + dealloc(allocation, r); } - for ( - auto it = concepts().begin(); - it != concepts().end(); - ++ it) - { - if (*it == r) { - concepts().erase(it); - delete (concept*)r; - return; + + for (auto ghost : ours) { + concept * referenced = intellect::level0::referenced(ghost, source); + if (referenced) { + throw still_referenced_by(ghost, referenced); } } - throw no_such_concept(r); + delete (concept*)r; } std::size_t allocated() { - return concepts().size(); + return index().size(); } } diff --git a/starts/meaning-vm/level-0/memorystore.hpp b/starts/meaning-vm/level-0/memorystore.hpp index 7843513..eff4235 100644 --- a/starts/meaning-vm/level-0/memorystore.hpp +++ b/starts/meaning-vm/level-0/memorystore.hpp @@ -7,8 +7,41 @@ namespace intellect { namespace level0 { -ref alloc(std::any data = {}); -void dealloc(ref); +// self-reference loops are real. +// +// one person can feel urgent about issue A, and act on this urgency to engage +// another person around B, who acts in a different way to someone else, eventually +// cycling back to stress that stimulates the original person to feel more urgent +// about issue A. +// human behavior can make arbitrary positive or negative feedback loops. +// +// here in memory allocation, i've designed a system intended to reduce such loops +// by encouraging my usage to be a certain way, but it still readily provides for +// them. +// +// in process expansion / simple thought, we also have the issue of recursion. +// if we trust a task to complete, and it ends up triggering itself in a subcontext, +// we could wait forever. +// +// the solution to many of these things is to recognize repetition in systems. +// we also become skeptical as things continue constantly. we expect to develop +// some level of understanding that they will shrink, or we stop them and try +// something else. + +namespace concepts { + +extern ref allocator(); // link shows what is holding something alive +extern ref allocates(); // link shows what is being held alive + +extern ref allocations(); // to use as a basic allocator for simple things +extern ref level0allocations(); // allocator for concepts internal to level0 + +} + +ref alloc(ref allocator, std::any data = {}); // new concept +void alloc(ref allocated, ref allocator); // extra ownership for concept +void realloc(ref allocated, ref allocator); // move ownership for concept to allocator +void dealloc(ref allocated, ref allocator); // remove ownership for concept std::size_t allocated(); } diff --git a/starts/meaning-vm/level-0/ref.cpp b/starts/meaning-vm/level-0/ref.cpp index d4758bd..87e911a 100644 --- a/starts/meaning-vm/level-0/ref.cpp +++ b/starts/meaning-vm/level-0/ref.cpp @@ -1,10 +1,12 @@ #include "ref.hpp" #include "concept.hpp" #include "errors.hpp" +#include "memorystore.hpp" #include using namespace intellect::level0; +using namespace concepts; std::string ref::dump(ref skipmarkertype, ref skipmarkertarget) { @@ -13,10 +15,12 @@ std::string ref::dump(ref skipmarkertype, ref skipmarkertarget) } std::string ret = std::to_string((unsigned long)ptr()) + ":\n"; for (auto & link : self.links()) { + if (link.first.linked(allocator(), level0allocations())) { continue; } ret += " " + std::to_string((unsigned long)link.first.ptr()) + ": " + std::to_string((unsigned long)link.second.ptr()) + "\n"; } self.link(skipmarkertype, skipmarkertarget); for (auto & link : self.links()) { + if (link.first.linked(allocator(), level0allocations())) { continue; } if (link.first == skipmarkertype && link.second == skipmarkertarget) { continue; } diff --git a/starts/meaning-vm/level-1/baseref.hpp b/starts/meaning-vm/level-1/baseref.hpp index e97db2d..5055d44 100644 --- a/starts/meaning-vm/level-1/baseref.hpp +++ b/starts/meaning-vm/level-1/baseref.hpp @@ -31,7 +31,7 @@ struct baseref : public level0::baseref ref operator[](ref subref) const { return self.get(subref); } template - void vset(ref const & type, T const & v) { self.set(type, level1::alloc(v)); } + void vset(ref const & type, T const & v) { self.set(type, level1::alloc(level0::concepts::allocations(), v)); } template std::function & fun() { return self.template val>(); } diff --git a/starts/meaning-vm/level-1/funcs.cpp b/starts/meaning-vm/level-1/funcs.cpp index c1cf21a..cfb44b7 100644 --- a/starts/meaning-vm/level-1/funcs.cpp +++ b/starts/meaning-vm/level-1/funcs.cpp @@ -19,9 +19,9 @@ static auto & namestruct() std::unordered_map,std::equal_to> conceptsByName; ref nameref; name_t() - : nameref(level0::alloc()) + : nameref(level0::alloc(level0::concepts::allocations())) { - level0::ref namestr = alloc((std::string)("name")); + level0::ref namestr = level0::alloc(nameref.ptr(), (std::string)("name")); nameref.set(nameref, namestr); conceptsByName.emplace(namestr.val(), nameref); } @@ -32,9 +32,9 @@ static auto & namestruct() void givename(concept* con, std::string const & name) { auto & ns = namestruct(); - level0::ref namestr = level0::alloc(name); + level0::ref namestr = level0::alloc(con, name); ns.conceptsByName.emplace(namestr.val(), con); - con.set(ns.nameref, namestr); + con->set(ns.nameref, namestr); } concept* getnamed(std::string const & name) @@ -44,10 +44,8 @@ concept* getnamed(std::string const & name) if (res != ns.conceptsByName.end()) { return res->second; } else { - level1::ref con = level0::alloc(); - level0::ref namestr = level0::alloc(name); - ns.conceptsByName.emplace(namestr.val(), con); - con.set(ns.nameref, namestr); + level1::ref con = level0::alloc(level0::concepts::allocations()); + givename(con, name); return con.ptr(); } } @@ -71,10 +69,9 @@ bool isa(concept* member, concept* group) return false; } -concept* alloc(std::any val) +concept* alloc(concept* allocator, std::any val) { - - ref ret = level0::alloc(val); + ref ret = level0::alloc(allocator, val); std::stringstream ss; ss << val.type().name() << "("; if (false); @@ -88,7 +85,7 @@ concept* alloc(std::any val) #undef t else { ss << "?"; } ss << ")"; - ret.link(concepts::name, level0::alloc(ss.str())); + ret.link(concepts::name, level0::alloc(ret, ss.str())); return ret; } @@ -104,6 +101,7 @@ std::string dump(concept* what, concept* skipmarkertype, concept* skipmarkertarg } std::string ret; for (auto & link : ref(what).links()) { + if (link.first.linked(level0::concepts::allocator(), level0::concepts::level0allocations())) { continue; } if (link.first == concepts::name) { continue; } if (ret.size() == 0) { ret = ref(what).name() + ":\n"; @@ -112,6 +110,7 @@ std::string dump(concept* what, concept* skipmarkertype, concept* skipmarkertarg } what->link(skipmarkertype, skipmarkertarget); for (auto & link : ref(what).links()) { + if (link.first.linked(level0::concepts::allocator(), level0::concepts::level0allocations())) { continue; } if (link.first.ptr() == skipmarkertype && link.second.ptr() == skipmarkertarget) { continue; } diff --git a/starts/meaning-vm/level-1/funcs.hpp b/starts/meaning-vm/level-1/funcs.hpp index 4b53ddd..9361917 100644 --- a/starts/meaning-vm/level-1/funcs.hpp +++ b/starts/meaning-vm/level-1/funcs.hpp @@ -18,7 +18,7 @@ bool isa(concept* member, concept* group); concept* hyphenate(concept* a, concept* b); -concept* alloc(std::any val); +concept* alloc(concept* allocator, std::any val); std::string dump(concept * what, concept * skipmarkertype, concept * skipmarkertarget); diff --git a/starts/meaning-vm/level-1/memorystore.cpp b/starts/meaning-vm/level-1/memorystore.cpp deleted file mode 100644 index 0bd109b..0000000 --- a/starts/meaning-vm/level-1/memorystore.cpp +++ /dev/null @@ -1,33 +0,0 @@ -#include "memorystore.hpp" - -#include "concepts.hpp" - -#include "../level-0/memorystore.hpp" - -namespace intellect { -namespace level1 { - -ref allocation_group("allocation-group"); -ref allocation_part("allocation-part"); - -ref alloc(ref grp, std::any data) -{ - ref res = level0::alloc(data); - keep(res, grp); -} - -void keep(ref allocated, ref grp) -{ - allocated.link(allocation_group, grp); - grp.link(allocation_part, allocated); -} - -void dealloc(ref grp, ref metagroup) -{ - -//} - -std::size_t allocatedgroups(); - -} -} diff --git a/starts/meaning-vm/level-1/memorystore.hpp b/starts/meaning-vm/level-1/memorystore.hpp deleted file mode 100644 index 625dad9..0000000 --- a/starts/meaning-vm/level-1/memorystore.hpp +++ /dev/null @@ -1,14 +0,0 @@ -#pragma once - -#include "common.hpp" - -namespace intellect { -namespace level1 { - -ref alloc(ref group, std::any data = {}); -void keep(ref allocated, ref group); -void dealloc(ref group, ref metagroup = concepts::nothing); -std::size_t allocatedgroups(); - -} -} diff --git a/starts/meaning-vm/level-1/sugar.cpp b/starts/meaning-vm/level-1/sugar.cpp index 24d59be..21f4001 100644 --- a/starts/meaning-vm/level-1/sugar.cpp +++ b/starts/meaning-vm/level-1/sugar.cpp @@ -49,15 +49,17 @@ ref movetoname(ref anonymous, ref name) // information is not available at this level. bool nonempty = false; for (auto & l : name.links()) { + if (l.first.linked(level0::concepts::allocator(), level0::concepts::level0allocations())) { continue; } if (l.first == concepts::name) { continue; } nonempty = true; } if (nonempty) { for (auto & link : anonymous.links()) { if (link.first == concepts::is && link.second == concepts::anonymous) { continue; } + if (link.first.linked(level0::concepts::allocator(), level0::concepts::level0allocations())) { continue; } if (link.first == concepts::name) { continue; } if (!name.linked(link.first, link.second)) { - throw std::logic_error(name.name() + " already defined otherwise from " + anonymous.get(concepts::is).name()); + throw std::logic_error(name.name() + " already defined otherwise from " + anonymous.getAll(concepts::is).begin()->name()); } } } @@ -66,12 +68,13 @@ ref movetoname(ref anonymous, ref name) anonymous.unlink(concepts::name, nam); if (!nonempty) { for (auto & l : anonymous.links()) { + if (l.first.linked(level0::concepts::allocator(), level0::concepts::level0allocations())) { continue; } name.link(l.first, l.second); } } anonymous.link(concepts::name, nam); - dealloc(anonymous); - dealloc(nam); + dealloc(anonymous, level0::concepts::allocations()); + //dealloc(nam, level0::concepts::allocations()); return name; } diff --git a/starts/meaning-vm/level0.cpp b/starts/meaning-vm/level0.cpp index 6ff0102..86ce0cd 100644 --- a/starts/meaning-vm/level0.cpp +++ b/starts/meaning-vm/level0.cpp @@ -5,17 +5,21 @@ using namespace intellect::level0; +#define out(name) std::cout << " " #name ":" << (long)name.ptr() + int main() { - ref a = alloc(); - ref b = alloc(); - ref c = alloc(); - ref d = alloc(); - ref e = alloc(); - auto numlink = alloc(); - auto codelink = alloc(); - - ref skip = alloc(); + ref store = alloc(concepts::allocations()); out(store); + ref a = alloc(store); out(a); + ref b = alloc(store); out(b); + ref c = alloc(store); out(c); + ref d = alloc(store); out(d); + ref e = alloc(store); out(e); + auto numlink = alloc(a); out(numlink); + auto codelink = alloc(a); out(codelink); + + ref skip = alloc(store); out(skip); + std::cout << std::endl; a.link( b, c, @@ -37,18 +41,8 @@ int main() std::cout << allocated() << " allocated" << std::endl; e.unlink(b, a); - auto num = a.get(numlink); - auto code = a.get(codelink); - dealloc(a); - dealloc(num); - dealloc(code); - dealloc(numlink); - dealloc(codelink); - dealloc(c); - dealloc(e); - dealloc(b); - dealloc(d); - dealloc(skip); + //dealloc(a, store); + dealloc(store, concepts::allocations()); std::cout << allocated() << " allocated" << std::endl; diff --git a/starts/meaning-vm/level1.cpp b/starts/meaning-vm/level1.cpp index 9498ddf..b1d06f1 100644 --- a/starts/meaning-vm/level1.cpp +++ b/starts/meaning-vm/level1.cpp @@ -7,6 +7,8 @@ using namespace intellect::level1::concepts; int main() { + std::cout << intellect::level0::allocated() << " allocated" << std::endl; + decls(make, linked, habit); decls(needs, assumes, makes); decls(not, topic); @@ -61,5 +63,9 @@ int main() std::cout << apple.dump("dumped", true) << std::endl; + std::cout << intellect::level0::allocated() << " allocated" << std::endl; + intellect::level0::dealloc(intellect::level0::concepts::allocations(), intellect::level0::concepts::level0allocations()); + std::cout << intellect::level0::allocated() << " allocated" << std::endl; + return 0; } -- cgit v1.2.3