diff --git a/demo/.envrc b/demo/.envrc index 1d953f4bd..07cbce683 100644 --- a/demo/.envrc +++ b/demo/.envrc @@ -1 +1 @@ -use nix +use flake .#dev-demo diff --git a/demo/.gitignore b/demo/.gitignore new file mode 100644 index 000000000..9ebaddbc1 --- /dev/null +++ b/demo/.gitignore @@ -0,0 +1,29 @@ +dist +dist-* +cabal-dev +*.o +*.hi +*.hie +*.chi +*.chs.h +*.dyn_o +*.dyn_hi +.hpc +.hsenv +.cabal-sandbox/ +cabal.sandbox.config +*.prof +*.aux +*.hp +*.eventlog +.stack-work/ +cabal.project.local +cabal.project.local~ +.HTF/ +.ghc.environment.* +.pre-commit-config.yaml +result +.direnv +.ipynb_checkpoints/ +__pycache__/ +.nixos-test-history \ No newline at end of file diff --git a/demo/.markdownlint.yaml b/demo/.markdownlint.yaml new file mode 100644 index 000000000..decc245a0 --- /dev/null +++ b/demo/.markdownlint.yaml @@ -0,0 +1,6 @@ +default: true +MD013: false +MD024: false +MD033: false +MD041: false +MD022: false diff --git a/demo/.shellcheckrc b/demo/.shellcheckrc new file mode 100644 index 000000000..3f3c577cf --- /dev/null +++ b/demo/.shellcheckrc @@ -0,0 +1 @@ +disable=SC2148,SC1090,SC2002 diff --git a/demo/.yamllint b/demo/.yamllint new file mode 100644 index 000000000..669c8646f --- /dev/null +++ b/demo/.yamllint @@ -0,0 +1,5 @@ +extends: default + +rules: + line-length: disable + document-start: disable diff --git a/demo/2025-10/README.md b/demo/2025-10/README.md index 5505e7adc..46d56f05c 100644 --- a/demo/2025-10/README.md +++ b/demo/2025-10/README.md @@ -1,227 +1,78 @@ -# Prototype demo - October 2025 +# Run the demo -Minimum viable demo of Leios network traffic interfering with Praos using a three node setup and prepared Praos and Leios data. +## Using Nix run (recommended) -> ![WARNING] -> TODO: Add overview / architecture diagram. +You can run the demo directly from the GitHub repository using Nix (requires SSH access): -See https://github.com/IntersectMBO/ouroboros-consensus/issues/1701 for more context. - -## Prepare the shell environment - -- If your environment can successfully execute `cabal build exe:cardano-node` from this commit, then it can build this demo's exes. - - ``` - $ git log -1 10.5.1 - commit ca1ec278070baf4481564a6ba7b4a5b9e3d9f366 (tag: 10.5.1, origin/release/10.5.1, nfrisby/leiosdemo2025-anchor) - Author: Jordan Millar - Date: Wed Jul 2 08:24:11 2025 -0400 - - Bump node version to 10.5.1 - ``` - -- The Python script needs `pandas` and `matplotlib`. -- The various commands and bash scripts below needs `toxiproxy`, `sqlite`, `ps` (which on a `nix-shell` might require the `procps` package for matching CLIB, eg), and so on. -- Set `CONSENSUS_BUILD_DIR` to the absolute path of a directory in which `cabal build exe:immdb-server` will succeed. -- Set `NODE_BUILD_DIR` to the absolute path of a directory in which `cabal build exe:cardano-node` will succeed. -- Set `CONSENSUS_REPO_DIR` to the absolute path of the `ouroboros-consensus` repo. - -- Checkout a patched version of the `cardano-node` repository, something like the following, eg. - -``` -6119c5cff0 - (HEAD -> nfrisby/leiosdemo2025, origin/nfrisby/leiosdemo2025) WIP add Leios demo Consensus s-r-p (25 hours ago) +```shell +nix run github:IntersectMBO/ouroboros-leios#leios-202510-demo ``` -- If you're using a `source-repository-package` stanza for the `cabal build exe:cardano-node` command in the `NODE_BUILD_DIR`, confirm that it identifies the `ouroboros-consensus` commit you want to use (eg the one you're reading this file in). +Or from a local checkout: -## Build the exes - -``` -$ (cd $CONSENSUS_BUILD_DIR; cabal build exe:immdb-server exe:leiosdemo202510) -$ IMMDB_SERVER="$(cd $CONSENSUS_BUILD_DIR; cabal list-bin exe:immdb-server)" -$ DEMO_TOOL="$(cd $CONSENSUS_BUILD_DIR; cabal list-bin exe:leiosdemo202510)" -$ (cd $CONSENSUS_BUILD_DIR; cabal build exe:cardano-node) -$ CARDANO_NODE="$(cd $CONSENSUS_BUILD_DIR; cabal list-bin exe:cardano-node)" +```shell +nix run .#leios-202510-demo ``` -## Prepare the input data files +The demo uses default values of `REF_SLOT=41` and `SECONDS_UNTIL_REF_SLOT=5`. You can override these: +```shell +SECONDS_UNTIL_REF_SLOT=10 REF_SLOT=200 nix run github:IntersectMBO/ouroboros-leios#leios-202510-demo ``` -$ (cd $CONSENSUS_BUILD_DIR; $DEMO_TOOL generate demoUpstream.db "${CONSENSUS_REPO_DIR}/demoManifest.json" demoBaseSchedule.json) -$ cp demoBaseSchedule.json demoSchedule.json -$ # You must now edit demoSchedule.json so that the first number in each array is 182.9 -$ echo '[]' >emptySchedule.json -$ # create the following symlinks -$ (cd $CONSENSUS_REPO_DIR; ls -l $(find nix/ -name genesis-*.json)) -lrwxrwxrwx 1 nfrisby nifr 30 Oct 24 16:27 nix/leios-mvd/immdb-node/genesis-alonzo.json -> ../genesis/genesis.alonzo.json -lrwxrwxrwx 1 nfrisby nifr 29 Oct 24 16:27 nix/leios-mvd/immdb-node/genesis-byron.json -> ../genesis/genesis.byron.json -lrwxrwxrwx 1 nfrisby nifr 30 Oct 24 16:27 nix/leios-mvd/immdb-node/genesis-conway.json -> ../genesis/genesis.conway.json -lrwxrwxrwx 1 nfrisby nifr 31 Oct 24 16:27 nix/leios-mvd/immdb-node/genesis-shelley.json -> ../genesis/genesis.shelley.json -lrwxrwxrwx 1 nfrisby nifr 30 Oct 24 16:27 nix/leios-mvd/leios-node/genesis-alonzo.json -> ../genesis/genesis.alonzo.json -lrwxrwxrwx 1 nfrisby nifr 29 Oct 24 16:27 nix/leios-mvd/leios-node/genesis-byron.json -> ../genesis/genesis.byron.json -lrwxrwxrwx 1 nfrisby nifr 30 Oct 24 16:27 nix/leios-mvd/leios-node/genesis-conway.json -> ../genesis/genesis.conway.json -lrwxrwxrwx 1 nfrisby nifr 31 Oct 24 16:27 nix/leios-mvd/leios-node/genesis-shelley.json -> ../genesis/genesis.shelley.json -``` - -## Prepare to run scenarios -Ensure a toxiproxy server is running. +## Using run-demo.sh directly -``` -$ toxiproxy-server 1>toxiproxy.log 2>&1 & -``` +Alternatively, you can run the script directly from a dev shell: -## Run the scenario +```shell +SECONDS_UNTIL_REF_SLOT=5 REF_SLOT=177 DATA="./data" ./run-demo.sh -Run the scenario with `emptySchedule.json`, ie no Leios traffic. +... +Each row represents a unique block seen by both nodes, joined by hash and slot. + slot hash latency_ms +0 2 4e93dab121aaeabf20a6b6112048260fb1b72ed94f10eb... 179118.490342 +1 44 bd384ce8792d89da9ab6d11d10fc70a36a2899e6c3b10d... 137309.362409 +2 52 23b021f8e2c06e64b10647d9eeb5c9f11e50181f5a5694... 129462.848231 +3 53 5ecd12b363657693f31e62421726fcc427788eed6d2fb2... 128463.045544 +4 59 0341e8795f13d6bcbd0d1fec0fc03fb75ede8cd6d75999... 122466.373131 +5 183 56515bfd5751ca2c1ca0f21050cdb1cd020e396c623a16... 605.664913 +6 187 60fd8fc00994ac1d3901f1d7a777edf5b99546a748fc7d... 3269.136876 +7 188 48cf5b44cb529d51b5b90c8b7c2572a27a2f22fc8933fe... 6842.006962 -``` -$ LEIOS_UPSTREAM_DB_PATH="$(pwd)/demoUpstream.db" LEIOS_SCHEDULE="$(pwd)/emptySchedule.json" SECONDS_UNTIL_REF_SLOT=5 REF_SLOT=177 CLUSTER_RUN_DATA="${CONSENSUS_REPO_DIR}/nix/leios-mvd" CARDANO_NODE=$CARDANO_NODE IMMDB_SERVER=$IMMDB_SERVER ${CONSENSUS_REPO_DIR}/scripts/leios-demo/leios-october-demo.sh -$ # wait about ~20 seconds before stopping the execution by pressing any key +Total unique block events matched: 8 ``` -Run the scenario with `demoSchedule.json`. +## Nix build targets -``` -$ LEIOS_UPSTREAM_DB_PATH="$(pwd)/demoUpstream.db" LEIOS_SCHEDULE="$(pwd)/demoSchedule.json" SECONDS_UNTIL_REF_SLOT=5 REF_SLOT=177 CLUSTER_RUN_DATA="${CONSENSUS_REPO_DIR}/nix/leios-mvd" CARDANO_NODE=$CARDANO_NODE IMMDB_SERVER=$IMMDB_SERVER ${CONSENSUS_REPO_DIR}/scripts/leios-demo/leios-october-demo.sh -$ # wait about ~20 seconds before stopping the execution by pressing any key -``` - -## Analysis - -Compare and contrast the `latency_ms` column for the rows with a slot that's after the reference slot 177. -The first few such ros (ie those within a couple seconds of the reference slot) seem to often also be disrupted, because the initial bulk syncing to catch up to the reference slot presumably leaves the node in a disrupted state for a short interval. - -**WARNING**. -Each execution consumes about 0.5 gigabytes of disk. -The script announces where (eg `Temporary data stored at: /run/user/1000/leios-october-demo.c5Wmxc`), so you can delete each run's data when necessary. - -**INFO**. -If you don't see any data in the 'Extracted and Merged Data Summary' table, then check the log files in the run's temporary directory. -This is where you might see messages about, eg, the missing `genesis-*.json` files, bad syntax in the `demoSchedule.json` file, etc. - -# Details about the demo components - -## The topology - -For this first iteration, the demo topology is a simple linear graph. +Build an empty Leios DB: -```mermaid -flowchart TD - MockedUpstreamPeer --> Node0 --> MockedDownstreamPeer +```shell +$ nix build .#leios-empty-db +$ sqlite3 result ".schema" +CREATE TABLE txCache +... ``` -**INFO**. -In this iteration of the demo, the mocked downstream peer (see section below) is simply another node, ie Node1. +Build a busy Leios DB from the manifest: -## The Praos traffic and Leios traffic - -In this iteration of the demo, the data and traffic is very simple. - -- The Praos data is a simple chain provided by the Performance&Tracing team. -- The mocked upstream peer serves each Praos block when the mocked wall-clock reaches the onset of their slots. -- The Leios data is ten 12.5 megabyte EBs. - They use the minimal number of txs necessary in order to accumulate 12.5 megabytes in order to minimize the CPU&heap overhead of the patched-in Leios logic, since this iteration of trhe demo is primarily intended to focus on networking. -- The mocked upstream peer serves those EBs just prior to the onset of one of the Praos block's slot, akin to (relatively minor) ATK-LeiosProtocolBurst attack. - Thus, the patched nodes are under significant Leios load when that Praos block begins diffusing. - -## The demo tool - -The `cabal run exe:leiosdemo202510 -- generate ...` command generates a SQLite database with the following schema. - -``` -CREATE TABLE ebPoints ( - ebSlot INTEGER NOT NULL - , - ebHashBytes BLOB NOT NULL - , - ebId INTEGER NOT NULL - , - PRIMARY KEY (ebSlot, ebHashBytes) - ) WITHOUT ROWID; -CREATE TABLE ebTxs ( - ebId INTEGER NOT NULL -- foreign key ebPoints.ebId - , - txOffset INTEGER NOT NULL - , - txHashBytes BLOB NOT NULL -- raw bytes - , - txBytesSize INTEGER NOT NULL - , - txBytes BLOB -- valid CBOR - , - PRIMARY KEY (ebId, txOffset) - ) WITHOUT ROWID; +```shell +$ nix build .#leios-busy-db +$ sqlite3 result ".schema" +CREATE TABLE txCache +... ``` -The contents of the generated database are determine by the given `manifest.json` file. -For now, see the `demoManifest.json` file for the primary schema: each "`txRecipe`" is simply the byte size of the transaction. - -The `generate` subcommand also generates a default `schedule.json`. -Each EB will have two array elements in the schedule. -The first number in an array element is a fractional slot, which determines when the mocked upstream peer will offer the payload. -The rest of the array element is `MsgLeiosBlockOffer` if the EB's byte size is listed or `MsgLeiosBlockTxsOffer` if `null` is listed. - -The secondary schema of the manifest allows for EBs to overlap (which isn't necessary for this demo, despite the pathced node fully supporting it). -Overlap is created by an alternative "`txRecipe`", an object `{"share": "XYZ", "startIncl": 90, "stopExcl": 105}` where `"nickname": "XYZ"` was included in a preceding _source_ EB recipe. -The `"startIncl`" and `"stopExcl"` are inclusive and exclusive indices into the source EB (aka a left-closed right-open interval); `"stopExcl"` is optional and defaults to the length of the source EB. -With this `"share"` syntax, it is possible for an EB to include the same tx multiple times. -That would not be a well-formed EB, but the prototype's behavior in response to such an EB is undefined---it's fine for the prototype to simply assume all the Leios EBs and txs in their closures are well-formed. -(TODO check for this one, since it's easy to check for---just in the patched node itself, or also in `generate`?) - -## The mocked upstream peer - -The mocked upstream peer is a patched variant of `immdb-server`. - -- It runs incomplete variants of LeiosNotify and LeiosFetch: just EBs and EB closures, nothing else (no EB announcements, no votes, no range requests). -- It serves the EBs present in the given `--leios-db`; it sends Leios notificaitons offering the data according to the given `--leios-schedule`. - See the demo tool section above for how to generate those files. - -## The patched node/node-under-test - -The patched node is a patched variant of `cardano-node`. -All of the material changes were made in the `ouroboros-consensus` repo; the `cardano-node` changes are merely for integration. - -- It runs the same incomplete variants of LeiosNotify and LeiosFetch as the mocked upstream peer. -- The Leios fetch request logic is a fully fledged first draft, with following primary shortcomings. - - It only handles EBs and EB closures, not votes and not range requests. - - It retains a number of heap objects in proportion with the number of txs in EBs it has acquired. - The real node---and so subsequent iterations of this prototype---must instead keep that data on disk. - This first draft was intended to do so, but we struggled to invent the fetch logic algorithm with the constraint that some of its state was on-disk; that's currently presumed to be possible, but has been deferred to a subsequent iteration of the prototype. - - It never discards any information. - The real node---and so subsequent iterations of this prototype---must instead discard EBs and EB closures once they're old enough, unless they are needed for the immutable chain. - - Once it decides to fetch a set of txs from an upstream peer for the sake of some EB closure(s), it does not necessarily compose those into an optimal set of requests for that peer. - We had not identified the potential for an optimizing algorithm here until writing this first prototype, so it just does something straight-forward and naive for now (which might be sufficient even for the real-node---we'll have to investigate later). - -There are no other changes. -In particular, that means the `ouroboros-network` mux doesn't not deprioritize Leios traffic. -That change is an example of what this first prototype is intended to potentially demonstrate the need for. -There are many such changes, from small to large. -Some examples includes the following. - -- The prototype uses SQLite3 with entirely default settings. - Maybe Write-Ahead Log mode would be much preferable, likely need to VACUUM at some point, and so on. -- The prototype uses a mutex to completely isolate every SQLite3 invocation---that's probably excessive, but was useful for some debugging during initial development (see the Engineering Notes appendix) -- The prototype chooses several _magic numbers_ for resource utilization limits (eg max bytes per reqeust, max outsanding bytes per peer, fetch decision logic rate-limiting, txCache disk-bandwidth rate-limiting, etc). - These all ultimately need to be tuned for the intended behvaiors on `mainnet`. -- The prototype does not deduplicate the storage of EBs' closures when they share txs. - This decision makes the LeiosFetch server a trivial single-pass instead of a join. - However, it "wastes" disk space and disk bandwidth. - It's left to future work to decide whether that's a worthwhile trade-off. - -## The mocked downstream node - -For simplicity, this is simply another instance of the patched node. -In the future, it could be comparatively lightweight and moreover could replay an arbitrary schedule of downstream requests, dual to the mocked upstream peer's arbitrary schedule of upstream notifications. - -# Appendix: Engineering Notes - -This section summarizes some lessons learned during the development of this prototype. - -- Hypothesis: A SQLite connection will continue to hold SQLite's internal EXCLUSIVE lock _even after the transaction is COMMITed_ when the write transaction involved a prepared statement that was accidentally not finalized. - That hypothesis was inferred from a painstaking debugging session, but I haven't not yet confirmed it in isolation. - The bugfix unsuprisingly amounted to using `bracket` for all prepare/finalize pairs and all BEGIN/COMMIT pairs; thankfully our DB patterns seem to accommodate such bracketing. -- The SQLite query plan optimizer might need more information in order to be reliable. - Therefore at least one join (the one that copies out of `txCache` for the EbTxs identified in an in-memory table) was replaced with application-level iteration. - It's not yet clear whether a one-time ANALYZE call might suffice, for example. - Even if it did, it's also not yet clear how much bandwidth usage/latency/jitter/etc might be reduced. +Build a busy Leios schedule from the manifest: + +```shell +$ nix build .#leios-busy-db.schedule +$ cat result-schedule +[ + [ + 182.9, + [ + 0, + "adfe0e24083d8dc2fc6192fcd9b01c0a2ad75d7dac5c3745de408ea69eaf62d8", + 28234 +... +``` diff --git a/demo/2025-10/analyse.py b/demo/2025-10/analyse.py new file mode 100644 index 000000000..69257152e --- /dev/null +++ b/demo/2025-10/analyse.py @@ -0,0 +1,407 @@ +import os +import sys +import json +import pandas as pd +import matplotlib.pyplot as plt + +# --- Configuration --- +# Filter for the event containing the timestamp we want to measure at node 0 and node 1 +BLOCK_EVENT_FILTER = "BlockFetch.Client.CompletedBlockFetch" +# Filter for the event containing the slot and hash. We need to do this because the 'CompletedBlockFetch' event does not contain the slot number. +HEADER_EVENT_FILTER = "ChainSync.Client.DownloadedHeader" + + +def filter_log_events(log_path: str, filter_text: str): + """ + Reads a log file, parses JSON lines, and extracts relevant fields + based on the filter type. + """ + log_filename = os.path.basename(log_path) + print(f"\n--- Analyzing Log: {log_filename} for event: '{filter_text}' ---") + + parsed_data = [] + + try: + with open(log_path, "r") as f: + for line in f: + try: + log_entry = json.loads(line) + + # Check if the namespace matches the filter + if log_entry.get("ns") == filter_text: + + event_data = log_entry.get("data", {}) + block_hash = None + block_slot = None + + # Determine extraction logic based on the event type + if filter_text == HEADER_EVENT_FILTER: + # Structure: "data":{"block": "HASH", ..., "slot": SLOT} + block_hash = event_data.get("block") + block_slot = event_data.get("slot") + elif filter_text == BLOCK_EVENT_FILTER: + # Structure: "data":{"block": "HASH", ...} + block_hash = event_data.get("block") + block_slot = None + + # Base record structure + record = { + "node": log_filename.split("-")[-1].split(".")[0], + "at": log_entry.get("at"), + "hash": block_hash, + "slot": block_slot, + } + + # Only add if the core fields were successfully extracted + if record["at"] and record["hash"]: + parsed_data.append(record) + + except json.JSONDecodeError: + continue + except Exception as e: + # This catch remains for general unexpected issues. + print( + f"Warning: Failed to parse or extract fields from a line in {log_filename}. Error: {e}", + file=sys.stderr, + ) + continue + + print( + f"Successfully extracted {len(parsed_data)} records matching '{filter_text}'." + ) + return parsed_data + + except FileNotFoundError: + print(f"Error: Log file not found at {log_path}.", file=sys.stderr) + return [] + except Exception as e: + print( + f"An unexpected error occurred while processing {log_path}: {e}", + file=sys.stderr, + ) + return [] + + +def create_and_clean_df( + records: list, node_id: str, timestamp_column: str, unique_subset: list +) -> pd.DataFrame: + """ + Converts records to a DataFrame, converts types, removes duplicates, + and renames the 'at' column. + """ + if not records: + # Return an empty DataFrame with the expected columns if no records were found. + # This prevents KeyError later during column selection. + return pd.DataFrame(columns=["hash", "slot", "at", "node"]).rename( + columns={"at": timestamp_column} + ) + + df = pd.DataFrame(records) + + # Convert columns to appropriate data types + try: + if "at" in df.columns: + df["at"] = pd.to_datetime(df["at"]) + if "slot" in df.columns: + df["slot"] = pd.to_numeric(df["slot"], errors="coerce").astype("Int64") + except Exception as e: + print( + f"Warning: Failed to convert data types in DataFrame for node {node_id}: {e}", + file=sys.stderr, + ) + return pd.DataFrame(columns=["hash", "slot", "at", "node"]).rename( + columns={"at": timestamp_column} + ) + + # Deduplication: Keep only the first (earliest) occurrence + initial_rows = len(df) + df = df.sort_values( + by="at" if "at" in df.columns else df.columns[0] + ).drop_duplicates(subset=unique_subset, keep="first") + + if len(df) < initial_rows: + duplicates_removed = initial_rows - len(df) + print( + f"Warning: Removed {duplicates_removed} duplicate log entries from node {node_id}." + ) + + # Rename the timestamp column for merging later + if "at" in df.columns: + df = df.rename(columns={"at": timestamp_column}) + + return df + + +def plot_onset_vs_arrival(df: pd.DataFrame, output_file: str = None): + """ + Generates and displays a scatter plot of slot_onset vs. at_node_1. + If output_file is provided, saves the plot to that file. + """ + print("\n--- Generating Scatter Plot ---") + try: + if "slot_onset" in df.columns and "at_node_1" in df.columns: + # Ensure both columns are datetime objects for plotting + df["slot_onset"] = pd.to_datetime(df["slot_onset"]) + df["at_node_1"] = pd.to_datetime(df["at_node_1"]) + + plt.figure(figsize=(10, 6)) + plt.scatter(df["slot_onset"], df["at_node_1"], alpha=0.5, s=10) + + # Add a y=x reference line + # Find common min/max for a good 1:1 line + all_times = pd.concat([df["slot_onset"], df["at_node_1"]]) + min_time = all_times.min() + max_time = all_times.max() + plt.plot( + [min_time, max_time], + [min_time, max_time], + "r--", + label="1:1 Line (Onset = Arrival)", + ) + + plt.title("Block Arrival Time (Node 1) vs. Slot Onset Time") + plt.xlabel("Slot Onset Time (Calculated)") + plt.ylabel("Block Arrival Time (at_node_1)") + plt.grid(True, linestyle="--", alpha=0.6) + plt.legend() + plt.tight_layout() + + # Rotate x-axis labels for better readability + plt.xticks(rotation=45) + + if output_file: + plt.savefig(output_file, bbox_inches="tight") + print(f"Plot saved to {output_file}") + else: + print("Displaying plot...") + plt.show() + + plt.close(plt.gcf()) # Close the figure to free memory + + else: + print( + "Warning: 'slot_onset' or 'at_node_1' column not found. Skipping plot generation." + ) + + except ImportError: + print( + "\n--- Plotting Skipped ---", + file=sys.stderr, + ) + print( + "To generate the plot, please install matplotlib: pip install matplotlib", + file=sys.stderr, + ) + except Exception as e: + print( + f"Error: Failed to generate plot. Error: {e}", + file=sys.stderr, + ) + + +if __name__ == "__main__": + if len(sys.argv) < 5 or len(sys.argv) > 6: + print( + "Configuration Error: Please provide initial-slot, initial-time, two log files, and optionally an output plot file.", + file=sys.stderr, + ) + print( + "Example Usage: python log_parser.py /path/to/node-0.log /path/to/node-1.log [output_plot.png]", + file=sys.stderr, + ) + sys.exit(1) + + # --- Argument Parsing --- + try: + initial_slot = int(sys.argv[1]) + except ValueError: + print( + f"Configuration Error: Could not parse initial-slot '{sys.argv[1]}' as an integer.", + file=sys.stderr, + ) + sys.exit(1) + + try: + initial_time_str = sys.argv[2] + # Try to parse as a POSIX timestamp (integer string) first + try: + posix_time = int(initial_time_str) + # Convert from POSIX seconds to a UTC datetime object + initial_time = pd.to_datetime(posix_time, unit="s", utc=True) + print( + f"Note: Interpreted initial-time '{initial_time_str}' as POSIX timestamp (UTC)." + ) + except ValueError: + # If not an integer, try to parse as a standard datetime string + initial_time = pd.to_datetime(initial_time_str) + # If the provided string has no timezone, assume UTC for consistency + if initial_time.tzinfo is None: + initial_time = initial_time.tz_localize("UTC") + print( + f"Note: Interpreted initial-time '{initial_time_str}' as datetime string (assuming UTC)." + ) + else: + # If it has a timezone, convert it to UTC for consistency + initial_time = initial_time.tz_convert("UTC") + + except Exception as e: + print( + f"Configuration Error: Could not parse initial-time '{sys.argv[2]}' as either a POSIX timestamp or a datetime string. Error: {e}", + file=sys.stderr, + ) + sys.exit(1) + + log_path_0 = sys.argv[3] + log_path_1 = sys.argv[4] + plot_output_file = sys.argv[5] if len(sys.argv) == 6 else None + + print("\n--- Initial Configuration ---") + print(f"Initial Slot: {initial_slot}") + print(f"Initial Time: {initial_time}") + print(f"Log File 0: {log_path_0}") + print(f"Log File 1: {log_path_1}") + if plot_output_file: + print(f"Plot Output File: {plot_output_file}") + + # --- STEP 1: Create Hash-to-Slot Lookup Table (Headers) --- + + # Collect header data from node 0 only (the primary source for slot mapping) + header_data = filter_log_events(log_path_0, HEADER_EVENT_FILTER) + + if not header_data: + print("\nNo header events found for slot/hash lookup. Exiting.") + sys.exit(0) + + # Create the header lookup DataFrame + df_headers_full = create_and_clean_df( + header_data, "0", "at_header_lookup", ["slot", "hash", "node"] + ) + + # Select only the necessary lookup columns and drop any entries where slot is still None + df_headers = ( + df_headers_full[["hash", "slot"]] + .dropna(subset=["slot"]) + .drop_duplicates(subset=["hash"], keep="first") + ) + print(f"Created Hash-to-Slot lookup table with {len(df_headers)} unique entries.") + + # --- STEP 2: Collect and Process Block Fetch Timestamps --- + + # Node 0 Block Fetch Data + raw_data_0 = filter_log_events(log_path_0, BLOCK_EVENT_FILTER) + df_node_0_block = create_and_clean_df( + raw_data_0, "0", "at_node_0", ["hash", "node"] + ) + + # Node 1 Block Fetch Data + raw_data_1 = filter_log_events(log_path_1, BLOCK_EVENT_FILTER) + df_node_1_block = create_and_clean_df( + raw_data_1, "1", "at_node_1", ["hash", "node"] + ) + + # --- STEP 3: Inject Slot Number into Block Fetch Data --- + + # Inject 'slot' into Node 0 data using 'hash' + df_node_0_final = pd.merge( + df_node_0_block[["hash", "at_node_0"]], df_headers, on="hash", how="inner" + ) + + # Inject 'slot' into Node 1 data using 'hash' + df_node_1_final = pd.merge( + df_node_1_block[["hash", "at_node_1"]], df_headers, on="hash", how="inner" + ) + + # --- STEP 4: Final Merge on Hash AND Slot --- + + if df_node_0_final.empty or df_node_1_final.empty: + print( + "\nCould not match block fetch times to slot numbers for one or both nodes. Exiting." + ) + sys.exit(0) + + # Final merge to compare the two nodes for the same block + df_merged = pd.merge( + df_node_0_final, + df_node_1_final, + on=["hash", "slot"], + how="inner", + ) + + # --- STEP 6: Calculate Slot Onset Time --- + print("\n--- Calculating Slot Onset Times ---") + print(f"Using base slot {initial_slot} at {initial_time} (1 slot = 1 second)") + try: + # Calculate the difference in slots (which equals seconds) + # We must ensure 'slot' is numeric, which create_and_clean_df should have done + df_merged["slot_diff_seconds"] = df_merged["slot"] - initial_slot + + # Convert the second difference into a timedelta and add to the initial time + df_merged["slot_onset"] = initial_time + pd.to_timedelta( + df_merged["slot_diff_seconds"], unit="s" + ) + + # Drop the intermediate calculation column + df_merged = df_merged.drop(columns=["slot_diff_seconds"]) + + except Exception as e: + print( + f"Error: Failed to calculate slot onset times. Check data types. Error: {e}", + file=sys.stderr, + ) + # Continue without onset time if calculation fails + pass + + # --- STEP 5: Calculate Latency (Time Difference) --- + df_merged["latency_ms"] = ( + df_merged["at_node_1"] - df_merged["slot_onset"] + ).dt.total_seconds() * 1000 + + # --- STEP 7: Calculate Diffs from Previous Slot --- + print("\n--- Calculating Diffs from Previous Slot ---") + + # Ensure dataframe is sorted by slot to calculate diffs correctly + df_merged = df_merged.sort_values(by="slot").reset_index(drop=True) + + # Calculate difference from the previous slot + df_merged["slot_diff_from_prev"] = df_merged["slot"].diff().fillna(0).astype(int) + + # Calculate difference from the previous slot's onset time (in seconds) + if "slot_onset" in df_merged.columns: + df_merged["onset_diff_from_prev_s"] = ( + df_merged["slot_onset"] + .diff() + .fillna(pd.Timedelta(seconds=0)) + .dt.total_seconds() + ) + else: + print( + "Warning: 'slot_onset' column not found. Skipping onset diff calculation." + ) + + # --- STEP 8: Generate Scatter Plot --- + # plot_onset_vs_arrival(df_merged, plot_output_file) + + print("\n--- Extracted and Merged Data Summary ---") + print( + "Each row represents a unique block seen by both nodes, joined by hash and slot." + ) + # Define desired column order, including the new 'slot_onset' and diffs + final_columns = [ + "slot", + "hash", + # "slot_onset", + # "at_node_0", + # "at_node_1", + "latency_ms", + # "slot_diff_from_prev", + # "onset_diff_from_prev_s", + ] + + # Filter list to only columns that actually exist in the dataframe + # This prevents an error if 'slot_onset' failed to be created + existing_columns = [col for col in final_columns if col in df_merged.columns] + + pd.set_option("display.max_columns", None) + pd.set_option("display.expand_frame_repr", False) + print(df_merged[existing_columns]) + print(f"\nTotal unique block events matched: {len(df_merged)}") diff --git a/demo/2025-10/build.nix b/demo/2025-10/build.nix new file mode 100644 index 000000000..b975b244d --- /dev/null +++ b/demo/2025-10/build.nix @@ -0,0 +1,89 @@ +{ + perSystem = + { pkgs, inputs', ... }: + { + packages = { + leios-empty-db = pkgs.stdenv.mkDerivation { + name = "leios-empty-db"; + src = ./.; + buildInputs = [ pkgs.sqlite ]; + buildPhase = '' + cat ${./leios-schema.sql} | sqlite3 $out; + ''; + }; + + leios-busy-db = pkgs.stdenv.mkDerivation { + src = ./.; + name = "leios-busy-db"; + buildInputs = [ + (inputs'.ouroboros-consensus.legacyPackages.hsPkgs.ouroboros-consensus.getComponent "exe:leiosdemo202510") + pkgs.jq + ]; + outputs = [ + "out" + "schedule" + ]; + buildPhase = '' + leiosdemo202510 generate leios.db ${./manifest.json} base-schedule.json + + # Make a schedule.json from the base-schedule.json such that the first number in each array is 182.9 + jq 'map(.[0] = 182.9)' base-schedule.json > schedule.json + + mv leios.db $out + mv schedule.json $schedule + ''; + }; + + leios-202510-demo = pkgs.writeShellApplication { + name = "leios-202510-demo"; + + runtimeInputs = [ + inputs'.cardano-node.packages.cardano-node + (inputs'.ouroboros-consensus.legacyPackages.hsPkgs.ouroboros-consensus-cardano.getComponent "exe:immdb-server") + (inputs'.ouroboros-consensus.legacyPackages.hsPkgs.ouroboros-consensus-cardano.getComponent "exe:db-analyser") + (inputs'.ouroboros-consensus.legacyPackages.hsPkgs.ouroboros-consensus.getComponent "exe:leiosdemo202510") + pkgs.toxiproxy + pkgs.sqlite + pkgs.jq + pkgs.procps + pkgs.coreutils + pkgs.gnused + pkgs.gnugrep + (pkgs.python3.withPackages ( + ps: with ps; [ + pandas + matplotlib + ] + )) + ]; + + text = '' + # Set default values for required environment variables + export SECONDS_UNTIL_REF_SLOT=''${SECONDS_UNTIL_REF_SLOT:-5} + export REF_SLOT=''${REF_SLOT:-41} + export CARDANO_NODE="${pkgs.lib.getExe inputs'.cardano-node.packages.cardano-node}" + export IMMDB_SERVER="${pkgs.lib.getExe (inputs'.ouroboros-consensus.legacyPackages.hsPkgs.ouroboros-consensus-cardano.getComponent "exe:immdb-server")}" + + # Copy demo files to a temporary directory + DEMO_DIR=$(mktemp -d) + trap 'rm -rf "$DEMO_DIR"' EXIT + + cp ${./run-demo.sh} "$DEMO_DIR/run-demo.sh" + cp ${./analyse.py} "$DEMO_DIR/analyse.py" + cp ${./leios-schema.sql} "$DEMO_DIR/leios-schema.sql" + cp ${./manifest.json} "$DEMO_DIR/manifest.json" + + # Copy cluster data to writable location + cp -r ${./data} "$DEMO_DIR/data" + chmod -R u+w "$DEMO_DIR/data" + export DATA="$DEMO_DIR/data" + + chmod +x "$DEMO_DIR/run-demo.sh" + + cd "$DEMO_DIR" + exec ./run-demo.sh "$@" + ''; + }; + }; + }; +} diff --git a/demo/2025-10/data/build.nix b/demo/2025-10/data/build.nix new file mode 100644 index 000000000..b5864533b --- /dev/null +++ b/demo/2025-10/data/build.nix @@ -0,0 +1,26 @@ +{ + perSystem = + { pkgs, ... }: + { + packages = { + genesis = pkgs.stdenv.mkDerivation { + name = "genesis"; + src = ./genesis; + buildPhase = '' + mkdir $out; + cp * $out; + ''; + }; + + immutable-db = pkgs.stdenv.mkDerivation { + name = "immutable-db"; + src = ./immdb-node/immutable; + buildPhase = '' + mkdir $out; + cp * $out; + ''; + }; + + }; + }; +} diff --git a/demo/2025-10/data/genesis/genesis.alonzo.json b/demo/2025-10/data/genesis/genesis.alonzo.json new file mode 100644 index 000000000..e13bd102b --- /dev/null +++ b/demo/2025-10/data/genesis/genesis.alonzo.json @@ -0,0 +1,188 @@ +{ + "collateralPercentage": 150, + "costModels": { + "PlutusV1": [ + 197209, + 0, + 1, + 1, + 396231, + 621, + 0, + 1, + 150000, + 1000, + 0, + 1, + 150000, + 32, + 2477736, + 29175, + 4, + 29773, + 100, + 29773, + 100, + 29773, + 100, + 29773, + 100, + 29773, + 100, + 29773, + 100, + 100, + 100, + 29773, + 100, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 150000, + 1000, + 0, + 1, + 150000, + 32, + 150000, + 1000, + 0, + 8, + 148000, + 425507, + 118, + 0, + 1, + 1, + 150000, + 1000, + 0, + 8, + 150000, + 112536, + 247, + 1, + 150000, + 10000, + 1, + 136542, + 1326, + 1, + 1000, + 150000, + 1000, + 1, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 1, + 1, + 150000, + 1, + 150000, + 4, + 103599, + 248, + 1, + 103599, + 248, + 1, + 145276, + 1366, + 1, + 179690, + 497, + 1, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 148000, + 425507, + 118, + 0, + 1, + 1, + 61516, + 11218, + 0, + 1, + 150000, + 32, + 148000, + 425507, + 118, + 0, + 1, + 1, + 148000, + 425507, + 118, + 0, + 1, + 1, + 2477736, + 29175, + 4, + 0, + 82363, + 4, + 150000, + 5000, + 0, + 1, + 150000, + 32, + 197209, + 0, + 1, + 1, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 3345831, + 1, + 1 + ] + }, + "executionPrices": { + "priceMemory": 0.0577, + "priceSteps": 0.0000721 + }, + "lovelacePerUTxOWord": 34482, + "maxBlockExUnits": { + "memory": 62000000, + "steps": 20000000000 + }, + "maxCollateralInputs": 3, + "maxTxExUnits": { + "memory": 14000000, + "steps": 10000000000 + }, + "maxValueSize": 5000 +} diff --git a/demo/2025-10/data/genesis/genesis.byron.json b/demo/2025-10/data/genesis/genesis.byron.json new file mode 100644 index 000000000..e2bf95e28 --- /dev/null +++ b/demo/2025-10/data/genesis/genesis.byron.json @@ -0,0 +1,42 @@ +{ "bootStakeholders": + { "a8f4fd08e2935ea584899dc306084595c4b9df394ea20dd855236a9d": 1 } +, "heavyDelegation": + { "a8f4fd08e2935ea584899dc306084595c4b9df394ea20dd855236a9d": + { "omega": 0 + , "issuerPk": + "JW5mw+Zo7XnJpBlqMnsrd+cfElAY8AFAWbQuF0+CqTQYgBz9eXza/EiY9sxugu/b6FwJW5fxe3rY83U7VFzEfg==" + , "delegatePk": + "zMajaA9h8Q6gUQ+y6VKHoj4Y1VBjlJyyS0v2eZn67RgNBOK63uxBdut6/1/kLaNMk+MuWB131W/abDCPs8b9og==" + , "cert": + "b12dd4d4d8c87a9af25fa6d5ee78a620573a6712fbeebfc45951d00bf4200a70cb6d4733cfddea576c4fd399e2fd6e2fd60d55f243bc6c8177ed599d699d6d06" + } } +, "startTime": 1759952614 +, "nonAvvmBalances": + { "2657WMsDfac5QzGGBef3oj7pwz4VwHCmNhkhLmN1SSs47qypuS7XQwFNCRVWansbi": + "30000" + , "2657WMsDfac6t6LUFkmDj8GCgJwUxNAPLMnionk3PbkLzVYHAiS7CpMGYUQjjhZQi": + "270000" + } +, "blockVersionData": + { "scriptVersion": 0 + , "slotDuration": "20000" + , "maxBlockSize": "641000" + , "maxHeaderSize": "200000" + , "maxTxSize": "4096" + , "maxProposalSize": "700" + , "mpcThd": "200000" + , "heavyDelThd": "300000" + , "updateVoteThd": "100000" + , "updateProposalThd": "100000" + , "updateImplicit": "10000" + , "softforkRule": + { "initThd": "900000" + , "minThd": "600000" + , "thdDecrement": "100000" + } + , "txFeePolicy": { "summand": "0" , "multiplier": "439460" } + , "unlockStakeEpoch": "184467" + } +, "protocolConsts": { "k": 3 , "protocolMagic": 42 } +, "avvmDistr": {} +} diff --git a/demo/2025-10/data/genesis/genesis.conway.json b/demo/2025-10/data/genesis/genesis.conway.json new file mode 100644 index 000000000..70f8103f3 --- /dev/null +++ b/demo/2025-10/data/genesis/genesis.conway.json @@ -0,0 +1,337 @@ +{ + "committee": { + "members": {}, + "threshold": 0 + }, + "committeeMaxTermLength": 146, + "committeeMinSize": 7, + "constitution": { + "anchor": { + "dataHash": "0000000000000000000000000000000000000000000000000000000000000000", + "url": "" + } + }, + "dRepActivity": 20, + "dRepDeposit": 500000000, + "dRepVotingThresholds": { + "committeeNoConfidence": 0.6, + "committeeNormal": 0.67, + "hardForkInitiation": 0.6, + "motionNoConfidence": 0.67, + "ppEconomicGroup": 0.67, + "ppGovGroup": 0.75, + "ppNetworkGroup": 0.67, + "ppTechnicalGroup": 0.67, + "treasuryWithdrawal": 0.67, + "updateToConstitution": 0.75 + }, + "govActionDeposit": 100000000000, + "govActionLifetime": 6, + "minFeeRefScriptCostPerByte": 15, + "plutusV3CostModel": [ + 100788, + 420, + 1, + 1, + 1000, + 173, + 0, + 1, + 1000, + 59957, + 4, + 1, + 11183, + 32, + 201305, + 8356, + 4, + 16000, + 100, + 16000, + 100, + 16000, + 100, + 16000, + 100, + 16000, + 100, + 16000, + 100, + 100, + 100, + 16000, + 100, + 94375, + 32, + 132994, + 32, + 61462, + 4, + 72010, + 178, + 0, + 1, + 22151, + 32, + 91189, + 769, + 4, + 2, + 85848, + 123203, + 7305, + -900, + 1716, + 549, + 57, + 85848, + 0, + 1, + 1, + 1000, + 42921, + 4, + 2, + 24548, + 29498, + 38, + 1, + 898148, + 27279, + 1, + 51775, + 558, + 1, + 39184, + 1000, + 60594, + 1, + 141895, + 32, + 83150, + 32, + 15299, + 32, + 76049, + 1, + 13169, + 4, + 22100, + 10, + 28999, + 74, + 1, + 28999, + 74, + 1, + 43285, + 552, + 1, + 44749, + 541, + 1, + 33852, + 32, + 68246, + 32, + 72362, + 32, + 7243, + 32, + 7391, + 32, + 11546, + 32, + 85848, + 123203, + 7305, + -900, + 1716, + 549, + 57, + 85848, + 0, + 1, + 90434, + 519, + 0, + 1, + 74433, + 32, + 85848, + 123203, + 7305, + -900, + 1716, + 549, + 57, + 85848, + 0, + 1, + 1, + 85848, + 123203, + 7305, + -900, + 1716, + 549, + 57, + 85848, + 0, + 1, + 955506, + 213312, + 0, + 2, + 270652, + 22588, + 4, + 1457325, + 64566, + 4, + 20467, + 1, + 4, + 0, + 141992, + 32, + 100788, + 420, + 1, + 1, + 81663, + 32, + 59498, + 32, + 20142, + 32, + 24588, + 32, + 20744, + 32, + 25933, + 32, + 24623, + 32, + 43053543, + 10, + 53384111, + 14333, + 10, + 43574283, + 26308, + 10, + 16000, + 100, + 16000, + 100, + 962335, + 18, + 2780678, + 6, + 442008, + 1, + 52538055, + 3756, + 18, + 267929, + 18, + 76433006, + 8868, + 18, + 52948122, + 18, + 1995836, + 36, + 3227919, + 12, + 901022, + 1, + 166917843, + 4307, + 36, + 284546, + 36, + 158221314, + 26549, + 36, + 74698472, + 36, + 333849714, + 1, + 254006273, + 72, + 2174038, + 72, + 2261318, + 64571, + 4, + 207616, + 8310, + 4, + 1293828, + 28716, + 63, + 0, + 1, + 1006041, + 43623, + 251, + 0, + 1, + 100181, + 726, + 719, + 0, + 1, + 100181, + 726, + 719, + 0, + 1, + 100181, + 726, + 719, + 0, + 1, + 107878, + 680, + 0, + 1, + 95336, + 1, + 281145, + 18848, + 0, + 1, + 180194, + 159, + 1, + 1, + 158519, + 8942, + 0, + 1, + 159378, + 8813, + 0, + 1, + 107490, + 3298, + 1, + 106057, + 655, + 1, + 1964219, + 24520, + 3 + ], + "poolVotingThresholds": { + "committeeNoConfidence": 0.51, + "committeeNormal": 0.51, + "hardForkInitiation": 0.51, + "motionNoConfidence": 0.51, + "ppSecurityGroup": 0.51 + } +} diff --git a/demo/2025-10/data/genesis/genesis.shelley.json b/demo/2025-10/data/genesis/genesis.shelley.json new file mode 100644 index 000000000..cd07b300b --- /dev/null +++ b/demo/2025-10/data/genesis/genesis.shelley.json @@ -0,0 +1,97 @@ +{ + "activeSlotsCoeff": 0.050, + "epochLength": 600, + "genDelegs": {}, + "initialFunds": { + "00635eef9a08f327a0ce009466914e8f607cebf76e9f4c9f92b0a829f4eab4c172777c708cd0bcac1a16d41b513e3a0f3dff8d182c2878947c": 900000000000000, + "00f00bb672d5d2f064707e6c955234da597e9b43ed6e458a3d15870a8257ef7aac3c0f6e4fbc3e253e3f4e58039986e89492c02c812e703d69": 900000000000000, + "601c6db4e8b6b36e265b9eecba0cb9a653cdd8701f708beccd911f838b": 9000000000000 + }, + "maxKESEvolutions": 62, + "maxLovelaceSupply": 2010000000000000, + "networkId": "Testnet", + "networkMagic": 42, + "protocolParams": { + "a0": 0.3, + "decentralisationParam": 0, + "eMax": 18, + "extraEntropy": { + "tag": "NeutralNonce" + }, + "keyDeposit": 2000000, + "maxBlockBodySize": 90112, + "maxBlockHeaderSize": 1100, + "maxTxSize": 16384, + "minFeeA": 44, + "minFeeB": 155381, + "minPoolCost": 340000000, + "minUTxOValue": 0, + "nOpt": 500, + "poolDeposit": 500000000, + "protocolVersion": { + "major": 10, + "minor": 0 + }, + "rho": 0.0030, + "tau": 0.2 + }, + "securityParam": 3, + "slotLength": 1, + "slotsPerKESPeriod": 129600, + "staking": { + "pools": { + "4c26da5ee3f61915d2df4167a53394b1f033623042a8d26ab7af5ef7": { + "cost": 0, + "margin": 0, + "metadata": null, + "owners": [], + "pledge": 0, + "publicKey": "4c26da5ee3f61915d2df4167a53394b1f033623042a8d26ab7af5ef7", + "relays": [ + { + "single host name": { + "dnsName": "node-0", + "port": 30000 + } + } + ], + "rewardAccount": { + "credential": { + "keyHash": "48d482deb658ae1aaa522a365e68f9747da98015500e1c260dca3c73" + }, + "network": "Testnet" + }, + "vrf": "03670fa208cb10b3452f04be890c931e4f34eff777dec589f1631d66c971c40c" + }, + "68b23036da5530e5853357a8dc9d03dd8e851b0e29a3eaf61b55b6cc": { + "cost": 0, + "margin": 0, + "metadata": null, + "owners": [], + "pledge": 0, + "publicKey": "68b23036da5530e5853357a8dc9d03dd8e851b0e29a3eaf61b55b6cc", + "relays": [ + { + "single host name": { + "dnsName": "node-1", + "port": 30001 + } + } + ], + "rewardAccount": { + "credential": { + "keyHash": "df587edcea6b53ed8bdc416be16f00beaaef18b5c6b25294275bf117" + }, + "network": "Testnet" + }, + "vrf": "0a570d439272a91eca089a9d04d9a94f11bb86c8daa3991fa67b35468049d60e" + } + }, + "stake": { + "57ef7aac3c0f6e4fbc3e253e3f4e58039986e89492c02c812e703d69": "4c26da5ee3f61915d2df4167a53394b1f033623042a8d26ab7af5ef7", + "eab4c172777c708cd0bcac1a16d41b513e3a0f3dff8d182c2878947c": "68b23036da5530e5853357a8dc9d03dd8e851b0e29a3eaf61b55b6cc" + } + }, + "systemStart": "2025-10-08T19:43:34Z", + "updateQuorum": 5 +} diff --git a/demo/2025-10/data/immdb-node/config.json b/demo/2025-10/data/immdb-node/config.json new file mode 100644 index 000000000..30d90eb9b --- /dev/null +++ b/demo/2025-10/data/immdb-node/config.json @@ -0,0 +1,279 @@ +{ + "AlonzoGenesisFile": "../genesis/genesis.alonzo.json", + "ByronGenesisFile": "../genesis/genesis.byron.json", + "ConwayGenesisFile": "../genesis/genesis.conway.json", + "ShelleyGenesisFile": "../genesis/genesis.shelley.json", + "ChainSyncIdleTimeout": 0, + "EnableP2P": true, + "ExperimentalHardForksEnabled": true, + "ExperimentalProtocolsEnabled": true, + "LastKnownBlockVersion-Alt": 0, + "LastKnownBlockVersion-Major": 3, + "LastKnownBlockVersion-Minor": 0, + "PeerSharing": false, + "Protocol": "Cardano", + "RequiresNetworkMagic": "RequiresMagic", + "SnapshotInterval": 4230, + "SyncTargetNumberOfActivePeers": 15, + "SyncTargetNumberOfEstablishedPeers": 40, + "TargetNumberOfActivePeers": 15, + "TargetNumberOfEstablishedPeers": 40, + "TestAllegraHardForkAtEpoch": 0, + "TestAlonzoHardForkAtEpoch": 0, + "TestBabbageHardForkAtEpoch": 0, + "TestConwayHardForkAtEpoch": 0, + "TestMaryHardForkAtEpoch": 0, + "TestShelleyHardForkAtEpoch": 0, + "TraceOptionForwarder": { + "connQueueSize": 64, + "disconnQueueSize": 128, + "maxReconnectDelay": 30 + }, + "TraceOptionMetricsPrefix": "cardano.node.metrics.", + "TraceOptionNodeName": "immdb-node", + "TraceOptionPeerFrequency": 2000, + "TraceOptionResourceFrequency": 1000, + "TraceOptions": { + "": { + "backends": [ + "Stdout MachineFormat", + "EKGBackend", + "Forwarder" + ], + "detail": "DNormal", + "severity": "Notice" + }, + "BlockFetch.Client": { + "severity": "Debug" + }, + "BlockFetch.Client.CompletedBlockFetch": { + "maxFrequency": 2.0 + }, + "BlockFetch.Decision": { + "severity": "Notice" + }, + "BlockFetch.Remote": { + "severity": "Notice" + }, + "BlockFetch.Remote.Serialised": { + "severity": "Notice" + }, + "BlockFetch.Server": { + "severity": "Debug" + }, + "BlockchainTime": { + "severity": "Notice" + }, + "ChainDB": { + "severity": "Debug" + }, + "ChainDB.AddBlockEvent.AddBlockValidation": { + "severity": "Silence" + }, + "ChainDB.AddBlockEvent.AddBlockValidation.ValidCandidate": { + "maxFrequency": 2.0 + }, + "ChainDB.AddBlockEvent.AddedBlockToQueue": { + "maxFrequency": 2.0 + }, + "ChainDB.AddBlockEvent.AddedBlockToVolatileDB": { + "maxFrequency": 2.0 + }, + "ChainDB.CopyToImmutableDBEvent.CopiedBlockToImmutableDB": { + "maxFrequency": 2.0 + }, + "ChainDB.LedgerEvent.Flavor.V1.OnDisk.BackingStoreEvent": { + "severity": "Silence" + }, + "ChainDB.LedgerEvent.Forker": { + "severity": "Silence" + }, + "ChainDB.ReplayBlock.LedgerReplay": { + "severity": "Notice" + }, + "ChainSync.Client": { + "severity": "Debug" + }, + "ChainSync.Local": { + "severity": "Notice" + }, + "ChainSync.Remote": { + "severity": "Notice" + }, + "ChainSync.Remote.Serialised": { + "severity": "Notice" + }, + "ChainSync.ServerBlock": { + "severity": "Notice" + }, + "ChainSync.ServerHeader": { + "severity": "Debug" + }, + "Consensus.GSM": { + "severity": "Info" + }, + "Forge.Loop": { + "severity": "Debug" + }, + "Forge.StateInfo": { + "severity": "Debug" + }, + "LedgerMetrics": { + "severity": "Info" + }, + "Mempool": { + "severity": "Debug" + }, + "Mempool.AttemptAdd": { + "severity": "Silence" + }, + "Mempool.LedgerFound": { + "severity": "Silence" + }, + "Mempool.LedgerNotFound": { + "severity": "Silence" + }, + "Mempool.SyncNotNeeded": { + "severity": "Silence" + }, + "Mempool.Synced": { + "severity": "Silence" + }, + "Net": { + "severity": "Notice" + }, + "Net.AcceptPolicy": { + "severity": "Debug" + }, + "Net.ConnectionManager.Local": { + "severity": "Debug" + }, + "Net.ConnectionManager.Remote": { + "severity": "Debug" + }, + "Net.ConnectionManager.Remote.ConnectionManagerCounters": { + "severity": "Silence" + }, + "Net.DNSResolver": { + "severity": "Notice" + }, + "Net.ErrorPolicy": { + "severity": "Info" + }, + "Net.ErrorPolicy.Local": { + "severity": "Debug" + }, + "Net.ErrorPolicy.Remote": { + "severity": "Debug" + }, + "Net.Handshake.Local": { + "severity": "Debug" + }, + "Net.Handshake.Remote": { + "severity": "Debug" + }, + "Net.InboundGovernor": { + "severity": "Warning" + }, + "Net.InboundGovernor.Local": { + "severity": "Debug" + }, + "Net.InboundGovernor.Remote": { + "severity": "Debug" + }, + "Net.InboundGovernor.Transition": { + "severity": "Debug" + }, + "Net.Mux.Local": { + "severity": "Notice" + }, + "Net.Mux.Remote": { + "severity": "Notice" + }, + "Net.PeerSelection": { + "severity": "Silence" + }, + "Net.PeerSelection.Actions": { + "severity": "Debug" + }, + "Net.PeerSelection.Counters": { + "detail": "DMinimal", + "severity": "Debug" + }, + "Net.PeerSelection.Initiator": { + "severity": "Notice" + }, + "Net.PeerSelection.Responder": { + "severity": "Notice" + }, + "Net.PeerSelection.Selection": { + "severity": "Debug" + }, + "Net.Peers.Ledger": { + "severity": "Debug" + }, + "Net.Peers.List": { + "severity": "Notice" + }, + "Net.Peers.LocalRoot": { + "severity": "Debug" + }, + "Net.Peers.PublicRoot": { + "severity": "Debug" + }, + "Net.Server.Local": { + "severity": "Debug" + }, + "Net.Server.Remote": { + "severity": "Debug" + }, + "Net.Subscription.DNS": { + "severity": "Debug" + }, + "Net.Subscription.IP": { + "severity": "Debug" + }, + "NodeState": { + "severity": "Notice" + }, + "Resources": { + "severity": "Debug" + }, + "Shutdown": { + "severity": "Notice" + }, + "Startup": { + "severity": "Notice" + }, + "Startup.DiffusionInit": { + "severity": "Debug" + }, + "StateQueryServer": { + "severity": "Notice" + }, + "TxSubmission.Local": { + "severity": "Notice" + }, + "TxSubmission.LocalServer": { + "severity": "Notice" + }, + "TxSubmission.MonitorClient": { + "severity": "Notice" + }, + "TxSubmission.Remote": { + "severity": "Notice" + }, + "TxSubmission.TxInbound": { + "severity": "Debug" + }, + "TxSubmission.TxOutbound": { + "severity": "Notice" + }, + "Version.NodeVersion": { + "severity": "Info" + } + }, + "TurnOnLogMetrics": true, + "TurnOnLogging": true, + "UseTraceDispatcher": true +} diff --git a/demo/2025-10/data/immdb-node/immutable/00000.chunk b/demo/2025-10/data/immdb-node/immutable/00000.chunk new file mode 100644 index 000000000..0b766c8ee Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00000.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00000.primary b/demo/2025-10/data/immdb-node/immutable/00000.primary new file mode 100644 index 000000000..9dffe10d0 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00000.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00000.secondary b/demo/2025-10/data/immdb-node/immutable/00000.secondary new file mode 100644 index 000000000..b6572daf2 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00000.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00001.chunk b/demo/2025-10/data/immdb-node/immutable/00001.chunk new file mode 100644 index 000000000..d38df30fe Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00001.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00001.primary b/demo/2025-10/data/immdb-node/immutable/00001.primary new file mode 100644 index 000000000..a37df378c Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00001.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00001.secondary b/demo/2025-10/data/immdb-node/immutable/00001.secondary new file mode 100644 index 000000000..8a8988e7d Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00001.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00002.chunk b/demo/2025-10/data/immdb-node/immutable/00002.chunk new file mode 100644 index 000000000..c621457ca Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00002.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00002.primary b/demo/2025-10/data/immdb-node/immutable/00002.primary new file mode 100644 index 000000000..3dd3ca8e9 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00002.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00002.secondary b/demo/2025-10/data/immdb-node/immutable/00002.secondary new file mode 100644 index 000000000..06acc09ac Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00002.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00003.chunk b/demo/2025-10/data/immdb-node/immutable/00003.chunk new file mode 100644 index 000000000..2016ff4c7 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00003.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00003.primary b/demo/2025-10/data/immdb-node/immutable/00003.primary new file mode 100644 index 000000000..31a0a654e Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00003.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00003.secondary b/demo/2025-10/data/immdb-node/immutable/00003.secondary new file mode 100644 index 000000000..b7e6e3e3c Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00003.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00004.chunk b/demo/2025-10/data/immdb-node/immutable/00004.chunk new file mode 100644 index 000000000..a5e1addf7 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00004.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00004.primary b/demo/2025-10/data/immdb-node/immutable/00004.primary new file mode 100644 index 000000000..6ca64bb57 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00004.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00004.secondary b/demo/2025-10/data/immdb-node/immutable/00004.secondary new file mode 100644 index 000000000..012a28138 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00004.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00005.chunk b/demo/2025-10/data/immdb-node/immutable/00005.chunk new file mode 100644 index 000000000..90e8154d3 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00005.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00005.primary b/demo/2025-10/data/immdb-node/immutable/00005.primary new file mode 100644 index 000000000..109ab6cb9 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00005.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00005.secondary b/demo/2025-10/data/immdb-node/immutable/00005.secondary new file mode 100644 index 000000000..e48e95f51 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00005.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00006.chunk b/demo/2025-10/data/immdb-node/immutable/00006.chunk new file mode 100644 index 000000000..205ba0688 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00006.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00006.primary b/demo/2025-10/data/immdb-node/immutable/00006.primary new file mode 100644 index 000000000..4394437a9 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00006.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00006.secondary b/demo/2025-10/data/immdb-node/immutable/00006.secondary new file mode 100644 index 000000000..63e547138 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00006.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00007.chunk b/demo/2025-10/data/immdb-node/immutable/00007.chunk new file mode 100644 index 000000000..dcb034716 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00007.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00007.primary b/demo/2025-10/data/immdb-node/immutable/00007.primary new file mode 100644 index 000000000..c8b6673f1 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00007.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00007.secondary b/demo/2025-10/data/immdb-node/immutable/00007.secondary new file mode 100644 index 000000000..64dda915a Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00007.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00008.chunk b/demo/2025-10/data/immdb-node/immutable/00008.chunk new file mode 100644 index 000000000..b28ee948c Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00008.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00008.primary b/demo/2025-10/data/immdb-node/immutable/00008.primary new file mode 100644 index 000000000..6e677301f Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00008.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00008.secondary b/demo/2025-10/data/immdb-node/immutable/00008.secondary new file mode 100644 index 000000000..9c60085f2 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00008.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00009.chunk b/demo/2025-10/data/immdb-node/immutable/00009.chunk new file mode 100644 index 000000000..7dec69aef Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00009.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00009.primary b/demo/2025-10/data/immdb-node/immutable/00009.primary new file mode 100644 index 000000000..35ef5387f Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00009.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00009.secondary b/demo/2025-10/data/immdb-node/immutable/00009.secondary new file mode 100644 index 000000000..9d0bf59ba Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00009.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00010.chunk b/demo/2025-10/data/immdb-node/immutable/00010.chunk new file mode 100644 index 000000000..b7a1377e1 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00010.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00010.primary b/demo/2025-10/data/immdb-node/immutable/00010.primary new file mode 100644 index 000000000..8708dcc33 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00010.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00010.secondary b/demo/2025-10/data/immdb-node/immutable/00010.secondary new file mode 100644 index 000000000..20b628ca4 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00010.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00011.chunk b/demo/2025-10/data/immdb-node/immutable/00011.chunk new file mode 100644 index 000000000..748e7d141 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00011.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00011.primary b/demo/2025-10/data/immdb-node/immutable/00011.primary new file mode 100644 index 000000000..2d580b899 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00011.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00011.secondary b/demo/2025-10/data/immdb-node/immutable/00011.secondary new file mode 100644 index 000000000..6a9c01a7d Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00011.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00012.chunk b/demo/2025-10/data/immdb-node/immutable/00012.chunk new file mode 100644 index 000000000..f3603b1c9 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00012.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00012.primary b/demo/2025-10/data/immdb-node/immutable/00012.primary new file mode 100644 index 000000000..7e672d383 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00012.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00012.secondary b/demo/2025-10/data/immdb-node/immutable/00012.secondary new file mode 100644 index 000000000..685cedd0b Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00012.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00013.chunk b/demo/2025-10/data/immdb-node/immutable/00013.chunk new file mode 100644 index 000000000..02a7f8317 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00013.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00013.primary b/demo/2025-10/data/immdb-node/immutable/00013.primary new file mode 100644 index 000000000..52b97f698 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00013.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00013.secondary b/demo/2025-10/data/immdb-node/immutable/00013.secondary new file mode 100644 index 000000000..6c6948284 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00013.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00014.chunk b/demo/2025-10/data/immdb-node/immutable/00014.chunk new file mode 100644 index 000000000..7301adec2 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00014.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00014.primary b/demo/2025-10/data/immdb-node/immutable/00014.primary new file mode 100644 index 000000000..bf89ed50d Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00014.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00014.secondary b/demo/2025-10/data/immdb-node/immutable/00014.secondary new file mode 100644 index 000000000..7a3ddbbdd Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00014.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00015.chunk b/demo/2025-10/data/immdb-node/immutable/00015.chunk new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-10/data/immdb-node/immutable/00015.primary b/demo/2025-10/data/immdb-node/immutable/00015.primary new file mode 100644 index 000000000..48e4f424b Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00015.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00015.secondary b/demo/2025-10/data/immdb-node/immutable/00015.secondary new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-10/data/immdb-node/immutable/00016.chunk b/demo/2025-10/data/immdb-node/immutable/00016.chunk new file mode 100644 index 000000000..422c3ca80 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00016.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00016.primary b/demo/2025-10/data/immdb-node/immutable/00016.primary new file mode 100644 index 000000000..51ba2b4ce Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00016.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00016.secondary b/demo/2025-10/data/immdb-node/immutable/00016.secondary new file mode 100644 index 000000000..4a371d489 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00016.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00017.chunk b/demo/2025-10/data/immdb-node/immutable/00017.chunk new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-10/data/immdb-node/immutable/00017.primary b/demo/2025-10/data/immdb-node/immutable/00017.primary new file mode 100644 index 000000000..48e4f424b Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00017.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00017.secondary b/demo/2025-10/data/immdb-node/immutable/00017.secondary new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-10/data/immdb-node/immutable/00018.chunk b/demo/2025-10/data/immdb-node/immutable/00018.chunk new file mode 100644 index 000000000..c2b08706b Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00018.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00018.primary b/demo/2025-10/data/immdb-node/immutable/00018.primary new file mode 100644 index 000000000..bb11205b2 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00018.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00018.secondary b/demo/2025-10/data/immdb-node/immutable/00018.secondary new file mode 100644 index 000000000..d0a247f15 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00018.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00019.chunk b/demo/2025-10/data/immdb-node/immutable/00019.chunk new file mode 100644 index 000000000..0e5a78254 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00019.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00019.primary b/demo/2025-10/data/immdb-node/immutable/00019.primary new file mode 100644 index 000000000..163f0d09a Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00019.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00019.secondary b/demo/2025-10/data/immdb-node/immutable/00019.secondary new file mode 100644 index 000000000..43a1b63d3 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00019.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00020.chunk b/demo/2025-10/data/immdb-node/immutable/00020.chunk new file mode 100644 index 000000000..86dc1f03e Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00020.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00020.primary b/demo/2025-10/data/immdb-node/immutable/00020.primary new file mode 100644 index 000000000..9dffe10d0 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00020.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00020.secondary b/demo/2025-10/data/immdb-node/immutable/00020.secondary new file mode 100644 index 000000000..6f9f4b5e3 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00020.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00021.chunk b/demo/2025-10/data/immdb-node/immutable/00021.chunk new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-10/data/immdb-node/immutable/00021.primary b/demo/2025-10/data/immdb-node/immutable/00021.primary new file mode 100644 index 000000000..48e4f424b Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00021.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00021.secondary b/demo/2025-10/data/immdb-node/immutable/00021.secondary new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-10/data/immdb-node/immutable/00022.chunk b/demo/2025-10/data/immdb-node/immutable/00022.chunk new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-10/data/immdb-node/immutable/00022.primary b/demo/2025-10/data/immdb-node/immutable/00022.primary new file mode 100644 index 000000000..48e4f424b Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00022.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00022.secondary b/demo/2025-10/data/immdb-node/immutable/00022.secondary new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-10/data/immdb-node/immutable/00023.chunk b/demo/2025-10/data/immdb-node/immutable/00023.chunk new file mode 100644 index 000000000..4c3ed055d Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00023.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00023.primary b/demo/2025-10/data/immdb-node/immutable/00023.primary new file mode 100644 index 000000000..3dd3ca8e9 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00023.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00023.secondary b/demo/2025-10/data/immdb-node/immutable/00023.secondary new file mode 100644 index 000000000..efe594a13 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00023.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00024.chunk b/demo/2025-10/data/immdb-node/immutable/00024.chunk new file mode 100644 index 000000000..53c872f6f Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00024.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00024.primary b/demo/2025-10/data/immdb-node/immutable/00024.primary new file mode 100644 index 000000000..0f3c16924 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00024.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00024.secondary b/demo/2025-10/data/immdb-node/immutable/00024.secondary new file mode 100644 index 000000000..65804de2f Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00024.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00025.chunk b/demo/2025-10/data/immdb-node/immutable/00025.chunk new file mode 100644 index 000000000..7ff8f1eaf Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00025.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00025.primary b/demo/2025-10/data/immdb-node/immutable/00025.primary new file mode 100644 index 000000000..b38afad2c Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00025.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00025.secondary b/demo/2025-10/data/immdb-node/immutable/00025.secondary new file mode 100644 index 000000000..654d5435c Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00025.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00026.chunk b/demo/2025-10/data/immdb-node/immutable/00026.chunk new file mode 100644 index 000000000..ec89ec932 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00026.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00026.primary b/demo/2025-10/data/immdb-node/immutable/00026.primary new file mode 100644 index 000000000..e142b3993 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00026.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00026.secondary b/demo/2025-10/data/immdb-node/immutable/00026.secondary new file mode 100644 index 000000000..615bafffe Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00026.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00027.chunk b/demo/2025-10/data/immdb-node/immutable/00027.chunk new file mode 100644 index 000000000..ec4d2a34d Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00027.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00027.primary b/demo/2025-10/data/immdb-node/immutable/00027.primary new file mode 100644 index 000000000..0cbb47687 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00027.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00027.secondary b/demo/2025-10/data/immdb-node/immutable/00027.secondary new file mode 100644 index 000000000..850d3070d Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00027.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00028.chunk b/demo/2025-10/data/immdb-node/immutable/00028.chunk new file mode 100644 index 000000000..e78a08bd6 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00028.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00028.primary b/demo/2025-10/data/immdb-node/immutable/00028.primary new file mode 100644 index 000000000..0ffe1bf25 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00028.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00028.secondary b/demo/2025-10/data/immdb-node/immutable/00028.secondary new file mode 100644 index 000000000..79862e0ca Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00028.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00029.chunk b/demo/2025-10/data/immdb-node/immutable/00029.chunk new file mode 100644 index 000000000..7d4eab3c1 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00029.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00029.primary b/demo/2025-10/data/immdb-node/immutable/00029.primary new file mode 100644 index 000000000..30f45b3e3 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00029.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00029.secondary b/demo/2025-10/data/immdb-node/immutable/00029.secondary new file mode 100644 index 000000000..8b674ff07 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00029.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00030.chunk b/demo/2025-10/data/immdb-node/immutable/00030.chunk new file mode 100644 index 000000000..0ccfdda5c Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00030.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00030.primary b/demo/2025-10/data/immdb-node/immutable/00030.primary new file mode 100644 index 000000000..6e677301f Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00030.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00030.secondary b/demo/2025-10/data/immdb-node/immutable/00030.secondary new file mode 100644 index 000000000..d1f503848 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00030.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00031.chunk b/demo/2025-10/data/immdb-node/immutable/00031.chunk new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-10/data/immdb-node/immutable/00031.primary b/demo/2025-10/data/immdb-node/immutable/00031.primary new file mode 100644 index 000000000..48e4f424b Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00031.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00031.secondary b/demo/2025-10/data/immdb-node/immutable/00031.secondary new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-10/data/immdb-node/immutable/00032.chunk b/demo/2025-10/data/immdb-node/immutable/00032.chunk new file mode 100644 index 000000000..5ae3066c4 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00032.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00032.primary b/demo/2025-10/data/immdb-node/immutable/00032.primary new file mode 100644 index 000000000..bf89ed50d Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00032.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00032.secondary b/demo/2025-10/data/immdb-node/immutable/00032.secondary new file mode 100644 index 000000000..2c083834c Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00032.secondary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00033.chunk b/demo/2025-10/data/immdb-node/immutable/00033.chunk new file mode 100644 index 000000000..2f88e7d00 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00033.chunk differ diff --git a/demo/2025-10/data/immdb-node/immutable/00033.primary b/demo/2025-10/data/immdb-node/immutable/00033.primary new file mode 100644 index 000000000..4c8c64f17 Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00033.primary differ diff --git a/demo/2025-10/data/immdb-node/immutable/00033.secondary b/demo/2025-10/data/immdb-node/immutable/00033.secondary new file mode 100644 index 000000000..ac158489b Binary files /dev/null and b/demo/2025-10/data/immdb-node/immutable/00033.secondary differ diff --git a/demo/2025-10/data/leios-node/config.json b/demo/2025-10/data/leios-node/config.json new file mode 100644 index 000000000..4784ce724 --- /dev/null +++ b/demo/2025-10/data/leios-node/config.json @@ -0,0 +1,277 @@ +{ + "AlonzoGenesisFile": "../genesis/genesis.alonzo.json", + "ByronGenesisFile": "../genesis/genesis.byron.json", + "ConwayGenesisFile": "../genesis/genesis.conway.json", + "ShelleyGenesisFile": "../genesis/genesis.shelley.json", + "ChainSyncIdleTimeout": 0, + "EnableP2P": true, + "ExperimentalHardForksEnabled": true, + "ExperimentalProtocolsEnabled": true, + "LastKnownBlockVersion-Alt": 0, + "LastKnownBlockVersion-Major": 3, + "LastKnownBlockVersion-Minor": 0, + "PeerSharing": false, + "Protocol": "Cardano", + "RequiresNetworkMagic": "RequiresMagic", + "SnapshotInterval": 4230, + "SyncTargetNumberOfActivePeers": 15, + "SyncTargetNumberOfEstablishedPeers": 40, + "TargetNumberOfActivePeers": 15, + "TargetNumberOfEstablishedPeers": 40, + "TestAllegraHardForkAtEpoch": 0, + "TestAlonzoHardForkAtEpoch": 0, + "TestBabbageHardForkAtEpoch": 0, + "TestConwayHardForkAtEpoch": 0, + "TestMaryHardForkAtEpoch": 0, + "TestShelleyHardForkAtEpoch": 0, + "TraceOptionForwarder": { + "connQueueSize": 64, + "disconnQueueSize": 128, + "maxReconnectDelay": 30 + }, + "TraceOptionMetricsPrefix": "cardano.node.metrics.", + "TraceOptionNodeName": "leios-node", + "TraceOptionPeerFrequency": 2000, + "TraceOptionResourceFrequency": 1000, + "TraceOptions": { + "": { + "backends": [ + "Stdout MachineFormat" + ], + "detail": "DNormal", + "severity": "Notice" + }, + "BlockFetch.Client": { + "severity": "Debug" + }, + "BlockFetch.Client.CompletedBlockFetch": { + "maxFrequency": 2.0 + }, + "BlockFetch.Decision": { + "severity": "Notice" + }, + "BlockFetch.Remote": { + "severity": "Notice" + }, + "BlockFetch.Remote.Serialised": { + "severity": "Notice" + }, + "BlockFetch.Server": { + "severity": "Debug" + }, + "BlockchainTime": { + "severity": "Notice" + }, + "ChainDB": { + "severity": "Debug" + }, + "ChainDB.AddBlockEvent.AddBlockValidation": { + "severity": "Silence" + }, + "ChainDB.AddBlockEvent.AddBlockValidation.ValidCandidate": { + "maxFrequency": 2.0 + }, + "ChainDB.AddBlockEvent.AddedBlockToQueue": { + "maxFrequency": 2.0 + }, + "ChainDB.AddBlockEvent.AddedBlockToVolatileDB": { + "maxFrequency": 2.0 + }, + "ChainDB.CopyToImmutableDBEvent.CopiedBlockToImmutableDB": { + "maxFrequency": 2.0 + }, + "ChainDB.LedgerEvent.Flavor.V1.OnDisk.BackingStoreEvent": { + "severity": "Silence" + }, + "ChainDB.LedgerEvent.Forker": { + "severity": "Silence" + }, + "ChainDB.ReplayBlock.LedgerReplay": { + "severity": "Notice" + }, + "ChainSync.Client": { + "severity": "Debug" + }, + "ChainSync.Local": { + "severity": "Notice" + }, + "ChainSync.Remote": { + "severity": "Notice" + }, + "ChainSync.Remote.Serialised": { + "severity": "Notice" + }, + "ChainSync.ServerBlock": { + "severity": "Notice" + }, + "ChainSync.ServerHeader": { + "severity": "Debug" + }, + "Consensus.GSM": { + "severity": "Info" + }, + "Forge.Loop": { + "severity": "Debug" + }, + "Forge.StateInfo": { + "severity": "Debug" + }, + "LedgerMetrics": { + "severity": "Info" + }, + "Mempool": { + "severity": "Debug" + }, + "Mempool.AttemptAdd": { + "severity": "Silence" + }, + "Mempool.LedgerFound": { + "severity": "Silence" + }, + "Mempool.LedgerNotFound": { + "severity": "Silence" + }, + "Mempool.SyncNotNeeded": { + "severity": "Silence" + }, + "Mempool.Synced": { + "severity": "Silence" + }, + "Net": { + "severity": "Notice" + }, + "Net.AcceptPolicy": { + "severity": "Debug" + }, + "Net.ConnectionManager.Local": { + "severity": "Debug" + }, + "Net.ConnectionManager.Remote": { + "severity": "Debug" + }, + "Net.ConnectionManager.Remote.ConnectionManagerCounters": { + "severity": "Silence" + }, + "Net.DNSResolver": { + "severity": "Notice" + }, + "Net.ErrorPolicy": { + "severity": "Info" + }, + "Net.ErrorPolicy.Local": { + "severity": "Debug" + }, + "Net.ErrorPolicy.Remote": { + "severity": "Debug" + }, + "Net.Handshake.Local": { + "severity": "Debug" + }, + "Net.Handshake.Remote": { + "severity": "Debug" + }, + "Net.InboundGovernor": { + "severity": "Warning" + }, + "Net.InboundGovernor.Local": { + "severity": "Debug" + }, + "Net.InboundGovernor.Remote": { + "severity": "Debug" + }, + "Net.InboundGovernor.Transition": { + "severity": "Debug" + }, + "Net.Mux.Local": { + "severity": "Notice" + }, + "Net.Mux.Remote": { + "severity": "Notice" + }, + "Net.PeerSelection": { + "severity": "Silence" + }, + "Net.PeerSelection.Actions": { + "severity": "Debug" + }, + "Net.PeerSelection.Counters": { + "detail": "DMinimal", + "severity": "Debug" + }, + "Net.PeerSelection.Initiator": { + "severity": "Notice" + }, + "Net.PeerSelection.Responder": { + "severity": "Notice" + }, + "Net.PeerSelection.Selection": { + "severity": "Debug" + }, + "Net.Peers.Ledger": { + "severity": "Debug" + }, + "Net.Peers.List": { + "severity": "Notice" + }, + "Net.Peers.LocalRoot": { + "severity": "Debug" + }, + "Net.Peers.PublicRoot": { + "severity": "Debug" + }, + "Net.Server.Local": { + "severity": "Debug" + }, + "Net.Server.Remote": { + "severity": "Debug" + }, + "Net.Subscription.DNS": { + "severity": "Debug" + }, + "Net.Subscription.IP": { + "severity": "Debug" + }, + "NodeState": { + "severity": "Notice" + }, + "Resources": { + "severity": "Debug" + }, + "Shutdown": { + "severity": "Notice" + }, + "Startup": { + "severity": "Notice" + }, + "Startup.DiffusionInit": { + "severity": "Debug" + }, + "StateQueryServer": { + "severity": "Notice" + }, + "TxSubmission.Local": { + "severity": "Notice" + }, + "TxSubmission.LocalServer": { + "severity": "Notice" + }, + "TxSubmission.MonitorClient": { + "severity": "Notice" + }, + "TxSubmission.Remote": { + "severity": "Notice" + }, + "TxSubmission.TxInbound": { + "severity": "Debug" + }, + "TxSubmission.TxOutbound": { + "severity": "Notice" + }, + "Version.NodeVersion": { + "severity": "Info" + } + }, + "TurnOnLogMetrics": true, + "TurnOnLogging": true, + "UseTraceDispatcher": true +} diff --git a/demo/2025-10/empty-schedule.json b/demo/2025-10/empty-schedule.json new file mode 100644 index 000000000..fe51488c7 --- /dev/null +++ b/demo/2025-10/empty-schedule.json @@ -0,0 +1 @@ +[] diff --git a/demo/2025-10/leios-schema.sql b/demo/2025-10/leios-schema.sql new file mode 100644 index 000000000..44e8c9746 --- /dev/null +++ b/demo/2025-10/leios-schema.sql @@ -0,0 +1,41 @@ +CREATE TABLE txCache ( + txHashBytes BLOB NOT NULL PRIMARY KEY -- raw bytes + , + txBytes BLOB NOT NULL -- valid CBOR + , + txBytesSize INTEGER NOT NULL + , + expiryUnixEpoch INTEGER NOT NULL + ) WITHOUT ROWID; +CREATE TABLE ebPoints ( + ebSlot INTEGER NOT NULL + , + ebHashBytes BLOB NOT NULL + , + ebId INTEGER NOT NULL + , + PRIMARY KEY (ebSlot, ebHashBytes) + ) WITHOUT ROWID; +CREATE TABLE ebTxs ( + ebId INTEGER NOT NULL -- foreign key ebPoints.ebId + , + txOffset INTEGER NOT NULL + , + txHashBytes BLOB NOT NULL -- raw bytes + , + txBytesSize INTEGER NOT NULL + , + txBytes BLOB -- valid CBOR + , + PRIMARY KEY (ebId, txOffset) + ) WITHOUT ROWID; +CREATE INDEX ebPointsExpiry + ON ebPoints (ebSlot ASC, ebId ASC); +CREATE INDEX txCacheExpiry + ON txCache (expiryUnixEpoch ASC, txHashBytes); +CREATE INDEX missingEbTxs + ON ebTxs (ebId DESC, txOffset ASC) + WHERE txBytes IS NULL; +CREATE INDEX acquiredEbTxs + ON ebTxs (ebId DESC, txOffset ASC) + WHERE txBytes IS NOT NULL; diff --git a/demo/2025-10/manifest.json b/demo/2025-10/manifest.json new file mode 100644 index 000000000..20e96f2f2 --- /dev/null +++ b/demo/2025-10/manifest.json @@ -0,0 +1,22 @@ +[ + {"slotNo": 0, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } + , + {"slotNo": 1, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } + , + {"slotNo": 2, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } + , + {"slotNo": 3, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } + , + {"slotNo": 4, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } + , + {"slotNo": 5, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } + , + {"slotNo": 6, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } + , + {"slotNo": 7, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } + , + {"slotNo": 8, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } + , + {"slotNo": 9, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } +] + diff --git a/demo/2025-10/run-demo.sh b/demo/2025-10/run-demo.sh new file mode 100755 index 000000000..5c11cbe73 --- /dev/null +++ b/demo/2025-10/run-demo.sh @@ -0,0 +1,277 @@ +set -e + +echo "Setup a temporary working directory leios-run-tmp-dir" +rm -fr ./leios-run-tmp-dir || true +TMP_DIR=$(mktemp -d "${TMPDIR:-/tmp}"/leios-october-demo.XXXXXX) +ln -s "$TMP_DIR" ./leios-run-tmp-dir + +echo "Generate the Leios DB and the schedules" +leiosdemo202510 generate "$TMP_DIR/upstream.db" manifest.json "$TMP_DIR/base-schedule.json" +# Make a schedule.json from the base-schedule.json such that the first number in each array is 182.9 +jq 'map(.[0] = 182.9)' "$TMP_DIR/base-schedule.json" > "$TMP_DIR/schedule.json" + + +if [[ ! "$SECONDS_UNTIL_REF_SLOT" =~ ^[0-9]*$ ]] || [[ "$SECONDS_UNTIL_REF_SLOT" -le 0 ]]; then + echo "Error: \${SECONDS_UNTIL_REF_SLOT} must be a positive integer of seconds, which will be added to the execution time of this script." >&2 + exit 1 +fi + +if [ ! -d "${DATA%/}" ]; then + DATA="${DATA%/}" + echo "Error: DATA directory '$DATA' not found or is not a directory." >&2 + exit 1 +fi + +if [[ -z "${CARDANO_NODE}" ]]; then + echo "Error: \${CARDANO_NODE} must be the path to the cardano-node exe." >&2 + exit 1 +fi + +if [[ -z "${IMMDB_SERVER}" ]]; then + echo "Error: \${IMMDB_SERVER} must be the path to the immdb-server exe." >&2 + exit 1 +fi + +if [[ -z "${REF_SLOT}" ]] || [[ ! "$REF_SLOT" =~ ^[0-9]*$ ]] || [[ "$REF_SLOT" -lt 0 ]]; then + echo "Error: \${REF_SLOT} must be a non-negative integer, a slot number" >&2 + exit 1 +fi + +now=$(date +%s) +ONSET_OF_REF_SLOT=$(( now + SECONDS_UNTIL_REF_SLOT )) +echo "REF_SLOT=$REF_SLOT" +echo "ONSET_OF_REF_SLOT=$ONSET_OF_REF_SLOT" +echo "$REF_SLOT" +echo "$ONSET_OF_REF_SLOT" + +# arbitrary choices + +PORT1=3001 +PORT2=3002 +PORT3=3003 + +TOXIPROXY=100 + +if pgrep -fx "toxiproxy-server" > /dev/null +then + echo "Toxiproxy is already running" +else + echo "Starting Toxiproxy" + toxiproxy-server 1> "$TMP_DIR/toxiproxy.log" 2>&1 & +fi + +# shellcheck disable=SC2329 +cleanup_proxy() { + toxiproxy-cli delete mocked-upstream-peer-proxy 2>/dev/null || true + toxiproxy-cli delete node0-proxy 2>/dev/null || true +} + +trap cleanup_proxy EXIT INT TERM + +# Clean up any existing proxies from previous runs +cleanup_proxy + +toxiproxy-cli create --listen 127.0.0.1:"$PORT1" --upstream 127.0.0.1:"$((TOXIPROXY + PORT1))" mocked-upstream-peer-proxy +toxiproxy-cli create --listen 127.0.0.1:"$PORT2" --upstream 127.0.0.1:"$((TOXIPROXY + PORT2))" node0-proxy + +for i in mocked-upstream-peer-proxy node0-proxy; do + # TODO magic numbers + toxiproxy-cli toxic add --type latency --attribute latency=150 --attribute jitter=30 $i # milliseconds + toxiproxy-cli toxic add --type bandwidth --attribute rate=2500 $i # kilobytes per second + # FYI, 125 kilobyte/s = 1 megabit/s, so EG 2500 kilobyte/s = 20 megabit/s +done + +echo "Ports: ${PORT1} ${PORT2} ${PORT3}, each plus ${TOXIPROXY} for toxiproxy" + + +## +## Run cardano-node (node-0) +## + +echo "Creating $TMP_DIR/topology-node-0.json" +cat << EOF > "$TMP_DIR/topology-node-0.json" +{ + "bootstrapPeers": [], + "localRoots": [ + { + "accessPoints": [ + { + "address": "127.0.0.1", + "port": ${PORT1} + } + ], + "advertise": false, + "trustable": true, + "valency": 1 + } + ], + "publicRoots": [] +} +EOF + +mkdir -p "$TMP_DIR/node-0/db" +cat leios-schema.sql | sqlite3 "$TMP_DIR/node-0/leios.db" + +env LEIOS_DB_PATH="$TMP_DIR/node-0/leios.db" \ + "$CARDANO_NODE" run \ + --config "$DATA/leios-node/config.json" \ + --topology "$TMP_DIR/topology-node-0.json" \ + --database-path "$TMP_DIR/node-0/db" \ + --socket-path "$TMP_DIR/node-0.socket" \ + --host-addr 127.0.0.1 --port $((TOXIPROXY + PORT2)) \ + &> "$TMP_DIR/cardano-node-0.log" & + +CARDANO_NODE_0_PID=$! + +echo "Cardano node 0 started with PID: $CARDANO_NODE_0_PID" + +## +## Run a second Cardano-node (To be eventually replaced by a mocked downstream node) +## + +cat << EOF > "$TMP_DIR/topology-node-1.json" +{ + "bootstrapPeers": [], + "localRoots": [ + { + "accessPoints": [ + { + "address": "127.0.0.1", + "port": ${PORT2} + } + ], + "advertise": false, + "trustable": true, + "valency": 1 + } + ], + "publicRoots": [] +} +EOF + +mkdir -p "$TMP_DIR/node-1/db" +cat leios-schema.sql | sqlite3 "$TMP_DIR/node-1/leios.db" + +env LEIOS_DB_PATH="$TMP_DIR/node-1/leios.db" \ + "$CARDANO_NODE" run \ + --config "$DATA/leios-node/config.json" \ + --topology "$TMP_DIR/topology-node-1.json" \ + --database-path "$TMP_DIR/node-1/db" \ + --socket-path "$TMP_DIR/node-1.socket" \ + --host-addr 127.0.0.1 --port "$PORT3" \ + &> "$TMP_DIR/cardano-node-1.log" & + +MOCKED_PEER_PID=$! + +echo "Cardano node 1 started with PID: $MOCKED_PEER_PID" + +## +## Run immdb-server +## + +"$IMMDB_SERVER" \ + --db "$DATA/immdb-node/immutable/" \ + --config "$DATA/immdb-node/config.json" \ + --initial-slot "$REF_SLOT" \ + --initial-time "$ONSET_OF_REF_SLOT" \ + --leios-schedule "$TMP_DIR/schedule.json" \ + --leios-db "$TMP_DIR/upstream.db" \ + --port $((TOXIPROXY + PORT1)) \ + &> "$TMP_DIR/immdb-server.log" & + +IMMDB_SERVER_PID=$! + +echo "ImmDB server started with PID: $IMMDB_SERVER_PID" + +# Wait briefly and check if immdb-server is still running +sleep 2 +if ! kill -0 "$IMMDB_SERVER_PID" 2>/dev/null; then + echo "ERROR: ImmDB server (PID $IMMDB_SERVER_PID) failed to start" >&2 + echo "Log output from $TMP_DIR/immdb-server.log:" >&2 + cat "$TMP_DIR/immdb-server.log" >&2 + kill "$CARDANO_NODE_0_PID" "$MOCKED_PEER_PID" 2>/dev/null || true + exit 1 +fi + +echo "All processes running successfully" + +TIMEOUT=25 +read -t $TIMEOUT -n 1 -s -r -p "Press any key to stop the spawned processes, or just wait $TIMEOUT seconds..." || true +echo + +echo "Killing processes $IMMDB_SERVER_PID (immdb-server), $CARDANO_NODE_0_PID (node-0), and $MOCKED_PEER_PID (node-1)..." + +kill "$IMMDB_SERVER_PID" 2>/dev/null || true +# Use negative PID to target the process group ID and SIGKILL for cardano-node processes. +kill "$CARDANO_NODE_0_PID" 2>/dev/null || true +kill "$MOCKED_PEER_PID" 2>/dev/null || true + +echo "Temporary data stored at: $TMP_DIR" + +# Database dumps + +echo +echo "=== Database Dumps ===" +echo + +echo "--- ImmDB Server (immutable db) ---" +db-analyser --db "$DATA/immdb-node/" --show-slot-block-no --v2-in-mem cardano --config "$DATA/immdb-node/config.json" > "$TMP_DIR/immdb-server-db-dump.txt" 2>&1 +echo "Saved to: $TMP_DIR/immdb-server-db-dump.txt" +echo + +echo "--- Node 0 (immutable db) ---" +if [ -d "$TMP_DIR/node-0/db/immutable" ]; then + db-analyser --db "$TMP_DIR/node-0/db/" --show-slot-block-no --v2-in-mem cardano --config "$DATA/leios-node/config.json" > "$TMP_DIR/node-0-db-dump.txt" 2>&1 + echo "Saved to: $TMP_DIR/node-0-db-dump.txt" +else + echo "No immutable db found at $TMP_DIR/node-0/db/immutable/" +fi +echo + +echo "--- Node 1 (immutable db) ---" +if [ -d "$TMP_DIR/node-1/db/immutable" ]; then + db-analyser --db "$TMP_DIR/node-1/db/" --show-slot-block-no --v2-in-mem cardano --config "$DATA/leios-node/config.json" > "$TMP_DIR/node-1-db-dump.txt" 2>&1 + echo "Saved to: $TMP_DIR/node-1-db-dump.txt" +else + echo "No immutable db found at $TMP_DIR/node-1/db/immutable/" +fi +echo + +echo "=== Leios SQLite Databases ===" +echo + +echo "--- Upstream Leios DB ---" +sqlite3 "$TMP_DIR/upstream.db" ".dump" > "$TMP_DIR/upstream-leios-db-dump.sql" +echo "Saved to: $TMP_DIR/upstream-leios-db-dump.sql" +echo + +echo "--- Node 0 Leios DB ---" +sqlite3 "$TMP_DIR/node-0/leios.db" ".dump" > "$TMP_DIR/node-0-leios-db-dump.sql" +echo "Saved to: $TMP_DIR/node-0-leios-db-dump.sql" +echo + +echo "--- Node 1 Leios DB ---" +sqlite3 "$TMP_DIR/node-1/leios.db" ".dump" > "$TMP_DIR/node-1-leios-db-dump.sql" +echo "Saved to: $TMP_DIR/node-1-leios-db-dump.sql" +echo + +# Log analysis + +cat "$TMP_DIR/cardano-node-0.log" | grep -v -i -e leios > "$TMP_DIR/logA" +cat "$TMP_DIR/cardano-node-1.log" | grep -v -i -e leios > "$TMP_DIR/logB" + +python3 analyse.py \ + "$REF_SLOT" "$ONSET_OF_REF_SLOT" \ + "$TMP_DIR/logA" "$TMP_DIR/logB" \ + "$TMP_DIR/scatter_plot.png" + +# Status + +echo +echo "Any processes still running:" +# shellcheck disable=SC2009 +ps aux | grep -e '[c]ardano-node' -e '[i]mmdb' | cut -c-180 + +echo "(Hopefully there were none!)" + +exit 0 diff --git a/demo/2025-11/.env b/demo/2025-11/.env new file mode 100644 index 000000000..a71c8e192 --- /dev/null +++ b/demo/2025-11/.env @@ -0,0 +1,13 @@ +WORKING_DIR=.tmp-leios-202511-demo + +DEF_CARDANO_NODE=cardano-node +DEF_IMMDB_SERVER=immdb-server +DEF_DATA_DIR=data +DEF_REF_SLOT=41 +DEF_SECONDS_UNTIL_REF_SLOT=5 +DEF_LEIOS_MANIFEST=manifest.json +DEF_ANALYSE_PY=analyse.py +DEF_PYTHON3=python +DEF_UPSTREAM_NODE_PORT=3001 +DEF_NODE0_PORT=3002 +DEF_DOWNSTREAM_NODE_PORT=3003 diff --git a/demo/2025-11/.envrc b/demo/2025-11/.envrc new file mode 100644 index 000000000..d6c9b14d0 --- /dev/null +++ b/demo/2025-11/.envrc @@ -0,0 +1 @@ +use flake .#dev-leios-202511-demo diff --git a/demo/2025-11/README.md b/demo/2025-11/README.md index 931249c8b..d8b3c728c 100644 --- a/demo/2025-11/README.md +++ b/demo/2025-11/README.md @@ -7,20 +7,20 @@ Slight improvement of the [October 2025 demonstration](../2025-10) using `tc` an - Observability/reporting/monitoring was improved. - Packaging of the prerequisites for executing the demo was improved. -![](./demo-2025-11.excalidraw.svg) +![Demo diagram](./demo-2025-11.excalidraw.svg) > [!TIP] > This is an excalidraw SVG with embedded scene so it can be loaded and edited in [https://excalidraw.com/]. ## Bufferbloat -The investigation into the unexpectedly high latency seen in October and related refinements to the prototype are apparent in the asynchronous conversation that took place in the comments on this tracking Issue https://github.com/IntersectMBO/ouroboros-consensus/issues/1756. +The investigation into the unexpectedly high latency seen in October and related refinements to the prototype are apparent in the asynchronous conversation that took place in the comments on a [tracking Issue](https://github.com/IntersectMBO/ouroboros-consensus/issues/1756). -- The latency was due to https://www.bufferbloat.net. +- The latency was due to a network phenomena called [bufferbloat](https://www.bufferbloat.net) In October, the bufferbloat arose directly from the naive use of [Toxiproxy](https://github.com/Shopify/toxiproxy) for the initial demo. - As user-space mechanism, Toxiproxy cannot introduce latency/rate/etc in a way that will influence the kernel algorithms managing the TCP stream. - [Linux Traffic Control](https://tldp.org/HOWTO/Traffic-Control-HOWTO/intro.html) is the approriate mechanism. -- An example of relevant commands for a more appropriate WAN (Wide Area Network) emulation can be found in this GitHub comment https://github.com/IntersectMBO/ouroboros-consensus/issues/1756#issuecomment-3587268042. +- An example of relevant commands for a more appropriate WAN (Wide Area Network) emulation can be found in [this GitHub comment](https://github.com/IntersectMBO/ouroboros-consensus/issues/1756#issuecomment-3587268042). - `htb rate 100mbt` limts the sender's bandwidth. - `fq_codel` paces the sender's traffic, adapting to any bottleneck between it and the recipient. - `netem delay` established the link latency of 20ms between `fq_codel` and the recipient. @@ -58,7 +58,7 @@ No other packages have yet been patched for this demo, the appropriate versions Beware that the listed commits do not already include `source-repository-package` stanzas in their `cabal.project` files, if that's the contributor's chosen method for cross-repo dependencies. -``` +```shell $ for i in ouroboros-consensus ouroboros-network cardano-node; do (cd $i; echo REPO $i; git log -1); done REPO ouroboros-consensus commit 7929c3716a18abb852f8abec7111c78f2059287e (HEAD -> nfrisby/leios-202511-demo, origin/nfrisby/leios-202511-demo) diff --git a/demo/2025-11/analyse.py b/demo/2025-11/analyse.py new file mode 100644 index 000000000..b31f01927 --- /dev/null +++ b/demo/2025-11/analyse.py @@ -0,0 +1,794 @@ +import os +import sys +import json +import pandas as pd +import matplotlib.pyplot as plt + +# --- Configuration --- +# Filter for the event containing the timestamp we want to measure at node0 and downstream +BLOCK_EVENT_FILTER = "BlockFetch.Client.CompletedBlockFetch" +# Filter for the event containing the slot and hash. We need to do this because the 'CompletedBlockFetch' event does not contain the slot number. +HEADER_EVENT_FILTER = "ChainSync.Client.DownloadedHeader" + +# Filter for the event containing the timestamp we want to measure at node0 and downstream +LEIOS_EVENT_FILTER = "Consensus.LeiosKernel" + +LEIOS_BLOCK_EVENT_SUBFILTER = "LeiosBlockAcquired" +LEIOS_BLOCKTXS_EVENT_SUBFILTER = "LeiosBlockTxsAcquired" + + +def filter_log_events(log_path: str, filter_text: str, subfilter_text: str = ""): + """ + Reads a log file, parses JSON lines, and extracts relevant fields + based on the filter type. + """ + log_filename = os.path.basename(log_path) + print(f"\n--- Analyzing Log: {log_filename} for event: '{filter_text}' ---") + + records = [] + + try: + with open(log_path, "r") as f: + for line in f: + try: + pc_log_entry = json.loads(line) + log_entry = json.loads(pc_log_entry["message"]) + + # Check if the namespace matches the filter + if log_entry.get("ns") == filter_text: + + event_data = log_entry.get("data", {}) + block_hash = None + block_slot = None + + # Determine extraction logic based on the event type + if filter_text == HEADER_EVENT_FILTER: + # Structure: "data":{"block": "HASH", ..., "slot": SLOT} + block_hash = event_data.get("block") + block_slot = event_data.get("slot") + elif filter_text == BLOCK_EVENT_FILTER: + # Structure: "data":{"block": "HASH", ...} + block_hash = event_data.get("block") + block_slot = None + elif filter_text == LEIOS_EVENT_FILTER: + # Structure: "data":{"kind": "LeiosBlockTxsAcquired", "ebHash": "HASH", "ebSlot": "SLOT"} + if subfilter_text != event_data.get("kind", "XXXXXXXX"): + continue + block_hash = event_data.get("ebHash") + block_slot = None # event_data.get("ebSlot") # slot comes from schedule.json + + # Base record structure + record = { + "at": log_entry.get("at"), + "hash": block_hash, + "slot": block_slot, + } + + # Only add if the core fields were successfully extracted + if record["at"] and record["hash"]: + records.append(record) + + except json.JSONDecodeError: + # Some log lines are not JSON; we simply skip those + continue + except (TypeError, KeyError): + # TypeError: message field is not a string (e.g., integer like 3002) + # KeyError: message field doesn't exist or other required field missing + continue + except Exception: + # Catch any other unexpected errors (e.g., AttributeError when message is not a dict) + # and continue processing the rest of the log + continue + + return records + + except Exception: + print( + f"An unexpected error occurred while processing {log_path}", file=sys.stderr + ) + raise + + +def create_and_clean_df(records: list, node_id: str) -> pd.DataFrame: + """ + Converts records to a DataFrame, converts types and removes duplicates. + """ + # Return an empty DataFrame with the expected columns if no records were found. + if not records: + return pd.DataFrame(columns=["hash", "slot", "at"]) + + df = pd.DataFrame(records) + + # Convert columns to appropriate data types + try: + df["at"] = pd.to_datetime(df["at"]) + if "slot" in df.columns: + df["slot"] = pd.to_numeric(df["slot"], errors="coerce").astype("Int64") + except Exception as e: + print( + f"Warning: Failed to convert data types in DataFrame for node {node_id}: {e}", + file=sys.stderr, + ) + raise + + # Deduplication: Keep only the first (earliest) occurrence + initial_rows = len(df) + df = df.sort_values(by="at").drop_duplicates(subset=["hash"], keep="first") + + if len(df) < initial_rows: + duplicates_removed = initial_rows - len(df) + print( + f"Warning: Removed {duplicates_removed} duplicate log entries from node {node_id}.", + file=sys.stderr, + ) + + return df + + +def load_block_arrivals(df_headers: pd.DataFrame, log_path: str, node_id: str): + """ + Loads the hash arrival times at the node of the given log file. + """ + raw_data = filter_log_events(log_path, BLOCK_EVENT_FILTER) + df = create_and_clean_df(raw_data, node_id)[["hash", "at"]] + + # add slot column + df = pd.merge(df, df_headers, on="hash", how="left") + + if df["slot"].isna().any(): + print( + f"Error: {node_id} downloaded somes blocks with unknown slot.", + file=sys.stderr, + ) + print( + df[df["slot"].isnull()], + file=sys.stderr, + ) + raise + + # Use 'Int64' to allow NaNs; see https://stackoverflow.com/a/54194908 + df["latency_ms"] = ( + ((df["at"] - df["slot_onset"]).dt.total_seconds() * 1000) + .round(0) + .astype("Int64") + ) + + return df + + +def load_leios_block_arrivals( + df_schedule: pd.DataFrame, log_path: str, node_id: str, subfilter: str +): + """ + Loads the hash arrival times for Leios blocks at the node of the given log file. + """ + raw_data = filter_log_events(log_path, LEIOS_EVENT_FILTER, subfilter) + df = create_and_clean_df(raw_data, node_id)[["hash", "at"]] + + # add slot column + df = pd.merge(df, df_schedule, on="hash", how="left") + + if df["offer_slot"].isna().any(): + print( + f"Error: {node_id} downloaded somes Leios blocks with unknown offer slot.", + file=sys.stderr, + ) + print( + df[df["offer_slot"].isnull()], + file=sys.stderr, + ) + raise + + if df.empty: + df["latency_ms"] = None + return df + + # Use 'Int64' to allow NaNs; see https://stackoverflow.com/a/54194908 + df["latency_ms"] = ( + ((df["at"] - df["offer"]).dt.total_seconds() * 1000).round(0).astype("Int64") + ) + + return df + + +def plot_onset_vs_arrival(df: pd.DataFrame, output_file: str = None): + """ + Generates and displays a scatter plot of slot_onset vs. at_downstream. + If output_file is provided, saves the plot to that file. + """ + print("\n--- Generating Scatter Plot ---") + try: + if "slot_onset" in df.columns and "at_downstream" in df.columns: + # Ensure both columns are datetime objects for plotting + df["slot_onset"] = pd.to_datetime(df["slot_onset"]) + df["at_downstream"] = pd.to_datetime(df["at_downstream"]) + + plt.figure(figsize=(10, 6)) + plt.scatter(df["slot_onset"], df["at_downstream"], alpha=0.5, s=10) + + # Add a y=x reference line + # Find common min/max for a good 1:1 line + all_times = pd.concat([df["slot_onset"], df["at_downstream"]]) + min_time = all_times.min() + max_time = all_times.max() + plt.plot( + [min_time, max_time], + [min_time, max_time], + "r--", + label="1:1 Line (Onset = Arrival)", + ) + + plt.title("Block Arrival Time (downstream) vs. Slot Onset Time") + plt.xlabel("Slot Onset Time (Calculated)") + plt.ylabel("Block Arrival Time (at_downstream)") + plt.grid(True, linestyle="--", alpha=0.6) + plt.legend() + plt.tight_layout() + + # Rotate x-axis labels for better readability + plt.xticks(rotation=45) + + if output_file: + plt.savefig(output_file, bbox_inches="tight") + print(f"Plot saved to {output_file}") + else: + print("Displaying plot...") + plt.show() + + plt.close(plt.gcf()) # Close the figure to free memory + + else: + print( + "Warning: 'slot_onset' or 'at_downstream' column not found. Skipping plot generation." + ) + + except ImportError: + print( + "\n--- Plotting Skipped ---", + file=sys.stderr, + ) + print( + "To generate the plot, please install matplotlib: pip install matplotlib", + file=sys.stderr, + ) + except Exception as e: + print( + f"Error: Failed to generate plot. Error: {e}", + file=sys.stderr, + ) + + +################################################################################ + +empty_sendrecv = pd.DataFrame( + columns=["at", "mux_at", "connection_id", "direction", "msg", "prevCount"] +) + +msgs_SendRecv = set( + [ + "MsgRollForward", + "MsgBlock", + "MsgRequestRange", + "MsgBlock", + "MsgLeiosBlockRequest", + "MsgLeiosBlock", + "MsgLeiosBlockTxsRequest", + "MsgLeiosBlockTxs", + ] +) + +nss_cardano_node_SendRecv = set( + [ + "LeiosFetch.Remote." + direction + "." + msg + for direction in ["Send", "Receive"] + for msg in ["BlockRequest", "Block", "BlockTxsRequest", "BlockTxs"] + ] + + [ + "ChainSync.Remote" + dotSerialised + "." + direction + ".RollForward" + for direction in ["Send", "Receive"] + for dotSerialised in ["", ".Serialised"] + ] + + [ + "BlockFetch.Remote" + dotSerialised + "." + direction + "." + msg + for direction in ["Send", "Receive"] + for dotSerialised in ["", ".Serialised"] + for msg in ["Block", "RequestRange"] + ] +) + + +def load_sendrecv_upstream(log_path: str): + """ + Reads a log file, parses JSON lines, and extracts relevant fields + for the upstream node. + """ + log_filename = os.path.basename(log_path) + print(f"\n--- Analyzing Log: {log_filename} for Leios SendRecvs ---") + + records = [] + + try: + with open(log_path, "r") as f: + n = 0 + for line in f: + n = n + 1 + try: + pc_log_entry = json.loads(line) + log_entry = json.loads(pc_log_entry["message"]) + record = { + "at": log_entry["at"], + "mux_at": log_entry["mux_at"], + "connection_id": log_entry["connectionId"], + "direction": log_entry["direction"], + "msg": str(log_entry["msg"]), + "prevCount": log_entry["prevCount"], + } + if record["msg"] not in msgs_SendRecv: + continue + except json.JSONDecodeError: + # Some log lines are not JSON; we simply skip those + continue + except KeyError: + # Some JSON lines are not SendRecv; we simply skip those + continue + except Exception: + # Skip lines that can't be parsed (e.g., process-compose noise) + continue + records.append(record) + + return pd.DataFrame(records) if records else empty_sendrecv + + except Exception: + print(f"While processing {log_path}", file=sys.stderr) + raise + + +def load_sendrecv_node(log_path: str): + """ + Reads a log file, parses JSON lines, and extracts relevant fields + for a cardano-node. + """ + log_filename = os.path.basename(log_path) + print(f"\n--- Analyzing Log: {log_filename} for Leios SendRecvs: ---") + + records = [] + + try: + with open(log_path, "r") as f: + n = 0 + cntrs = {} + for line in f: + n = n + 1 + try: + pc_log_entry = json.loads(line) + log_entry = json.loads(pc_log_entry["message"]) + if log_entry.get("ns", None) not in nss_cardano_node_SendRecv: + # Some JSON lines are not SendRecv; we simply skip those + continue + connection_id = log_entry["data"]["peer"]["connectionId"] + direction = log_entry["data"]["kind"] + msg = str(log_entry["data"]["msg"]["kind"]) + + prevCount = cntrs.get((direction, msg, connection_id), 0) + cntrs[(direction, msg, connection_id)] = prevCount + 1 + + record = { + "at": log_entry["at"], + "mux_at": log_entry["data"]["mux_at"], + "connection_id": connection_id, + "direction": direction, + "msg": msg, + "prevCount": prevCount, + } + if record["msg"] not in msgs_SendRecv: + continue + except json.JSONDecodeError: + # Some log lines are not JSON; we simply skip those + continue + except Exception: + # Skip lines that can't be parsed (e.g., process-compose noise) + continue + records.append(record) + + return pd.DataFrame(records) if records else empty_sendrecv + + except Exception: + print(f"While processing {log_path}", file=sys.stderr) + raise + + +def noFlip(x): + return x + + +def flipDirection(s: str): + if "Recv" == s: + return "Send" + elif "Send" == s: + return "Recv" + else: + raise ValueError + + +def flipConnectionId(s: str): + left, right = s.split() + return right + " " + left + + +flips = { + "connection_id": lambda x: x.apply(flipConnectionId), + "direction": lambda x: x.apply(flipDirection), +} + + +def join_sendrecv( + left_connId: str, left_id: str, left: pd.DataFrame, rite_id: str, rite: pd.DataFrame +): + df = pd.merge( + left[left["connection_id"] == left_connId], + rite[rite["connection_id"] == flipConnectionId(left_connId)].apply( + lambda x: flips.get(x.name, noFlip)(x) + ), + suffixes=["_" + left_id, "_" + rite_id], + on=["msg", "connection_id", "direction", "prevCount"], + how="outer", + ).drop(columns=["connection_id"]) + + df["push_at"] = None + df["send_at"] = None + df["recv_at"] = None + df["pull_at"] = None + # df.["push_at"][df["direction"] == "Send"] = df["at_" + left_id], but avoiding Copy-on-Write pitfalls + df.loc[df["direction"] == "Send", "send_at"] = df["at_" + left_id] + df.loc[df["direction"] == "Send", "push_at"] = df["mux_at_" + left_id] + df.loc[df["direction"] == "Send", "recv_at"] = df["mux_at_" + rite_id] + df.loc[df["direction"] == "Send", "pull_at"] = df["at_" + rite_id] + df.loc[df["direction"] == "Recv", "send_at"] = df["at_" + rite_id] + df.loc[df["direction"] == "Recv", "push_at"] = df["mux_at_" + rite_id] + df.loc[df["direction"] == "Recv", "recv_at"] = df["mux_at_" + left_id] + df.loc[df["direction"] == "Recv", "pull_at"] = df["at_" + left_id] + + df = df.drop(columns=["at_" + left_id, "at_" + rite_id]) + + df.loc[df["direction"] == "Recv", "dir"] = "<- " + df.loc[df["direction"] == "Send", "dir"] = " ->" + + df = ( + df.drop(columns=["direction"]) + .sort_values(by=["push_at"]) + .reset_index(drop=True) + ) + + df["send_latency_ms"] = ( + ( + abs( + pd.to_datetime(df["send_at"], utc=True) + - pd.to_datetime(df["push_at"], utc=True) + ).dt.total_seconds() + * 1000 + ) + .round(0) + .astype("Int64") + ) + df["transport_latency_ms"] = ( + ( + abs( + pd.to_datetime(df["recv_at"], utc=True) + - pd.to_datetime(df["send_at"], utc=True) + ).dt.total_seconds() + * 1000 + ) + .round(0) + .astype("Int64") + ) + df["recv_latency_ms"] = ( + ( + abs( + pd.to_datetime(df["pull_at"], utc=True) + - pd.to_datetime(df["recv_at"], utc=True) + ).dt.total_seconds() + * 1000 + ) + .round(0) + .astype("Int64") + ) + df["latency_ms"] = ( + ( + abs( + pd.to_datetime(df["pull_at"], utc=True) + - pd.to_datetime(df["push_at"], utc=True) + ).dt.total_seconds() + * 1000 + ) + .round(0) + .astype("Int64") + ) + + return df + + +################################################################################ + + +def subscriptOrNone(xs, i): + return xs[i] if i < len(xs) else None + + +if __name__ == "__main__": + # --- Argument Parsing --- + try: + initial_slot_str = sys.argv[1] + initial_time_str = sys.argv[2] + eb_schedule_path = sys.argv[3] + log_path_upstream = sys.argv[4] + log_path_node0 = sys.argv[5] + log_path_downstream = sys.argv[6] + plot_output_file = subscriptOrNone(sys.argv, 7) + except IndexError: + print( + "Configuration Error: Please provide initial-slot, initial-time, EB sending schedule, three log files, and optionally an output plot file.", + file=sys.stderr, + ) + print( + "Example Usage: python log_parser.py demoSchedule.json /path/to/upstream.log /path/to/node0.log /path/to/downstream.log [output_plot.png]", + file=sys.stderr, + ) + sys.exit(1) + + try: + initial_slot = int(initial_slot_str) + except ValueError: + print( + f"Configuration Error: Could not parse initial-slot '{initial_slot_str}' as an integer.", + file=sys.stderr, + ) + sys.exit(1) + + # Try to parse as a POSIX timestamp (integer string) or else as a datetime string + try: + try: + posix_time = int(initial_time_str) + # Convert from POSIX seconds to a UTC datetime object + initial_time = pd.to_datetime(posix_time, unit="s", utc=True) + print( + f"Note: Interpreted initial-time '{initial_time_str}' as POSIX timestamp (UTC)." + ) + except ValueError: + # If not an integer, try to parse as a standard datetime string + initial_time = pd.to_datetime(initial_time_str) + # If the provided string has no timezone, assume UTC for consistency + if initial_time.tzinfo is None: + initial_time = initial_time.tz_localize("UTC") + print( + f"Note: Interpreted initial-time '{initial_time_str}' as datetime string (assuming UTC)." + ) + else: + # If it has a timezone, convert it to UTC for consistency + initial_time = initial_time.tz_convert("UTC") + except Exception as e: + print( + f"Configuration Error: Could not parse initial-time '{initial_time_str}' as either a POSIX timestamp or a datetime string. Error: {e}", + file=sys.stderr, + ) + sys.exit(1) + + print("\n--- Initial Configuration ---") + print(f"Initial Slot: {initial_slot}") + print(f"Initial Time: {initial_time}") + print(f"node0 Log File: {log_path_node0}") + print(f"downstream Log File: {log_path_downstream}") + if plot_output_file: + print(f"Plot Output File: {plot_output_file}") + + # Collect header data + # + # node0 log suffices, since downstream only has a header if node0 does. + header_data = filter_log_events(log_path_node0, HEADER_EVENT_FILTER) + + if not header_data: + print("\nNo header events found for slot/hash lookup. Exiting.") + sys.exit(0) + + # Create the header lookup DataFrame + # + # Retain only the hash and slot columns and only if slot isn't None + df_headers = ( + create_and_clean_df(header_data, "node0")[["hash", "slot"]] + .dropna(subset=["slot"]) + .drop_duplicates(subset=["hash"], keep="first") + ) + + print(f"Created Hash-to-Slot lookup table with {len(df_headers)} unique entries.") + + try: + # Calculate the difference in slots (where 1 slot happens to be 1 second) + slot_diff_seconds = df_headers["slot"] - initial_slot + + # Convert the second difference into a timedelta and add to the initial time + df_headers["slot_onset"] = initial_time + pd.to_timedelta( + slot_diff_seconds, unit="s" + ) + except Exception: + print("Error: Failed to calculate slot onset times.", file=sys.stderr) + raise + + df_node0 = load_block_arrivals(df_headers, log_path_node0, "node0") + df_downstream = load_block_arrivals(df_headers, log_path_downstream, "downstream") + + if df_node0.empty or df_downstream.empty: + print( + "\nCould not match block fetch times to slot numbers for one or both nodes. Exiting." + ) + sys.exit(0) + + # We also merge on "slot_onset" to retain it. It's a function of "slot", so + # this is harmless. + df_merged = pd.merge( + df_node0, + df_downstream, + suffixes=["_node0", "_downstream"], + on=[ + "slot", + "slot_onset", + "hash", + ], # note that this determines order of resulting rows + how="outer", + ) + + # plot_onset_vs_arrival(df_merged, plot_output_file) + + print("\n--- Extracted and Merged Data Summary ---") + print( + "Each row represents a unique Praos block seen by both nodes, joined by hash and slot." + ) + # Which columns to display + display_columns = [ + "slot", + "hash", + "slot_onset", + "latency_ms_node0", + "latency_ms_downstream", + ] + + pd.set_option("display.max_columns", None) + pd.set_option("display.max_rows", None) + pd.set_option("display.expand_frame_repr", False) + print(df_merged[display_columns]) + + # ---------------------------------------- again, for Leios messages + + # Create the schedule lookup DataFrame + with open(eb_schedule_path) as f: + schedule_json = json.load(f) + + # only the MsgLeiosBlockTxsOffer messages + df_schedule = pd.DataFrame( + [(x[0], x[1][1]) for x in schedule_json if x[1][2] is None], + columns=["offer_slot", "hash"], + ) + + print(f"Created Hash-to-Offer lookup table with {len(df_schedule)} unique entries.") + + try: + # Calculate the difference in slots (where 1 slot happens to be 1 second) + slot_diff_seconds = df_schedule["offer_slot"] - initial_slot + + # Convert the second difference into a timedelta and add to the initial time + df_schedule["offer"] = initial_time + pd.to_timedelta( + slot_diff_seconds, unit="s" + ) + except Exception: + print("Error: Failed to calculate offer times.", file=sys.stderr) + raise + + df_leios_block_node0 = load_leios_block_arrivals( + df_schedule, log_path_node0, "node0", LEIOS_BLOCK_EVENT_SUBFILTER + ) + df_leios_block_downstream = load_leios_block_arrivals( + df_schedule, log_path_downstream, "downstream", LEIOS_BLOCK_EVENT_SUBFILTER + ) + + # We also merge on "slot_onset" to retain it. It's a function of "slot", so + # this is harmless. + df_leios_block_merged = pd.merge( + df_leios_block_node0, + df_leios_block_downstream, + suffixes=["_node0", "_downstream"], + on=[ + "offer_slot", + "offer", + "hash", + ], # note that this determines order of resulting rows + how="outer", + ) + + print("\n--- Extracted and Merged Data Summary for Leios blocks ---") + print( + "Each row represents a unique Leios block seen by both nodes, joined by hash and offer slot." + ) + # Which columns to display + leios_display_columns = [ + "offer_slot", + "hash", + "offer", + "latency_ms_node0", + "latency_ms_downstream", + ] + print(df_leios_block_merged[leios_display_columns]) + + df_leios_blocktxs_node0 = load_leios_block_arrivals( + df_schedule, log_path_node0, "node0", LEIOS_BLOCKTXS_EVENT_SUBFILTER + ) + df_leios_blocktxs_downstream = load_leios_block_arrivals( + df_schedule, log_path_downstream, "downstream", LEIOS_BLOCKTXS_EVENT_SUBFILTER + ) + + # We also merge on "slot_onset" to retain it. It's a function of "slot", so + # this is harmless. + df_leios_blocktxs_merged = pd.merge( + df_leios_blocktxs_node0, + df_leios_blocktxs_downstream, + suffixes=["_node0", "_downstream"], + on=[ + "offer_slot", + "offer", + "hash", + ], # note that this determines order of resulting rows + how="outer", + ) + + print("\n--- Extracted and Merged Data Summary for Leios blocks ---") + print( + "Each row represents a unique Leios closure seen by both nodes, joined by hash and offer slot." + ) + # Which columns to display + leios_display_columns = [ + "offer_slot", + "hash", + "offer", + "latency_ms_node0", + "latency_ms_downstream", + ] + + print(df_leios_blocktxs_merged[leios_display_columns]) + + # ---------------------------------------- and finally for each BlockTxs mini protocol message + + df_sendrecv_upstream = load_sendrecv_upstream(log_path_upstream) + df_sendrecv_node0 = load_sendrecv_node(log_path_node0) + df_sendrecv_downstream = load_sendrecv_node(log_path_downstream) + + df_sendrecv_upstream_node0 = join_sendrecv( + df_sendrecv_upstream["connection_id"][0], + "upstream", + df_sendrecv_upstream, + "node0", + df_sendrecv_node0, + ) + df_sendrecv_node0_downstream = join_sendrecv( + flipConnectionId(df_sendrecv_downstream["connection_id"][0]), + "node0", + df_sendrecv_node0, + "downstream", + df_sendrecv_downstream, + ) + + # Which columns to display + sendrecv_display_columns = [ + "push_at", + "dir", + "msg", + "prevCount", + "send_latency_ms", + "transport_latency_ms", + "recv_latency_ms", + "pull_at", + ] + print( + "\n--- Extracted and Merged Data Summary for requests and replies between upstream and node0 ---" + ) + print(df_sendrecv_upstream_node0[sendrecv_display_columns]) + print( + "\n--- Extracted and Merged Data Summary for requests and replies between node0 and downstream ---" + ) + print(df_sendrecv_node0_downstream[sendrecv_display_columns]) diff --git a/demo/2025-11/build.nix b/demo/2025-11/build.nix new file mode 100644 index 000000000..a5db014f2 --- /dev/null +++ b/demo/2025-11/build.nix @@ -0,0 +1,53 @@ +{ + perSystem = + { + pkgs, + config, + lib, + ... + }: + { + devShells.dev-leios-202511-demo = pkgs.mkShell { + name = "dev-leios-202511-demo"; + src = ./.; + inputsFrom = [ config.devShells.dev-demo ]; + packages = [ pkgs.process-compose ]; + inherit (config.devShells.dev-demo) IMMDB_SERVER CARDANO_NODE; + }; + + packages = { + leios_202511_demo = pkgs.writeShellApplication { + name = "leios_202511_demo"; + runtimeInputs = + config.devShells.dev-leios-202511-demo.nativeBuildInputs + ++ config.devShells.dev-leios-202511-demo.buildInputs; + runtimeEnv = { + # Non configurable + WORKING_DIR = ".tmp-leios-202511-demo"; + UPSTREAM_NODE_PORT = 3001; + NODE0_PORT = 3002; + DOWNSTREAM_NODE_PORT = 3003; + # Configurable (if you see DEF_FOO that's a default value for FOO if unset) + DEF_CARDANO_NODE = config.devShells.dev-leios-202511-demo.CARDANO_NODE; + DEF_IMMDB_SERVER = config.devShells.dev-leios-202511-demo.IMMDB_SERVER; + DEF_REF_SLOT = 41; + DEF_SECONDS_UNTIL_REF_SLOT = 5; + DEF_LEIOS_MANIFEST = ./manifest.json; + DEF_DATA_DIR = ./data; + DEF_ANALYSE_PY = ./analyse.py; + DEF_PYTHON3 = lib.getExe ( + pkgs.python3.withPackages ( + ps: with ps; [ + pandas + matplotlib + ] + ) + ); + }; + text = '' + process-compose --no-server -f ${./process-compose.yaml}; + ''; + }; + }; + }; +} diff --git a/demo/2025-11/data/downstream-node/config.json b/demo/2025-11/data/downstream-node/config.json new file mode 100644 index 000000000..deb7dd43f --- /dev/null +++ b/demo/2025-11/data/downstream-node/config.json @@ -0,0 +1,282 @@ +{ + "AlonzoGenesisFile": "../genesis/genesis.alonzo.json", + "ByronGenesisFile": "../genesis/genesis.byron.json", + "ConwayGenesisFile": "../genesis/genesis.conway.json", + "ShelleyGenesisFile": "../genesis/genesis.shelley.json", + "ChainSyncIdleTimeout": 0, + "EnableP2P": true, + "ExperimentalHardForksEnabled": true, + "ExperimentalProtocolsEnabled": true, + "LastKnownBlockVersion-Alt": 0, + "LastKnownBlockVersion-Major": 3, + "LastKnownBlockVersion-Minor": 0, + "PeerSharing": false, + "Protocol": "Cardano", + "RequiresNetworkMagic": "RequiresMagic", + "SnapshotInterval": 4230, + "SyncTargetNumberOfActivePeers": 15, + "SyncTargetNumberOfEstablishedPeers": 40, + "TargetNumberOfActivePeers": 15, + "TargetNumberOfEstablishedPeers": 40, + "TestAllegraHardForkAtEpoch": 0, + "TestAlonzoHardForkAtEpoch": 0, + "TestBabbageHardForkAtEpoch": 0, + "TestConwayHardForkAtEpoch": 0, + "TestMaryHardForkAtEpoch": 0, + "TestShelleyHardForkAtEpoch": 0, + "TraceOptionForwarder": { + "connQueueSize": 64, + "disconnQueueSize": 128, + "maxReconnectDelay": 30 + }, + "TraceOptionMetricsPrefix": "cardano.node.metrics.", + "TraceOptionNodeName": "downstream-node", + "TraceOptionPeerFrequency": 2000, + "TraceOptionResourceFrequency": 1000, + "TraceOptions": { + "": { + "backends": [ + "Stdout MachineFormat", + "PrometheusSimple 127.0.0.1 12902" + ], + "detail": "DNormal", + "severity": "Notice" + }, + "BlockFetch.Client": { + "severity": "Debug" + }, + "BlockFetch.Client.CompletedBlockFetch": { + "maxFrequency": 2.0 + }, + "BlockFetch.Decision": { + "severity": "Notice" + }, + "BlockFetch.Remote": { + "severity": "Notice" + }, + "BlockFetch.Remote.Serialised": { + "severity": "Notice" + }, + "BlockFetch.Server": { + "severity": "Debug" + }, + "BlockchainTime": { + "severity": "Notice" + }, + "ChainDB": { + "severity": "Debug" + }, + "ChainDB.AddBlockEvent.AddBlockValidation": { + "severity": "Silence" + }, + "ChainDB.AddBlockEvent.AddBlockValidation.ValidCandidate": { + "maxFrequency": 2.0 + }, + "ChainDB.AddBlockEvent.AddedBlockToQueue": { + "maxFrequency": 2.0 + }, + "ChainDB.AddBlockEvent.AddedBlockToVolatileDB": { + "maxFrequency": 2.0 + }, + "ChainDB.CopyToImmutableDBEvent.CopiedBlockToImmutableDB": { + "maxFrequency": 2.0 + }, + "ChainDB.LedgerEvent.Flavor.V1.OnDisk.BackingStoreEvent": { + "severity": "Silence" + }, + "ChainDB.LedgerEvent.Forker": { + "severity": "Silence" + }, + "ChainDB.ReplayBlock.LedgerReplay": { + "severity": "Notice" + }, + "ChainSync.Client": { + "severity": "Debug" + }, + "ChainSync.Local": { + "severity": "Notice" + }, + "ChainSync.Remote": { + "severity": "Notice" + }, + "ChainSync.Remote.Serialised": { + "severity": "Notice" + }, + "ChainSync.ServerBlock": { + "severity": "Notice" + }, + "ChainSync.ServerHeader": { + "severity": "Debug" + }, + "Consensus.GSM": { + "severity": "Info" + }, + "Forge.Loop": { + "severity": "Debug" + }, + "Forge.StateInfo": { + "severity": "Debug" + }, + "LedgerMetrics": { + "severity": "Info" + }, + "Mempool": { + "severity": "Debug" + }, + "Mempool.AttemptAdd": { + "severity": "Silence" + }, + "Mempool.LedgerFound": { + "severity": "Silence" + }, + "Mempool.LedgerNotFound": { + "severity": "Silence" + }, + "Mempool.SyncNotNeeded": { + "severity": "Silence" + }, + "Mempool.Synced": { + "severity": "Silence" + }, + "Net": { + "severity": "Notice" + }, + "Net.AcceptPolicy": { + "severity": "Debug" + }, + "Net.ConnectionManager.Local": { + "severity": "Debug" + }, + "Net.ConnectionManager.Remote": { + "severity": "Debug" + }, + "Net.ConnectionManager.Remote.ConnectionManagerCounters": { + "severity": "Silence" + }, + "Net.DNSResolver": { + "severity": "Notice" + }, + "Net.ErrorPolicy": { + "severity": "Info" + }, + "Net.ErrorPolicy.Local": { + "severity": "Debug" + }, + "Net.ErrorPolicy.Remote": { + "severity": "Debug" + }, + "Net.Handshake.Local": { + "severity": "Debug" + }, + "Net.Handshake.Remote": { + "severity": "Debug" + }, + "Net.InboundGovernor": { + "severity": "Warning" + }, + "Net.InboundGovernor.Local": { + "severity": "Debug" + }, + "Net.InboundGovernor.Remote": { + "severity": "Debug" + }, + "Net.InboundGovernor.Transition": { + "severity": "Debug" + }, + "Net.Mux.Local": { + "severity": "Notice" + }, + "Net.Mux.Remote": { + "severity": "Notice" + }, + "Net.PeerSelection": { + "severity": "Silence" + }, + "Net.PeerSelection.Actions": { + "severity": "Debug" + }, + "Net.PeerSelection.Counters": { + "detail": "DMinimal", + "severity": "Debug" + }, + "Net.PeerSelection.Initiator": { + "severity": "Notice" + }, + "Net.PeerSelection.Responder": { + "severity": "Notice" + }, + "Net.PeerSelection.Selection": { + "severity": "Debug" + }, + "Net.Peers.Ledger": { + "severity": "Debug" + }, + "Net.Peers.List": { + "severity": "Notice" + }, + "Net.Peers.LocalRoot": { + "severity": "Debug" + }, + "Net.Peers.PublicRoot": { + "severity": "Debug" + }, + "Net.Server.Local": { + "severity": "Debug" + }, + "Net.Server.Remote": { + "severity": "Debug" + }, + "Net.Subscription.DNS": { + "severity": "Debug" + }, + "Net.Subscription.IP": { + "severity": "Debug" + }, + "NodeState": { + "severity": "Notice" + }, + "Resources": { + "severity": "Debug" + }, + "Shutdown": { + "severity": "Notice" + }, + "Startup": { + "severity": "Notice" + }, + "Startup.DiffusionInit": { + "severity": "Debug" + }, + "StateQueryServer": { + "severity": "Notice" + }, + "TxSubmission.Local": { + "severity": "Notice" + }, + "TxSubmission.LocalServer": { + "severity": "Notice" + }, + "TxSubmission.MonitorClient": { + "severity": "Notice" + }, + "TxSubmission.Remote": { + "severity": "Notice" + }, + "TxSubmission.TxInbound": { + "severity": "Debug" + }, + "TxSubmission.TxOutbound": { + "severity": "Notice" + }, + "Version.NodeVersion": { + "severity": "Info" + }, + "LeiosNotify.Remote": { "severity": "Debug", "maxFrequency": 0 }, + "LeiosFetch.Remote": { "severity": "Debug", "maxFrequency": 0 }, + "Consensus.LeiosKernel": { "severity": "Debug", "maxFrequency": 0 }, + "Consensus.LeiosPeer": { "severity": "Debug", "maxFrequency": 0 } + }, + "TurnOnLogMetrics": true, + "TurnOnLogging": true, + "UseTraceDispatcher": true +} diff --git a/demo/2025-11/data/genesis/genesis.alonzo.json b/demo/2025-11/data/genesis/genesis.alonzo.json new file mode 100644 index 000000000..e13bd102b --- /dev/null +++ b/demo/2025-11/data/genesis/genesis.alonzo.json @@ -0,0 +1,188 @@ +{ + "collateralPercentage": 150, + "costModels": { + "PlutusV1": [ + 197209, + 0, + 1, + 1, + 396231, + 621, + 0, + 1, + 150000, + 1000, + 0, + 1, + 150000, + 32, + 2477736, + 29175, + 4, + 29773, + 100, + 29773, + 100, + 29773, + 100, + 29773, + 100, + 29773, + 100, + 29773, + 100, + 100, + 100, + 29773, + 100, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 150000, + 1000, + 0, + 1, + 150000, + 32, + 150000, + 1000, + 0, + 8, + 148000, + 425507, + 118, + 0, + 1, + 1, + 150000, + 1000, + 0, + 8, + 150000, + 112536, + 247, + 1, + 150000, + 10000, + 1, + 136542, + 1326, + 1, + 1000, + 150000, + 1000, + 1, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 1, + 1, + 150000, + 1, + 150000, + 4, + 103599, + 248, + 1, + 103599, + 248, + 1, + 145276, + 1366, + 1, + 179690, + 497, + 1, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 148000, + 425507, + 118, + 0, + 1, + 1, + 61516, + 11218, + 0, + 1, + 150000, + 32, + 148000, + 425507, + 118, + 0, + 1, + 1, + 148000, + 425507, + 118, + 0, + 1, + 1, + 2477736, + 29175, + 4, + 0, + 82363, + 4, + 150000, + 5000, + 0, + 1, + 150000, + 32, + 197209, + 0, + 1, + 1, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 150000, + 32, + 3345831, + 1, + 1 + ] + }, + "executionPrices": { + "priceMemory": 0.0577, + "priceSteps": 0.0000721 + }, + "lovelacePerUTxOWord": 34482, + "maxBlockExUnits": { + "memory": 62000000, + "steps": 20000000000 + }, + "maxCollateralInputs": 3, + "maxTxExUnits": { + "memory": 14000000, + "steps": 10000000000 + }, + "maxValueSize": 5000 +} diff --git a/demo/2025-11/data/genesis/genesis.byron.json b/demo/2025-11/data/genesis/genesis.byron.json new file mode 100644 index 000000000..e2bf95e28 --- /dev/null +++ b/demo/2025-11/data/genesis/genesis.byron.json @@ -0,0 +1,42 @@ +{ "bootStakeholders": + { "a8f4fd08e2935ea584899dc306084595c4b9df394ea20dd855236a9d": 1 } +, "heavyDelegation": + { "a8f4fd08e2935ea584899dc306084595c4b9df394ea20dd855236a9d": + { "omega": 0 + , "issuerPk": + "JW5mw+Zo7XnJpBlqMnsrd+cfElAY8AFAWbQuF0+CqTQYgBz9eXza/EiY9sxugu/b6FwJW5fxe3rY83U7VFzEfg==" + , "delegatePk": + "zMajaA9h8Q6gUQ+y6VKHoj4Y1VBjlJyyS0v2eZn67RgNBOK63uxBdut6/1/kLaNMk+MuWB131W/abDCPs8b9og==" + , "cert": + "b12dd4d4d8c87a9af25fa6d5ee78a620573a6712fbeebfc45951d00bf4200a70cb6d4733cfddea576c4fd399e2fd6e2fd60d55f243bc6c8177ed599d699d6d06" + } } +, "startTime": 1759952614 +, "nonAvvmBalances": + { "2657WMsDfac5QzGGBef3oj7pwz4VwHCmNhkhLmN1SSs47qypuS7XQwFNCRVWansbi": + "30000" + , "2657WMsDfac6t6LUFkmDj8GCgJwUxNAPLMnionk3PbkLzVYHAiS7CpMGYUQjjhZQi": + "270000" + } +, "blockVersionData": + { "scriptVersion": 0 + , "slotDuration": "20000" + , "maxBlockSize": "641000" + , "maxHeaderSize": "200000" + , "maxTxSize": "4096" + , "maxProposalSize": "700" + , "mpcThd": "200000" + , "heavyDelThd": "300000" + , "updateVoteThd": "100000" + , "updateProposalThd": "100000" + , "updateImplicit": "10000" + , "softforkRule": + { "initThd": "900000" + , "minThd": "600000" + , "thdDecrement": "100000" + } + , "txFeePolicy": { "summand": "0" , "multiplier": "439460" } + , "unlockStakeEpoch": "184467" + } +, "protocolConsts": { "k": 3 , "protocolMagic": 42 } +, "avvmDistr": {} +} diff --git a/demo/2025-11/data/genesis/genesis.conway.json b/demo/2025-11/data/genesis/genesis.conway.json new file mode 100644 index 000000000..70f8103f3 --- /dev/null +++ b/demo/2025-11/data/genesis/genesis.conway.json @@ -0,0 +1,337 @@ +{ + "committee": { + "members": {}, + "threshold": 0 + }, + "committeeMaxTermLength": 146, + "committeeMinSize": 7, + "constitution": { + "anchor": { + "dataHash": "0000000000000000000000000000000000000000000000000000000000000000", + "url": "" + } + }, + "dRepActivity": 20, + "dRepDeposit": 500000000, + "dRepVotingThresholds": { + "committeeNoConfidence": 0.6, + "committeeNormal": 0.67, + "hardForkInitiation": 0.6, + "motionNoConfidence": 0.67, + "ppEconomicGroup": 0.67, + "ppGovGroup": 0.75, + "ppNetworkGroup": 0.67, + "ppTechnicalGroup": 0.67, + "treasuryWithdrawal": 0.67, + "updateToConstitution": 0.75 + }, + "govActionDeposit": 100000000000, + "govActionLifetime": 6, + "minFeeRefScriptCostPerByte": 15, + "plutusV3CostModel": [ + 100788, + 420, + 1, + 1, + 1000, + 173, + 0, + 1, + 1000, + 59957, + 4, + 1, + 11183, + 32, + 201305, + 8356, + 4, + 16000, + 100, + 16000, + 100, + 16000, + 100, + 16000, + 100, + 16000, + 100, + 16000, + 100, + 100, + 100, + 16000, + 100, + 94375, + 32, + 132994, + 32, + 61462, + 4, + 72010, + 178, + 0, + 1, + 22151, + 32, + 91189, + 769, + 4, + 2, + 85848, + 123203, + 7305, + -900, + 1716, + 549, + 57, + 85848, + 0, + 1, + 1, + 1000, + 42921, + 4, + 2, + 24548, + 29498, + 38, + 1, + 898148, + 27279, + 1, + 51775, + 558, + 1, + 39184, + 1000, + 60594, + 1, + 141895, + 32, + 83150, + 32, + 15299, + 32, + 76049, + 1, + 13169, + 4, + 22100, + 10, + 28999, + 74, + 1, + 28999, + 74, + 1, + 43285, + 552, + 1, + 44749, + 541, + 1, + 33852, + 32, + 68246, + 32, + 72362, + 32, + 7243, + 32, + 7391, + 32, + 11546, + 32, + 85848, + 123203, + 7305, + -900, + 1716, + 549, + 57, + 85848, + 0, + 1, + 90434, + 519, + 0, + 1, + 74433, + 32, + 85848, + 123203, + 7305, + -900, + 1716, + 549, + 57, + 85848, + 0, + 1, + 1, + 85848, + 123203, + 7305, + -900, + 1716, + 549, + 57, + 85848, + 0, + 1, + 955506, + 213312, + 0, + 2, + 270652, + 22588, + 4, + 1457325, + 64566, + 4, + 20467, + 1, + 4, + 0, + 141992, + 32, + 100788, + 420, + 1, + 1, + 81663, + 32, + 59498, + 32, + 20142, + 32, + 24588, + 32, + 20744, + 32, + 25933, + 32, + 24623, + 32, + 43053543, + 10, + 53384111, + 14333, + 10, + 43574283, + 26308, + 10, + 16000, + 100, + 16000, + 100, + 962335, + 18, + 2780678, + 6, + 442008, + 1, + 52538055, + 3756, + 18, + 267929, + 18, + 76433006, + 8868, + 18, + 52948122, + 18, + 1995836, + 36, + 3227919, + 12, + 901022, + 1, + 166917843, + 4307, + 36, + 284546, + 36, + 158221314, + 26549, + 36, + 74698472, + 36, + 333849714, + 1, + 254006273, + 72, + 2174038, + 72, + 2261318, + 64571, + 4, + 207616, + 8310, + 4, + 1293828, + 28716, + 63, + 0, + 1, + 1006041, + 43623, + 251, + 0, + 1, + 100181, + 726, + 719, + 0, + 1, + 100181, + 726, + 719, + 0, + 1, + 100181, + 726, + 719, + 0, + 1, + 107878, + 680, + 0, + 1, + 95336, + 1, + 281145, + 18848, + 0, + 1, + 180194, + 159, + 1, + 1, + 158519, + 8942, + 0, + 1, + 159378, + 8813, + 0, + 1, + 107490, + 3298, + 1, + 106057, + 655, + 1, + 1964219, + 24520, + 3 + ], + "poolVotingThresholds": { + "committeeNoConfidence": 0.51, + "committeeNormal": 0.51, + "hardForkInitiation": 0.51, + "motionNoConfidence": 0.51, + "ppSecurityGroup": 0.51 + } +} diff --git a/demo/2025-11/data/genesis/genesis.shelley.json b/demo/2025-11/data/genesis/genesis.shelley.json new file mode 100644 index 000000000..cd07b300b --- /dev/null +++ b/demo/2025-11/data/genesis/genesis.shelley.json @@ -0,0 +1,97 @@ +{ + "activeSlotsCoeff": 0.050, + "epochLength": 600, + "genDelegs": {}, + "initialFunds": { + "00635eef9a08f327a0ce009466914e8f607cebf76e9f4c9f92b0a829f4eab4c172777c708cd0bcac1a16d41b513e3a0f3dff8d182c2878947c": 900000000000000, + "00f00bb672d5d2f064707e6c955234da597e9b43ed6e458a3d15870a8257ef7aac3c0f6e4fbc3e253e3f4e58039986e89492c02c812e703d69": 900000000000000, + "601c6db4e8b6b36e265b9eecba0cb9a653cdd8701f708beccd911f838b": 9000000000000 + }, + "maxKESEvolutions": 62, + "maxLovelaceSupply": 2010000000000000, + "networkId": "Testnet", + "networkMagic": 42, + "protocolParams": { + "a0": 0.3, + "decentralisationParam": 0, + "eMax": 18, + "extraEntropy": { + "tag": "NeutralNonce" + }, + "keyDeposit": 2000000, + "maxBlockBodySize": 90112, + "maxBlockHeaderSize": 1100, + "maxTxSize": 16384, + "minFeeA": 44, + "minFeeB": 155381, + "minPoolCost": 340000000, + "minUTxOValue": 0, + "nOpt": 500, + "poolDeposit": 500000000, + "protocolVersion": { + "major": 10, + "minor": 0 + }, + "rho": 0.0030, + "tau": 0.2 + }, + "securityParam": 3, + "slotLength": 1, + "slotsPerKESPeriod": 129600, + "staking": { + "pools": { + "4c26da5ee3f61915d2df4167a53394b1f033623042a8d26ab7af5ef7": { + "cost": 0, + "margin": 0, + "metadata": null, + "owners": [], + "pledge": 0, + "publicKey": "4c26da5ee3f61915d2df4167a53394b1f033623042a8d26ab7af5ef7", + "relays": [ + { + "single host name": { + "dnsName": "node-0", + "port": 30000 + } + } + ], + "rewardAccount": { + "credential": { + "keyHash": "48d482deb658ae1aaa522a365e68f9747da98015500e1c260dca3c73" + }, + "network": "Testnet" + }, + "vrf": "03670fa208cb10b3452f04be890c931e4f34eff777dec589f1631d66c971c40c" + }, + "68b23036da5530e5853357a8dc9d03dd8e851b0e29a3eaf61b55b6cc": { + "cost": 0, + "margin": 0, + "metadata": null, + "owners": [], + "pledge": 0, + "publicKey": "68b23036da5530e5853357a8dc9d03dd8e851b0e29a3eaf61b55b6cc", + "relays": [ + { + "single host name": { + "dnsName": "node-1", + "port": 30001 + } + } + ], + "rewardAccount": { + "credential": { + "keyHash": "df587edcea6b53ed8bdc416be16f00beaaef18b5c6b25294275bf117" + }, + "network": "Testnet" + }, + "vrf": "0a570d439272a91eca089a9d04d9a94f11bb86c8daa3991fa67b35468049d60e" + } + }, + "stake": { + "57ef7aac3c0f6e4fbc3e253e3f4e58039986e89492c02c812e703d69": "4c26da5ee3f61915d2df4167a53394b1f033623042a8d26ab7af5ef7", + "eab4c172777c708cd0bcac1a16d41b513e3a0f3dff8d182c2878947c": "68b23036da5530e5853357a8dc9d03dd8e851b0e29a3eaf61b55b6cc" + } + }, + "systemStart": "2025-10-08T19:43:34Z", + "updateQuorum": 5 +} diff --git a/demo/2025-11/data/leios-schema.sql b/demo/2025-11/data/leios-schema.sql new file mode 100644 index 000000000..44e8c9746 --- /dev/null +++ b/demo/2025-11/data/leios-schema.sql @@ -0,0 +1,41 @@ +CREATE TABLE txCache ( + txHashBytes BLOB NOT NULL PRIMARY KEY -- raw bytes + , + txBytes BLOB NOT NULL -- valid CBOR + , + txBytesSize INTEGER NOT NULL + , + expiryUnixEpoch INTEGER NOT NULL + ) WITHOUT ROWID; +CREATE TABLE ebPoints ( + ebSlot INTEGER NOT NULL + , + ebHashBytes BLOB NOT NULL + , + ebId INTEGER NOT NULL + , + PRIMARY KEY (ebSlot, ebHashBytes) + ) WITHOUT ROWID; +CREATE TABLE ebTxs ( + ebId INTEGER NOT NULL -- foreign key ebPoints.ebId + , + txOffset INTEGER NOT NULL + , + txHashBytes BLOB NOT NULL -- raw bytes + , + txBytesSize INTEGER NOT NULL + , + txBytes BLOB -- valid CBOR + , + PRIMARY KEY (ebId, txOffset) + ) WITHOUT ROWID; +CREATE INDEX ebPointsExpiry + ON ebPoints (ebSlot ASC, ebId ASC); +CREATE INDEX txCacheExpiry + ON txCache (expiryUnixEpoch ASC, txHashBytes); +CREATE INDEX missingEbTxs + ON ebTxs (ebId DESC, txOffset ASC) + WHERE txBytes IS NULL; +CREATE INDEX acquiredEbTxs + ON ebTxs (ebId DESC, txOffset ASC) + WHERE txBytes IS NOT NULL; diff --git a/demo/2025-11/data/node0/config.json b/demo/2025-11/data/node0/config.json new file mode 100644 index 000000000..c36172a23 --- /dev/null +++ b/demo/2025-11/data/node0/config.json @@ -0,0 +1,282 @@ +{ + "AlonzoGenesisFile": "../genesis/genesis.alonzo.json", + "ByronGenesisFile": "../genesis/genesis.byron.json", + "ConwayGenesisFile": "../genesis/genesis.conway.json", + "ShelleyGenesisFile": "../genesis/genesis.shelley.json", + "ChainSyncIdleTimeout": 0, + "EnableP2P": true, + "ExperimentalHardForksEnabled": true, + "ExperimentalProtocolsEnabled": true, + "LastKnownBlockVersion-Alt": 0, + "LastKnownBlockVersion-Major": 3, + "LastKnownBlockVersion-Minor": 0, + "PeerSharing": false, + "Protocol": "Cardano", + "RequiresNetworkMagic": "RequiresMagic", + "SnapshotInterval": 4230, + "SyncTargetNumberOfActivePeers": 15, + "SyncTargetNumberOfEstablishedPeers": 40, + "TargetNumberOfActivePeers": 15, + "TargetNumberOfEstablishedPeers": 40, + "TestAllegraHardForkAtEpoch": 0, + "TestAlonzoHardForkAtEpoch": 0, + "TestBabbageHardForkAtEpoch": 0, + "TestConwayHardForkAtEpoch": 0, + "TestMaryHardForkAtEpoch": 0, + "TestShelleyHardForkAtEpoch": 0, + "TraceOptionForwarder": { + "connQueueSize": 64, + "disconnQueueSize": 128, + "maxReconnectDelay": 30 + }, + "TraceOptionMetricsPrefix": "cardano.node.metrics.", + "TraceOptionNodeName": "node0", + "TraceOptionPeerFrequency": 2000, + "TraceOptionResourceFrequency": 1000, + "TraceOptions": { + "": { + "backends": [ + "Stdout MachineFormat", + "PrometheusSimple 127.0.0.1 12901" + ], + "detail": "DNormal", + "severity": "Notice" + }, + "BlockFetch.Client": { + "severity": "Debug" + }, + "BlockFetch.Client.CompletedBlockFetch": { + "maxFrequency": 2.0 + }, + "BlockFetch.Decision": { + "severity": "Notice" + }, + "BlockFetch.Remote": { + "severity": "Notice" + }, + "BlockFetch.Remote.Serialised": { + "severity": "Notice" + }, + "BlockFetch.Server": { + "severity": "Debug" + }, + "BlockchainTime": { + "severity": "Notice" + }, + "ChainDB": { + "severity": "Debug" + }, + "ChainDB.AddBlockEvent.AddBlockValidation": { + "severity": "Silence" + }, + "ChainDB.AddBlockEvent.AddBlockValidation.ValidCandidate": { + "maxFrequency": 2.0 + }, + "ChainDB.AddBlockEvent.AddedBlockToQueue": { + "maxFrequency": 2.0 + }, + "ChainDB.AddBlockEvent.AddedBlockToVolatileDB": { + "maxFrequency": 2.0 + }, + "ChainDB.CopyToImmutableDBEvent.CopiedBlockToImmutableDB": { + "maxFrequency": 2.0 + }, + "ChainDB.LedgerEvent.Flavor.V1.OnDisk.BackingStoreEvent": { + "severity": "Silence" + }, + "ChainDB.LedgerEvent.Forker": { + "severity": "Silence" + }, + "ChainDB.ReplayBlock.LedgerReplay": { + "severity": "Notice" + }, + "ChainSync.Client": { + "severity": "Debug" + }, + "ChainSync.Local": { + "severity": "Notice" + }, + "ChainSync.Remote": { + "severity": "Notice" + }, + "ChainSync.Remote.Serialised": { + "severity": "Notice" + }, + "ChainSync.ServerBlock": { + "severity": "Notice" + }, + "ChainSync.ServerHeader": { + "severity": "Debug" + }, + "Consensus.GSM": { + "severity": "Info" + }, + "Forge.Loop": { + "severity": "Debug" + }, + "Forge.StateInfo": { + "severity": "Debug" + }, + "LedgerMetrics": { + "severity": "Info" + }, + "Mempool": { + "severity": "Debug" + }, + "Mempool.AttemptAdd": { + "severity": "Silence" + }, + "Mempool.LedgerFound": { + "severity": "Silence" + }, + "Mempool.LedgerNotFound": { + "severity": "Silence" + }, + "Mempool.SyncNotNeeded": { + "severity": "Silence" + }, + "Mempool.Synced": { + "severity": "Silence" + }, + "Net": { + "severity": "Notice" + }, + "Net.AcceptPolicy": { + "severity": "Debug" + }, + "Net.ConnectionManager.Local": { + "severity": "Debug" + }, + "Net.ConnectionManager.Remote": { + "severity": "Debug" + }, + "Net.ConnectionManager.Remote.ConnectionManagerCounters": { + "severity": "Silence" + }, + "Net.DNSResolver": { + "severity": "Notice" + }, + "Net.ErrorPolicy": { + "severity": "Info" + }, + "Net.ErrorPolicy.Local": { + "severity": "Debug" + }, + "Net.ErrorPolicy.Remote": { + "severity": "Debug" + }, + "Net.Handshake.Local": { + "severity": "Debug" + }, + "Net.Handshake.Remote": { + "severity": "Debug" + }, + "Net.InboundGovernor": { + "severity": "Warning" + }, + "Net.InboundGovernor.Local": { + "severity": "Debug" + }, + "Net.InboundGovernor.Remote": { + "severity": "Debug" + }, + "Net.InboundGovernor.Transition": { + "severity": "Debug" + }, + "Net.Mux.Local": { + "severity": "Notice" + }, + "Net.Mux.Remote": { + "severity": "Notice" + }, + "Net.PeerSelection": { + "severity": "Silence" + }, + "Net.PeerSelection.Actions": { + "severity": "Debug" + }, + "Net.PeerSelection.Counters": { + "detail": "DMinimal", + "severity": "Debug" + }, + "Net.PeerSelection.Initiator": { + "severity": "Notice" + }, + "Net.PeerSelection.Responder": { + "severity": "Notice" + }, + "Net.PeerSelection.Selection": { + "severity": "Debug" + }, + "Net.Peers.Ledger": { + "severity": "Debug" + }, + "Net.Peers.List": { + "severity": "Notice" + }, + "Net.Peers.LocalRoot": { + "severity": "Debug" + }, + "Net.Peers.PublicRoot": { + "severity": "Debug" + }, + "Net.Server.Local": { + "severity": "Debug" + }, + "Net.Server.Remote": { + "severity": "Debug" + }, + "Net.Subscription.DNS": { + "severity": "Debug" + }, + "Net.Subscription.IP": { + "severity": "Debug" + }, + "NodeState": { + "severity": "Notice" + }, + "Resources": { + "severity": "Debug" + }, + "Shutdown": { + "severity": "Notice" + }, + "Startup": { + "severity": "Notice" + }, + "Startup.DiffusionInit": { + "severity": "Debug" + }, + "StateQueryServer": { + "severity": "Notice" + }, + "TxSubmission.Local": { + "severity": "Notice" + }, + "TxSubmission.LocalServer": { + "severity": "Notice" + }, + "TxSubmission.MonitorClient": { + "severity": "Notice" + }, + "TxSubmission.Remote": { + "severity": "Notice" + }, + "TxSubmission.TxInbound": { + "severity": "Debug" + }, + "TxSubmission.TxOutbound": { + "severity": "Notice" + }, + "Version.NodeVersion": { + "severity": "Info" + }, + "LeiosNotify.Remote": { "severity": "Debug", "maxFrequency": 0 }, + "LeiosFetch.Remote": { "severity": "Debug", "maxFrequency": 0 }, + "Consensus.LeiosKernel": { "severity": "Debug", "maxFrequency": 0 }, + "Consensus.LeiosPeer": { "severity": "Debug", "maxFrequency": 0 } + }, + "TurnOnLogMetrics": true, + "TurnOnLogging": true, + "UseTraceDispatcher": true +} diff --git a/demo/2025-11/data/topology.template.json b/demo/2025-11/data/topology.template.json new file mode 100644 index 000000000..6da4530b9 --- /dev/null +++ b/demo/2025-11/data/topology.template.json @@ -0,0 +1,17 @@ +{ + "bootstrapPeers": [], + "localRoots": [ + { + "accessPoints": [ + { + "address": "127.0.0.1", + "port": "#REPLACE#" + } + ], + "advertise": false, + "trustable": true, + "valency": 1 + } + ], + "publicRoots": [] +} diff --git a/demo/2025-11/data/upstream-node/config.json b/demo/2025-11/data/upstream-node/config.json new file mode 100644 index 000000000..c447c6495 --- /dev/null +++ b/demo/2025-11/data/upstream-node/config.json @@ -0,0 +1,282 @@ +{ + "AlonzoGenesisFile": "../genesis/genesis.alonzo.json", + "ByronGenesisFile": "../genesis/genesis.byron.json", + "ConwayGenesisFile": "../genesis/genesis.conway.json", + "ShelleyGenesisFile": "../genesis/genesis.shelley.json", + "ChainSyncIdleTimeout": 0, + "EnableP2P": true, + "ExperimentalHardForksEnabled": true, + "ExperimentalProtocolsEnabled": true, + "LastKnownBlockVersion-Alt": 0, + "LastKnownBlockVersion-Major": 3, + "LastKnownBlockVersion-Minor": 0, + "PeerSharing": false, + "Protocol": "Cardano", + "RequiresNetworkMagic": "RequiresMagic", + "SnapshotInterval": 4230, + "SyncTargetNumberOfActivePeers": 15, + "SyncTargetNumberOfEstablishedPeers": 40, + "TargetNumberOfActivePeers": 15, + "TargetNumberOfEstablishedPeers": 40, + "TestAllegraHardForkAtEpoch": 0, + "TestAlonzoHardForkAtEpoch": 0, + "TestBabbageHardForkAtEpoch": 0, + "TestConwayHardForkAtEpoch": 0, + "TestMaryHardForkAtEpoch": 0, + "TestShelleyHardForkAtEpoch": 0, + "TraceOptionForwarder": { + "connQueueSize": 64, + "disconnQueueSize": 128, + "maxReconnectDelay": 30 + }, + "TraceOptionMetricsPrefix": "cardano.node.metrics.", + "TraceOptionNodeName": "immdb-node", + "TraceOptionPeerFrequency": 2000, + "TraceOptionResourceFrequency": 1000, + "TraceOptions": { + "": { + "backends": [ + "Stdout MachineFormat", + "PrometheusSimple 127.0.0.1 12900" + ], + "detail": "DNormal", + "severity": "Notice" + }, + "BlockFetch.Client": { + "severity": "Debug" + }, + "BlockFetch.Client.CompletedBlockFetch": { + "maxFrequency": 2.0 + }, + "BlockFetch.Decision": { + "severity": "Notice" + }, + "BlockFetch.Remote": { + "severity": "Notice" + }, + "BlockFetch.Remote.Serialised": { + "severity": "Notice" + }, + "BlockFetch.Server": { + "severity": "Debug" + }, + "BlockchainTime": { + "severity": "Notice" + }, + "ChainDB": { + "severity": "Debug" + }, + "ChainDB.AddBlockEvent.AddBlockValidation": { + "severity": "Silence" + }, + "ChainDB.AddBlockEvent.AddBlockValidation.ValidCandidate": { + "maxFrequency": 2.0 + }, + "ChainDB.AddBlockEvent.AddedBlockToQueue": { + "maxFrequency": 2.0 + }, + "ChainDB.AddBlockEvent.AddedBlockToVolatileDB": { + "maxFrequency": 2.0 + }, + "ChainDB.CopyToImmutableDBEvent.CopiedBlockToImmutableDB": { + "maxFrequency": 2.0 + }, + "ChainDB.LedgerEvent.Flavor.V1.OnDisk.BackingStoreEvent": { + "severity": "Silence" + }, + "ChainDB.LedgerEvent.Forker": { + "severity": "Silence" + }, + "ChainDB.ReplayBlock.LedgerReplay": { + "severity": "Notice" + }, + "ChainSync.Client": { + "severity": "Debug" + }, + "ChainSync.Local": { + "severity": "Notice" + }, + "ChainSync.Remote": { + "severity": "Notice" + }, + "ChainSync.Remote.Serialised": { + "severity": "Notice" + }, + "ChainSync.ServerBlock": { + "severity": "Notice" + }, + "ChainSync.ServerHeader": { + "severity": "Debug" + }, + "Consensus.GSM": { + "severity": "Info" + }, + "Forge.Loop": { + "severity": "Debug" + }, + "Forge.StateInfo": { + "severity": "Debug" + }, + "LedgerMetrics": { + "severity": "Info" + }, + "Mempool": { + "severity": "Debug" + }, + "Mempool.AttemptAdd": { + "severity": "Silence" + }, + "Mempool.LedgerFound": { + "severity": "Silence" + }, + "Mempool.LedgerNotFound": { + "severity": "Silence" + }, + "Mempool.SyncNotNeeded": { + "severity": "Silence" + }, + "Mempool.Synced": { + "severity": "Silence" + }, + "Net": { + "severity": "Notice" + }, + "Net.AcceptPolicy": { + "severity": "Debug" + }, + "Net.ConnectionManager.Local": { + "severity": "Debug" + }, + "Net.ConnectionManager.Remote": { + "severity": "Debug" + }, + "Net.ConnectionManager.Remote.ConnectionManagerCounters": { + "severity": "Silence" + }, + "Net.DNSResolver": { + "severity": "Notice" + }, + "Net.ErrorPolicy": { + "severity": "Info" + }, + "Net.ErrorPolicy.Local": { + "severity": "Debug" + }, + "Net.ErrorPolicy.Remote": { + "severity": "Debug" + }, + "Net.Handshake.Local": { + "severity": "Debug" + }, + "Net.Handshake.Remote": { + "severity": "Debug" + }, + "Net.InboundGovernor": { + "severity": "Warning" + }, + "Net.InboundGovernor.Local": { + "severity": "Debug" + }, + "Net.InboundGovernor.Remote": { + "severity": "Debug" + }, + "Net.InboundGovernor.Transition": { + "severity": "Debug" + }, + "Net.Mux.Local": { + "severity": "Notice" + }, + "Net.Mux.Remote": { + "severity": "Notice" + }, + "Net.PeerSelection": { + "severity": "Silence" + }, + "Net.PeerSelection.Actions": { + "severity": "Debug" + }, + "Net.PeerSelection.Counters": { + "detail": "DMinimal", + "severity": "Debug" + }, + "Net.PeerSelection.Initiator": { + "severity": "Notice" + }, + "Net.PeerSelection.Responder": { + "severity": "Notice" + }, + "Net.PeerSelection.Selection": { + "severity": "Debug" + }, + "Net.Peers.Ledger": { + "severity": "Debug" + }, + "Net.Peers.List": { + "severity": "Notice" + }, + "Net.Peers.LocalRoot": { + "severity": "Debug" + }, + "Net.Peers.PublicRoot": { + "severity": "Debug" + }, + "Net.Server.Local": { + "severity": "Debug" + }, + "Net.Server.Remote": { + "severity": "Debug" + }, + "Net.Subscription.DNS": { + "severity": "Debug" + }, + "Net.Subscription.IP": { + "severity": "Debug" + }, + "NodeState": { + "severity": "Notice" + }, + "Resources": { + "severity": "Debug" + }, + "Shutdown": { + "severity": "Notice" + }, + "Startup": { + "severity": "Notice" + }, + "Startup.DiffusionInit": { + "severity": "Debug" + }, + "StateQueryServer": { + "severity": "Notice" + }, + "TxSubmission.Local": { + "severity": "Notice" + }, + "TxSubmission.LocalServer": { + "severity": "Notice" + }, + "TxSubmission.MonitorClient": { + "severity": "Notice" + }, + "TxSubmission.Remote": { + "severity": "Notice" + }, + "TxSubmission.TxInbound": { + "severity": "Debug" + }, + "TxSubmission.TxOutbound": { + "severity": "Notice" + }, + "Version.NodeVersion": { + "severity": "Info" + }, + "LeiosNotify.Remote": { "severity": "Debug", "maxFrequency": 0 }, + "LeiosFetch.Remote": { "severity": "Debug", "maxFrequency": 0 }, + "Consensus.LeiosKernel": { "severity": "Debug", "maxFrequency": 0 }, + "Consensus.LeiosPeer": { "severity": "Debug", "maxFrequency": 0 } + }, + "TurnOnLogMetrics": true, + "TurnOnLogging": true, + "UseTraceDispatcher": true +} diff --git a/demo/2025-11/data/upstream-node/immutable/00000.chunk b/demo/2025-11/data/upstream-node/immutable/00000.chunk new file mode 100644 index 000000000..0b766c8ee Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00000.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00000.primary b/demo/2025-11/data/upstream-node/immutable/00000.primary new file mode 100644 index 000000000..9dffe10d0 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00000.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00000.secondary b/demo/2025-11/data/upstream-node/immutable/00000.secondary new file mode 100644 index 000000000..b6572daf2 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00000.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00001.chunk b/demo/2025-11/data/upstream-node/immutable/00001.chunk new file mode 100644 index 000000000..d38df30fe Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00001.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00001.primary b/demo/2025-11/data/upstream-node/immutable/00001.primary new file mode 100644 index 000000000..a37df378c Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00001.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00001.secondary b/demo/2025-11/data/upstream-node/immutable/00001.secondary new file mode 100644 index 000000000..8a8988e7d Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00001.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00002.chunk b/demo/2025-11/data/upstream-node/immutable/00002.chunk new file mode 100644 index 000000000..c621457ca Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00002.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00002.primary b/demo/2025-11/data/upstream-node/immutable/00002.primary new file mode 100644 index 000000000..3dd3ca8e9 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00002.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00002.secondary b/demo/2025-11/data/upstream-node/immutable/00002.secondary new file mode 100644 index 000000000..06acc09ac Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00002.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00003.chunk b/demo/2025-11/data/upstream-node/immutable/00003.chunk new file mode 100644 index 000000000..2016ff4c7 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00003.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00003.primary b/demo/2025-11/data/upstream-node/immutable/00003.primary new file mode 100644 index 000000000..31a0a654e Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00003.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00003.secondary b/demo/2025-11/data/upstream-node/immutable/00003.secondary new file mode 100644 index 000000000..b7e6e3e3c Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00003.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00004.chunk b/demo/2025-11/data/upstream-node/immutable/00004.chunk new file mode 100644 index 000000000..a5e1addf7 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00004.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00004.primary b/demo/2025-11/data/upstream-node/immutable/00004.primary new file mode 100644 index 000000000..6ca64bb57 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00004.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00004.secondary b/demo/2025-11/data/upstream-node/immutable/00004.secondary new file mode 100644 index 000000000..012a28138 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00004.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00005.chunk b/demo/2025-11/data/upstream-node/immutable/00005.chunk new file mode 100644 index 000000000..90e8154d3 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00005.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00005.primary b/demo/2025-11/data/upstream-node/immutable/00005.primary new file mode 100644 index 000000000..109ab6cb9 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00005.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00005.secondary b/demo/2025-11/data/upstream-node/immutable/00005.secondary new file mode 100644 index 000000000..e48e95f51 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00005.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00006.chunk b/demo/2025-11/data/upstream-node/immutable/00006.chunk new file mode 100644 index 000000000..205ba0688 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00006.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00006.primary b/demo/2025-11/data/upstream-node/immutable/00006.primary new file mode 100644 index 000000000..4394437a9 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00006.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00006.secondary b/demo/2025-11/data/upstream-node/immutable/00006.secondary new file mode 100644 index 000000000..63e547138 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00006.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00007.chunk b/demo/2025-11/data/upstream-node/immutable/00007.chunk new file mode 100644 index 000000000..dcb034716 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00007.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00007.primary b/demo/2025-11/data/upstream-node/immutable/00007.primary new file mode 100644 index 000000000..c8b6673f1 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00007.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00007.secondary b/demo/2025-11/data/upstream-node/immutable/00007.secondary new file mode 100644 index 000000000..64dda915a Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00007.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00008.chunk b/demo/2025-11/data/upstream-node/immutable/00008.chunk new file mode 100644 index 000000000..b28ee948c Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00008.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00008.primary b/demo/2025-11/data/upstream-node/immutable/00008.primary new file mode 100644 index 000000000..6e677301f Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00008.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00008.secondary b/demo/2025-11/data/upstream-node/immutable/00008.secondary new file mode 100644 index 000000000..9c60085f2 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00008.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00009.chunk b/demo/2025-11/data/upstream-node/immutable/00009.chunk new file mode 100644 index 000000000..7dec69aef Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00009.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00009.primary b/demo/2025-11/data/upstream-node/immutable/00009.primary new file mode 100644 index 000000000..35ef5387f Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00009.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00009.secondary b/demo/2025-11/data/upstream-node/immutable/00009.secondary new file mode 100644 index 000000000..9d0bf59ba Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00009.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00010.chunk b/demo/2025-11/data/upstream-node/immutable/00010.chunk new file mode 100644 index 000000000..b7a1377e1 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00010.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00010.primary b/demo/2025-11/data/upstream-node/immutable/00010.primary new file mode 100644 index 000000000..8708dcc33 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00010.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00010.secondary b/demo/2025-11/data/upstream-node/immutable/00010.secondary new file mode 100644 index 000000000..20b628ca4 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00010.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00011.chunk b/demo/2025-11/data/upstream-node/immutable/00011.chunk new file mode 100644 index 000000000..748e7d141 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00011.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00011.primary b/demo/2025-11/data/upstream-node/immutable/00011.primary new file mode 100644 index 000000000..2d580b899 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00011.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00011.secondary b/demo/2025-11/data/upstream-node/immutable/00011.secondary new file mode 100644 index 000000000..6a9c01a7d Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00011.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00012.chunk b/demo/2025-11/data/upstream-node/immutable/00012.chunk new file mode 100644 index 000000000..f3603b1c9 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00012.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00012.primary b/demo/2025-11/data/upstream-node/immutable/00012.primary new file mode 100644 index 000000000..7e672d383 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00012.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00012.secondary b/demo/2025-11/data/upstream-node/immutable/00012.secondary new file mode 100644 index 000000000..685cedd0b Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00012.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00013.chunk b/demo/2025-11/data/upstream-node/immutable/00013.chunk new file mode 100644 index 000000000..02a7f8317 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00013.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00013.primary b/demo/2025-11/data/upstream-node/immutable/00013.primary new file mode 100644 index 000000000..52b97f698 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00013.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00013.secondary b/demo/2025-11/data/upstream-node/immutable/00013.secondary new file mode 100644 index 000000000..6c6948284 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00013.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00014.chunk b/demo/2025-11/data/upstream-node/immutable/00014.chunk new file mode 100644 index 000000000..7301adec2 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00014.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00014.primary b/demo/2025-11/data/upstream-node/immutable/00014.primary new file mode 100644 index 000000000..bf89ed50d Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00014.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00014.secondary b/demo/2025-11/data/upstream-node/immutable/00014.secondary new file mode 100644 index 000000000..7a3ddbbdd Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00014.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00015.chunk b/demo/2025-11/data/upstream-node/immutable/00015.chunk new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-11/data/upstream-node/immutable/00015.primary b/demo/2025-11/data/upstream-node/immutable/00015.primary new file mode 100644 index 000000000..48e4f424b Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00015.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00015.secondary b/demo/2025-11/data/upstream-node/immutable/00015.secondary new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-11/data/upstream-node/immutable/00016.chunk b/demo/2025-11/data/upstream-node/immutable/00016.chunk new file mode 100644 index 000000000..422c3ca80 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00016.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00016.primary b/demo/2025-11/data/upstream-node/immutable/00016.primary new file mode 100644 index 000000000..51ba2b4ce Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00016.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00016.secondary b/demo/2025-11/data/upstream-node/immutable/00016.secondary new file mode 100644 index 000000000..4a371d489 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00016.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00017.chunk b/demo/2025-11/data/upstream-node/immutable/00017.chunk new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-11/data/upstream-node/immutable/00017.primary b/demo/2025-11/data/upstream-node/immutable/00017.primary new file mode 100644 index 000000000..48e4f424b Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00017.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00017.secondary b/demo/2025-11/data/upstream-node/immutable/00017.secondary new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-11/data/upstream-node/immutable/00018.chunk b/demo/2025-11/data/upstream-node/immutable/00018.chunk new file mode 100644 index 000000000..c2b08706b Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00018.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00018.primary b/demo/2025-11/data/upstream-node/immutable/00018.primary new file mode 100644 index 000000000..bb11205b2 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00018.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00018.secondary b/demo/2025-11/data/upstream-node/immutable/00018.secondary new file mode 100644 index 000000000..d0a247f15 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00018.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00019.chunk b/demo/2025-11/data/upstream-node/immutable/00019.chunk new file mode 100644 index 000000000..0e5a78254 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00019.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00019.primary b/demo/2025-11/data/upstream-node/immutable/00019.primary new file mode 100644 index 000000000..163f0d09a Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00019.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00019.secondary b/demo/2025-11/data/upstream-node/immutable/00019.secondary new file mode 100644 index 000000000..43a1b63d3 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00019.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00020.chunk b/demo/2025-11/data/upstream-node/immutable/00020.chunk new file mode 100644 index 000000000..86dc1f03e Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00020.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00020.primary b/demo/2025-11/data/upstream-node/immutable/00020.primary new file mode 100644 index 000000000..9dffe10d0 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00020.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00020.secondary b/demo/2025-11/data/upstream-node/immutable/00020.secondary new file mode 100644 index 000000000..6f9f4b5e3 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00020.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00021.chunk b/demo/2025-11/data/upstream-node/immutable/00021.chunk new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-11/data/upstream-node/immutable/00021.primary b/demo/2025-11/data/upstream-node/immutable/00021.primary new file mode 100644 index 000000000..48e4f424b Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00021.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00021.secondary b/demo/2025-11/data/upstream-node/immutable/00021.secondary new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-11/data/upstream-node/immutable/00022.chunk b/demo/2025-11/data/upstream-node/immutable/00022.chunk new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-11/data/upstream-node/immutable/00022.primary b/demo/2025-11/data/upstream-node/immutable/00022.primary new file mode 100644 index 000000000..48e4f424b Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00022.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00022.secondary b/demo/2025-11/data/upstream-node/immutable/00022.secondary new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-11/data/upstream-node/immutable/00023.chunk b/demo/2025-11/data/upstream-node/immutable/00023.chunk new file mode 100644 index 000000000..4c3ed055d Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00023.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00023.primary b/demo/2025-11/data/upstream-node/immutable/00023.primary new file mode 100644 index 000000000..3dd3ca8e9 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00023.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00023.secondary b/demo/2025-11/data/upstream-node/immutable/00023.secondary new file mode 100644 index 000000000..efe594a13 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00023.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00024.chunk b/demo/2025-11/data/upstream-node/immutable/00024.chunk new file mode 100644 index 000000000..53c872f6f Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00024.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00024.primary b/demo/2025-11/data/upstream-node/immutable/00024.primary new file mode 100644 index 000000000..0f3c16924 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00024.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00024.secondary b/demo/2025-11/data/upstream-node/immutable/00024.secondary new file mode 100644 index 000000000..65804de2f Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00024.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00025.chunk b/demo/2025-11/data/upstream-node/immutable/00025.chunk new file mode 100644 index 000000000..7ff8f1eaf Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00025.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00025.primary b/demo/2025-11/data/upstream-node/immutable/00025.primary new file mode 100644 index 000000000..b38afad2c Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00025.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00025.secondary b/demo/2025-11/data/upstream-node/immutable/00025.secondary new file mode 100644 index 000000000..654d5435c Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00025.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00026.chunk b/demo/2025-11/data/upstream-node/immutable/00026.chunk new file mode 100644 index 000000000..ec89ec932 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00026.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00026.primary b/demo/2025-11/data/upstream-node/immutable/00026.primary new file mode 100644 index 000000000..e142b3993 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00026.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00026.secondary b/demo/2025-11/data/upstream-node/immutable/00026.secondary new file mode 100644 index 000000000..615bafffe Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00026.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00027.chunk b/demo/2025-11/data/upstream-node/immutable/00027.chunk new file mode 100644 index 000000000..ec4d2a34d Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00027.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00027.primary b/demo/2025-11/data/upstream-node/immutable/00027.primary new file mode 100644 index 000000000..0cbb47687 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00027.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00027.secondary b/demo/2025-11/data/upstream-node/immutable/00027.secondary new file mode 100644 index 000000000..850d3070d Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00027.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00028.chunk b/demo/2025-11/data/upstream-node/immutable/00028.chunk new file mode 100644 index 000000000..e78a08bd6 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00028.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00028.primary b/demo/2025-11/data/upstream-node/immutable/00028.primary new file mode 100644 index 000000000..0ffe1bf25 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00028.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00028.secondary b/demo/2025-11/data/upstream-node/immutable/00028.secondary new file mode 100644 index 000000000..79862e0ca Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00028.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00029.chunk b/demo/2025-11/data/upstream-node/immutable/00029.chunk new file mode 100644 index 000000000..7d4eab3c1 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00029.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00029.primary b/demo/2025-11/data/upstream-node/immutable/00029.primary new file mode 100644 index 000000000..30f45b3e3 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00029.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00029.secondary b/demo/2025-11/data/upstream-node/immutable/00029.secondary new file mode 100644 index 000000000..8b674ff07 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00029.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00030.chunk b/demo/2025-11/data/upstream-node/immutable/00030.chunk new file mode 100644 index 000000000..0ccfdda5c Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00030.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00030.primary b/demo/2025-11/data/upstream-node/immutable/00030.primary new file mode 100644 index 000000000..6e677301f Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00030.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00030.secondary b/demo/2025-11/data/upstream-node/immutable/00030.secondary new file mode 100644 index 000000000..d1f503848 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00030.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00031.chunk b/demo/2025-11/data/upstream-node/immutable/00031.chunk new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-11/data/upstream-node/immutable/00031.primary b/demo/2025-11/data/upstream-node/immutable/00031.primary new file mode 100644 index 000000000..48e4f424b Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00031.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00031.secondary b/demo/2025-11/data/upstream-node/immutable/00031.secondary new file mode 100644 index 000000000..e69de29bb diff --git a/demo/2025-11/data/upstream-node/immutable/00032.chunk b/demo/2025-11/data/upstream-node/immutable/00032.chunk new file mode 100644 index 000000000..5ae3066c4 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00032.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00032.primary b/demo/2025-11/data/upstream-node/immutable/00032.primary new file mode 100644 index 000000000..bf89ed50d Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00032.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00032.secondary b/demo/2025-11/data/upstream-node/immutable/00032.secondary new file mode 100644 index 000000000..2c083834c Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00032.secondary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00033.chunk b/demo/2025-11/data/upstream-node/immutable/00033.chunk new file mode 100644 index 000000000..2f88e7d00 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00033.chunk differ diff --git a/demo/2025-11/data/upstream-node/immutable/00033.primary b/demo/2025-11/data/upstream-node/immutable/00033.primary new file mode 100644 index 000000000..4c8c64f17 Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00033.primary differ diff --git a/demo/2025-11/data/upstream-node/immutable/00033.secondary b/demo/2025-11/data/upstream-node/immutable/00033.secondary new file mode 100644 index 000000000..ac158489b Binary files /dev/null and b/demo/2025-11/data/upstream-node/immutable/00033.secondary differ diff --git a/demo/2025-11/manifest.json b/demo/2025-11/manifest.json new file mode 100644 index 000000000..20e96f2f2 --- /dev/null +++ b/demo/2025-11/manifest.json @@ -0,0 +1,22 @@ +[ + {"slotNo": 0, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } + , + {"slotNo": 1, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } + , + {"slotNo": 2, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } + , + {"slotNo": 3, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } + , + {"slotNo": 4, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } + , + {"slotNo": 5, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } + , + {"slotNo": 6, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } + , + {"slotNo": 7, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } + , + {"slotNo": 8, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } + , + {"slotNo": 9, "txRecipes": [ 15390, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384, 16384] } +] + diff --git a/demo/2025-11/process-compose.yaml b/demo/2025-11/process-compose.yaml new file mode 100644 index 000000000..23edf72b6 --- /dev/null +++ b/demo/2025-11/process-compose.yaml @@ -0,0 +1,230 @@ +version: "0.5" + +processes: + Init: + command: | + set -exo pipefail; + + echo "Initializing WORKING_DIR"; + if [ ! -d "$WORKING_DIR" ]; then + mkdir "$WORKING_DIR" + echo "Working directory created: $WORKING_DIR" + fi; + + cat <<-EOF > "$WORKING_DIR/.env" + CARDANO_NODE=${CARDANO_NODE:-"$DEF_CARDANO_NODE"} + IMMDB_SERVER=${IMMDB_SERVER:-"$DEF_IMMDB_SERVER"} + SECONDS_UNTIL_REF_SLOT=${SECONDS_UNTIL_REF_SLOT:-"$DEF_SECONDS_UNTIL_REF_SLOT"} + REF_SLOT=${REF_SLOT:-"$DEF_REF_SLOT"} + DATA_DIR=${DATA_DIR:-"$DEF_DATA_DIR"} + LEIOS_MANIFEST=${LEIOS_MANIFEST:-"$DEF_LEIOS_MANIFEST"} + PYTHON3=${PYTHON3:-"$DEF_PYTHON3"} + ANALYSE_PY=${ANALYSE_PY:-"$DEF_ANALYSE_PY"} + UPSTREAM_NODE_DIR="$WORKING_DIR/upstream-node" + NODE0_DIR="$WORKING_DIR/node0" + DOWNSTREAM_NODE_DIR="$WORKING_DIR/downstream-node" + UPSTREAM_NODE_PORT=${UPSTREAM_NODE_PORT:-"$DEF_UPSTREAM_NODE_PORT"} + NODE0_PORT=${NODE0_PORT:-"$DEF_NODE0_PORT"} + DOWNSTREAM_NODE_PORT=${DOWNSTREAM_NODE_PORT:-"$DEF_DOWNSTREAM_NODE_PORT"} + EOF + + set -a && source "$WORKING_DIR/.env" && set +a; + + if [ ! -d "$WORKING_DIR/genesis" ]; then + echo "Copying genesis"; + cp -fr "$DATA_DIR/genesis" "$WORKING_DIR/genesis"; + chmod -R +rw "$WORKING_DIR/genesis"; + fi; + + now=$(date +%s); + cat <<-EOF >> "$WORKING_DIR/.env" + ONSET_OF_REF_SLOT=$(( now + SECONDS_UNTIL_REF_SLOT )) + EOF + + + availability: + restart: "on_failure" + + + PrepareUpstreamNode: + command: | + set -exuo pipefail; + set -a && source "$WORKING_DIR/.env" && set +a; + + if [ -d "$UPSTREAM_NODE_DIR" ]; then + echo "Removing old $UPSTREAM_NODE_DIR" + rm -fr "$UPSTREAM_NODE_DIR"; + fi + + mkdir "$UPSTREAM_NODE_DIR"; + echo "Working directory created for upstream-node: $UPSTREAM_NODE_DIR"; + + echo "Generate the Leios DB and the schedules"; + + leiosdemo202510 generate \ + "$UPSTREAM_NODE_DIR/leios.db" \ + "$LEIOS_MANIFEST" \ + "$UPSTREAM_NODE_DIR/base-schedule.json"; + + if [[ ! -v LEIOS_SCHEDULE ]]; then + jq 'map(.[0] = 182.9)' "$UPSTREAM_NODE_DIR/base-schedule.json" > "$UPSTREAM_NODE_DIR/schedule.json" + echo "LEIOS_SCHEDULE not set, using default"; + else + cp -f "$LEIOS_SCHEDULE" "$UPSTREAM_NODE_DIR/schedule.json"; + fi; + + cp -f "$DATA_DIR/upstream-node/config.json" "$UPSTREAM_NODE_DIR/config.json"; + cp -fr "$DATA_DIR/upstream-node/immutable" "$UPSTREAM_NODE_DIR"; + chmod -R +rw "$UPSTREAM_NODE_DIR"; + + depends_on: + Init: + condition: process_completed_successfully + availability: + restart: "on_failure" + + UpstreamNode: + command: | + set -exuo pipefail; + set -a && source "$WORKING_DIR/.env" && set +a; + + cd "$UPSTREAM_NODE_DIR"; + $IMMDB_SERVER \ + --db "immutable/" \ + --config "config.json" \ + --initial-slot "$REF_SLOT" \ + --initial-time "$ONSET_OF_REF_SLOT" \ + --leios-schedule "schedule.json" \ + --leios-db "leios.db" \ + --port $((UPSTREAM_NODE_PORT)); + log_location: "${WORKING_DIR}/upstream-node/log" + depends_on: + PrepareUpstreamNode: + condition: process_completed_successfully + availability: + restart: "always" + + PrepareNode0: + command: | + set -exuo pipefail; + set -a && source "$WORKING_DIR/.env" && set +a; + + if [ -d "$NODE0_DIR" ]; then + echo "Removing old $NODE0_DIR" + rm -fr "$NODE0_DIR"; + fi + + mkdir "$NODE0_DIR"; + echo "Working directory created for node0: $NODE0_DIR"; + + cat "$DATA_DIR/leios-schema.sql" | sqlite3 "$NODE0_DIR/leios.db"; + jq --argjson port "$UPSTREAM_NODE_PORT" '.localRoots[0].accessPoints[0].port = $port' "$DATA_DIR/topology.template.json" > "$NODE0_DIR/topology.json"; + cp -f "$DATA_DIR/node0/config.json" "$NODE0_DIR/config.json"; + + depends_on: + Init: + condition: process_completed_successfully + availability: + restart: "on_failure" + + Node0: + command: | + set -exuo pipefail; + set -a && source "$WORKING_DIR/.env" && set +a; + + cd "$NODE0_DIR"; + echo $NODE0_PORT; + export LEIOS_DB_PATH="leios.db"; + "$CARDANO_NODE" run \ + --config "config.json" \ + --topology "topology.json" \ + --database-path "db" \ + --socket-path "socket" \ + --host-addr 127.0.0.1 --port "$NODE0_PORT"; + log_location: "${WORKING_DIR}/node0/log" + depends_on: + PrepareNode0: + condition: process_completed_successfully + availability: + restart: "always" + + PrepareDownstreamNode: + command: | + set -exuo pipefail; + set -a && source "$WORKING_DIR/.env" && set +a; + + if [ -d "$DOWNSTREAM_NODE_DIR" ]; then + echo "Removing old $DOWNSTREAM_NODE_DIR" + rm -fr "$DOWNSTREAM_NODE_DIR"; + fi + + mkdir "$DOWNSTREAM_NODE_DIR"; + echo "Working directory created for downstream-node: $DOWNSTREAM_NODE_DIR"; + + cat "$DATA_DIR/leios-schema.sql" | sqlite3 "$DOWNSTREAM_NODE_DIR/leios.db"; + jq --argjson port "$NODE0_PORT" '.localRoots[0].accessPoints[0].port = $port' "$DATA_DIR/topology.template.json" > "$DOWNSTREAM_NODE_DIR/topology.json"; + cp -f "$DATA_DIR/downstream-node/config.json" "$DOWNSTREAM_NODE_DIR/config.json"; + + depends_on: + Init: + condition: process_completed_successfully + availability: + restart: "on_failure" + + DownstreamNode: + command: | + set -exuo pipefail; + set -a && source "$WORKING_DIR/.env" && set +a; + + cd "$DOWNSTREAM_NODE_DIR"; + export LEIOS_DB_PATH="leios.db"; + "$CARDANO_NODE" run \ + --config "config.json" \ + --topology "topology.json" \ + --database-path "db" \ + --socket-path "socket" \ + --host-addr 127.0.0.1 --port "$DOWNSTREAM_NODE_PORT"; + + log_location: "${WORKING_DIR}/downstream-node/log" + depends_on: + PrepareDownstreamNode: + condition: process_completed_successfully + availability: + restart: "always" + + Analyze: + command: | + set -exuo pipefail; + set -a && source "$WORKING_DIR/.env" && set +a; + + while true; do + sleep 1 + "$PYTHON3" "$ANALYSE_PY" \ + "$REF_SLOT" "$ONSET_OF_REF_SLOT" \ + "$UPSTREAM_NODE_DIR/schedule.json" \ + "$UPSTREAM_NODE_DIR/log" \ + "$NODE0_DIR/log" \ + "$DOWNSTREAM_NODE_DIR/log" \ + "$WORKING_DIR/scatter_plot.png" + done; + + log_location: "${WORKING_DIR}/analyse.log" + depends_on: + Init: + condition: process_completed_successfully + availability: + restart: "always" + + Test: + command: | + set -exuo pipefail; + + while true; do + cat "$WORKING_DIR/.env"; + ls -la; + done; + depends_on: + Init: + condition: process_completed_successfully + availability: + restart: "always" diff --git a/demo/README.md b/demo/README.md index 4d5032c31..7199c10d8 100644 --- a/demo/README.md +++ b/demo/README.md @@ -1,12 +1,126 @@ -# Demos +# Leios demo -This is a collection of Leios demonstrations created using specially patched versions of `cardano-node` and other components not originating from this repository: - -- [2025-10](2025-10/): Minimum viable demo of Leios network traffic interfering with Praos -- [2025-11](2025-11/): Improvement of MVD using tc and better observability +Ouroboros Leios prototype demos. There are other, component-specific demos you might be looking for: - [Visualizer](../ui) contains a few stored scenarios that are standalone demos - [Cryptography](../crypto-benchmarks.rs/demo) demo of signing/verifying votes and certificates - [Trace translator](../scripts/trace-translator/demo) has an example/demo + +## Prototypes + +Leios prototyping is visibile in the following PRs: + +1. [cardano-node](https://github.com/IntersectMBO/cardano-node/pull/6386) +2. [ouroboros-consensus](https://github.com/IntersectMBO/ouroboros-consensus/pull/1793) +3. [ouroboros-network](https://github.com/IntersectMBO/ouroboros-network/tree/nfrisby/leios-202511-demo) + +All prototyping artifacts are in their `leios-prototype` branch. +For each demo a special tag `leios-prototype-demo-YYYYMM` will be attached to denote the components used in the demo for a particular month. + +## Flake inputs + +The repository pulls in patched cardano-node and ouroboros-consensus as visible +in [flake.nix](../flake.nix): + +```nix + cardano-node.url = "github:intersectmbo/cardano-node?ref=..."; + + ouroboros-consensus.url = "github:intersectmbo/ouroboros-consensus?ref=..."; +``` + +To point to newer/different versions you want to set the appropriate +[ref](https://git-scm.com/book/en/v2/Git-Internals-Git-References). + +> The refs in these two URLs need to identify commits that have up-to-date +> source-repository-packages for the custom commits used in ouroboros-network, +> ouroboros-consensus, cardano-node. + +```shell +nix flake lock --update-input cardano-node --update-input ouroboros-consensus +``` + +## build.nix convention + +Every `build.nix` files is a [flake-parts module](https://flake.parts/) and is +automatically loaded when found. + +## Using the repository + +Enter the shell either by + +```shell +nix develop +``` + +or if you're using Direnv the shell will automatically load once you + +```shell +direnv allow +``` + +To invoke code formatting and checks on the entire repo use + +```shell +$ nix fmt +black................................................(no files to check)Skipped +deadnix..................................................................Passed +markdownlint.............................................................Passed +nixfmt-rfc-style.........................................................Passed +shellcheck...............................................................Passed +``` + +or alternatively in the shell + +```shell +$ pre-commit run --all +black................................................(no files to check)Skipped +deadnix..................................................................Passed +markdownlint.............................................................Passed +nixfmt-rfc-style.........................................................Passed +shellcheck...............................................................Passed +``` + +This repository is using +[git-hooks.nix](https://github.com/cachix/git-hooks.nix) and to manage said +hooks edit [./pre-commit-hooks.nix](./pre-commit-hooks.nix). + +## Running the Leios 202511 demo + +Run the Leios X-Ray + +```shell +export LOG_PATH=".tmp-leios-202511-demo/*/log" +export SS_FILTER="( sport = 3001 and dport = 3002 ) or ( sport = 3002 and dport = 3001 ) or ( sport = 3002 and dport = 3003 ) or ( sport = 3003 and dport = 3002 )" +nix run git+ssh://git@github.com/IntersectMBO/ouroboros-leios#x_ray +``` + +Run the Leios experiment with default configuration + +```shell +nix run git+ssh://git@github.com/IntersectMBO/ouroboros-leios#leios_202511_demo +``` + +If you want to further configure the experiment set the following environment +variables: + +```shell +CARDANO_NODE=cardano-node +IMMDB_SERVER=immdb-server +DATA_DIR=data +REF_SLOT=41 +SECONDS_UNTIL_REF_SLOT=5 +LEIOS_MANIFEST=manifest.json +ANALYSE_PY=analyse.py +PYTHON3=python +CARDANO_NODE=cardano-node +IMMDB_SERVER=immdb-server +``` + +To clean up just delete the working directories + +```shell +rm -fr .tmp-leios-202511-demo +rm -fr .tmp-x-ray +``` diff --git a/demo/build.nix b/demo/build.nix new file mode 100644 index 000000000..20141c1a4 --- /dev/null +++ b/demo/build.nix @@ -0,0 +1,79 @@ +{ inputs, ... }: +{ + + perSystem = + { + config, + pkgs, + inputs', + system, + ... + }: + { + packages = { + leios-cardano-node = inputs'.cardano-node.packages.cardano-node; + } + // (with inputs'.ouroboros-consensus.legacyPackages.hsPkgs; { + leios-immdb-server = ouroboros-consensus-cardano.getComponent "exe:immdb-server"; + leios-demo-tool = ouroboros-consensus.getComponent "exe:leiosdemo202510"; + }); + + checks = { + pre-commit-demo = inputs.pre-commit-hooks.lib.${system}.run { + src = ./.; + hooks = import ./pre-commit-hooks.nix; + }; + }; + + devShells.dev-demo = pkgs.mkShell { + name = "dev-demo"; + + buildInputs = + config.checks.pre-commit-demo.enabledPackages + ++ [ + inputs'.cardano-node.packages.cardano-node + inputs'.cardano-node.packages.cardano-tracer + ] + ++ (with inputs'.ouroboros-consensus.legacyPackages.hsPkgs; [ + (ouroboros-consensus-cardano.getComponent "exe:immdb-server") + (ouroboros-consensus-cardano.getComponent "exe:db-analyser") + (ouroboros-consensus.getComponent "exe:leiosdemo202510") + ]) + ++ (with pkgs.python3Packages; [ + + python + ipython + pandas + altair + pip + virtualenv + python-lsp-server + black + itables + ipywidgets + jupyterlab-widgets + widgetsnbextension + jupyterlab + jupyter + plotly + matplotlib + + ]) + ++ [ + pkgs.fd + pkgs.bash + pkgs.toxiproxy + pkgs.sqlite + pkgs.grafana-alloy + pkgs.loki + pkgs.iproute2 # ss + ]; + + CARDANO_NODE = pkgs.lib.getExe inputs'.cardano-node.packages.cardano-node; + IMMDB_SERVER = pkgs.lib.getExe ( + inputs'.ouroboros-consensus.legacyPackages.hsPkgs.ouroboros-consensus-cardano.getComponent "exe:immdb-server" + ); + }; + + }; +} diff --git a/demo/extras/http_command/build.nix b/demo/extras/http_command/build.nix new file mode 100644 index 000000000..fb51aa4da --- /dev/null +++ b/demo/extras/http_command/build.nix @@ -0,0 +1,48 @@ +{ + + perSystem = + { + pkgs, + config, + ... + }: + { + packages = { + http_command_on_request = pkgs.writeShellApplication { + name = "on_request"; + text = builtins.readFile ./on_request.sh; + }; + + http_command = pkgs.writeShellApplication { + name = "http_command"; + runtimeInputs = [ + pkgs.socat + config.packages.http_command_on_request + ]; + text = builtins.readFile ./server.sh; + }; + }; + + checks.test_http_command = pkgs.stdenv.mkDerivation { + name = "test_http_command"; + src = ./.; + buildInputs = [ + pkgs.curl + config.packages.http_command + ]; + buildPhase = '' + touch $out + before=$(ls) + http_command 127.0.0.1 1337 "ls" & + sleep 1 + after=$(curl 127.0.0.1:1337) + if [[ "$before" != "$after" ]]; then + echo "Before and after should match" + echo before: $before + echo after: $after + exit 1 + fi + ''; + }; + }; +} diff --git a/demo/extras/http_command/on_request.sh b/demo/extras/http_command/on_request.sh new file mode 100755 index 000000000..8da2a149a --- /dev/null +++ b/demo/extras/http_command/on_request.sh @@ -0,0 +1,9 @@ +read -r REQUEST_LINE + +if [[ "$REQUEST_LINE" =~ ^GET ]]; then + OUTPUT=$($COMMAND) + + echo -n -e "HTTP/1.1 200 OK\r\nContent-Length: ${#OUTPUT}\r\nConnection: keep-alive\r\n\r\n${OUTPUT}" +else + echo -n -e "HTTP/1.1 405 Method Not Allowed\r\n\r\n" +fi diff --git a/demo/extras/http_command/result b/demo/extras/http_command/result new file mode 120000 index 000000000..07cc041ab --- /dev/null +++ b/demo/extras/http_command/result @@ -0,0 +1 @@ +/nix/store/2djksg4h1bzria65cfqz711zd9fcd6gk-test_ss_http_exporter \ No newline at end of file diff --git a/demo/extras/http_command/server.sh b/demo/extras/http_command/server.sh new file mode 100755 index 000000000..375f9afb7 --- /dev/null +++ b/demo/extras/http_command/server.sh @@ -0,0 +1,24 @@ +# A simple, single-threaded Bash HTTP server that executes command supplied +# as an argument and returns the output +# +# Dependencies: +# - socat +# - on_request +# +# Usage: +# ./http_command.sh 127.0.0.1 9100 "ls" + +# --- Configuration --- +LISTEN_ADDR=${1:-"0.0.0.0"} +LISTEN_PORT=${2:-9100} +COMMAND=${3:-""} +export COMMAND + +log() { + echo "[$(date +'%Y-%m-%d %H:%M:%S')] $1" +} + +log "Starting HTTP Command on ${LISTEN_ADDR}:${LISTEN_PORT}..." +log "Command: ${COMMAND}" + +socat -d TCP4-LISTEN:"$LISTEN_PORT",bind="$LISTEN_ADDR",reuseaddr,fork SYSTEM:on_request,sigint,nofork diff --git a/demo/extras/ss_to_prometheus/build.nix b/demo/extras/ss_to_prometheus/build.nix new file mode 100644 index 000000000..61ea498b7 --- /dev/null +++ b/demo/extras/ss_to_prometheus/build.nix @@ -0,0 +1,91 @@ +{ + + perSystem = + { + pkgs, + config, + ... + }: + { + packages = { + + ss_prom = pkgs.writeShellApplication { + name = "ss_prom"; + + runtimeInputs = [ + pkgs.procps + pkgs.coreutils + pkgs.iproute2 + ]; + + text = builtins.readFile ./ss_prom.sh; + }; + + ss_http_exporter = pkgs.writeShellApplication { + name = "ss_http_exporter"; + + runtimeInputs = [ + config.packages.http_command + config.packages.ss_prom + ]; + + text = builtins.readFile ./ss_http_exporter.sh; + }; + }; + + checks = { + + test_ss_to_prometheus = pkgs.stdenv.mkDerivation { + name = "test_ss_to_prometheus"; + src = ./.; + buildPhase = '' + . ${./ss_prom.sh} + cat ${./test/dport_https_sockets.ss} | ss_to_prometheus > result.prom + diff result.prom ${./test/dport_https_sockets.prom} + touch $out + ''; + }; + + test_ss_prom = pkgs.stdenv.mkDerivation { + name = "test_ss_prom"; + src = ./.; + buildInputs = [ + config.packages.ss_prom + pkgs.netcat + ]; + buildPhase = '' + nc -l 1234 & + nc -p 1337 127.0.0.1 1234 & + sleep 2 + ss_prom "dport = 1234" > result.prom + cat result.prom | grep -v "#" | cut -d " " -f 1 > got + cat ${./test/localhost_1234.prom} | grep -v "#" | cut -d " " -f 1 > wanted + diff wanted got + mv result.prom $out + ''; + }; + + test_ss_http_exporter = pkgs.stdenv.mkDerivation { + name = "test_ss_http_exporter"; + src = ./.; + buildInputs = [ + config.packages.ss_http_exporter + pkgs.curl + pkgs.netcat + ]; + buildPhase = '' + nc -l 1234 & + nc -p 1337 127.0.0.1 1234 & + ss_http_exporter 127.0.0.1 9100 "dport = 1234" & + sleep 2 + curl 127.0.0.1:9100 > result.prom + cat result.prom | grep -v "#" | cut -d " " -f 1 > got + cat ${./test/localhost_1234.prom} | grep -v "#" | cut -d " " -f 1 > wanted + diff wanted got + mv result.prom $out + ''; + }; + + }; + }; +} diff --git a/demo/extras/ss_to_prometheus/result b/demo/extras/ss_to_prometheus/result new file mode 120000 index 000000000..f215888d8 --- /dev/null +++ b/demo/extras/ss_to_prometheus/result @@ -0,0 +1 @@ +/nix/store/nmssvgpkzdrplmy8j1k9fl9f6lpr20sv-test_ss_prom \ No newline at end of file diff --git a/demo/extras/ss_to_prometheus/ss_http_exporter.sh b/demo/extras/ss_to_prometheus/ss_http_exporter.sh new file mode 100755 index 000000000..a920b26ef --- /dev/null +++ b/demo/extras/ss_to_prometheus/ss_http_exporter.sh @@ -0,0 +1,15 @@ +# HTTP exporter for `ss` +# Dependencies: +# - ss (iproute2) +# - http_command +# - ss_to_prometheus +# +# Usage: +# ./ss_http_exporter.sh 127.0.0.1 9100 "dport :443" + +# --- Configuration --- +LISTEN_ADDR=${1:-"0.0.0.0"} +LISTEN_PORT=${2:-9100} +FILTER=${3:-""} + +http_command "$LISTEN_ADDR" "$LISTEN_PORT" "ss_prom $FILTER" diff --git a/demo/extras/ss_to_prometheus/ss_prom.sh b/demo/extras/ss_to_prometheus/ss_prom.sh new file mode 100755 index 000000000..e346c9ae0 --- /dev/null +++ b/demo/extras/ss_to_prometheus/ss_prom.sh @@ -0,0 +1,324 @@ +# Translate `ss -n -i -m -t -p ` output into Prometheus metrics format +# +# Usage: +# ss_prom +# +# References +# 1. https://blog.mygraphql.com/en/notes/low-tec/network/tcp-inspect/ +# 2. https://man7.org/linux/man-pages/man8/ss.8.html +# 3. https://prometheus.io/docs/concepts/metric_types/ + +SS_METRIC_PREFIX="ss_tcp" + +# Function to split IP and Port from an address string (handles IPv4 and IPv6) +# Arguments: $1=address_port_string, $2=variable_name_for_ip, $3=variable_name_for_port +split_addr_port() { + local addr_port_str="$1" + local ip_var="$2" + local port_var="$3" + + # Check for IPv6 format: [address]:port + if [[ "$addr_port_str" =~ ^\[(.+)\]:([0-9A-Za-z]+)$ ]]; then + # Capture groups for IPv6: BASH_REMATCH[1] is IP, BASH_REMATCH[2] is Port + eval "$ip_var"="${BASH_REMATCH[1]}" + eval "$port_var"="${BASH_REMATCH[2]}" + elif [[ "$addr_port_str" =~ ^([0-9a-fA-F\.\:]+):([0-9A-Za-z]+)$ ]]; then + # Capture groups for IPv4 or non-bracketed IPv6: BASH_REMATCH[1] is IP, BASH_REMATCH[2] is Port + eval "$ip_var"="${BASH_REMATCH[1]}" + eval "$port_var"="${BASH_REMATCH[2]}" + else + # Handle cases where the port is named (e.g., :https) + IFS=':' read -r ip_val port_val <<< "$addr_port_str" + eval "$ip_var"="$ip_val" + eval "$port_var"="$port_val" + fi +} + +# Process input line by line +function ss_to_prometheus(){ + # Variables to store the labels of the current connection block + local CURRENT_LABELS="" + local CURRENT_SRC_IP="" + local CURRENT_SRC_PORT="" + local CURRENT_DST_IP="" + local CURRENT_DST_PORT="" + + while IFS= read -r line; do + # Skip header lines + if [[ "$line" =~ ^State\ Recv-Q ]]; then + continue + fi + + # ESTAB 0 0 [2001:1620:713d:1300:6b8b:54dd:34fd:9bf9]:53608 [2a00:1450:400a:1001::65]:443 users:(("firefox",pid=3642,fd=208)) + if [[ "$line" =~ ^(ESTAB|LISTEN|CLOSE|SYN-SENT|TIME-WAIT) ]]; then + # Reset metric extraction status + CURRENT_LABELS="" + + # Split the line into an array to access address fields. We need to preserve spaces for now. + # Temporarily use awk to isolate the fifth and sixth columns (Local:Port and Peer:Port) + # because Bash field splitting is unreliable due to variable white space. + line_="$(echo "$line" | tr -s ' ')" + tcp_state="$(echo "$line_" | cut -d " " -f 1)" + recv_q="$(echo "$line_" | cut -d " " -f 2)" + send_q="$(echo "$line_" | cut -d " " -f 3)" + local_addr_port="$(echo "$line_" | cut -d " " -f 4)" + peer_addr_port="$(echo "$line_" | cut -d " " -f 5)" + users="$(echo "$line_" | cut -d " " -f 6)" + + # Extract IPs and Ports + split_addr_port "$local_addr_port" "CURRENT_SRC_IP" "CURRENT_SRC_PORT" + split_addr_port "$peer_addr_port" "CURRENT_DST_IP" "CURRENT_DST_PORT" + + # Extract the program name and pid of the process + # users:(("firefox",pid=3642,fd=208)) + if [[ "$users" =~ users:\(\(\"([^\"]+)\",pid=([0-9]+) ]]; then + program="${BASH_REMATCH[1]}" + pid="${BASH_REMATCH[2]}" + CURRENT_LABELS="program=\"$program\",pid=\"$pid\"," + fi + + # Construct the Prometheus label string + CURRENT_LABELS="${CURRENT_LABELS}src_ip=\"$CURRENT_SRC_IP\",src_port=\"$CURRENT_SRC_PORT\",dst_ip=\"$CURRENT_DST_IP\",dst_port=\"$CURRENT_DST_PORT\",tcp_state=\"$tcp_state\"" + + # --- 2. Metric Line Check --- + # If labels are set and the line contains metric keywords (is indented) + elif [[ -n "$CURRENT_LABELS" ]] && [[ "$line" =~ skmem|rto|rtt|cwnd ]]; then + + # echo "# TYPE ${SS_METRIC_PREFIX}_recv_q gauge" + echo "${SS_METRIC_PREFIX}_recv_q{$CURRENT_LABELS} $recv_q" + # echo "# TYPE ${SS_METRIC_PREFIX}_send_q gauge" + echo "${SS_METRIC_PREFIX}_send_q{$CURRENT_LABELS} $send_q" + + + # --- Metric Extraction using Bash Regex --- + + # Regex captures: 1=AVG, 2=DEV + # rtt:23.037/17.652 + if [[ "$line" =~ rtt:([0-9]+\.[0-9]+)/([0-9]+\.[0-9]+) ]]; then + rtt_avg="${BASH_REMATCH[1]}" + rtt_dev="${BASH_REMATCH[2]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_rtt_avg_ms gauge" + echo "${SS_METRIC_PREFIX}_rtt_avg_ms{$CURRENT_LABELS} $rtt_avg" + # echo "# TYPE ${SS_METRIC_PREFIX}_rtt_dev_ms gauge" + echo "${SS_METRIC_PREFIX}_rtt_dev_ms{$CURRENT_LABELS} $rtt_dev" + fi + + # skmem:(r0,rb131072,t0,tb46080,f0,w0,o0,bl0,d0) + # Extract Receive Buffer (rbY from skmem:(rX,rbY,tZ,tbW)) + if [[ "$line" =~ skmem:\(r([0-9+]),rb([0-9]+),t([0-9]+),tb([0-9]+),f([0-9]+),w([0-9]+),o([0-9]+),bl([0-9]+),d([0-9]+) ]]; then + rmem_alloc="${BASH_REMATCH[1]}" + rcv_buf="${BASH_REMATCH[2]}" + wmem_alloc="${BASH_REMATCH[3]}" + snd_buf="${BASH_REMATCH[4]}" + fwd_alloc="${BASH_REMATCH[5]}" + wmem_queued="${BASH_REMATCH[6]}" + opt_mem="${BASH_REMATCH[7]}" + back_log="${BASH_REMATCH[8]}" + sock_drop="${BASH_REMATCH[9]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_rmem_alloc gauge" + echo "${SS_METRIC_PREFIX}_rmem_alloc{$CURRENT_LABELS} $rmem_alloc" + # echo "# TYPE ${SS_METRIC_PREFIX}_rcv_buf gauge" + echo "${SS_METRIC_PREFIX}_rcv_buf{$CURRENT_LABELS} $rcv_buf" + # echo "# TYPE ${SS_METRIC_PREFIX}_wmem_alloc gauge" + echo "${SS_METRIC_PREFIX}_wmem_alloc{$CURRENT_LABELS} $wmem_alloc" + # echo "# TYPE ${SS_METRIC_PREFIX}_snd_buf gauge" + echo "${SS_METRIC_PREFIX}_snd_buf{$CURRENT_LABELS} $snd_buf" + # echo "# TYPE ${SS_METRIC_PREFIX}_fwd_alloc gauge" + echo "${SS_METRIC_PREFIX}_fwd_alloc{$CURRENT_LABELS} $fwd_alloc" + # echo "# TYPE ${SS_METRIC_PREFIX}_wmem_queued gauge" + echo "${SS_METRIC_PREFIX}_wmem_queued{$CURRENT_LABELS} $wmem_queued" + # echo "# TYPE ${SS_METRIC_PREFIX}_opt_mem gauge" + echo "${SS_METRIC_PREFIX}_opt_mem{$CURRENT_LABELS} $opt_mem" + # echo "# TYPE ${SS_METRIC_PREFIX}_back_log gauge" + echo "${SS_METRIC_PREFIX}_back_log{$CURRENT_LABELS} $back_log" + # echo "# TYPE ${SS_METRIC_PREFIX}_sock_drop gauge" + echo "${SS_METRIC_PREFIX}_sock_drop{$CURRENT_LABELS} $sock_drop" + fi + + # bytes_sent:33496 + if [[ "$line" =~ bytes_sent:([0-9]+) ]]; then + bytes_sent="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_bytes_sent counter" + echo "${SS_METRIC_PREFIX}_bytes_sent{$CURRENT_LABELS} $bytes_sent" + fi + + # bytes_acked:33497 + if [[ "$line" =~ bytes_acked:([0-9]+) ]]; then + bytes_acked="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_bytes_acked counter" + echo "${SS_METRIC_PREFIX}_bytes_acked{$CURRENT_LABELS} $bytes_acked" + fi + + # bytes_received:52142 + if [[ "$line" =~ bytes_received:([0-9]+) ]]; then + bytes_received="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_bytes_received counter" + echo "${SS_METRIC_PREFIX}_bytes_received{$CURRENT_LABELS} $bytes_received" + fi + + # segs_out:852 + if [[ "$line" =~ segs_out:([0-9]+) ]]; then + segs_out="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_segs_out counter" + echo "${SS_METRIC_PREFIX}_segs_out{$CURRENT_LABELS} $segs_out" + fi + + # segs_in:681 + if [[ "$line" =~ segs_in:([0-9]+) ]]; then + segs_in="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_segs_in counter" + echo "${SS_METRIC_PREFIX}_segs_in{$CURRENT_LABELS} $segs_in" + fi + + # data_segs_out:491 + if [[ "$line" =~ data_segs_out:([0-9]+) ]]; then + data_segs_out="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_data_segs_out counter" + echo "${SS_METRIC_PREFIX}_data_segs_out{$CURRENT_LABELS} $data_segs_out" + fi + + # data_segs_in:360 + if [[ "$line" =~ data_segs_in:([0-9]+) ]]; then + data_segs_in="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_data_segs_in counter" + echo "${SS_METRIC_PREFIX}_data_segs_in{$CURRENT_LABELS} $data_segs_in" + fi + + # lastsnd:242 + if [[ "$line" =~ lastsnd:([0-9]+) ]]; then + lastsnd="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_lastsnd_ms gauge" + echo "${SS_METRIC_PREFIX}_lastsnd_ms{$CURRENT_LABELS} $lastsnd" + fi + + # lastrcv:230 + if [[ "$line" =~ lastrcv:([0-9]+) ]]; then + lastrcv="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_lastrcv_ms gauge" + echo "${SS_METRIC_PREFIX}_lastrcv_ms{$CURRENT_LABELS} $lastrcv" + fi + + # lastack:230 + if [[ "$line" =~ lastack:([0-9]+) ]]; then + lastack="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_lastack_ms gauge" + echo "${SS_METRIC_PREFIX}_lastack_ms{$CURRENT_LABELS} $lastack" + fi + + # ato:40 + if [[ "$line" =~ ato:([0-9]+) ]]; then + ato="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_ato_ms gauge" + echo "${SS_METRIC_PREFIX}_ato_ms{$CURRENT_LABELS} $ato" + fi + + # mss:1288 + if [[ "$line" =~ mss:([0-9]+) ]]; then + mss="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_mss gauge" + echo "${SS_METRIC_PREFIX}_mss{$CURRENT_LABELS} $mss" + fi + + # pmtu:1500 + if [[ "$line" =~ pmtu:([0-9]+) ]]; then + pmtu="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_pmtu gauge" + echo "${SS_METRIC_PREFIX}_pmtu{$CURRENT_LABELS} $pmtu" + fi + + # rcvmss:1288 + if [[ "$line" =~ rcvmss:([0-9]+) ]]; then + rcvmss="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_rcvmss gauge" + echo "${SS_METRIC_PREFIX}_rcvmss{$CURRENT_LABELS} $rcvmss" + fi + + # advmss:1448 + if [[ "$line" =~ advmss:([0-9]+) ]]; then + advmss="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_advmss gauge" + echo "${SS_METRIC_PREFIX}_advmss{$CURRENT_LABELS} $advmss" + fi + + # cwnd:10 + if [[ "$line" =~ cwnd:([0-9]+) ]]; then + cwnd="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_cwnd gauge" + echo "${SS_METRIC_PREFIX}_cwnd{$CURRENT_LABELS} $cwnd" + fi + + # rto:224 + if [[ "$line" =~ rto:([0-9]+) ]]; then + rto="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_rto_ms gauge" + echo "${SS_METRIC_PREFIX}_rto_ms{$CURRENT_LABELS} $rto" + fi + + # delivered:383 + if [[ "$line" =~ delivered:([0-9]+) ]]; then + delivered="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_delivered gauge" + echo "${SS_METRIC_PREFIX}_delivered{$CURRENT_LABELS} $delivered" + fi + + # busy:9998ms + if [[ "$line" =~ busy:([0-9]+)ms ]]; then + busy="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_busy_ms gauge" + echo "${SS_METRIC_PREFIX}_busy_ms{$CURRENT_LABELS} $busy" + fi + + # rcv_space:14480 + if [[ "$line" =~ rcv_space:([0-9]+) ]]; then + rcv_space="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_rcv_space gauge" + echo "${SS_METRIC_PREFIX}_rcv_space{$CURRENT_LABELS} $rcv_space" + fi + + # rcv_ssthresh:86953 + if [[ "$line" =~ rcv_ssthresh:([0-9]+) ]]; then + rcv_ssthresh="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_rcv_ssthresh gauge" + echo "${SS_METRIC_PREFIX}_rcv_ssthresh{$CURRENT_LABELS} $rcv_ssthresh" + fi + + # minrtt:9.682 + if [[ "$line" =~ minrtt:([0-9]+.[0-9]+) ]]; then + minrtt="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_rcv_minrtt gauge" + echo "${SS_METRIC_PREFIX}_minrtt{$CURRENT_LABELS} $minrtt" + fi + + # snd_wnd:40960 + if [[ "$line" =~ snd_wnd:([0-9]+) ]]; then + snd_wnd="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_snd_wnd gauge" + echo "${SS_METRIC_PREFIX}_snd_wnd{$CURRENT_LABELS} $snd_wnd" + fi + + # rcv_wnd:87040 + if [[ "$line" =~ rcv_wnd:([0-9]+) ]]; then + rcv_wnd="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_rcv_wnd gauge" + echo "${SS_METRIC_PREFIX}_rcv_wnd{$CURRENT_LABELS} $rcv_wnd" + fi + + # notsent:49232 + if [[ "$line" =~ notsent:([0-9]+) ]]; then + notsent="${BASH_REMATCH[1]}" + # echo "# TYPE ${SS_METRIC_PREFIX}_notsent gauge" + echo "${SS_METRIC_PREFIX}_notsent{$CURRENT_LABELS} $notsent" + fi + + # Clear the labels for the next connection block + CURRENT_LABELS="" + fi + done +} + +# https://stackoverflow.com/questions/2683279/how-to-detect-if-a-script-is-being-sourced +(return 0 2>/dev/null) && sourced=1 || sourced=0 + +if [[ $sourced == 0 ]]; then + ss -n -i -m -t -p "$@" | ss_to_prometheus +fi diff --git a/demo/extras/ss_to_prometheus/test/dport_https_sockets.prom b/demo/extras/ss_to_prometheus/test/dport_https_sockets.prom new file mode 100644 index 000000000..4704f96ac --- /dev/null +++ b/demo/extras/ss_to_prometheus/test/dport_https_sockets.prom @@ -0,0 +1,472 @@ +ss_tcp_recv_q{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_send_q{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rtt_avg_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 91.09 +ss_tcp_rtt_dev_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 0.487 +ss_tcp_rmem_alloc{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rcv_buf{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 131072 +ss_tcp_wmem_alloc{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_snd_buf{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 368640 +ss_tcp_fwd_alloc{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_wmem_queued{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_opt_mem{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_back_log{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_sock_drop{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_bytes_sent{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 1624932 +ss_tcp_bytes_acked{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 1624464 +ss_tcp_bytes_received{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 5293 +ss_tcp_segs_out{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 6697 +ss_tcp_segs_in{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 4607 +ss_tcp_data_segs_out{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 6690 +ss_tcp_data_segs_in{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 46 +ss_tcp_lastsnd_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 1174 +ss_tcp_lastrcv_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 1572 +ss_tcp_lastack_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 1083 +ss_tcp_ato_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 40 +ss_tcp_mss{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 1388 +ss_tcp_pmtu{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 1500 +ss_tcp_rcvmss{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 1448 +ss_tcp_advmss{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 1448 +ss_tcp_cwnd{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 10 +ss_tcp_rto_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 292 +ss_tcp_delivered{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 6688 +ss_tcp_busy_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 95572 +ss_tcp_rcv_space{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 14480 +ss_tcp_rcv_ssthresh{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 78568 +ss_tcp_minrtt{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 89.134 +ss_tcp_snd_wnd{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 1089792 +ss_tcp_rcv_wnd{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="36088",dst_ip="178.128.133.161",dst_port="443",tcp_state="ESTAB"} 78592 +ss_tcp_recv_q{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_send_q{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rtt_avg_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 24.858 +ss_tcp_rtt_dev_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 19.063 +ss_tcp_rmem_alloc{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rcv_buf{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 446170 +ss_tcp_wmem_alloc{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_snd_buf{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 46080 +ss_tcp_fwd_alloc{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_wmem_queued{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_opt_mem{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_back_log{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_sock_drop{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 13 +ss_tcp_bytes_sent{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 162547 +ss_tcp_bytes_acked{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 162548 +ss_tcp_bytes_received{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 527520 +ss_tcp_segs_out{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 4877 +ss_tcp_segs_in{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 4113 +ss_tcp_data_segs_out{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 2289 +ss_tcp_data_segs_in{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 2644 +ss_tcp_lastsnd_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 4145 +ss_tcp_lastrcv_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 4134 +ss_tcp_lastack_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 4134 +ss_tcp_ato_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 63 +ss_tcp_mss{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 1288 +ss_tcp_pmtu{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 1500 +ss_tcp_rcvmss{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 1288 +ss_tcp_advmss{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 1448 +ss_tcp_cwnd{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 10 +ss_tcp_rto_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 225 +ss_tcp_delivered{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 2290 +ss_tcp_busy_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 58609 +ss_tcp_rcv_space{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 31996 +ss_tcp_rcv_ssthresh{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 297429 +ss_tcp_minrtt{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 10.017 +ss_tcp_snd_wnd{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 40960 +ss_tcp_rcv_wnd{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="59858",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 297472 +ss_tcp_recv_q{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_send_q{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rtt_avg_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 105.284 +ss_tcp_rtt_dev_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 6.383 +ss_tcp_rmem_alloc{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rcv_buf{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 131072 +ss_tcp_wmem_alloc{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_snd_buf{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 87040 +ss_tcp_fwd_alloc{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_wmem_queued{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_opt_mem{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_back_log{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_sock_drop{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_bytes_sent{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 27086 +ss_tcp_bytes_acked{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 27087 +ss_tcp_bytes_received{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 6410 +ss_tcp_segs_out{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 89 +ss_tcp_segs_in{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 89 +ss_tcp_data_segs_out{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 62 +ss_tcp_data_segs_in{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 47 +ss_tcp_lastsnd_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 35149 +ss_tcp_lastrcv_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 35149 +ss_tcp_lastack_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 35043 +ss_tcp_ato_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 40 +ss_tcp_mss{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 1424 +ss_tcp_pmtu{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 1500 +ss_tcp_rcvmss{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 1424 +ss_tcp_advmss{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 1448 +ss_tcp_cwnd{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 10 +ss_tcp_rto_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 306 +ss_tcp_delivered{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 63 +ss_tcp_busy_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 3890 +ss_tcp_rcv_space{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 14480 +ss_tcp_rcv_ssthresh{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 75480 +ss_tcp_minrtt{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 100.048 +ss_tcp_snd_wnd{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 143360 +ss_tcp_rcv_wnd{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="49986",dst_ip="140.82.112.26",dst_port="443",tcp_state="ESTAB"} 75520 +ss_tcp_recv_q{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 40 +ss_tcp_send_q{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 0 +ss_tcp_rtt_avg_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 5.93 +ss_tcp_rtt_dev_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 2.212 +ss_tcp_bytes_sent{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 753 +ss_tcp_bytes_acked{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 754 +ss_tcp_bytes_received{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 515 +ss_tcp_segs_out{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 15 +ss_tcp_segs_in{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 14 +ss_tcp_data_segs_out{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 2 +ss_tcp_data_segs_in{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 4 +ss_tcp_lastsnd_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 296749 +ss_tcp_lastrcv_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 56742 +ss_tcp_lastack_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 11657 +ss_tcp_ato_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 40 +ss_tcp_mss{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 1428 +ss_tcp_pmtu{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 1500 +ss_tcp_rcvmss{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 536 +ss_tcp_advmss{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 1448 +ss_tcp_cwnd{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 10 +ss_tcp_rto_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 206 +ss_tcp_delivered{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 3 +ss_tcp_busy_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 10 +ss_tcp_rcv_space{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 14480 +ss_tcp_rcv_ssthresh{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 64088 +ss_tcp_minrtt{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 4.489 +ss_tcp_snd_wnd{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 67072 +ss_tcp_rcv_wnd{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="47938",dst_ip="143.204.55.127",dst_port="443",tcp_state="CLOSE-WAIT"} 64128 +ss_tcp_recv_q{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_send_q{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rtt_avg_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 7.038 +ss_tcp_rtt_dev_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 2.378 +ss_tcp_rmem_alloc{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rcv_buf{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 131072 +ss_tcp_wmem_alloc{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_snd_buf{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 87040 +ss_tcp_fwd_alloc{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_wmem_queued{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_opt_mem{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_back_log{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_sock_drop{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_bytes_sent{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 2097 +ss_tcp_bytes_acked{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 2098 +ss_tcp_bytes_received{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 1266 +ss_tcp_segs_out{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 10 +ss_tcp_segs_in{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 9 +ss_tcp_data_segs_out{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 5 +ss_tcp_data_segs_in{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 4 +ss_tcp_lastsnd_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 146688 +ss_tcp_lastrcv_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 146688 +ss_tcp_lastack_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 146682 +ss_tcp_ato_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 40 +ss_tcp_mss{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 1400 +ss_tcp_pmtu{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 1500 +ss_tcp_rcvmss{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 832 +ss_tcp_advmss{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 1448 +ss_tcp_cwnd{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 10 +ss_tcp_rto_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 208 +ss_tcp_delivered{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 6 +ss_tcp_busy_ms{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 30 +ss_tcp_rcv_space{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 14480 +ss_tcp_rcv_ssthresh{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 64088 +ss_tcp_minrtt{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 5.286 +ss_tcp_snd_wnd{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 267264 +ss_tcp_rcv_wnd{program="firefox",pid="39648",src_ip="192.168.178.21",src_port="46866",dst_ip="34.107.243.93",dst_port="443",tcp_state="ESTAB"} 63232 +ss_tcp_recv_q{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_send_q{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rtt_avg_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 22.971 +ss_tcp_rtt_dev_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 17.416 +ss_tcp_rmem_alloc{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rcv_buf{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 1956004 +ss_tcp_wmem_alloc{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_snd_buf{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 46080 +ss_tcp_fwd_alloc{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_wmem_queued{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_opt_mem{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_back_log{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_sock_drop{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_bytes_sent{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 132374 +ss_tcp_bytes_acked{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 132375 +ss_tcp_bytes_received{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 205879 +ss_tcp_segs_out{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 3639 +ss_tcp_segs_in{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 2923 +ss_tcp_data_segs_out{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 2106 +ss_tcp_data_segs_in{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 1532 +ss_tcp_lastsnd_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 2016 +ss_tcp_lastrcv_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 2005 +ss_tcp_lastack_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 2005 +ss_tcp_ato_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 40 +ss_tcp_mss{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 1288 +ss_tcp_pmtu{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 1500 +ss_tcp_rcvmss{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 1288 +ss_tcp_advmss{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 1448 +ss_tcp_cwnd{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 10 +ss_tcp_rto_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 223 +ss_tcp_delivered{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 2107 +ss_tcp_busy_ms{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 54867 +ss_tcp_rcv_space{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 67242 +ss_tcp_rcv_ssthresh{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 305315 +ss_tcp_minrtt{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 9.308 +ss_tcp_snd_wnd{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 40960 +ss_tcp_rcv_wnd{program="slack",pid="1109505",src_ip="192.168.178.21",src_port="54908",dst_ip="3.67.245.95",dst_port="443",tcp_state="ESTAB"} 305408 +ss_tcp_recv_q{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_send_q{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rtt_avg_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 5.101 +ss_tcp_rtt_dev_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 1.185 +ss_tcp_rmem_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rcv_buf{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 2020034 +ss_tcp_wmem_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_snd_buf{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 87040 +ss_tcp_fwd_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_wmem_queued{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_opt_mem{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_back_log{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_sock_drop{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 2 +ss_tcp_bytes_sent{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 334953 +ss_tcp_bytes_acked{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 334954 +ss_tcp_bytes_received{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 91562 +ss_tcp_segs_out{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 477 +ss_tcp_segs_in{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 585 +ss_tcp_data_segs_out{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 389 +ss_tcp_data_segs_in{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 258 +ss_tcp_lastsnd_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 5842 +ss_tcp_lastrcv_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 5842 +ss_tcp_lastack_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 5834 +ss_tcp_ato_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 40 +ss_tcp_mss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 1428 +ss_tcp_pmtu{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 1500 +ss_tcp_rcvmss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 1208 +ss_tcp_advmss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 1428 +ss_tcp_cwnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 10 +ss_tcp_rto_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 206 +ss_tcp_delivered{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 390 +ss_tcp_busy_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 822 +ss_tcp_rcv_space{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 66868 +ss_tcp_rcv_ssthresh{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 168722 +ss_tcp_minrtt{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 2.824 +ss_tcp_snd_wnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 143616 +ss_tcp_rcv_wnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="44686",dst_ip="2a00:1450:400a:803::200e",dst_port="443",tcp_state="ESTAB"} 168832 +ss_tcp_recv_q{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_send_q{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rtt_avg_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 4.06 +ss_tcp_rtt_dev_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 0.718 +ss_tcp_rmem_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rcv_buf{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 2199713 +ss_tcp_wmem_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_snd_buf{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 87040 +ss_tcp_fwd_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_wmem_queued{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_opt_mem{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_back_log{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_sock_drop{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 5 +ss_tcp_bytes_sent{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 217578 +ss_tcp_bytes_acked{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 217579 +ss_tcp_bytes_received{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 179757 +ss_tcp_segs_out{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 1669 +ss_tcp_segs_in{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 2043 +ss_tcp_data_segs_out{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 592 +ss_tcp_data_segs_in{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 1474 +ss_tcp_lastsnd_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 94422 +ss_tcp_lastrcv_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 11852 +ss_tcp_lastack_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 11852 +ss_tcp_ato_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 40 +ss_tcp_mss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 1428 +ss_tcp_pmtu{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 1500 +ss_tcp_rcvmss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 1208 +ss_tcp_advmss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 1428 +ss_tcp_cwnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 10 +ss_tcp_rto_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 205 +ss_tcp_delivered{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 593 +ss_tcp_busy_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 1775 +ss_tcp_rcv_space{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 66770 +ss_tcp_rcv_ssthresh{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 215004 +ss_tcp_minrtt{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 2.941 +ss_tcp_snd_wnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 143616 +ss_tcp_rcv_wnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="51706",dst_ip="2a00:1450:400a:1000::5f",dst_port="443",tcp_state="ESTAB"} 215040 +ss_tcp_recv_q{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_send_q{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rtt_avg_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 7.269 +ss_tcp_rtt_dev_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 2.039 +ss_tcp_rmem_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rcv_buf{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 131072 +ss_tcp_wmem_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_snd_buf{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 87040 +ss_tcp_fwd_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_wmem_queued{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_opt_mem{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_back_log{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_sock_drop{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_bytes_sent{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 5655 +ss_tcp_bytes_acked{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 5656 +ss_tcp_bytes_received{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 3902 +ss_tcp_segs_out{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 18 +ss_tcp_segs_in{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 18 +ss_tcp_data_segs_out{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 10 +ss_tcp_data_segs_in{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 9 +ss_tcp_lastsnd_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 20443 +ss_tcp_lastrcv_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 20435 +ss_tcp_lastack_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 20435 +ss_tcp_ato_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 40 +ss_tcp_mss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 1428 +ss_tcp_pmtu{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 1500 +ss_tcp_rcvmss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 1208 +ss_tcp_advmss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 1428 +ss_tcp_cwnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 10 +ss_tcp_rto_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 208 +ss_tcp_delivered{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 11 +ss_tcp_busy_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 37 +ss_tcp_rcv_space{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 14280 +ss_tcp_rcv_ssthresh{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 64108 +ss_tcp_minrtt{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 4.816 +ss_tcp_snd_wnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 264960 +ss_tcp_rcv_wnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="58914",dst_ip="2a00:1450:400a:1000::65",dst_port="443",tcp_state="ESTAB"} 61312 +ss_tcp_recv_q{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_send_q{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rtt_avg_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 15.926 +ss_tcp_rtt_dev_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 0.48 +ss_tcp_rmem_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rcv_buf{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 3327263 +ss_tcp_wmem_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_snd_buf{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 87040 +ss_tcp_fwd_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_wmem_queued{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_opt_mem{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_back_log{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_sock_drop{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 9 +ss_tcp_bytes_sent{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 37765 +ss_tcp_bytes_acked{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 37766 +ss_tcp_bytes_received{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 141395 +ss_tcp_segs_out{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 5912 +ss_tcp_segs_in{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 5962 +ss_tcp_data_segs_out{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 1073 +ss_tcp_data_segs_in{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 4889 +ss_tcp_lastsnd_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 14309 +ss_tcp_lastrcv_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 1483 +ss_tcp_lastack_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 1483 +ss_tcp_ato_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 40 +ss_tcp_mss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 1428 +ss_tcp_pmtu{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 1500 +ss_tcp_rcvmss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 1428 +ss_tcp_advmss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 1428 +ss_tcp_cwnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 10 +ss_tcp_rto_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 216 +ss_tcp_delivered{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 1074 +ss_tcp_busy_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 19183 +ss_tcp_rcv_space{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 68272 +ss_tcp_rcv_ssthresh{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 64108 +ss_tcp_minrtt{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 13.995 +ss_tcp_snd_wnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 150016 +ss_tcp_rcv_wnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="41268",dst_ip="2a04:4e42:41::347",dst_port="443",tcp_state="ESTAB"} 64128 +ss_tcp_recv_q{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_send_q{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rtt_avg_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 6.332 +ss_tcp_rtt_dev_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 2.101 +ss_tcp_rmem_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rcv_buf{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 131072 +ss_tcp_wmem_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_snd_buf{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 87040 +ss_tcp_fwd_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_wmem_queued{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_opt_mem{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_back_log{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_sock_drop{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_bytes_sent{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 1975 +ss_tcp_bytes_acked{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 1976 +ss_tcp_bytes_received{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 6510 +ss_tcp_segs_out{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 22 +ss_tcp_segs_in{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 19 +ss_tcp_data_segs_out{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 8 +ss_tcp_data_segs_in{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 12 +ss_tcp_lastsnd_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 44725 +ss_tcp_lastrcv_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 44720 +ss_tcp_lastack_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 44720 +ss_tcp_ato_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 40 +ss_tcp_mss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 1428 +ss_tcp_pmtu{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 1500 +ss_tcp_rcvmss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 1208 +ss_tcp_advmss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 1428 +ss_tcp_cwnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 10 +ss_tcp_rto_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 207 +ss_tcp_delivered{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 9 +ss_tcp_busy_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 37 +ss_tcp_rcv_space{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 14280 +ss_tcp_rcv_ssthresh{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 73857 +ss_tcp_minrtt{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 3.298 +ss_tcp_snd_wnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 268544 +ss_tcp_rcv_wnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49760",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 73984 +ss_tcp_recv_q{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_send_q{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rtt_avg_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 4.874 +ss_tcp_rtt_dev_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 1.238 +ss_tcp_rmem_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rcv_buf{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 131072 +ss_tcp_wmem_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_snd_buf{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 87040 +ss_tcp_fwd_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_wmem_queued{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_opt_mem{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_back_log{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_sock_drop{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_bytes_sent{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 12086 +ss_tcp_bytes_acked{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 12087 +ss_tcp_bytes_received{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 4764 +ss_tcp_segs_out{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 25 +ss_tcp_segs_in{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 31 +ss_tcp_data_segs_out{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 17 +ss_tcp_data_segs_in{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 16 +ss_tcp_lastsnd_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 2111 +ss_tcp_lastrcv_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 2111 +ss_tcp_lastack_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 2107 +ss_tcp_ato_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 40 +ss_tcp_mss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 1428 +ss_tcp_pmtu{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 1500 +ss_tcp_rcvmss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 1208 +ss_tcp_advmss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 1428 +ss_tcp_cwnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 10 +ss_tcp_rto_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 205 +ss_tcp_delivered{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 18 +ss_tcp_busy_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 36 +ss_tcp_rcv_space{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 14280 +ss_tcp_rcv_ssthresh{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 76519 +ss_tcp_minrtt{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 3.426 +ss_tcp_snd_wnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 258816 +ss_tcp_rcv_wnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="60036",dst_ip="2a00:1450:400a:1001::65",dst_port="443",tcp_state="ESTAB"} 76544 +ss_tcp_recv_q{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_send_q{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rtt_avg_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 5.224 +ss_tcp_rtt_dev_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 0.776 +ss_tcp_rmem_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_rcv_buf{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 131072 +ss_tcp_wmem_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_snd_buf{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 87040 +ss_tcp_fwd_alloc{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_wmem_queued{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_opt_mem{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_back_log{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_sock_drop{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 0 +ss_tcp_bytes_sent{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 2772 +ss_tcp_bytes_acked{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 2773 +ss_tcp_bytes_received{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 2029 +ss_tcp_segs_out{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 14 +ss_tcp_segs_in{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 11 +ss_tcp_data_segs_out{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 7 +ss_tcp_data_segs_in{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 6 +ss_tcp_lastsnd_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 44725 +ss_tcp_lastrcv_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 44720 +ss_tcp_lastack_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 44720 +ss_tcp_ato_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 40 +ss_tcp_mss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 1428 +ss_tcp_pmtu{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 1500 +ss_tcp_rcvmss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 1208 +ss_tcp_advmss{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 1428 +ss_tcp_cwnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 10 +ss_tcp_rto_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 206 +ss_tcp_delivered{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 8 +ss_tcp_busy_ms{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 22 +ss_tcp_rcv_space{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 14280 +ss_tcp_rcv_ssthresh{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 67824 +ss_tcp_minrtt{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 4.409 +ss_tcp_snd_wnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 267520 +ss_tcp_rcv_wnd{program="firefox",pid="39648",src_ip="2001:1620:713d:1300:b43c:fc6b:cb53:3c03",src_port="49758",dst_ip="2a00:1450:400a:803::2001",dst_port="443",tcp_state="ESTAB"} 67840 diff --git a/demo/extras/ss_to_prometheus/test/dport_https_sockets.ss b/demo/extras/ss_to_prometheus/test/dport_https_sockets.ss new file mode 100644 index 000000000..012b74f88 --- /dev/null +++ b/demo/extras/ss_to_prometheus/test/dport_https_sockets.ss @@ -0,0 +1,27 @@ +State Recv-Q Send-Q Local Address:Port Peer Address:PortProcess +ESTAB 0 0 192.168.178.21:36088 178.128.133.161:443 users:(("firefox",pid=39648,fd=198)) + skmem:(r0,rb131072,t0,tb368640,f0,w0,o0,bl0,d0) cubic wscale:7,7 rto:292 rtt:91.09/0.487 ato:40 mss:1388 pmtu:1500 rcvmss:1448 advmss:1448 cwnd:10 ssthresh:13 bytes_sent:1624932 bytes_retrans:469 bytes_acked:1624464 bytes_received:5293 segs_out:6697 segs_in:4607 data_segs_out:6690 data_segs_in:46 send 1219014bps lastsnd:1174 lastrcv:1572 lastack:1083 pacing_rate 1462808bps delivery_rate 6863544bps delivered:6688 busy:95572ms retrans:0/1 rcv_rtt:94 rcv_space:14480 rcv_ssthresh:78568 minrtt:89.134 snd_wnd:1089792 rcv_wnd:78592 +ESTAB 0 0 192.168.178.21:59858 3.67.245.95:443 users:(("slack",pid=1109505,fd=37)) + skmem:(r0,rb446170,t0,tb46080,f0,w0,o0,bl0,d13) cubic wscale:12,7 rto:225 rtt:24.858/19.063 ato:63 mss:1288 pmtu:1500 rcvmss:1288 advmss:1448 cwnd:10 bytes_sent:162547 bytes_acked:162548 bytes_received:527520 segs_out:4877 segs_in:4113 data_segs_out:2289 data_segs_in:2644 send 4145144bps lastsnd:4145 lastrcv:4134 lastack:4134 pacing_rate 8290288bps delivery_rate 2396088bps delivered:2290 app_limited busy:58609ms rcv_rtt:2406.7 rcv_space:31996 rcv_ssthresh:297429 minrtt:10.017 snd_wnd:40960 rcv_wnd:297472 +ESTAB 0 0 192.168.178.21:49986 140.82.112.26:443 users:(("firefox",pid=39648,fd=169)) + skmem:(r0,rb131072,t0,tb87040,f0,w0,o0,bl0,d0) cubic wscale:10,7 rto:306 rtt:105.284/6.383 ato:40 mss:1424 pmtu:1500 rcvmss:1424 advmss:1448 cwnd:10 bytes_sent:27086 bytes_acked:27087 bytes_received:6410 segs_out:89 segs_in:89 data_segs_out:62 data_segs_in:47 send 1082026bps lastsnd:35149 lastrcv:35149 lastack:35043 pacing_rate 2164032bps delivery_rate 459488bps delivered:63 app_limited busy:3890ms rcv_space:14480 rcv_ssthresh:75480 minrtt:100.048 snd_wnd:143360 rcv_wnd:75520 +CLOSE-WAIT 40 0 192.168.178.21:47938 143.204.55.127:443 users:(("slack",pid=1109505,fd=28)) + skmem:(r896,rb131072,t0,tb87040,f3200,w0,o0,bl0,d2) cubic wscale:9,7 rto:206 rtt:5.93/2.212 ato:40 mss:1428 pmtu:1500 rcvmss:536 advmss:1448 cwnd:10 bytes_sent:753 bytes_acked:754 bytes_received:515 segs_out:15 segs_in:14 data_segs_out:2 data_segs_in:4 send 19264755bps lastsnd:296749 lastrcv:56742 lastack:11657 pacing_rate 38527880bps delivery_rate 2544880bps delivered:3 app_limited busy:10ms rcv_space:14480 rcv_ssthresh:64088 minrtt:4.489 rcv_ooopack:1 snd_wnd:67072 rcv_wnd:64128 +ESTAB 0 0 192.168.178.21:46866 34.107.243.93:443 users:(("firefox",pid=39648,fd=159)) + skmem:(r0,rb131072,t0,tb87040,f0,w0,o0,bl0,d0) cubic wscale:8,7 rto:208 rtt:7.038/2.378 ato:40 mss:1400 pmtu:1500 rcvmss:832 advmss:1448 cwnd:10 bytes_sent:2097 bytes_acked:2098 bytes_received:1266 segs_out:10 segs_in:9 data_segs_out:5 data_segs_in:4 send 15913612bps lastsnd:146688 lastrcv:146688 lastack:146682 pacing_rate 31823832bps delivery_rate 2826496bps delivered:6 app_limited busy:30ms rcv_space:14480 rcv_ssthresh:64088 minrtt:5.286 snd_wnd:267264 rcv_wnd:63232 +ESTAB 0 0 192.168.178.21:54908 3.67.245.95:443 users:(("slack",pid=1109505,fd=32)) + skmem:(r0,rb1956004,t0,tb46080,f0,w0,o0,bl0,d0) cubic wscale:12,7 rto:223 rtt:22.971/17.416 ato:40 mss:1288 pmtu:1500 rcvmss:1288 advmss:1448 cwnd:10 bytes_sent:132374 bytes_acked:132375 bytes_received:205879 segs_out:3639 segs_in:2923 data_segs_out:2106 data_segs_in:1532 send 4485656bps lastsnd:2016 lastrcv:2005 lastack:2005 pacing_rate 8970968bps delivery_rate 2514192bps delivered:2107 app_limited busy:54867ms rcv_rtt:472681 rcv_space:67242 rcv_ssthresh:305315 minrtt:9.308 snd_wnd:40960 rcv_wnd:305408 +ESTAB 0 0 [2001:1620:713d:1300:b43c:fc6b:cb53:3c03]:44686 [2a00:1450:400a:803::200e]:443 users:(("firefox",pid=39648,fd=117)) + skmem:(r0,rb2020034,t0,tb87040,f0,w0,o0,bl0,d2) cubic wscale:8,7 rto:206 rtt:5.101/1.185 ato:40 mss:1428 pmtu:1500 rcvmss:1208 advmss:1428 cwnd:10 bytes_sent:334953 bytes_acked:334954 bytes_received:91562 segs_out:477 segs_in:585 data_segs_out:389 data_segs_in:258 send 22395609bps lastsnd:5842 lastrcv:5842 lastack:5834 pacing_rate 44787920bps delivery_rate 13317272bps delivered:390 app_limited busy:822ms rcv_rtt:275586 rcv_space:66868 rcv_ssthresh:168722 minrtt:2.824 snd_wnd:143616 rcv_wnd:168832 +ESTAB 0 0 [2001:1620:713d:1300:b43c:fc6b:cb53:3c03]:51706 [2a00:1450:400a:1000::5f]:443 users:(("firefox",pid=39648,fd=167)) + skmem:(r0,rb2199713,t0,tb87040,f0,w0,o0,bl0,d5) cubic wscale:8,7 rto:205 rtt:4.06/0.718 ato:40 mss:1428 pmtu:1500 rcvmss:1208 advmss:1428 cwnd:10 bytes_sent:217578 bytes_acked:217579 bytes_received:179757 segs_out:1669 segs_in:2043 data_segs_out:592 data_segs_in:1474 send 28137931bps lastsnd:94422 lastrcv:11852 lastack:11852 pacing_rate 56265464bps delivery_rate 12707448bps delivered:593 app_limited busy:1775ms rcv_rtt:27716.4 rcv_space:66770 rcv_ssthresh:215004 minrtt:2.941 rcv_ooopack:1 snd_wnd:143616 rcv_wnd:215040 +ESTAB 0 0 [2001:1620:713d:1300:b43c:fc6b:cb53:3c03]:58914 [2a00:1450:400a:1000::65]:443 users:(("firefox",pid=39648,fd=162)) + skmem:(r0,rb131072,t0,tb87040,f0,w0,o0,bl0,d0) cubic wscale:8,7 rto:208 rtt:7.269/2.039 ato:40 mss:1428 pmtu:1500 rcvmss:1208 advmss:1428 cwnd:10 bytes_sent:5655 bytes_acked:5656 bytes_received:3902 segs_out:18 segs_in:18 data_segs_out:10 data_segs_in:9 send 15716054bps lastsnd:20443 lastrcv:20435 lastack:20435 pacing_rate 31430480bps delivery_rate 6397312bps delivered:11 app_limited busy:37ms rcv_space:14280 rcv_ssthresh:64108 minrtt:4.816 snd_wnd:264960 rcv_wnd:61312 +ESTAB 0 0 [2001:1620:713d:1300:b43c:fc6b:cb53:3c03]:41268 [2a04:4e42:41::347]:443 users:(("firefox",pid=39648,fd=164)) + skmem:(r0,rb3327263,t0,tb87040,f0,w0,o0,bl0,d9) cubic wscale:9,7 rto:216 rtt:15.926/0.48 ato:40 mss:1428 pmtu:1500 rcvmss:1428 advmss:1428 cwnd:10 bytes_sent:37765 bytes_acked:37766 bytes_received:141395 segs_out:5912 segs_in:5962 data_segs_out:1073 data_segs_in:4889 send 7173176bps lastsnd:14309 lastrcv:1483 lastack:1483 pacing_rate 14345672bps delivery_rate 2157504bps delivered:1074 app_limited busy:19183ms rcv_rtt:476059 rcv_space:68272 rcv_ssthresh:64108 minrtt:13.995 snd_wnd:150016 rcv_wnd:64128 +ESTAB 0 0 [2001:1620:713d:1300:b43c:fc6b:cb53:3c03]:49760 [2a00:1450:400a:803::2001]:443 users:(("firefox",pid=39648,fd=149)) + skmem:(r0,rb131072,t0,tb87040,f0,w0,o0,bl0,d0) cubic wscale:8,7 rto:207 rtt:6.332/2.101 ato:40 mss:1428 pmtu:1500 rcvmss:1208 advmss:1428 cwnd:10 bytes_sent:1975 bytes_acked:1976 bytes_received:6510 segs_out:22 segs_in:19 data_segs_out:8 data_segs_in:12 send 18041693bps lastsnd:44725 lastrcv:44720 lastack:44720 pacing_rate 36083384bps delivery_rate 6237504bps delivered:9 app_limited busy:37ms rcv_space:14280 rcv_ssthresh:73857 minrtt:3.298 rcv_ooopack:1 snd_wnd:268544 rcv_wnd:73984 +ESTAB 0 0 [2001:1620:713d:1300:b43c:fc6b:cb53:3c03]:60036 [2a00:1450:400a:1001::65]:443 users:(("firefox",pid=39648,fd=129)) + skmem:(r0,rb131072,t0,tb87040,f0,w0,o0,bl0,d0) cubic wscale:8,7 rto:205 rtt:4.874/1.238 ato:40 mss:1428 pmtu:1500 rcvmss:1208 advmss:1428 cwnd:10 bytes_sent:12086 bytes_acked:12087 bytes_received:4764 segs_out:25 segs_in:31 data_segs_out:17 data_segs_in:16 send 23438654bps lastsnd:2111 lastrcv:2111 lastack:2107 pacing_rate 46873696bps delivery_rate 8950632bps delivered:18 app_limited busy:36ms rcv_space:14280 rcv_ssthresh:76519 minrtt:3.426 snd_wnd:258816 rcv_wnd:76544 +ESTAB 0 0 [2001:1620:713d:1300:b43c:fc6b:cb53:3c03]:49758 [2a00:1450:400a:803::2001]:443 users:(("firefox",pid=39648,fd=106)) + skmem:(r0,rb131072,t0,tb87040,f0,w0,o0,bl0,d0) cubic wscale:8,7 rto:206 rtt:5.224/0.776 ato:40 mss:1428 pmtu:1500 rcvmss:1208 advmss:1428 cwnd:10 bytes_sent:2772 bytes_acked:2773 bytes_received:2029 segs_out:14 segs_in:11 data_segs_out:7 data_segs_in:6 send 21868300bps lastsnd:44725 lastrcv:44720 lastack:44720 pacing_rate 43730320bps delivery_rate 6937648bps delivered:8 app_limited busy:22ms rcv_space:14280 rcv_ssthresh:67824 minrtt:4.409 snd_wnd:267520 rcv_wnd:67840 diff --git a/demo/extras/ss_to_prometheus/test/localhost_1234.prom b/demo/extras/ss_to_prometheus/test/localhost_1234.prom new file mode 100644 index 000000000..48e6bd747 --- /dev/null +++ b/demo/extras/ss_to_prometheus/test/localhost_1234.prom @@ -0,0 +1,31 @@ +ss_tcp_recv_q{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_send_q{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_rtt_avg_ms{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_rtt_dev_ms{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_rmem_alloc{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_rcv_buf{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_wmem_alloc{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_snd_buf{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_fwd_alloc{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_wmem_queued{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_opt_mem{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_back_log{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_sock_drop{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_bytes_acked{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_segs_out{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_segs_in{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_lastsnd_ms{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_lastrcv_ms{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_lastack_ms{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_mss{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_pmtu{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_rcvmss{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_advmss{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_cwnd{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_rto_ms{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_delivered{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_rcv_space{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_rcv_ssthresh{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_minrtt{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_snd_wnd{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} +ss_tcp_rcv_wnd{program="nc",pid="43",src_ip="127.0.0.1",src_port="1337",dst_ip="127.0.0.1",dst_port="1234",tcp_state="ESTAB"} diff --git a/demo/extras/x_ray/.env b/demo/extras/x_ray/.env new file mode 100644 index 000000000..2167699bb --- /dev/null +++ b/demo/extras/x_ray/.env @@ -0,0 +1,7 @@ +SS_FILTER="( sport = 3001 and dport = 3002 ) or ( sport = 3002 and dport = 3001 ) or ( sport = 3002 and dport = 3003 ) or ( sport = 3003 and dport = 3002 )" +GRAFANA_INI="grafana.ini" +GRAFANA_HOMEPATH="grafana" +ALLOY_CONFIG="alloy" +PROMETHEUS_CONFIG="prometheus.yaml" +LOKI_CONFIG="loki.yaml" +LOG_PATH="../../leios-202511-demo/.tmp-leios-202511-demo/*/log" diff --git a/demo/extras/x_ray/.envrc b/demo/extras/x_ray/.envrc new file mode 100644 index 000000000..186e86d05 --- /dev/null +++ b/demo/extras/x_ray/.envrc @@ -0,0 +1 @@ +use flake .#dev-x-ray diff --git a/demo/extras/x_ray/README.md b/demo/extras/x_ray/README.md new file mode 100644 index 000000000..fef35ab70 --- /dev/null +++ b/demo/extras/x_ray/README.md @@ -0,0 +1,83 @@ +# X-RAY - socket stats with Grafana + +Position your terminal into the current direcotry and enter the shell with + +```shell +nix develop .#dev-x-ray +``` + +Or if you use Direnv with Nix + +```shell +direnv allow +``` + +You can either work with this setup step by step, or use the +awesome [process-compose](https://f1bonacc1.github.io/process-compose/) + +## Step by step +Let's make some sockets to monitor + +```shell +nc -k -l 127.0.0.1 1337 & +echo hello | nc -p 1336 127.0.0.1 1337 & +``` + +Start the SS HTTP exporter that collects statistics about 1337 sockets + +```shell +ss_http_exporter 127.0.0.1 9100 "dport = 1337" & +``` + +Check that it works + +```shell +$ curl 127.0.0.1:9100 +# TYPE ss_socket_recv_q gauge +ss_socket_recv_q{src_ip="127.0.0.1",src_port="ischat",dst_ip="127.0.0.1",dst_port="menandmice-dns",tcp_state="ESTAB"} 0 +# TYPE ss_socket_send_q gauge +ss_socket_send_q{src_ip="127.0.0.1",src_port="ischat",dst_ip="127.0.0.1",dst_port="menandmice-dns",tcp_state="ESTAB"} 0 +... +``` + +Start Prometheus so we can send metrics to it + +```shell +prometheus --web.listen-address="0.0.0.0:9090" --web.enable-remote-write-receiver +``` + +Run Alloy configure to scrape the SS HTTP Exporter + +```shell +alloy run alloy +``` + +Finally run Grafana + +```shell +grafana server --config grafana.ini --homepath grafana +``` + +[Open Grafana in the browser](http://localhost:3001) + +![Grafana screenshot](grafana-screenshot.png "Grafana screenshot") + +Clean up + +```shell +pkill "socat|grafana|prometheus|alloy" +``` + +## process-compose + +Run the setup + +```shell +process-compose -f process-compose.yaml +``` + +You should see + +![process-compose](process-compose-screenshot.png "process-compose screenshot") + +[Open Grafana in the browser](http://localhost:3001) diff --git a/demo/extras/x_ray/alloy b/demo/extras/x_ray/alloy new file mode 100644 index 000000000..5eafe8492 --- /dev/null +++ b/demo/extras/x_ray/alloy @@ -0,0 +1,194 @@ +prometheus.remote_write "prometheus" { + endpoint { + url = "http://127.0.0.1:9090/api/v1/write" + } +} + +prometheus.scrape "ss_exporter" { + targets = [ + { + "__address__" = "127.0.0.1:9100", + "job" = "ss_metrics", + "instance" = "localhost", + }, + ] + + metrics_path = "/" + + scrape_timeout = "250ms" + scrape_interval = "250ms" + + forward_to = [prometheus.remote_write.prometheus.receiver] +} + +// TODO(bladyjoker): Make this configurable via env +prometheus.scrape "cardano_node_exporter" { + targets = [ + { + "__address__" = "127.0.0.1:12900", + "job" = "cardano_node_metrics", + "instance" = "localhost", + "alias" = "upstream-node", + "process" = "UpstreamNode", + }, + { + "__address__" = "127.0.0.1:12901", + "job" = "cardano_node_metrics", + "instance" = "localhost", + "alias" = "node0", + "process" = "Node0", + }, + { + "__address__" = "127.0.0.1:12902", + "job" = "cardano_node_metrics", + "instance" = "localhost", + "alias" = "downstream-node", + "process" = "DownstreamNode", + }, + ] + + metrics_path = "/metrics" + + scrape_timeout = "1s" + scrape_interval = "1s" + + forward_to = [prometheus.remote_write.prometheus.receiver] +} + +loki.write "loki" { + endpoint { + url = "http://localhost:3100/loki/api/v1/push" + batch_size = "2MB" + } +} + +local.file_match "local_files" { + path_targets = [{"__path__" = sys.env("LOG_PATH")}] + sync_period = "5s" +} + +loki.source.file "process_compose_log_scrape" { + targets = local.file_match.local_files.targets + forward_to = [loki.process.extract_process_compose_logs.receiver] + tail_from_end = false +} + +loki.process "extract_process_compose_logs" { + stage.json { + expressions = { + level = "level", + process = "process", + replica = "replica", + message = "message", + } + } + + stage.labels { + values = { + level = "level", + process = "process", + replica = "replica", + } + } + + stage.static_labels { + values = { + service = "process-compose", + type = "process-compose", + } + } + + stage.output { + source = "message" + } + + forward_to = [ + loki.write.loki.receiver, + loki.process.extract_cardano_node_logs.receiver, + loki.process.extract_immdb_server_logs.receiver, + ] +} + +loki.process "extract_cardano_node_logs" { + stage.json { + expressions = { + at = "at", + sev = "sev", + host = "host", + thread = "thread", + ns = "ns", + data = "data", + } + } + + stage.timestamp { + source = "at" + format = "RFC3339" + } + + stage.labels { + values = { + level = "sev", + alias = "host", + host = "host", + instance = "host", + sev = "sev", + thread = "thread", + ns = "ns", + } + } + + stage.static_labels { + values = { + service = "cardano-node", + type = "cardano-node", + } + } + + stage.output { + source = "data" + } + + forward_to = [loki.write.loki.receiver] +} + +loki.process "extract_immdb_server_logs" { + stage.match { + selector = "{process=\"UpstreamNode\"}" + action = "keep" + + stage.json { + expressions = { + at = "at", + connectionId = "connectionId", + direction = "direction", + prevCount = "prevCount", + msg = "msg", + } + } + + stage.timestamp { + source = "at" + format = "RFC3339" + } + + stage.labels { + values = { + connectionId = "connectionId", + direction = "direction", + } + } + + stage.static_labels { + values = { + service = "immdb-server", + type = "immdb-server", + } + } + + stage.output { + source = "msg" + } + } + forward_to = [loki.write.loki.receiver] +} diff --git a/demo/extras/x_ray/build.nix b/demo/extras/x_ray/build.nix new file mode 100644 index 000000000..6b7eab6c9 --- /dev/null +++ b/demo/extras/x_ray/build.nix @@ -0,0 +1,43 @@ +{ + + perSystem = + { + pkgs, + config, + ... + }: + { + + devShells.dev-x-ray = pkgs.mkShell { + packages = [ + pkgs.nettools + pkgs.netcat + pkgs.grafana + pkgs.grafana-alloy + pkgs.grafana-loki + pkgs.prometheus + pkgs.process-compose + config.packages.ss_http_exporter + ]; + GRAFANA_SHARE = "${pkgs.grafana}/share/grafana"; + shellHook = ''''; + }; + + packages.x_ray = pkgs.writeShellApplication { + name = "x_ray"; + runtimeInputs = config.devShells.dev-x-ray.nativeBuildInputs; + runtimeEnv = { + inherit (config.devShells.dev-x-ray) GRAFANA_SHARE; + GRAFANA_INI = ./grafana.ini; + GRAFANA_HOMEPATH = ./grafana; + ALLOY_CONFIG = ./alloy; + PROMETHEUS_CONFIG = ./prometheus.yaml; + LOKI_CONFIG = ./loki.yaml; + }; + text = '' + process-compose --no-server -f ${./process-compose.yaml}; + ''; + }; + + }; +} diff --git a/demo/extras/x_ray/grafana-screenshot.png b/demo/extras/x_ray/grafana-screenshot.png new file mode 100644 index 000000000..680004403 Binary files /dev/null and b/demo/extras/x_ray/grafana-screenshot.png differ diff --git a/demo/extras/x_ray/grafana.ini b/demo/extras/x_ray/grafana.ini new file mode 100644 index 000000000..7b5517a30 --- /dev/null +++ b/demo/extras/x_ray/grafana.ini @@ -0,0 +1,28 @@ +[server] +domain=localhost +enable_gzip=true +enforce_domain=true +http_addr=0.0.0.0 +http_port=3000 +protocol=http +root_url=%(protocol)s://%(domain)s:%(http_port)s/ +static_root_path = ${GRAFANA_SHARE}/public + +[security] +admin_email=admin@localhost +admin_user=admin +admin_password=admin +secret_key=SW2YcwTIb9zpOOhoPsMm + +[auth.anonymous] +enabled = true +org_role = "Admin" + +[plugin.grafana-image-renderer] +rendering_ignore_https_errors = true + +[analytics] +check_for_plugin_updates=false +check_for_updates=false +feedback_links_enabled=false +reporting_enabled=false diff --git a/demo/extras/x_ray/grafana/conf/defaults.ini b/demo/extras/x_ray/grafana/conf/defaults.ini new file mode 100644 index 000000000..bca78940a --- /dev/null +++ b/demo/extras/x_ray/grafana/conf/defaults.ini @@ -0,0 +1,2227 @@ +##################### Grafana Configuration Defaults ##################### +# +# Do not modify this file in grafana installs +# + +# possible values : production, development +app_mode = production + +# instance name, defaults to HOSTNAME environment variable value or hostname if HOSTNAME var is empty +instance_name = ${HOSTNAME} + +target = + +#################################### Paths ############################### +[paths] +# Path to where grafana can store temp files, sessions, and the sqlite3 db (if that is used) +data = data + +# Temporary files in `data` directory older than given duration will be removed +temp_data_lifetime = 24h + +# Directory where grafana can store logs +logs = data/log + +# Directory where grafana will automatically scan and look for plugins +plugins = data/plugins + +# folder that contains provisioning config files that grafana will apply on startup and while running. +provisioning = conf/provisioning + +# Directories that are permitted to contain local repositories. +# This is a list. Each entry is delimited by a pipe (|). No leading or trailing spaces are supported. +# These do not need to be absolute paths, in which case they'll be relative to the path where you are running Grafana. +# Empty entries will return an error, unless the string is just a single pipe. +# Example: permitted_provisioning_paths = /tmp|/etc/grafana/repositories|conf/provisioning +permitted_provisioning_paths = devenv/dev-dashboards|conf/provisioning + +#################################### Server ############################## +[server] +# Protocol (http, https, h2, socket) +protocol = http + +# Minimum TLS version allowed. By default, this value is empty. Accepted values are: TLS1.2, TLS1.3. If nothing is set TLS1.2 would be taken +min_tls_version = "" + +# The ip address to bind to, empty will bind to all interfaces +http_addr = + +# The http port to use +http_port = 3000 + +# The public facing domain name used to access grafana from a browser +domain = localhost + +# Redirect to correct domain if host header does not match domain +# Prevents DNS rebinding attacks +enforce_domain = false + +# The full public facing url +root_url = %(protocol)s://%(domain)s:%(http_port)s/ + +# Serve Grafana from subpath specified in `root_url` setting. By default it is set to `false` for compatibility reasons. +serve_from_sub_path = false + +# Log web requests +router_logging = false + +# the path relative working path +static_root_path = public + +# enable gzip +enable_gzip = false + +# https certs & key file +cert_file = +cert_key = +cert_pass = + +# Certificates file watch interval +certs_watch_interval = + +# Unix socket gid +# Changing the gid of a file without privileges requires that the target group is in the group of the process and that the process is the file owner +# It is recommended to set the gid as http server user gid +# Not set when the value is -1 +socket_gid = -1 + +# Unix socket mode +socket_mode = 0660 + +# Unix socket path +socket = /tmp/grafana.sock + +# CDN Url +cdn_url = + +# Sets the maximum time in minutes before timing out read of an incoming request and closing idle connections. +# `0` means there is no timeout for reading the request. +read_timeout = 0 + +# This setting enables you to specify additional headers that the server adds to HTTP(S) responses. +[server.custom_response_headers] +#exampleHeader1 = exampleValue1 +#exampleHeader2 = exampleValue2 + +[environment] +# Sets whether the local file system is available for Grafana to use. Default is true for backward compatibility. +local_file_system_available = true + +#################################### GRPC Server ######################### +[grpc_server] +network = "tcp" +address = "127.0.0.1:10000" +use_tls = false +cert_file = +key_file = +# this will log the request and response for each unary gRPC call +enable_logging = false + +# Maximum size of a message that can be received in bytes. If not set, uses the gRPC default (4MiB). +max_recv_msg_size = + +# Maximum size of a message that can be sent in bytes. If not set, uses the gRPC default (unlimited). +max_send_msg_size = + +#################################### Database ############################ +[database] +# You can configure the database connection by specifying type, host, name, user and password +# as separate properties or as on string using the url property. + +# Either "mysql", "postgres" or "sqlite3", it's your choice +type = sqlite3 +host = 127.0.0.1:3306 +name = grafana +user = root +# If the password contains # or ; you have to wrap it with triple quotes. Ex """#password;""" +password = +# Use either URL or the previous fields to configure the database +# Example: mysql://user:secret@host:port/database +url = + +# Set to true or false to enable or disable high availability mode. +# When it's set to false some functions will be simplified and only run in-process +# instead of relying on the database. +# +# Only set it to false if you run only a single instance of Grafana. +high_availability = true + +# Max idle conn setting default is 2 +max_idle_conn = 2 + +# Max conn setting default is 0 (mean not set) +max_open_conn = + +# Connection Max Lifetime default is 14400 (means 14400 seconds or 4 hours) +conn_max_lifetime = 14400 + +# Set to true to log the sql calls and execution times. +log_queries = + +# For "postgres", use either "disable", "require" or "verify-full" +# For "mysql", use either "true", "false", or "skip-verify". +ssl_mode = disable + +# For "postgres", use either "1" to enable or "0" to disable SNI +ssl_sni = + +# Database drivers may support different transaction isolation levels. +# Currently, only "mysql" driver supports isolation levels. +# If the value is empty - driver's default isolation level is applied. +# For "mysql" use "READ-UNCOMMITTED", "READ-COMMITTED", "REPEATABLE-READ" or "SERIALIZABLE". +isolation_level = + +ca_cert_path = +client_key_path = +client_cert_path = +server_cert_name = + +# For "sqlite3" only, path relative to data_path setting +path = grafana.db + +# For "sqlite3" only. cache mode setting used for connecting to the database +cache_mode = private + +# For "sqlite3" only. Enable/disable Write-Ahead Logging, https://sqlite.org/wal.html. Default is false. +wal = false + +# For "mysql" and "postgres". Lock the database for the migrations, default is true. +migration_locking = true + +# For "mysql" and "postgres" only if migrationLocking is set. How many seconds to wait before failing to lock the database for the migrations, default is 0. +locking_attempt_timeout_sec = 0 + +# For "sqlite" only. How many times to retry query in case of database is locked failures. Default is 0 (disabled). +query_retries = 0 + +# For "sqlite" only. How many times to retry transaction in case of database is locked failures. Default is 5. +transaction_retries = 5 + +# Set to true to add metrics and tracing for database queries. +instrument_queries = false + +# Set to true to delete auto-generated primary keys during migrations. +# This is useful when databases have auto-generated primary keys enabled. +delete_auto_gen_ids = false + +#################################### Cache server ############################# +[remote_cache] +# Either "redis", "memcached" or "database" default is "database" +type = database + +# cache connectionstring options +# database: will use Grafana primary database. +# redis: config like redis server e.g. `addr=127.0.0.1:6379,pool_size=100,db=0,username=grafana,password=grafanaRocks,ssl=false`. Only addr is required. ssl may be 'true', 'false', or 'insecure'. +# memcache: 127.0.0.1:11211 +connstr = + +# prefix prepended to all the keys in the remote cache +prefix = + +# This enables encryption of values stored in the remote cache +encryption = + +#################################### Data proxy ########################### +[dataproxy] + +# This enables data proxy logging, default is false +logging = false + +# How long the data proxy waits to read the headers of the response before timing out, default is 30 seconds. +# This setting also applies to core backend HTTP data sources where query requests use an HTTP client with timeout set. +timeout = 30 + +# How long the data proxy waits to establish a TCP connection before timing out, default is 10 seconds. +dialTimeout = 10 + +# How many seconds the data proxy waits before sending a keepalive request. +keep_alive_seconds = 30 + +# How many seconds the data proxy waits for a successful TLS Handshake before timing out. +tls_handshake_timeout_seconds = 10 + +# How many seconds the data proxy will wait for a server's first response headers after +# fully writing the request headers if the request has an "Expect: 100-continue" +# header. A value of 0 will result in the body being sent immediately, without +# waiting for the server to approve. +expect_continue_timeout_seconds = 1 + +# Optionally limits the total number of connections per host, including connections in the dialing, +# active, and idle states. On limit violation, dials will block. +# A value of zero (0) means no limit. +max_conns_per_host = 0 + +# The maximum number of idle connections that Grafana will keep alive. +max_idle_connections = 100 + +# How many seconds the data proxy keeps an idle connection open before timing out. +idle_conn_timeout_seconds = 90 + +# If enabled and user is not anonymous, data proxy will add X-Grafana-User header with username into the request. +send_user_header = false + +# Limit the amount of bytes that will be read/accepted from responses of outgoing HTTP requests. +response_limit = 0 + +# Limits the number of rows that Grafana will process from SQL data sources. +row_limit = 1000000 + +# Sets a custom value for the `User-Agent` header for outgoing data proxy requests. If empty, the default value is `Grafana/` (for example `Grafana/9.0.0`). +user_agent = + +#################################### Analytics ########################### +[analytics] +# Server reporting, sends usage counters to stats.grafana.org every 24 hours. +# No ip addresses are being tracked, only simple counters to track +# running instances, dashboard and error counts. It is very helpful to us. +# Change this option to false to disable reporting. +reporting_enabled = true + +# The name of the distributor of the Grafana instance. Ex hosted-grafana, grafana-labs +reporting_distributor = grafana-labs + +# Set to false to disable all checks to https://grafana.com +# for new versions of grafana. The check is used +# in some UI views to notify that a grafana update exists. +# This option does not cause any auto updates, nor send any information +# only a GET request to https://grafana.com/api/grafana/versions/stable to get the latest version. +check_for_updates = true + +# Set to false to disable all checks to https://grafana.com +# for new versions of plugins. The check is used +# in some UI views to notify that a plugin update exists. +# This option does not cause any auto updates, nor send any information +# only a GET request to https://grafana.com to get the latest versions. +check_for_plugin_updates = true + +# Google Analytics universal tracking code, only enabled if you specify an id here +google_analytics_ua_id = + +# Google Analytics 4 tracking code, only enabled if you specify an id here +google_analytics_4_id = + +# When Google Analytics 4 Enhanced event measurement is enabled, we will try to avoid sending duplicate events and let Google Analytics 4 detect navigation changes, etc. +google_analytics_4_send_manual_page_views = false + +# Google Tag Manager ID, only enabled if you specify an id here +google_tag_manager_id = + +# Rudderstack write key, enabled only if rudderstack_data_plane_url is also set +rudderstack_write_key = + +# Rudderstack data plane url, enabled only if rudderstack_write_key is also set +rudderstack_data_plane_url = + +# Rudderstack SDK url, optional, only valid if rudderstack_write_key and rudderstack_data_plane_url is also set +rudderstack_sdk_url = + +# Rudderstack Config url, optional, used by Rudderstack SDK to fetch source config +rudderstack_config_url = + +# Rudderstack Integrations URL, optional. Only valid if you pass the SDK version 1.1 or higher +rudderstack_integrations_url = + +# Intercom secret, optional, used to hash user_id before passing to Intercom via Rudderstack +intercom_secret = + +# Application Insights connection string. Specify an URL string to enable this feature. +application_insights_connection_string = + +# Optional. Specifies an Application Insights endpoint URL where the endpoint string is wrapped in backticks ``. +application_insights_endpoint_url = + +# Controls if the UI contains any links to user feedback forms +feedback_links_enabled = true + +# Static context that is being added to analytics events +reporting_static_context = + +# Logs interaction events to the browser javascript console, intended for development only +browser_console_reporter = false + +#################################### Security ############################ +[security] +# disable creation of admin user on first start of grafana +disable_initial_admin_creation = false + +# default admin user, created on startup +admin_user = admin + +# default admin password, can be changed before first start of grafana, or in profile settings +admin_password = admin + +# default admin email, created on startup +admin_email = admin@localhost + +# used for signing +secret_key = SW2YcwTIb9zpOOhoPsMm + +# current key provider used for envelope encryption, default to static value specified by secret_key +encryption_provider = secretKey.v1 + +# list of configured key providers, space separated (Enterprise only): e.g., awskms.v1 azurekv.v1 +available_encryption_providers = + +# disable gravatar profile images +disable_gravatar = false + +# data source proxy whitelist (ip_or_domain:port separated by spaces) +data_source_proxy_whitelist = + +# disable protection against brute force login attempts +disable_brute_force_login_protection = false + +# max number of failed login attempts before user gets locked +brute_force_login_protection_max_attempts = 5 + +# disable protection against brute force login attempts by username +disable_username_login_protection = false + +# disable protection against brute force login attempts by IP address +disable_ip_address_login_protection = true + +# set to true if you host Grafana behind HTTPS. default is false. +cookie_secure = false + +# set cookie SameSite attribute. defaults to `lax`. can be set to "lax", "strict", "none" and "disabled" +cookie_samesite = lax + +# set to true if you want to allow browsers to render Grafana in a ,