Advertisement
Guest User

Untitled

a guest
Mar 1st, 2021
207
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 8.64 KB | None | 0 0
  1. const std = @import("std");
  2.  
  3. const State = enum {
  4. peekto,
  5. readto,
  6. output,
  7. start,
  8. done,
  9. sever,
  10. anyinput,
  11. };
  12.  
  13. const stageError = error {
  14. noInStream,
  15. noOutStream,
  16. };
  17.  
  18. const Conn = struct {
  19. src:*Stage = undefined, // used by output
  20. from:usize = 0,
  21. sout:usize = 0,
  22. dst:*Stage = undefined, // user by input
  23. to:usize = 0,
  24. sin:usize = 0,
  25. in:bool = false,
  26. data:usize = undefined,
  27.  
  28. fn set(self:*Conn, p:[]Stage, f:usize, o:usize, t:usize, s:usize) void {
  29. self.from=f;
  30. self.src=&p[f];
  31. self.sout=o;
  32. self.to=t;
  33. self.dst=&p[t];
  34. self.sin=s;
  35. if (o==0) self.src.outC = self;
  36. if (s==0) self.dst.inC = self;
  37. }
  38.  
  39. //pub fn format(
  40. // self: SelfType,
  41. // comptime fmt: []const u8,
  42. // options: FormatOptions,
  43. // writer: anytype,
  44. //) !void {
  45. // if (fmt.len == 0) {
  46. // return std.fmt.format(writer, "Conn{*} src {*} {} dst {*} {} in {} {}\n\n",.{self, self.src, self.sout, self.dst, self.sin, self.in, self.data});
  47. // } else {
  48. // @compileError("Unknown format string: '" ++ fmt ++ "'");
  49. // }
  50. //}
  51.  
  52. };
  53.  
  54. const Stage = struct {
  55. outC:?*Conn = null,
  56. inC:?*Conn = null,
  57. state:State = .start,
  58. frame:anyframe = undefined,
  59. n:*std.ArrayList(Conn),
  60.  
  61. pub fn peekto(self:*Stage) !usize {
  62. std.log.info("peekto {*} inC {*}\n",.{self, self.inC});
  63. if (self.inC) |c| {
  64. std.log.info("peekto {*} in {} {}\n",.{c, c.in, c.data});
  65. while (!c.in) {
  66. std.log.info("while suspended",.{});
  67. suspend{
  68. self.state = .peekto;
  69. self.frame=@frame();
  70. }
  71. }
  72. std.log.info("while exited",.{});
  73. }
  74. if (self.inC) |c| {
  75. self.state = .done;
  76. return c.data;
  77. }
  78. self.state = .done;
  79. return error.noInStream;
  80. }
  81.  
  82. pub fn readto(self:*Stage) !usize {
  83. if (self.inC) |c| {
  84. while (!c.in) {
  85. suspend{
  86. self.state = .readto;
  87. self.frame=@frame();
  88. }
  89. }
  90. }
  91. if (self.inC) |c| {
  92. c.in = false;
  93. self.state = .done;
  94. return c.data;
  95. }
  96. self.state = .done;
  97. return error.noInStream;
  98. }
  99.  
  100. pub fn output(self:*Stage, v:usize) !void {
  101. if (self.outC) |c| {
  102. while (c.in) {
  103. suspend {
  104. self.state = .output;
  105. self.frame=@frame();
  106. }
  107. }
  108. }
  109. if (self.outC) |c| {
  110. // std.log.info("p {} s {} v {}",.{l.num, l.sin, v});
  111. c.in = true;
  112. c.data = v;
  113. self.state = .done;
  114. return;
  115. }
  116. self.state = .done;
  117. return error.noOutStream;
  118. }
  119.  
  120. pub fn selectOutput(self:*Stage, o:usize) !void {
  121. return self.setoutC(o);
  122. }
  123.  
  124. pub fn selectInput(self:*Stage, i:usize) !void {
  125. return self.setinC(i);
  126. }
  127.  
  128. pub fn selectAnyInput(self:*Stage) !usize {
  129. if (self.inC) |c| {
  130. while (!c.in) {
  131. suspend {
  132. self.state = .anyinput;
  133. self.frame=@frame();
  134. }
  135. }
  136. }
  137. if (self.inC) |c| {
  138. self.state = .done;
  139. return c.sin;
  140. }
  141. self.state = .done;
  142. return error.noInStream;
  143. }
  144.  
  145. pub fn setinC(self:*Stage, i:usize) !void {
  146. for (self.n.items) |*c| {
  147. if (c.dst == self and c.sin == i) {
  148. self.inC = c;
  149. return;
  150. }
  151. }
  152. return error.noInStream;
  153. }
  154.  
  155. pub fn setoutC(self:*Stage, o:usize) !void {
  156. for (self.n.items) |*c| {
  157. if (c.src == self and c.sout == o) {
  158. self.outC = c;
  159. return;
  160. }
  161. }
  162. return error.noOutStream;
  163. }
  164. };
  165.  
  166. fn exactdiv(self:*Stage, d:usize) !void {
  167. var i:usize = undefined;
  168. while (true) {
  169. i = try self.peekto();
  170. if (i%d == 0)
  171. try self.selectOutput(0)
  172. else
  173. try self.selectOutput(1);
  174.  
  175. _ = try self.output(i);
  176. _ = try self.readto();
  177. }
  178. }
  179.  
  180. fn console(self:*Stage) !void {
  181. const stdout = std.io.getStdOut().writer();
  182. var i:usize = undefined;
  183. while (true) {
  184. i = try self.peekto();
  185. try stdout.print(" {}\n", .{i});
  186. _ = try self.output(i);
  187. _ = try self.readto();
  188. }
  189. }
  190.  
  191. fn fanin(self:*Stage) !void {
  192. while (true) {
  193. _ = try self.selectAnyInput();
  194. try self.output(try self.peekto());
  195. _ = try self.readto();
  196. }
  197. }
  198.  
  199. fn gen(self:*Stage, limit:usize) !void {
  200. var i:usize = 0;
  201. while (i<limit) : (i+=1) {
  202. try self.output(i);
  203. }
  204. }
  205.  
  206. // print("{any}\n", .{ std.mem.asBytes(&s.in).* });
  207.  
  208. pub fn main() !void {
  209.  
  210. var arena = std.heap.ArenaAllocator.init(std.heap.page_allocator);
  211. defer arena.deinit();
  212. const allocator = &arena.allocator;
  213.  
  214. var nodes = try std.ArrayList(Conn).initCapacity(allocator, 20);
  215.  
  216. try nodes.resize(20);
  217. for (nodes.items) |_| {
  218. try nodes.append(Conn{});
  219. }
  220.  
  221. var p = [_]Stage{
  222. Stage{.n=&nodes},
  223. Stage{.n=&nodes},
  224. Stage{.n=&nodes},
  225. Stage{.n=&nodes},
  226. Stage{.n=&nodes}
  227. };
  228.  
  229. nodes.items[0].set(&p,3,0,4,0);
  230. nodes.items[1].set(&p,2,0,3,0);
  231. nodes.items[2].set(&p,1,0,3,1);
  232. nodes.items[3].set(&p,1,1,2,0);
  233. nodes.items[4].set(&p,0,0,1,0);
  234. try nodes.resize(5); // think the rest the Conn nodes are still initialized incase we add connections dynamicily
  235.  
  236. for (nodes.items) |*c| {
  237. std.log.info("start {*} src {*} {} dst {*} {} in {} {}\n\n",.{c, c.src, c.sout, c.dst, c.sin, c.in, c.data});
  238. }
  239.  
  240. //p[0].set(.{Conn.set(&p,0,0,1,0), null});
  241. //p[1].set(.{Conn.set(&p,1,0,3,1), Conn.set(&p,1,1,2,0)});
  242. //p[2].set(.{Conn.set(&p,2,0,3,0), null});
  243. //p[3].set(.{Conn.set(&p,3,0,4,0), null});
  244. //p[4].set(.{null, null});
  245.  
  246. _ = @asyncCall(try allocator.alignedAlloc(u8,16,@frameSize(console)), {}, console, .{&p[4]} );
  247. _ = @asyncCall(try allocator.alignedAlloc(u8,16,@frameSize(fanin)), {}, fanin, .{&p[3]} );
  248. _ = @asyncCall(try allocator.alignedAlloc(u8,16,@frameSize(exactdiv)), {}, exactdiv, .{&p[2], 3} );
  249. _ = @asyncCall(try allocator.alignedAlloc(u8,16,@frameSize(exactdiv)), {}, exactdiv, .{&p[1], 2} );
  250. _ = @asyncCall(try allocator.alignedAlloc(u8,16,@frameSize(gen)), {}, gen, .{&p[0], 10} );
  251.  
  252. // main dispatch loop
  253.  
  254. running: while (true) {
  255. std.log.info("\n\n",.{});
  256. for (nodes.items) |*c, i| {
  257. // const c = &nodes.items[i];
  258. // std.log.info("dst.state {} {} sin {} {} in {}\n",.{c.dst.state, c.to, c.sin, c.dst.outs, c.in });
  259. std.log.info("dst.state {} {} sin {} in {} {} ",.{c.dst.state, c.to, c.sin, c.in, c.data });
  260. std.log.info("src.state {} {} sout {} in {}",.{c.src.state, c.from, c.sout, c.in });
  261.  
  262. if ((c.dst.state == .peekto or c.dst.state == .readto) and c.in) {
  263. resume c.dst.frame;
  264. std.log.info("p dst.state {} {} sin {} in {} {}\n\n",.{c.dst.state, c.to, c.sin, c.in, c.data });
  265. continue :running;
  266. }
  267.  
  268. if (c.dst.state == .anyinput and c.in) {
  269. c.dst.inC = c;
  270. resume c.dst.frame;
  271. std.log.info("p dst.state {} {} sin {} \n\n",.{c.dst.state, c.to, c.sin });
  272. continue :running;
  273. }
  274.  
  275. // std.log.info("src.state {} sout {} in {}\n",.{c.src.state, c.sout, c.in });
  276. if (c.src.state == .output and !c.in) {
  277. resume c.src.frame;
  278. std.log.info("p src.state {} {} sout {} in {} {}\n\n",.{c.src.state, c.from, c.sout, c.in, c.data });
  279. continue :running;
  280. }
  281. }
  282. // when we use os threads in stages we will need to wait for them here.
  283. break;
  284. }
  285. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement