screeps-microkernel
TypeScript icon, indicating that this package has built-in type declarations

1.1.1 • Public • Published

Best Damn Screeps Microkernel

An opinionated microkernel for Screeps that schedules tasks and monitors CPU usage.

npm install screeps-microkernel --save

Be sure to import * as kernel from 'screeps-microkernel'; / let kernel = require('screeps-microkernel') the package at the top of your main.js (before any other import/requires) for best performance. Also be sure to call kernel.run(...) / kernel(...) at the start of your main loop.

Kernel

Theory of Operation

Functionality Overview

Startup
  • Deserialize Memory
  • Boost Priority of anything that didn't get run in a tick, updating starvation counts
  • Fill priority queues based on task list
Task Execution
  • Monitors CPU usage & executes tasks from queue if sufficient CPU based on estimate
  • Updates CPU cost after task completes (via EMA)
Shutdown
  • Record kernel CPU stats
  • Serialize Memory

Writing Tasks

Because it's presumed that there will be many instances of a given task's code running for different game objects, Tasks shall take the form of a function closure or coroutine in order to store local state in heap memory. Tasks factory functions are initialized with IDs of game objects, which must then return a function that will be called with no arguments.

Tasks shall persist any data they need to rebuild their state in game Memory,

Task Factories

Task Factories create and initialize Task Functions from task arguments. Task Factories have a signature of (...args) => () => RETURN_CODE.

Task Functions

Task functions must have a signature of () => RETURN_CODE. If RETURN_CODE is non-zero, the kernel will log an error.

The task's args are provided when creating the task. These can only be strings or numbers because of serialization. The args are intended to be used to provide the name(s) or id(s) of game entities for the task to operate on.

Registering Task Factories

Because object references are lost on a code reload, the kernel needs references to the appropriate function to run for each task. The kernel function register_task_function is used to provide this reference to the kernel and returns a 'task key' for the task. Every task function must be registered with the kernel before the kernel is run, and should be done outside of the main loop, as register doesn't deduplicate registrations. The 'task key' returned by register_task_function must be passed as the task_key parameter to create_task.

Creating Tasks

The function will be called with the arguments provided to the create_task function via the task_args parameter. Multiple tasks that run the same code with different arguments can readibly be created, all referencing the same task key, but a separate task key is needed for each different function that should be run as a task. Task code must first be registered as described above.

Priorities

Tasks of a lower priority number are always run before tasks of a higher priority number. Note that CRITICAL priority is the lowest, at 0, and LOW is the highest number at 3. While the relationship between the numbers and names are counter-intuitive, the enum names do what an English speaker would generally expect.

Priority Levels

CRITICAL

These tasks are run every tick, regardless of CPU cost.

HIGH

These tasks are run only if they are anticipated not to exceed Game.cpu.tickLimit. Note that high CPU costs at this priority level will drain your CPU bucket.

MEDIUM

These tasks are run if they are anticipated not to exceed Game.cpu.limit, or anticipated not to exceed Game.cpu.tickLimit if Game.cpu.bucket > 5000 (half or more full).

LOW

These tasks are run only if they are anticipated not to exceed Game.cpu.limit.

Task Starvation

Every tick that a task is not able to run due to CPU limits is recorded as being stagnant. As a task becomes more stagnant, it will be bumped up to a higher priority level until it is able to run.

System Calls FIXME

register_task_function

Registers a code object with the kernel that can be run by one or more tasks.

create_task

Adds Task to Task List. Task will not start running until next tick.

If create_task is called from within another task, the created task becomes a child of the first task. If called from code not being run via the kernel, the task has no parent.

kill_task

Stops a task from running in the future. Also stops child tasks.

get_task_ID

Returns the ID of the currently running task.

get_tasks

Returns the tasks currently scheduled to run, mapped by Task ID.

Dependencies (0)

    Dev Dependencies (7)

    Package Sidebar

    Install

    npm i screeps-microkernel

    Weekly Downloads

    1

    Version

    1.1.1

    License

    MIT

    Unpacked Size

    48 kB

    Total Files

    8

    Last publish

    Collaborators

    • riggs