add gate/net pointer lists

This commit is contained in:
Redo 2022-11-04 16:29:11 -06:00
parent 5aa11f9e43
commit 658bcc6ad8
7 changed files with 62 additions and 190 deletions

View File

@ -1,106 +1 @@
local ffi = FFI or require("ffi")
Simulation = Simulation or {}
function Simulation.compile_code(sim, text)
-- todo: compile some kind of DSL into machine code
return code, size
end
--local net_program_code = Simulation.compile_code( [[
--
--]] )
function Simulation.compile(sim)
sim.compilation = {
gates = {},
wires = {},
cgates = {},
cwires = {},
}
local comp = sim.compilation
-- assemble a list of all nets
local all_nets_t = {}
for k, wire in pairs(sim.wires) do
local net = Wire.getgroup(wire)
all_nets_t[net] = net
end
local all_nets = {}
for net_id, net in pairs(all_nets_t) do
table.insert(comp.nets, net)
local cdata = ffi.new("char["..(ffi.sizeof("struct Net") + ffi.sizeof("struct Gate*")*net.num_gates_update).."]")
local cnet = ffi.cast(cdata, "struct Net")
comp.cnets[net] = cnet
end
-- assemble a list of all gates
local all_gates = {}
for k, gate in pairs(sim.gates) do
table.insert(comp.gates, gate)
local cdata = ffi.new("char["..(ffi.sizeof("struct Gate") + ffi.sizeof("struct OutPort")*gate.num_ports_out).."]")
local cgate = ffi.cast(cdata, "struct Gate")
comp.cgates[gate] = cgate
end
for netidx, net in ipairs(comp.nets) do
local cnet = comp.cnets[net] or error("no cnet")
cnet.in_queue = net.in_queue
cnet.num_out_ports_on = net.state_num
cnet.state = net.state
cnet.update_tick = net.update_tick
for i = 1, net.num_gates_update do
local gate = net.gates_update[i]
local cgate = comp.cgates[gate] or error("no cgate")
cnet.gates_update[i-1] = cgate
end
end
for gateidx, gate in ipairs(comp.gates) do
local cgate = comp.cgates[gate] or error("no cgate")
cgate.in_queue = gate.in_queue
local j = 0
for i, port in ipairs(gate.ports) do
if port.type == PortTypes.output then
local net = port.group
if net then
local cnet = comp.cnets[net] or error("no cnet")
cgate.out_ports[j].net = cnet
else
cgate.out_ports[j].net = 0
end
cgate.out_ports[j].state = gate.port_states[i] or error("no gate port_state")
j = j + 1
end
end
end
end
function Simulation.decompile(sim)
local comp = sim.compilation
for netidx, net in ipairs(comp.nets) do
local cnet = comp.cnets[net] or error("no cnet")
net.in_queue = cnet.in_queue
net.state_num = cnet.num_out_ports_on
net.state = cnet.state
net.update_tick = cnet.update_tick
end
for gateidx, gate in ipairs(comp.gates) do
local cgate = comp.cgates[gate] or error("no cgate")
gate.in_queue = cgate.in_queue
local j = 0
for i, port in ipairs(gate.ports) do
if port.type == PortTypes.output then
gate.port_states[i] = cgate.out_ports[j].state
j = j + 1
end
end
end
end
function Simulation.tick_compiled(sim, count)
end

View File

@ -1,75 +1 @@
void sim_init(int num_gates, int num_nets);
void sim_add_gate(int gateid, int logic_func_id, char* logic_func_name, int num_out_ports, char* data);
void sim_add_net(int netid, int num_gates_update);
void sim_connect_out_port(int gateid, int index, int netid);
void sim_connect_in_port(int gateid, int index, int netid);
void sim_tick(int count);
void sim_get_net_state(int netid);
void sim_get_port_state(int gateid, int index);
void sim_set_net_state(int netid);
void sim_set_port_state(int gateid, int index);
void sim_delete_net(int netid);
void sim_delete_gate(int gateid);
////////
void sim_create(unsigned int datalen, char* text);
#include <stdlib.h>
#include <assert.h>
typedef unsigned int uint;
typedef unsigned long long u64;
void sim_copy_logic_function(
char** prog,
char* in_queue,
char* out_port_states,
int logic_func,
char** port_in_net_states,
char** port_out_net_inqueue,
char** port_out_net_update_func,
int num_ports_in,
int num_ports_out
) {
// todo: indata = inport net state pointers, outport net in queue pointers, outport net update function pointers
}
void sim_compile_gate(char** prog, char** data, int** idat, u64* indata) {
int num_ports_in = *(indata++);
int num_ports_out = *(indata++);
int in_queue = *(indata++);
int logic_func = *(indata++);
char* port_in_net_states[256];
sim_copy_logic_function( // copy logic function into program
prog,
*data,
(*data)+1,
logic_func,
&indata,
num_ports_in,
num_ports_out
);
*(*data++) = in_queue; // alloc bool for in queue
for(int i=0; i<num_ports_out; i++) { // alloc bool for each output state
*((*data)++) = *(indata++);
}
}
void sim_compile_net_function(char** prog, char* in_queue, int* gates, u64** indata, int num_gates_update) {
}
void sim_compile_net(char** prog, char** data, int** idat, u64* indata) {
int num_gates_update = *(indata++);
int num_ports_on = *(indata++);
int in_queue = *(indata++);
sim_compile_net_function(prog, *data, *idat, &indata, num_gates_update);
*((*data)++) = in_queue;
*((*idat)++) = num_ports_on;
}

Binary file not shown.

View File

@ -3,6 +3,18 @@ local ffi = FFI or require("ffi")
Gate = {}
ffi.cdef [[
struct Net;
struct Gate {
int* in_queue;
int* port_states;
int** port_net_state;
int** port_net_state_num;
int** port_net_in_queue;
struct Net** port_nets_c;
};
]]
function Gate.new(objref, definition)
local gate = {
-- Logic Critical
@ -14,10 +26,21 @@ function Gate.new(objref, definition)
port_net_state = ffi.new("int*["..(#definition.ports+1).."]"),
port_net_state_num = ffi.new("int*["..(#definition.ports+1).."]"),
port_net_in_queue = ffi.new("int*["..(#definition.ports+1).."]"),
port_nets_c = ffi.new("struct Net*["..(#definition.ports+1).."]"),
objref = objref,
definition = definition,
}
gate.in_queue[0] = 0
gate.c = ffi.new("struct Gate")
gate.c.in_queue = gate.in_queue
gate.c.port_states = gate.port_states
gate.c.port_net_state = gate.port_net_state
gate.c.port_net_state_num = gate.port_net_state_num
gate.c.port_net_in_queue = gate.port_net_in_queue
gate.c.port_nets_c = gate.port_nets_c
return gate
end

View File

@ -75,7 +75,6 @@ end
function GateDefinition.constructgate(def, objref, position, rotation)
local gate = Gate.new(objref, def)
gate.in_queue[0] = 0
for i = 1, #def.ports do
local portd = def.ports[i]
local type = portd.type

View File

@ -1,8 +1,19 @@
local ffi = FFI
local ffi = FFI or require("ffi")
Group = {}
ffi.cdef [[
struct Gate;
struct Net {
int* state;
int* state_num;
int* in_queue;
int* update_tick;
struct Gate** gates_update_c;
};
]]
function Group.new()
local net = {
-- Logic Critical
@ -11,7 +22,8 @@ function Group.new()
in_queue = ffi.new("int[1]"),
update_tick = ffi.new("int[1]"),
gates_update = {},
num_gates_update = 0,
num_gates_update = ffi.new("int[1]"),
gates_update_c = nil,
fxstate = 0,
@ -26,6 +38,14 @@ function Group.new()
net.state_num[0] = 0
net.in_queue[0] = 0
net.update_tick[0] = 0
net.c = ffi.new("struct Net")
net.c.state = net.state
net.c.state_num = net.state_num
net.c.in_queue = net.in_queue
net.c.update_tick = net.update_tick
net.c.gates_update_c = ffi.cast("struct Gate**", 0)
return net
end
@ -186,7 +206,7 @@ function Group.setstate(group, state)
group.state[0] = state
group.update_tick[0] = sim.current_tick
local len = group.num_gates_update
local len = group.num_gates_update[0]
for i = 1, len do
local gate = group.gates_update[i]
if gate and gate.in_queue[0]==0 then
@ -203,13 +223,22 @@ function Group.update(group)
Group.setstate(group, group.state_num[0]>0 and 1 or 0)
end
function Group.rebuild_ports(group)
group.gates_update = {}
group.num_gates_update = 0
for k, port in pairs(group.in_ports) do
function Group.rebuild_ports(net)
net.gates_update = {}
net.num_gates_update[0] = 0
local gates_seen = {}
for k, port in pairs(net.in_ports) do
if port.causeupdate then
array_add(group.gates_update, Port.getgate(port))
group.num_gates_update = group.num_gates_update + 1
local gate = Port.getgate(port)
if not gates_seen[gate] then
gates_seen[gate] = true
net.gates_update[net.num_gates_update[0]+1] = gate
net.num_gates_update[0] = net.num_gates_update[0] + 1
end
end
end
net.gates_update_c = ffi.new("struct Gate*["..(net.num_gates_update[0]).."]")
for i = 0, net.num_gates_update[0]-1 do
net.gates_update_c[i] = net.gates_update[i+1].c
end
end

View File

@ -141,7 +141,7 @@ function network_update()
local group = Wire.getgroup(wire)
local numwires = 0; for k, wire2 in pairs(group.wires ) do numwires = numwires +1 end
local numportsi = 0; for k, port in pairs(group.in_ports ) do numportsi = numportsi+1 end
local numgatesu = group.num_gates_update
local numgatesu = group.num_gates_update[0]
local numportso = 0; local numportson=0;
for k, port in pairs(group.out_ports) do
numportso = numportso+1