Files
neuron/dist/realizer.c
T
Will Anderson 2622bb04bd ELP: two-layer activation pipeline (activate → suppress → reason → generate)
elp-input.el: replace broken engram_search_json with engram_activate_json
as Layer 1. Layer 2 suppress/filter keeps nodes with non-zero salience/
importance. Reason step extracts patient from top activated node content.
ELP grammar realizes the response via generate().

routes.el: add 'elp' event_type to handle_dharma_recv so the studio can
route ELP requests through dharma.
2026-05-03 11:31:04 -05:00

425 lines
17 KiB
C

#include <stdint.h>
#include <stdlib.h>
#include "el_runtime.h"
el_val_t lang_profile(el_val_t code, el_val_t word_order, el_val_t morph_type, el_val_t has_case, el_val_t has_gender, el_val_t script_dir, el_val_t agreement, el_val_t null_subject);
el_val_t lang_get(el_val_t profile, el_val_t key);
el_val_t lang_profile_en(void);
el_val_t lang_profile_ja(void);
el_val_t lang_profile_ar(void);
el_val_t lang_profile_zh(void);
el_val_t lang_profile_de(void);
el_val_t lang_profile_es(void);
el_val_t lang_profile_fi(void);
el_val_t lang_profile_sw(void);
el_val_t lang_profile_hi(void);
el_val_t lang_profile_ru(void);
el_val_t lang_profile_fr(void);
el_val_t lang_profile_la(void);
el_val_t lang_profile_he(void);
el_val_t lang_profile_sa(void);
el_val_t lang_profile_got(void);
el_val_t lang_profile_non(void);
el_val_t lang_profile_enm(void);
el_val_t lang_profile_pi(void);
el_val_t lang_profile_grc(void);
el_val_t lang_profile_ang(void);
el_val_t lang_profile_fro(void);
el_val_t lang_profile_goh(void);
el_val_t lang_profile_sga(void);
el_val_t lang_profile_txb(void);
el_val_t lang_profile_peo(void);
el_val_t lang_profile_akk(void);
el_val_t lang_profile_uga(void);
el_val_t lang_profile_egy(void);
el_val_t lang_profile_sux(void);
el_val_t lang_profile_gez(void);
el_val_t lang_profile_cop(void);
el_val_t lang_from_code(el_val_t code);
el_val_t lang_default(void);
el_val_t lang_is_isolating(el_val_t profile);
el_val_t lang_is_agglutinative(el_val_t profile);
el_val_t lang_is_fusional(el_val_t profile);
el_val_t lang_is_polysynthetic(el_val_t profile);
el_val_t lang_is_rtl(el_val_t profile);
el_val_t lang_has_null_subject(el_val_t profile);
el_val_t lang_has_case(el_val_t profile);
el_val_t lang_has_gender(el_val_t profile);
el_val_t lang_word_order(el_val_t profile);
el_val_t lang_code(el_val_t profile);
el_val_t str_ends(el_val_t s, el_val_t suf);
el_val_t str_last_char(el_val_t s);
el_val_t str_last2(el_val_t s);
el_val_t str_last3(el_val_t s);
el_val_t str_drop_last(el_val_t s, el_val_t n);
el_val_t is_vowel(el_val_t c);
el_val_t morph_apply_suffix(el_val_t base, el_val_t suffix);
el_val_t en_irregular_plural(el_val_t word);
el_val_t en_irregular_singular(el_val_t word);
el_val_t en_irregular_verb(el_val_t base);
el_val_t en_verb_3sg(el_val_t base);
el_val_t en_should_double_final(el_val_t base);
el_val_t en_verb_past(el_val_t base);
el_val_t en_verb_gerund(el_val_t base);
el_val_t en_pluralize_regular(el_val_t singular);
el_val_t en_verb_form(el_val_t base, el_val_t tense, el_val_t person, el_val_t number);
el_val_t agree_determiner(el_val_t det, el_val_t noun);
el_val_t morph_pluralize(el_val_t noun, el_val_t profile);
el_val_t morph_map_canonical(el_val_t verb, el_val_t code);
el_val_t morph_conjugate(el_val_t verb, el_val_t tense, el_val_t person, el_val_t number, el_val_t profile);
el_val_t morph_inflect(el_val_t word, el_val_t features, el_val_t profile);
el_val_t pluralize(el_val_t singular);
el_val_t singularize(el_val_t plural);
el_val_t verb_form(el_val_t base, el_val_t tense, el_val_t person, el_val_t number);
el_val_t irregular_plural(el_val_t word);
el_val_t irregular_singular(el_val_t word);
el_val_t slots_get(el_val_t slots, el_val_t key);
el_val_t slots_set(el_val_t slots, el_val_t key, el_val_t val);
el_val_t make_slots(el_val_t k0, el_val_t v0);
el_val_t make_slots2(el_val_t k0, el_val_t v0, el_val_t k1, el_val_t v1);
el_val_t make_slots3(el_val_t k0, el_val_t v0, el_val_t k1, el_val_t v1, el_val_t k2, el_val_t v2);
el_val_t make_slots4(el_val_t k0, el_val_t v0, el_val_t k1, el_val_t v1, el_val_t k2, el_val_t v2, el_val_t k3, el_val_t v3);
el_val_t make_slots5(el_val_t k0, el_val_t v0, el_val_t k1, el_val_t v1, el_val_t k2, el_val_t v2, el_val_t k3, el_val_t v3, el_val_t k4, el_val_t v4);
el_val_t rule_id(el_val_t rule);
el_val_t rule_lhs(el_val_t rule);
el_val_t rule_rhs_len(el_val_t rule);
el_val_t rule_rhs(el_val_t rule, el_val_t idx);
el_val_t make_rule(el_val_t id, el_val_t lhs, el_val_t r0);
el_val_t make_rule2(el_val_t id, el_val_t lhs, el_val_t r0, el_val_t r1);
el_val_t make_rule3(el_val_t id, el_val_t lhs, el_val_t r0, el_val_t r1, el_val_t r2);
el_val_t make_rule4(el_val_t id, el_val_t lhs, el_val_t r0, el_val_t r1, el_val_t r2, el_val_t r3);
el_val_t build_rules(void);
el_val_t get_rules(void);
el_val_t find_rule(el_val_t rule_id_str);
el_val_t make_leaf(el_val_t label, el_val_t word);
el_val_t make_node1(el_val_t label, el_val_t child0);
el_val_t make_node2(el_val_t label, el_val_t child0, el_val_t child1);
el_val_t make_node3(el_val_t label, el_val_t child0, el_val_t child1, el_val_t child2);
el_val_t make_node4(el_val_t label, el_val_t child0, el_val_t child1, el_val_t child2, el_val_t child3);
el_val_t nlg_is_ws(el_val_t c);
el_val_t skip_ws(el_val_t s, el_val_t pos);
el_val_t scan_token(el_val_t s, el_val_t start);
el_val_t render_tree(el_val_t tree);
el_val_t gram_word_order(el_val_t profile);
el_val_t gram_order_constituents(el_val_t subj, el_val_t verb, el_val_t obj, el_val_t profile);
el_val_t gram_build_vp(el_val_t verb, el_val_t aux, el_val_t profile);
el_val_t gram_question_strategy(el_val_t profile);
el_val_t is_pronoun(el_val_t word);
el_val_t build_np(el_val_t referent, el_val_t slots);
el_val_t build_pp(el_val_t loc);
el_val_t build_vp_body(el_val_t slots);
el_val_t build_vp_from_slots(el_val_t slots);
el_val_t generate_tree(el_val_t rule_id_str, el_val_t slots);
el_val_t agent_person(el_val_t agent);
el_val_t agent_number(el_val_t agent);
el_val_t realize_np(el_val_t referent, el_val_t number);
el_val_t realize_vp_lang(el_val_t base_verb, el_val_t tense, el_val_t aspect, el_val_t person, el_val_t number, el_val_t profile);
el_val_t realize_question_lang(el_val_t predicate, el_val_t tense, el_val_t aspect, el_val_t person, el_val_t number, el_val_t agent, el_val_t patient, el_val_t location, el_val_t profile);
el_val_t capitalize_first(el_val_t s);
el_val_t add_punct(el_val_t s, el_val_t intent);
el_val_t realize_lang(el_val_t form, el_val_t profile);
el_val_t realize(el_val_t form);
el_val_t agent_person(el_val_t agent) {
if (str_eq(agent, EL_STR("I"))) {
return EL_STR("first");
}
if (str_eq(agent, EL_STR("me"))) {
return EL_STR("first");
}
if (str_eq(agent, EL_STR("we"))) {
return EL_STR("first");
}
if (str_eq(agent, EL_STR("us"))) {
return EL_STR("first");
}
if (str_eq(agent, EL_STR("you"))) {
return EL_STR("second");
}
return EL_STR("third");
return 0;
}
el_val_t agent_number(el_val_t agent) {
if (str_eq(agent, EL_STR("I"))) {
return EL_STR("singular");
}
if (str_eq(agent, EL_STR("me"))) {
return EL_STR("singular");
}
if (str_eq(agent, EL_STR("he"))) {
return EL_STR("singular");
}
if (str_eq(agent, EL_STR("him"))) {
return EL_STR("singular");
}
if (str_eq(agent, EL_STR("she"))) {
return EL_STR("singular");
}
if (str_eq(agent, EL_STR("her"))) {
return EL_STR("singular");
}
if (str_eq(agent, EL_STR("it"))) {
return EL_STR("singular");
}
if (str_eq(agent, EL_STR("you"))) {
return EL_STR("singular");
}
if (str_eq(agent, EL_STR("we"))) {
return EL_STR("plural");
}
if (str_eq(agent, EL_STR("us"))) {
return EL_STR("plural");
}
if (str_eq(agent, EL_STR("they"))) {
return EL_STR("plural");
}
if (str_eq(agent, EL_STR("them"))) {
return EL_STR("plural");
}
return EL_STR("singular");
return 0;
}
el_val_t realize_np(el_val_t referent, el_val_t number) {
return referent;
return 0;
}
el_val_t realize_vp_lang(el_val_t base_verb, el_val_t tense, el_val_t aspect, el_val_t person, el_val_t number, el_val_t profile) {
el_val_t empty_aux = EL_STR("");
if (str_eq(tense, EL_STR("future"))) {
el_val_t code = lang_get(profile, EL_STR("code"));
if (str_eq(code, EL_STR("en"))) {
el_val_t result = native_list_empty();
result = native_list_append(result, base_verb);
result = native_list_append(result, EL_STR("will"));
return result;
}
el_val_t surf = morph_conjugate(base_verb, tense, person, number, profile);
el_val_t result = native_list_empty();
result = native_list_append(result, surf);
result = native_list_append(result, empty_aux);
return result;
}
if (str_eq(aspect, EL_STR("progressive"))) {
el_val_t gerund = morph_conjugate(base_verb, EL_STR("progressive"), person, number, profile);
el_val_t be_aux = morph_conjugate(EL_STR("be"), tense, person, number, profile);
el_val_t result = native_list_empty();
result = native_list_append(result, gerund);
result = native_list_append(result, be_aux);
return result;
}
if (str_eq(aspect, EL_STR("perfect"))) {
el_val_t pp = morph_conjugate(base_verb, EL_STR("perfect"), person, number, profile);
el_val_t have_form = morph_conjugate(EL_STR("have"), tense, person, number, profile);
el_val_t result = native_list_empty();
result = native_list_append(result, pp);
result = native_list_append(result, have_form);
return result;
}
el_val_t surf = morph_conjugate(base_verb, tense, person, number, profile);
el_val_t result = native_list_empty();
result = native_list_append(result, surf);
result = native_list_append(result, empty_aux);
return result;
return 0;
}
el_val_t realize_question_lang(el_val_t predicate, el_val_t tense, el_val_t aspect, el_val_t person, el_val_t number, el_val_t agent, el_val_t patient, el_val_t location, el_val_t profile) {
el_val_t strategy = gram_question_strategy(profile);
el_val_t code = lang_get(profile, EL_STR("code"));
if (str_eq(strategy, EL_STR("do-support"))) {
if (str_eq(aspect, EL_STR("progressive"))) {
el_val_t vp_pair = realize_vp_lang(predicate, tense, EL_STR("progressive"), person, number, profile);
el_val_t gerund = native_list_get(vp_pair, 0);
el_val_t be_aux = native_list_get(vp_pair, 1);
el_val_t parts = native_list_empty();
parts = native_list_append(parts, be_aux);
parts = native_list_append(parts, agent);
parts = native_list_append(parts, gerund);
if (!str_eq(patient, EL_STR(""))) {
parts = native_list_append(parts, patient);
}
if (!str_eq(location, EL_STR(""))) {
parts = native_list_append(parts, location);
}
return str_join(parts, EL_STR(" "));
}
if (str_eq(aspect, EL_STR("perfect"))) {
el_val_t vp_pair = realize_vp_lang(predicate, tense, EL_STR("perfect"), person, number, profile);
el_val_t pp = native_list_get(vp_pair, 0);
el_val_t have_aux = native_list_get(vp_pair, 1);
el_val_t parts = native_list_empty();
parts = native_list_append(parts, have_aux);
parts = native_list_append(parts, agent);
parts = native_list_append(parts, pp);
if (!str_eq(patient, EL_STR(""))) {
parts = native_list_append(parts, patient);
}
if (!str_eq(location, EL_STR(""))) {
parts = native_list_append(parts, location);
}
return str_join(parts, EL_STR(" "));
}
if (str_eq(predicate, EL_STR("be"))) {
el_val_t be_form = morph_conjugate(EL_STR("be"), tense, person, number, profile);
el_val_t parts = native_list_empty();
parts = native_list_append(parts, be_form);
parts = native_list_append(parts, agent);
if (!str_eq(patient, EL_STR(""))) {
parts = native_list_append(parts, patient);
}
if (!str_eq(location, EL_STR(""))) {
parts = native_list_append(parts, location);
}
return str_join(parts, EL_STR(" "));
}
el_val_t do_form = morph_conjugate(EL_STR("do"), tense, person, number, profile);
el_val_t parts = native_list_empty();
parts = native_list_append(parts, do_form);
parts = native_list_append(parts, agent);
parts = native_list_append(parts, predicate);
if (!str_eq(patient, EL_STR(""))) {
parts = native_list_append(parts, patient);
}
if (!str_eq(location, EL_STR(""))) {
parts = native_list_append(parts, location);
}
return str_join(parts, EL_STR(" "));
}
if (str_eq(strategy, EL_STR("particle"))) {
el_val_t vp_pair = realize_vp_lang(predicate, tense, aspect, person, number, profile);
el_val_t verb_s = native_list_get(vp_pair, 0);
el_val_t aux_s = native_list_get(vp_pair, 1);
el_val_t vp_str = gram_build_vp(verb_s, aux_s, profile);
el_val_t core = gram_order_constituents(agent, vp_str, patient, profile);
el_val_t loc_part = EL_STR("");
if (!str_eq(location, EL_STR(""))) {
loc_part = el_str_concat(el_str_concat(core, EL_STR(" ")), location);
} else {
loc_part = core;
}
if (str_eq(code, EL_STR("ja"))) {
return el_str_concat(loc_part, EL_STR(" \xe3\x81\x8b"));
}
if (str_eq(code, EL_STR("hi"))) {
return el_str_concat(loc_part, EL_STR(" \xe0\xa4\x95\xe0\xa5\x8d\xe0\xa4\xaf\xe0\xa4\xbe"));
}
if (str_eq(code, EL_STR("fi"))) {
return el_str_concat(loc_part, EL_STR("-ko"));
}
return el_str_concat(loc_part, EL_STR("?"));
}
if (str_eq(strategy, EL_STR("inversion"))) {
el_val_t vp_pair = realize_vp_lang(predicate, tense, aspect, person, number, profile);
el_val_t verb_s = native_list_get(vp_pair, 0);
el_val_t aux_s = native_list_get(vp_pair, 1);
el_val_t parts = native_list_empty();
if (!str_eq(aux_s, EL_STR(""))) {
parts = native_list_append(parts, aux_s);
} else {
parts = native_list_append(parts, verb_s);
}
parts = native_list_append(parts, agent);
if (!str_eq(aux_s, EL_STR(""))) {
parts = native_list_append(parts, verb_s);
}
if (!str_eq(patient, EL_STR(""))) {
parts = native_list_append(parts, patient);
}
if (!str_eq(location, EL_STR(""))) {
parts = native_list_append(parts, location);
}
return str_join(parts, EL_STR(" "));
}
el_val_t vp_pair = realize_vp_lang(predicate, tense, aspect, person, number, profile);
el_val_t verb_s = native_list_get(vp_pair, 0);
el_val_t aux_s = native_list_get(vp_pair, 1);
el_val_t vp_str = gram_build_vp(verb_s, aux_s, profile);
el_val_t core = gram_order_constituents(agent, vp_str, patient, profile);
if (!str_eq(location, EL_STR(""))) {
return el_str_concat(el_str_concat(core, EL_STR(" ")), location);
}
return core;
return 0;
}
el_val_t capitalize_first(el_val_t s) {
el_val_t n = str_len(s);
if (n == 0) {
return s;
}
el_val_t first = str_slice(s, 0, 1);
el_val_t rest = str_slice(s, 1, n);
return el_str_concat(str_to_upper(first), rest);
return 0;
}
el_val_t add_punct(el_val_t s, el_val_t intent) {
if (str_eq(intent, EL_STR("question"))) {
return el_str_concat(s, EL_STR("?"));
}
return el_str_concat(s, EL_STR("."));
return 0;
}
el_val_t realize_lang(el_val_t form, el_val_t profile) {
el_val_t intent = slots_get(form, EL_STR("intent"));
el_val_t agent = slots_get(form, EL_STR("agent"));
el_val_t predicate = slots_get(form, EL_STR("predicate"));
el_val_t patient = slots_get(form, EL_STR("patient"));
el_val_t location = slots_get(form, EL_STR("location"));
el_val_t tense_raw = slots_get(form, EL_STR("tense"));
el_val_t aspect_raw = slots_get(form, EL_STR("aspect"));
el_val_t tense = tense_raw;
if (str_eq(tense, EL_STR(""))) {
tense = EL_STR("present");
}
el_val_t aspect = aspect_raw;
if (str_eq(aspect, EL_STR(""))) {
aspect = EL_STR("simple");
}
el_val_t person = agent_person(agent);
el_val_t number = agent_number(agent);
if (str_eq(intent, EL_STR("command"))) {
el_val_t parts = native_list_empty();
parts = native_list_append(parts, predicate);
if (!str_eq(patient, EL_STR(""))) {
parts = native_list_append(parts, patient);
}
if (!str_eq(location, EL_STR(""))) {
parts = native_list_append(parts, location);
}
el_val_t sentence = str_join(parts, EL_STR(" "));
return add_punct(capitalize_first(sentence), EL_STR("command"));
}
if (str_eq(intent, EL_STR("question"))) {
el_val_t surface = realize_question_lang(predicate, tense, aspect, person, number, agent, patient, location, profile);
return add_punct(capitalize_first(surface), EL_STR("question"));
}
el_val_t vp_pair = realize_vp_lang(predicate, tense, aspect, person, number, profile);
el_val_t verb_surf = native_list_get(vp_pair, 0);
el_val_t aux_surf = native_list_get(vp_pair, 1);
el_val_t vp_str = gram_build_vp(verb_surf, aux_surf, profile);
el_val_t core = gram_order_constituents(agent, vp_str, patient, profile);
el_val_t parts = native_list_empty();
parts = native_list_append(parts, core);
if (!str_eq(location, EL_STR(""))) {
parts = native_list_append(parts, location);
}
el_val_t sentence = str_join(parts, EL_STR(" "));
return add_punct(capitalize_first(sentence), EL_STR("assert"));
return 0;
}
el_val_t realize(el_val_t form) {
el_val_t lang_code = slots_get(form, EL_STR("lang"));
if (str_eq(lang_code, EL_STR(""))) {
return realize_lang(form, lang_default());
}
return realize_lang(form, lang_from_code(lang_code));
return 0;
}