Add shadow simulation rln wakunode2

This commit is contained in:
alrevuelta 2023-10-20 09:57:43 +02:00
parent 4f65895be8
commit 612a783e6a
No known key found for this signature in database
GPG Key ID: F345C9F3CCDB886E
9 changed files with 31122 additions and 0 deletions

3
.gitignore vendored Normal file
View File

@ -0,0 +1,3 @@
**/.DS_Store
rln-delay-simulations/.idea/*
**/__pycache__

View File

@ -0,0 +1,47 @@
## rln-delay-simulations
This folder contains a `shadow` configuration to simulate `1000` `nwaku` nodes in an end to end setup:
* `nwaku` binaries are used, built with `make wakunode2` but with a minor modification, see [simulations](https://github.com/waku-org/nwaku/compare/master...simulations)
* `rln` is used with hardcoded static memberships, to avoid the sepolia node + contract, [see](https://raw.githubusercontent.com/waku-org/nwaku/master/waku/waku_rln_relay/constants.nim).
* Focused on measuring message propagation delays. Each message that is sent, encodes the timestamp when it was created.
* Requires significant resources to run (tested with 256 GB RAM)
* See simulation parameters: latency, bandwidth, amount of nodes, amount of publishers.
* Note that due to TCP flow control, when using big messages the first ones to arrive will show a higher delay. Filter them out to not bias the measurements.
## How to run
Get `nwaku` codebase and checkout to [simulations](https://github.com/waku-org/nwaku/tree/simulations) branch, build it and start the [shadow](https://github.com/shadow/shadow) simulation. Ensure `path` points to the `wakunode2` binary and you have enough resources.
```
git clone https://github.com/waku-org/nwaku.git
cd nwaku
git checkout simulations
make wakunode2
shadow shadow.yaml
```
## How to analyze
First check that the simulation finished ok. Check that the numbers match.
```
grep -nr 'ended_simulation' shadow.data | wc -l
# expected: 1000 (simulation finished ok in all nodes)
grep -nr 'tx_msg' shadow.data | wc -l
# expected: 10 (total of published messages)
grep -nr 'rx_msg' shadow.data | wc -l
# expected: 9990 (total rx messages)
```
Get metrics:
```
grep -nr 'rx_msg' shadow.data > latency.txt
grep -nr 'mesh_size' shadow.data > mesh_size.txt
```
Print results:
```
python analyze.py latency.txt "arrival_diff="
python analyze.py mesh_size.txt "mesh_size="
```

View File

@ -0,0 +1,26 @@
import numpy as np
import sys
def load(file_name, field):
latencies = []
with open(file_name, "r") as file:
for line in file.readlines():
if field in line:
# first message bias the latency due to tcp flow control
if "seq=" in line:
seq = int(line.strip().split("seq=")[1].split(" ")[0])
if seq in [0]:
continue
x = line.strip().split(field)[1].split(" ")[0]
latencies.append(int(x))
return np.array(latencies)
if __name__ == "__main__":
file = sys.argv[1]
field = sys.argv[2]
array = load(file, field)
print("Data file:", file, "field:", field)
print(f"number_samples={array.size}")
print(f"Percentiles. P75={np.percentile(array, 75)} P95={np.percentile(array, 95)}")
print(f"Statistics. mean={np.mean(array)} max={array.max()} min={array.min()}")

Binary file not shown.

After

Width:  |  Height:  |  Size: 226 KiB

View File

@ -0,0 +1,33 @@
import matplotlib.pyplot as plt
import scienceplots
import numpy as np
from analyze import load
latencies = [load("raw/latency_10kb.txt", "arrival_diff="),
load("raw/latency_100kb.txt", "arrival_diff="),
load("raw/latency_500kb.txt", "arrival_diff=")]
print(latencies)
with plt.style.context(['science', 'ieee']):
fig, ax = plt.subplots()
bp = ax.boxplot(latencies,notch=True, vert=True, patch_artist=True,
showfliers=True, whis=100000000000)
for patch, color in zip(bp['boxes'], ['red', 'blue', 'green']):
patch.set_facecolor(color)
ax.set(title="Message latencies distribution\nD=6 nodes=1000 samples="+str(latencies[1].size), xlabel='Scenario', ylabel='Message propagation time (ms)')
ax.grid(linestyle='-')
my_legend = []
for msg_size in [10, 100, 500]:
my_legend.append("Message size: " + str(msg_size) + " kB")
ax.legend([bp["boxes"][i] for i in range(len(my_legend))], my_legend, loc='upper left', fontsize=5)
for i, line in enumerate(bp['medians']):
x, y = line.get_xydata()[1]
text = r' $ \mu =$ ' + '{:.0f} ms\n'.format(latencies[i].mean(axis=0)) + r' $ p_{95} = $ ' + '{:.0f} ms'.format(np.percentile(latencies[i], 95))
ax.annotate(text, xy=(x + 0.1, y), fontsize=6)
fig.set_size_inches(4, 3)
fig.savefig('plot.jpg', dpi=600)

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff