#CooperativeMultitasking

cslinuxboycslinuxboy
2023-08-23

Decided to give a try for my now that I'm getting back into . So far I like what I see. I'll ditch for now.

Karsten Schmidttoxi@mastodon.thi.ng
2023-08-10

#ReleaseThursday As promised, a new version of thi.ng/fibers is out now and includes several new fiber operators/combinators and all the essentials for channel-based communication between processes/fibers (aka #CSP). The CSP channel supports arbitrary buffer sizes & implementations to achieve a range of blocking/non-blocking behaviors for reads/writes. And because all channel ops (read/write/close) are fiber-based, they can also be combined with all the other available operators, enabling some pretty powerful and expressive usage patterns...

More demos & tutorial forthcoming. Check the readme, API docs & examples and please report back with any feedback/questions/suggestions...

πŸ«ΆπŸš€

#ThingUmbrella #TypeScript #CooperativeMultitasking

Karsten Schmidttoxi@mastodon.thi.ng
2023-08-09

After some friendly inquiry by @computersandblues, I spent a few hours today adding basic CSP (#CommunicatingSequentialProcesses) primitives for thi.ng/fibers and writing some preliminary documentation. I'm amazed how simple (and easy!) it was this time around (compared to thi.ng/csp) and it's giving me big hopes for the fiber based approach in general...

Readme section:
github.com/thi-ng/umbrella/blo

2-channel ping/pong example:
github.com/thi-ng/umbrella/blo

Source code & doc strings:
github.com/thi-ng/umbrella/blo

#ThingUmbrella #TypeScript #Coroutines #CSP #CooperativeMultitasking

Excerpt from readme:

"CSP primitives (Communicating Sequential Processes)

In addition to the operators above, the basic fiber implementation can also be used to construct other types of primitives, like these required for channel-based communication between processes. The package includes a fiber-based read/write channel primitive which can be customized with different buffer behaviors to control blocking behaviors and backpressure handling (aka attempting to write faster to a channel than values are being read, essentially a memory management issue).
Buffering behaviors

The following channel buffer types are included, all accepting a max. capacity and all implementing the required IReadWriteBuffer interface:

fifo: First in, first out. Writes to the channel will start blocking once the buffer's capacity is reached, otherwise complete immediately. Likewise, channel reads are non-blocking whilst there're more buffered values available. Reads will only block if the buffer is empty.

lifo: First in, last out. Read/write behavior is mostly the same as with fifo, with the important difference, that (as the name indicates), the last value written will be the first value read (i.e. stack behavior).

sliding: Sliding window buffer. Writes to the channel are never blocking! Once the buffer's capacity is reached, a new write will first expunge the oldest buffered value (similar to LRU cache behavior). Read behavior is the same as for fifo.
..."TypeScript source code (ping/pong example):

import { channel, fiber, wait } from "@thi.ng/fibers";
import { ConsoleLogger } from "@thi.ng/logger";

// create idle main fiber with custom options
const app = fiber(null, {
    id: "main",
    logger: new ConsoleLogger("app"),
    terminate: true,
});

// create CSP channels (w/ default config)
const ping = channel<number>();
const pong = channel<number>();

// attach ping/pong child processes
app.forkAll(
    // ping
    function* () {
        let x: number | undefined;
        while (ping.readable()) {
            // blocking read op
            x = yield* ping.read();
            // check if channel was closed meanwhile
            if (x === undefined) break;
            console.log("PING", x);
            // blocking write op to other channel
            yield* pong.write(x);
            // slowdown
            yield* wait(100);
        }
    },
    // pong (very similar)
    function* () {
        let x: number | undefined;
        while (pong.readable()) {
            x = yield* pong.read();
            if (x === undefined) break;
            console.log("PONG", x);
            yield* ping.write(x + 1);
        }
    },
    // channel managment
    function* () {
        // kickoff ping/pong
        yield* ping.write(0);
        yield* wait(1000);
        // wait for both channels to close
        yield* ping.close();
        yield* pong.close();
    }
);
app.run();

Client Info

Server: https://mastodon.social
Version: 2025.04
Repository: https://github.com/cyevgeniy/lmst