Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Make reactor names available at runtime #2450

Merged
merged 7 commits into from
Dec 30, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -1087,6 +1087,60 @@ private static String deferredAllocationForEffectsOnInputs(ReactorInstance react
return code.toString();
}

/**
* Set the parent pointer and reactor name. If the reactor is in a bank, the name will be the
* instance name with [index] appended.
*
* @param reactor The reactor instance.
*/
private static String deferredSetParentAndName(ReactorInstance reactor) {
var code = new CodeBuilder();
if (reactor.isBank()) {
// First, generate code to determine the size of the memory needed for the name.
code.pr("char* format = \"%s[%d]\";");
code.pr(
"int length = snprintf(NULL, 0, format, \""
+ reactor.getName()
+ "\", "
+ CUtil.bankIndexName(reactor)
+ ");\n");
code.pr(
CUtil.reactorRef(reactor)
+ "->base.name = (char*)lf_allocate(length + 1, sizeof(char),"
+ " (allocation_record_t**)&((self_base_t*)"
+ CUtil.reactorRef(reactor)
+ ")->allocations);");
code.pr(
"if("
+ CUtil.reactorRef(reactor)
+ "->base.name != NULL) {"); // Will be NULL if lf_allocate fails.
code.indent();
code.pr(
"snprintf("
+ CUtil.reactorRef(reactor)
+ "->base.name, length + 1, format, \""
+ reactor.getName()
+ "\", "
+ CUtil.bankIndexName(reactor)
+ ");");
code.unindent();
code.pr("}");
} else {
code.pr(CUtil.reactorRef(reactor) + "->base.name = \"" + reactor.getName() + "\";");
}
ReactorInstance parent = reactor.getParent();
if (parent == null) {
code.pr(CUtil.reactorRef(reactor) + "->base.parent = (self_base_t*)NULL;");
} else {
code.pr(
CUtil.reactorRef(reactor)
+ "->base.parent = (self_base_t*)"
+ CUtil.reactorRef(parent)
+ ";");
}
return code.toString();
}

/**
* Perform initialization functions that must be performed after all reactor runtime instances
* have been created. This function creates nested loops over nested banks.
Expand All @@ -1104,6 +1158,9 @@ private static String deferredInitialize(
// over bank members for the reactor's parent.
code.startScopedBlock(reactor);

// Set the parent pointer and name for the reactor.
code.pr(deferredSetParentAndName(reactor));

// If the child has a multiport that is an effect of some reaction in its container,
// then we have to generate code to allocate memory for arrays pointing to
// its data. If the child is a bank, then memory is allocated for the entire
Expand Down
58 changes: 58 additions & 0 deletions test/C/src/ReactorName.lf
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
target C {
build-type: debug
}

preamble {=
#include <string.h>
=}

reactor A(parent_bank_index: size_t = 0) {
reaction(startup) {=
const char* name = lf_reactor_full_name(self);
lf_print("name: %s", name);
char buffer[20];
snprintf(buffer, 20, "ReactorName.b[%zu].a", self->parent_bank_index);
if (strcmp(buffer, name) != 0) {
lf_print_error_and_exit("full name does not match");
}
name = lf_reactor_name(self);
if (strcmp("a", name) != 0) {
lf_print_error_and_exit("name does not match");
}
=}
}

reactor B(bank_index: size_t = 0) {
a = new A(parent_bank_index=bank_index)

reaction(startup) {=
const char* name = lf_reactor_full_name(self);
lf_print("name: %s", name);
char buffer[20];
snprintf(buffer, 20, "ReactorName.b[%zu]", self->bank_index);
if (strcmp(buffer, name) != 0) {
lf_print_error_and_exit("full name does not match");
}
name = lf_reactor_name(self);
snprintf(buffer, 20, "b[%zu]", self->bank_index);
if (strcmp(buffer, name) != 0) {
lf_print_error_and_exit("name does not match");
}
=}
}

main reactor {
b = new[3] B()

reaction(startup) {=
const char* name = lf_reactor_full_name(self);
lf_print("name: %s", name);
if (strcmp("ReactorName", name) != 0) {
lf_print_error_and_exit("full name does not match");
}
name = lf_reactor_name(self);
if (strcmp("ReactorName", name) != 0) {
lf_print_error_and_exit("name does not match");
}
=}
}
Loading