Compare commits

..

11 Commits

Author SHA1 Message Date
d888713e97 Enable oneAPI and ROCm (#9)
All checks were successful
MetagraphOptimization_CI / docs (push) Successful in 8m30s
MetagraphOptimization_CI / test (push) Successful in 22m2s
Co-authored-by: Anton Reinhard <anton.reinhard@proton.me>
Reviewed-on: #9
2024-05-08 19:26:18 +02:00
38e7ff3b90 Seed Randomness, Fix tests (#8)
All checks were successful
MetagraphOptimization_CI / docs (push) Successful in 7m34s
MetagraphOptimization_CI / test (push) Successful in 20m49s
Seeded randomness in all places, however, multithreaded randomness still exists.

Disabled some tests that are failing, will add issues and fix later. These are related to (likely) precision problems in the ABC model, which is not priority, and the Node Fusion, which will be fundamentally reworked anyways.

Co-authored-by: Anton Reinhard <anton.reinhard@proton.me>
Reviewed-on: #8
2024-05-08 18:04:48 +02:00
7d7782f97f Add Workaround for Trie implementation for Julia version 1.10+ (#7)
Some checks failed
MetagraphOptimization_CI / docs (push) Successful in 8m32s
MetagraphOptimization_CI / test (push) Failing after 12m1s
Co-authored-by: Anton Reinhard <anton.reinhard@proton.me>
Reviewed-on: #7
2024-05-08 14:00:25 +02:00
87dbaf2c32 experiments (#1)
All checks were successful
MetagraphOptimization_CI / docs (push) Successful in 10m41s
MetagraphOptimization_CI / test (push) Successful in 30m40s
Co-authored-by: Anton Reinhard <anton.reinhard@proton.me>
Reviewed-on: #1
2024-05-08 12:03:27 +02:00
82ed774b7e Tape Machine (#30)
Adds a tape machine way of executing the code.
The tape machine is a series of FunctionCall objects, which can either be called one by one, or be used to generate expressions to make up a function.

Reviewed-on: Rubydragon/MetagraphOptimization.jl#30
Co-authored-by: Anton Reinhard <anton.reinhard@proton.me>
Co-committed-by: Anton Reinhard <anton.reinhard@proton.me>
2024-01-03 16:38:32 +01:00
92e0eeaaef heterogeneity (#27)
Prepare things to work with heterogeneity, make things work on GPU

Reviewed-on: Rubydragon/MetagraphOptimization.jl#27
Co-authored-by: Anton Reinhard <anton.reinhard@proton.me>
Co-committed-by: Anton Reinhard <anton.reinhard@proton.me>
2023-12-18 14:31:52 +01:00
c90346e948 Add QED Model (#25)
Reviewed-on: Rubydragon/MetagraphOptimization.jl#25
Co-authored-by: Anton Reinhard <anton.reinhard@proton.me>
Co-committed-by: Anton Reinhard <anton.reinhard@proton.me>
2023-12-07 02:54:15 +01:00
938bf216e5 Improve actions workflow by removing prepare step (#23)
Reviewed-on: Rubydragon/MetagraphOptimization.jl#23
Co-authored-by: Anton Reinhard <anton.reinhard@proton.me>
Co-committed-by: Anton Reinhard <anton.reinhard@proton.me>
2023-11-24 19:20:05 +01:00
04d5673b44 Use SafeTestsets for testing (#22)
Fixes issue #18

Reviewed-on: Rubydragon/MetagraphOptimization.jl#22
Co-authored-by: Anton Reinhard <anton.reinhard@proton.me>
Co-committed-by: Anton Reinhard <anton.reinhard@proton.me>
2023-11-22 16:01:17 +01:00
b7560685d4 Optimizer interface and sample implementation (#19)
Reviewed-on: Rubydragon/MetagraphOptimization.jl#19
Co-authored-by: Anton Reinhard <anton.reinhard@proton.me>
Co-committed-by: Anton Reinhard <anton.reinhard@proton.me>
2023-11-22 13:51:54 +01:00
16274919e4 Cost Estimation interface (#14)
See issue #13

Reviewed-on: Rubydragon/MetagraphOptimization.jl#14
Co-authored-by: Anton Reinhard <anton.reinhard@proton.me>
Co-committed-by: Anton Reinhard <anton.reinhard@proton.me>
2023-11-17 01:31:31 +01:00
231 changed files with 11074 additions and 2090 deletions

1
.gitattributes vendored
View File

@ -1,2 +1,3 @@
input/AB->ABBBBBBBBB.txt filter=lfs diff=lfs merge=lfs -text
input/AB->ABBBBBBB.txt filter=lfs diff=lfs merge=lfs -text
*.zip filter=lfs diff=lfs merge=lfs -text

View File

@ -7,64 +7,7 @@ env:
JULIA_DEPOT_PATH: './.julia'
jobs:
prepare:
runs-on: ubuntu-22.04
steps:
- name: Checkout repository
uses: actions/checkout@v3
with:
fetch-depth: 0
- name: Setup Julia environment
uses: https://github.com/julia-actions/setup-julia@v1.9.2
with:
version: '1.9.2'
# needed for the file hashing, should be removed when ${{ hashFiles('**/Project.toml') }} is supported in gitea
- name: Setup go environment
uses: actions/setup-go@v3
with:
go-version: '1.20'
- name: Hash files
uses: https://gitea.com/actions/go-hashfiles@v0.0.1
id: get-hash
with:
patterns: |-
**/Project.toml
- name: Restore Cache
uses: actions/cache/restore@v3
id: cache-restore
with:
path: |
.julia/artifacts
.julia/packages
.julia/registries
key: julia-${{ steps.get-hash.outputs.hash }}
- name: Check cache hit
if: steps.cache-restore.outputs.cache-hit == 'true'
run: exit 0
- name: Install dependencies
run: |
julia --project=./ -e 'import Pkg; Pkg.instantiate(); Pkg.precompile()'
julia --project=examples/ -e 'import Pkg; Pkg.develop(Pkg.PackageSpec(path=pwd())); Pkg.instantiate(); Pkg.precompile()'
julia --project=docs/ -e 'import Pkg; Pkg.develop(Pkg.PackageSpec(path=pwd())); Pkg.instantiate(); Pkg.precompile()'
- name: Cache Julia packages
uses: actions/cache/save@v3
with:
path: |
.julia/artifacts
.julia/packages
.julia/registries
key: julia-${{ steps.get-hash.outputs.hash }}
test:
needs: prepare
runs-on: ubuntu-22.04
steps:
@ -74,37 +17,14 @@ jobs:
fetch-depth: 0
- name: Setup Julia environment
uses: https://github.com/julia-actions/setup-julia@v1.9.2
uses: https://github.com/julia-actions/setup-julia@v2
with:
version: '1.9.2'
version: '1.10'
# needed for the file hashing, should be removed when ${{ hashFiles('**/Project.toml') }} is supported in gitea
- name: Setup go environment
uses: actions/setup-go@v3
with:
go-version: '1.20'
- name: Hash files
uses: https://gitea.com/actions/go-hashfiles@v0.0.1
id: get-hash
with:
patterns: |-
**/Project.toml
- name: Restore cached Julia packages
uses: actions/cache/restore@v3
with:
path: |
.julia/artifacts
.julia/packages
.julia/registries
key: julia-${{ steps.get-hash.outputs.hash }}
- name: Install dependencies
- name: Instantiate
run: |
julia --project=./ -e 'import Pkg; Pkg.instantiate(); Pkg.precompile()'
julia --project=examples/ -e 'import Pkg; Pkg.develop(Pkg.PackageSpec(path=pwd())); Pkg.instantiate(); Pkg.precompile()'
julia --project=docs/ -e 'import Pkg; Pkg.develop(Pkg.PackageSpec(path=pwd())); Pkg.instantiate(); Pkg.precompile()'
julia --project=./ -e 'using Pkg; Pkg.instantiate()'
julia --project=./ -e 'using Pkg; Pkg.add(url="https://github.com/QEDjl-project/QEDprocesses.jl/")'
- name: Format check
run: |
@ -114,19 +34,21 @@ jobs:
if out == ""
exit(0)
else
@error "Some files have not been formatted !!!"
@error "Some files have not been formatted!!!"
write(stdout, out)
exit(1)
end'
- name: Run tests
run: julia --project=./ -t 4 -e 'import Pkg; Pkg.test()' -O0
run: julia --project=./ -t 4 -e 'using Pkg; Pkg.test()' -O0
- name: Run examples
run: julia --project=examples/ -t 4 -e 'include("examples/import_bench.jl")' -O3
run: |
julia --project=examples/ -e 'using Pkg; Pkg.develop(Pkg.PackageSpec(path=pwd())); Pkg.instantiate(); Pkg.precompile()'
julia --project=examples/ -t 4 -e 'include("examples/import_bench.jl")' -O3
julia --project=examples/ -t 4 -e 'include("examples/ab5.jl")' -O3
docs:
needs: prepare
runs-on: ubuntu-22.04
steps:
@ -136,40 +58,14 @@ jobs:
fetch-depth: 0
- name: Setup Julia environment
uses: https://github.com/julia-actions/setup-julia@v1.9.2
uses: https://github.com/julia-actions/setup-julia@v2
with:
version: '1.9.2'
# needed for the file hashing, should be removed when ${{ hashFiles('**/Project.toml') }} is supported in gitea
- name: Setup go environment
uses: actions/setup-go@v3
with:
go-version: '1.20'
- name: Hash files
uses: https://gitea.com/actions/go-hashfiles@v0.0.1
id: get-hash
with:
patterns: |-
**/Project.toml
- name: Restore cached Julia packages
uses: actions/cache/restore@v3
with:
path: |
.julia/artifacts
.julia/packages
.julia/registries
key: julia-${{ steps.get-hash.outputs.hash }}
- name: Install dependencies
run: |
julia --project=./ -e 'import Pkg; Pkg.instantiate(); Pkg.precompile()'
julia --project=examples/ -e 'import Pkg; Pkg.develop(Pkg.PackageSpec(path=pwd())); Pkg.instantiate(); Pkg.precompile()'
julia --project=docs/ -e 'import Pkg; Pkg.develop(Pkg.PackageSpec(path=pwd())); Pkg.instantiate(); Pkg.precompile()'
version: '1.10'
- name: Build docs
run: julia --project=docs/ docs/make.jl
run: |
julia --project=docs/ -e 'using Pkg; Pkg.develop(Pkg.PackageSpec(path=pwd())); Pkg.instantiate(); Pkg.precompile()'
julia --project=docs/ docs/make.jl
- name: Upload artifacts
uses: actions/upload-artifact@v3

6
.gitignore vendored
View File

@ -5,6 +5,7 @@
# Files generated by invoking Julia with --track-allocation
*.mem
*.pb.gz
# System-specific files and directories generated by the BinaryProvider and BinDeps packages
# They contain absolute paths specific to the host computer, and so should not be committed
@ -28,3 +29,8 @@ Manifest.toml
.vscode
.julia
**/.ipynb_checkpoints/
*.bkp
*.sif
data/hemera_temp

View File

@ -4,19 +4,25 @@ authors = ["Anton Reinhard <anton.reinhard@proton.me>"]
version = "0.1.0"
[deps]
AMDGPU = "21141c5a-9bdb-4563-92ae-f87d6854732e"
AccurateArithmetic = "22286c92-06ac-501d-9306-4abd417d9753"
CUDA = "052768ef-5323-5732-b1bb-66c8b64840ba"
Combinatorics = "861a8166-3701-5b0c-9a16-15d98fcdc6aa"
DataStructures = "864edb3b-99cc-5e75-8d2d-829cb0a9cfe8"
ForwardDiff = "f6369f11-7733-5829-9624-2563aa707210"
JuliaFormatter = "98e50ef6-434e-11e9-1051-2b60c6c9e899"
KernelAbstractions = "63c18a36-062a-441e-b654-da1e3ab1ce7c"
NumaAllocators = "21436f30-1b4a-4f08-87af-e26101bb5379"
QEDbase = "10e22c08-3ccb-4172-bfcf-7d7aa3d04d93"
QEDprocesses = "46de9c38-1bb3-4547-a1ec-da24d767fdad"
Random = "9a3f8284-a2c9-5f02-9a11-845980a1fd5c"
Roots = "f2b01f46-fcfa-551c-844a-d8ac1e96c665"
StaticArrays = "90137ffa-7385-5640-81b9-e52037218182"
UUIDs = "cf7118a7-6976-5b1a-9a39-7adc72f591a4"
oneAPI = "8f75cd03-7ff8-4ecb-9b8f-daf728133b1b"
[extras]
CUDA_Runtime_jll = "76a88914-d11a-5bdc-97e0-2f5a05c973a2"
Test = "8dfed614-e22c-5e08-85e1-65c5234f0b40"
[targets]

View File

@ -50,8 +50,8 @@ Problems:
For graphs AB->AB^n:
- Number of Sums should always be 1
- Number of ComputeTaskS2 should always be (n+1)!
- Number of ComputeTaskU should always be (n+3)
- Number of ComputeTaskABC_S2 should always be (n+1)!
- Number of ComputeTaskABC_U should always be (n+3)
Times are from my home machine: AMD Ryzen 7900X3D, 64GB DDR5 RAM @ 6000MHz (not necessarily up to date, check Jupyter Notebooks in `notebooks/` instead)
@ -59,9 +59,9 @@ Times are from my home machine: AMD Ryzen 7900X3D, 64GB DDR5 RAM @ 6000MHz (not
$ julia --project examples/import_bench.jl
AB->AB:
Graph:
Nodes: Total: 34, DataTask: 19, ComputeTaskP: 4,
ComputeTaskS2: 2, ComputeTaskV: 4, ComputeTaskU: 4,
ComputeTaskSum: 1
Nodes: Total: 34, DataTask: 19, ComputeTaskABC_P: 4,
ComputeTaskABC_S2: 2, ComputeTaskABC_V: 4, ComputeTaskABC_U: 4,
ComputeTaskABC_Sum: 1
Edges: 37
Total Compute Effort: 185
Total Data Transfer: 102
@ -71,9 +71,9 @@ Graph:
AB->ABBB:
Graph:
Nodes: Total: 280, DataTask: 143, ComputeTaskP: 6,
ComputeTaskS2: 24, ComputeTaskV: 64, ComputeTaskU: 6,
ComputeTaskSum: 1, ComputeTaskS1: 36
Nodes: Total: 280, DataTask: 143, ComputeTaskABC_P: 6,
ComputeTaskABC_S2: 24, ComputeTaskABC_V: 64, ComputeTaskABC_U: 6,
ComputeTaskABC_Sum: 1, ComputeTaskABC_S1: 36
Edges: 385
Total Compute Effort: 2007
Total Data Transfer: 828
@ -83,9 +83,9 @@ Graph:
AB->ABBBBB:
Graph:
Nodes: Total: 7854, DataTask: 3931, ComputeTaskP: 8,
ComputeTaskS2: 720, ComputeTaskV: 1956, ComputeTaskU: 8,
ComputeTaskSum: 1, ComputeTaskS1: 1230
Nodes: Total: 7854, DataTask: 3931, ComputeTaskABC_P: 8,
ComputeTaskABC_S2: 720, ComputeTaskABC_V: 1956, ComputeTaskABC_U: 8,
ComputeTaskABC_Sum: 1, ComputeTaskABC_S1: 1230
Edges: 11241
Total Compute Effort: 58789
Total Data Transfer: 23244
@ -95,9 +95,9 @@ Graph:
AB->ABBBBBBB:
Graph:
Nodes: Total: 438436, DataTask: 219223, ComputeTaskP: 10,
ComputeTaskS2: 40320, ComputeTaskV: 109600, ComputeTaskU: 10,
ComputeTaskSum: 1, ComputeTaskS1: 69272
Nodes: Total: 438436, DataTask: 219223, ComputeTaskABC_P: 10,
ComputeTaskABC_S2: 40320, ComputeTaskABC_V: 109600, ComputeTaskABC_U: 10,
ComputeTaskABC_Sum: 1, ComputeTaskABC_S1: 69272
Edges: 628665
Total Compute Effort: 3288131
Total Data Transfer: 1297700
@ -107,7 +107,7 @@ Graph:
AB->ABBBBBBBBB:
Graph:
Nodes: Total: 39456442, DataTask: 19728227, ComputeTaskS1: 6235290, ComputeTaskP: 12, ComputeTaskU: 12, ComputeTaskV: 9864100, ComputeTaskS2: 3628800, ComputeTaskSum: 1
Nodes: Total: 39456442, DataTask: 19728227, ComputeTaskABC_S1: 6235290, ComputeTaskABC_P: 12, ComputeTaskABC_U: 12, ComputeTaskABC_V: 9864100, ComputeTaskABC_S2: 3628800, ComputeTaskABC_Sum: 1
Edges: 56578129
Total Compute Effort: 295923153
Total Data Transfer: 175407750
@ -116,9 +116,9 @@ Graph:
ABAB->ABAB:
Graph:
Nodes: Total: 3218, DataTask: 1613, ComputeTaskP: 8,
ComputeTaskS2: 288, ComputeTaskV: 796, ComputeTaskU: 8,
ComputeTaskSum: 1, ComputeTaskS1: 504
Nodes: Total: 3218, DataTask: 1613, ComputeTaskABC_P: 8,
ComputeTaskABC_S2: 288, ComputeTaskABC_V: 796, ComputeTaskABC_U: 8,
ComputeTaskABC_Sum: 1, ComputeTaskABC_S1: 504
Edges: 4581
Total Compute Effort: 24009
Total Data Transfer: 9494
@ -128,9 +128,9 @@ Graph:
ABAB->ABC:
Graph:
Nodes: Total: 817, DataTask: 412, ComputeTaskP: 7,
ComputeTaskS2: 72, ComputeTaskV: 198, ComputeTaskU: 7,
ComputeTaskSum: 1, ComputeTaskS1: 120
Nodes: Total: 817, DataTask: 412, ComputeTaskABC_P: 7,
ComputeTaskABC_S2: 72, ComputeTaskABC_V: 198, ComputeTaskABC_U: 7,
ComputeTaskABC_Sum: 1, ComputeTaskABC_S1: 120
Edges: 1151
Total Compute Effort: 6028
Total Data Transfer: 2411

170
data/evaluate.jl Normal file
View File

@ -0,0 +1,170 @@
using CSV
using DataFrames
using Plots
using StatsPlots
using LaTeXStrings
if (length(ARGS) < 1)
println("Please use with \"input_file.csv\"")
end
processes = [
"QED Process: 'ke->ke'",
"QED Process: 'ke->kke'",
"QED Process: 'ke->kkke'",
#"QED Process: 'ke->kkkke'",
#"QED Process: 'ke->kkkkke'",
#"QED Process: 'ke->kkkkkke'",
#"QED Process: 'ke->kkkkkkke'",
"ABC Process: 'AB->AB'",
"ABC Process: 'AB->ABBB'",
#"ABC Process: 'AB->ABBBBB'",
]
function proc_to_n(str::AbstractString)
parts = split(str, "'")
parts = split(parts[2], "->")
k_count = count(c -> c == 'k', parts[2])
return k_count
end
function beautify_title(str::AbstractString)
parts = split(str, "'")
preprefix = parts[1]
infix = parts[2]
sufsuffix = parts[3]
parts = split(infix, "->")
prefix = parts[1]
suffix = parts[2]
k_count = count(c -> c == 'k', suffix)
B_count = count(c -> c == 'B', suffix)
if k_count == 1 || B_count == 1
new_suffix = suffix
elseif k_count >= 1
new_suffix = replace(suffix, r"k+" => "k^$k_count")
elseif B_count >= 1
new_suffix = replace(suffix, r"B+" => "B^$B_count")
end
return preprefix * L"%$prefix \rightarrow %$new_suffix" * sufsuffix
end
input_file = ARGS[1]
df = CSV.read(input_file, DataFrame)
n_inputs = df[:, "n_inputs"][1]
# plotting with threads as x axis
for process_name in processes
title_string = "$(beautify_title(process_name)), $n_inputs samples"
println("$title_string")
process_no_opt = process_name * " not optimized"
process_red = process_name * " reduced"
process_tape_no_opt = process_name * " not optimized tape"
process_tape_red = process_name * " reduced tape"
df_no_opt = filter(:process_name => x -> x == process_no_opt, df)
df_red = filter(:process_name => x -> x == process_red, df)
df_tape_no_opt = filter(:process_name => x -> x == process_tape_no_opt, df)
df_tape_red = filter(:process_name => x -> x == process_tape_red, df)
@df df_no_opt scatter(:cpu_threads, :cpu_time, label = "unoptimized function", markershape = :circle)
@df df_red scatter!(:cpu_threads, :cpu_time, label = "reduced function", markershape = :rect)
@df df_tape_no_opt scatter!(:cpu_threads, :cpu_time, label = "unoptimized tape", markershape = :utriangle)
@df df_tape_red scatter!(:cpu_threads, :cpu_time, label = "reduced tape", markershape = :star)
plot!(
title = title_string,
yscale = :linear,
legend = :outerright,
legendcolumns = 1,
legend_font_pointsize = 10,
size = (800, 600),
ylabel = "execution time (s)",
xlabel = "threads (#)",
)
savefig("$(process_name)_time.pdf")
@df df_no_opt scatter(:cpu_threads, :cpu_rate, label = "unoptimized function", markershape = :circle)
@df df_red scatter!(:cpu_threads, :cpu_rate, label = "reduced function", markershape = :rect)
@df df_tape_no_opt scatter!(:cpu_threads, :cpu_rate, label = "unoptimized tape", markershape = :utriangle)
@df df_tape_red scatter!(:cpu_threads, :cpu_rate, label = "reduced tape", markershape = :star)
plot!(
title = "Sample rate, " * title_string,
yscale = :log10,
legend = :outerright,
legendcolumns = 1,
legend_font_pointsize = 10,
size = (800, 600),
ylabel = "rate (" * L"s^{-1}" * ")",
xlabel = "threads (#)",
)
savefig("$(process_name)_rate.pdf")
@df df_no_opt scatter(:cpu_threads, :cpu_gflops, label = "unoptimized function", markershape = :circle)
@df df_red scatter!(:cpu_threads, :cpu_gflops, label = "reduced function", markershape = :rect)
@df df_tape_no_opt scatter!(:cpu_threads, :cpu_gflops, label = "unoptimized tape", markershape = :utriangle)
@df df_tape_red scatter!(:cpu_threads, :cpu_gflops, label = "reduced tape", markershape = :star)
plot!(
title = "CPU performance, " * title_string,
yscale = :linear,
legend = :outerright,
legendcolumns = 1,
legend_font_pointsize = 10,
size = (800, 600),
ylabel = "CPU performance (GFLOPS)",
xlabel = "threads (#)",
)
savefig("$(process_name)_performance.pdf")
end
# plotting with process size as x axis
THREADS = [1, 2, 4, 8, 16]
for threads in THREADS
title_string = "$threads threads, $n_inputs samples"
df_filt = filter(:cpu_threads => x -> x == threads, df)
df_filt = filter(:process_name => x -> proc_to_n(x) >= 1, df_filt)
df_filt.process_size = @. proc_to_n(df_filt.process_name)
df_no_opt = filter(:process_name => x -> match(r" not optimized$", x) !== nothing, df_filt)
df_red = filter(:process_name => x -> match(r" reduced$", x) !== nothing, df_filt)
df_tape_no_opt = filter(:process_name => x -> match(r" not optimized tape$", x) !== nothing, df_filt)
df_tape_red = filter(:process_name => x -> match(r" reduced tape$", x) !== nothing, df_filt)
@df df_no_opt scatter(:process_size, :graph_gen_time, label = "graph generation time")
@df df_red scatter!(:process_size, :optimization_time, label = "optimization time")
@df df_no_opt scatter!(:process_size, :function_generation_time, label = "unoptimized function generation time")
@df df_tape_no_opt scatter!(:process_size, :function_generation_time, label = "unoptimized tape generation time")
@df df_red scatter!(:process_size, :function_generation_time, label = "reduced function generation time")
@df df_tape_red scatter!(:process_size, :function_generation_time, label = "reduced tape generation time")
plot!(
title = "function generation times, " * title_string,
yscale = :log10,
legend = :outerbottom,
legendcolumns = 2,
legend_font_pointsize = 10,
size = (800, 600),
ylabel = "time (s)",
xlabel = "process size (#)",
)
savefig("gen_times_$(threads)_threads.pdf")
end

View File

@ -0,0 +1,143 @@
using CSV
using DataFrames
using Plots
using StatsPlots
using LaTeXStrings
if (length(ARGS) < 1)
println("Please use with \"input_file.csv\"")
end
processes = [
"QED Process: 'ke->ke'",
"QED Process: 'ke->kke'",
"QED Process: 'ke->kkke'",
"QED Process: 'ke->kkkke'",
"QED Process: 'ke->kkkkke'",
#"QED Process: 'ke->kkkkkke'",
#"QED Process: 'ke->kkkkkkke'",
"ABC Process: 'AB->AB'",
"ABC Process: 'AB->ABBB'",
"ABC Process: 'AB->ABBBBB'",
]
function proc_to_n(str::AbstractString)
parts = split(str, "'")
parts = split(parts[2], "->")
k_count = count(c -> c == 'k', parts[2])
return k_count
end
function abc_proc_to_n(str::AbstractString)
parts = split(str, "'")
parts = split(parts[2], "->")
b_count = count(c -> c == 'B', parts[2])
return b_count
end
function beautify_title(str::AbstractString)
parts = split(str, "'")
preprefix = parts[1]
infix = parts[2]
sufsuffix = parts[3]
parts = split(infix, "->")
prefix = parts[1]
suffix = parts[2]
k_count = count(c -> c == 'k', suffix)
B_count = count(c -> c == 'B', suffix)
if k_count == 1 || B_count == 1
new_suffix = suffix
elseif k_count >= 1
new_suffix = replace(suffix, r"k+" => "k^$k_count")
elseif B_count >= 1
new_suffix = replace(suffix, r"B+" => "B^$B_count")
end
return preprefix * L"%$prefix \rightarrow %$new_suffix" * sufsuffix
end
input_file = ARGS[1]
df = CSV.read(input_file, DataFrame)
n_inputs = df[:, "n_inputs"][1]
title_string = "QED N-Photon Compton Scattering\nCalculate 1,048,576 (\$2^{20}\$) Matrix Elements"
df_filt = filter(:process_name => x -> proc_to_n(x) >= 1, df)
df_filt.process_size = @. proc_to_n(df_filt.process_name)
df_red = filter(:process_name => x -> match(r" reduced$", x) !== nothing, df_filt)
@df df_red scatter(
:process_size,
:cpu_time,
yerror = :cpu_std,
label = "CPU execution time, 32 threads (s)",
markersize = 6,
)
@df df_red scatter!(
:process_size,
:gpu_time,
yerror = :gpu_std,
label = "GPU execution time, A100 80GB (s)",
markersize = 6,
)
plot!(
#title = title_string,
yscale = :log10,
legend = :outerbottom,
legendcolumns = 2,
legend_font_pointsize = 10,
size = (800, 600),
ylabel = "time (s)",
xlabel = "process size (#)",
)
savefig("cpu_vs_gpu_qed.pdf")
title_string = "\$AB\\rightarrow AB^n\$ ABC Processes\nCalculate 1,048,576 (\$2^{20}\$) Matrix Elements"
df_filt = filter(:process_name => x -> abc_proc_to_n(x) >= 1, df)
df_filt.process_size = @. abc_proc_to_n(df_filt.process_name)
df_red = filter(:process_name => x -> match(r" reduced$", x) !== nothing, df_filt)
@df df_red scatter(
:process_size,
:cpu_time,
yerror = :cpu_std,
label = "CPU execution time, 32 threads (s)",
markersize = 6,
)
@df df_red scatter!(
:process_size,
:gpu_time,
yerror = :gpu_std,
label = "GPU execution time, A100 80GB (s)",
markersize = 6,
)
plot!(
#title = title_string,
yscale = :log10,
legend = :outerbottom,
legendcolumns = 2,
legend_font_pointsize = 10,
size = (800, 600),
ylabel = "time (s)",
xlabel = "process size (#)",
)
savefig("cpu_vs_gpu_abc.pdf")

View File

@ -0,0 +1,212 @@
using CSV
using DataFrames
using Plots
using StatsPlots
using LaTeXStrings
if (length(ARGS) < 1)
println("Please use with \"input_file.csv\"")
end
processes = [
"QED Process: 'ke->ke'",
"QED Process: 'ke->kke'",
"QED Process: 'ke->kkke'",
"QED Process: 'ke->kkkke'",
"QED Process: 'ke->kkkkke'",
]
function proc_to_n(str::AbstractString)
parts = split(str, "'")
parts = split(parts[2], "->")
k_count = count(c -> c == 'k', parts[2])
return k_count
end
function beautify_title(str::AbstractString)
parts = split(str, "'")
preprefix = parts[1]
infix = parts[2]
sufsuffix = parts[3]
parts = split(infix, "->")
prefix = parts[1]
suffix = parts[2]
k_count = count(c -> c == 'k', suffix)
B_count = count(c -> c == 'B', suffix)
if k_count == 1 || B_count == 1
new_suffix = suffix
elseif k_count >= 1
new_suffix = replace(suffix, r"k+" => "k^$k_count")
elseif B_count >= 1
new_suffix = replace(suffix, r"B+" => "B^$B_count")
end
return "QED Compton Scattering Process " * L"%$prefix \rightarrow %$new_suffix" * sufsuffix
end
input_file = ARGS[1]
df = CSV.read(input_file, DataFrame)
n_inputs = df[:, "n_inputs"][1]
gpus = df.gpu_devices[1]
cpus = df.cpu_threads[1]
power = Int(round(log2(n_inputs)))
chunk_sizes = [
"\$2^{10}\$",
"\$2^{11}\$",
"\$2^{12}\$",
"\$2^{13}\$",
"\$2^{14}\$",
"\$2^{15}\$",
"\$2^{16}\$",
"\$2^{17}\$",
"\$2^{18}\$",
"\$2^{19}\$",
"\$2^{20}\$",
]
best_times = Vector{Float64}()
best_times_std = Vector{Float64}()
# plotting with threads as x axis
for process_name in processes
df_filt = filter(:process_name => x -> x == process_name, df)
df_filt.cpu_ratio = df_filt.cpu_chunks ./ (df_filt.cpu_chunks .+ df_filt.gpu_chunks) .* 100.0
df_filt.gpu_ratio = df_filt.gpu_chunks ./ (df_filt.cpu_chunks .+ df_filt.gpu_chunks) .* 100.0
push!(best_times, minimum(df_filt.time))
bar(chunk_sizes, df_filt.cpu_ratio, label = "workload completed by \$$(cpus)\$ CPU threads (%)")
bar!(
chunk_sizes,
[100 for _ in chunk_sizes],
label = "workload completed by $(gpus) GPUs (%)",
fillto = df_filt.cpu_ratio,
)
plot!(
#title = "$(beautify_title(process_name))\nComputing $(n_inputs) (\$2^{$(power)}\$) Matrix Elements",
yscale = :linear,
#xticks = [1024 4096 16384 65536 262144 1048576],
ylim = (0, 105),
legend = :outerbottom,
legendcolumns = 1,
legend_font_pointsize = 10,
#size = (800, 600),
ylabel = "contribution (%)",
xlabel = "chunk size (#)",
)
savefig("full_node_chunk_size_$(proc_to_n(process_name))k_ratio.pdf")
scatter(
chunk_sizes,
df_filt.rate,
label = "total execution rate (\$s^{-1}\$)",
#title = "$(beautify_title(process_name))\nComputing $(n_inputs) (\$2^{$(power)}\$) Matrix Elements",
ylim = (0, :auto),
#yscale = :log10,
#xticks = [1024 4096 16384 65536 262144 1048576],
legend = :outerbottom,
legendcolumns = 1,
legend_font_pointsize = 10,
#size = (800, 600),
ylabel = "rate (\$s^{-1}\$)",
xlabel = "chunk size (#)",
markersize = 7,
)
savefig("full_node_chunk_size_$(proc_to_n(process_name))k_rate.pdf")
scatter(
chunk_sizes,
df_filt.time,
yerror = df_filt.std,
label = "total execution time (s)",
#title = "$(beautify_title(process_name))\nComputing $(n_inputs) (\$2^{$(power)}\$) Matrix Elements",
#xticks = [1024 4096 16384 65536 262144 1048576],
ylim = (0, maximum(df_filt.time) * 1.05),
legend = :outerbottom,
legendcolumns = 1,
legend_font_pointsize = 10,
#size = (800, 600),
ylabel = "time (s)",
xlabel = "chunk size (#)",
markersize = 7,
)
savefig("full_node_chunk_size_$(proc_to_n(process_name))k_time.pdf")
end
# plotting with process size as x axis
A100_rates = [2.530045276927587e9, 1.16972304616864e9, 2.0002725972692013e8, 3.495722925446318e7, 4.792187095617111e6]
CPU_32threads_rates =
[3.2691139045711152e7, 1.1578342663759507e7, 3.1670680975577887e6, 731037.7069429948, 115001.5594731802]
theory_rates = (A100_rates .+ CPU_32threads_rates) .* 4
scatter(
proc_to_n.(processes),
best_times,
label = "full node best achieved time (s)",
#title = "QED N-Photon Compton Scattering\nComputing $(n_inputs) (\$2^{$(power)}\$) Matrix Elements",
ylim = (0, maximum(best_times) * 1.05),
legend = :outerbottom,
legendcolumns = 1,
legend_font_pointsize = 10,
#size = (800, 600),
ylabel = "time (s)",
xlabel = "process size (#)",
markersize = 7,
)
savefig("full_node_process_best_time.pdf")
scatter(
proc_to_n.(processes),
(n_inputs ./ best_times),
label = "full node best achieved rate (\$s^{-1}\$)",
#title = "QED N-Photon Compton Scattering\nComputing $(n_inputs) (\$2^{$(power)}\$) Matrix Elements",
ylim = (0, maximum(n_inputs ./ best_times) * 1.05),
legend = :outerbottom,
legendcolumns = 1,
legend_font_pointsize = 10,
#size = (800, 600),
ylabel = "rate (\$s^{-1}\$)",
xlabel = "process size (#)",
markersize = 7,
)
savefig("full_node_process_best_rate.pdf")
scatter(
proc_to_n.(processes),
[(n_inputs ./ best_times) theory_rates],
label = ["full node best achieved rate (\$s^{-1}\$)" "theoretical rate from previous benchmarks (\$s^{-1}\$)"],
#title = "QED N-Photon Compton Scattering\nComputing $(n_inputs) (\$2^{$(power)}\$) Matrix Elements",
#ylim = (0, max(maximum(n_inputs ./ best_times), maximum(theory_rates)) * 1.05),
yscale = :log10,
legend = :outerbottom,
legendcolumns = 1,
legend_font_pointsize = 10,
#size = (800, 600),
ylabel = "rate (\$s^{-1}\$)",
xlabel = "process size (#)",
markersize = 7,
)
savefig("full_node_process_best_rate_plus_theory.pdf")

232
data/evaluate_gen.jl Normal file
View File

@ -0,0 +1,232 @@
using CSV
using DataFrames
using Plots
using StatsPlots
using LaTeXStrings
if (length(ARGS) < 1)
println("Please use with \"input_file.csv\"")
end
function proc_to_n(str::AbstractString)
parts = split(str, "->")
k_count = count(c -> c == 'k', parts[2])
return k_count
end
input_file = ARGS[1]
df = CSV.read(input_file, DataFrame)
# plotting with process size as x axis
THREADS = [1]
for threads in THREADS
title_string = "n-photon Compton diagram generation"
df_filt = filter(:cpu_threads => x -> x == threads, df)
df_filt = filter(:process_name => x -> proc_to_n(x) >= 1, df_filt)
# ns -> s
df_filt.graph_gen_mean = @. df_filt.graph_gen_mean / 1e9
df_filt.graph_gen_std = @. df_filt.graph_gen_std / 1e9
# B -> MB (not MiB since the log scale is base 10)
df_filt.graph_mem = @. df_filt.graph_mem / 1e6
df_filt.graph_mem_reduced = @. df_filt.graph_mem_reduced / 1e6
df_filt.process_size = @. proc_to_n(df_filt.process_name)
l = length(df_filt.process_size)
println(df_filt[!, :process_size])
println(df_filt[!, :graph_mem])
println(df_filt[!, :graph_mem_reduced])
@df df_filt scatter(:process_size, :graph_mem, label = "unreduced graph", markersize = 7)
scatter!(
df_filt[!, :process_size],
df_filt[!, :graph_mem_reduced],
label = "reduced graph",
markershape = :square,
markersize = 7,
)
plot!(
title = "n-photon Compton diagram memory footprint",
yscale = :log10,
legend = :outerbottom,
minorgrid = true,
xticks = :process_size,
#yticks = [1e-3, 1e-1, 1e1, 1e3],
xgrid = false,
xminorticks = false,
legendcolumns = 1,
legend_font_pointsize = 12,
fontsize = 12,
size = (800, 600),
ylabel = "memory footprint (MB)",
xlabel = "process size (#)",
)
savefig("gen_memory_$(threads).pdf")
@df df_filt scatter(
:process_size,
:graph_gen_mean,
yerror = :graph_gen_std,
label = "graph generation time",
markersize = 7,
)
scatter!(
df_filt[!, :process_size],
df_filt[!, :graph_elapsed_reduce],
label = "graph reduction time",
markershape = :square,
markersize = 7,
)
plot!(
title = title_string,
yscale = :log10,
legend = :outerbottom,
minorgrid = true,
xticks = :process_size,
yticks = [1e-3, 1e-1, 1e1, 1e3],
xgrid = false,
xminorticks = false,
legendcolumns = 1,
legend_font_pointsize = 12,
fontsize = 12,
size = (800, 600),
ylabel = "time (s)",
xlabel = "process size (#)",
)
savefig("gen_times_$(threads)_threads.pdf")
exit(0)
# graph size
title_string = "n-photon Compton unreduced graph size"
@df df_filt scatter(:process_size, :graph_nodes, label = "nodes", markershape = :circle)
@df df_filt scatter!(:process_size, :graph_edges, label = "edges", markershape = :square)
@df df_filt scatter!(:process_size, :graph_u_nodes, label = "U-nodes", markershape = :star)
@df df_filt scatter!(:process_size, :graph_v_nodes, label = "V-nodes", markershape = :utriangle)
@df df_filt scatter!(:process_size[2:end], :graph_s1_nodes[2:end], label = "S1-nodes", markershape = :x)
@df df_filt scatter!(:process_size, :graph_s2_nodes, label = "S2-nodes", markershape = :diamond)
plot!(
title = title_string,
yscale = :log10,
legend = :outerbottom,
yminorgrid = true,
xticks = :process_size,
yticks = [1e1, 1e3, 1e5, 1e7],
xgrid = false,
xminorticks = false,
legendcolumns = 2,
legend_font_pointsize = 10,
size = (800, 600),
ylabel = "(#)",
xlabel = "process size (#)",
)
savefig("compton_graph_size_unreduced.pdf")
# graph size
title_string = "n-photon Compton reduced graph size"
@df df_filt scatter(:process_size, :graph_nodes_reduced, label = "nodes", markershape = :circle)
@df df_filt scatter!(:process_size, :graph_edges_reduced, label = "edges", markershape = :square)
@df df_filt scatter!(:process_size, :graph_u_nodes_reduced, label = "U-nodes", markershape = :star)
@df df_filt scatter!(:process_size, :graph_v_nodes_reduced, label = "V-nodes", markershape = :utriangle)
@df df_filt scatter!(:process_size[2:end], :graph_s1_nodes_reduced[2:end], label = "S1-nodes", markershape = :x)
@df df_filt scatter!(:process_size, :graph_s2_nodes_reduced, label = "S2-nodes", markershape = :diamond)
plot!(
title = title_string,
yscale = :log10,
legend = :outerbottom,
yminorgrid = true,
xticks = :process_size,
yticks = [1e1, 1e2, 1e3, 1e4, 1e5, 1e6],
xgrid = false,
xminorticks = false,
legendcolumns = 2,
legend_font_pointsize = 10,
size = (800, 600),
ylabel = "(#)",
xlabel = "process size (#)",
)
savefig("compton_graph_size_reduced.pdf")
# graph size versus
title_string = "n-photon Compton graph sizes"
@df df_filt scatter(:process_size, :graph_nodes, label = "nodes", markershape = :circle)
@df df_filt scatter!(:process_size, :graph_edges, label = "edges", markershape = :square)
@df df_filt scatter!(:process_size, :graph_nodes_reduced, label = "nodes (after reduction)", markershape = :star)
@df df_filt scatter!(
:process_size,
:graph_edges_reduced,
label = "edges (after reduction)",
markershape = :utriangle,
)
plot!(
title = title_string,
yscale = :log10,
legend = :outerbottom,
yminorgrid = true,
xticks = :process_size,
yticks = [1e1, 1e2, 1e3, 1e4, 1e5, 1e6],
xgrid = false,
xminorticks = false,
legendcolumns = 2,
legend_font_pointsize = 10,
size = (800, 600),
ylabel = "(#)",
xlabel = "process size (#)",
)
savefig("compton_graph_size_versus.pdf")
end
# for a specific process, plot times with threads as x
process = "ke->kkkkkkkke"
title_string = "n-photon Compton diagram generation times, $process"
df_filt = filter(:process_name => x -> x == process, df)
df_filt.graph_gen_mean = @. df_filt.graph_gen_mean / 1e9
df_filt.graph_gen_std = @. df_filt.graph_gen_std / 1e9
@df df_filt scatter(
:cpu_threads,
:graph_gen_mean,
yerror = :graph_gen_std,
label = "graph generation time",
markersize = 7,
)
plot!(
title = title_string,
yscale = :linear,
legend = :outerbottom,
minorgrid = true,
xticks = :cpu_threads,
#yticks = [1e-3, 1e-2, 1e-1, 1e-0, 1e1],
ylim = (0, max(df_filt[!, :graph_gen_mean]...) * 1.1),
xgrid = false,
xminorticks = false,
legendcolumns = 1,
legend_font_pointsize = 10,
size = (800, 600),
ylabel = "time (s)",
xlabel = "process size (#)",
)
savefig("gen_times_$(process).pdf")

View File

@ -0,0 +1,52 @@
using CSV
using DataFrames
using Plots
using StatsPlots
using LaTeXStrings
if (length(ARGS) < 2)
println("Please use with \"input_file.csv\" \"input_file_onesided.csv\"")
end
function proc_to_n(str::AbstractString)
parts = split(str, "->")
k_count = count(c -> c == 'k', parts[2])
return k_count
end
input_file = ARGS[1]
input_file_onesided = ARGS[2]
df = CSV.read(input_file, DataFrame)
df2 = CSV.read(input_file_onesided, DataFrame)
df_filt = filter(:process_name => x -> proc_to_n(x) >= 1 && proc_to_n(x) <= 7, df)
df_filt.process_size = @. proc_to_n(df_filt.process_name)
df_filt2 = filter(:process_name => x -> proc_to_n(x) >= 1 && proc_to_n(x) <= 7, df2)
df_filt2.process_size = @. proc_to_n(df_filt2.process_name)
# graph size
title_string = "n-photon Compton reduced graph size"
@df df_filt scatter(:process_size, :graph_nodes_reduced, label = "nodes, two-sided generation", markershape = :circle)
@df df_filt2 scatter!(:process_size, :graph_nodes_reduced, label = "nodes, one-sided generation", markershape = :square)
plot!(
title = title_string,
yscale = :log10,
legend = :outerbottom,
yminorgrid = true,
xticks = :process_size,
yticks = [1e1, 1e2, 1e3, 1e4, 1e5, 1e6],
xgrid = false,
xminorticks = false,
legendcolumns = 2,
legend_font_pointsize = 10,
size = (800, 600),
ylabel = "(#)",
xlabel = "process size (#)",
)
savefig("compton_diagram_gen_comparison.pdf")

130
data/evaluate_gpu.jl Normal file
View File

@ -0,0 +1,130 @@
using CSV
using DataFrames
using Plots
using StatsPlots
using LaTeXStrings
if (length(ARGS) < 1)
println("Please use with \"input_file.csv\"")
end
processes = [
"QED Process: 'ke->ke'",
"QED Process: 'ke->kke'",
"QED Process: 'ke->kkke'",
"QED Process: 'ke->kkkke'",
"QED Process: 'ke->kkkkke'",
"ABC Process: 'AB->AB'",
"ABC Process: 'AB->ABBB'",
"ABC Process: 'AB->ABBBBB'",
]
function proc_to_n(str::AbstractString)
parts = split(str, "'")
parts = split(parts[2], "->")
k_count = count(c -> c == 'k', parts[2])
return k_count
end
function beautify_title(str::AbstractString)
parts = split(str, "'")
preprefix = parts[1]
infix = parts[2]
sufsuffix = parts[3]
parts = split(infix, "->")
prefix = parts[1]
suffix = parts[2]
k_count = count(c -> c == 'k', suffix)
B_count = count(c -> c == 'B', suffix)
if k_count == 1 || B_count == 1
new_suffix = suffix
elseif k_count >= 1
new_suffix = replace(suffix, r"k+" => "k^$k_count")
elseif B_count >= 1
new_suffix = replace(suffix, r"B+" => "B^$B_count")
end
return preprefix * L"%$prefix \rightarrow %$new_suffix" * sufsuffix
end
input_file = ARGS[1]
df = CSV.read(input_file, DataFrame)
n_inputs = df[:, "n_inputs"][1]
gpu_name = df[:, "gpu_name"][1]
if (gpu_name == "")
println("Results file did not execute everything on GPU! (or didn't write gpu name)")
exit(0)
end
# plotting with process size as x axis
title_string = "GPU $gpu_name, $n_inputs samples"
df_filt = filter(:process_name => x -> proc_to_n(x) >= 1, df)
df_filt.gpu_rate = df_filt.gpu_rate
df_filt.gpu_time = df_filt.gpu_time
df_filt.gpu_gflops = df_filt.gpu_gflops
df_filt.process_size = @. proc_to_n(df_filt.process_name)
df_no_opt = filter(:process_name => x -> match(r" not optimized$", x) !== nothing, df_filt)
df_red = filter(:process_name => x -> match(r" reduced$", x) !== nothing, df_filt)
@df df_no_opt scatter(:process_size, :gpu_rate, label = "unoptimized function execution rate", markersize = 7)
@df df_red scatter!(:process_size, :gpu_rate, label = "reduced function execution rate", markersize = 7)
plot!(
#title = title_string * ", sample rate",
yscale = :log10,
legend = :outerbottom,
xticks = [1, 2, 3, 4, 5],
legendcolumns = 2,
legend_font_pointsize = 10,
size = (800, 600),
ylabel = "rate (" * L"s^{-1}" * ")",
xlabel = "process size (#)",
)
savefig("gpu_rate_$(gpu_name).pdf")
@df df_no_opt scatter(:process_size, :gpu_time, label = "unoptimized function execution time", markersize = 7)
@df df_red scatter!(:process_size, :gpu_time, label = "reduced function execution time", markersize = 7)
plot!(
#title = title_string * ", execution time",
yscale = :log10,
legend = :outerbottom,
xticks = [1, 2, 3, 4, 5],
legendcolumns = 2,
legend_font_pointsize = 10,
size = (800, 600),
ylabel = "time (s)",
xlabel = "process size (#)",
)
savefig("gpu_times_$(gpu_name).pdf")
@df df_no_opt scatter(:process_size, :gpu_gflops, label = "unoptimized function", markersize = 7)
@df df_red scatter!(:process_size, :gpu_gflops, label = "reduced function", markersize = 7)
plot!(
#title = title_string * ", GFLOPS",
yscale = :linear,
legend = :outerbottom,
xticks = [1, 2, 3, 4, 5],
legendcolumns = 2,
legend_font_pointsize = 10,
size = (800, 600),
ylabel = "performance (GFLOPS)",
xlabel = "process size (#)",
)
savefig("gpu_perf_$(gpu_name).pdf")

View File

@ -0,0 +1,279 @@
using Plots
using StatsPlots
using CSV
using DataFrames
using LaTeXStrings
if (length(ARGS) < 2)
println("Please use with \"input_file.csv\" \"input_file_gpu.csv\"")
end
function proc_to_n(str::AbstractString)
parts = split(str, "'")
parts = split(parts[2], "->")
k_count = count(c -> c == 'k', parts[2])
return k_count
end
function beautify_title(str::AbstractString)
parts = split(str, "->")
prefix = parts[1]
suffix = parts[2]
k_count = count(c -> c == 'k', suffix)
B_count = count(c -> c == 'B', suffix)
if k_count == 1 || B_count == 1
new_suffix = suffix
elseif k_count >= 1
new_suffix = replace(suffix, r"k+" => "k^$k_count")
elseif B_count >= 1
new_suffix = replace(suffix, r"B+" => "B^$B_count")
end
return L"%$prefix \rightarrow %$new_suffix"
end
processes = ["ke->ke", "ke->kke", "ke->kkke", "ke->kkkke", "ke->kkkkke", "AB->AB", "AB->ABBB", "AB->ABBBBB"]
input_file = ARGS[1]
input_file_gpu = ARGS[2]
df = CSV.read(input_file, DataFrame)
df_gpu = CSV.read(input_file_gpu, DataFrame)
n_inputs = 2^20
#=
for process in processes
df_filt = filter(:process => x -> x == process, df)
df_filt_gpu = filter(:process => x -> x == process, df_gpu)
# add dummy factors to get the numbers in similar orders of magnitude
df_filt.cumulative_optimization_time = df_filt.cumulative_optimization_time .* 1e4
df_filt_gpu.cumulative_optimization_time = df_filt_gpu.cumulative_optimization_time .* 1e4
df_filt_gpu.gpu_t = df_filt_gpu.gpu_t .* 1e3
cpu = !isempty(df_filt)
gpu = !isempty(df_filt_gpu)
ymax = 0.0
if cpu
@df df_filt scatter(
:operations,
:cumulative_optimization_time,
label = "Cumulative Optimization Time (x10000) (s)",
markersize = 4,
)
ymax = max(df_filt[!, :cpu_st_t]..., df_filt[!, :cumulative_optimization_time]...) * 1.1 * 1e4
@df df_filt scatter!(
:operations,
:cpu_st_t,
label = "Single-Threaded Execution (s)",
markersize = 4,
markershape = :square,
)
end
if gpu
if !cpu
@df df_filt_gpu scatter(
:operations,
:cumulative_optimization_time,
label = "Cumulative Optimization Time (x10000) (s)",
markersize = 4,
)
ymax = max(df_filt_gpu[!, :gpu_t]..., df_filt_gpu[!, :cumulative_optimization_time]...) * 1.1 * 1e4
end
@df df_filt_gpu scatter!(
:operations,
:gpu_t,
label = "GPU Execution (x1000) (s)",
markersize = 4,
markershape = :diamond,
)
end
if cpu || gpu
plot!(
title = ("$(beautify_title(process)) Reduction Progression ($(n_inputs) Inputs)"),
xscale = :linear,
yscale = :linear,
#ylim = (0, ymax),
legend = :outerbottom,
minorgrid = true,
xticks = :process_size,
#yticks = [1e-3, 1e-1, 1e1, 1e3],
xgrid = false,
xminorticks = false,
legendcolumns = 1,
legend_font_pointsize = 12,
fontsize = 12,
size = (800, 600),
xlabel = "optimizer steps (#)",
ylabel = "time (s)",
)
savefig("$(String(process))_reduction_bench.pdf")
end
end
# ABC vs QED
AB_process = "AB->ABBB"
abc_label = "\$A + B \\rightarrow A + 3B\$"
QED_process = "ke->kkkke"
qed_label = "\$e^- + \\gamma \\rightarrow e^- + 4\\gamma\$"
df_filt_AB = filter(:process => x -> x == AB_process, df)
df_filt_QED = filter(:process => x -> x == QED_process, df)
max_AB = max(df_filt_AB[!, :operations]...)
max_QED = max(df_filt_QED[!, :operations]...)
df_filt_AB.reduction_progress = df_filt_AB.operations ./ max_AB .* 100.0
df_filt_QED.reduction_progress = df_filt_QED.operations ./ max_QED .* 100.0
df_filt_AB.relative_performance = df_filt_AB.cpu_st_t ./ df_filt_AB[!, :cpu_st_t][1] .* 100.0
df_filt_QED.relative_performance = df_filt_QED.cpu_st_t ./ df_filt_QED[!, :cpu_st_t][1] .* 100.0
@df df_filt_AB scatter(:reduction_progress, :relative_performance, label = abc_label, markersize = 4)
@df df_filt_QED scatter!(:reduction_progress, :relative_performance, label = qed_label, markersize = 4)
plot!(
#title = ("Relative Performance of $(beautify_title(QED_process)) versus $(beautify_title(AB_process)) on CPU"),
xscale = :linear,
yscale = :linear,
#ylim = (0, ymax),
legend = :outerbottom,
minorgrid = true,
xticks = :process_size,
#yticks = [1e-3, 1e-1, 1e1, 1e3],
xgrid = false,
xminorticks = false,
legendcolumns = 1,
legend_font_pointsize = 12,
fontsize = 12,
size = (800, 600),
xlabel = "reduction progress (%)",
ylabel = "relative time taken (%)",
)
savefig("reduction_bench_relative.pdf")
# ABC vs QED on GPU
AB_process = "AB->ABBB"
abc_label = "\$A + B \\rightarrow A + 3B\$"
QED_process = "ke->kkkke"
qed_label = "\$e^- + \\gamma \\rightarrow e^- + 4\\gamma\$"
df_filt_AB = filter(:process => x -> x == AB_process, df_gpu)
df_filt_QED = filter(:process => x -> x == QED_process, df_gpu)
max_AB = max(df_filt_AB[!, :operations]...)
max_QED = max(df_filt_QED[!, :operations]...)
df_filt_AB.reduction_progress = df_filt_AB.operations ./ max_AB .* 100.0
df_filt_QED.reduction_progress = df_filt_QED.operations ./ max_QED .* 100.0
df_filt_AB.relative_performance = df_filt_AB.gpu_t ./ df_filt_AB[!, :gpu_t][1] .* 100.0
df_filt_QED.relative_performance = df_filt_QED.gpu_t ./ df_filt_QED[!, :gpu_t][1] .* 100.0
df_filt_AB.relative_std = df_filt_AB.gpu_s ./ df_filt_AB[!, :gpu_t][1] .* 100.0
df_filt_QED.relative_std = df_filt_QED.gpu_s ./ df_filt_QED[!, :gpu_t][1] .* 100.0
@df df_filt_AB scatter(
:reduction_progress,
:relative_performance,
yerror = :relative_std,
label = abc_label,
markersize = 4,
)
@df df_filt_QED scatter!(
:reduction_progress,
:relative_performance,
yerror = :relative_std,
label = qed_label,
markersize = 4,
)
plot!(
#title = "Relative Performance of $(beautify_title(QED_process)) versus $(beautify_title(AB_process)) on GPU (A100)",
xscale = :linear,
yscale = :linear,
#ylim = (0, ymax),
legend = :outerbottom,
minorgrid = true,
xticks = :process_size,
#yticks = [1e-3, 1e-1, 1e1, 1e3],
xgrid = false,
xminorticks = false,
legendcolumns = 1,
legend_font_pointsize = 12,
fontsize = 12,
size = (800, 600),
xlabel = "reduction progress (%)",
ylabel = "relative time taken (%)",
)
savefig("reduction_bench_relative_gpu.pdf")
=#
QED_process = "ke->kkke"
QED_label = "\$\\e^- + \\gamma \\rightarrow \\e^- + 3\\gamma\$"
df_filt_QED_GPU = filter(:process => x -> x == QED_process, df_gpu)
df_filt_QED_CPU = filter(:process => x -> x == QED_process, df)
max_QED = max(df_filt_QED_CPU[!, :operations]...)
df_filt_QED_GPU.reduction_progress = df_filt_QED_GPU.operations ./ max_QED .* 100.0
df_filt_QED_CPU.reduction_progress = df_filt_QED_CPU.operations ./ max_QED .* 100.0
df_filt_QED_GPU.relative_performance = df_filt_QED_GPU.gpu_t ./ df_filt_QED_GPU[!, :gpu_t][1] .* 100.0
df_filt_QED_CPU.relative_performance = df_filt_QED_CPU.cpu_st_t ./ df_filt_QED_CPU[!, :cpu_st_t][1] .* 100.0
df_filt_QED_GPU.relative_std = df_filt_QED_GPU.gpu_s ./ df_filt_QED_GPU[!, :gpu_t][1] .* 100.0
df_filt_QED_CPU.relative_std = df_filt_QED_CPU.cpu_st_s ./ df_filt_QED_CPU[!, :cpu_st_t][1] .* 100.0
@df df_filt_QED_CPU scatter(
:reduction_progress,
:relative_performance,
yerror = :relative_std,
label = "CPU relative time taken (%)",
markersize = 4,
)
@df df_filt_QED_GPU scatter!(
:reduction_progress,
:relative_performance,
yerror = :relative_std,
label = "GPU relative time taken (%)",
markersize = 4,
)
plot!(
#title = "Relative Performance of $(beautify_title(QED_process)) on CPU versus GPU",
xscale = :linear,
yscale = :linear,
ylim = (0, :auto),
legend = :outerbottom,
minorgrid = true,
xticks = :process_size,
#yticks = [1e-3, 1e-1, 1e1, 1e3],
xgrid = false,
xminorticks = false,
legendcolumns = 1,
legend_font_pointsize = 12,
fontsize = 12,
size = (800, 600),
xlabel = "reduction progress (%)",
ylabel = "relative time taken (%)",
)
savefig("reduction_bench_relative_cpu_vs_gpu.pdf")

BIN
data/results.zip (Stored with Git LFS) Normal file

Binary file not shown.

View File

@ -2,3 +2,4 @@
Documenter = "e30172f5-a6a5-5a46-863b-614d45cd2de4"
DocumenterTools = "35a29f4d-8980-5a13-9543-d66fff28ecb8"
MetagraphOptimization = "3e869610-d48d-4942-ba70-c1b702a33ca4"
QEDprocesses = "46de9c38-1bb3-4547-a1ec-da24d767fdad"

View File

@ -0,0 +1,259 @@
<mxfile host="Electron" modified="2023-11-25T19:36:18.149Z" agent="Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) draw.io/21.6.1 Chrome/114.0.5735.289 Electron/25.9.4 Safari/537.36" etag="hBUSDG3lmnElLEv2sh-Z" version="21.6.1" type="device">
<diagram name="Page-1" id="pzz-rsbNjEFeZeQIA-38">
<mxGraphModel dx="1430" dy="853" grid="1" gridSize="10" guides="1" tooltips="1" connect="1" arrows="1" fold="1" page="1" pageScale="1" pageWidth="500" pageHeight="900" math="0" shadow="0">
<root>
<mxCell id="0" />
<mxCell id="1" parent="0" />
<mxCell id="KG5lhhUBjoQ79gfvQvIC-19" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-6" target="KG5lhhUBjoQ79gfvQvIC-18" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-6" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;base_state&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;AdjointBiSpinor&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="190" y="600" width="120" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-20" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-7" target="KG5lhhUBjoQ79gfvQvIC-18" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-7" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;base_state&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;BiSpinor&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="310" y="600" width="120" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-28" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-8" target="KG5lhhUBjoQ79gfvQvIC-26" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-8" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;base_state&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;AdjointBiSpinor&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="550" y="600" width="120" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-29" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-9" target="KG5lhhUBjoQ79gfvQvIC-26" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-9" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;base_state&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;BiSpinor&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="430" y="600" width="120" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-21" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-14" target="KG5lhhUBjoQ79gfvQvIC-6" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-14" value="U(p&lt;sub&gt;1&lt;/sub&gt;)&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font color=&quot;#0000ff&quot;&gt;&lt;b&gt;IncomingAntiFermion&lt;/b&gt;&lt;/font&gt;&lt;br&gt;Outer Edge" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="190" y="700" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-22" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-15" target="KG5lhhUBjoQ79gfvQvIC-7" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-15" value="U(e&lt;sub style=&quot;border-color: var(--border-color);&quot;&gt;1&lt;/sub&gt;)&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;b&gt;&lt;font color=&quot;#0000ff&quot;&gt;IncomingFermion&lt;br&gt;&lt;/font&gt;&lt;/b&gt;Outer Edge" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="310" y="700" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-23" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-16" target="KG5lhhUBjoQ79gfvQvIC-9" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-16" value="U(p&lt;span style=&quot;font-size: 10px;&quot;&gt;&lt;sub&gt;2&lt;/sub&gt;&lt;/span&gt;)&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;b&gt;&lt;font color=&quot;#0000ff&quot;&gt;OutgoingAntiFermion&lt;br&gt;&lt;/font&gt;&lt;/b&gt;Outer Edge" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="430" y="700" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-24" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-17" target="KG5lhhUBjoQ79gfvQvIC-8" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-17" value="U(e&lt;sub style=&quot;border-color: var(--border-color);&quot;&gt;2&lt;/sub&gt;)&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;b&gt;&lt;font color=&quot;#0000ff&quot;&gt;OutgoingFermion&lt;br&gt;&lt;/font&gt;&lt;/b&gt;Outer Edge" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="550" y="700" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-30" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-18" target="KG5lhhUBjoQ79gfvQvIC-25" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-18" value="V(e&lt;sub&gt;1&lt;/sub&gt;, p&lt;sub&gt;1&lt;/sub&gt;)&lt;br&gt;Result Particle:&lt;br&gt;q: &lt;font color=&quot;#0000ff&quot;&gt;&lt;b&gt;OutgoingPhoton&lt;br&gt;&lt;/b&gt;&lt;/font&gt;" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="240" y="480" width="140" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-36" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-25" target="KG5lhhUBjoQ79gfvQvIC-35" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-25" value="&lt;b&gt;&lt;font color=&quot;#336600&quot;&gt;vertex&lt;/font&gt;&lt;/b&gt; -&amp;gt;&lt;br&gt;AdjointBiSpinor * &lt;br&gt;DiracMatrix *&lt;br&gt;BiSpinor&lt;br&gt;=&amp;nbsp;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font color=&quot;#cc00cc&quot; style=&quot;border-color: var(--border-color);&quot;&gt;Complex&lt;br&gt;&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="250" y="360" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-32" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-26" target="KG5lhhUBjoQ79gfvQvIC-27" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-26" value="V(e&lt;sub&gt;2&lt;/sub&gt;, p&lt;sub&gt;2&lt;/sub&gt;)&lt;br&gt;Result Particle:&lt;br&gt;q&#39;: &lt;b&gt;&lt;font color=&quot;#0000ff&quot;&gt;IncomingPhoton&lt;/font&gt;&lt;/b&gt;" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="480" y="480" width="140" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-37" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-27" target="KG5lhhUBjoQ79gfvQvIC-35" edge="1">
<mxGeometry relative="1" as="geometry">
<Array as="points">
<mxPoint x="550" y="340" />
<mxPoint x="420" y="340" />
</Array>
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-27" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;vertex&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;AdjointBiSpinor * &lt;br&gt;DiracMatrix *&lt;br&gt;BiSpinor&lt;br&gt;=&amp;nbsp;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font color=&quot;#cc00cc&quot; style=&quot;border-color: var(--border-color);&quot;&gt;Complex&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="490" y="360" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-39" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-35" target="KG5lhhUBjoQ79gfvQvIC-38" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-35" value="S2(q, q&#39;)&lt;br&gt;q == -q&#39;&lt;br&gt;&lt;b&gt;&lt;font color=&quot;#0000ff&quot;&gt;No Result Particle&lt;/font&gt;&lt;/b&gt;" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="360" y="240" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-71" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-38" target="KG5lhhUBjoQ79gfvQvIC-70" edge="1">
<mxGeometry relative="1" as="geometry">
<Array as="points">
<mxPoint x="670" y="170" />
</Array>
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-38" value="&lt;b style=&quot;&quot;&gt;&lt;font color=&quot;#336600&quot;&gt;inner_edge&lt;/font&gt;&lt;/b&gt; -&amp;gt;&lt;br&gt;Complex * propagator(q) * Complex&amp;nbsp;&lt;br&gt;=&amp;nbsp;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;Complex&lt;br&gt;&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="350" y="140" width="140" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-40" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-41" target="KG5lhhUBjoQ79gfvQvIC-57" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-41" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;base_state&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;AdjointBiSpinor&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="670" y="600" width="120" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-68" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-43" target="KG5lhhUBjoQ79gfvQvIC-61" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-43" value="&lt;b style=&quot;&quot;&gt;&lt;font color=&quot;#336600&quot;&gt;base_state&lt;/font&gt;&lt;/b&gt; -&amp;gt;&lt;br&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;AdjointBiSpinor&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="1030" y="600" width="120" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-67" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-45" target="KG5lhhUBjoQ79gfvQvIC-57" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-45" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;base_state&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;BiSpinor&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="790" y="600" width="120" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-46" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-47" target="KG5lhhUBjoQ79gfvQvIC-61" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-47" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;base_state&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;BiSpinor&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="910" y="600" width="120" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-48" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-49" target="KG5lhhUBjoQ79gfvQvIC-41" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-49" value="U(p&lt;sub style=&quot;border-color: var(--border-color);&quot;&gt;1&lt;/sub&gt;)&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#0000ff&quot;&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;IncomingAntiFermion&lt;/b&gt;&lt;/font&gt;&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;Outer Edge" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="670" y="700" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-69" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-51" target="KG5lhhUBjoQ79gfvQvIC-43" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-51" value="U(e&lt;sub&gt;2&lt;/sub&gt;)&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#0000ff&quot;&gt;OutgoingFermion&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;/font&gt;&lt;/b&gt;Outer Edge" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="1030" y="700" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-52" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-53" target="KG5lhhUBjoQ79gfvQvIC-47" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-53" value="U(e&lt;sub&gt;1&lt;/sub&gt;)&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#0000ff&quot;&gt;IncomingFermion&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;/font&gt;&lt;/b&gt;Outer Edge" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="910" y="700" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-54" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-55" target="KG5lhhUBjoQ79gfvQvIC-45" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-55" value="U(p&lt;sub style=&quot;border-color: var(--border-color);&quot;&gt;2&lt;/sub&gt;)&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font color=&quot;#0000ff&quot;&gt;&lt;b&gt;OutgoingAntiFermion&lt;br&gt;&lt;/b&gt;&lt;/font&gt;Outer Edge" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="790" y="700" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-56" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-57" target="KG5lhhUBjoQ79gfvQvIC-59" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-57" value="&lt;font style=&quot;font-size: 12px;&quot;&gt;V(p&lt;sub&gt;1&lt;/sub&gt;, p&lt;sub&gt;2&lt;/sub&gt;)&lt;/font&gt;&lt;br&gt;Result Particle:&lt;br&gt;q: &lt;b&gt;&lt;font color=&quot;#0000ff&quot;&gt;IncomingPhoton&lt;/font&gt;&lt;/b&gt;" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="720" y="480" width="140" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-58" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-59" target="KG5lhhUBjoQ79gfvQvIC-65" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-59" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;vertex&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;AdjointBiSpinor * &lt;br&gt;DiracMatrix *&lt;br&gt;BiSpinor&lt;br&gt;=&amp;nbsp;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;Complex&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="730" y="360" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-60" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-61" target="KG5lhhUBjoQ79gfvQvIC-63" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-61" value="&lt;font style=&quot;font-size: 12px;&quot;&gt;V(e&lt;sub&gt;1&lt;/sub&gt;, e&lt;sub&gt;2&lt;/sub&gt;)&lt;/font&gt;&lt;br&gt;Result Particle:&lt;br&gt;q&#39;: &lt;font color=&quot;#0000ff&quot;&gt;&lt;b&gt;OutgoingPhoton&lt;/b&gt;&lt;/font&gt;" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="960" y="480" width="140" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-62" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-63" target="KG5lhhUBjoQ79gfvQvIC-65" edge="1">
<mxGeometry relative="1" as="geometry">
<Array as="points">
<mxPoint x="1030" y="340" />
<mxPoint x="900" y="340" />
</Array>
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-63" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;vertex&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;AdjointBiSpinor * &lt;br&gt;DiracMatrix * &lt;br&gt;BiSpinor &lt;br&gt;=&amp;nbsp;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;Complex&lt;br&gt;&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="970" y="360" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-64" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-65" target="KG5lhhUBjoQ79gfvQvIC-66" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-65" value="S2(q, q&#39;)&lt;br&gt;q == -q&#39;&lt;br&gt;&lt;b&gt;&lt;font color=&quot;#0000ff&quot;&gt;No Result Particle&lt;/font&gt;&lt;/b&gt;" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="840" y="240" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-72" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-66" target="KG5lhhUBjoQ79gfvQvIC-70" edge="1">
<mxGeometry relative="1" as="geometry">
<Array as="points">
<mxPoint x="670" y="170" />
</Array>
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-66" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;inner_edge&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;Complex * propagator(q) * Complex&lt;br&gt;=&amp;nbsp;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font color=&quot;#cc00cc&quot;&gt;Complex&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="830" y="140" width="140" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-70" value="&lt;span style=&quot;font-size: 32px;&quot;&gt;diff()&lt;/span&gt;" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#ffcd28;strokeColor=#d79b00;gradientColor=#ffa500;" parent="1" vertex="1">
<mxGeometry x="610" y="20" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-73" value="&lt;b&gt;&lt;font style=&quot;font-size: 22px;&quot;&gt;ValueAcc&lt;/font&gt;&lt;/b&gt;" style="text;html=1;strokeColor=none;fillColor=none;align=center;verticalAlign=middle;whiteSpace=wrap;rounded=0;" parent="1" vertex="1">
<mxGeometry x="10" y="155" width="120" height="30" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-74" value="&lt;b&gt;&lt;font style=&quot;font-size: 22px;&quot;&gt;ValueAcc&lt;/font&gt;&lt;/b&gt;" style="text;html=1;strokeColor=none;fillColor=none;align=center;verticalAlign=middle;whiteSpace=wrap;rounded=0;" parent="1" vertex="1">
<mxGeometry x="10" y="385" width="120" height="30" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-75" value="&lt;b&gt;&lt;font style=&quot;font-size: 22px;&quot;&gt;ValueAcc&lt;/font&gt;&lt;/b&gt;" style="text;html=1;strokeColor=none;fillColor=none;align=center;verticalAlign=middle;whiteSpace=wrap;rounded=0;" parent="1" vertex="1">
<mxGeometry x="10" y="615" width="120" height="30" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-76" value="&lt;b&gt;&lt;font style=&quot;font-size: 22px;&quot;&gt;Particle Propagation&lt;/font&gt;&lt;/b&gt;" style="text;html=1;strokeColor=none;fillColor=none;align=center;verticalAlign=middle;whiteSpace=wrap;rounded=0;" parent="1" vertex="1">
<mxGeometry x="10" y="725" width="120" height="30" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-77" value="&lt;b&gt;&lt;font style=&quot;font-size: 22px;&quot;&gt;Particle Propagation&lt;/font&gt;&lt;/b&gt;" style="text;html=1;strokeColor=none;fillColor=none;align=center;verticalAlign=middle;whiteSpace=wrap;rounded=0;" parent="1" vertex="1">
<mxGeometry x="10" y="505" width="120" height="30" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-78" value="&lt;b&gt;&lt;font style=&quot;font-size: 22px;&quot;&gt;Particle Propagation&lt;/font&gt;&lt;/b&gt;" style="text;html=1;strokeColor=none;fillColor=none;align=center;verticalAlign=middle;whiteSpace=wrap;rounded=0;" parent="1" vertex="1">
<mxGeometry x="10" y="265" width="120" height="30" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-79" value="" style="endArrow=none;dashed=1;html=1;dashPattern=1 3;strokeWidth=2;rounded=0;" parent="1" edge="1">
<mxGeometry width="50" height="50" relative="1" as="geometry">
<mxPoint y="220" as="sourcePoint" />
<mxPoint x="1160" y="220" as="targetPoint" />
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-80" value="" style="endArrow=none;dashed=1;html=1;dashPattern=1 3;strokeWidth=2;rounded=0;" parent="1" edge="1">
<mxGeometry width="50" height="50" relative="1" as="geometry">
<mxPoint y="340" as="sourcePoint" />
<mxPoint x="1160" y="340" as="targetPoint" />
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-81" value="" style="endArrow=none;dashed=1;html=1;dashPattern=1 3;strokeWidth=2;rounded=0;" parent="1" edge="1">
<mxGeometry width="50" height="50" relative="1" as="geometry">
<mxPoint y="460" as="sourcePoint" />
<mxPoint x="1160" y="460" as="targetPoint" />
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-82" value="" style="endArrow=none;dashed=1;html=1;dashPattern=1 3;strokeWidth=2;rounded=0;" parent="1" edge="1">
<mxGeometry width="50" height="50" relative="1" as="geometry">
<mxPoint y="120" as="sourcePoint" />
<mxPoint x="1160" y="120" as="targetPoint" />
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-83" value="" style="endArrow=none;dashed=1;html=1;dashPattern=1 3;strokeWidth=2;rounded=0;" parent="1" edge="1">
<mxGeometry width="50" height="50" relative="1" as="geometry">
<mxPoint y="580" as="sourcePoint" />
<mxPoint x="1160" y="580" as="targetPoint" />
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-84" value="" style="endArrow=none;dashed=1;html=1;dashPattern=1 3;strokeWidth=2;rounded=0;" parent="1" edge="1">
<mxGeometry width="50" height="50" relative="1" as="geometry">
<mxPoint y="680" as="sourcePoint" />
<mxPoint x="1160" y="680" as="targetPoint" />
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-85" value="" style="endArrow=none;dashed=1;html=1;dashPattern=1 3;strokeWidth=2;rounded=0;" parent="1" edge="1">
<mxGeometry width="50" height="50" relative="1" as="geometry">
<mxPoint y="800" as="sourcePoint" />
<mxPoint x="1160" y="800" as="targetPoint" />
</mxGeometry>
</mxCell>
</root>
</mxGraphModel>
</diagram>
</mxfile>

View File

@ -0,0 +1,259 @@
<mxfile host="Electron" modified="2023-11-25T19:38:46.724Z" agent="Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) draw.io/21.6.1 Chrome/114.0.5735.289 Electron/25.9.4 Safari/537.36" etag="GgWoS9drZkpaqTCZiHI_" version="21.6.1" type="device">
<diagram name="Page-1" id="pzz-rsbNjEFeZeQIA-38">
<mxGraphModel dx="1430" dy="853" grid="1" gridSize="10" guides="1" tooltips="1" connect="1" arrows="1" fold="1" page="1" pageScale="1" pageWidth="500" pageHeight="900" math="0" shadow="0">
<root>
<mxCell id="0" />
<mxCell id="1" parent="0" />
<mxCell id="KG5lhhUBjoQ79gfvQvIC-19" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-6" target="KG5lhhUBjoQ79gfvQvIC-18" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-6" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;base_state&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font color=&quot;#cc00cc&quot;&gt;LorentzVector&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="190" y="600" width="120" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-20" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-7" target="KG5lhhUBjoQ79gfvQvIC-18" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-7" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;base_state&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;BiSpinor&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="310" y="600" width="120" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-28" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-8" target="KG5lhhUBjoQ79gfvQvIC-26" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-8" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;base_state&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;AdjointBiSpinor&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="550" y="600" width="120" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-29" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-9" target="KG5lhhUBjoQ79gfvQvIC-26" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-9" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;base_state&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;LorentzVector&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="430" y="600" width="120" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-21" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-14" target="KG5lhhUBjoQ79gfvQvIC-6" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-14" value="U(γ&lt;sub style=&quot;border-color: var(--border-color);&quot;&gt;1&lt;/sub&gt;)&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font color=&quot;#0000ff&quot;&gt;&lt;b&gt;IncomingPhoton&lt;/b&gt;&lt;/font&gt;&lt;br&gt;Outer Edge" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="190" y="700" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-22" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-15" target="KG5lhhUBjoQ79gfvQvIC-7" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-15" value="U(p&lt;sub style=&quot;border-color: var(--border-color);&quot;&gt;1&lt;/sub&gt;)&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;b&gt;&lt;font color=&quot;#0000ff&quot;&gt;IncomingFermion&lt;br&gt;&lt;/font&gt;&lt;/b&gt;Outer Edge" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="310" y="700" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-23" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-16" target="KG5lhhUBjoQ79gfvQvIC-9" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-16" value="U(γ&lt;sub style=&quot;border-color: var(--border-color);&quot;&gt;2&lt;/sub&gt;)&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;b&gt;&lt;font color=&quot;#0000ff&quot;&gt;OutgoingPhoton&lt;br&gt;&lt;/font&gt;&lt;/b&gt;Outer Edge" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="430" y="700" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-24" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-17" target="KG5lhhUBjoQ79gfvQvIC-8" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-17" value="U(p&lt;sub style=&quot;border-color: var(--border-color);&quot;&gt;2&lt;/sub&gt;)&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;b&gt;&lt;font color=&quot;#0000ff&quot;&gt;OutgoingFermion&lt;br&gt;&lt;/font&gt;&lt;/b&gt;Outer Edge" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="550" y="700" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-30" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-18" target="KG5lhhUBjoQ79gfvQvIC-25" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-18" value="V(γ&lt;sub&gt;1&lt;/sub&gt;, p&lt;sub&gt;1&lt;/sub&gt;)&lt;br&gt;Result Particle:&lt;br&gt;q: &lt;font color=&quot;#0000ff&quot;&gt;&lt;b&gt;OutgoingFermion&lt;/b&gt;&lt;/font&gt;" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="240" y="480" width="140" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-36" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-25" target="KG5lhhUBjoQ79gfvQvIC-35" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-25" value="&lt;b&gt;&lt;font color=&quot;#336600&quot;&gt;vertex&lt;/font&gt;&lt;/b&gt; -&amp;gt;&lt;br&gt;LorentzVector * DiracMatrix * &lt;br&gt;BiSpinor&lt;br&gt;=&amp;nbsp;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font color=&quot;#cc00cc&quot; style=&quot;border-color: var(--border-color);&quot;&gt;BiSpinor&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="250" y="360" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-32" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-26" target="KG5lhhUBjoQ79gfvQvIC-27" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-26" value="V(γ&lt;sub&gt;2&lt;/sub&gt;, p&lt;sub&gt;2&lt;/sub&gt;)&lt;br&gt;Result Particle:&lt;br&gt;q&#39;: &lt;b&gt;&lt;font color=&quot;#0000ff&quot;&gt;IncomingFermion&lt;/font&gt;&lt;/b&gt;" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="480" y="480" width="140" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-37" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-27" target="KG5lhhUBjoQ79gfvQvIC-35" edge="1">
<mxGeometry relative="1" as="geometry">
<Array as="points">
<mxPoint x="550" y="340" />
<mxPoint x="420" y="340" />
</Array>
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-27" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;vertex&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;AdjointBiSpinor * LorentzVector * &lt;br&gt;DiracMatrix &lt;br&gt;=&amp;nbsp;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font color=&quot;#cc00cc&quot; style=&quot;border-color: var(--border-color);&quot;&gt;AdjointBiSpinor&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="490" y="360" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-39" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-35" target="KG5lhhUBjoQ79gfvQvIC-38" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-35" value="S2(q, q&#39;)&lt;br&gt;q == -q&#39;&lt;br&gt;&lt;b&gt;&lt;font color=&quot;#0000ff&quot;&gt;No Result Particle&lt;/font&gt;&lt;/b&gt;" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="360" y="240" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-71" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-38" target="KG5lhhUBjoQ79gfvQvIC-70" edge="1">
<mxGeometry relative="1" as="geometry">
<Array as="points">
<mxPoint x="670" y="170" />
</Array>
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-38" value="&lt;b style=&quot;&quot;&gt;&lt;font color=&quot;#336600&quot;&gt;inner_edge&lt;/font&gt;&lt;/b&gt; -&amp;gt;&lt;br&gt;AdjointBiSpinor * propagator(q) * BiSpinor =&amp;nbsp;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;ComplexF64&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="350" y="140" width="140" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-40" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-41" target="KG5lhhUBjoQ79gfvQvIC-57" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-41" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;base_state&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;LorentzVector&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="670" y="600" width="120" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-68" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-43" target="KG5lhhUBjoQ79gfvQvIC-61" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-43" value="&lt;b style=&quot;&quot;&gt;&lt;font color=&quot;#336600&quot;&gt;base_state&lt;/font&gt;&lt;/b&gt; -&amp;gt;&lt;br&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;BiSpinor&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="1030" y="600" width="120" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-67" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-45" target="KG5lhhUBjoQ79gfvQvIC-57" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-45" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;base_state&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;AdjointBiSpinor&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="790" y="600" width="120" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-46" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-47" target="KG5lhhUBjoQ79gfvQvIC-61" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-47" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;base_state&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;LorentzVector&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="910" y="600" width="120" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-48" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-49" target="KG5lhhUBjoQ79gfvQvIC-41" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-49" value="U(γ&lt;sub style=&quot;border-color: var(--border-color);&quot;&gt;1&lt;/sub&gt;)&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#0000ff&quot;&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;IncomingPhoton&lt;/b&gt;&lt;/font&gt;&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;Outer Edge" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="670" y="700" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-69" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-51" target="KG5lhhUBjoQ79gfvQvIC-43" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-51" value="U(p&lt;sub style=&quot;border-color: var(--border-color);&quot;&gt;1&lt;/sub&gt;)&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#0000ff&quot;&gt;IncomingFermion&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;/font&gt;&lt;/b&gt;Outer Edge" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="1030" y="700" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-52" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-53" target="KG5lhhUBjoQ79gfvQvIC-47" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-53" value="U(γ&lt;sub style=&quot;border-color: var(--border-color);&quot;&gt;2&lt;/sub&gt;)&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#0000ff&quot;&gt;OutgoingPhoton&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;/font&gt;&lt;/b&gt;Outer Edge" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="910" y="700" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-54" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-55" target="KG5lhhUBjoQ79gfvQvIC-45" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-55" value="U(p&lt;sub style=&quot;border-color: var(--border-color);&quot;&gt;2&lt;/sub&gt;)&lt;br style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font color=&quot;#0000ff&quot;&gt;&lt;b&gt;OutgoingFermion&lt;br&gt;&lt;/b&gt;&lt;/font&gt;Outer Edge" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="790" y="700" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-56" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-57" target="KG5lhhUBjoQ79gfvQvIC-59" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-57" value="V(γ&lt;sub&gt;1&lt;/sub&gt;, p&lt;span style=&quot;font-size: 10px;&quot;&gt;&lt;sub&gt;2&lt;/sub&gt;&lt;/span&gt;)&lt;br&gt;Result Particle:&lt;br&gt;q: &lt;b&gt;&lt;font color=&quot;#0000ff&quot;&gt;IncomingFermion&lt;/font&gt;&lt;/b&gt;" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="720" y="480" width="140" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-58" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-59" target="KG5lhhUBjoQ79gfvQvIC-65" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-59" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;vertex&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;AdjointBiSpinor * LorentzVector * &lt;br&gt;DiracMatrix&amp;nbsp;&lt;br&gt;=&amp;nbsp;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;AdjointBiSpinor&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="730" y="360" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-60" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-61" target="KG5lhhUBjoQ79gfvQvIC-63" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-61" value="V(γ&lt;sub&gt;2&lt;/sub&gt;, p&lt;span style=&quot;font-size: 10px;&quot;&gt;&lt;sub&gt;1&lt;/sub&gt;&lt;/span&gt;)&lt;br&gt;Result Particle:&lt;br&gt;q&#39;: &lt;b&gt;&lt;font color=&quot;#0000ff&quot;&gt;OutgoingFermion&lt;/font&gt;&lt;/b&gt;" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="960" y="480" width="140" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-62" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-63" target="KG5lhhUBjoQ79gfvQvIC-65" edge="1">
<mxGeometry relative="1" as="geometry">
<Array as="points">
<mxPoint x="1030" y="340" />
<mxPoint x="900" y="340" />
</Array>
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-63" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;vertex&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;LorentzVector * &lt;br&gt;DiracMatrix * &lt;br&gt;BiSpinor &lt;br&gt;=&amp;nbsp;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#cc00cc&quot;&gt;BiSpinor&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="970" y="360" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-64" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-65" target="KG5lhhUBjoQ79gfvQvIC-66" edge="1">
<mxGeometry relative="1" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-65" value="S2(q, q&#39;)&lt;br&gt;q == -q&#39;&lt;br&gt;&lt;b&gt;&lt;font color=&quot;#0000ff&quot;&gt;No Result Particle&lt;/font&gt;&lt;/b&gt;" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#9AC7BF;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="840" y="240" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-72" style="edgeStyle=orthogonalEdgeStyle;rounded=0;orthogonalLoop=1;jettySize=auto;html=1;strokeWidth=2;" parent="1" source="KG5lhhUBjoQ79gfvQvIC-66" target="KG5lhhUBjoQ79gfvQvIC-70" edge="1">
<mxGeometry relative="1" as="geometry">
<Array as="points">
<mxPoint x="670" y="170" />
</Array>
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-66" value="&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font style=&quot;border-color: var(--border-color);&quot; color=&quot;#336600&quot;&gt;inner_edge&lt;/font&gt;&lt;/b&gt;&amp;nbsp;-&amp;gt;&lt;br&gt;AdjointBiSpinor * propagator(q) * BiSpinor =&amp;nbsp;&lt;b style=&quot;border-color: var(--border-color);&quot;&gt;&lt;font color=&quot;#cc00cc&quot;&gt;ComplexF64&lt;/font&gt;&lt;/b&gt;" style="rounded=1;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#f5f5f5;gradientColor=#b3b3b3;strokeColor=#666666;" parent="1" vertex="1">
<mxGeometry x="830" y="140" width="140" height="60" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-70" value="&lt;font style=&quot;font-size: 32px;&quot;&gt;Σ&lt;/font&gt;" style="ellipse;whiteSpace=wrap;html=1;strokeWidth=2;fillColor=#ffcd28;strokeColor=#d79b00;gradientColor=#ffa500;" parent="1" vertex="1">
<mxGeometry x="610" y="20" width="120" height="80" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-73" value="&lt;b&gt;&lt;font style=&quot;font-size: 22px;&quot;&gt;ValueAcc&lt;/font&gt;&lt;/b&gt;" style="text;html=1;strokeColor=none;fillColor=none;align=center;verticalAlign=middle;whiteSpace=wrap;rounded=0;" parent="1" vertex="1">
<mxGeometry x="10" y="155" width="120" height="30" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-74" value="&lt;b&gt;&lt;font style=&quot;font-size: 22px;&quot;&gt;ValueAcc&lt;/font&gt;&lt;/b&gt;" style="text;html=1;strokeColor=none;fillColor=none;align=center;verticalAlign=middle;whiteSpace=wrap;rounded=0;" parent="1" vertex="1">
<mxGeometry x="10" y="385" width="120" height="30" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-75" value="&lt;b&gt;&lt;font style=&quot;font-size: 22px;&quot;&gt;ValueAcc&lt;/font&gt;&lt;/b&gt;" style="text;html=1;strokeColor=none;fillColor=none;align=center;verticalAlign=middle;whiteSpace=wrap;rounded=0;" parent="1" vertex="1">
<mxGeometry x="10" y="615" width="120" height="30" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-76" value="&lt;b&gt;&lt;font style=&quot;font-size: 22px;&quot;&gt;Particle Propagation&lt;/font&gt;&lt;/b&gt;" style="text;html=1;strokeColor=none;fillColor=none;align=center;verticalAlign=middle;whiteSpace=wrap;rounded=0;" parent="1" vertex="1">
<mxGeometry x="10" y="725" width="120" height="30" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-77" value="&lt;b&gt;&lt;font style=&quot;font-size: 22px;&quot;&gt;Particle Propagation&lt;/font&gt;&lt;/b&gt;" style="text;html=1;strokeColor=none;fillColor=none;align=center;verticalAlign=middle;whiteSpace=wrap;rounded=0;" parent="1" vertex="1">
<mxGeometry x="10" y="505" width="120" height="30" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-78" value="&lt;b&gt;&lt;font style=&quot;font-size: 22px;&quot;&gt;Particle Propagation&lt;/font&gt;&lt;/b&gt;" style="text;html=1;strokeColor=none;fillColor=none;align=center;verticalAlign=middle;whiteSpace=wrap;rounded=0;" parent="1" vertex="1">
<mxGeometry x="10" y="265" width="120" height="30" as="geometry" />
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-79" value="" style="endArrow=none;dashed=1;html=1;dashPattern=1 3;strokeWidth=2;rounded=0;" parent="1" edge="1">
<mxGeometry width="50" height="50" relative="1" as="geometry">
<mxPoint y="220" as="sourcePoint" />
<mxPoint x="1160" y="220" as="targetPoint" />
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-80" value="" style="endArrow=none;dashed=1;html=1;dashPattern=1 3;strokeWidth=2;rounded=0;" parent="1" edge="1">
<mxGeometry width="50" height="50" relative="1" as="geometry">
<mxPoint y="340" as="sourcePoint" />
<mxPoint x="1160" y="340" as="targetPoint" />
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-81" value="" style="endArrow=none;dashed=1;html=1;dashPattern=1 3;strokeWidth=2;rounded=0;" parent="1" edge="1">
<mxGeometry width="50" height="50" relative="1" as="geometry">
<mxPoint y="460" as="sourcePoint" />
<mxPoint x="1160" y="460" as="targetPoint" />
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-82" value="" style="endArrow=none;dashed=1;html=1;dashPattern=1 3;strokeWidth=2;rounded=0;" parent="1" edge="1">
<mxGeometry width="50" height="50" relative="1" as="geometry">
<mxPoint y="120" as="sourcePoint" />
<mxPoint x="1160" y="120" as="targetPoint" />
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-83" value="" style="endArrow=none;dashed=1;html=1;dashPattern=1 3;strokeWidth=2;rounded=0;" parent="1" edge="1">
<mxGeometry width="50" height="50" relative="1" as="geometry">
<mxPoint y="580" as="sourcePoint" />
<mxPoint x="1160" y="580" as="targetPoint" />
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-84" value="" style="endArrow=none;dashed=1;html=1;dashPattern=1 3;strokeWidth=2;rounded=0;" parent="1" edge="1">
<mxGeometry width="50" height="50" relative="1" as="geometry">
<mxPoint y="680" as="sourcePoint" />
<mxPoint x="1160" y="680" as="targetPoint" />
</mxGeometry>
</mxCell>
<mxCell id="KG5lhhUBjoQ79gfvQvIC-85" value="" style="endArrow=none;dashed=1;html=1;dashPattern=1 3;strokeWidth=2;rounded=0;" parent="1" edge="1">
<mxGeometry width="50" height="50" relative="1" as="geometry">
<mxPoint y="800" as="sourcePoint" />
<mxPoint x="1160" y="800" as="targetPoint" />
</mxGeometry>
</mxCell>
</root>
</mxGraphModel>
</diagram>
</mxfile>

View File

@ -1,8 +1,23 @@
# Code Generation
## Main
## Types
```@autodocs
Modules = [MetagraphOptimization]
Pages = ["code_gen/main.jl"]
Pages = ["code_gen/type.jl"]
Order = [:type, :constant, :function]
```
## Function Generation
Implementations for generation of a callable function. A function generated this way cannot immediately be called. One Julia World Age has to pass before this is possible, which happens when the global Julia scope advances. If the DAG and therefore the generated function becomes too large, use the tape machine instead, since compiling large functions becomes infeasible.
```@autodocs
Modules = [MetagraphOptimization]
Pages = ["code_gen/function.jl"]
Order = [:function]
```
## Tape Machine
```@autodocs
Modules = [MetagraphOptimization]
Pages = ["code_gen/tabe_machine.jl"]
Order = [:function]
```

View File

@ -1,4 +1,4 @@
# Models
# Estimation
## Interface

View File

@ -69,4 +69,58 @@ Order = [:function]
## QED-Model
*To be added*
### Feynman Diagrams
```@autodocs
Modules = [MetagraphOptimization]
Pages = ["models/qed/diagrams.jl"]
Order = [:type, :function, :constant]
```
### Types
```@autodocs
Modules = [MetagraphOptimization]
Pages = ["models/qed/types.jl"]
Order = [:type, :constant]
```
### Particle
```@autodocs
Modules = [MetagraphOptimization]
Pages = ["models/qed/particle.jl"]
Order = [:type, :constant, :function]
```
### Parse
```@autodocs
Modules = [MetagraphOptimization]
Pages = ["models/qed/parse.jl"]
Order = [:function]
```
### Properties
```@autodocs
Modules = [MetagraphOptimization]
Pages = ["models/qed/properties.jl"]
Order = [:function]
```
### Create
```@autodocs
Modules = [MetagraphOptimization]
Pages = ["models/qed/create.jl"]
Order = [:function]
```
### Compute
```@autodocs
Modules = [MetagraphOptimization]
Pages = ["models/qed/compute.jl"]
Order = [:function]
```
### Print
```@autodocs
Modules = [MetagraphOptimization]
Pages = ["models/qed/print.jl"]
Order = [:function]
```

View File

@ -0,0 +1,41 @@
# Optimization
## Interface
The interface that has to be implemented for an optimization algorithm.
```@autodocs
Modules = [MetagraphOptimization]
Pages = ["optimization/interafce.jl"]
Order = [:type, :constant, :function]
```
## Random Walk Optimizer
Implementation of a random walk algorithm.
```@autodocs
Modules = [MetagraphOptimization]
Pages = ["estimator/random_walk.jl"]
Order = [:type, :function]
```
## Reduction Optimizer
Implementation of a an optimizer that reduces as far as possible.
```@autodocs
Modules = [MetagraphOptimization]
Pages = ["estimator/reduce.jl"]
Order = [:type, :function]
```
## Greedy Optimizer
Implementation of a greedy optimization algorithm.
```@autodocs
Modules = [MetagraphOptimization]
Pages = ["estimator/greedy.jl"]
Order = [:type, :function]
```

View File

@ -7,6 +7,13 @@ Pages = ["scheduler/interface.jl"]
Order = [:type, :function]
```
## Types
```@autodocs
Modules = [MetagraphOptimization]
Pages = ["scheduler/type.jl"]
Order = [:type, :function]
```
## Greedy
```@autodocs
Modules = [MetagraphOptimization]

View File

@ -34,10 +34,3 @@ Modules = [MetagraphOptimization]
Pages = ["task/properties.jl"]
Order = [:function]
```
## Print
```@autodocs
Modules = [MetagraphOptimization]
Pages = ["task/print.jl"]
Order = [:function]
```

File diff suppressed because one or more lines are too long

View File

@ -1,3 +1,10 @@
[deps]
BenchmarkTools = "6e4b80f9-dd63-53aa-95a3-0cdb28fa8baf"
CSV = "336ed68f-0bac-5ca0-87d4-7b16caf5d00b"
CUDA = "052768ef-5323-5732-b1bb-66c8b64840ba"
DataFrames = "a93c6f00-e57d-5684-b7b6-d8193f3e46c0"
MetagraphOptimization = "3e869610-d48d-4942-ba70-c1b702a33ca4"
Plots = "91a5bcdd-55d7-5caf-9e0b-520d859cae80"
QEDbase = "10e22c08-3ccb-4172-bfcf-7d7aa3d04d93"
QEDprocesses = "46de9c38-1bb3-4547-a1ec-da24d767fdad"
StatsPlots = "f3b207a7-027a-5e70-b257-86293d7955fd"

View File

@ -17,9 +17,8 @@ println("Parsing DAG")
println("Generating input data")
@time input_data = [gen_process_input(process) for _ in 1:1000]
include("profiling_utilities.jl")
println("Reducing graph")
@time reduce_all!(graph)
@time optimize_to_fixpoint!(ReductionOptimizer(), graph)
println("Generating compute function")
@time compute_func = get_compute_function(graph, process, machine)

View File

@ -17,9 +17,8 @@ println("Parsing DAG")
println("Generating input data")
@time input_data = [gen_process_input(process) for _ in 1:1000]
include("profiling_utilities.jl")
println("Reducing graph")
@time reduce_all!(graph)
@time optimize_to_fixpoint!(ReductionOptimizer(), graph)
println("Generating compute function")
@time compute_func = get_compute_function(graph, process, machine)

249
examples/full_node_bench.jl Normal file
View File

@ -0,0 +1,249 @@
using MetagraphOptimization
using CUDA
using UUIDs
using DataFrames
using CSV
using Random
using BenchmarkTools
using Dates
using Base.Threads
function log(x...)
println(now(), " ", join(x, " ")...)
flush(stdout)
return nothing
end
results_filename = "full_node_bench.csv"
df = DataFrame(
process_name = String[],
cpu_threads = Int[],
gpu_devices = Int[],
n_inputs = Int[],
chunk_size = Int[],
time = Float64[],
std = Float64[],
rate = Float64[],
cpu_chunks = Float64[],
gpu_chunks = Float64[],
memory_est = Float64[],
)
# if they exist, read existing results and append new ones
if isfile(results_filename)
df = CSV.read(results_filename, DataFrame)
end
nInputs = 2^26
lck = ReentrantLock()
progress = 1
cpu_chunks = 0
gpu_chunks = 0
chunkSizes = [1024, 4096, 16384, 65536, 262144, 1048576] # 2^10 to 2^20
function cpu_worker(compute_func, inputs, chunk_size)
global progress
global cpu_chunks
global lck
quit = false
work_start = 0
work_end = 0
while true
lock(lck) do
if progress >= nInputs
quit = true
else
work_start = progress
progress = progress + chunk_size
work_end = min(progress - 1, nInputs)
cpu_chunks = cpu_chunks + 1
#log("CPU Worker $(Threads.threadid()) computing $(cpu_chunks)th cpu chunk ($work_start, $work_end)")
end
end
if quit
break
end
for i in work_start:work_end
compute_func(inputs[i])
end
end
#log("CPU Worker on $(Threads.threadid()) finished!")
return nothing
end
# called with a specific device selected
function gpu_worker(kernel!, inputs, chunk_size)
global progress
global gpu_chunks
global lck
cuOutputs = CuVector{ComplexF64}()
resize!(cuOutputs, chunk_size)
quit = false
work_start = 0
work_end = 0
while true
lock(lck) do
if progress >= nInputs
quit = true
else
work_start = progress
progress = progress + chunk_size
work_end = min(progress - 1, nInputs)
gpu_chunks = gpu_chunks + 1
#log("GPU Worker $(CUDA.device()) computing $(gpu_chunks)th gpu chunk ($work_start, $work_end)")
end
end
if quit
break
end
cuInputs = CuVector(inputs[work_start:work_end])
ts = 32
bs = Int(chunk_size / 32)
@cuda threads = ts blocks = bs always_inline = true kernel!(cuInputs, cuOutputs, chunk_size)
CUDA.device_synchronize()
end
#log("GPU Worker on Device $(CUDA.device()) finished!")
return nothing
end
cpu_gpu_ratio = Vector{Tuple{Int, Int}}()
function full_compute(compute_func, kernel!, inputs, chunk_size)
global progress
progress = 1
global cpu_chunks
cpu_chunks = 0
global gpu_chunks
gpu_chunks = 0
tasks = Vector()
for dev in CUDA.devices()
t = Threads.@spawn device!(dev) do
gpu_worker(kernel!, inputs, chunk_size)
return nothing
end
push!(tasks, t)
end
for i in 1:(Threads.nthreads() - length(CUDA.devices()))
t = Threads.@spawn cpu_worker(compute_func, inputs, chunk_size)
push!(tasks, t)
end
for t in tasks
wait(t)
end
push!(cpu_gpu_ratio, (cpu_chunks, gpu_chunks))
return nothing
end
function bench(compute_function, kernel!, inputs, chunk_size)
global cpu_gpu_ratio
empty!(cpu_gpu_ratio)
bench = @benchmark begin
full_compute($compute_function, $kernel!, $inputs, $chunk_size)
end gcsample = true seconds = 60
time = median(bench.times) / 1e9
s = std(bench.times) / 1e9
rate = length(inputs) / time
med_cpu_chunks = median(getindex.(cpu_gpu_ratio, 1))
med_gpu_chunks = median(getindex.(cpu_gpu_ratio, 2))
mem_estimate = bench.memory
log("CPU/GPU ratios: $(cpu_gpu_ratio)")
return (time, rate, s, med_cpu_chunks, med_gpu_chunks, mem_estimate)
end
function full_node_bench(process::MetagraphOptimization.AbstractProcessDescription, func, kernel!, chunk_size, inputs)
process_name = string(process)
log("\n--- Benchmarking $(process_name) on $(nInputs) with chunk size $(chunk_size) ---")
log("Available Cuda Devices:")
display.(CUDA.devices())
log("Benchmarking full node...")
(time, rate, s, med_cpu_chunks, med_gpu_chunks, mem_estimate) = bench(func, kernel!, inputs, chunk_size)
log(
"Benchmarking complete with median time $(time), $(med_cpu_chunks) cpu chunks, and $(med_gpu_chunks) gpu chunks.",
)
push!(
df,
Dict(
:process_name => process_name,
:cpu_threads => Threads.nthreads() - length(CUDA.devices()),
:gpu_devices => length(CUDA.devices()),
:n_inputs => nInputs,
:chunk_size => chunk_size,
:time => time,
:std => s,
:rate => rate,
:cpu_chunks => med_cpu_chunks,
:gpu_chunks => med_gpu_chunks,
:memory_est => mem_estimate,
),
)
return nothing
end
# use "mock" machine that only uses cpu for compilation
machine = Machine(
[
MetagraphOptimization.NumaNode(
0,
1,
MetagraphOptimization.default_strategy(MetagraphOptimization.NumaNode),
-1.0,
UUIDs.uuid1(),
),
],
[-1.0;;],
)
optimizer = ReductionOptimizer()
processes = ["ke->ke", "ke->kke", "ke->kkke", "ke->kkkke", "ke->kkkkke"]
for proc in processes
process = parse_process(proc, QEDModel())
graph = gen_graph(process)
optimize_to_fixpoint!(optimizer, graph)
compute_func = get_compute_function(graph, process, machine)
kernel! = get_cuda_kernel(graph, process, machine)
log("Generating $nInputs inputs with $(Threads.nthreads()) threads...")
inputs = Vector{typeof(gen_process_input(process))}()
resize!(inputs, nInputs)
procs = Vector{typeof(process)}()
for i in 1:Threads.nthreads()
push!(procs, copy(process))
end
@inbounds Threads.@threads for i in eachindex(inputs)
inputs[i] = gen_process_input(procs[Threads.nthreads()])
end
for chunk_size in chunkSizes
full_node_bench(process, compute_func, kernel!, chunk_size, inputs)
CSV.write(results_filename, df)
end
end;

View File

@ -34,9 +34,10 @@ function import_bench()
bench_txt("AB->ABBB.txt")
bench_txt("AB->ABBBBB.txt")
bench_txt("AB->ABBBBBBB.txt")
#bench_txt("AB->ABBBBBBBBB.txt")
bench_txt("AB->ABBBBBBBBB.txt")
bench_txt("ABAB->ABAB.txt")
return bench_txt("ABAB->ABC.txt")
bench_txt("ABAB->ABC.txt")
return nothing
end
import_bench()

View File

@ -1,59 +0,0 @@
function random_walk!(g::DAG, n::Int64)
# the purpose here is to do "random" operations on the graph to simulate an optimizer
reset_graph!(g)
properties = get_properties(g)
for i in 1:n
# choose push or pop
if rand(Bool)
# push
opt = get_operations(g)
# choose one of fuse/split/reduce
option = rand(1:3)
if option == 1 && !isempty(opt.nodeFusions)
push_operation!(g, rand(collect(opt.nodeFusions)))
elseif option == 2 && !isempty(opt.nodeReductions)
push_operation!(g, rand(collect(opt.nodeReductions)))
elseif option == 3 && !isempty(opt.nodeSplits)
push_operation!(g, rand(collect(opt.nodeSplits)))
else
i = i - 1
end
else
# pop
if (can_pop(g))
pop_operation!(g)
else
i = i - 1
end
end
end
return nothing
end
function reduce_all!(g::DAG)
reset_graph!(g)
opt = get_operations(g)
while (!isempty(opt.nodeReductions))
push_operation!(g, pop!(opt.nodeReductions))
if (isempty(opt.nodeReductions))
opt = get_operations(g)
end
end
return nothing
end
function reduce_one!(g::DAG)
opt = get_operations(g)
if !isempty(opt.nodeReductions)
push_operation!(g, pop!(opt.nodeReductions))
end
opt = get_operations(g)
return nothing
end

272
examples/qed_bench.jl Normal file
View File

@ -0,0 +1,272 @@
using MetagraphOptimization
using LIKWID
using CUDA
using UUIDs
using DataFrames
using CSV
using Random
using BenchmarkTools
using Dates
DISABLE_GPU = false
function log(x...)
println(now(), " ", join(x, " ")...)
return flush(stdout)
end
results_filename = "bench_results_$(Threads.nthreads()).csv"
df = DataFrame(
process_name = String[],
graph_gen_time = Float64[],
optimization_time = Float64[],
function_generation_time = Float64[],
graph_nodes = Int[],
graph_edges = Int[],
graph_mem = Float64[],
cpu_threads = Int[],
n_inputs = Int[],
nflops_likwid = Int[],
cpu_time = Float64[],
cpu_std = Float64[],
cpu_rate = Float64[],
cpu_gflops = Float64[],
gpu_name = String[],
gpu_time = Float64[],
gpu_std = Float64[],
gpu_rate = Float64[],
gpu_gflops = Float64[],
)
# if they exist, read existing results and append new ones
if isfile(results_filename)
df = CSV.read(results_filename, DataFrame)
end
nInputs = 2^20
function cpu_bench(compute_function, inputs)
bench = @benchmark begin
@inbounds Threads.@threads for i in eachindex($inputs)
@invokelatest $compute_function($inputs[i])
end
end gcsample = true samples = 20 evals = 1
time = median(bench.times) / 1e9
s = std(bench.times) / 1e9
rate = length(inputs) / time
return (time, rate, s)
end
function gpu_bench(kernel!, inputs)
n = length(inputs)
outputs = CuVector{ComplexF64}()
resize!(outputs, n)
ts = 32
bs = Int(n / ts)
bench = @benchmark begin
@cuda threads = $ts blocks = $bs always_inline = true $kernel!($inputs, $outputs, $n)
CUDA.device_synchronize()
end gcsample = true samples = 20 evals = 1
time = median(bench.times) / 1e9
s = std(bench.times) / 1e9
rate = length(inputs) / time
return (time, rate, s)
end
function bench_process(
process::MetagraphOptimization.AbstractProcessDescription,
process_name::String,
graph::DAG,
func,
kernel!,
gen_time::Float64,
opt_time::Float64,
func_time::Float64;
use_likwid = false,
use_gpu = true,
)
log("\n--- Benchmarking $(process_name) ---")
if DISABLE_GPU
use_gpu = false
end
graph_props = GraphProperties(graph)
NFLOPs = graph_props.computeEffort
nflops_likwid = 0
if use_likwid
input = gen_process_input(process)
func(input) # compile first
# get rid of annoying output to console
oldstd = stdout
redirect_stdout(devnull)
_, events = @perfmon "FLOPS_DP" func(input)
redirect_stdout(oldstd) # recover original stdout
NFLOPs = first(events["FLOPS_DP"])["RETIRED_SSE_AVX_FLOPS_ALL"]
nflops_likwid = NFLOPs
end
log("Generating $nInputs inputs with $(Threads.nthreads()) threads...")
inputs = Vector{typeof(gen_process_input(process))}()
resize!(inputs, nInputs)
processes = Vector{typeof(process)}()
for i in 1:Threads.nthreads()
push!(processes, copy(process))
end
@inbounds Threads.@threads for i in eachindex(inputs)
inputs[i] = gen_process_input(processes[Threads.nthreads()])
end
log("Benchmarking CPU with $(Threads.nthreads()) threads...")
(time_cpu, rate_cpu, std_cpu) = cpu_bench(func, inputs)
flops_cpu = (rate_cpu * NFLOPs) / 10^9
time_gpu = 0.0
std_gpu = 0.0
rate_gpu = 0.0
flops_gpu = 0.0
gpu_name = "none"
if use_gpu
log("Benchmarking GPU...")
gpu_name = "$(name(first(CUDA.devices())))"
cuInputs = CuArray(inputs)
(time_gpu, rate_gpu, std_gpu) = gpu_bench(kernel!, cuInputs)
flops_gpu = (rate_gpu * NFLOPs) / 10^9
else
log("Skipping GPU...")
end
log("\nBenchmark Summary for $(process):")
if use_likwid
log("Measured FLOPS by LIKWID: $NFLOPs")
else
log("Total graph compute effort: $NFLOPs")
end
log("Total input size: $(bytes_to_human_readable(Base.summarysize(inputs)))")
log("CPU, $(Threads.nthreads()) threads")
log(" Time: $time_cpu")
log(" Rate: $rate_cpu")
log(" GFLOPS: $flops_cpu")
if use_gpu
log("GPU, $gpu_name")
log(" Time: $time_gpu")
log(" Rate: $rate_gpu")
log(" GFLOPS: $flops_gpu")
end
if (process_name != "warmup")
push!(
df,
Dict(
:process_name => process_name,
:graph_gen_time => gen_time,
:optimization_time => opt_time,
:function_generation_time => func_time,
:graph_nodes => graph_props.noNodes,
:graph_edges => graph_props.noEdges,
:graph_mem => MetagraphOptimization.mem(graph),
:cpu_threads => Threads.nthreads(),
:n_inputs => nInputs,
:nflops_likwid => nflops_likwid,
:cpu_time => time_cpu,
:cpu_std => std_cpu,
:cpu_rate => rate_cpu,
:cpu_gflops => flops_cpu,
:gpu_name => gpu_name,
:gpu_time => time_gpu,
:gpu_std => std_gpu,
:gpu_rate => rate_gpu,
:gpu_gflops => flops_gpu,
),
)
end
return nothing
end
# use "mock" machine that only uses cpu
machine = Machine(
[
MetagraphOptimization.NumaNode(
0,
1,
MetagraphOptimization.default_strategy(MetagraphOptimization.NumaNode),
-1.0,
UUIDs.uuid1(),
),
],
[-1.0;;],
)
# sadly cannot put these in functions because the world age must increase after the function is created which happens only in the global scope
## -- WARMUP TO COMPILE FUNCTIONS first
#=
optimizer = RandomWalkOptimizer(MersenneTwister(0))
# 2-photon compton
process = parse_process("ke->kke", QEDModel())
gen_time = @elapsed graph = gen_graph(process)
opt_time = @elapsed optimize!(optimizer, graph, 200)
func_gen_time = @elapsed compute_func = get_compute_function(graph, process, machine)
kernel! = get_cuda_kernel(graph, process, machine)
bench_process(process, "warmup", graph, compute_func, kernel!, gen_time, opt_time, func_gen_time)
optimizer = ReductionOptimizer()
# AB->AB^3
process = parse_process("AB->ABBB", ABCModel())
gen_time = @elapsed graph = parse_dag("input/AB->ABBB.txt", ABCModel())
opt_time = @elapsed optimize_to_fixpoint!(optimizer, graph)
func_gen_time = @elapsed compute_func = get_compute_function(graph, process, machine)
kernel! = get_cuda_kernel(graph, process, machine)
bench_process(process, "warmup", graph, compute_func, kernel!, gen_time, opt_time, func_gen_time)
=#
## -- WARMUP END
optimizer = ReductionOptimizer()
processes = ["ke->ke", "ke->kke", "ke->kkke", "ke->kkkke", "ke->kkkkke"]
for process_str in processes
# compton
process = parse_process(process_str, QEDModel())
gen_time = @elapsed graph = gen_graph(process)
func_gen_time = @elapsed compute_func = get_compute_function(graph, process, machine)
kernel! = get_cuda_kernel(graph, process, machine)
bench_process(process, "$process not optimized", graph, compute_func, kernel!, gen_time, 0.0, func_gen_time)
opt_time = @elapsed optimize_to_fixpoint!(optimizer, graph)
func_gen_time = @elapsed compute_func = get_compute_function(graph, process, machine)
kernel! = get_cuda_kernel(graph, process, machine)
bench_process(process, "$process reduced", graph, compute_func, kernel!, gen_time, opt_time, func_gen_time)
CSV.write(results_filename, df)
end
processes = ["AB->AB", "AB->ABBB", "AB->ABBBBB", "AB->ABBBBBBB"]
for process_str in processes
# AB->AB
process = parse_process(process_str, ABCModel())
gen_time = @elapsed graph = parse_dag("input/$(process_str).txt", ABCModel())
func_gen_time = @elapsed compute_func = get_compute_function(graph, process, machine)
kernel! = get_cuda_kernel(graph, process, machine)
bench_process(process, "$process not optimized", graph, compute_func, kernel!, gen_time, 0.0, func_gen_time)
opt_time = @elapsed optimize_to_fixpoint!(optimizer, graph)
func_gen_time = @elapsed compute_func = get_compute_function(graph, process, machine)
kernel! = get_cuda_kernel(graph, process, machine)
bench_process(process, "$process reduced", graph, compute_func, kernel!, gen_time, opt_time, func_gen_time)
CSV.write(results_filename, df)
end

View File

@ -0,0 +1,163 @@
using MetagraphOptimization
using CUDA
using UUIDs
using BenchmarkTools
using DataFrames
using CSV
results_filename = "bench_results_reduction_steps.csv"
df = DataFrame(
threads = Int[],
process = String[],
operations = Int[],
cumulative_optimization_time = Float64[],
graph_nodes = Int[],
graph_edges = Int[],
graph_ce = Float64[],
graph_dt = Float64[],
graph_ci = Float64[],
gen_func_t = Float64[],
cpu_compile_t = Float64[],
cpu_st_t = Float64[],
cpu_mt_t = Float64[],
gpu_compile_t = Float64[],
gpu_t = Float64[],
)
# if they exist, read existing results and append new ones
if isfile(results_filename)
df = CSV.read(results_filename, DataFrame)
end
function bench(func, inputs)
compile_time = @elapsed func(inputs[1])
single_thread = @benchmark $func.($inputs)
multi_threaded = @benchmark Threads.@threads for i in eachindex($inputs)
$func($inputs[i])
end
return (
cpu_compile_time = compile_time,
gpu_compile_time = 0.0,
cpu_single_thread_time = mean(single_thread.times) / 1e9,
cpu_multi_thread_time = mean(multi_threaded.times) / 1e9,
gpu_time = 0.0,
)
end
# preparation of machine
machine = Machine(
[
MetagraphOptimization.NumaNode(
0,
1,
MetagraphOptimization.default_strategy(MetagraphOptimization.NumaNode),
-1.0,
UUIDs.uuid1(),
),
],
[-1.0;;],
)
# bench and produce data
n_inputs = 50_000
optimizer = ReductionOptimizer()
processes = [("ke->kke", 5), ("ke->ke", 1), ("ke->kke", 1), ("ke->kkke", 1), ("ke->kkkke", 1), ("ke->kkkkke", 1)]
for (process_str, STEPSIZE) in processes
n = 0
opt_time_cum = 0
process = parse_process(process_str, QEDModel())
graph = gen_graph(process)
inputs = [gen_process_input(process) for _ in 1:n_inputs]
get_compute_function(graph, process, machine)
while true
func_gen_time = @elapsed func = get_compute_function(graph, process, machine)
res = bench(func, inputs)
graph_properties = get_properties(graph)
push!(
df,
(
Threads.nthreads(),
process_str,
n,
opt_time_cum,
graph_properties.noNodes,
graph_properties.noEdges,
graph_properties.computeEffort,
graph_properties.data,
graph_properties.computeIntensity,
func_gen_time,
res.cpu_compile_time,
res.cpu_single_thread_time,
res.cpu_multi_thread_time,
res.gpu_compile_time,
res.gpu_time,
),
)
CSV.write(results_filename, df)
if fixpoint_reached(optimizer, graph)
break
end
opt_time_cum += @elapsed optimize!(optimizer, graph, STEPSIZE)
n += STEPSIZE
end
end
CSV.write(results_filename, df)
for (process_str, STEPSIZE) in [("AB->AB", 1), ("AB->ABBB", 1), ("AB->ABBBBB", 1)]
n = 0
opt_time_cum = 0
process = parse_process(process_str, ABCModel())
graph = parse_dag("input/$process_str.txt", ABCModel())
inputs = [gen_process_input(process) for _ in 1:n_inputs]
get_compute_function(graph, process, machine)
while true
func_gen_time = @elapsed func = get_compute_function(graph, process, machine)
res = bench(func, inputs)
graph_properties = get_properties(graph)
push!(
df,
(
Threads.nthreads(),
process_str,
n,
opt_time_cum,
graph_properties.noNodes,
graph_properties.noEdges,
graph_properties.computeEffort,
graph_properties.data,
graph_properties.computeIntensity,
func_gen_time,
res.cpu_compile_time,
res.cpu_single_thread_time,
res.cpu_multi_thread_time,
res.gpu_compile_time,
res.gpu_time,
),
)
CSV.write(results_filename, df)
if fixpoint_reached(optimizer, graph)
break
end
opt_time_cum += @elapsed optimize!(optimizer, graph, STEPSIZE)
n += STEPSIZE
end
end
CSV.write(results_filename, df)

View File

@ -0,0 +1,208 @@
using MetagraphOptimization
using CUDA
using UUIDs
using BenchmarkTools
using DataFrames
using CSV
using Dates
results_filename = "bench_results_reduction_steps_gpu.csv"
df = DataFrame(
threads = Int[],
process = String[],
operations = Int[],
cumulative_optimization_time = Float64[],
graph_nodes = Int[],
graph_edges = Int[],
graph_ce = Float64[],
graph_dt = Float64[],
graph_ci = Float64[],
cpu_st_t = Float64[],
cpu_st_s = Float64[],
cpu_mt_t = Float64[],
cpu_mt_s = Float64[],
cpu_mem = Float64[],
gpu_t = Float64[],
gpu_s = Float64[],
gpu_mem = Float64[],
)
# if they exist, read existing results and append new ones
if isfile(results_filename)
df = CSV.read(results_filename, DataFrame)
end
function log(x...)
println(now(), " ", join(x, " ")...)
return flush(stdout)
end
function bench(func, kernel!, inputs)
# gpu part
n = length(inputs)
cu_inputs = CuVector(inputs)
cu_outputs = CuVector{ComplexF64}()
resize!(cu_outputs, n)
ts = 32
bs = Int(n / ts)
bench = @benchmark begin
@cuda threads = $ts blocks = $bs always_inline = true $kernel!($cu_inputs, $cu_outputs, $n)
CUDA.device_synchronize()
end gcsample = true samples = 20 evals = 1
gpu_time = median(bench.times) / 1e9
gpu_std = std(bench.times) / 1e9
gpu_mem = bench.memory
# cpu part
single_thread = @benchmark $func.($inputs)
multi_threaded = @benchmark Threads.@threads for i in eachindex($inputs)
$func($inputs[i])
end
cpu_st_time = median(single_thread.times) / 1e9
cpu_st_std = std(single_thread.times) / 1e9
cpu_mt_time = median(multi_threaded.times) / 1e9
cpu_mt_std = std(multi_threaded.times) / 1e9
cpu_mem = std(single_thread.times)
return (
cpu_single_thread_time = cpu_st_time,
cpu_single_thread_std = cpu_st_std,
cpu_multi_thread_time = cpu_mt_time,
cpu_multi_thread_std = cpu_mt_std,
cpu_mem = cpu_mem,
gpu_time = gpu_time,
gpu_std = gpu_std,
gpu_mem = gpu_mem,
)
end
log("Available CUDA devices:")
for dev in CUDA.devices()
display(dev)
end
# preparation of machine
machine = Machine(
[
MetagraphOptimization.NumaNode(
0,
1,
MetagraphOptimization.default_strategy(MetagraphOptimization.NumaNode),
-1.0,
UUIDs.uuid1(),
),
],
[-1.0;;],
)
# bench and produce data
n_inputs = 2^16
optimizer = ReductionOptimizer()
processes = [("ke->ke", 1), ("ke->kke", 1), ("ke->kkke", 1), ("ke->kkkke", 5)]
for (process_str, STEPSIZE) in processes
n = 0
opt_time_cum = 0
process = parse_process(process_str, QEDModel())
graph = gen_graph(process)
inputs = Vector([gen_process_input(process) for _ in 1:n_inputs])
get_compute_function(graph, process, machine)
while true
func = get_compute_function(graph, process, machine)
kernel! = get_cuda_kernel(graph, process, machine)
res = bench(func, kernel!, inputs)
graph_properties = get_properties(graph)
push!(
df,
(
Threads.nthreads(),
process_str,
n,
opt_time_cum,
graph_properties.noNodes,
graph_properties.noEdges,
graph_properties.computeEffort,
graph_properties.data,
graph_properties.computeIntensity,
res.cpu_single_thread_time,
res.cpu_single_thread_std,
res.cpu_multi_thread_time,
res.cpu_multi_thread_std,
res.cpu_mem,
res.gpu_time,
res.gpu_std,
res.gpu_mem,
),
)
CSV.write(results_filename, df)
if fixpoint_reached(optimizer, graph)
break
end
opt_time_cum += @elapsed optimize!(optimizer, graph, STEPSIZE)
n += STEPSIZE
end
end
CSV.write(results_filename, df)
for (process_str, STEPSIZE) in [("AB->AB", 1), ("AB->ABBB", 1), ("AB->ABBBBB", 1)]
n = 0
opt_time_cum = 0
process = parse_process(process_str, ABCModel())
graph = parse_dag("input/$process_str.txt", ABCModel())
inputs = Vector([gen_process_input(process) for _ in 1:n_inputs])
get_compute_function(graph, process, machine)
while true
func = get_compute_function(graph, process, machine)
kernel! = get_cuda_kernel(graph, process, machine)
res = bench(func, kernel!, inputs)
graph_properties = get_properties(graph)
push!(
df,
(
Threads.nthreads(),
process_str,
n,
opt_time_cum,
graph_properties.noNodes,
graph_properties.noEdges,
graph_properties.computeEffort,
graph_properties.data,
graph_properties.computeIntensity,
res.cpu_single_thread_time,
res.cpu_single_thread_std,
res.cpu_multi_thread_time,
res.cpu_multi_thread_std,
res.cpu_mem,
res.gpu_time,
res.gpu_std,
res.gpu_mem,
),
)
CSV.write(results_filename, df)
if fixpoint_reached(optimizer, graph)
break
end
opt_time_cum += @elapsed optimize!(optimizer, graph, STEPSIZE)
n += STEPSIZE
end
end
CSV.write(results_filename, df)

232
examples/qed_bench_tape.jl Normal file
View File

@ -0,0 +1,232 @@
using MetagraphOptimization
using LIKWID
using UUIDs
using DataFrames
using CSV
using Random
using BenchmarkTools
using Dates
function log(x...)
println(now(), " ", join(x, " ")...)
return flush(stdout)
end
results_filename = "bench_results_tape_$(Threads.nthreads()).csv"
df = DataFrame(
process_name = String[],
graph_gen_time = Float64[],
optimization_time = Float64[],
function_generation_time = Float64[],
graph_nodes = Int[],
graph_edges = Int[],
graph_mem = Float64[],
cpu_threads = Int[],
n_inputs = Int[],
nflops_likwid = Int[],
cpu_time = Float64[],
cpu_rate = Float64[],
cpu_gflops = Float64[],
cpu_std = Float64[],
gpu_name = String[],
gpu_time = Float64[],
gpu_std = Float64[],
gpu_rate = Float64[],
gpu_gflops = Float64[],
)
# if they exist, read existing results and append new ones
if isfile(results_filename)
df = CSV.read(results_filename, DataFrame)
end
nInputs = 1_000_000
# use "mock" machine that only uses cpu
machine = Machine(
[
MetagraphOptimization.NumaNode(
0,
1,
MetagraphOptimization.default_strategy(MetagraphOptimization.NumaNode),
-1.0,
UUIDs.uuid1(),
),
],
[-1.0;;],
)
function cpu_bench(tape, inputs)
bench = @benchmark begin
@inbounds Threads.@threads for i in eachindex($inputs)
execute_tape($tape, $inputs[i])
end
end gcsample = true seconds = 300
time = mean(bench.times) / 1e9
s = std(bench.times) / 1e9
rate = length(inputs) / time
return (time, rate, s)
end
function bench_process(
process::MetagraphOptimization.AbstractProcessDescription,
process_name::String,
graph::DAG,
gen_time::Float64,
opt_time::Float64,
io::IO = stdout;
use_likwid = false,
)
log("\n--- Benchmarking $(process_name) ---")
func_time = @elapsed tape = gen_tape(graph, process, machine)
graph_props = GraphProperties(graph)
NFLOPs = graph_props.computeEffort
nflops_likwid = 0
if use_likwid
input = gen_process_input(process)
# get rid of annoying output to console
oldstd = stdout
redirect_stdout(devnull)
_, events = @perfmon "FLOPS_DP" execute_tape(tape, input)
redirect_stdout(oldstd) # recover original stdout
NFLOPs = first(events["FLOPS_DP"])["RETIRED_SSE_AVX_FLOPS_ALL"]
nflops_likwid = NFLOPs
end
log("Generating $nInputs inputs with $(Threads.nthreads()) threads...")
inputs = Vector{typeof(gen_process_input(process))}()
resize!(inputs, nInputs)
processes = Vector{typeof(process)}()
for i in 1:Threads.nthreads()
push!(processes, copy(process))
end
@inbounds Threads.@threads for i in eachindex(inputs)
inputs[i] = gen_process_input(processes[Threads.nthreads()])
end
log("Benchmarking CPU with $(Threads.nthreads()) threads...")
(time_cpu, rate_cpu, std_cpu) = cpu_bench(tape, inputs)
flops_cpu = (rate_cpu * NFLOPs) / 10^9
log("\nBenchmark Summary for $(process):")
if use_likwid
log("Measured FLOPS by LIKWID: $NFLOPs")
else
log("Total graph compute effort: $NFLOPs")
end
log("Total input size: $(bytes_to_human_readable(Base.summarysize(inputs)))")
log("CPU, $(Threads.nthreads()) threads")
log(" Time: $time_cpu")
log(" Rate: $rate_cpu")
log(" GFLOPS: $flops_cpu")
if (process_name != "warmup")
push!(
df,
Dict(
:process_name => process_name,
:graph_gen_time => gen_time,
:optimization_time => opt_time,
:function_generation_time => func_time,
:graph_nodes => graph_props.noNodes,
:graph_edges => graph_props.noEdges,
:graph_mem => MetagraphOptimization.mem(graph),
:cpu_threads => Threads.nthreads(),
:n_inputs => nInputs,
:nflops_likwid => nflops_likwid,
:cpu_time => time_cpu,
:cpu_std => std_cpu,
:cpu_rate => rate_cpu,
:cpu_gflops => flops_cpu,
:gpu_name => "none",
:gpu_time => 0.0,
:gpu_std => 0.0,
:gpu_rate => 0.0,
:gpu_gflops => 0.0,
),
)
end
return nothing
end
function bench_qed(process_string::String, skip_unoptimized = false)
optimizer = ReductionOptimizer()
process = parse_process(process_string, QEDModel())
gen_time = @elapsed graph = gen_graph(process)
opt_time = 0.0
if !skip_unoptimized
bench_process(process, "$process not optimized tape", graph, gen_time, opt_time)
end
opt_time = @elapsed optimize_to_fixpoint!(optimizer, graph)
bench_process(process, "$process reduced tape", graph, gen_time, opt_time)
return nothing
end
function bench_abc(process_string::String)
optimizer = ReductionOptimizer()
process = parse_process(process_string, ABCModel())
gen_time = @elapsed graph = parse_dag("input/$process_string.txt", ABCModel())
bench_process(process, "$process not optimized tape", graph, gen_time, 0.0)
opt_time = @elapsed optimize_to_fixpoint!(optimizer, graph)
bench_process(process, "$process reduced tape", graph, gen_time, opt_time)
return nothing
end
# sadly cannot put these in functions because the world age must increase after the function is created which happens only in the global scope
## -- WARMUP TO COMPILE FUNCTIONS first
optimizer = ReductionOptimizer()
process = parse_process("ke->kke", QEDModel())
gen_time = @elapsed graph = gen_graph(process)
opt_time = @elapsed optimize_to_fixpoint!(optimizer, graph)
bench_process(process, "warmup", graph, gen_time, opt_time)
# AB->AB^3
process = parse_process("AB->ABBB", ABCModel())
gen_time = @elapsed graph = parse_dag("input/AB->ABBB.txt", ABCModel())
opt_time = @elapsed optimize_to_fixpoint!(optimizer, graph)
bench_process(process, "warmup", graph, gen_time, opt_time)
## -- WARMUP END
# compton
bench_qed("ke->ke")
CSV.write(results_filename, df)
bench_qed("ke->kke")
CSV.write(results_filename, df)
bench_qed("ke->kkke")
CSV.write(results_filename, df)
bench_qed("ke->kkkke")
CSV.write(results_filename, df)
bench_qed("ke->kkkkke")
CSV.write(results_filename, df)
bench_qed("ke->kkkkkke")
CSV.write(results_filename, df)
bench_qed("ke->kkkkkkke")
CSV.write(results_filename, df)
bench_abc("AB->AB")
CSV.write(results_filename, df)
bench_abc("AB->ABBB")
CSV.write(results_filename, df)
bench_abc("AB->ABBBBB")
CSV.write(results_filename, df)

144
examples/qed_gen_bench.jl Normal file
View File

@ -0,0 +1,144 @@
using MetagraphOptimization
using DataFrames
using CSV
using BenchmarkTools
using StatsBase
results_filename = "qed_gen_results_$(Threads.nthreads()).csv"
df = DataFrame(
process_name = String[],
cpu_threads = Int[],
graph_gen_samples = Int[],
graph_gen_mean = Float64[],
graph_gen_std = Float64[],
graph_gen_median = Float64[],
graph_nodes = Int[],
graph_data_nodes = Int[],
graph_u_nodes = Int[],
graph_v_nodes = Int[],
graph_s1_nodes = Int[],
graph_s2_nodes = Int[],
graph_edges = Int[],
graph_nodes_reduced = Int[],
graph_data_nodes_reduced = Int[],
graph_u_nodes_reduced = Int[],
graph_v_nodes_reduced = Int[],
graph_s1_nodes_reduced = Int[],
graph_s2_nodes_reduced = Int[],
graph_edges_reduced = Int[],
graph_mem = Float64[],
graph_mem_reduced = Float64[],
graph_elapsed_reduce = Float64[],
)
function bench_process(process::AbstractString; warmup = false, optimize = true)
println("Benchmarking $process...")
model = QEDModel()
proc = parse_process(process, model)
gen_bench = @benchmark gen_graph($proc) gcsample = true seconds = 5
graph = gen_graph(proc)
props = GraphProperties(graph)
node_dict = countmap(typeof.(graph.nodes))
graph_size = Base.summarysize(graph)
reduce_elapsed = -1.0
node_dict_reduced = Dict()
graph_size_reduced = -1.0
props_reduced = GraphProperties()
if optimize
reduce_elapsed = @elapsed optimize_to_fixpoint!(ReductionOptimizer(), graph)
props_reduced = GraphProperties(graph)
node_dict_reduced = countmap(typeof.(graph.nodes))
graph_size_reduced = Base.summarysize(graph)
end
if warmup
return nothing
end
push!(
df,
Dict(
:process_name => process,
:cpu_threads => Threads.nthreads(),
:graph_gen_samples => length(gen_bench.times),
:graph_gen_mean => mean(gen_bench.times),
:graph_gen_std => std(gen_bench.times),
:graph_gen_median => median(gen_bench.times),
:graph_nodes => props.noNodes,
:graph_data_nodes => get(node_dict, DataTaskNode{DataTask}, 0),
:graph_u_nodes => get(node_dict, ComputeTaskNode{ComputeTaskQED_U}, 0),
:graph_v_nodes => get(node_dict, ComputeTaskNode{ComputeTaskQED_V}, 0),
:graph_s1_nodes => get(node_dict, ComputeTaskNode{ComputeTaskQED_S1}, 0),
:graph_s2_nodes => get(node_dict, ComputeTaskNode{ComputeTaskQED_S2}, 0),
:graph_edges => props.noEdges,
:graph_nodes_reduced => props_reduced.noNodes,
:graph_data_nodes_reduced => get(node_dict_reduced, DataTaskNode{DataTask}, 0),
:graph_u_nodes_reduced => get(node_dict_reduced, ComputeTaskNode{ComputeTaskQED_U}, 0),
:graph_v_nodes_reduced => get(node_dict_reduced, ComputeTaskNode{ComputeTaskQED_V}, 0),
:graph_s1_nodes_reduced => get(node_dict_reduced, ComputeTaskNode{ComputeTaskQED_S1}, 0),
:graph_s2_nodes_reduced => get(node_dict_reduced, ComputeTaskNode{ComputeTaskQED_S2}, 0),
:graph_edges_reduced => props_reduced.noEdges,
:graph_mem => graph_size,
:graph_mem_reduced => graph_size_reduced,
:graph_elapsed_reduce => reduce_elapsed,
),
)
return nothing
end
processes = [
("ke->ke", true),
("ke->kke", true),
("ke->kkke", true),
("ke->kkkke", true),
("ke->kkkkke", true),
("ke->kkkkkke", true),
("ke->kkkkkkke", true),
#("ke->kkkkkkkke", false),
#("ke->kkkkkkkkke", false),
]
df = DataFrame(
process_name = String[],
cpu_threads = Int[],
graph_gen_samples = Int[],
graph_gen_mean = Float64[],
graph_gen_std = Float64[],
graph_gen_median = Float64[],
graph_nodes = Int[],
graph_data_nodes = Int[],
graph_u_nodes = Int[],
graph_v_nodes = Int[],
graph_s1_nodes = Int[],
graph_s2_nodes = Int[],
graph_edges = Int[],
graph_nodes_reduced = Int[],
graph_data_nodes_reduced = Int[],
graph_u_nodes_reduced = Int[],
graph_v_nodes_reduced = Int[],
graph_s1_nodes_reduced = Int[],
graph_s2_nodes_reduced = Int[],
graph_edges_reduced = Int[],
graph_mem = Float64[],
graph_mem_reduced = Float64[],
graph_elapsed_reduce = Float64[],
)
# if they exist, read existing results and append new ones
if isfile(results_filename)
df = CSV.read(results_filename, DataFrame)
end
bench_process("ke->kke", warmup = true)
for (process, opt) in processes
bench_process(process, optimize = opt)
CSV.write(results_filename, df)
end

View File

@ -0,0 +1,63 @@
Bootstrap: docker
From: nvidia/cuda:12.3.1-devel-ubuntu20.04
%labels
Requires CUDA driver 470.57+.
%environment
export LANG=C
%runscript
nvidia-smi
./run.sh
%post
. /.singularity.d/env/10-docker*.sh
apt-get update
apt-get install -y pciutils
DEBIAN_FRONTEND='noninteractive' apt-get -y -o Dpkg::Options::='--force-confdef' -o Dpkg::Options::='--force-confold' install build-essential cuda-compat-12-3 libibverbs-dev ibverbs-utils gcc wget git libcap2-bin
apt-get -y autoremove; apt-get -y clean
cd /tmp
# install slurm
: ${SLURM_VERSION:=17-02-11-1}
wget https://github.com/SchedMD/slurm/archive/slurm-${SLURM_VERSION}.tar.gz
tar -xf slurm-${SLURM_VERSION}.tar.gz
cd slurm-slurm-${SLURM_VERSION}
./configure --prefix=/usr/ --sysconfdir=/etc/slurm --localstatedir=/var --disable-debug
make -C contribs/pmi2 -j$(nproc) install
cd ..
rm -rf slurm-*
# install julia
cd ~
wget https://julialang-s3.julialang.org/bin/linux/x64/1.9/julia-1.9.4-linux-x86_64.tar.gz
tar zxvf julia-1.9.4-linux-x86_64.tar.gz
mv julia-1.9.4/ /opt/julia-1.9.4
#mkdir /usr/local/bin
ln -s /opt/julia-1.9.4/bin/julia /usr/local/bin/julia
#Add nvidia driver paths to the environment variables
echo "\n #Nvidia driver paths \n" >> /environment
echo 'export PATH="/nvbin:$PATH"' >> /environment
echo 'export LD_LIBRARY_PATH="/nvlib:$LD_LIBRARY_PATH"' >> /environment
#Add CUDA paths
echo "\n #Cuda paths \n" >> /environment
echo 'export CPATH="/usr/local/cuda/include:$CPATH"' >> /environment
echo 'export PATH="/usr/local/cuda/bin:$PATH"' >> /environment
echo 'export LD_LIBRARY_PATH="/usr/local/cuda/lib64:$LD_LIBRARY_PATH"' >> /environment
echo 'export CUDA_HOME="/usr/local/cuda"' >> /environment
# install likwid
VERSION=5.3.0
wget http://ftp.fau.de/pub/likwid/likwid-$VERSION.tar.gz
tar -xaf likwid-$VERSION.tar.gz
cd likwid-$VERSION
# accessdaemon doesn't work because of permissions
sed -i 's/ACCESSMODE = accessdaemon/ACCESSMODE = perf_event/g' config.mk
make -j4
make -j4 install
echo 'export LD_LIBRARY_PATH="/usr/local/lib:$LD_LIBRARY_PATH"' >> /environment

View File

@ -0,0 +1,22 @@
#!/bin/bash
#SBATCH --array=1-32
#SBATCH --job-name=qed_bench
#SBATCH --partition=intel
#SBATCH --time=16:00:00
#SBATCH --nodes=1
#SBATCH --ntasks=1
#SBATCH --cpus-per-task=32
#SBATCH --mem=16GB
#SBATCH --output=simulation-%A-%a.out
#SBATCH --error=simulation-%A-%a.err
cd $HOME/repos/metagraph_optimization
module load singularity
module load git
printf "Current git commit hash: " > results/git.txt
git rev-parse HEAD >> results/git.txt
git status >> results/git.txt
singularity exec experiments/CUDA_container.sif ./experiments/run_qed_exec.sh $SLURM_ARRAY_TASK_ID

View File

@ -0,0 +1,24 @@
#!/bin/bash
#SBATCH --job-name=qed_bench
#SBATCH --partition=casus_a100
#SBATCH --account=casus
#SBATCH --time=8:00:00
#SBATCH --nodes=1
#SBATCH --ntasks=1
#SBATCH --cpus-per-task=32
#SBATCH --gres=gpu:1
#SBATCH --mem=256GB
#SBATCH --output=simulation-%A-%a.out
#SBATCH --error=simulation-%A-%a.err
cd $HOME/repos/metagraph_optimization
module load singularity
module load git
module load cuda/12.1
printf "Current git commit hash: " > results/git.txt
git rev-parse HEAD >> results/git.txt
git status >> results/git.txt
singularity exec --nv experiments/CUDA_container.sif ./experiments/run_qed_exec.sh 32

View File

@ -0,0 +1,24 @@
#!/bin/bash
#SBATCH --job-name=qed_bench
#SBATCH --partition=casus_a100
#SBATCH --account=casus
#SBATCH --time=8:00:00
#SBATCH --nodes=1
#SBATCH --ntasks=1
#SBATCH --cpus-per-task=128
#SBATCH --gres=gpu:4
#SBATCH --mem=2048GB
#SBATCH --output=simulation-%A-%a.out
#SBATCH --error=simulation-%A-%a.err
cd $HOME/repos/metagraph_optimization
module load singularity
module load git
module load cuda/12.1
printf "Current git commit hash: " > results/git_reduce_bench_gpu.txt
git rev-parse HEAD >> results/git_reduce_bench_gpu.txt
git status >> results/git_reduce_bench_gpu.txt
singularity exec --nv experiments/CUDA_container.sif ./experiments/full_node.sh

View File

@ -0,0 +1,22 @@
#!/bin/bash
#SBATCH --array=1-8
#SBATCH --job-name=qed_diag_gen
#SBATCH --partition=intel
#SBATCH --time=4:00:00
#SBATCH --nodes=1
#SBATCH --ntasks=1
#SBATCH --cpus-per-task=8
#SBATCH --mem=64GB
#SBATCH --output=simulation-%A-%a.out
#SBATCH --error=simulation-%A-%a.err
cd $HOME/repos/metagraph_optimization
module load singularity
module load git
printf "Current git commit hash: " > results/git.txt
git rev-parse HEAD >> results/git.txt
git status >> results/git.txt
singularity exec experiments/CUDA_container.sif ./experiments/run_gen_diagram.sh $SLURM_ARRAY_TASK_ID

View File

@ -0,0 +1,21 @@
#!/bin/bash
#SBATCH --job-name=qed_bench
#SBATCH --partition=intel
#SBATCH --time=48:00:00
#SBATCH --nodes=1
#SBATCH --ntasks=1
#SBATCH --cpus-per-task=32
#SBATCH --mem=24GB
#SBATCH --output=simulation-%A-%a.out
#SBATCH --error=simulation-%A-%a.err
cd $HOME/repos/metagraph_optimization
module load singularity
module load git
printf "Current git commit hash: " > results/git_reduce_bench.txt
git rev-parse HEAD >> results/git_reduce_bench.txt
git status >> results/git_reduce_bench.txt
singularity exec experiments/CUDA_container.sif ./experiments/run_reduce_bench.sh

View File

@ -0,0 +1,24 @@
#!/bin/bash
#SBATCH --job-name=qed_bench
#SBATCH --partition=casus_a100
#SBATCH --account=casus
#SBATCH --time=16:00:00
#SBATCH --nodes=1
#SBATCH --ntasks=1
#SBATCH --cpus-per-task=32
#SBATCH --gres=gpu:1
#SBATCH --mem=256GB
#SBATCH --output=simulation-%A-%a.out
#SBATCH --error=simulation-%A-%a.err
cd $HOME/repos/metagraph_optimization
module load singularity
module load git
module load cuda/12.1
printf "Current git commit hash: " > results/git_reduce_bench_gpu.txt
git rev-parse HEAD >> results/git_reduce_bench_gpu.txt
git status >> results/git_reduce_bench_gpu.txt
singularity exec --nv experiments/CUDA_container.sif ./experiments/run_reduce_bench_gpu.sh

25
experiments/full_node.sh Executable file
View File

@ -0,0 +1,25 @@
#!/bin/bash
SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )
LOG_FILE="$SCRIPT_DIR/../julia_full_node.log"
cd $SCRIPT_DIR/..
echo "Writing system info..."
# collect some information of the used node and system
uname -a > results/system_full_node.txt
julia --version > results/julia_full_node.txt
lscpu > results/cpu_full_node.txt
nvidia-smi > results/cuda_gpu_full_node.txt
lsblk > results/storage_full_node.txt
lspci > results/pci_full_node.txt
#echo "Initiating julia..."
#julia --threads=8 --project=./ -e 'using Pkg; Pkg.instantiate(); Pkg.add(url="https://github.com/QEDjl-project/QEDprocesses.jl/")' >> $LOG_FILE 2>&1 || exit 1 # need current dev version of QEDprocesses
#julia --threads=8 --project=./ -e 'using Pkg; Pkg.instantiate(); Pkg.add(url="https://github.com/AntonReinhard/QEDbase.jl/tree/fix_bs_multiplication")' >> $LOG_FILE 2>&1 || exit 1 # need a specific fix for abs*bs multiplication for gpu
#julia --threads=8 -e 'using Pkg; Pkg.add("CSV"); Pkg.add("DataFrames"); Pkg.add("CUDA"); Pkg.add("Random"); Pkg.add("BenchmarkTools"); Pkg.add("Dates")' >> $LOG_FILE 2>&1 || exit 1 # add requirements for the bench script
#julia --project -e 'using CUDA; CUDA.set_runtime_version!(VersionNumber("12.1"))' >> $LOG_FILE 2>&1 || echo "Failed to set CUDA version number"
echo "Benchmarking Full Node 128 Threads + *GPUs*"
julia --project -O3 --threads=128 examples/full_node_bench.jl >> $LOG_FILE 2>&1 || echo "-- Something went wrong, check logs --"

27
experiments/run_gen_diagram.sh Executable file
View File

@ -0,0 +1,27 @@
#!/bin/bash
# first arg = number of threads
i=$1
SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )
LOG_FILE="$SCRIPT_DIR/../julia.log"
cd $SCRIPT_DIR/..
echo "Writing system info..."
# collect some information of the used node and system
uname -a > results/system.txt
julia --version > results/julia.txt
lscpu > results/cpu.txt
lsblk > results/storage.txt
lspci > results/pci.txt
echo "Initiating julia..."
julia --threads=8 --project=./ -e 'using Pkg; Pkg.instantiate(); Pkg.add(url="https://github.com/QEDjl-project/QEDprocesses.jl/")' >> $LOG_FILE 2>&1 || exit 1 # need current dev version of QEDprocesses
julia --threads=8 --project=./ -e 'using Pkg; Pkg.instantiate(); Pkg.add(url="https://github.com/AntonReinhard/QEDbase.jl/tree/fix_bs_multiplication")' >> $LOG_FILE 2>&1 || exit 1 # need a specific fix for abs*bs multiplication for gpu
julia --threads=8 -e 'using Pkg; Pkg.add("CSV"); Pkg.add("DataFrames"); Pkg.add("BenchmarkTools"); Pkg.add("StatsBase")' >> $LOG_FILE 2>&1 || exit 1 # add requirements for the bench script
echo "Benchmarking with $i threads..."
julia --project -O3 --threads=$i examples/qed_gen_bench.jl >> $LOG_FILE 2>&1 || echo "-- Something went wrong, check logs --"

31
experiments/run_qed_exec.sh Executable file
View File

@ -0,0 +1,31 @@
#!/bin/bash
# first arg = number of threads
i=$1
SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )
LOG_FILE="$SCRIPT_DIR/../julia_$i.log"
cd $SCRIPT_DIR/..
echo "Writing system info..."
# collect some information of the used node and system
uname -a > results/system_$i.txt
julia --version > results/julia_$i.txt
lscpu > results/cpu_$i.txt
nvidia-smi > results/cuda_gpu_$i.txt
lsblk > results/storage_$i.txt
lspci > results/pci_$i.txt
echo "Initiating julia..."
#julia --threads=8 --project=./ -e 'using Pkg; Pkg.instantiate(); Pkg.add(url="https://github.com/QEDjl-project/QEDprocesses.jl/")' >> $LOG_FILE 2>&1 || exit 1 # need current dev version of QEDprocesses
#julia --threads=8 --project=./ -e 'using Pkg; Pkg.instantiate(); Pkg.add(url="https://github.com/AntonReinhard/QEDbase.jl/tree/fix_bs_multiplication")' >> $LOG_FILE 2>&1 || exit 1 # need a specific fix for abs*bs multiplication for gpu
#julia --threads=8 -e 'using Pkg; Pkg.add("CSV"); Pkg.add("DataFrames"); Pkg.add("LIKWID"); Pkg.add("CUDA"); Pkg.add("Random"); Pkg.add("BenchmarkTools"); Pkg.add("Dates")' >> $LOG_FILE 2>&1 || exit 1 # add requirements for the bench script
#julia --project -e 'using CUDA; CUDA.set_runtime_version!(VersionNumber("12.1"))' >> $LOG_FILE 2>&1 || echo "Failed to set CUDA version number"
echo "Benchmarking $i Threads"
julia --project -O3 --threads=$i examples/qed_bench.jl >> $LOG_FILE 2>&1 || echo "-- Something went wrong, check logs --"
echo "Benchmarking Tape variant $i Threads"
julia --project -O3 --threads=$i examples/qed_bench_tape.jl >> $LOG_FILE 2>&1 || echo "-- Something went wrong, check logs --"

24
experiments/run_reduce_bench.sh Executable file
View File

@ -0,0 +1,24 @@
#!/bin/bash
SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )
LOG_FILE="$SCRIPT_DIR/../julia_bench_reduce.log"
cd $SCRIPT_DIR/..
echo "Writing system info..."
# collect some information of the used node and system
uname -a > results/system_bench_reduce.txt
julia --version > results/julia_bench_reduce.txt
lscpu > results/cpu_bench_reduce.txt
nvidia-smi > results/cuda_gpu_bench_reduce.txt
lsblk > results/storage_bench_reduce.txt
lspci > results/pci_bench_reduce.txt
#echo "Initiating julia..."
#julia --threads=8 --project=./ -e 'using Pkg; Pkg.instantiate(); Pkg.add(url="https://github.com/QEDjl-project/QEDprocesses.jl/")' >> $LOG_FILE 2>&1 || exit 1 # need current dev version of QEDprocesses
#julia --threads=8 --project=./ -e 'using Pkg; Pkg.instantiate(); Pkg.add(url="https://github.com/AntonReinhard/QEDbase.jl/tree/fix_bs_multiplication")' >> $LOG_FILE 2>&1 || exit 1 # need a specific fix for abs*bs multiplication for gpu
#julia --threads=8 -e 'using Pkg; Pkg.add("CSV"); Pkg.add("DataFrames"); Pkg.add("LIKWID"); Pkg.add("CUDA"); Pkg.add("Random"); Pkg.add("BenchmarkTools"); Pkg.add("Dates")' >> $LOG_FILE 2>&1 || exit 1 # add requirements for the bench script
echo "Benchmarking Reduction 32 Threads"
julia --project -O3 --threads=32 examples/qed_bench_reduction_steps.jl >> $LOG_FILE 2>&1 || echo "-- Something went wrong, check logs --"

View File

@ -0,0 +1,25 @@
#!/bin/bash
SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )
LOG_FILE="$SCRIPT_DIR/../julia_bench_reduce_gpu.log"
cd $SCRIPT_DIR/..
echo "Writing system info..."
# collect some information of the used node and system
uname -a > results/system_bench_reduce_gpu.txt
julia --version > results/julia_bench_reduce_gpu.txt
lscpu > results/cpu_bench_reduce_gpu.txt
nvidia-smi > results/cuda_gpu_bench_reduce_gpu.txt
lsblk > results/storage_bench_reduce_gpu.txt
lspci > results/pci_bench_reduce_gpu.txt
#echo "Initiating julia..."
#julia --threads=8 --project=./ -e 'using Pkg; Pkg.instantiate(); Pkg.add(url="https://github.com/QEDjl-project/QEDprocesses.jl/")' >> $LOG_FILE 2>&1 || exit 1 # need current dev version of QEDprocesses
#julia --threads=8 --project=./ -e 'using Pkg; Pkg.instantiate(); Pkg.add(url="https://github.com/AntonReinhard/QEDbase.jl/tree/fix_bs_multiplication")' >> $LOG_FILE 2>&1 || exit 1 # need a specific fix for abs*bs multiplication for gpu
#julia --threads=8 -e 'using Pkg; Pkg.add("CSV"); Pkg.add("DataFrames"); Pkg.add("LIKWID"); Pkg.add("CUDA"); Pkg.add("Random"); Pkg.add("BenchmarkTools"); Pkg.add("Dates")' >> $LOG_FILE 2>&1 || exit 1 # add requirements for the bench script
#julia --project -e 'using CUDA; CUDA.set_runtime_version!(VersionNumber("12.1"))' >> $LOG_FILE 2>&1 || echo "Failed to set CUDA version number"
echo "Benchmarking Reduction 32 Threads, *GPU*"
julia --project -O3 --threads=32 examples/qed_bench_reduction_steps_gpu.jl >> $LOG_FILE 2>&1 || echo "-- Something went wrong, check logs --"

Binary file not shown.

Binary file not shown.

3
images/README.md Normal file
View File

@ -0,0 +1,3 @@
# Images
In this folder we collect benchmark results in pdf form which may be useful in the future.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

BIN
images/cpu_vs_gpu_abc.pdf Normal file

Binary file not shown.

BIN
images/cpu_vs_gpu_qed.pdf Normal file

Binary file not shown.

View File

@ -0,0 +1,3 @@
# Full Node Benchmarks
Done using `experiments/full_node.sh` on hemera, using 128 threads and 4 A100 GPUs.

Binary file not shown.

BIN
images/gen_memory.pdf Normal file

Binary file not shown.

BIN
images/gen_times.pdf Normal file

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Some files were not shown because too many files have changed in this diff Show More