Compare commits
53 Commits
main
...
release/1.
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
76123892a8 | ||
|
|
ebe4f4f4ca | ||
|
|
8da7214dcb | ||
|
|
1a661e3eb3 | ||
|
|
6cfdca7260 | ||
|
|
f92207df66 | ||
|
|
5ef151a8d9 | ||
|
|
566b7d3164 | ||
|
|
2d4f6484be | ||
|
|
386dd738cf | ||
|
|
f60be3e9e6 | ||
|
|
d402bc8a50 | ||
|
|
672751f9b1 | ||
|
|
5566fa6c03 | ||
|
|
71dc906c77 | ||
|
|
d162c10919 | ||
|
|
04ca254644 | ||
|
|
c7d11d09c7 | ||
|
|
c6268f2ac7 | ||
|
|
1a0e19bb9b | ||
|
|
2e3e3e3e2d | ||
|
|
68fa3cb303 | ||
|
|
9f8a88d2f8 | ||
|
|
c2b63da4f5 | ||
|
|
928a716175 | ||
|
|
68a66f231f | ||
|
|
cd8276cd5e | ||
|
|
14089604b1 | ||
|
|
aaf4cbaa65 | ||
|
|
cba43c240e | ||
|
|
b6370c9cfb | ||
|
|
4b2a132140 | ||
|
|
f13c4cdc3b | ||
|
|
e257545d1f | ||
|
|
0aa7fce039 | ||
|
|
8905c01158 | ||
|
|
bb699527cf | ||
|
|
eee64873b0 | ||
|
|
d6407fffff | ||
|
|
194bd97730 | ||
|
|
d507027e83 | ||
|
|
8f9b392e0b | ||
|
|
73faccf108 | ||
|
|
a9913f38c1 | ||
|
|
2dff35a2a4 | ||
|
|
6a9ec440c7 | ||
|
|
1b48c09742 | ||
|
|
0d56c051d6 | ||
|
|
80b6f1a4f9 | ||
|
|
fca7ef732c | ||
|
|
b60a4d9b30 | ||
|
|
2077f48c35 | ||
|
|
abe9868899 |
@@ -11,6 +11,8 @@ env:
|
||||
SLACK_ICON: https://pbs.twimg.com/profile_images/1274014582265298945/OjBKP9kn_400x400.png
|
||||
SLACK_USERNAME: ${{ secrets.BOT_USERNAME }}
|
||||
SLACK_WEBHOOK: ${{ secrets.SLACK_WEBHOOK }}
|
||||
SLACKIFY_MARKDOWN: true
|
||||
PULL_REQUEST_MD_LINK: ""
|
||||
CHECKOUT_TOKEN: ${{ secrets.REPO_CHECKOUT_TOKEN || secrets.GITHUB_TOKEN }}
|
||||
# Secrets will be available only to zama-ai organization members
|
||||
SECRETS_AVAILABLE: ${{ secrets.JOB_SECRET != '' }}
|
||||
@@ -51,7 +53,7 @@ jobs:
|
||||
name: Backward compatibility tests
|
||||
needs: [ setup-instance ]
|
||||
concurrency:
|
||||
group: ${{ github.workflow }}_${{ github.head_ref || github.ref }}
|
||||
group: ${{ github.workflow_ref }}
|
||||
cancel-in-progress: true
|
||||
runs-on: ${{ needs.setup-instance.outputs.runner-name }}
|
||||
steps:
|
||||
@@ -62,18 +64,14 @@ jobs:
|
||||
token: ${{ env.CHECKOUT_TOKEN }}
|
||||
|
||||
- name: Install latest stable
|
||||
uses: dtolnay/rust-toolchain@a54c7afa936fefeb4456b2dd8068152669aa8203
|
||||
uses: dtolnay/rust-toolchain@888c2e1ea69ab0d4330cbf0af1ecc7b68f368cc1
|
||||
with:
|
||||
toolchain: stable
|
||||
|
||||
- name: Install git-lfs
|
||||
run: |
|
||||
sudo apt update && sudo apt -y install git-lfs
|
||||
|
||||
- name: Use specific data branch
|
||||
if: ${{ contains(github.event.pull_request.labels.*.name, 'data_PR') }}
|
||||
env:
|
||||
PR_BRANCH: ${{ github.head_ref || github.ref_name }}
|
||||
PR_BRANCH: ${{ github.ref_name }}
|
||||
run: |
|
||||
echo "BACKWARD_COMPAT_DATA_BRANCH=${PR_BRANCH}" >> "${GITHUB_ENV}"
|
||||
|
||||
@@ -83,7 +81,23 @@ jobs:
|
||||
BRANCH="$(make backward_compat_branch)"
|
||||
echo "branch=${BRANCH}" >> "${GITHUB_OUTPUT}"
|
||||
|
||||
- name: Get backward compat branch head SHA
|
||||
id: backward_compat_sha
|
||||
env:
|
||||
REPO_URL: "https://github.com/zama-ai/tfhe-backward-compat-data"
|
||||
run: |
|
||||
SHA=$(git ls-remote ${{ env.REPO_URL }} refs/heads/${{ steps.backward_compat_branch.outputs.branch }} | awk '{print $1}')
|
||||
echo "sha=${SHA}" >> "${GITHUB_OUTPUT}"
|
||||
|
||||
- name: Retrieve data from cache
|
||||
id: retrieve-data-cache
|
||||
uses: actions/cache/restore@d4323d4df104b026a6aa633fdb11d772146be0bf #v4.2.2
|
||||
with:
|
||||
path: tests/tfhe-backward-compat-data
|
||||
key: ${{ steps.backward_compat_branch.outputs.branch }}_${{ steps.backward_compat_sha.outputs.sha }}
|
||||
|
||||
- name: Clone test data
|
||||
if: steps.retrieve-data-cache.outputs.cache-hit != 'true'
|
||||
uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683
|
||||
with:
|
||||
persist-credentials: 'false'
|
||||
@@ -96,13 +110,26 @@ jobs:
|
||||
run: |
|
||||
make test_backward_compatibility_ci
|
||||
|
||||
- name: Store data in cache
|
||||
if: steps.retrieve-data-cache.outputs.cache-hit != 'true'
|
||||
continue-on-error: true
|
||||
uses: actions/cache/save@d4323d4df104b026a6aa633fdb11d772146be0bf #v4.2.2
|
||||
with:
|
||||
path: tests/tfhe-backward-compat-data
|
||||
key: ${{ steps.backward_compat_branch.outputs.branch }}_${{ steps.backward_compat_sha.outputs.sha }}
|
||||
|
||||
- name: Set pull-request URL
|
||||
if: ${{ failure() && github.event_name == 'pull_request' }}
|
||||
run: |
|
||||
echo "PULL_REQUEST_MD_LINK=[pull-request](${{ vars.PR_BASE_URL }}${{ github.event.pull_request.number }}), " >> "${GITHUB_ENV}"
|
||||
|
||||
- name: Slack Notification
|
||||
if: ${{ failure() }}
|
||||
continue-on-error: true
|
||||
uses: rtCamp/action-slack-notify@c33737706dea87cd7784c687dadc9adf1be59990
|
||||
env:
|
||||
SLACK_COLOR: ${{ job.status }}
|
||||
SLACK_MESSAGE: "Backward compatibility tests finished with status: ${{ job.status }} on '${{ env.BRANCH }}'. (${{ env.ACTION_RUN_URL }})"
|
||||
SLACK_MESSAGE: "Backward compatibility tests finished with status: ${{ job.status }}. (${{ env.PULL_REQUEST_MD_LINK }}[action run](${{ env.ACTION_RUN_URL }}))"
|
||||
|
||||
teardown-instance:
|
||||
name: Teardown instance (backward-compat-tests)
|
||||
@@ -127,4 +154,4 @@ jobs:
|
||||
uses: rtCamp/action-slack-notify@c33737706dea87cd7784c687dadc9adf1be59990
|
||||
env:
|
||||
SLACK_COLOR: ${{ job.status }}
|
||||
SLACK_MESSAGE: "Instance teardown (backward-compat-tests) finished with status: ${{ job.status }} on '${{ env.BRANCH }}'. (${{ env.ACTION_RUN_URL }})"
|
||||
SLACK_MESSAGE: "Instance teardown (backward-compat-tests) finished with status: ${{ job.status }}. (${{ env.ACTION_RUN_URL }})"
|
||||
|
||||
4
.github/workflows/aws_tfhe_fast_tests.yml
vendored
@@ -209,7 +209,7 @@ jobs:
|
||||
|
||||
- name: Node cache restoration
|
||||
id: node-cache
|
||||
uses: actions/cache/restore@1bd1e32a3bdc45362d1e726936510720a7c30a57 #v4.2.0
|
||||
uses: actions/cache/restore@0c907a75c2c80ebcb7f088228285e798b750cf8f #v4.2.1
|
||||
with:
|
||||
path: |
|
||||
~/.nvm
|
||||
@@ -222,7 +222,7 @@ jobs:
|
||||
make install_node
|
||||
|
||||
- name: Node cache save
|
||||
uses: actions/cache/save@1bd1e32a3bdc45362d1e726936510720a7c30a57 #v4.2.0
|
||||
uses: actions/cache/save@0c907a75c2c80ebcb7f088228285e798b750cf8f #v4.2.1
|
||||
if: steps.node-cache.outputs.cache-hit != 'true'
|
||||
with:
|
||||
path: |
|
||||
|
||||
4
.github/workflows/aws_tfhe_wasm_tests.yml
vendored
@@ -73,7 +73,7 @@ jobs:
|
||||
|
||||
- name: Node cache restoration
|
||||
id: node-cache
|
||||
uses: actions/cache/restore@1bd1e32a3bdc45362d1e726936510720a7c30a57 #v4.2.0
|
||||
uses: actions/cache/restore@0c907a75c2c80ebcb7f088228285e798b750cf8f #v4.2.1
|
||||
with:
|
||||
path: |
|
||||
~/.nvm
|
||||
@@ -86,7 +86,7 @@ jobs:
|
||||
make install_node
|
||||
|
||||
- name: Node cache save
|
||||
uses: actions/cache/save@1bd1e32a3bdc45362d1e726936510720a7c30a57 #v4.2.0
|
||||
uses: actions/cache/save@0c907a75c2c80ebcb7f088228285e798b750cf8f #v4.2.1
|
||||
if: steps.node-cache.outputs.cache-hit != 'true'
|
||||
with:
|
||||
path: |
|
||||
|
||||
2
.github/workflows/benchmark_boolean.yml
vendored
@@ -94,7 +94,7 @@ jobs:
|
||||
--append-results
|
||||
|
||||
- name: Upload parsed results artifact
|
||||
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08
|
||||
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1
|
||||
with:
|
||||
name: ${{ github.sha }}_boolean
|
||||
path: ${{ env.RESULTS_FILENAME }}
|
||||
|
||||
3
.github/workflows/benchmark_core_crypto.yml
vendored
@@ -68,6 +68,7 @@ jobs:
|
||||
|
||||
- name: Run benchmarks with AVX512
|
||||
run: |
|
||||
make bench_ks_pbs
|
||||
make bench_pbs
|
||||
make bench_pbs128
|
||||
make bench_ks
|
||||
@@ -85,7 +86,7 @@ jobs:
|
||||
--walk-subdirs
|
||||
|
||||
- name: Upload parsed results artifact
|
||||
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08
|
||||
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1
|
||||
with:
|
||||
name: ${{ github.sha }}_core_crypto
|
||||
path: ${{ env.RESULTS_FILENAME }}
|
||||
|
||||
2
.github/workflows/benchmark_erc20.yml
vendored
@@ -99,7 +99,7 @@ jobs:
|
||||
--append-results
|
||||
|
||||
- name: Upload parsed results artifact
|
||||
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08
|
||||
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1
|
||||
with:
|
||||
name: ${{ github.sha }}_erc20
|
||||
path: ${{ env.RESULTS_FILENAME }}
|
||||
|
||||
4
.github/workflows/benchmark_gpu_4090.yml
vendored
@@ -80,7 +80,7 @@ jobs:
|
||||
--walk-subdirs
|
||||
|
||||
- name: Upload parsed results artifact
|
||||
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08
|
||||
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1
|
||||
with:
|
||||
name: ${{ github.sha }}_integer_multi_bit_gpu_default
|
||||
path: ${{ env.RESULTS_FILENAME }}
|
||||
@@ -157,7 +157,7 @@ jobs:
|
||||
|
||||
|
||||
- name: Upload parsed results artifact
|
||||
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08
|
||||
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1
|
||||
with:
|
||||
name: ${{ github.sha }}_core_crypto
|
||||
path: ${{ env.RESULTS_FILENAME }}
|
||||
|
||||
@@ -77,6 +77,7 @@ jobs:
|
||||
|
||||
- name: Run benchmarks with AVX512
|
||||
run: |
|
||||
make bench_ks_pbs_gpu
|
||||
make bench_pbs_gpu
|
||||
make bench_ks_gpu
|
||||
|
||||
@@ -94,7 +95,7 @@ jobs:
|
||||
--walk-subdirs
|
||||
|
||||
- name: Upload parsed results artifact
|
||||
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08
|
||||
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1
|
||||
with:
|
||||
name: ${{ github.sha }}_core_crypto
|
||||
path: ${{ env.RESULTS_FILENAME }}
|
||||
|
||||
@@ -120,7 +120,7 @@ jobs:
|
||||
--name-suffix avx512
|
||||
|
||||
- name: Upload parsed results artifact
|
||||
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08
|
||||
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1
|
||||
with:
|
||||
name: ${{ github.sha }}_erc20_${{ inputs.profile }}
|
||||
path: ${{ env.RESULTS_FILENAME }}
|
||||
|
||||
@@ -196,7 +196,7 @@ jobs:
|
||||
--bench-type ${{ matrix.bench_type }}
|
||||
|
||||
- name: Upload parsed results artifact
|
||||
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08
|
||||
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1
|
||||
with:
|
||||
name: ${{ github.sha }}_${{ matrix.command }}_${{ matrix.op_flavor }}_${{ inputs.profile }}
|
||||
path: ${{ env.RESULTS_FILENAME }}
|
||||
|
||||
2
.github/workflows/benchmark_integer.yml
vendored
@@ -172,7 +172,7 @@ jobs:
|
||||
--bench-type ${{ matrix.bench_type }}
|
||||
|
||||
- name: Upload parsed results artifact
|
||||
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08
|
||||
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1
|
||||
with:
|
||||
name: ${{ github.sha }}_${{ matrix.command }}_${{ matrix.op_flavor }}_${{ matrix.bench_type }}
|
||||
path: ${{ env.RESULTS_FILENAME }}
|
||||
|
||||
2
.github/workflows/benchmark_shortint.yml
vendored
@@ -138,7 +138,7 @@ jobs:
|
||||
--append-results
|
||||
|
||||
- name: Upload parsed results artifact
|
||||
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08
|
||||
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1
|
||||
with:
|
||||
name: ${{ github.sha }}_shortint_${{ matrix.op_flavor }}
|
||||
path: ${{ env.RESULTS_FILENAME }}
|
||||
|
||||
@@ -166,7 +166,7 @@ jobs:
|
||||
--bench-type ${{ matrix.bench_type }}
|
||||
|
||||
- name: Upload parsed results artifact
|
||||
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08
|
||||
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1
|
||||
with:
|
||||
name: ${{ github.sha }}_${{ matrix.command }}_${{ matrix.op_flavor }}_${{ matrix.bench_type }}
|
||||
path: ${{ env.RESULTS_FILENAME }}
|
||||
|
||||
2
.github/workflows/benchmark_tfhe_fft.yml
vendored
@@ -84,7 +84,7 @@ jobs:
|
||||
--name-suffix avx512
|
||||
|
||||
- name: Upload parsed results artifact
|
||||
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08
|
||||
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1
|
||||
with:
|
||||
name: ${{ github.sha }}_fft
|
||||
path: ${{ env.RESULTS_FILENAME }}
|
||||
|
||||
2
.github/workflows/benchmark_tfhe_ntt.yml
vendored
@@ -84,7 +84,7 @@ jobs:
|
||||
--name-suffix avx512
|
||||
|
||||
- name: Upload parsed results artifact
|
||||
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08
|
||||
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1
|
||||
with:
|
||||
name: ${{ github.sha }}_ntt
|
||||
path: ${{ env.RESULTS_FILENAME }}
|
||||
|
||||
2
.github/workflows/benchmark_tfhe_zk_pok.yml
vendored
@@ -132,7 +132,7 @@ jobs:
|
||||
--bench-type ${{ env.BENCH_TYPE }}
|
||||
|
||||
- name: Upload parsed results artifact
|
||||
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08
|
||||
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1
|
||||
with:
|
||||
name: ${{ github.sha }}_tfhe_zk_pok
|
||||
path: ${{ env.RESULTS_FILENAME }}
|
||||
|
||||
6
.github/workflows/benchmark_wasm_client.yml
vendored
@@ -110,7 +110,7 @@ jobs:
|
||||
|
||||
- name: Node cache restoration
|
||||
id: node-cache
|
||||
uses: actions/cache/restore@1bd1e32a3bdc45362d1e726936510720a7c30a57 #v4.2.0
|
||||
uses: actions/cache/restore@0c907a75c2c80ebcb7f088228285e798b750cf8f #v4.2.1
|
||||
with:
|
||||
path: |
|
||||
~/.nvm
|
||||
@@ -123,7 +123,7 @@ jobs:
|
||||
make install_node
|
||||
|
||||
- name: Node cache save
|
||||
uses: actions/cache/save@1bd1e32a3bdc45362d1e726936510720a7c30a57 #v4.2.0
|
||||
uses: actions/cache/save@0c907a75c2c80ebcb7f088228285e798b750cf8f #v4.2.1
|
||||
if: steps.node-cache.outputs.cache-hit != 'true'
|
||||
with:
|
||||
path: |
|
||||
@@ -167,7 +167,7 @@ jobs:
|
||||
--append-results
|
||||
|
||||
- name: Upload parsed results artifact
|
||||
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08
|
||||
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1
|
||||
with:
|
||||
name: ${{ github.sha }}_wasm_${{ matrix.browser }}
|
||||
path: ${{ env.RESULTS_FILENAME }}
|
||||
|
||||
2
.github/workflows/benchmark_zk_pke.yml
vendored
@@ -179,7 +179,7 @@ jobs:
|
||||
--append-results
|
||||
|
||||
- name: Upload parsed results artifact
|
||||
uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08
|
||||
uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1
|
||||
with:
|
||||
name: ${{ github.sha }}_integer_zk
|
||||
path: ${{ env.RESULTS_FILENAME }}
|
||||
|
||||
63
.github/workflows/cargo_test_fft.yml
vendored
@@ -3,16 +3,46 @@ name: Cargo Test tfhe-fft
|
||||
|
||||
on:
|
||||
pull_request:
|
||||
push:
|
||||
branches:
|
||||
- main
|
||||
|
||||
env:
|
||||
CARGO_TERM_COLOR: always
|
||||
IS_PULL_REQUEST: ${{ github.event_name == 'pull_request' }}
|
||||
|
||||
concurrency:
|
||||
group: ${{ github.workflow }}-${{ github.head_ref }}
|
||||
cancel-in-progress: true
|
||||
|
||||
jobs:
|
||||
should-run:
|
||||
runs-on: ubuntu-latest
|
||||
permissions:
|
||||
pull-requests: read
|
||||
outputs:
|
||||
fft_test: ${{ env.IS_PULL_REQUEST == 'false' || steps.changed-files.outputs.fft_any_changed }}
|
||||
steps:
|
||||
- name: Checkout tfhe-rs
|
||||
uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683
|
||||
with:
|
||||
fetch-depth: 0
|
||||
persist-credentials: 'false'
|
||||
|
||||
- name: Check for file changes
|
||||
id: changed-files
|
||||
uses: tj-actions/changed-files@dcc7a0cba800f454d79fff4b993e8c3555bcc0a8
|
||||
with:
|
||||
files_yaml: |
|
||||
fft:
|
||||
- tfhe/Cargo.toml
|
||||
- Makefile
|
||||
- tfhe-fft/**
|
||||
- '.github/workflows/cargo_test_fft.yml'
|
||||
|
||||
cargo-tests-fft:
|
||||
needs: should-run
|
||||
if: needs.should-run.outputs.fft_test == 'true'
|
||||
runs-on: ${{ matrix.runner_type }}
|
||||
strategy:
|
||||
matrix:
|
||||
@@ -39,6 +69,8 @@ jobs:
|
||||
make test_fft_no_std
|
||||
|
||||
cargo-tests-fft-nightly:
|
||||
needs: should-run
|
||||
if: needs.should-run.outputs.fft_test == 'true'
|
||||
runs-on: ${{ matrix.runner_type }}
|
||||
strategy:
|
||||
matrix:
|
||||
@@ -61,7 +93,9 @@ jobs:
|
||||
make test_fft_no_std_nightly
|
||||
|
||||
cargo-tests-fft-node-js:
|
||||
runs-on: "ubuntu-latest"
|
||||
needs: should-run
|
||||
if: needs.should-run.outputs.fft_test == 'true'
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683
|
||||
|
||||
@@ -69,3 +103,30 @@ jobs:
|
||||
run: |
|
||||
make install_node
|
||||
make test_fft_node_js_ci
|
||||
|
||||
cargo-tests-fft-successful:
|
||||
needs: [ should-run, cargo-tests-fft, cargo-tests-fft-nightly, cargo-tests-fft-node-js ]
|
||||
if: ${{ always() }}
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Tests do not need to run
|
||||
if: needs.should-run.outputs.fft_test == 'false'
|
||||
run: |
|
||||
echo "tfhe-fft files haven't changed tests don't need to run"
|
||||
|
||||
- name: Check all tests passed
|
||||
if: needs.should-run.outputs.fft_test == 'true' &&
|
||||
needs.cargo-tests-fft.result == 'success' &&
|
||||
needs.cargo-tests-fft-nightly.result == 'success' &&
|
||||
needs.cargo-tests-fft-node-js.result == 'success'
|
||||
run: |
|
||||
echo "All tfhe-fft test passed"
|
||||
|
||||
- name: Check tests failure
|
||||
if: needs.should-run.outputs.fft_test == 'true' &&
|
||||
(needs.cargo-tests-fft.result != 'success' ||
|
||||
needs.cargo-tests-fft-nightly.result != 'success' ||
|
||||
needs.cargo-tests-fft-node-js.result != 'success')
|
||||
run: |
|
||||
echo "Some tfhe-fft tests failed"
|
||||
exit 1
|
||||
|
||||
59
.github/workflows/cargo_test_ntt.yml
vendored
@@ -3,16 +3,46 @@ name: Cargo Test tfhe-ntt
|
||||
|
||||
on:
|
||||
pull_request:
|
||||
push:
|
||||
branches:
|
||||
- main
|
||||
|
||||
env:
|
||||
CARGO_TERM_COLOR: always
|
||||
IS_PULL_REQUEST: ${{ github.event_name == 'pull_request' }}
|
||||
|
||||
concurrency:
|
||||
group: ${{ github.workflow }}-${{ github.head_ref }}
|
||||
cancel-in-progress: true
|
||||
|
||||
jobs:
|
||||
jobs:
|
||||
should-run:
|
||||
runs-on: ubuntu-latest
|
||||
permissions:
|
||||
pull-requests: read
|
||||
outputs:
|
||||
ntt_test: ${{ env.IS_PULL_REQUEST == 'false' || steps.changed-files.outputs.ntt_any_changed }}
|
||||
steps:
|
||||
- name: Checkout tfhe-rs
|
||||
uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683
|
||||
with:
|
||||
fetch-depth: 0
|
||||
persist-credentials: 'false'
|
||||
|
||||
- name: Check for file changes
|
||||
id: changed-files
|
||||
uses: tj-actions/changed-files@dcc7a0cba800f454d79fff4b993e8c3555bcc0a8
|
||||
with:
|
||||
files_yaml: |
|
||||
ntt:
|
||||
- tfhe/Cargo.toml
|
||||
- Makefile
|
||||
- tfhe-ntt/**
|
||||
- '.github/workflows/cargo_test_ntt.yml'
|
||||
|
||||
cargo-tests-ntt:
|
||||
needs: should-run
|
||||
if: needs.should-run.outputs.ntt_test == 'true'
|
||||
runs-on: ${{ matrix.os }}
|
||||
strategy:
|
||||
matrix:
|
||||
@@ -34,6 +64,8 @@ jobs:
|
||||
run: make test_ntt_no_std
|
||||
|
||||
cargo-tests-ntt-nightly:
|
||||
needs: should-run
|
||||
if: needs.should-run.outputs.ntt_test == 'true'
|
||||
runs-on: ${{ matrix.os }}
|
||||
strategy:
|
||||
matrix:
|
||||
@@ -52,3 +84,28 @@ jobs:
|
||||
|
||||
- name: Test no-std nightly
|
||||
run: make test_ntt_no_std_nightly
|
||||
|
||||
cargo-tests-ntt-successful:
|
||||
needs: [ should-run, cargo-tests-ntt, cargo-tests-ntt-nightly ]
|
||||
if: ${{ always() }}
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Tests do not need to run
|
||||
if: needs.should-run.outputs.ntt_test == 'false'
|
||||
run: |
|
||||
echo "tfhe-ntt files haven't changed tests don't need to run"
|
||||
|
||||
- name: Check all tests success
|
||||
if: needs.should-run.outputs.ntt_test == 'true' &&
|
||||
needs.cargo-tests-ntt.result == 'success' &&
|
||||
needs.cargo-tests-ntt-nightly.result == 'success'
|
||||
run: |
|
||||
echo "All tfhe-ntt tests passed"
|
||||
|
||||
- name: Check tests failure
|
||||
if: needs.should-run.outputs.ntt_test == 'true' &&
|
||||
(needs.cargo-tests-ntt.result != 'success' ||
|
||||
needs.cargo-tests-ntt-nightly.result != 'success')
|
||||
run: |
|
||||
echo "Some tfhe-ntt tests failed"
|
||||
exit 1
|
||||
|
||||
11
.github/workflows/make_release.yml
vendored
@@ -51,7 +51,7 @@ jobs:
|
||||
- name: Prepare package
|
||||
run: |
|
||||
cargo package -p tfhe
|
||||
- uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08 # v4.6.0
|
||||
- uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1 # v4.6.1
|
||||
with:
|
||||
name: crate
|
||||
path: target/package/*.crate
|
||||
@@ -81,7 +81,7 @@ jobs:
|
||||
# For provenance of npmjs publish
|
||||
permissions:
|
||||
contents: read
|
||||
id-token: write
|
||||
id-token: write # also needed for OIDC token exchange on crates.io
|
||||
steps:
|
||||
- name: Checkout
|
||||
uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
|
||||
@@ -98,13 +98,16 @@ jobs:
|
||||
with:
|
||||
name: crate
|
||||
path: target/package
|
||||
- name: Authenticate on registry
|
||||
uses: rust-lang/crates-io-auth-action@e919bc7605cde86df457cf5b93c5e103838bd879 # v1.0.1
|
||||
id: auth
|
||||
- name: Publish crate.io package
|
||||
if: ${{ inputs.push_to_crates }}
|
||||
env:
|
||||
CRATES_TOKEN: ${{ secrets.CARGO_REGISTRY_TOKEN }}
|
||||
CARGO_REGISTRY_TOKEN: ${{ steps.auth.outputs.token }}
|
||||
DRY_RUN: ${{ inputs.dry_run && '--dry-run' || '' }}
|
||||
run: |
|
||||
cargo publish -p tfhe --token ${{ env.CRATES_TOKEN }} ${{ env.DRY_RUN }}
|
||||
cargo publish -p tfhe ${{ env.DRY_RUN }}
|
||||
|
||||
- name: Generate hash
|
||||
id: published_hash
|
||||
|
||||
11
.github/workflows/make_release_cuda.yml
vendored
@@ -115,6 +115,9 @@ jobs:
|
||||
name: Publish CUDA Release
|
||||
needs: [setup-instance, package] # for comparing hashes
|
||||
runs-on: ${{ needs.setup-instance.outputs.runner-name }}
|
||||
permissions:
|
||||
# Needed for OIDC token exchange on crates.io
|
||||
id-token: write
|
||||
strategy:
|
||||
fail-fast: false
|
||||
# explicit include-based build matrix, of known valid options
|
||||
@@ -152,12 +155,16 @@ jobs:
|
||||
echo "HOME=/home/ubuntu";
|
||||
} >> "${GITHUB_ENV}"
|
||||
|
||||
- name: Authenticate on registry
|
||||
uses: rust-lang/crates-io-auth-action@e919bc7605cde86df457cf5b93c5e103838bd879 # v1.0.1
|
||||
id: auth
|
||||
|
||||
- name: Publish crate.io package
|
||||
env:
|
||||
CRATES_TOKEN: ${{ secrets.CARGO_REGISTRY_TOKEN }}
|
||||
CARGO_REGISTRY_TOKEN: ${{ steps.auth.outputs.token }}
|
||||
DRY_RUN: ${{ inputs.dry_run && '--dry-run' || '' }}
|
||||
run: |
|
||||
cargo publish -p tfhe-cuda-backend --token ${{ env.CRATES_TOKEN }} ${{ env.DRY_RUN }}
|
||||
cargo publish -p tfhe-cuda-backend ${{ env.DRY_RUN }}
|
||||
|
||||
- name: Generate hash
|
||||
id: published_hash
|
||||
|
||||
12
.github/workflows/make_release_tfhe_csprng.yml
vendored
@@ -30,7 +30,7 @@ jobs:
|
||||
- name: Prepare package
|
||||
run: |
|
||||
cargo package -p tfhe-csprng
|
||||
- uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08 # v4.6.0
|
||||
- uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1 # v4.6.1
|
||||
with:
|
||||
name: crate-tfhe-csprng
|
||||
path: target/package/*.crate
|
||||
@@ -59,6 +59,9 @@ jobs:
|
||||
name: Publish tfhe-csprng Release
|
||||
needs: [verify_tag, package]
|
||||
runs-on: ubuntu-latest
|
||||
permissions:
|
||||
# Needed for OIDC token exchange on crates.io
|
||||
id-token: write
|
||||
steps:
|
||||
- name: Checkout
|
||||
uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
|
||||
@@ -70,12 +73,15 @@ jobs:
|
||||
with:
|
||||
name: crate-tfhe-csprng
|
||||
path: target/package
|
||||
- name: Authenticate on registry
|
||||
uses: rust-lang/crates-io-auth-action@e919bc7605cde86df457cf5b93c5e103838bd879 # v1.0.1
|
||||
id: auth
|
||||
- name: Publish crate.io package
|
||||
env:
|
||||
CRATES_TOKEN: ${{ secrets.CARGO_REGISTRY_TOKEN }}
|
||||
CARGO_REGISTRY_TOKEN: ${{ steps.auth.outputs.token }}
|
||||
DRY_RUN: ${{ inputs.dry_run && '--dry-run' || '' }}
|
||||
run: |
|
||||
cargo publish -p tfhe-csprng --token ${{ env.CRATES_TOKEN }} ${{ env.DRY_RUN }}
|
||||
cargo publish -p tfhe-csprng ${{ env.DRY_RUN }}
|
||||
- name: Generate hash
|
||||
id: published_hash
|
||||
run: cd target/package && echo "pub_hash=$(sha256sum ./*.crate | base64 -w0)" >> "${GITHUB_OUTPUT}"
|
||||
|
||||
13
.github/workflows/make_release_tfhe_fft.yml
vendored
@@ -33,7 +33,7 @@ jobs:
|
||||
- name: Prepare package
|
||||
run: |
|
||||
cargo package -p tfhe-fft
|
||||
- uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08 # v4.6.0
|
||||
- uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1 # v4.6.1
|
||||
with:
|
||||
name: crate
|
||||
path: target/package/*.crate
|
||||
@@ -60,6 +60,9 @@ jobs:
|
||||
name: Publish tfhe-fft Release
|
||||
runs-on: ubuntu-latest
|
||||
needs: [verify_tag, package] # for comparing hashes
|
||||
permissions:
|
||||
# Needed for OIDC token exchange on crates.io
|
||||
id-token: write
|
||||
steps:
|
||||
- name: Checkout
|
||||
uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
|
||||
@@ -67,12 +70,16 @@ jobs:
|
||||
fetch-depth: 0
|
||||
token: ${{ secrets.FHE_ACTIONS_TOKEN }}
|
||||
|
||||
- name: Authenticate on registry
|
||||
uses: rust-lang/crates-io-auth-action@e919bc7605cde86df457cf5b93c5e103838bd879 # v1.0.1
|
||||
id: auth
|
||||
|
||||
- name: Publish crate.io package
|
||||
env:
|
||||
CRATES_TOKEN: ${{ secrets.CARGO_REGISTRY_TOKEN }}
|
||||
CARGO_REGISTRY_TOKEN: ${{ steps.auth.outputs.token }}
|
||||
DRY_RUN: ${{ inputs.dry_run && '--dry-run' || '' }}
|
||||
run: |
|
||||
cargo publish -p tfhe-fft --token ${{ env.CRATES_TOKEN }} ${{ env.DRY_RUN }}
|
||||
cargo publish -p tfhe-fft ${{ env.DRY_RUN }}
|
||||
|
||||
- name: Generate hash
|
||||
id: published_hash
|
||||
|
||||
13
.github/workflows/make_release_tfhe_ntt.yml
vendored
@@ -33,7 +33,7 @@ jobs:
|
||||
- name: Prepare package
|
||||
run: |
|
||||
cargo package -p tfhe-ntt
|
||||
- uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08 # v4.6.0
|
||||
- uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1 # v4.6.1
|
||||
with:
|
||||
name: crate
|
||||
path: target/package/*.crate
|
||||
@@ -60,18 +60,25 @@ jobs:
|
||||
name: Publish tfhe-ntt Release
|
||||
runs-on: ubuntu-latest
|
||||
needs: [verify_tag, package] # for comparing hashes
|
||||
permissions:
|
||||
# Needed for OIDC token exchange on crates.io
|
||||
id-token: write
|
||||
steps:
|
||||
- name: Checkout
|
||||
uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
|
||||
with:
|
||||
fetch-depth: 0
|
||||
|
||||
- name: Authenticate on registry
|
||||
uses: rust-lang/crates-io-auth-action@e919bc7605cde86df457cf5b93c5e103838bd879 # v1.0.1
|
||||
id: auth
|
||||
|
||||
- name: Publish crate.io package
|
||||
env:
|
||||
CRATES_TOKEN: ${{ secrets.CARGO_REGISTRY_TOKEN }}
|
||||
CARGO_REGISTRY_TOKEN: ${{ steps.auth.outputs.token }}
|
||||
DRY_RUN: ${{ inputs.dry_run && '--dry-run' || '' }}
|
||||
run: |
|
||||
cargo publish -p tfhe-ntt --token ${{ env.CRATES_TOKEN }} ${{ env.DRY_RUN }}
|
||||
cargo publish -p tfhe-ntt ${{ env.DRY_RUN }}
|
||||
|
||||
- name: Generate hash
|
||||
id: published_hash
|
||||
|
||||
@@ -2,14 +2,13 @@ name: Publish tfhe-versionable release
|
||||
|
||||
on:
|
||||
workflow_dispatch:
|
||||
inputs:
|
||||
dry_run:
|
||||
description: "Dry-run"
|
||||
type: boolean
|
||||
default: true
|
||||
|
||||
env:
|
||||
ACTION_RUN_URL: ${{ github.server_url }}/${{ github.repository }}/actions/runs/${{ github.run_id }}
|
||||
SLACK_CHANNEL: ${{ secrets.SLACK_CHANNEL }}
|
||||
SLACK_ICON: https://pbs.twimg.com/profile_images/1274014582265298945/OjBKP9kn_400x400.png
|
||||
SLACK_USERNAME: ${{ secrets.BOT_USERNAME }}
|
||||
SLACK_WEBHOOK: ${{ secrets.SLACK_WEBHOOK }}
|
||||
|
||||
jobs:
|
||||
verify_tag:
|
||||
@@ -19,6 +18,7 @@ jobs:
|
||||
READ_ORG_TOKEN: ${{ secrets.READ_ORG_TOKEN }}
|
||||
|
||||
package-derive:
|
||||
name: Package tfhe-versionable-derive Release
|
||||
runs-on: ubuntu-latest
|
||||
outputs:
|
||||
hash: ${{ steps.hash.outputs.hash }}
|
||||
@@ -30,7 +30,7 @@ jobs:
|
||||
- name: Prepare package
|
||||
run: |
|
||||
cargo package -p tfhe-versionable-derive
|
||||
- uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08 # v4.6.0
|
||||
- uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1 # v4.6.1
|
||||
with:
|
||||
name: crate-tfhe-versionable-derive
|
||||
path: target/package/*.crate
|
||||
@@ -53,9 +53,12 @@ jobs:
|
||||
base64-subjects: ${{ needs.package-derive.outputs.hash }}
|
||||
|
||||
publish_release-derive:
|
||||
name: Publish tfhe-versionable Release
|
||||
needs: [verify_tag, package-derive] # for comparing hashes
|
||||
name: Publish tfhe-versionable-derive Release
|
||||
needs: [ verify_tag, package-derive ] # for comparing hashes
|
||||
runs-on: ubuntu-latest
|
||||
permissions:
|
||||
# Needed for OIDC token exchange on crates.io
|
||||
id-token: write
|
||||
steps:
|
||||
- name: Checkout
|
||||
uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
|
||||
@@ -68,11 +71,14 @@ jobs:
|
||||
with:
|
||||
name: crate-tfhe-versionable-derive
|
||||
path: target/package
|
||||
- name: Authenticate on registry
|
||||
uses: rust-lang/crates-io-auth-action@e919bc7605cde86df457cf5b93c5e103838bd879 # v1.0.1
|
||||
id: auth
|
||||
- name: Publish crate.io package
|
||||
env:
|
||||
CRATES_TOKEN: ${{ secrets.CARGO_REGISTRY_TOKEN }}
|
||||
CARGO_REGISTRY_TOKEN: ${{ steps.auth.outputs.token }}
|
||||
run: |
|
||||
cargo publish -p tfhe-versionable-derive --token ${{ env.CRATES_TOKEN }} ${{ env.DRY_RUN }}
|
||||
cargo publish -p tfhe-versionable-derive
|
||||
- name: Generate hash
|
||||
id: published_hash
|
||||
run: cd target/package && echo "pub_hash=$(sha256sum ./*.crate | base64 -w0)" >> "${GITHUB_OUTPUT}"
|
||||
@@ -82,24 +88,18 @@ jobs:
|
||||
uses: rtCamp/action-slack-notify@c33737706dea87cd7784c687dadc9adf1be59990 # v2.3.2
|
||||
env:
|
||||
SLACK_COLOR: failure
|
||||
SLACK_CHANNEL: ${{ secrets.SLACK_CHANNEL }}
|
||||
SLACK_ICON: https://pbs.twimg.com/profile_images/1274014582265298945/OjBKP9kn_400x400.png
|
||||
SLACK_MESSAGE: "SLSA tfhe-versionable-derive - hash comparison failure: (${{ env.ACTION_RUN_URL }})"
|
||||
SLACK_USERNAME: ${{ secrets.BOT_USERNAME }}
|
||||
SLACK_WEBHOOK: ${{ secrets.SLACK_WEBHOOK }}
|
||||
- name: Slack Notification
|
||||
if: ${{ failure() }}
|
||||
continue-on-error: true
|
||||
uses: rtCamp/action-slack-notify@c33737706dea87cd7784c687dadc9adf1be59990 # v2.3.2
|
||||
env:
|
||||
SLACK_COLOR: ${{ job.status }}
|
||||
SLACK_CHANNEL: ${{ secrets.SLACK_CHANNEL }}
|
||||
SLACK_ICON: https://pbs.twimg.com/profile_images/1274014582265298945/OjBKP9kn_400x400.png
|
||||
SLACK_MESSAGE: "tfhe-versionable-derive release finished with status: ${{ job.status }}. (${{ env.ACTION_RUN_URL }})"
|
||||
SLACK_USERNAME: ${{ secrets.BOT_USERNAME }}
|
||||
SLACK_WEBHOOK: ${{ secrets.SLACK_WEBHOOK }}
|
||||
|
||||
package:
|
||||
name: Package tfhe-versionable Release
|
||||
needs: publish_release-derive
|
||||
runs-on: ubuntu-latest
|
||||
outputs:
|
||||
hash: ${{ steps.hash.outputs.hash }}
|
||||
@@ -111,7 +111,7 @@ jobs:
|
||||
- name: Prepare package
|
||||
run: |
|
||||
cargo package -p tfhe-versionable
|
||||
- uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08 # v4.6.0
|
||||
- uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1 # v4.6.1
|
||||
with:
|
||||
name: crate-tfhe-versionable
|
||||
path: target/package/*.crate
|
||||
@@ -120,7 +120,7 @@ jobs:
|
||||
run: cd target/package && echo "hash=$(sha256sum ./*.crate | base64 -w0)" >> "${GITHUB_OUTPUT}"
|
||||
|
||||
provenance:
|
||||
needs: [package]
|
||||
needs: package
|
||||
uses: slsa-framework/slsa-github-generator/.github/workflows/generator_generic_slsa3.yml@v2.0.0
|
||||
permissions:
|
||||
# Needed to detect the GitHub Actions environment
|
||||
@@ -135,7 +135,7 @@ jobs:
|
||||
|
||||
publish_release:
|
||||
name: Publish tfhe-versionable Release
|
||||
needs: [package] # for comparing hashes
|
||||
needs: package # for comparing hashes
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Checkout
|
||||
@@ -147,36 +147,28 @@ jobs:
|
||||
with:
|
||||
name: crate-tfhe-versionable
|
||||
path: target/package
|
||||
- name: Authenticate on registry
|
||||
uses: rust-lang/crates-io-auth-action@e919bc7605cde86df457cf5b93c5e103838bd879 # v1.0.1
|
||||
id: auth
|
||||
- name: Publish crate.io package
|
||||
env:
|
||||
CRATES_TOKEN: ${{ secrets.CARGO_REGISTRY_TOKEN }}
|
||||
CARGO_REGISTRY_TOKEN: ${{ steps.auth.outputs.token }}
|
||||
run: |
|
||||
cargo publish -p tfhe-versionable --token ${{ env.CRATES_TOKEN }} ${{ env.DRY_RUN }}
|
||||
|
||||
cargo publish -p tfhe-versionable
|
||||
- name: Generate hash
|
||||
id: published_hash
|
||||
run: cd target/package && echo "pub_hash=$(sha256sum ./*.crate | base64 -w0)" >> "${GITHUB_OUTPUT}"
|
||||
|
||||
- name: Slack notification (hashes comparison)
|
||||
if: ${{ needs.package.outputs.hash != steps.published_hash.outputs.pub_hash }}
|
||||
continue-on-error: true
|
||||
uses: rtCamp/action-slack-notify@c33737706dea87cd7784c687dadc9adf1be59990 # v2.3.2
|
||||
env:
|
||||
SLACK_COLOR: failure
|
||||
SLACK_CHANNEL: ${{ secrets.SLACK_CHANNEL }}
|
||||
SLACK_ICON: https://pbs.twimg.com/profile_images/1274014582265298945/OjBKP9kn_400x400.png
|
||||
SLACK_MESSAGE: "SLSA tfhe-versionable - hash comparison failure: (${{ env.ACTION_RUN_URL }})"
|
||||
SLACK_USERNAME: ${{ secrets.BOT_USERNAME }}
|
||||
SLACK_WEBHOOK: ${{ secrets.SLACK_WEBHOOK }}
|
||||
|
||||
- name: Slack Notification
|
||||
if: ${{ failure() }}
|
||||
continue-on-error: true
|
||||
uses: rtCamp/action-slack-notify@c33737706dea87cd7784c687dadc9adf1be59990 # v2.3.2
|
||||
env:
|
||||
SLACK_COLOR: ${{ job.status }}
|
||||
SLACK_CHANNEL: ${{ secrets.SLACK_CHANNEL }}
|
||||
SLACK_ICON: https://pbs.twimg.com/profile_images/1274014582265298945/OjBKP9kn_400x400.png
|
||||
SLACK_MESSAGE: "tfhe-versionable release finished with status: ${{ job.status }}. (${{ env.ACTION_RUN_URL }})"
|
||||
SLACK_USERNAME: ${{ secrets.BOT_USERNAME }}
|
||||
SLACK_WEBHOOK: ${{ secrets.SLACK_WEBHOOK }}
|
||||
|
||||
12
.github/workflows/make_release_zk_pok.yml
vendored
@@ -24,7 +24,7 @@ jobs:
|
||||
- name: Prepare package
|
||||
run: |
|
||||
cargo package -p tfhe-zk-pok
|
||||
- uses: actions/upload-artifact@65c4c4a1ddee5b72f698fdd19549f0f0fb45cf08 # v4.6.0
|
||||
- uses: actions/upload-artifact@4cec3d8aa04e39d1a68397de0c4cd6fb9dce8ec1 # v4.6.1
|
||||
with:
|
||||
name: crate-zk-pok
|
||||
path: target/package/*.crate
|
||||
@@ -56,6 +56,9 @@ jobs:
|
||||
name: Publish tfhe-zk-pok Release
|
||||
needs: [verify_tag, package] # for comparing hashes
|
||||
runs-on: ubuntu-latest
|
||||
permissions:
|
||||
# Needed for OIDC token exchange on crates.io
|
||||
id-token: write
|
||||
steps:
|
||||
- name: Checkout
|
||||
uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
|
||||
@@ -68,12 +71,15 @@ jobs:
|
||||
with:
|
||||
name: crate-zk-pok
|
||||
path: target/package
|
||||
- name: Authenticate on registry
|
||||
uses: rust-lang/crates-io-auth-action@e919bc7605cde86df457cf5b93c5e103838bd879 # v1.0.1
|
||||
id: auth
|
||||
- name: Publish crate.io package
|
||||
env:
|
||||
CRATES_TOKEN: ${{ secrets.CARGO_REGISTRY_TOKEN }}
|
||||
CARGO_REGISTRY_TOKEN: ${{ steps.auth.outputs.token }}
|
||||
DRY_RUN: ${{ inputs.dry_run && '--dry-run' || '' }}
|
||||
run: |
|
||||
cargo publish -p tfhe-zk-pok --token ${{ env.CRATES_TOKEN }} ${{ env.DRY_RUN }}
|
||||
cargo publish -p tfhe-zk-pok ${{ env.DRY_RUN }}
|
||||
- name: Verify hash
|
||||
id: published_hash
|
||||
run: cd target/package && echo "pub_hash=$(sha256sum ./*.crate | base64 -w0)" >> "${GITHUB_OUTPUT}"
|
||||
|
||||
1
.gitignore
vendored
@@ -37,3 +37,4 @@ package-lock.json
|
||||
|
||||
# Dir used for backward compatibility test data
|
||||
tests/tfhe-backward-compat-data/
|
||||
ci/
|
||||
|
||||
233
CONTRIBUTING.md
Normal file
@@ -0,0 +1,233 @@
|
||||
# Contributing to TFHE-rs
|
||||
|
||||
This document provides guidance on how to contribute to **TFHE-rs**.
|
||||
|
||||
There are two ways to contribute:
|
||||
|
||||
- **Report issues:** Open issues on GitHub to report bugs, suggest improvements, or note typos.
|
||||
- **Submit codes**: To become an official contributor, you must sign our Contributor License Agreement (CLA). Our CLA-bot will guide you through this process when you open your first pull request.
|
||||
|
||||
## 1. Setting up the project
|
||||
|
||||
Start by [forking](https://docs.github.com/en/pull-requests/collaborating-with-pull-requests/working-with-forks/fork-a-repo) the **TFHE-rs** repository.
|
||||
|
||||
{% hint style="info" %}
|
||||
- **Rust version**: Ensure that you use a Rust version >= 1.81 to compile **TFHE-rs**.
|
||||
- **Incompatibility**: AArch64-based machines are not yet supported for Windows as it's currently missing an entropy source to be able to seed the [CSPRNGs](https://en.wikipedia.org/wiki/Cryptographically_secure_pseudorandom_number_generator) used in **TFHE-rs**.
|
||||
- **Performance**: For optimal performance, it is highly recommended to run **TFHE-rs** code in release mode with cargo's `--release` flag.
|
||||
{% endhint %}
|
||||
|
||||
To get more details about the library, please refer to the [documentation](https://docs.zama.ai/tfhe-rs).
|
||||
|
||||
## 2. Creating a new branch
|
||||
|
||||
When creating your branch, make sure to use the following format :
|
||||
|
||||
```
|
||||
git checkout -b {feat|fix|docs|chore…}/short_description
|
||||
```
|
||||
|
||||
For example:
|
||||
|
||||
```
|
||||
git checkout -b feat/new_feature_X
|
||||
```
|
||||
|
||||
## 3. Before committing
|
||||
|
||||
### 3.1 Linting
|
||||
|
||||
Each commit to **TFHE-rs** should conform to the standards of the project. In particular, every source code, docker or workflows files should be linted to prevent programmatic and stylistic errors.
|
||||
|
||||
- Rust source code linters: `clippy`
|
||||
- Typescript/Javascript source code linters: `eslint`, `prettier`
|
||||
|
||||
To apply automatic code formatting, run:
|
||||
|
||||
```
|
||||
make fmt
|
||||
```
|
||||
|
||||
You can perform linting of all Cargo targets with:
|
||||
|
||||
```
|
||||
make clippy_all_targets
|
||||
```
|
||||
|
||||
### 3.2 Testing
|
||||
|
||||
Your contributions must include comprehensive documentation and tests without breaking existing tests. To run pre-commit checks, execute:
|
||||
|
||||
```
|
||||
make pcc
|
||||
```
|
||||
|
||||
This command ensure that all the targets in the library are building correctly.
|
||||
For a faster check, use:
|
||||
|
||||
```
|
||||
make fpcc
|
||||
```
|
||||
|
||||
If you're contributing to GPU code, run also:
|
||||
|
||||
```
|
||||
make pcc_gpu
|
||||
```
|
||||
|
||||
Unit testing suites are heavy and can require a lot of computing power and RAM availability.
|
||||
Whilst tests are run automatically in continuous integration pipeline, you can run tests locally.
|
||||
|
||||
All unit tests have a command formatted as:
|
||||
|
||||
```
|
||||
make test_*
|
||||
```
|
||||
|
||||
Run `make help` to display a list of all the commands available.
|
||||
|
||||
To quickly test your changes locally, follow these steps:
|
||||
1. Locate where the code has changed.
|
||||
2. Add (or modify) a Cargo test filter to the corresponding `make` target in Makefile.
|
||||
3. Run the target.
|
||||
|
||||
{% hint style="success" %}
|
||||
`make test_<something>` will print the underlying cargo command in STDOUT. You can quickly test your changes by copy/pasting the command and then modify it to suit your needs.
|
||||
{% endhint %}
|
||||
|
||||
For example, if you made changes in `tfhe/src/integer/*`, you can test them with the following steps:
|
||||
1. In `test_integer` target, replace the filter `-- integer::` by `-- my_new_test`.
|
||||
2. Run `make test_integer`.
|
||||
|
||||
## 4. Committing
|
||||
|
||||
**TFHE-rs** follows the conventional commit specification to maintain a consistent commit history, essential for Semantic Versioning ([semver.org](https://semver.org/)).
|
||||
Commit messages are automatically checked in CI and will be rejected if they do not comply, so make sure that you follow the commit conventions detailed on [this page]
|
||||
(https://www.conventionalcommits.org/en/v1.0.0/).
|
||||
|
||||
## 5. Rebasing
|
||||
|
||||
Before creating a pull request, rebase your branch on the repository's `main` branch. Merge commits are not permitted, thus rebasing ensures fewer conflicts and a smoother PR review process.
|
||||
|
||||
## 6. Opening a Pull Request
|
||||
|
||||
Once your changes are ready, open a pull request.
|
||||
|
||||
For instructions on creating a PR from a fork, refer to GitHub's [official documentation](https://docs.github.com/en/pull-requests/collaborating-with-pull-requests/proposing-changes-to-your-work-with-pull-requests/creating-a-pull-request-from-a-fork).
|
||||
|
||||
## 7. Continuous integration
|
||||
|
||||
Before a pull request can be merged, several test suites run automatically. Below is an overview of the CI process:
|
||||
|
||||
```mermaid
|
||||
---
|
||||
title: Continuous Integration Process
|
||||
---
|
||||
sequenceDiagram
|
||||
autonumber
|
||||
|
||||
participant Contributor
|
||||
participant GitHub
|
||||
participant Reviewer
|
||||
participant CI-pipeline
|
||||
|
||||
Contributor ->> GitHub: Open pull-request
|
||||
GitHub -->> Contributor: Ask for CLA signing (once)
|
||||
loop
|
||||
Reviewer ->> GitHub: Review code
|
||||
Reviewer ->> CI-pipeline: Approve workflows (short-run)
|
||||
CI-pipeline -->> GitHub: Send checks results
|
||||
Contributor ->> GitHub: Make changes
|
||||
end
|
||||
Reviewer ->> GitHub: Pull-request approval
|
||||
Reviewer ->> CI-pipeline: Approve workflows (long-run)
|
||||
CI-pipeline -->> GitHub: Send checks results
|
||||
Reviewer -->> GitHub: Merge if pipeline green
|
||||
```
|
||||
|
||||
> [!Note]
|
||||
>Useful details:
|
||||
>* pipeline is triggered by humans
|
||||
>* review team is located in Paris timezone, pipeline launch will most likely happen during office hours
|
||||
>* direct changes to CI related files are not allowed for external contributors
|
||||
>* run `make pcc` to fix any build errors before pushing commits
|
||||
|
||||
## 8. Data versioning
|
||||
|
||||
Data serialized with TFHE-rs must remain backward compatible. This is done using the [tfhe-versionable](https://crates.io/crates/tfhe-versionable) crate.
|
||||
|
||||
If you modify a type that derives `Versionize` in a backward-incompatible way, an upgrade implementation must be provided.
|
||||
|
||||
For example, these changes are data breaking:
|
||||
* Adding a field to a struct.
|
||||
* Changing the order of the fields within a struct or the variants within an enum.
|
||||
* Renaming a field of a struct or a variant of an enum.
|
||||
* Changing the type of field in a struct or a variant in an enum.
|
||||
|
||||
On the contrary, these changes are *not* data breaking:
|
||||
* Renaming a type (unless it implements the `Named` trait).
|
||||
* Adding a variant to the end of an enum.
|
||||
|
||||
## Example: adding a field
|
||||
|
||||
Suppose you want to add an i32 field to a type named `MyType`. The original type is defined as:
|
||||
```rust
|
||||
#[derive(Serialize, Deserialize, Versionize)]
|
||||
#[versionize(MyTypeVersions)]
|
||||
struct MyType {
|
||||
val: u64,
|
||||
}
|
||||
```
|
||||
And you want to change it to:
|
||||
```rust
|
||||
#[derive(Serialize, Deserialize, Versionize)]
|
||||
#[versionize(MyTypeVersions)]
|
||||
struct MyType {
|
||||
val: u64,
|
||||
other_val: i32
|
||||
}
|
||||
```
|
||||
|
||||
Follow these steps:
|
||||
|
||||
1. Navigate to the definition of the dispatch enum of this type. This is the type inside the `#[versionize(MyTypeVersions)]` macro attribute. In general, this type has the same name as the base type with a `Versions` suffix. You should find something like
|
||||
|
||||
```rust
|
||||
#[derive(VersionsDispatch)]
|
||||
enum MyTypeVersions {
|
||||
V0(MyTypeV0),
|
||||
V1(MyType)
|
||||
}
|
||||
```
|
||||
|
||||
2. Add a new variant to the enum to preserve the previous version of the type. You can simply copy and paste the previous definition of the type and add a version suffix:
|
||||
|
||||
```rust
|
||||
#[derive(Version)]
|
||||
struct MyTypeV1 {
|
||||
val: u64,
|
||||
}
|
||||
|
||||
#[derive(VersionsDispatch)]
|
||||
enum MyTypeVersions {
|
||||
V0(MyTypeV0),
|
||||
V1(MyTypeV1),
|
||||
V2(MyType) // Here this points to your modified type
|
||||
}
|
||||
```
|
||||
|
||||
3. Implement the `Upgrade` trait to define how we should go from the previous version to the current version:
|
||||
```rust
|
||||
impl Upgrade<MyType> for MyTypeV1 {
|
||||
type Error = Infallible;
|
||||
|
||||
fn upgrade(self) -> Result<MyType, Self::Error> {
|
||||
Ok(MyType {
|
||||
val: self.val,
|
||||
other_val: 0
|
||||
})
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
4. Fix the upgrade target of the previous version. In this example, `impl Upgrade<MyType> for MyTypeV0 {` should simply be changed to `impl Upgrade<MyTypeV1> for MyTypeV0 {`
|
||||
@@ -21,9 +21,9 @@ bytemuck = "1.14.3"
|
||||
dyn-stack = { version = "0.11", default-features = false }
|
||||
itertools = "0.14"
|
||||
num-complex = "0.4"
|
||||
pulp = { version = "0.20", default-features = false }
|
||||
pulp = { version = ">=0.21, <0.21.5", default-features = false }
|
||||
rand = "0.8"
|
||||
rayon = "1"
|
||||
rayon = "1.11"
|
||||
serde = { version = "1.0", default-features = false }
|
||||
wasm-bindgen = "0.2.100"
|
||||
|
||||
|
||||
27
Makefile
@@ -18,6 +18,8 @@ FAST_BENCH?=FALSE
|
||||
NIGHTLY_TESTS?=FALSE
|
||||
BENCH_OP_FLAVOR?=DEFAULT
|
||||
BENCH_TYPE?=latency
|
||||
BENCH_PARAM_TYPE?=classical
|
||||
BENCH_PARAMS_SET?=default
|
||||
NODE_VERSION=22.6
|
||||
BACKWARD_COMPAT_DATA_URL=https://github.com/zama-ai/tfhe-backward-compat-data.git
|
||||
BACKWARD_COMPAT_DATA_BRANCH?=$(shell ./scripts/backward_compat_data_version.py)
|
||||
@@ -431,6 +433,7 @@ clippy_versionable: install_rs_check_toolchain
|
||||
.PHONY: clippy_tfhe_lints # Run clippy lints on tfhe-lints
|
||||
clippy_tfhe_lints: install_cargo_dylint # the toolchain is selected with toolchain.toml
|
||||
cd utils/tfhe-lints && \
|
||||
rustup toolchain install && \
|
||||
cargo clippy --all-targets -- --no-deps -D warnings
|
||||
|
||||
.PHONY: clippy_all # Run all clippy targets
|
||||
@@ -907,6 +910,7 @@ test_versionable: install_rs_build_toolchain
|
||||
.PHONY: test_tfhe_lints # Run test on tfhe-lints
|
||||
test_tfhe_lints: install_cargo_dylint
|
||||
cd utils/tfhe-lints && \
|
||||
rustup toolchain install && \
|
||||
cargo test
|
||||
|
||||
# The backward compat data repo holds historical binary data but also rust code to generate and load them.
|
||||
@@ -1171,10 +1175,24 @@ bench_boolean: install_rs_check_toolchain
|
||||
|
||||
.PHONY: bench_pbs # Run benchmarks for PBS
|
||||
bench_pbs: install_rs_check_toolchain
|
||||
RUSTFLAGS="$(RUSTFLAGS)" cargo $(CARGO_RS_CHECK_TOOLCHAIN) bench \
|
||||
RUSTFLAGS="$(RUSTFLAGS)" __TFHE_RS_PARAMS_SET=$(BENCH_PARAMS_SET) cargo $(CARGO_RS_CHECK_TOOLCHAIN) bench \
|
||||
--bench pbs-bench \
|
||||
--features=boolean,shortint,internal-keycache,nightly-avx512 -p $(TFHE_SPEC)
|
||||
|
||||
.PHONY: bench_ks_pbs # Run benchmarks for KS-PBS
|
||||
bench_ks_pbs: install_rs_check_toolchain
|
||||
RUSTFLAGS="$(RUSTFLAGS)" __TFHE_RS_PARAM_TYPE=$(BENCH_PARAM_TYPE) __TFHE_RS_PARAMS_SET=$(BENCH_PARAMS_SET) \
|
||||
cargo $(CARGO_RS_CHECK_TOOLCHAIN) bench \
|
||||
--bench ks-pbs-bench \
|
||||
--features=boolean,shortint,internal-keycache,nightly-avx512 -p $(TFHE_SPEC)
|
||||
|
||||
.PHONY: bench_ks_pbs_gpu # Run benchmarks for KS-PBS on GPU backend
|
||||
bench_ks_pbs_gpu: install_rs_check_toolchain
|
||||
RUSTFLAGS="$(RUSTFLAGS)" __TFHE_RS_PARAM_TYPE=$(BENCH_PARAM_TYPE) __TFHE_RS_PARAMS_SET=$(BENCH_PARAMS_SET) \
|
||||
cargo $(CARGO_RS_CHECK_TOOLCHAIN) bench \
|
||||
--bench ks-pbs-bench \
|
||||
--features=boolean,shortint,gpu,internal-keycache,nightly-avx512 -p $(TFHE_SPEC)
|
||||
|
||||
.PHONY: bench_pbs128 # Run benchmarks for PBS using FFT 128 bits
|
||||
bench_pbs128: install_rs_check_toolchain
|
||||
RUSTFLAGS="$(RUSTFLAGS)" cargo $(CARGO_RS_CHECK_TOOLCHAIN) bench \
|
||||
@@ -1183,19 +1201,20 @@ bench_pbs128: install_rs_check_toolchain
|
||||
|
||||
.PHONY: bench_pbs_gpu # Run benchmarks for PBS on GPU backend
|
||||
bench_pbs_gpu: install_rs_check_toolchain
|
||||
RUSTFLAGS="$(RUSTFLAGS)" __TFHE_RS_FAST_BENCH=$(FAST_BENCH) cargo $(CARGO_RS_CHECK_TOOLCHAIN) bench \
|
||||
RUSTFLAGS="$(RUSTFLAGS)" __TFHE_RS_FAST_BENCH=$(FAST_BENCH) __TFHE_RS_PARAMS_SET=$(BENCH_PARAMS_SET) \
|
||||
cargo $(CARGO_RS_CHECK_TOOLCHAIN) bench \
|
||||
--bench pbs-bench \
|
||||
--features=boolean,shortint,gpu,internal-keycache,nightly-avx512 -p $(TFHE_SPEC)
|
||||
|
||||
.PHONY: bench_ks # Run benchmarks for keyswitch
|
||||
bench_ks: install_rs_check_toolchain
|
||||
RUSTFLAGS="$(RUSTFLAGS)" cargo $(CARGO_RS_CHECK_TOOLCHAIN) bench \
|
||||
RUSTFLAGS="$(RUSTFLAGS)" __TFHE_RS_PARAMS_SET=$(BENCH_PARAMS_SET) cargo $(CARGO_RS_CHECK_TOOLCHAIN) bench \
|
||||
--bench ks-bench \
|
||||
--features=boolean,shortint,internal-keycache,nightly-avx512 -p $(TFHE_SPEC)
|
||||
|
||||
.PHONY: bench_ks_gpu # Run benchmarks for PBS on GPU backend
|
||||
bench_ks_gpu: install_rs_check_toolchain
|
||||
RUSTFLAGS="$(RUSTFLAGS)" cargo $(CARGO_RS_CHECK_TOOLCHAIN) bench \
|
||||
RUSTFLAGS="$(RUSTFLAGS)" __TFHE_RS_PARAMS_SET=$(BENCH_PARAMS_SET) cargo $(CARGO_RS_CHECK_TOOLCHAIN) bench \
|
||||
--bench ks-bench \
|
||||
--features=boolean,shortint,gpu,internal-keycache,nightly-avx512 -p $(TFHE_SPEC)
|
||||
|
||||
|
||||
36
README.md
@@ -10,7 +10,7 @@
|
||||
<hr/>
|
||||
|
||||
<p align="center">
|
||||
<a href="https://docs.zama.ai/tfhe-rs"> 📒 Documentation</a> | <a href="https://zama.ai/community"> 💛 Community support</a> | <a href="https://github.com/zama-ai/awesome-zama"> 📚 FHE resources by Zama</a>
|
||||
<a href="https://github.com/zama-ai/tfhe-rs-handbook/blob/main/tfhe-rs-handbook.pdf"> 📃 Read Handbook</a> |<a href="https://docs.zama.ai/tfhe-rs"> 📒 Documentation</a> | <a href="https://zama.ai/community"> 💛 Community support</a> | <a href="https://github.com/zama-ai/awesome-zama"> 📚 FHE resources by Zama</a>
|
||||
</p>
|
||||
|
||||
|
||||
@@ -67,6 +67,9 @@ production-ready library for all the advanced features of TFHE.
|
||||
|
||||
## Getting started
|
||||
|
||||
> [!Important]
|
||||
> **TFHE-rs** released its first stable version v1.0.0 in February 2025, stabilizing the high-level API for the x86 CPU backend.
|
||||
|
||||
### Cargo.toml configuration
|
||||
To use the latest version of `TFHE-rs` in your project, you first need to add it as a dependency in your `Cargo.toml`:
|
||||
|
||||
@@ -75,13 +78,13 @@ tfhe = { version = "*", features = ["boolean", "shortint", "integer"] }
|
||||
```
|
||||
|
||||
> [!Note]
|
||||
> Note: You need to use a Rust version >= 1.81 to compile TFHE-rs.
|
||||
> Note: You need to use Rust version >= 1.84 to compile TFHE-rs.
|
||||
|
||||
> [!Note]
|
||||
> Note: aarch64-based machines are not yet supported for Windows as it's currently missing an entropy source to be able to seed the [CSPRNGs](https://en.wikipedia.org/wiki/Cryptographically_secure_pseudorandom_number_generator) used in TFHE-rs.
|
||||
> Note: AArch64-based machines are not supported for Windows as it's currently missing an entropy source to be able to seed the [CSPRNGs](https://en.wikipedia.org/wiki/Cryptographically_secure_pseudorandom_number_generator) used in TFHE-rs.
|
||||
|
||||
<p align="right">
|
||||
<a href="#about" > ↑ Back to top </a>
|
||||
<a href="#about" > ↑ Back to top </a>
|
||||
</p>
|
||||
|
||||
### A simple example
|
||||
@@ -138,7 +141,7 @@ fn main() -> Result<(), Box<dyn std::error::Error>> {
|
||||
}
|
||||
```
|
||||
|
||||
To run this code, use the following command:
|
||||
To run this code, use the following command:
|
||||
<p align="center"> <code> cargo run --release </code> </p>
|
||||
|
||||
> [!Note]
|
||||
@@ -148,12 +151,15 @@ to run in release mode with cargo's `--release` flag to have the best performanc
|
||||
*Find an example with more explanations in [this part of the documentation](https://docs.zama.ai/tfhe-rs/get-started/quick_start)*
|
||||
|
||||
<p align="right">
|
||||
<a href="#about" > ↑ Back to top </a>
|
||||
<a href="#about" > ↑ Back to top </a>
|
||||
</p>
|
||||
|
||||
|
||||
|
||||
## Resources
|
||||
## Resources
|
||||
|
||||
### TFHE-rs Handbook
|
||||
A document containing scientific and technical details about algorithms implemented into the library is available here: [TFHE-rs: A (Practical) Handbook](https://github.com/zama-ai/tfhe-rs-handbook/blob/main/tfhe-rs-handbook.pdf).
|
||||
|
||||
### TFHE deep dive
|
||||
- [TFHE Deep Dive - Part I - Ciphertext types](https://www.zama.ai/post/tfhe-deep-dive-part-1)
|
||||
@@ -176,7 +182,7 @@ to run in release mode with cargo's `--release` flag to have the best performanc
|
||||
|
||||
Full, comprehensive documentation is available here: [https://docs.zama.ai/tfhe-rs](https://docs.zama.ai/tfhe-rs).
|
||||
<p align="right">
|
||||
<a href="#about" > ↑ Back to top </a>
|
||||
<a href="#about" > ↑ Back to top </a>
|
||||
</p>
|
||||
|
||||
|
||||
@@ -194,9 +200,13 @@ When a new update is published in the Lattice Estimator, we update parameters ac
|
||||
|
||||
### Security model
|
||||
|
||||
The default parameters for the TFHE-rs library are chosen considering the IND-CPA security model, and are selected with a bootstrapping failure probability fixed at p_error = $2^{-64}$. In particular, it is assumed that the results of decrypted computations are not shared by the secret key owner with any third parties, as such an action can lead to leakage of the secret encryption key. If you are designing an application where decryptions must be shared, you will need to craft custom encryption parameters which are chosen in consideration of the IND-CPA^D security model [1].
|
||||
By default, the parameter sets used in the High-Level API with the x86 CPU backend have a failure probability $\le 2^{128}$ to securely work in the IND-CPA^D model using the algorithmic techniques provided in our code base [1].
|
||||
If you want to work within the IND-CPA security model, which is less strict than the IND-CPA-D model, the parameter sets can easily be changed and would have slightly better performance. More details can be found in the [TFHE-rs documentation](https://docs.zama.ai/tfhe-rs).
|
||||
|
||||
[1] Li, Baiyu, et al. "Securing approximate homomorphic encryption using differential privacy." Annual International Cryptology Conference. Cham: Springer Nature Switzerland, 2022. https://eprint.iacr.org/2022/816.pdf
|
||||
The default parameters used in the High-Level API with the GPU backend are chosen considering the IND-CPA security model, and are selected with a bootstrapping failure probability fixed at $p_{error} \le 2^{-64}$. In particular, it is assumed that the results of decrypted computations are not shared by the secret key owner with any third parties, as such an action can lead to leakage of the secret encryption key. If you are designing an application where decryptions must be shared, you will need to craft custom encryption parameters which are chosen in consideration of the IND-CPA^D security model [2].
|
||||
|
||||
[1] Bernard, Olivier, et al. "Drifting Towards Better Error Probabilities in Fully Homomorphic Encryption Schemes". https://eprint.iacr.org/2024/1718.pdf
|
||||
[2] Li, Baiyu, et al. "Securing approximate homomorphic encryption using differential privacy." Annual International Cryptology Conference. Cham: Springer Nature Switzerland, 2022. https://eprint.iacr.org/2022/816.pdf
|
||||
|
||||
#### Side-channel attacks
|
||||
|
||||
@@ -245,7 +255,7 @@ This software is distributed under the **BSD-3-Clause-Clear** license. Read [thi
|
||||
>We are open to collaborating and advancing the FHE space with our partners. If you have specific needs, please email us at hello@zama.ai.
|
||||
|
||||
<p align="right">
|
||||
<a href="#about" > ↑ Back to top </a>
|
||||
<a href="#about" > ↑ Back to top </a>
|
||||
</p>
|
||||
|
||||
|
||||
@@ -259,8 +269,8 @@ This software is distributed under the **BSD-3-Clause-Clear** license. Read [thi
|
||||
</picture>
|
||||
</a>
|
||||
|
||||
🌟 If you find this project helpful or interesting, please consider giving it a star on GitHub! Your support helps to grow the community and motivates further development.
|
||||
🌟 If you find this project helpful or interesting, please consider giving it a star on GitHub! Your support helps to grow the community and motivates further development.
|
||||
|
||||
<p align="right">
|
||||
<a href="#about" > ↑ Back to top </a>
|
||||
<a href="#about" > ↑ Back to top </a>
|
||||
</p>
|
||||
|
||||
@@ -48,6 +48,8 @@ fn transcipher_from_1_1_stream(
|
||||
) -> FheUint64 {
|
||||
assert_eq!(stream.len(), 64);
|
||||
|
||||
let id_lut = internal_server_key.generate_lookup_table(|x| x);
|
||||
|
||||
let pairs = (0..32)
|
||||
.into_par_iter()
|
||||
.map(|i| {
|
||||
@@ -57,10 +59,11 @@ fn transcipher_from_1_1_stream(
|
||||
let b0 = &stream[8 * byte_idx + 2 * pair_idx];
|
||||
let b1 = &stream[8 * byte_idx + 2 * pair_idx + 1];
|
||||
|
||||
casting_key.cast(
|
||||
&internal_server_key
|
||||
.unchecked_add(b0, &internal_server_key.unchecked_scalar_mul(b1, 2)),
|
||||
)
|
||||
let mut combined = internal_server_key
|
||||
.unchecked_add(b0, &internal_server_key.unchecked_scalar_mul(b1, 2));
|
||||
internal_server_key.apply_lookup_table_assign(&mut combined, &id_lut);
|
||||
|
||||
casting_key.cast(&combined)
|
||||
})
|
||||
.collect::<Vec<_>>();
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
[package]
|
||||
name = "tfhe-cuda-backend"
|
||||
version = "0.8.0"
|
||||
version = "0.8.1"
|
||||
edition = "2021"
|
||||
authors = ["Zama team"]
|
||||
license = "BSD-3-Clause-Clear"
|
||||
|
||||
@@ -13,24 +13,26 @@ and forth between the CPU and the GPU, to create and destroy Cuda streams, etc.:
|
||||
- `cuda_get_number_of_gpus`
|
||||
- `cuda_synchronize_device`
|
||||
The cryptographic operations it provides are:
|
||||
- an amortized implementation of the TFHE programmable bootstrap: `cuda_bootstrap_amortized_lwe_ciphertext_vector_32` and `cuda_bootstrap_amortized_lwe_ciphertext_vector_64`
|
||||
- a low latency implementation of the TFHE programmable bootstrap: `cuda_bootstrap_low latency_lwe_ciphertext_vector_32` and `cuda_bootstrap_low_latency_lwe_ciphertext_vector_64`
|
||||
- the keyswitch: `cuda_keyswitch_lwe_ciphertext_vector_32` and `cuda_keyswitch_lwe_ciphertext_vector_64`
|
||||
- the larger precision programmable bootstrap (wop PBS, which supports up to 16 bits of message while the classical PBS only supports up to 8 bits of message) and its sub-components: `cuda_wop_pbs_64`, `cuda_extract_bits_64`, `cuda_circuit_bootstrap_64`, `cuda_cmux_tree_64`, `cuda_blind_rotation_sample_extraction_64`
|
||||
- acceleration for leveled operations: `cuda_negate_lwe_ciphertext_vector_64`, `cuda_add_lwe_ciphertext_vector_64`, `cuda_add_lwe_ciphertext_vector_plaintext_vector_64`, `cuda_mult_lwe_ciphertext_vector_cleartext_vector`.
|
||||
- an implementation of the classical TFHE programmable bootstrap,
|
||||
- an implementation of the multi-bit TFHE programmable bootstrap,
|
||||
- the keyswitch,
|
||||
- acceleration for leveled operations,
|
||||
- acceleration for arithmetics over encrypted integers of arbitrary size,
|
||||
- acceleration for integer compression/decompression.
|
||||
|
||||
## Dependencies
|
||||
|
||||
**Disclaimer**: Compilation on Windows/Mac is not supported yet. Only Nvidia GPUs are supported.
|
||||
|
||||
- nvidia driver - for example, if you're running Ubuntu 20.04 check this [page](https://linuxconfig.org/how-to-install-the-nvidia-drivers-on-ubuntu-20-04-focal-fossa-linux) for installation
|
||||
- nvidia driver - for example, if you're running Ubuntu 20.04 check this [page](https://linuxconfig.org/how-to-install-the-nvidia-drivers-on-ubuntu-20-04-focal-fossa-linux) for installation. You need an Nvidia GPU with Compute Capability >= 3.0
|
||||
- [nvcc](https://docs.nvidia.com/cuda/cuda-installation-guide-linux/index.html) >= 10.0
|
||||
- [gcc](https://gcc.gnu.org/) >= 8.0 - check this [page](https://gist.github.com/ax3l/9489132) for more details about nvcc/gcc compatible versions
|
||||
- [cmake](https://cmake.org/) >= 3.24
|
||||
- libclang, to match Rust bingen [requirements](https://rust-lang.github.io/rust-bindgen/requirements.html) >= 9.0
|
||||
|
||||
## Build
|
||||
|
||||
The Cuda project held in `tfhe-cuda-backend` can be compiled independently from TFHE-rs in the following way:
|
||||
The Cuda project held in `tfhe-cuda-backend` can be compiled independently of TFHE-rs in the following way:
|
||||
```
|
||||
git clone git@github.com:zama-ai/tfhe-rs
|
||||
cd backends/tfhe-cuda-backend/cuda
|
||||
|
||||
@@ -18,7 +18,7 @@ void cuda_convert_lwe_ciphertext_vector_to_cpu_64(void *stream,
|
||||
void cuda_glwe_sample_extract_64(void *stream, uint32_t gpu_index,
|
||||
void *lwe_array_out, void const *glwe_array_in,
|
||||
uint32_t const *nth_array, uint32_t num_nths,
|
||||
uint32_t glwe_dimension,
|
||||
uint32_t lwe_per_glwe, uint32_t glwe_dimension,
|
||||
uint32_t polynomial_size);
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -102,9 +102,7 @@ template <typename Torus> struct int_decompression {
|
||||
// Example: in the 2_2 case we are mapping a 2 bits message onto a 4 bits
|
||||
// space, we want to keep the original 2 bits value in the 4 bits space,
|
||||
// so we apply the identity and the encoding will rescale it for us.
|
||||
auto decompression_rescale_f = [encryption_params](Torus x) -> Torus {
|
||||
return x;
|
||||
};
|
||||
auto decompression_rescale_f = [](Torus x) -> Torus { return x; };
|
||||
|
||||
auto effective_compression_message_modulus =
|
||||
encryption_params.carry_modulus;
|
||||
|
||||
@@ -4728,4 +4728,5 @@ void update_degrees_after_scalar_bitxor(uint64_t *output_degrees,
|
||||
uint64_t *clear_degrees,
|
||||
uint64_t *input_degrees,
|
||||
uint32_t num_clear_blocks);
|
||||
std::pair<bool, bool> get_invert_flags(COMPARISON_TYPE compare);
|
||||
#endif // CUDA_INTEGER_UTILITIES_H
|
||||
|
||||
@@ -24,7 +24,7 @@ void cuda_convert_lwe_ciphertext_vector_to_cpu_64(void *stream,
|
||||
void cuda_glwe_sample_extract_64(void *stream, uint32_t gpu_index,
|
||||
void *lwe_array_out, void const *glwe_array_in,
|
||||
uint32_t const *nth_array, uint32_t num_nths,
|
||||
uint32_t glwe_dimension,
|
||||
uint32_t lwe_per_glwe, uint32_t glwe_dimension,
|
||||
uint32_t polynomial_size) {
|
||||
|
||||
switch (polynomial_size) {
|
||||
@@ -32,43 +32,43 @@ void cuda_glwe_sample_extract_64(void *stream, uint32_t gpu_index,
|
||||
host_sample_extract<uint64_t, AmortizedDegree<256>>(
|
||||
static_cast<cudaStream_t>(stream), gpu_index, (uint64_t *)lwe_array_out,
|
||||
(uint64_t const *)glwe_array_in, (uint32_t const *)nth_array, num_nths,
|
||||
glwe_dimension);
|
||||
lwe_per_glwe, glwe_dimension);
|
||||
break;
|
||||
case 512:
|
||||
host_sample_extract<uint64_t, AmortizedDegree<512>>(
|
||||
static_cast<cudaStream_t>(stream), gpu_index, (uint64_t *)lwe_array_out,
|
||||
(uint64_t const *)glwe_array_in, (uint32_t const *)nth_array, num_nths,
|
||||
glwe_dimension);
|
||||
lwe_per_glwe, glwe_dimension);
|
||||
break;
|
||||
case 1024:
|
||||
host_sample_extract<uint64_t, AmortizedDegree<1024>>(
|
||||
static_cast<cudaStream_t>(stream), gpu_index, (uint64_t *)lwe_array_out,
|
||||
(uint64_t const *)glwe_array_in, (uint32_t const *)nth_array, num_nths,
|
||||
glwe_dimension);
|
||||
lwe_per_glwe, glwe_dimension);
|
||||
break;
|
||||
case 2048:
|
||||
host_sample_extract<uint64_t, AmortizedDegree<2048>>(
|
||||
static_cast<cudaStream_t>(stream), gpu_index, (uint64_t *)lwe_array_out,
|
||||
(uint64_t const *)glwe_array_in, (uint32_t const *)nth_array, num_nths,
|
||||
glwe_dimension);
|
||||
lwe_per_glwe, glwe_dimension);
|
||||
break;
|
||||
case 4096:
|
||||
host_sample_extract<uint64_t, AmortizedDegree<4096>>(
|
||||
static_cast<cudaStream_t>(stream), gpu_index, (uint64_t *)lwe_array_out,
|
||||
(uint64_t const *)glwe_array_in, (uint32_t const *)nth_array, num_nths,
|
||||
glwe_dimension);
|
||||
lwe_per_glwe, glwe_dimension);
|
||||
break;
|
||||
case 8192:
|
||||
host_sample_extract<uint64_t, AmortizedDegree<8192>>(
|
||||
static_cast<cudaStream_t>(stream), gpu_index, (uint64_t *)lwe_array_out,
|
||||
(uint64_t const *)glwe_array_in, (uint32_t const *)nth_array, num_nths,
|
||||
glwe_dimension);
|
||||
lwe_per_glwe, glwe_dimension);
|
||||
break;
|
||||
case 16384:
|
||||
host_sample_extract<uint64_t, AmortizedDegree<16384>>(
|
||||
static_cast<cudaStream_t>(stream), gpu_index, (uint64_t *)lwe_array_out,
|
||||
(uint64_t const *)glwe_array_in, (uint32_t const *)nth_array, num_nths,
|
||||
glwe_dimension);
|
||||
lwe_per_glwe, glwe_dimension);
|
||||
break;
|
||||
default:
|
||||
PANIC("Cuda error: unsupported polynomial size. Supported "
|
||||
|
||||
@@ -28,7 +28,7 @@ void cuda_convert_lwe_ciphertext_vector_to_cpu(cudaStream_t stream,
|
||||
|
||||
template <typename Torus, class params>
|
||||
__global__ void sample_extract(Torus *lwe_array_out, Torus const *glwe_array_in,
|
||||
uint32_t const *nth_array,
|
||||
uint32_t const *nth_array, uint32_t lwe_per_glwe,
|
||||
uint32_t glwe_dimension) {
|
||||
|
||||
const int input_id = blockIdx.x;
|
||||
@@ -39,28 +39,28 @@ __global__ void sample_extract(Torus *lwe_array_out, Torus const *glwe_array_in,
|
||||
auto lwe_out = lwe_array_out + input_id * lwe_output_size;
|
||||
|
||||
// We assume each GLWE will store the first polynomial_size inputs
|
||||
uint32_t lwe_per_glwe = params::degree;
|
||||
auto glwe_in = glwe_array_in + (input_id / lwe_per_glwe) * glwe_input_size;
|
||||
|
||||
// nth is ensured to be in [0, lwe_per_glwe)
|
||||
auto nth = nth_array[input_id] % lwe_per_glwe;
|
||||
// nth is ensured to be in [0, params::degree)
|
||||
auto nth = nth_array[input_id] % params::degree;
|
||||
|
||||
sample_extract_mask<Torus, params>(lwe_out, glwe_in, glwe_dimension, nth);
|
||||
sample_extract_body<Torus, params>(lwe_out, glwe_in, glwe_dimension, nth);
|
||||
}
|
||||
|
||||
// lwe_per_glwe LWEs will be extracted per GLWE ciphertext, thus we need to have
|
||||
// enough indexes
|
||||
template <typename Torus, class params>
|
||||
__host__ void host_sample_extract(cudaStream_t stream, uint32_t gpu_index,
|
||||
Torus *lwe_array_out,
|
||||
Torus const *glwe_array_in,
|
||||
uint32_t const *nth_array, uint32_t num_nths,
|
||||
uint32_t glwe_dimension) {
|
||||
__host__ void
|
||||
host_sample_extract(cudaStream_t stream, uint32_t gpu_index,
|
||||
Torus *lwe_array_out, Torus const *glwe_array_in,
|
||||
uint32_t const *nth_array, uint32_t num_nths,
|
||||
uint32_t lwe_per_glwe, uint32_t glwe_dimension) {
|
||||
cuda_set_device(gpu_index);
|
||||
|
||||
dim3 grid(num_nths);
|
||||
dim3 thds(params::degree / params::opt);
|
||||
sample_extract<Torus, params><<<grid, thds, 0, stream>>>(
|
||||
lwe_array_out, glwe_array_in, nth_array, glwe_dimension);
|
||||
lwe_array_out, glwe_array_in, nth_array, lwe_per_glwe, glwe_dimension);
|
||||
check_cuda_error(cudaGetLastError());
|
||||
}
|
||||
|
||||
|
||||
@@ -43,6 +43,9 @@ __global__ void pack(Torus *array_out, Torus *array_in, uint32_t log_modulus,
|
||||
}
|
||||
}
|
||||
|
||||
/// Packs `num_lwes` LWE-ciphertext contained in `num_glwes` GLWE-ciphertext in
|
||||
/// a compressed array This function follows the naming used in the CPU
|
||||
/// implementation
|
||||
template <typename Torus>
|
||||
__host__ void host_pack(cudaStream_t stream, uint32_t gpu_index,
|
||||
Torus *array_out, Torus *array_in, uint32_t num_glwes,
|
||||
@@ -55,26 +58,23 @@ __host__ void host_pack(cudaStream_t stream, uint32_t gpu_index,
|
||||
|
||||
auto log_modulus = mem_ptr->storage_log_modulus;
|
||||
// [0..num_glwes-1) GLWEs
|
||||
auto in_len = (compression_params.glwe_dimension + 1) *
|
||||
compression_params.polynomial_size;
|
||||
auto in_len = num_glwes * compression_params.glwe_dimension *
|
||||
compression_params.polynomial_size +
|
||||
num_lwes;
|
||||
|
||||
auto number_bits_to_pack = in_len * log_modulus;
|
||||
auto nbits = sizeof(Torus) * 8;
|
||||
|
||||
// number_bits_to_pack.div_ceil(Scalar::BITS)
|
||||
auto nbits = sizeof(Torus) * 8;
|
||||
auto out_len = (number_bits_to_pack + nbits - 1) / nbits;
|
||||
|
||||
// Last GLWE
|
||||
number_bits_to_pack = in_len * log_modulus;
|
||||
auto last_out_len = (number_bits_to_pack + nbits - 1) / nbits;
|
||||
|
||||
auto num_coeffs = (num_glwes - 1) * out_len + last_out_len;
|
||||
|
||||
int num_blocks = 0, num_threads = 0;
|
||||
getNumBlocksAndThreads(num_coeffs, 1024, num_blocks, num_threads);
|
||||
getNumBlocksAndThreads(out_len, 1024, num_blocks, num_threads);
|
||||
|
||||
dim3 grid(num_blocks);
|
||||
dim3 threads(num_threads);
|
||||
pack<Torus><<<grid, threads, 0, stream>>>(array_out, array_in, log_modulus,
|
||||
num_coeffs, in_len, out_len);
|
||||
out_len, in_len, out_len);
|
||||
check_cuda_error(cudaGetLastError());
|
||||
}
|
||||
|
||||
@@ -99,14 +99,13 @@ host_integer_compress(cudaStream_t const *streams, uint32_t const *gpu_indexes,
|
||||
uint32_t lwe_in_size = input_lwe_dimension + 1;
|
||||
uint32_t glwe_out_size = (compression_params.glwe_dimension + 1) *
|
||||
compression_params.polynomial_size;
|
||||
uint32_t num_glwes_for_compression =
|
||||
num_radix_blocks / mem_ptr->lwe_per_glwe + 1;
|
||||
uint32_t num_glwes =
|
||||
(num_radix_blocks + mem_ptr->lwe_per_glwe - 1) / mem_ptr->lwe_per_glwe;
|
||||
|
||||
// Keyswitch LWEs to GLWE
|
||||
auto tmp_glwe_array_out = mem_ptr->tmp_glwe_array_out;
|
||||
cuda_memset_async(tmp_glwe_array_out, 0,
|
||||
num_glwes_for_compression *
|
||||
(compression_params.glwe_dimension + 1) *
|
||||
num_glwes * (compression_params.glwe_dimension + 1) *
|
||||
compression_params.polynomial_size * sizeof(Torus),
|
||||
streams[0], gpu_indexes[0]);
|
||||
auto fp_ks_buffer = mem_ptr->fp_ks_buffer;
|
||||
@@ -131,23 +130,21 @@ host_integer_compress(cudaStream_t const *streams, uint32_t const *gpu_indexes,
|
||||
// Modulus switch
|
||||
host_modulus_switch_inplace<Torus>(
|
||||
streams[0], gpu_indexes[0], tmp_glwe_array_out,
|
||||
num_glwes_for_compression * (compression_params.glwe_dimension + 1) *
|
||||
compression_params.polynomial_size,
|
||||
num_glwes * compression_params.glwe_dimension *
|
||||
compression_params.polynomial_size +
|
||||
num_radix_blocks,
|
||||
mem_ptr->storage_log_modulus);
|
||||
|
||||
host_pack<Torus>(streams[0], gpu_indexes[0], glwe_array_out,
|
||||
tmp_glwe_array_out, num_glwes_for_compression,
|
||||
num_radix_blocks, mem_ptr);
|
||||
tmp_glwe_array_out, num_glwes, num_radix_blocks, mem_ptr);
|
||||
}
|
||||
|
||||
template <typename Torus>
|
||||
__global__ void extract(Torus *glwe_array_out, Torus const *array_in,
|
||||
uint32_t index, uint32_t log_modulus,
|
||||
uint32_t input_len, uint32_t initial_out_len) {
|
||||
uint32_t log_modulus, uint32_t initial_out_len) {
|
||||
auto nbits = sizeof(Torus) * 8;
|
||||
|
||||
auto i = threadIdx.x + blockIdx.x * blockDim.x;
|
||||
auto chunk_array_in = array_in + index * input_len;
|
||||
if (i < initial_out_len) {
|
||||
// Unpack
|
||||
Torus mask = ((Torus)1 << log_modulus) - 1;
|
||||
@@ -161,12 +158,11 @@ __global__ void extract(Torus *glwe_array_out, Torus const *array_in,
|
||||
|
||||
Torus unpacked_i;
|
||||
if (start_block == end_block_inclusive) {
|
||||
auto single_part = chunk_array_in[start_block] >> start_remainder;
|
||||
auto single_part = array_in[start_block] >> start_remainder;
|
||||
unpacked_i = single_part & mask;
|
||||
} else {
|
||||
auto first_part = chunk_array_in[start_block] >> start_remainder;
|
||||
auto second_part = chunk_array_in[start_block + 1]
|
||||
<< (nbits - start_remainder);
|
||||
auto first_part = array_in[start_block] >> start_remainder;
|
||||
auto second_part = array_in[start_block + 1] << (nbits - start_remainder);
|
||||
|
||||
unpacked_i = (first_part | second_part) & mask;
|
||||
}
|
||||
@@ -177,6 +173,7 @@ __global__ void extract(Torus *glwe_array_out, Torus const *array_in,
|
||||
}
|
||||
|
||||
/// Extracts the glwe_index-nth GLWE ciphertext
|
||||
/// This function follows the naming used in the CPU implementation
|
||||
template <typename Torus>
|
||||
__host__ void host_extract(cudaStream_t stream, uint32_t gpu_index,
|
||||
Torus *glwe_array_out, Torus const *array_in,
|
||||
@@ -188,36 +185,51 @@ __host__ void host_extract(cudaStream_t stream, uint32_t gpu_index,
|
||||
cuda_set_device(gpu_index);
|
||||
|
||||
auto compression_params = mem_ptr->compression_params;
|
||||
|
||||
auto log_modulus = mem_ptr->storage_log_modulus;
|
||||
auto glwe_ciphertext_size = (compression_params.glwe_dimension + 1) *
|
||||
compression_params.polynomial_size;
|
||||
|
||||
uint32_t body_count = mem_ptr->body_count;
|
||||
auto num_glwes = (body_count + compression_params.polynomial_size - 1) /
|
||||
compression_params.polynomial_size;
|
||||
|
||||
// Compressed length of the compressed GLWE we want to extract
|
||||
if (mem_ptr->body_count % compression_params.polynomial_size == 0)
|
||||
body_count = compression_params.polynomial_size;
|
||||
else if (glwe_index == num_glwes - 1)
|
||||
body_count = mem_ptr->body_count % compression_params.polynomial_size;
|
||||
else
|
||||
body_count = compression_params.polynomial_size;
|
||||
|
||||
uint32_t body_count =
|
||||
std::min(mem_ptr->body_count, compression_params.polynomial_size);
|
||||
auto initial_out_len =
|
||||
compression_params.glwe_dimension * compression_params.polynomial_size +
|
||||
body_count;
|
||||
|
||||
auto compressed_glwe_accumulator_size =
|
||||
(compression_params.glwe_dimension + 1) *
|
||||
compression_params.polynomial_size;
|
||||
auto number_bits_to_unpack = compressed_glwe_accumulator_size * log_modulus;
|
||||
// Calculates how many bits this particular GLWE shall use
|
||||
auto number_bits_to_unpack = initial_out_len * log_modulus;
|
||||
auto nbits = sizeof(Torus) * 8;
|
||||
// number_bits_to_unpack.div_ceil(Scalar::BITS)
|
||||
auto input_len = (number_bits_to_unpack + nbits - 1) / nbits;
|
||||
|
||||
// We assure the tail of the glwe is zeroed
|
||||
auto zeroed_slice = glwe_array_out + initial_out_len;
|
||||
cuda_memset_async(zeroed_slice, 0,
|
||||
(compression_params.polynomial_size - body_count) *
|
||||
sizeof(Torus),
|
||||
stream, gpu_index);
|
||||
// Calculates how many bits a full-packed GLWE shall use
|
||||
number_bits_to_unpack = glwe_ciphertext_size * log_modulus;
|
||||
auto len = (number_bits_to_unpack + nbits - 1) / nbits;
|
||||
// Uses that length to set the input pointer
|
||||
auto chunk_array_in = array_in + glwe_index * len;
|
||||
|
||||
// Ensure the tail of the GLWE is zeroed
|
||||
if (initial_out_len < glwe_ciphertext_size) {
|
||||
auto zeroed_slice = glwe_array_out + initial_out_len;
|
||||
cuda_memset_async(glwe_array_out, 0,
|
||||
(glwe_ciphertext_size - initial_out_len) * sizeof(Torus),
|
||||
stream, gpu_index);
|
||||
}
|
||||
|
||||
int num_blocks = 0, num_threads = 0;
|
||||
getNumBlocksAndThreads(initial_out_len, 128, num_blocks, num_threads);
|
||||
dim3 grid(num_blocks);
|
||||
dim3 threads(num_threads);
|
||||
extract<Torus><<<grid, threads, 0, stream>>>(glwe_array_out, array_in,
|
||||
glwe_index, log_modulus,
|
||||
input_len, initial_out_len);
|
||||
extract<Torus><<<grid, threads, 0, stream>>>(glwe_array_out, chunk_array_in,
|
||||
log_modulus, initial_out_len);
|
||||
check_cuda_error(cudaGetLastError());
|
||||
}
|
||||
|
||||
@@ -235,18 +247,13 @@ __host__ void host_integer_decompress(
|
||||
|
||||
auto compression_params = h_mem_ptr->compression_params;
|
||||
auto lwe_per_glwe = compression_params.polynomial_size;
|
||||
if (indexes_array_size > lwe_per_glwe)
|
||||
PANIC("Cuda error: too many LWEs to decompress. The number of LWEs should "
|
||||
"be smaller than "
|
||||
"polynomial_size.")
|
||||
|
||||
auto num_radix_blocks = h_mem_ptr->num_radix_blocks;
|
||||
if (num_radix_blocks != indexes_array_size)
|
||||
PANIC("Cuda error: wrong number of LWEs in decompress: the number of LWEs "
|
||||
"should be the same as indexes_array_size.")
|
||||
|
||||
// the first element is the last index in h_indexes_array that lies in the
|
||||
// related GLWE
|
||||
// the first element is the number of LWEs that lies in the related GLWE
|
||||
std::vector<std::pair<int, Torus *>> glwe_vec;
|
||||
|
||||
// Extract all GLWEs
|
||||
@@ -257,7 +264,7 @@ __host__ void host_integer_decompress(
|
||||
auto extracted_glwe = h_mem_ptr->tmp_extracted_glwe;
|
||||
host_extract<Torus>(streams[0], gpu_indexes[0], extracted_glwe,
|
||||
d_packed_glwe_in, current_glwe_index, h_mem_ptr);
|
||||
glwe_vec.push_back(std::make_pair(0, extracted_glwe));
|
||||
glwe_vec.push_back(std::make_pair(1, extracted_glwe));
|
||||
for (int i = 1; i < indexes_array_size; i++) {
|
||||
auto glwe_index = h_indexes_array[i] / lwe_per_glwe;
|
||||
if (glwe_index != current_glwe_index) {
|
||||
@@ -266,10 +273,10 @@ __host__ void host_integer_decompress(
|
||||
// Extracts a new GLWE
|
||||
host_extract<Torus>(streams[0], gpu_indexes[0], extracted_glwe,
|
||||
d_packed_glwe_in, glwe_index, h_mem_ptr);
|
||||
glwe_vec.push_back(std::make_pair(i, extracted_glwe));
|
||||
glwe_vec.push_back(std::make_pair(1, extracted_glwe));
|
||||
} else {
|
||||
// Updates the index
|
||||
glwe_vec.back().first++;
|
||||
// Updates the quantity
|
||||
++glwe_vec.back().first;
|
||||
}
|
||||
}
|
||||
// Sample extract all LWEs
|
||||
@@ -279,17 +286,16 @@ __host__ void host_integer_decompress(
|
||||
uint32_t current_idx = 0;
|
||||
auto d_indexes_array_chunk = d_indexes_array;
|
||||
for (const auto &max_idx_and_glwe : glwe_vec) {
|
||||
uint32_t last_idx = max_idx_and_glwe.first;
|
||||
const auto num_lwes = max_idx_and_glwe.first;
|
||||
extracted_glwe = max_idx_and_glwe.second;
|
||||
|
||||
auto num_lwes = last_idx + 1 - current_idx;
|
||||
cuda_glwe_sample_extract_64(streams[0], gpu_indexes[0], extracted_lwe,
|
||||
extracted_glwe, d_indexes_array_chunk, num_lwes,
|
||||
compression_params.glwe_dimension,
|
||||
compression_params.polynomial_size);
|
||||
cuda_glwe_sample_extract_64(
|
||||
streams[0], gpu_indexes[0], extracted_lwe, extracted_glwe,
|
||||
d_indexes_array_chunk, num_lwes, compression_params.polynomial_size,
|
||||
compression_params.glwe_dimension, compression_params.polynomial_size);
|
||||
d_indexes_array_chunk += num_lwes;
|
||||
extracted_lwe += num_lwes * lwe_accumulator_size;
|
||||
current_idx = last_idx;
|
||||
current_idx += num_lwes;
|
||||
}
|
||||
|
||||
// Reset
|
||||
|
||||
@@ -575,8 +575,8 @@ __host__ void host_unsigned_integer_div_rem_kb(
|
||||
cuda_synchronize_stream(mem_ptr->sub_streams_3[j], gpu_indexes[j]);
|
||||
}
|
||||
|
||||
assert(first_trivial_block - 1 == cleaned_merged_interesting_remainder.len);
|
||||
assert(first_trivial_block - 1 == new_remainder.len);
|
||||
assert(first_trivial_block == cleaned_merged_interesting_remainder.len);
|
||||
assert(first_trivial_block == new_remainder.len);
|
||||
|
||||
remainder1.copy_from(cleaned_merged_interesting_remainder, 0,
|
||||
first_trivial_block - 1, streams[0], gpu_indexes[0]);
|
||||
|
||||
@@ -1,5 +1,36 @@
|
||||
#include "integer/scalar_comparison.cuh"
|
||||
|
||||
#include <iostream>
|
||||
#include <utility> // for std::pair
|
||||
|
||||
std::pair<bool, bool> get_invert_flags(COMPARISON_TYPE compare) {
|
||||
bool invert_operands;
|
||||
bool invert_subtraction_result;
|
||||
|
||||
switch (compare) {
|
||||
case COMPARISON_TYPE::LT:
|
||||
invert_operands = false;
|
||||
invert_subtraction_result = false;
|
||||
break;
|
||||
case COMPARISON_TYPE::LE:
|
||||
invert_operands = true;
|
||||
invert_subtraction_result = true;
|
||||
break;
|
||||
case COMPARISON_TYPE::GT:
|
||||
invert_operands = true;
|
||||
invert_subtraction_result = false;
|
||||
break;
|
||||
case COMPARISON_TYPE::GE:
|
||||
invert_operands = false;
|
||||
invert_subtraction_result = true;
|
||||
break;
|
||||
default:
|
||||
PANIC("Cuda error: invalid comparison type")
|
||||
}
|
||||
|
||||
return {invert_operands, invert_subtraction_result};
|
||||
}
|
||||
|
||||
void cuda_scalar_comparison_integer_radix_ciphertext_kb_64(
|
||||
void *const *streams, uint32_t const *gpu_indexes, uint32_t gpu_count,
|
||||
void *lwe_array_out, void const *lwe_array_in, void const *scalar_blocks,
|
||||
@@ -22,9 +53,9 @@ void cuda_scalar_comparison_integer_radix_ciphertext_kb_64(
|
||||
case GE:
|
||||
case LT:
|
||||
case LE:
|
||||
if (lwe_ciphertext_count % 2 != 0)
|
||||
if (lwe_ciphertext_count % 2 != 0 && lwe_ciphertext_count != 1)
|
||||
PANIC("Cuda error (scalar comparisons): the number of radix blocks has "
|
||||
"to be even.")
|
||||
"to be even or equal to 1.")
|
||||
host_integer_radix_scalar_difference_check_kb<uint64_t>(
|
||||
(cudaStream_t *)(streams), gpu_indexes, gpu_count,
|
||||
static_cast<uint64_t *>(lwe_array_out),
|
||||
|
||||
@@ -2,6 +2,27 @@
|
||||
#define CUDA_INTEGER_SCALAR_COMPARISON_OPS_CUH
|
||||
|
||||
#include "integer/comparison.cuh"
|
||||
template <typename Torus>
|
||||
Torus is_x_less_than_y_given_input_borrow(Torus last_x_block,
|
||||
Torus last_y_block, Torus borrow,
|
||||
uint32_t message_modulus) {
|
||||
Torus last_bit_pos = log2_int(message_modulus) - 1;
|
||||
Torus mask = (1 << last_bit_pos) - 1;
|
||||
Torus x_without_last_bit = last_x_block & mask;
|
||||
Torus y_without_last_bit = last_y_block & mask;
|
||||
|
||||
bool input_borrow_to_last_bit =
|
||||
x_without_last_bit < (y_without_last_bit + borrow);
|
||||
|
||||
Torus result = last_x_block - (last_y_block + borrow);
|
||||
|
||||
Torus output_sign_bit = (result >> last_bit_pos) & 1;
|
||||
bool output_borrow = last_x_block < (last_y_block + borrow);
|
||||
|
||||
Torus overflow_flag = (Torus)(input_borrow_to_last_bit ^ output_borrow);
|
||||
|
||||
return output_sign_bit ^ overflow_flag;
|
||||
}
|
||||
|
||||
template <typename Torus>
|
||||
__host__ void scalar_compare_radix_blocks_kb(
|
||||
@@ -205,42 +226,79 @@ __host__ void integer_radix_unsigned_scalar_difference_check_kb(
|
||||
lwe_array_msb_out, bsks, ksks, 1, lut, lut->params.message_modulus);
|
||||
|
||||
} else {
|
||||
// We only have to do the regular comparison
|
||||
// And not the part where we compare most significant blocks with zeros
|
||||
// total_num_radix_blocks == total_num_scalar_blocks
|
||||
uint32_t num_lsb_radix_blocks = total_num_radix_blocks;
|
||||
uint32_t num_scalar_blocks = total_num_scalar_blocks;
|
||||
if (total_num_radix_blocks == 1) {
|
||||
std::pair<bool, bool> invert_flags = get_invert_flags(mem_ptr->op);
|
||||
Torus scalar = 0;
|
||||
cuda_memcpy_async_to_cpu(&scalar, scalar_blocks, sizeof(Torus),
|
||||
streams[0], gpu_indexes[0]);
|
||||
cuda_synchronize_stream(streams[0], gpu_indexes[0]);
|
||||
auto one_block_lut_f = [invert_flags, scalar](Torus x) -> Torus {
|
||||
Torus x_0;
|
||||
Torus x_1;
|
||||
if (invert_flags.first) {
|
||||
x_0 = scalar;
|
||||
x_1 = x;
|
||||
} else {
|
||||
x_0 = x;
|
||||
x_1 = scalar;
|
||||
}
|
||||
auto overflowed = x_0 < x_1;
|
||||
return (Torus)(invert_flags.second ^ overflowed);
|
||||
};
|
||||
int_radix_lut<Torus> *one_block_lut = new int_radix_lut<Torus>(
|
||||
streams, gpu_indexes, gpu_count, params, 1, 1, true);
|
||||
|
||||
Torus *lhs = diff_buffer->tmp_packed;
|
||||
Torus *rhs =
|
||||
diff_buffer->tmp_packed + total_num_radix_blocks / 2 * big_lwe_size;
|
||||
generate_device_accumulator<Torus>(
|
||||
streams[0], gpu_indexes[0], one_block_lut->get_lut(0, 0),
|
||||
one_block_lut->get_degree(0), one_block_lut->get_max_degree(0),
|
||||
params.glwe_dimension, params.polynomial_size, params.message_modulus,
|
||||
params.carry_modulus, one_block_lut_f);
|
||||
|
||||
pack_blocks<Torus>(streams[0], gpu_indexes[0], lhs, lwe_array_in,
|
||||
big_lwe_dimension, num_lsb_radix_blocks,
|
||||
message_modulus);
|
||||
pack_blocks<Torus>(streams[0], gpu_indexes[0], rhs, scalar_blocks, 0,
|
||||
num_scalar_blocks, message_modulus);
|
||||
one_block_lut->broadcast_lut(streams, gpu_indexes, 0);
|
||||
|
||||
// From this point we have half number of blocks
|
||||
num_lsb_radix_blocks /= 2;
|
||||
num_scalar_blocks /= 2;
|
||||
legacy_integer_radix_apply_univariate_lookup_table_kb<Torus>(
|
||||
streams, gpu_indexes, gpu_count, lwe_array_out, lwe_array_in, bsks,
|
||||
ksks, 1, one_block_lut);
|
||||
one_block_lut->release(streams, gpu_indexes, gpu_count);
|
||||
delete one_block_lut;
|
||||
} else {
|
||||
// We only have to do the regular comparison
|
||||
// And not the part where we compare most significant blocks with zeros
|
||||
// total_num_radix_blocks == total_num_scalar_blocks
|
||||
uint32_t num_lsb_radix_blocks = total_num_radix_blocks;
|
||||
uint32_t num_scalar_blocks = total_num_scalar_blocks;
|
||||
|
||||
// comparisons will be assigned
|
||||
// - 0 if lhs < rhs
|
||||
// - 1 if lhs == rhs
|
||||
// - 2 if lhs > rhs
|
||||
auto comparisons = mem_ptr->tmp_lwe_array_out;
|
||||
scalar_compare_radix_blocks_kb<Torus>(streams, gpu_indexes, gpu_count,
|
||||
comparisons, lhs, rhs, mem_ptr, bsks,
|
||||
ksks, num_lsb_radix_blocks);
|
||||
Torus *lhs = diff_buffer->tmp_packed;
|
||||
Torus *rhs =
|
||||
diff_buffer->tmp_packed + total_num_radix_blocks / 2 * big_lwe_size;
|
||||
|
||||
// Reduces a vec containing radix blocks that encrypts a sign
|
||||
// (inferior, equal, superior) to one single radix block containing the
|
||||
// final sign
|
||||
tree_sign_reduction<Torus>(streams, gpu_indexes, gpu_count, lwe_array_out,
|
||||
comparisons, mem_ptr->diff_buffer->tree_buffer,
|
||||
sign_handler_f, bsks, ksks,
|
||||
num_lsb_radix_blocks);
|
||||
pack_blocks<Torus>(streams[0], gpu_indexes[0], lhs, lwe_array_in,
|
||||
big_lwe_dimension, num_lsb_radix_blocks,
|
||||
message_modulus);
|
||||
pack_blocks<Torus>(streams[0], gpu_indexes[0], rhs, scalar_blocks, 0,
|
||||
num_scalar_blocks, message_modulus);
|
||||
|
||||
// From this point we have half number of blocks
|
||||
num_lsb_radix_blocks /= 2;
|
||||
num_scalar_blocks /= 2;
|
||||
|
||||
// comparisons will be assigned
|
||||
// - 0 if lhs < rhs
|
||||
// - 1 if lhs == rhs
|
||||
// - 2 if lhs > rhs
|
||||
auto comparisons = mem_ptr->tmp_lwe_array_out;
|
||||
scalar_compare_radix_blocks_kb<Torus>(streams, gpu_indexes, gpu_count,
|
||||
comparisons, lhs, rhs, mem_ptr,
|
||||
bsks, ksks, num_lsb_radix_blocks);
|
||||
|
||||
// Reduces a vec containing radix blocks that encrypts a sign
|
||||
// (inferior, equal, superior) to one single radix block containing the
|
||||
// final sign
|
||||
tree_sign_reduction<Torus>(streams, gpu_indexes, gpu_count, lwe_array_out,
|
||||
comparisons, mem_ptr->diff_buffer->tree_buffer,
|
||||
sign_handler_f, bsks, ksks,
|
||||
num_lsb_radix_blocks);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -448,65 +506,104 @@ __host__ void integer_radix_signed_scalar_difference_check_kb(
|
||||
2);
|
||||
|
||||
} else {
|
||||
// We only have to do the regular comparison
|
||||
// And not the part where we compare most significant blocks with zeros
|
||||
// total_num_radix_blocks == total_num_scalar_blocks
|
||||
uint32_t num_lsb_radix_blocks = total_num_radix_blocks;
|
||||
if (total_num_radix_blocks == 1) {
|
||||
std::pair<bool, bool> invert_flags = get_invert_flags(mem_ptr->op);
|
||||
Torus scalar = 0;
|
||||
cuda_memcpy_async_to_cpu(&scalar, scalar_blocks, sizeof(Torus),
|
||||
streams[0], gpu_indexes[0]);
|
||||
cuda_synchronize_stream(streams[0], gpu_indexes[0]);
|
||||
auto one_block_lut_f = [invert_flags, scalar,
|
||||
message_modulus](Torus x) -> Torus {
|
||||
Torus x_0;
|
||||
Torus x_1;
|
||||
if (invert_flags.first) {
|
||||
x_0 = scalar;
|
||||
x_1 = x;
|
||||
} else {
|
||||
x_0 = x;
|
||||
x_1 = scalar;
|
||||
}
|
||||
return (Torus)(invert_flags.second) ^
|
||||
is_x_less_than_y_given_input_borrow<Torus>(x_0, x_1, 0,
|
||||
message_modulus);
|
||||
};
|
||||
int_radix_lut<Torus> *one_block_lut = new int_radix_lut<Torus>(
|
||||
streams, gpu_indexes, gpu_count, params, 1, 1, true);
|
||||
|
||||
for (uint j = 0; j < gpu_count; j++) {
|
||||
cuda_synchronize_stream(streams[j], gpu_indexes[j]);
|
||||
generate_device_accumulator<Torus>(
|
||||
streams[0], gpu_indexes[0], one_block_lut->get_lut(0, 0),
|
||||
one_block_lut->get_degree(0), one_block_lut->get_max_degree(0),
|
||||
params.glwe_dimension, params.polynomial_size, params.message_modulus,
|
||||
params.carry_modulus, one_block_lut_f);
|
||||
|
||||
one_block_lut->broadcast_lut(streams, gpu_indexes, 0);
|
||||
|
||||
legacy_integer_radix_apply_univariate_lookup_table_kb<Torus>(
|
||||
streams, gpu_indexes, gpu_count, lwe_array_out, lwe_array_in, bsks,
|
||||
ksks, 1, one_block_lut);
|
||||
one_block_lut->release(streams, gpu_indexes, gpu_count);
|
||||
delete one_block_lut;
|
||||
} else {
|
||||
// We only have to do the regular comparison
|
||||
// And not the part where we compare most significant blocks with zeros
|
||||
// total_num_radix_blocks == total_num_scalar_blocks
|
||||
uint32_t num_lsb_radix_blocks = total_num_radix_blocks;
|
||||
|
||||
for (uint j = 0; j < gpu_count; j++) {
|
||||
cuda_synchronize_stream(streams[j], gpu_indexes[j]);
|
||||
}
|
||||
auto lsb_streams = mem_ptr->lsb_streams;
|
||||
auto msb_streams = mem_ptr->msb_streams;
|
||||
|
||||
auto lwe_array_ct_out = mem_ptr->tmp_lwe_array_out;
|
||||
auto lwe_array_sign_out =
|
||||
lwe_array_ct_out + (num_lsb_radix_blocks / 2) * big_lwe_size;
|
||||
Torus *lhs = diff_buffer->tmp_packed;
|
||||
Torus *rhs =
|
||||
diff_buffer->tmp_packed + total_num_radix_blocks / 2 * big_lwe_size;
|
||||
|
||||
pack_blocks<Torus>(lsb_streams[0], gpu_indexes[0], lhs, lwe_array_in,
|
||||
big_lwe_dimension, num_lsb_radix_blocks - 1,
|
||||
message_modulus);
|
||||
pack_blocks<Torus>(lsb_streams[0], gpu_indexes[0], rhs, scalar_blocks, 0,
|
||||
num_lsb_radix_blocks - 1, message_modulus);
|
||||
|
||||
// From this point we have half number of blocks
|
||||
num_lsb_radix_blocks /= 2;
|
||||
|
||||
// comparisons will be assigned
|
||||
// - 0 if lhs < rhs
|
||||
// - 1 if lhs == rhs
|
||||
// - 2 if lhs > rhs
|
||||
scalar_compare_radix_blocks_kb<Torus>(lsb_streams, gpu_indexes, gpu_count,
|
||||
lwe_array_ct_out, lhs, rhs, mem_ptr,
|
||||
bsks, ksks, num_lsb_radix_blocks);
|
||||
Torus const *encrypted_sign_block =
|
||||
lwe_array_in + (total_num_radix_blocks - 1) * big_lwe_size;
|
||||
Torus const *scalar_sign_block =
|
||||
scalar_blocks + (total_num_scalar_blocks - 1);
|
||||
|
||||
auto trivial_sign_block = mem_ptr->tmp_trivial_sign_block;
|
||||
create_trivial_radix<Torus>(
|
||||
msb_streams[0], gpu_indexes[0], trivial_sign_block, scalar_sign_block,
|
||||
big_lwe_dimension, 1, 1, message_modulus, carry_modulus);
|
||||
|
||||
legacy_integer_radix_apply_bivariate_lookup_table_kb<Torus>(
|
||||
msb_streams, gpu_indexes, gpu_count, lwe_array_sign_out,
|
||||
encrypted_sign_block, trivial_sign_block, bsks, ksks, 1,
|
||||
mem_ptr->signed_lut, mem_ptr->signed_lut->params.message_modulus);
|
||||
for (uint j = 0; j < mem_ptr->active_gpu_count; j++) {
|
||||
cuda_synchronize_stream(lsb_streams[j], gpu_indexes[j]);
|
||||
cuda_synchronize_stream(msb_streams[j], gpu_indexes[j]);
|
||||
}
|
||||
|
||||
// Reduces a vec containing radix blocks that encrypts a sign
|
||||
// (inferior, equal, superior) to one single radix block containing the
|
||||
// final sign
|
||||
reduce_signs<Torus>(streams, gpu_indexes, gpu_count, lwe_array_out,
|
||||
lwe_array_ct_out, mem_ptr, sign_handler_f, bsks, ksks,
|
||||
num_lsb_radix_blocks + 1);
|
||||
}
|
||||
auto lsb_streams = mem_ptr->lsb_streams;
|
||||
auto msb_streams = mem_ptr->msb_streams;
|
||||
|
||||
auto lwe_array_ct_out = mem_ptr->tmp_lwe_array_out;
|
||||
auto lwe_array_sign_out =
|
||||
lwe_array_ct_out + (num_lsb_radix_blocks / 2) * big_lwe_size;
|
||||
Torus *lhs = diff_buffer->tmp_packed;
|
||||
Torus *rhs =
|
||||
diff_buffer->tmp_packed + total_num_radix_blocks / 2 * big_lwe_size;
|
||||
|
||||
pack_blocks<Torus>(lsb_streams[0], gpu_indexes[0], lhs, lwe_array_in,
|
||||
big_lwe_dimension, num_lsb_radix_blocks - 1,
|
||||
message_modulus);
|
||||
pack_blocks<Torus>(lsb_streams[0], gpu_indexes[0], rhs, scalar_blocks, 0,
|
||||
num_lsb_radix_blocks - 1, message_modulus);
|
||||
|
||||
// From this point we have half number of blocks
|
||||
num_lsb_radix_blocks /= 2;
|
||||
|
||||
// comparisons will be assigned
|
||||
// - 0 if lhs < rhs
|
||||
// - 1 if lhs == rhs
|
||||
// - 2 if lhs > rhs
|
||||
scalar_compare_radix_blocks_kb<Torus>(lsb_streams, gpu_indexes, gpu_count,
|
||||
lwe_array_ct_out, lhs, rhs, mem_ptr,
|
||||
bsks, ksks, num_lsb_radix_blocks);
|
||||
Torus const *encrypted_sign_block =
|
||||
lwe_array_in + (total_num_radix_blocks - 1) * big_lwe_size;
|
||||
Torus const *scalar_sign_block =
|
||||
scalar_blocks + (total_num_scalar_blocks - 1);
|
||||
|
||||
auto trivial_sign_block = mem_ptr->tmp_trivial_sign_block;
|
||||
create_trivial_radix<Torus>(
|
||||
msb_streams[0], gpu_indexes[0], trivial_sign_block, scalar_sign_block,
|
||||
big_lwe_dimension, 1, 1, message_modulus, carry_modulus);
|
||||
|
||||
legacy_integer_radix_apply_bivariate_lookup_table_kb<Torus>(
|
||||
msb_streams, gpu_indexes, gpu_count, lwe_array_sign_out,
|
||||
encrypted_sign_block, trivial_sign_block, bsks, ksks, 1,
|
||||
mem_ptr->signed_lut, mem_ptr->signed_lut->params.message_modulus);
|
||||
for (uint j = 0; j < mem_ptr->active_gpu_count; j++) {
|
||||
cuda_synchronize_stream(lsb_streams[j], gpu_indexes[j]);
|
||||
cuda_synchronize_stream(msb_streams[j], gpu_indexes[j]);
|
||||
}
|
||||
|
||||
// Reduces a vec containing radix blocks that encrypts a sign
|
||||
// (inferior, equal, superior) to one single radix block containing the
|
||||
// final sign
|
||||
reduce_signs<Torus>(streams, gpu_indexes, gpu_count, lwe_array_out,
|
||||
lwe_array_ct_out, mem_ptr, sign_handler_f, bsks, ksks,
|
||||
num_lsb_radix_blocks + 1);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -26,7 +26,7 @@ get_join_buffer_element(int level_id, int glwe_id, G &group,
|
||||
* Both operands should be at fourier domain
|
||||
*
|
||||
* This function assumes:
|
||||
* - Thread blocks at dimension x relates to the decomposition level.
|
||||
* - Thread blocks at dimension z relates to the decomposition level.
|
||||
* - Thread blocks at dimension y relates to the glwe dimension.
|
||||
* - polynomial_size / params::opt threads are available per block
|
||||
*/
|
||||
@@ -38,55 +38,6 @@ mul_ggsw_glwe_in_fourier_domain(double2 *fft, double2 *join_buffer,
|
||||
bool support_dsm = false) {
|
||||
const uint32_t polynomial_size = params::degree;
|
||||
const uint32_t glwe_dimension = gridDim.y - 1;
|
||||
const uint32_t level_count = gridDim.x;
|
||||
|
||||
// The first product is used to initialize level_join_buffer
|
||||
auto this_block_rank = get_this_block_rank<G>(group, support_dsm);
|
||||
|
||||
// Continues multiplying fft by every polynomial in that particular bsk level
|
||||
// Each y-block accumulates in a different polynomial at each iteration
|
||||
auto bsk_slice = get_ith_mask_kth_block(
|
||||
bootstrapping_key, iteration, blockIdx.y, blockIdx.x, polynomial_size,
|
||||
glwe_dimension, level_count);
|
||||
for (int j = 0; j < glwe_dimension + 1; j++) {
|
||||
int idx = (j + this_block_rank) % (glwe_dimension + 1);
|
||||
|
||||
auto bsk_poly = bsk_slice + idx * polynomial_size / 2;
|
||||
auto buffer_slice = get_join_buffer_element<G>(blockIdx.x, idx, group,
|
||||
join_buffer, polynomial_size,
|
||||
glwe_dimension, support_dsm);
|
||||
|
||||
polynomial_product_accumulate_in_fourier_domain<params, double2>(
|
||||
buffer_slice, fft, bsk_poly, j == 0);
|
||||
group.sync();
|
||||
}
|
||||
|
||||
// -----------------------------------------------------------------
|
||||
// All blocks are synchronized here; after this sync, level_join_buffer has
|
||||
// the values needed from every other block
|
||||
|
||||
// accumulate rest of the products into fft buffer
|
||||
for (int l = 0; l < level_count; l++) {
|
||||
auto cur_src_acc = get_join_buffer_element<G>(l, blockIdx.y, group,
|
||||
join_buffer, polynomial_size,
|
||||
glwe_dimension, support_dsm);
|
||||
|
||||
polynomial_accumulate_in_fourier_domain<params>(fft, cur_src_acc, l == 0);
|
||||
}
|
||||
|
||||
synchronize_threads_in_block();
|
||||
}
|
||||
// This is a temporary function to have a working version of the tbc-PBS
|
||||
// with large integers.
|
||||
// TO DO: we should erase this function when the other flavors of the PBS also
|
||||
// work with the number of samples in the first block dimension.
|
||||
template <typename G, class params>
|
||||
__device__ void mul_ggsw_glwe_in_fourier_domain_tbc(
|
||||
double2 *fft, double2 *join_buffer,
|
||||
const double2 *__restrict__ bootstrapping_key, int iteration, G &group,
|
||||
bool support_dsm = false) {
|
||||
const uint32_t polynomial_size = params::degree;
|
||||
const uint32_t glwe_dimension = gridDim.y - 1;
|
||||
const uint32_t level_count = gridDim.z;
|
||||
|
||||
// The first product is used to initialize level_join_buffer
|
||||
|
||||
@@ -60,8 +60,8 @@ __global__ void device_programmable_bootstrap_cg(
|
||||
if constexpr (SMD == FULLSM) {
|
||||
selected_memory = sharedmem;
|
||||
} else {
|
||||
int block_index = blockIdx.x + blockIdx.y * gridDim.x +
|
||||
blockIdx.z * gridDim.x * gridDim.y;
|
||||
int block_index = blockIdx.z + blockIdx.y * gridDim.z +
|
||||
blockIdx.x * gridDim.z * gridDim.y;
|
||||
selected_memory = &device_mem[block_index * device_memory_size_per_block];
|
||||
}
|
||||
|
||||
@@ -80,14 +80,14 @@ __global__ void device_programmable_bootstrap_cg(
|
||||
// The third dimension of the block is used to determine on which ciphertext
|
||||
// this block is operating, in the case of batch bootstraps
|
||||
const Torus *block_lwe_array_in =
|
||||
&lwe_array_in[lwe_input_indexes[blockIdx.z] * (lwe_dimension + 1)];
|
||||
&lwe_array_in[lwe_input_indexes[blockIdx.x] * (lwe_dimension + 1)];
|
||||
|
||||
const Torus *block_lut_vector =
|
||||
&lut_vector[lut_vector_indexes[blockIdx.z] * params::degree *
|
||||
&lut_vector[lut_vector_indexes[blockIdx.x] * params::degree *
|
||||
(glwe_dimension + 1)];
|
||||
|
||||
double2 *block_join_buffer =
|
||||
&join_buffer[blockIdx.z * level_count * (glwe_dimension + 1) *
|
||||
&join_buffer[blockIdx.x * level_count * (glwe_dimension + 1) *
|
||||
params::degree / 2];
|
||||
// Since the space is L1 cache is small, we use the same memory location for
|
||||
// the rotated accumulator and the fft accumulator, since we know that the
|
||||
@@ -128,7 +128,7 @@ __global__ void device_programmable_bootstrap_cg(
|
||||
// accumulator decomposed at level 0, 1 at 1, etc.)
|
||||
GadgetMatrix<Torus, params> gadget_acc(base_log, level_count,
|
||||
accumulator_rotated);
|
||||
gadget_acc.decompose_and_compress_level(accumulator_fft, blockIdx.x);
|
||||
gadget_acc.decompose_and_compress_level(accumulator_fft, blockIdx.z);
|
||||
NSMFFT_direct<HalfDegree<params>>(accumulator_fft);
|
||||
synchronize_threads_in_block();
|
||||
|
||||
@@ -142,11 +142,11 @@ __global__ void device_programmable_bootstrap_cg(
|
||||
}
|
||||
|
||||
auto block_lwe_array_out =
|
||||
&lwe_array_out[lwe_output_indexes[blockIdx.z] *
|
||||
&lwe_array_out[lwe_output_indexes[blockIdx.x] *
|
||||
(glwe_dimension * polynomial_size + 1) +
|
||||
blockIdx.y * polynomial_size];
|
||||
|
||||
if (blockIdx.x == 0) {
|
||||
if (blockIdx.z == 0) {
|
||||
if (blockIdx.y < glwe_dimension) {
|
||||
// Perform a sample extract. At this point, all blocks have the result,
|
||||
// but we do the computation at block 0 to avoid waiting for extra blocks,
|
||||
@@ -156,9 +156,9 @@ __global__ void device_programmable_bootstrap_cg(
|
||||
for (int i = 1; i < num_many_lut; i++) {
|
||||
auto next_lwe_array_out =
|
||||
lwe_array_out +
|
||||
(i * gridDim.z * (glwe_dimension * polynomial_size + 1));
|
||||
(i * gridDim.x * (glwe_dimension * polynomial_size + 1));
|
||||
auto next_block_lwe_array_out =
|
||||
&next_lwe_array_out[lwe_output_indexes[blockIdx.z] *
|
||||
&next_lwe_array_out[lwe_output_indexes[blockIdx.x] *
|
||||
(glwe_dimension * polynomial_size + 1) +
|
||||
blockIdx.y * polynomial_size];
|
||||
|
||||
@@ -173,9 +173,9 @@ __global__ void device_programmable_bootstrap_cg(
|
||||
|
||||
auto next_lwe_array_out =
|
||||
lwe_array_out +
|
||||
(i * gridDim.z * (glwe_dimension * polynomial_size + 1));
|
||||
(i * gridDim.x * (glwe_dimension * polynomial_size + 1));
|
||||
auto next_block_lwe_array_out =
|
||||
&next_lwe_array_out[lwe_output_indexes[blockIdx.z] *
|
||||
&next_lwe_array_out[lwe_output_indexes[blockIdx.x] *
|
||||
(glwe_dimension * polynomial_size + 1) +
|
||||
blockIdx.y * polynomial_size];
|
||||
|
||||
@@ -257,7 +257,7 @@ __host__ void host_programmable_bootstrap_cg(
|
||||
double2 *buffer_fft = buffer->global_join_buffer;
|
||||
|
||||
int thds = polynomial_size / params::opt;
|
||||
dim3 grid(level_count, glwe_dimension + 1, input_lwe_ciphertext_count);
|
||||
dim3 grid(input_lwe_ciphertext_count, glwe_dimension + 1, level_count);
|
||||
|
||||
void *kernel_args[16];
|
||||
kernel_args[0] = &lwe_array_out;
|
||||
|
||||
@@ -45,8 +45,8 @@ __global__ void __launch_bounds__(params::degree / params::opt)
|
||||
if constexpr (SMD == FULLSM) {
|
||||
selected_memory = sharedmem;
|
||||
} else {
|
||||
int block_index = blockIdx.x + blockIdx.y * gridDim.x +
|
||||
blockIdx.z * gridDim.x * gridDim.y;
|
||||
int block_index = blockIdx.z + blockIdx.y * gridDim.z +
|
||||
blockIdx.x * gridDim.z * gridDim.y;
|
||||
selected_memory = &device_mem[block_index * device_memory_size_per_block];
|
||||
}
|
||||
|
||||
@@ -61,22 +61,22 @@ __global__ void __launch_bounds__(params::degree / params::opt)
|
||||
// The third dimension of the block is used to determine on which ciphertext
|
||||
// this block is operating, in the case of batch bootstraps
|
||||
const Torus *block_lwe_array_in =
|
||||
&lwe_array_in[lwe_input_indexes[blockIdx.z] * (lwe_dimension + 1)];
|
||||
&lwe_array_in[lwe_input_indexes[blockIdx.x] * (lwe_dimension + 1)];
|
||||
|
||||
const Torus *block_lut_vector =
|
||||
&lut_vector[lut_vector_indexes[blockIdx.z] * params::degree *
|
||||
&lut_vector[lut_vector_indexes[blockIdx.x] * params::degree *
|
||||
(glwe_dimension + 1)];
|
||||
|
||||
double2 *block_join_buffer =
|
||||
&join_buffer[blockIdx.z * level_count * (glwe_dimension + 1) *
|
||||
&join_buffer[blockIdx.x * level_count * (glwe_dimension + 1) *
|
||||
params::degree / 2];
|
||||
|
||||
Torus *global_accumulator_slice =
|
||||
&global_accumulator[(blockIdx.y + blockIdx.z * (glwe_dimension + 1)) *
|
||||
&global_accumulator[(blockIdx.y + blockIdx.x * (glwe_dimension + 1)) *
|
||||
params::degree];
|
||||
|
||||
const double2 *keybundle =
|
||||
&keybundle_array[blockIdx.z * keybundle_size_per_input];
|
||||
&keybundle_array[blockIdx.x * keybundle_size_per_input];
|
||||
|
||||
if (lwe_offset == 0) {
|
||||
// Put "b" in [0, 2N[
|
||||
@@ -106,7 +106,7 @@ __global__ void __launch_bounds__(params::degree / params::opt)
|
||||
// accumulator_rotated decomposed at level 0, 1 at 1, etc.)
|
||||
GadgetMatrix<Torus, params> gadget_acc(base_log, level_count,
|
||||
accumulator_rotated);
|
||||
gadget_acc.decompose_and_compress_level(accumulator_fft, blockIdx.x);
|
||||
gadget_acc.decompose_and_compress_level(accumulator_fft, blockIdx.z);
|
||||
NSMFFT_direct<HalfDegree<params>>(accumulator_fft);
|
||||
synchronize_threads_in_block();
|
||||
|
||||
@@ -121,10 +121,10 @@ __global__ void __launch_bounds__(params::degree / params::opt)
|
||||
|
||||
auto accumulator = accumulator_rotated;
|
||||
|
||||
if (blockIdx.x == 0) {
|
||||
if (blockIdx.z == 0) {
|
||||
if (lwe_offset + lwe_chunk_size >= (lwe_dimension / grouping_factor)) {
|
||||
auto block_lwe_array_out =
|
||||
&lwe_array_out[lwe_output_indexes[blockIdx.z] *
|
||||
&lwe_array_out[lwe_output_indexes[blockIdx.x] *
|
||||
(glwe_dimension * polynomial_size + 1) +
|
||||
blockIdx.y * polynomial_size];
|
||||
|
||||
@@ -139,9 +139,9 @@ __global__ void __launch_bounds__(params::degree / params::opt)
|
||||
for (int i = 1; i < num_many_lut; i++) {
|
||||
auto next_lwe_array_out =
|
||||
lwe_array_out +
|
||||
(i * gridDim.z * (glwe_dimension * polynomial_size + 1));
|
||||
(i * gridDim.x * (glwe_dimension * polynomial_size + 1));
|
||||
auto next_block_lwe_array_out =
|
||||
&next_lwe_array_out[lwe_output_indexes[blockIdx.z] *
|
||||
&next_lwe_array_out[lwe_output_indexes[blockIdx.x] *
|
||||
(glwe_dimension * polynomial_size + 1) +
|
||||
blockIdx.y * polynomial_size];
|
||||
|
||||
@@ -159,9 +159,9 @@ __global__ void __launch_bounds__(params::degree / params::opt)
|
||||
|
||||
auto next_lwe_array_out =
|
||||
lwe_array_out +
|
||||
(i * gridDim.z * (glwe_dimension * polynomial_size + 1));
|
||||
(i * gridDim.x * (glwe_dimension * polynomial_size + 1));
|
||||
auto next_block_lwe_array_out =
|
||||
&next_lwe_array_out[lwe_output_indexes[blockIdx.z] *
|
||||
&next_lwe_array_out[lwe_output_indexes[blockIdx.x] *
|
||||
(glwe_dimension * polynomial_size + 1) +
|
||||
blockIdx.y * polynomial_size];
|
||||
|
||||
@@ -349,7 +349,7 @@ __host__ void execute_cg_external_product_loop(
|
||||
kernel_args[20] = &num_many_lut;
|
||||
kernel_args[21] = &lut_stride;
|
||||
|
||||
dim3 grid_accumulate(level_count, glwe_dimension + 1, num_samples);
|
||||
dim3 grid_accumulate(num_samples, glwe_dimension + 1, level_count);
|
||||
dim3 thds(polynomial_size / params::opt, 1, 1);
|
||||
|
||||
if (max_shared_memory < partial_dm) {
|
||||
|
||||
@@ -40,8 +40,8 @@ __global__ void __launch_bounds__(params::degree / params::opt)
|
||||
if constexpr (SMD == FULLSM) {
|
||||
selected_memory = sharedmem;
|
||||
} else {
|
||||
int block_index = blockIdx.x + blockIdx.y * gridDim.x +
|
||||
blockIdx.z * gridDim.x * gridDim.y;
|
||||
int block_index = blockIdx.z + blockIdx.y * gridDim.z +
|
||||
blockIdx.x * gridDim.z * gridDim.y;
|
||||
selected_memory = &device_mem[block_index * device_memory_size_per_block];
|
||||
}
|
||||
|
||||
@@ -56,19 +56,19 @@ __global__ void __launch_bounds__(params::degree / params::opt)
|
||||
// The third dimension of the block is used to determine on which ciphertext
|
||||
// this block is operating, in the case of batch bootstraps
|
||||
const Torus *block_lwe_array_in =
|
||||
&lwe_array_in[lwe_input_indexes[blockIdx.z] * (lwe_dimension + 1)];
|
||||
&lwe_array_in[lwe_input_indexes[blockIdx.x] * (lwe_dimension + 1)];
|
||||
|
||||
const Torus *block_lut_vector =
|
||||
&lut_vector[lut_vector_indexes[blockIdx.z] * params::degree *
|
||||
&lut_vector[lut_vector_indexes[blockIdx.x] * params::degree *
|
||||
(glwe_dimension + 1)];
|
||||
|
||||
Torus *global_slice =
|
||||
global_accumulator +
|
||||
(blockIdx.y + blockIdx.z * (glwe_dimension + 1)) * params::degree;
|
||||
(blockIdx.y + blockIdx.x * (glwe_dimension + 1)) * params::degree;
|
||||
|
||||
double2 *global_fft_slice =
|
||||
global_join_buffer + (blockIdx.y + blockIdx.x * (glwe_dimension + 1) +
|
||||
blockIdx.z * level_count * (glwe_dimension + 1)) *
|
||||
global_join_buffer + (blockIdx.y + blockIdx.z * (glwe_dimension + 1) +
|
||||
blockIdx.x * level_count * (glwe_dimension + 1)) *
|
||||
(polynomial_size / 2);
|
||||
|
||||
if (lwe_iteration == 0) {
|
||||
@@ -116,7 +116,7 @@ __global__ void __launch_bounds__(params::degree / params::opt)
|
||||
// decomposition, for the mask and the body (so block 0 will have the
|
||||
// accumulator decomposed at level 0, 1 at 1, etc.)
|
||||
GadgetMatrix<Torus, params> gadget_acc(base_log, level_count, accumulator);
|
||||
gadget_acc.decompose_and_compress_level(accumulator_fft, blockIdx.x);
|
||||
gadget_acc.decompose_and_compress_level(accumulator_fft, blockIdx.z);
|
||||
|
||||
// We are using the same memory space for accumulator_fft and
|
||||
// accumulator_rotated, so we need to synchronize here to make sure they
|
||||
@@ -375,7 +375,7 @@ __host__ void execute_step_one(
|
||||
int max_shared_memory = cuda_get_max_shared_memory(gpu_index);
|
||||
cuda_set_device(gpu_index);
|
||||
int thds = polynomial_size / params::opt;
|
||||
dim3 grid(level_count, glwe_dimension + 1, input_lwe_ciphertext_count);
|
||||
dim3 grid(input_lwe_ciphertext_count, glwe_dimension + 1, level_count);
|
||||
|
||||
if (max_shared_memory < partial_sm) {
|
||||
device_programmable_bootstrap_step_one<Torus, params, NOSM>
|
||||
|
||||
@@ -169,8 +169,8 @@ __global__ void __launch_bounds__(params::degree / params::opt)
|
||||
if constexpr (SMD == FULLSM) {
|
||||
selected_memory = sharedmem;
|
||||
} else {
|
||||
int block_index = blockIdx.x + blockIdx.y * gridDim.x +
|
||||
blockIdx.z * gridDim.x * gridDim.y;
|
||||
int block_index = blockIdx.z + blockIdx.y * gridDim.z +
|
||||
blockIdx.x * gridDim.z * gridDim.y;
|
||||
selected_memory = &device_mem[block_index * device_memory_size_per_block];
|
||||
}
|
||||
|
||||
@@ -183,19 +183,19 @@ __global__ void __launch_bounds__(params::degree / params::opt)
|
||||
accumulator_fft = (double2 *)sharedmem;
|
||||
|
||||
const Torus *block_lwe_array_in =
|
||||
&lwe_array_in[lwe_input_indexes[blockIdx.z] * (lwe_dimension + 1)];
|
||||
&lwe_array_in[lwe_input_indexes[blockIdx.x] * (lwe_dimension + 1)];
|
||||
|
||||
const Torus *block_lut_vector =
|
||||
&lut_vector[lut_vector_indexes[blockIdx.z] * params::degree *
|
||||
&lut_vector[lut_vector_indexes[blockIdx.x] * params::degree *
|
||||
(glwe_dimension + 1)];
|
||||
|
||||
Torus *global_slice =
|
||||
&global_accumulator[(blockIdx.y + blockIdx.z * (glwe_dimension + 1)) *
|
||||
&global_accumulator[(blockIdx.y + blockIdx.x * (glwe_dimension + 1)) *
|
||||
params::degree];
|
||||
|
||||
double2 *global_fft_slice =
|
||||
&global_accumulator_fft[(blockIdx.y + blockIdx.x * (glwe_dimension + 1) +
|
||||
blockIdx.z * level_count *
|
||||
&global_accumulator_fft[(blockIdx.y + blockIdx.z * (glwe_dimension + 1) +
|
||||
blockIdx.x * level_count *
|
||||
(glwe_dimension + 1)) *
|
||||
(polynomial_size / 2)];
|
||||
|
||||
@@ -232,7 +232,7 @@ __global__ void __launch_bounds__(params::degree / params::opt)
|
||||
// decomposition, for the mask and the body (so block 0 will have the
|
||||
// accumulator decomposed at level 0, 1 at 1, etc.)
|
||||
GadgetMatrix<Torus, params> gadget_acc(base_log, level_count, accumulator);
|
||||
gadget_acc.decompose_and_compress_level(accumulator_fft, blockIdx.x);
|
||||
gadget_acc.decompose_and_compress_level(accumulator_fft, blockIdx.z);
|
||||
|
||||
// We are using the same memory space for accumulator_fft and
|
||||
// accumulator_rotated, so we need to synchronize here to make sure they
|
||||
@@ -560,7 +560,7 @@ execute_step_one(cudaStream_t stream, uint32_t gpu_index,
|
||||
auto global_accumulator = buffer->global_accumulator;
|
||||
auto global_accumulator_fft = buffer->global_join_buffer;
|
||||
|
||||
dim3 grid_accumulate_step_one(level_count, glwe_dimension + 1, num_samples);
|
||||
dim3 grid_accumulate_step_one(num_samples, glwe_dimension + 1, level_count);
|
||||
dim3 thds(polynomial_size / params::opt, 1, 1);
|
||||
|
||||
if (max_shared_memory < partial_sm_accumulate_step_one)
|
||||
|
||||
@@ -62,8 +62,8 @@ __global__ void device_programmable_bootstrap_tbc(
|
||||
if (support_dsm)
|
||||
selected_memory += sizeof(Torus) * polynomial_size;
|
||||
} else {
|
||||
int block_index = blockIdx.x + blockIdx.y * gridDim.x +
|
||||
blockIdx.z * gridDim.x * gridDim.y;
|
||||
int block_index = blockIdx.z + blockIdx.y * gridDim.z +
|
||||
blockIdx.x * gridDim.z * gridDim.y;
|
||||
selected_memory = &device_mem[block_index * device_memory_size_per_block];
|
||||
}
|
||||
|
||||
@@ -83,14 +83,14 @@ __global__ void device_programmable_bootstrap_tbc(
|
||||
// The third dimension of the block is used to determine on which ciphertext
|
||||
// this block is operating, in the case of batch bootstraps
|
||||
const Torus *block_lwe_array_in =
|
||||
&lwe_array_in[lwe_input_indexes[blockIdx.z] * (lwe_dimension + 1)];
|
||||
&lwe_array_in[lwe_input_indexes[blockIdx.x] * (lwe_dimension + 1)];
|
||||
|
||||
const Torus *block_lut_vector =
|
||||
&lut_vector[lut_vector_indexes[blockIdx.z] * params::degree *
|
||||
&lut_vector[lut_vector_indexes[blockIdx.x] * params::degree *
|
||||
(glwe_dimension + 1)];
|
||||
|
||||
double2 *block_join_buffer =
|
||||
&join_buffer[blockIdx.z * level_count * (glwe_dimension + 1) *
|
||||
&join_buffer[blockIdx.x * level_count * (glwe_dimension + 1) *
|
||||
params::degree / 2];
|
||||
// Since the space is L1 cache is small, we use the same memory location for
|
||||
// the rotated accumulator and the fft accumulator, since we know that the
|
||||
@@ -132,7 +132,7 @@ __global__ void device_programmable_bootstrap_tbc(
|
||||
// accumulator decomposed at level 0, 1 at 1, etc.)
|
||||
GadgetMatrix<Torus, params> gadget_acc(base_log, level_count,
|
||||
accumulator_rotated);
|
||||
gadget_acc.decompose_and_compress_level(accumulator_fft, blockIdx.x);
|
||||
gadget_acc.decompose_and_compress_level(accumulator_fft, blockIdx.z);
|
||||
NSMFFT_direct<HalfDegree<params>>(accumulator_fft);
|
||||
synchronize_threads_in_block();
|
||||
|
||||
@@ -147,11 +147,11 @@ __global__ void device_programmable_bootstrap_tbc(
|
||||
}
|
||||
|
||||
auto block_lwe_array_out =
|
||||
&lwe_array_out[lwe_output_indexes[blockIdx.z] *
|
||||
&lwe_array_out[lwe_output_indexes[blockIdx.x] *
|
||||
(glwe_dimension * polynomial_size + 1) +
|
||||
blockIdx.y * polynomial_size];
|
||||
|
||||
if (blockIdx.x == 0) {
|
||||
if (blockIdx.z == 0) {
|
||||
if (blockIdx.y < glwe_dimension) {
|
||||
// Perform a sample extract. At this point, all blocks have the result,
|
||||
// but we do the computation at block 0 to avoid waiting for extra blocks,
|
||||
@@ -162,9 +162,9 @@ __global__ void device_programmable_bootstrap_tbc(
|
||||
for (int i = 1; i < num_many_lut; i++) {
|
||||
auto next_lwe_array_out =
|
||||
lwe_array_out +
|
||||
(i * gridDim.z * (glwe_dimension * polynomial_size + 1));
|
||||
(i * gridDim.x * (glwe_dimension * polynomial_size + 1));
|
||||
auto next_block_lwe_array_out =
|
||||
&next_lwe_array_out[lwe_output_indexes[blockIdx.z] *
|
||||
&next_lwe_array_out[lwe_output_indexes[blockIdx.x] *
|
||||
(glwe_dimension * polynomial_size + 1) +
|
||||
blockIdx.y * polynomial_size];
|
||||
|
||||
@@ -180,9 +180,9 @@ __global__ void device_programmable_bootstrap_tbc(
|
||||
|
||||
auto next_lwe_array_out =
|
||||
lwe_array_out +
|
||||
(i * gridDim.z * (glwe_dimension * polynomial_size + 1));
|
||||
(i * gridDim.x * (glwe_dimension * polynomial_size + 1));
|
||||
auto next_block_lwe_array_out =
|
||||
&next_lwe_array_out[lwe_output_indexes[blockIdx.z] *
|
||||
&next_lwe_array_out[lwe_output_indexes[blockIdx.x] *
|
||||
(glwe_dimension * polynomial_size + 1) +
|
||||
blockIdx.y * polynomial_size];
|
||||
|
||||
@@ -292,7 +292,7 @@ __host__ void host_programmable_bootstrap_tbc(
|
||||
double2 *buffer_fft = buffer->global_join_buffer;
|
||||
|
||||
int thds = polynomial_size / params::opt;
|
||||
dim3 grid(level_count, glwe_dimension + 1, input_lwe_ciphertext_count);
|
||||
dim3 grid(input_lwe_ciphertext_count, glwe_dimension + 1, level_count);
|
||||
|
||||
cudaLaunchConfig_t config = {0};
|
||||
// The grid dimension is not affected by cluster launch, and is still
|
||||
@@ -303,9 +303,9 @@ __host__ void host_programmable_bootstrap_tbc(
|
||||
|
||||
cudaLaunchAttribute attribute[1];
|
||||
attribute[0].id = cudaLaunchAttributeClusterDimension;
|
||||
attribute[0].val.clusterDim.x = level_count; // Cluster size in X-dimension
|
||||
attribute[0].val.clusterDim.x = 1;
|
||||
attribute[0].val.clusterDim.y = (glwe_dimension + 1);
|
||||
attribute[0].val.clusterDim.z = 1;
|
||||
attribute[0].val.clusterDim.z = level_count; // Cluster size in Z-dimension
|
||||
config.attrs = attribute;
|
||||
config.numAttrs = 1;
|
||||
config.stream = stream;
|
||||
@@ -424,7 +424,7 @@ __host__ bool supports_thread_block_clusters_on_classic_programmable_bootstrap(
|
||||
|
||||
int cluster_size;
|
||||
|
||||
dim3 grid_accumulate(level_count, glwe_dimension + 1, num_samples);
|
||||
dim3 grid_accumulate(num_samples, glwe_dimension + 1, level_count);
|
||||
dim3 thds(polynomial_size / params::opt, 1, 1);
|
||||
|
||||
cudaLaunchConfig_t config = {0};
|
||||
|
||||
@@ -118,7 +118,7 @@ __global__ void __launch_bounds__(params::degree / params::opt)
|
||||
synchronize_threads_in_block();
|
||||
|
||||
// Perform G^-1(ACC) * GGSW -> GLWE
|
||||
mul_ggsw_glwe_in_fourier_domain_tbc<cluster_group, params>(
|
||||
mul_ggsw_glwe_in_fourier_domain<cluster_group, params>(
|
||||
accumulator_fft, block_join_buffer, keybundle, i, cluster, support_dsm);
|
||||
NSMFFT_inverse<HalfDegree<params>>(accumulator_fft);
|
||||
synchronize_threads_in_block();
|
||||
|
||||
@@ -30,6 +30,7 @@ unsafe extern "C" {
|
||||
glwe_array_in: *const ffi::c_void,
|
||||
nth_array: *const u32,
|
||||
num_nths: u32,
|
||||
lwe_per_glwe: u32,
|
||||
glwe_dimension: u32,
|
||||
polynomial_size: u32,
|
||||
);
|
||||
|
||||
@@ -1,18 +1,18 @@
|
||||
[backend.aws.cpu-big]
|
||||
region = "eu-west-3"
|
||||
image_id = "ami-0cd5012d17ae64070"
|
||||
image_id = "ami-0449b775abf884686"
|
||||
instance_type = "m6i.32xlarge"
|
||||
user = "ubuntu"
|
||||
|
||||
[backend.aws.cpu-big_fallback]
|
||||
region = "us-east-1"
|
||||
image_id = "ami-04e3bb9aebb6786df"
|
||||
image_id = "ami-0c6e54f3be8d03234"
|
||||
instance_type = "m6i.32xlarge"
|
||||
user = "ubuntu"
|
||||
|
||||
[backend.aws.cpu-small]
|
||||
region = "eu-west-3"
|
||||
image_id = "ami-0cd5012d17ae64070"
|
||||
image_id = "ami-0449b775abf884686"
|
||||
instance_type = "m6i.4xlarge"
|
||||
user = "ubuntu"
|
||||
|
||||
|
||||
@@ -10,7 +10,7 @@ const DIR_TO_IGNORE: [&str; 3] = [
|
||||
"tests/tfhe-backward-compat-data",
|
||||
];
|
||||
|
||||
const FILES_TO_IGNORE: [&str; 6] = [
|
||||
const FILES_TO_IGNORE: [&str; 7] = [
|
||||
// This contains fragments of code that are unrelated to TFHE-rs
|
||||
"tfhe/docs/tutorials/sha256_bool.md",
|
||||
// TODO: This contains code that could be executed as a trivium docstring
|
||||
@@ -22,6 +22,7 @@ const FILES_TO_IGNORE: [&str; 6] = [
|
||||
// TODO: find a way to test the tfhe-ntt readme
|
||||
"tfhe-ntt/README.md",
|
||||
"utils/tfhe-lints/README.md",
|
||||
"CONTRIBUTING.md",
|
||||
];
|
||||
|
||||
pub fn check_tfhe_docs_are_tested() -> Result<(), Error> {
|
||||
@@ -126,10 +127,18 @@ pub fn check_tfhe_docs_are_tested() -> Result<(), Error> {
|
||||
}
|
||||
|
||||
let difference = doc_files.difference(&tested_files);
|
||||
let files_that_may_not_exist = tested_files.difference(&doc_files);
|
||||
let files_that_dont_exist: Vec<_> = files_that_may_not_exist
|
||||
.into_iter()
|
||||
.filter(|p| !p.exists())
|
||||
.collect();
|
||||
|
||||
let debug_format = format!("missing file from user doc tests: {difference:#?}");
|
||||
let debug_format = format!(
|
||||
"missing file from user doc tests: {difference:#?}\n\
|
||||
files that are tested but don't exist: {files_that_dont_exist:#?}"
|
||||
);
|
||||
|
||||
if difference.count() != 0 {
|
||||
if difference.count() != 0 || !files_that_dont_exist.is_empty() {
|
||||
return Err(Error::new(ErrorKind::NotFound, debug_format));
|
||||
}
|
||||
|
||||
|
||||
@@ -43,7 +43,7 @@ impl<BlockCipher: AesBlockCipher> AesCtrGenerator<BlockCipher> {
|
||||
let first_index = self.state.table_index().incremented();
|
||||
let output = (0..n_children.0)
|
||||
.into_par_iter()
|
||||
.zip(rayon::iter::repeatn(
|
||||
.zip(rayon::iter::repeat_n(
|
||||
(self.block_cipher.clone(), first_index, n_bytes),
|
||||
n_children.0,
|
||||
))
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
[package]
|
||||
name = "tfhe"
|
||||
version = "1.0.0"
|
||||
version = "1.0.1"
|
||||
edition = "2021"
|
||||
readme = "../README.md"
|
||||
keywords = ["fully", "homomorphic", "encryption", "fhe", "cryptography"]
|
||||
@@ -60,7 +60,7 @@ tfhe-fft = { version = "0.8.0", path = "../tfhe-fft", features = [
|
||||
] }
|
||||
tfhe-ntt = { version = "0.5.0", path = "../tfhe-ntt" }
|
||||
pulp = { workspace = true, features = ["default"] }
|
||||
tfhe-cuda-backend = { version = "0.8.0", path = "../backends/tfhe-cuda-backend", optional = true }
|
||||
tfhe-cuda-backend = { version = "0.8.1", path = "../backends/tfhe-cuda-backend", optional = true }
|
||||
aligned-vec = { workspace = true, features = ["default", "serde"] }
|
||||
dyn-stack = { workspace = true, features = ["default"] }
|
||||
paste = "1.0.7"
|
||||
@@ -162,6 +162,12 @@ path = "benches/core_crypto/pbs_bench.rs"
|
||||
harness = false
|
||||
required-features = ["boolean", "shortint", "internal-keycache"]
|
||||
|
||||
[[bench]]
|
||||
name = "ks-pbs-bench"
|
||||
path = "benches/core_crypto/ks_pbs_bench.rs"
|
||||
harness = false
|
||||
required-features = ["shortint", "internal-keycache"]
|
||||
|
||||
[[bench]]
|
||||
name = "dev-bench"
|
||||
path = "benches/core_crypto/dev_bench.rs"
|
||||
|
||||
@@ -1,8 +1,11 @@
|
||||
#[path = "../utilities.rs"]
|
||||
mod utilities;
|
||||
|
||||
use crate::utilities::{write_to_json, CryptoParametersRecord, OperatorType};
|
||||
use criterion::{black_box, criterion_main, Criterion};
|
||||
use crate::utilities::{
|
||||
filter_parameters, init_parameters_set, write_to_json, CryptoParametersRecord, DesiredBackend,
|
||||
DesiredNoiseDistribution, OperatorType, ParametersSet, PARAMETERS_SET,
|
||||
};
|
||||
use criterion::{black_box, Criterion};
|
||||
use serde::Serialize;
|
||||
use tfhe::boolean::prelude::*;
|
||||
use tfhe::core_crypto::prelude::*;
|
||||
@@ -10,7 +13,7 @@ use tfhe::keycache::NamedParam;
|
||||
use tfhe::shortint::parameters::current_params::{
|
||||
V1_0_PARAM_MESSAGE_1_CARRY_1_KS_PBS_GAUSSIAN_2M128,
|
||||
V1_0_PARAM_MESSAGE_2_CARRY_2_KS_PBS_GAUSSIAN_2M128,
|
||||
V1_0_PARAM_MESSAGE_3_CARRY_3_KS_PBS_GAUSSIAN_2M128,
|
||||
V1_0_PARAM_MESSAGE_3_CARRY_3_KS_PBS_GAUSSIAN_2M128, VEC_ALL_MULTI_BIT_PBS_PARAMETERS,
|
||||
};
|
||||
#[cfg(not(feature = "gpu"))]
|
||||
use tfhe::shortint::parameters::current_params::{
|
||||
@@ -29,9 +32,11 @@ use tfhe::shortint::parameters::{
|
||||
#[cfg(feature = "gpu")]
|
||||
use tfhe::shortint::parameters::{
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_1_CARRY_1_KS_PBS_GAUSSIAN_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_1_CARRY_1_KS_PBS_TUNIFORM_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_2_CARRY_2_KS_PBS_GAUSSIAN_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_2_CARRY_2_KS_PBS_TUNIFORM_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_3_CARRY_3_KS_PBS_GAUSSIAN_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_3_CARRY_3_KS_PBS_TUNIFORM_2M64,
|
||||
};
|
||||
use tfhe::shortint::prelude::*;
|
||||
use tfhe::shortint::{MultiBitPBSParameters, PBSParameters};
|
||||
@@ -64,8 +69,10 @@ const SHORTINT_MULTI_BIT_BENCH_PARAMS: [MultiBitPBSParameters; 6] = [
|
||||
];
|
||||
|
||||
#[cfg(feature = "gpu")]
|
||||
const SHORTINT_MULTI_BIT_BENCH_PARAMS: [MultiBitPBSParameters; 4] = [
|
||||
const SHORTINT_MULTI_BIT_BENCH_PARAMS: [MultiBitPBSParameters; 6] = [
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_1_CARRY_1_KS_PBS_TUNIFORM_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_2_CARRY_2_KS_PBS_TUNIFORM_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_3_CARRY_3_KS_PBS_TUNIFORM_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_1_CARRY_1_KS_PBS_GAUSSIAN_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_2_CARRY_2_KS_PBS_GAUSSIAN_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_3_CARRY_3_KS_PBS_GAUSSIAN_2M64,
|
||||
@@ -80,28 +87,78 @@ const BOOLEAN_BENCH_PARAMS: [(&str, BooleanParameters); 2] = [
|
||||
];
|
||||
|
||||
fn benchmark_parameters_64bits() -> Vec<(String, CryptoParametersRecord<u64>)> {
|
||||
let classic = SHORTINT_BENCH_PARAMS
|
||||
.iter()
|
||||
.map(|params| {
|
||||
(
|
||||
params.name(),
|
||||
<ClassicPBSParameters as Into<PBSParameters>>::into(*params)
|
||||
.to_owned()
|
||||
.into(),
|
||||
let (classic, multi_bit) = match PARAMETERS_SET.get().unwrap() {
|
||||
ParametersSet::Default => {
|
||||
let classic = SHORTINT_BENCH_PARAMS
|
||||
.iter()
|
||||
.map(|params| {
|
||||
(
|
||||
params.name(),
|
||||
<ClassicPBSParameters as Into<PBSParameters>>::into(*params)
|
||||
.to_owned()
|
||||
.into(),
|
||||
)
|
||||
})
|
||||
.collect::<Vec<(String, CryptoParametersRecord<u64>)>>();
|
||||
|
||||
let multi_bit = SHORTINT_MULTI_BIT_BENCH_PARAMS
|
||||
.iter()
|
||||
.map(|params| {
|
||||
(
|
||||
params.name(),
|
||||
<MultiBitPBSParameters as Into<PBSParameters>>::into(*params)
|
||||
.to_owned()
|
||||
.into(),
|
||||
)
|
||||
})
|
||||
.collect();
|
||||
|
||||
(classic, multi_bit)
|
||||
}
|
||||
ParametersSet::All => {
|
||||
let desired_noise = DesiredNoiseDistribution::Both;
|
||||
let desired_backend = if cfg!(feature = "gpu") {
|
||||
DesiredBackend::Gpu
|
||||
} else {
|
||||
DesiredBackend::Cpu
|
||||
};
|
||||
|
||||
let classic = filter_parameters(
|
||||
&VEC_ALL_CLASSIC_PBS_PARAMETERS,
|
||||
desired_noise,
|
||||
DesiredBackend::Cpu, // No parameters set are specific to GPU in this vector
|
||||
)
|
||||
})
|
||||
.collect::<Vec<(String, CryptoParametersRecord<u64>)>>();
|
||||
let multi_bit = SHORTINT_MULTI_BIT_BENCH_PARAMS
|
||||
.iter()
|
||||
.map(|params| {
|
||||
(
|
||||
params.name(),
|
||||
<MultiBitPBSParameters as Into<PBSParameters>>::into(*params)
|
||||
.to_owned()
|
||||
.into(),
|
||||
.into_iter()
|
||||
.map(|(params, name)| {
|
||||
(
|
||||
name.to_string(),
|
||||
<ClassicPBSParameters as Into<PBSParameters>>::into(*params)
|
||||
.to_owned()
|
||||
.into(),
|
||||
)
|
||||
})
|
||||
.collect::<Vec<(String, CryptoParametersRecord<u64>)>>();
|
||||
|
||||
let multi_bit = filter_parameters(
|
||||
&VEC_ALL_MULTI_BIT_PBS_PARAMETERS,
|
||||
desired_noise,
|
||||
desired_backend,
|
||||
)
|
||||
})
|
||||
.collect();
|
||||
.into_iter()
|
||||
.map(|(params, name)| {
|
||||
(
|
||||
name.to_string(),
|
||||
<MultiBitPBSParameters as Into<PBSParameters>>::into(*params)
|
||||
.to_owned()
|
||||
.into(),
|
||||
)
|
||||
})
|
||||
.collect();
|
||||
|
||||
(classic, multi_bit)
|
||||
}
|
||||
};
|
||||
|
||||
[classic, multi_bit].concat()
|
||||
}
|
||||
|
||||
@@ -526,6 +583,7 @@ mod cuda {
|
||||
|
||||
#[cfg(feature = "gpu")]
|
||||
use cuda::cuda_keyswitch_group;
|
||||
use tfhe::shortint::parameters::v1_0::VEC_ALL_CLASSIC_PBS_PARAMETERS;
|
||||
|
||||
pub fn keyswitch_group() {
|
||||
let mut criterion: Criterion<_> = (Criterion::default()
|
||||
@@ -555,7 +613,24 @@ pub fn packing_keyswitch_group() {
|
||||
);
|
||||
}
|
||||
|
||||
#[cfg(not(feature = "gpu"))]
|
||||
criterion_main!(keyswitch_group, packing_keyswitch_group);
|
||||
#[cfg(feature = "gpu")]
|
||||
criterion_main!(cuda_keyswitch_group);
|
||||
fn go_through_gpu_bench_groups() {
|
||||
cuda_keyswitch_group();
|
||||
}
|
||||
|
||||
#[cfg(not(feature = "gpu"))]
|
||||
fn go_through_cpu_bench_groups() {
|
||||
keyswitch_group();
|
||||
packing_keyswitch_group();
|
||||
}
|
||||
|
||||
fn main() {
|
||||
init_parameters_set();
|
||||
|
||||
#[cfg(feature = "gpu")]
|
||||
go_through_gpu_bench_groups();
|
||||
#[cfg(not(feature = "gpu"))]
|
||||
go_through_cpu_bench_groups();
|
||||
|
||||
Criterion::default().configure_from_args().final_summary();
|
||||
}
|
||||
|
||||
760
tfhe/benches/core_crypto/ks_pbs_bench.rs
Normal file
@@ -0,0 +1,760 @@
|
||||
#[path = "../utilities.rs"]
|
||||
mod utilities;
|
||||
|
||||
use crate::utilities::{
|
||||
filter_parameters, init_parameters_set, multi_bit_num_threads, write_to_json,
|
||||
CryptoParametersRecord, DesiredBackend, DesiredNoiseDistribution, OperatorType, ParametersSet,
|
||||
PARAMETERS_SET,
|
||||
};
|
||||
use criterion::{black_box, Criterion};
|
||||
use serde::Serialize;
|
||||
use std::env;
|
||||
use tfhe::core_crypto::prelude::*;
|
||||
use tfhe::keycache::NamedParam;
|
||||
use tfhe::shortint::parameters::current_params::*;
|
||||
use tfhe::shortint::parameters::*;
|
||||
|
||||
const SHORTINT_BENCH_PARAMS_TUNIFORM: [ClassicPBSParameters; 4] = [
|
||||
V1_0_PARAM_MESSAGE_1_CARRY_1_KS_PBS_TUNIFORM_2M128,
|
||||
V1_0_PARAM_MESSAGE_2_CARRY_2_KS_PBS_TUNIFORM_2M128,
|
||||
V1_0_PARAM_MESSAGE_3_CARRY_3_KS_PBS_TUNIFORM_2M128,
|
||||
V1_0_PARAM_MESSAGE_4_CARRY_4_KS_PBS_TUNIFORM_2M128,
|
||||
];
|
||||
|
||||
const SHORTINT_BENCH_PARAMS_GAUSSIAN: [ClassicPBSParameters; 4] = [
|
||||
V1_0_PARAM_MESSAGE_1_CARRY_1_KS_PBS_GAUSSIAN_2M128,
|
||||
V1_0_PARAM_MESSAGE_2_CARRY_2_KS_PBS_GAUSSIAN_2M128,
|
||||
V1_0_PARAM_MESSAGE_3_CARRY_3_KS_PBS_GAUSSIAN_2M128,
|
||||
V1_0_PARAM_MESSAGE_4_CARRY_4_KS_PBS_GAUSSIAN_2M128,
|
||||
];
|
||||
|
||||
#[cfg(feature = "gpu")]
|
||||
const SHORTINT_MULTI_BIT_BENCH_PARAMS: [MultiBitPBSParameters; 6] = [
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_1_CARRY_1_KS_PBS_TUNIFORM_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_2_CARRY_2_KS_PBS_TUNIFORM_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_3_CARRY_3_KS_PBS_TUNIFORM_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_1_CARRY_1_KS_PBS_GAUSSIAN_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_2_CARRY_2_KS_PBS_GAUSSIAN_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_3_CARRY_3_KS_PBS_GAUSSIAN_2M64,
|
||||
];
|
||||
|
||||
#[cfg(not(feature = "gpu"))]
|
||||
const SHORTINT_MULTI_BIT_BENCH_PARAMS: [MultiBitPBSParameters; 6] = [
|
||||
V1_0_PARAM_MULTI_BIT_GROUP_2_MESSAGE_1_CARRY_1_KS_PBS_GAUSSIAN_2M64,
|
||||
V1_0_PARAM_MULTI_BIT_GROUP_2_MESSAGE_2_CARRY_2_KS_PBS_GAUSSIAN_2M64,
|
||||
V1_0_PARAM_MULTI_BIT_GROUP_2_MESSAGE_3_CARRY_3_KS_PBS_GAUSSIAN_2M64,
|
||||
V1_0_PARAM_MULTI_BIT_GROUP_3_MESSAGE_1_CARRY_1_KS_PBS_GAUSSIAN_2M64,
|
||||
V1_0_PARAM_MULTI_BIT_GROUP_3_MESSAGE_2_CARRY_2_KS_PBS_GAUSSIAN_2M64,
|
||||
V1_0_PARAM_MULTI_BIT_GROUP_3_MESSAGE_3_CARRY_3_KS_PBS_GAUSSIAN_2M64,
|
||||
];
|
||||
|
||||
fn benchmark_parameters() -> Vec<(String, CryptoParametersRecord<u64>)> {
|
||||
match PARAMETERS_SET.get().unwrap() {
|
||||
ParametersSet::Default => SHORTINT_BENCH_PARAMS_TUNIFORM
|
||||
.iter()
|
||||
.chain(SHORTINT_BENCH_PARAMS_GAUSSIAN.iter())
|
||||
.map(|params| {
|
||||
(
|
||||
params.name(),
|
||||
<ClassicPBSParameters as Into<PBSParameters>>::into(*params)
|
||||
.to_owned()
|
||||
.into(),
|
||||
)
|
||||
})
|
||||
.collect(),
|
||||
ParametersSet::All => {
|
||||
filter_parameters(
|
||||
&VEC_ALL_CLASSIC_PBS_PARAMETERS,
|
||||
DesiredNoiseDistribution::Both,
|
||||
DesiredBackend::Cpu, // No parameters set are specific to GPU in this vector
|
||||
)
|
||||
.into_iter()
|
||||
.map(|(params, name)| {
|
||||
(
|
||||
name.to_string(),
|
||||
<ClassicPBSParameters as Into<PBSParameters>>::into(*params)
|
||||
.to_owned()
|
||||
.into(),
|
||||
)
|
||||
})
|
||||
.collect()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn multi_bit_benchmark_parameters(
|
||||
) -> Vec<(String, CryptoParametersRecord<u64>, LweBskGroupingFactor)> {
|
||||
match PARAMETERS_SET.get().unwrap() {
|
||||
ParametersSet::Default => SHORTINT_MULTI_BIT_BENCH_PARAMS
|
||||
.iter()
|
||||
.map(|params| {
|
||||
(
|
||||
params.name(),
|
||||
<MultiBitPBSParameters as Into<PBSParameters>>::into(*params)
|
||||
.to_owned()
|
||||
.into(),
|
||||
params.grouping_factor,
|
||||
)
|
||||
})
|
||||
.collect(),
|
||||
ParametersSet::All => {
|
||||
let desired_backend = if cfg!(feature = "gpu") {
|
||||
DesiredBackend::Gpu
|
||||
} else {
|
||||
DesiredBackend::Cpu
|
||||
};
|
||||
filter_parameters(
|
||||
&VEC_ALL_MULTI_BIT_PBS_PARAMETERS,
|
||||
DesiredNoiseDistribution::Both,
|
||||
desired_backend,
|
||||
)
|
||||
.into_iter()
|
||||
.map(|(params, name)| {
|
||||
(
|
||||
name.to_string(),
|
||||
<MultiBitPBSParameters as Into<PBSParameters>>::into(*params)
|
||||
.to_owned()
|
||||
.into(),
|
||||
params.grouping_factor,
|
||||
)
|
||||
})
|
||||
.collect()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn ks_pbs<Scalar: UnsignedTorus + CastInto<usize> + Serialize>(
|
||||
c: &mut Criterion,
|
||||
parameters: &[(String, CryptoParametersRecord<Scalar>)],
|
||||
) {
|
||||
let bench_name = "core_crypto::ks_pbs";
|
||||
let mut bench_group = c.benchmark_group(bench_name);
|
||||
bench_group
|
||||
.sample_size(10)
|
||||
.measurement_time(std::time::Duration::from_secs(30));
|
||||
|
||||
// Create the PRNG
|
||||
let mut seeder = new_seeder();
|
||||
let seeder = seeder.as_mut();
|
||||
let mut encryption_generator =
|
||||
EncryptionRandomGenerator::<DefaultRandomGenerator>::new(seeder.seed(), seeder);
|
||||
let mut secret_generator = SecretRandomGenerator::<DefaultRandomGenerator>::new(seeder.seed());
|
||||
|
||||
for (name, params) in parameters.iter() {
|
||||
// Create the LweSecretKey
|
||||
let input_lwe_secret_key = allocate_and_generate_new_binary_lwe_secret_key(
|
||||
params.lwe_dimension.unwrap(),
|
||||
&mut secret_generator,
|
||||
);
|
||||
let output_glwe_secret_key: GlweSecretKeyOwned<Scalar> =
|
||||
allocate_and_generate_new_binary_glwe_secret_key(
|
||||
params.glwe_dimension.unwrap(),
|
||||
params.polynomial_size.unwrap(),
|
||||
&mut secret_generator,
|
||||
);
|
||||
let output_lwe_secret_key = output_glwe_secret_key.into_lwe_secret_key();
|
||||
|
||||
let ksk_big_to_small = allocate_and_generate_new_lwe_keyswitch_key(
|
||||
&output_lwe_secret_key,
|
||||
&input_lwe_secret_key,
|
||||
params.ks_base_log.unwrap(),
|
||||
params.ks_level.unwrap(),
|
||||
params.lwe_noise_distribution.unwrap(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
&mut encryption_generator,
|
||||
);
|
||||
|
||||
// Create the empty bootstrapping key in the Fourier domain
|
||||
let fourier_bsk = FourierLweBootstrapKey::new(
|
||||
params.lwe_dimension.unwrap(),
|
||||
params.glwe_dimension.unwrap().to_glwe_size(),
|
||||
params.polynomial_size.unwrap(),
|
||||
params.pbs_base_log.unwrap(),
|
||||
params.pbs_level.unwrap(),
|
||||
);
|
||||
|
||||
// Allocate a new LweCiphertext and encrypt our plaintext
|
||||
let input_ks_ct: LweCiphertextOwned<Scalar> = allocate_and_encrypt_new_lwe_ciphertext(
|
||||
&output_lwe_secret_key,
|
||||
Plaintext(Scalar::ONE),
|
||||
params.lwe_noise_distribution.unwrap(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
&mut encryption_generator,
|
||||
);
|
||||
|
||||
let mut output_ks_ct: LweCiphertextOwned<Scalar> = LweCiphertext::new(
|
||||
Scalar::ZERO,
|
||||
input_lwe_secret_key.lwe_dimension().to_lwe_size(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
);
|
||||
|
||||
let accumulator = GlweCiphertext::new(
|
||||
Scalar::ZERO,
|
||||
params.glwe_dimension.unwrap().to_glwe_size(),
|
||||
params.polynomial_size.unwrap(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
);
|
||||
|
||||
// Allocate the LweCiphertext to store the result of the PBS
|
||||
let mut output_pbs_ct = LweCiphertext::new(
|
||||
Scalar::ZERO,
|
||||
output_lwe_secret_key.lwe_dimension().to_lwe_size(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
);
|
||||
|
||||
let mut buffers = ComputationBuffers::new();
|
||||
|
||||
let fft = Fft::new(fourier_bsk.polynomial_size());
|
||||
let fft = fft.as_view();
|
||||
|
||||
buffers.resize(
|
||||
programmable_bootstrap_lwe_ciphertext_mem_optimized_requirement::<Scalar>(
|
||||
fourier_bsk.glwe_size(),
|
||||
fourier_bsk.polynomial_size(),
|
||||
fft,
|
||||
)
|
||||
.unwrap()
|
||||
.unaligned_bytes_required(),
|
||||
);
|
||||
|
||||
let id = format!("{bench_name}::{name}");
|
||||
{
|
||||
bench_group.bench_function(&id, |b| {
|
||||
b.iter(|| {
|
||||
keyswitch_lwe_ciphertext(&ksk_big_to_small, &input_ks_ct, &mut output_ks_ct);
|
||||
programmable_bootstrap_lwe_ciphertext_mem_optimized(
|
||||
&output_ks_ct,
|
||||
&mut output_pbs_ct,
|
||||
&accumulator.as_view(),
|
||||
&fourier_bsk,
|
||||
fft,
|
||||
buffers.stack(),
|
||||
);
|
||||
black_box(&mut output_pbs_ct);
|
||||
})
|
||||
});
|
||||
}
|
||||
|
||||
let bit_size = (params.message_modulus.unwrap_or(2) as u32).ilog2();
|
||||
write_to_json(
|
||||
&id,
|
||||
*params,
|
||||
name,
|
||||
"ks-pbs",
|
||||
&OperatorType::Atomic,
|
||||
bit_size,
|
||||
vec![bit_size],
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
fn multi_bit_ks_pbs<
|
||||
Scalar: UnsignedTorus + CastInto<usize> + CastFrom<usize> + Default + Sync + Serialize,
|
||||
>(
|
||||
c: &mut Criterion,
|
||||
parameters: &[(String, CryptoParametersRecord<Scalar>, LweBskGroupingFactor)],
|
||||
deterministic_pbs: bool,
|
||||
) {
|
||||
let bench_name = if deterministic_pbs {
|
||||
"core_crypto::multi_bit_deterministic_ks_pbs"
|
||||
} else {
|
||||
"core_crypto::multi_bit_ks_pbs"
|
||||
};
|
||||
let mut bench_group = c.benchmark_group(bench_name);
|
||||
bench_group
|
||||
.sample_size(10)
|
||||
.measurement_time(std::time::Duration::from_secs(30));
|
||||
|
||||
// Create the PRNG
|
||||
let mut seeder = new_seeder();
|
||||
let seeder = seeder.as_mut();
|
||||
let mut encryption_generator =
|
||||
EncryptionRandomGenerator::<DefaultRandomGenerator>::new(seeder.seed(), seeder);
|
||||
let mut secret_generator = SecretRandomGenerator::<DefaultRandomGenerator>::new(seeder.seed());
|
||||
|
||||
for (name, params, grouping_factor) in parameters.iter() {
|
||||
// Create the LweSecretKey
|
||||
let input_lwe_secret_key = allocate_and_generate_new_binary_lwe_secret_key(
|
||||
params.lwe_dimension.unwrap(),
|
||||
&mut secret_generator,
|
||||
);
|
||||
let output_glwe_secret_key: GlweSecretKeyOwned<Scalar> =
|
||||
allocate_and_generate_new_binary_glwe_secret_key(
|
||||
params.glwe_dimension.unwrap(),
|
||||
params.polynomial_size.unwrap(),
|
||||
&mut secret_generator,
|
||||
);
|
||||
let output_lwe_secret_key = output_glwe_secret_key.into_lwe_secret_key();
|
||||
|
||||
let ksk_big_to_small = allocate_and_generate_new_lwe_keyswitch_key(
|
||||
&output_lwe_secret_key,
|
||||
&input_lwe_secret_key,
|
||||
params.ks_base_log.unwrap(),
|
||||
params.ks_level.unwrap(),
|
||||
params.lwe_noise_distribution.unwrap(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
&mut encryption_generator,
|
||||
);
|
||||
|
||||
let multi_bit_bsk = FourierLweMultiBitBootstrapKey::new(
|
||||
params.lwe_dimension.unwrap(),
|
||||
params.glwe_dimension.unwrap().to_glwe_size(),
|
||||
params.polynomial_size.unwrap(),
|
||||
params.pbs_base_log.unwrap(),
|
||||
params.pbs_level.unwrap(),
|
||||
*grouping_factor,
|
||||
);
|
||||
|
||||
// Allocate a new LweCiphertext and encrypt our plaintext
|
||||
let input_ks_ct: LweCiphertextOwned<Scalar> = allocate_and_encrypt_new_lwe_ciphertext(
|
||||
&output_lwe_secret_key,
|
||||
Plaintext(Scalar::ONE),
|
||||
params.lwe_noise_distribution.unwrap(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
&mut encryption_generator,
|
||||
);
|
||||
|
||||
let mut output_ks_ct: LweCiphertextOwned<Scalar> = LweCiphertext::new(
|
||||
Scalar::ZERO,
|
||||
input_lwe_secret_key.lwe_dimension().to_lwe_size(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
);
|
||||
|
||||
let accumulator = GlweCiphertext::new(
|
||||
Scalar::ZERO,
|
||||
params.glwe_dimension.unwrap().to_glwe_size(),
|
||||
params.polynomial_size.unwrap(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
);
|
||||
|
||||
// Allocate the LweCiphertext to store the result of the PBS
|
||||
let mut output_pbs_ct = LweCiphertext::new(
|
||||
Scalar::ZERO,
|
||||
output_lwe_secret_key.lwe_dimension().to_lwe_size(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
);
|
||||
|
||||
let thread_count = multi_bit_num_threads(
|
||||
params.message_modulus.unwrap(),
|
||||
params.carry_modulus.unwrap(),
|
||||
grouping_factor.0,
|
||||
)
|
||||
.unwrap() as usize;
|
||||
|
||||
let id = format!("{bench_name}::{name}::parallelized");
|
||||
bench_group.bench_function(&id, |b| {
|
||||
b.iter(|| {
|
||||
keyswitch_lwe_ciphertext(&ksk_big_to_small, &input_ks_ct, &mut output_ks_ct);
|
||||
multi_bit_programmable_bootstrap_lwe_ciphertext(
|
||||
&output_ks_ct,
|
||||
&mut output_pbs_ct,
|
||||
&accumulator.as_view(),
|
||||
&multi_bit_bsk,
|
||||
ThreadCount(thread_count),
|
||||
deterministic_pbs,
|
||||
);
|
||||
black_box(&mut output_pbs_ct);
|
||||
})
|
||||
});
|
||||
|
||||
let bit_size = params.message_modulus.unwrap().ilog2();
|
||||
write_to_json(
|
||||
&id,
|
||||
*params,
|
||||
name,
|
||||
"ks-pbs",
|
||||
&OperatorType::Atomic,
|
||||
bit_size,
|
||||
vec![bit_size],
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(feature = "gpu")]
|
||||
mod cuda {
|
||||
use super::{benchmark_parameters, multi_bit_benchmark_parameters};
|
||||
use crate::utilities::{
|
||||
write_to_json, CryptoParametersRecord, OperatorType, GPU_MAX_SUPPORTED_POLYNOMIAL_SIZE,
|
||||
};
|
||||
use criterion::{black_box, Criterion};
|
||||
use serde::Serialize;
|
||||
use tfhe::core_crypto::gpu::glwe_ciphertext_list::CudaGlweCiphertextList;
|
||||
use tfhe::core_crypto::gpu::lwe_bootstrap_key::CudaLweBootstrapKey;
|
||||
use tfhe::core_crypto::gpu::lwe_ciphertext_list::CudaLweCiphertextList;
|
||||
use tfhe::core_crypto::gpu::lwe_keyswitch_key::CudaLweKeyswitchKey;
|
||||
use tfhe::core_crypto::gpu::lwe_multi_bit_bootstrap_key::CudaLweMultiBitBootstrapKey;
|
||||
use tfhe::core_crypto::gpu::vec::{CudaVec, GpuIndex};
|
||||
use tfhe::core_crypto::gpu::{
|
||||
cuda_keyswitch_lwe_ciphertext, cuda_multi_bit_programmable_bootstrap_lwe_ciphertext,
|
||||
cuda_programmable_bootstrap_lwe_ciphertext, CudaStreams,
|
||||
};
|
||||
use tfhe::core_crypto::prelude::*;
|
||||
|
||||
fn cuda_ks_pbs<Scalar: UnsignedTorus + CastInto<usize> + Serialize>(
|
||||
c: &mut Criterion,
|
||||
parameters: &[(String, CryptoParametersRecord<Scalar>)],
|
||||
) {
|
||||
let bench_name = "core_crypto::cuda::ks_pbs";
|
||||
let mut bench_group = c.benchmark_group(bench_name);
|
||||
bench_group
|
||||
.sample_size(10)
|
||||
.measurement_time(std::time::Duration::from_secs(30));
|
||||
|
||||
// Create the PRNG
|
||||
let mut seeder = new_seeder();
|
||||
let seeder = seeder.as_mut();
|
||||
let mut encryption_generator =
|
||||
EncryptionRandomGenerator::<DefaultRandomGenerator>::new(seeder.seed(), seeder);
|
||||
let mut secret_generator =
|
||||
SecretRandomGenerator::<DefaultRandomGenerator>::new(seeder.seed());
|
||||
|
||||
let gpu_index = 0;
|
||||
let stream = CudaStreams::new_single_gpu(GpuIndex::new(gpu_index));
|
||||
|
||||
for (name, params) in parameters.iter() {
|
||||
if params.polynomial_size.unwrap().0 > GPU_MAX_SUPPORTED_POLYNOMIAL_SIZE {
|
||||
println!("[WARNING] polynomial size is too large for parameters set '{}' (max: {}, got: {})", name, GPU_MAX_SUPPORTED_POLYNOMIAL_SIZE, params.polynomial_size.unwrap().0);
|
||||
continue;
|
||||
}
|
||||
|
||||
// Create the LweSecretKey
|
||||
let input_lwe_secret_key = allocate_and_generate_new_binary_lwe_secret_key(
|
||||
params.lwe_dimension.unwrap(),
|
||||
&mut secret_generator,
|
||||
);
|
||||
let output_glwe_secret_key: GlweSecretKeyOwned<Scalar> =
|
||||
allocate_and_generate_new_binary_glwe_secret_key(
|
||||
params.glwe_dimension.unwrap(),
|
||||
params.polynomial_size.unwrap(),
|
||||
&mut secret_generator,
|
||||
);
|
||||
let output_lwe_secret_key = output_glwe_secret_key.into_lwe_secret_key();
|
||||
|
||||
let ksk_big_to_small = allocate_and_generate_new_lwe_keyswitch_key(
|
||||
&output_lwe_secret_key,
|
||||
&input_lwe_secret_key,
|
||||
params.ks_base_log.unwrap(),
|
||||
params.ks_level.unwrap(),
|
||||
params.lwe_noise_distribution.unwrap(),
|
||||
CiphertextModulus::new_native(),
|
||||
&mut encryption_generator,
|
||||
);
|
||||
let ksk_big_to_small_gpu =
|
||||
CudaLweKeyswitchKey::from_lwe_keyswitch_key(&ksk_big_to_small, &stream);
|
||||
|
||||
let bsk = LweBootstrapKey::new(
|
||||
Scalar::ZERO,
|
||||
params.glwe_dimension.unwrap().to_glwe_size(),
|
||||
params.polynomial_size.unwrap(),
|
||||
params.pbs_base_log.unwrap(),
|
||||
params.pbs_level.unwrap(),
|
||||
params.lwe_dimension.unwrap(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
);
|
||||
let bsk_gpu = CudaLweBootstrapKey::from_lwe_bootstrap_key(&bsk, &stream);
|
||||
|
||||
// Allocate a new LweCiphertext and encrypt our plaintext
|
||||
let input_ks_ct = allocate_and_encrypt_new_lwe_ciphertext(
|
||||
&input_lwe_secret_key,
|
||||
Plaintext(Scalar::ZERO),
|
||||
params.lwe_noise_distribution.unwrap(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
&mut encryption_generator,
|
||||
);
|
||||
let input_ks_ct_gpu = CudaLweCiphertextList::from_lwe_ciphertext(&input_ks_ct, &stream);
|
||||
|
||||
let output_ks_ct: LweCiphertextOwned<Scalar> = LweCiphertext::new(
|
||||
Scalar::ZERO,
|
||||
input_lwe_secret_key.lwe_dimension().to_lwe_size(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
);
|
||||
let mut output_ks_ct_gpu =
|
||||
CudaLweCiphertextList::from_lwe_ciphertext(&output_ks_ct, &stream);
|
||||
|
||||
let accumulator = GlweCiphertext::new(
|
||||
Scalar::ZERO,
|
||||
params.glwe_dimension.unwrap().to_glwe_size(),
|
||||
params.polynomial_size.unwrap(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
);
|
||||
let accumulator_gpu =
|
||||
CudaGlweCiphertextList::from_glwe_ciphertext(&accumulator, &stream);
|
||||
|
||||
// Allocate the LweCiphertext to store the result of the PBS
|
||||
let output_pbs_ct = LweCiphertext::new(
|
||||
Scalar::ZERO,
|
||||
output_lwe_secret_key.lwe_dimension().to_lwe_size(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
);
|
||||
let mut output_pbs_ct_gpu =
|
||||
CudaLweCiphertextList::from_lwe_ciphertext(&output_pbs_ct, &stream);
|
||||
|
||||
let h_indexes = &[Scalar::ZERO];
|
||||
stream.synchronize();
|
||||
let mut d_input_indexes = unsafe { CudaVec::<Scalar>::new_async(1, &stream, 0) };
|
||||
let mut d_output_indexes = unsafe { CudaVec::<Scalar>::new_async(1, &stream, 0) };
|
||||
let mut d_lut_indexes = unsafe { CudaVec::<Scalar>::new_async(1, &stream, 0) };
|
||||
unsafe {
|
||||
d_input_indexes.copy_from_cpu_async(h_indexes.as_ref(), &stream, 0);
|
||||
d_output_indexes.copy_from_cpu_async(h_indexes.as_ref(), &stream, 0);
|
||||
d_lut_indexes.copy_from_cpu_async(h_indexes.as_ref(), &stream, 0);
|
||||
}
|
||||
stream.synchronize();
|
||||
|
||||
let id = format!("{bench_name}::{name}");
|
||||
{
|
||||
bench_group.bench_function(&id, |b| {
|
||||
b.iter(|| {
|
||||
cuda_keyswitch_lwe_ciphertext(
|
||||
&ksk_big_to_small_gpu,
|
||||
&input_ks_ct_gpu,
|
||||
&mut output_ks_ct_gpu,
|
||||
&d_input_indexes,
|
||||
&d_output_indexes,
|
||||
&stream,
|
||||
);
|
||||
cuda_programmable_bootstrap_lwe_ciphertext(
|
||||
&output_ks_ct_gpu,
|
||||
&mut output_pbs_ct_gpu,
|
||||
&accumulator_gpu,
|
||||
&d_lut_indexes,
|
||||
&d_output_indexes,
|
||||
&d_input_indexes,
|
||||
LweCiphertextCount(1),
|
||||
&bsk_gpu,
|
||||
&stream,
|
||||
);
|
||||
black_box(&mut output_pbs_ct_gpu);
|
||||
})
|
||||
});
|
||||
}
|
||||
|
||||
let bit_size = (params.message_modulus.unwrap_or(2) as u32).ilog2();
|
||||
write_to_json(
|
||||
&id,
|
||||
*params,
|
||||
name,
|
||||
"ks-pbs",
|
||||
&OperatorType::Atomic,
|
||||
bit_size,
|
||||
vec![bit_size],
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
fn cuda_multi_bit_ks_pbs<
|
||||
Scalar: UnsignedTorus + CastInto<usize> + CastFrom<usize> + Default + Serialize + Sync,
|
||||
>(
|
||||
c: &mut Criterion,
|
||||
parameters: &[(String, CryptoParametersRecord<Scalar>, LweBskGroupingFactor)],
|
||||
) {
|
||||
let bench_name = "core_crypto::cuda::multi_bit_ks_pbs";
|
||||
let mut bench_group = c.benchmark_group(bench_name);
|
||||
bench_group
|
||||
.sample_size(10)
|
||||
.measurement_time(std::time::Duration::from_secs(30));
|
||||
|
||||
// Create the PRNG
|
||||
let mut seeder = new_seeder();
|
||||
let seeder = seeder.as_mut();
|
||||
let mut encryption_generator =
|
||||
EncryptionRandomGenerator::<DefaultRandomGenerator>::new(seeder.seed(), seeder);
|
||||
let mut secret_generator =
|
||||
SecretRandomGenerator::<DefaultRandomGenerator>::new(seeder.seed());
|
||||
|
||||
let gpu_index = 0;
|
||||
let stream = CudaStreams::new_single_gpu(GpuIndex::new(gpu_index));
|
||||
|
||||
for (name, params, grouping_factor) in parameters.iter() {
|
||||
if params.polynomial_size.unwrap().0 > GPU_MAX_SUPPORTED_POLYNOMIAL_SIZE {
|
||||
println!("[WARNING] polynomial size is too large for parameters set '{}' (max: {}, got: {})", name, GPU_MAX_SUPPORTED_POLYNOMIAL_SIZE, params.polynomial_size.unwrap().0);
|
||||
continue;
|
||||
}
|
||||
|
||||
// Create the LweSecretKey
|
||||
let input_lwe_secret_key = allocate_and_generate_new_binary_lwe_secret_key(
|
||||
params.lwe_dimension.unwrap(),
|
||||
&mut secret_generator,
|
||||
);
|
||||
let output_glwe_secret_key: GlweSecretKeyOwned<Scalar> =
|
||||
allocate_and_generate_new_binary_glwe_secret_key(
|
||||
params.glwe_dimension.unwrap(),
|
||||
params.polynomial_size.unwrap(),
|
||||
&mut secret_generator,
|
||||
);
|
||||
let output_lwe_secret_key = output_glwe_secret_key.into_lwe_secret_key();
|
||||
|
||||
let ksk_big_to_small = allocate_and_generate_new_lwe_keyswitch_key(
|
||||
&output_lwe_secret_key,
|
||||
&input_lwe_secret_key,
|
||||
params.ks_base_log.unwrap(),
|
||||
params.ks_level.unwrap(),
|
||||
params.lwe_noise_distribution.unwrap(),
|
||||
CiphertextModulus::new_native(),
|
||||
&mut encryption_generator,
|
||||
);
|
||||
let ksk_big_to_small_gpu =
|
||||
CudaLweKeyswitchKey::from_lwe_keyswitch_key(&ksk_big_to_small, &stream);
|
||||
|
||||
let multi_bit_bsk = LweMultiBitBootstrapKey::new(
|
||||
Scalar::ZERO,
|
||||
params.glwe_dimension.unwrap().to_glwe_size(),
|
||||
params.polynomial_size.unwrap(),
|
||||
params.pbs_base_log.unwrap(),
|
||||
params.pbs_level.unwrap(),
|
||||
params.lwe_dimension.unwrap(),
|
||||
*grouping_factor,
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
);
|
||||
let multi_bit_bsk_gpu = CudaLweMultiBitBootstrapKey::from_lwe_multi_bit_bootstrap_key(
|
||||
&multi_bit_bsk,
|
||||
&stream,
|
||||
);
|
||||
|
||||
// Allocate a new LweCiphertext and encrypt our plaintext
|
||||
let input_ks_ct = allocate_and_encrypt_new_lwe_ciphertext(
|
||||
&input_lwe_secret_key,
|
||||
Plaintext(Scalar::ZERO),
|
||||
params.lwe_noise_distribution.unwrap(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
&mut encryption_generator,
|
||||
);
|
||||
let input_ks_ct_gpu = CudaLweCiphertextList::from_lwe_ciphertext(&input_ks_ct, &stream);
|
||||
|
||||
let output_ks_ct: LweCiphertextOwned<Scalar> = LweCiphertext::new(
|
||||
Scalar::ZERO,
|
||||
input_lwe_secret_key.lwe_dimension().to_lwe_size(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
);
|
||||
let mut output_ks_ct_gpu =
|
||||
CudaLweCiphertextList::from_lwe_ciphertext(&output_ks_ct, &stream);
|
||||
|
||||
let accumulator = GlweCiphertext::new(
|
||||
Scalar::ZERO,
|
||||
params.glwe_dimension.unwrap().to_glwe_size(),
|
||||
params.polynomial_size.unwrap(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
);
|
||||
let accumulator_gpu =
|
||||
CudaGlweCiphertextList::from_glwe_ciphertext(&accumulator, &stream);
|
||||
|
||||
// Allocate the LweCiphertext to store the result of the PBS
|
||||
let output_pbs_ct = LweCiphertext::new(
|
||||
Scalar::ZERO,
|
||||
output_lwe_secret_key.lwe_dimension().to_lwe_size(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
);
|
||||
let mut output_pbs_ct_gpu =
|
||||
CudaLweCiphertextList::from_lwe_ciphertext(&output_pbs_ct, &stream);
|
||||
|
||||
let h_indexes = &[Scalar::ZERO];
|
||||
stream.synchronize();
|
||||
let mut d_input_indexes = unsafe { CudaVec::<Scalar>::new_async(1, &stream, 0) };
|
||||
let mut d_output_indexes = unsafe { CudaVec::<Scalar>::new_async(1, &stream, 0) };
|
||||
let mut d_lut_indexes = unsafe { CudaVec::<Scalar>::new_async(1, &stream, 0) };
|
||||
unsafe {
|
||||
d_input_indexes.copy_from_cpu_async(h_indexes.as_ref(), &stream, 0);
|
||||
d_output_indexes.copy_from_cpu_async(h_indexes.as_ref(), &stream, 0);
|
||||
d_lut_indexes.copy_from_cpu_async(h_indexes.as_ref(), &stream, 0);
|
||||
}
|
||||
stream.synchronize();
|
||||
|
||||
let id = format!("{bench_name}::{name}");
|
||||
bench_group.bench_function(&id, |b| {
|
||||
b.iter(|| {
|
||||
cuda_keyswitch_lwe_ciphertext(
|
||||
&ksk_big_to_small_gpu,
|
||||
&input_ks_ct_gpu,
|
||||
&mut output_ks_ct_gpu,
|
||||
&d_input_indexes,
|
||||
&d_output_indexes,
|
||||
&stream,
|
||||
);
|
||||
cuda_multi_bit_programmable_bootstrap_lwe_ciphertext(
|
||||
&output_ks_ct_gpu,
|
||||
&mut output_pbs_ct_gpu,
|
||||
&accumulator_gpu,
|
||||
&d_lut_indexes,
|
||||
&d_output_indexes,
|
||||
&d_input_indexes,
|
||||
&multi_bit_bsk_gpu,
|
||||
&stream,
|
||||
);
|
||||
black_box(&mut output_ks_ct_gpu);
|
||||
})
|
||||
});
|
||||
|
||||
let bit_size = params.message_modulus.unwrap().ilog2();
|
||||
write_to_json(
|
||||
&id,
|
||||
*params,
|
||||
name,
|
||||
"ks-pbs",
|
||||
&OperatorType::Atomic,
|
||||
bit_size,
|
||||
vec![bit_size],
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
pub fn cuda_ks_pbs_group() {
|
||||
let mut criterion: Criterion<_> = (Criterion::default()).configure_from_args();
|
||||
cuda_ks_pbs(&mut criterion, &benchmark_parameters());
|
||||
}
|
||||
|
||||
pub fn cuda_multi_bit_ks_pbs_group() {
|
||||
let mut criterion: Criterion<_> = (Criterion::default()).configure_from_args();
|
||||
cuda_multi_bit_ks_pbs(&mut criterion, &multi_bit_benchmark_parameters());
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(feature = "gpu")]
|
||||
use cuda::{cuda_ks_pbs_group, cuda_multi_bit_ks_pbs_group};
|
||||
|
||||
pub fn ks_pbs_group() {
|
||||
let mut criterion: Criterion<_> = (Criterion::default()).configure_from_args();
|
||||
ks_pbs(&mut criterion, &benchmark_parameters());
|
||||
}
|
||||
|
||||
pub fn multi_bit_ks_pbs_group() {
|
||||
let mut criterion: Criterion<_> = (Criterion::default()).configure_from_args();
|
||||
multi_bit_ks_pbs(&mut criterion, &multi_bit_benchmark_parameters(), false);
|
||||
multi_bit_ks_pbs(&mut criterion, &multi_bit_benchmark_parameters(), true);
|
||||
}
|
||||
|
||||
#[cfg(feature = "gpu")]
|
||||
fn go_through_gpu_bench_groups(val: &str) {
|
||||
match val.to_lowercase().as_str() {
|
||||
"classical" => cuda_ks_pbs_group(),
|
||||
"multi_bit" => cuda_multi_bit_ks_pbs_group(),
|
||||
_ => panic!("unknown benchmark operations flavor"),
|
||||
};
|
||||
}
|
||||
|
||||
#[cfg(not(feature = "gpu"))]
|
||||
fn go_through_cpu_bench_groups(val: &str) {
|
||||
match val.to_lowercase().as_str() {
|
||||
"classical" => ks_pbs_group(),
|
||||
"multi_bit" => multi_bit_ks_pbs_group(),
|
||||
_ => panic!("unknown benchmark operations flavor"),
|
||||
}
|
||||
}
|
||||
|
||||
fn main() {
|
||||
init_parameters_set();
|
||||
|
||||
match env::var("__TFHE_RS_PARAM_TYPE") {
|
||||
Ok(val) => {
|
||||
#[cfg(feature = "gpu")]
|
||||
go_through_gpu_bench_groups(&val);
|
||||
#[cfg(not(feature = "gpu"))]
|
||||
go_through_cpu_bench_groups(&val);
|
||||
}
|
||||
Err(_) => {
|
||||
ks_pbs_group();
|
||||
multi_bit_ks_pbs_group()
|
||||
}
|
||||
};
|
||||
|
||||
Criterion::default().configure_from_args().final_summary();
|
||||
}
|
||||
@@ -1,8 +1,12 @@
|
||||
#[path = "../utilities.rs"]
|
||||
mod utilities;
|
||||
|
||||
use crate::utilities::{write_to_json, CryptoParametersRecord, OperatorType};
|
||||
use criterion::{black_box, criterion_main, Criterion};
|
||||
use crate::utilities::{
|
||||
filter_parameters, init_parameters_set, multi_bit_num_threads, write_to_json,
|
||||
CryptoParametersRecord, DesiredBackend, DesiredNoiseDistribution, OperatorType, ParametersSet,
|
||||
PARAMETERS_SET,
|
||||
};
|
||||
use criterion::{black_box, Criterion};
|
||||
use rayon::prelude::*;
|
||||
use serde::Serialize;
|
||||
use tfhe::boolean::parameters::{
|
||||
@@ -14,8 +18,12 @@ use tfhe::keycache::NamedParam;
|
||||
use tfhe::shortint::parameters::current_params::*;
|
||||
use tfhe::shortint::parameters::*;
|
||||
|
||||
const SHORTINT_BENCH_PARAMS_TUNIFORM: [ClassicPBSParameters; 1] =
|
||||
[PARAM_MESSAGE_2_CARRY_2_KS_PBS_TUNIFORM_2M128];
|
||||
const SHORTINT_BENCH_PARAMS_TUNIFORM: [ClassicPBSParameters; 4] = [
|
||||
V1_0_PARAM_MESSAGE_1_CARRY_1_KS_PBS_TUNIFORM_2M128,
|
||||
V1_0_PARAM_MESSAGE_2_CARRY_2_KS_PBS_TUNIFORM_2M128,
|
||||
V1_0_PARAM_MESSAGE_3_CARRY_3_KS_PBS_TUNIFORM_2M128,
|
||||
V1_0_PARAM_MESSAGE_4_CARRY_4_KS_PBS_TUNIFORM_2M128,
|
||||
];
|
||||
|
||||
const SHORTINT_BENCH_PARAMS_GAUSSIAN: [ClassicPBSParameters; 4] = [
|
||||
V1_0_PARAM_MESSAGE_1_CARRY_1_KS_PBS_GAUSSIAN_2M128,
|
||||
@@ -24,6 +32,26 @@ const SHORTINT_BENCH_PARAMS_GAUSSIAN: [ClassicPBSParameters; 4] = [
|
||||
V1_0_PARAM_MESSAGE_4_CARRY_4_KS_PBS_GAUSSIAN_2M128,
|
||||
];
|
||||
|
||||
#[cfg(feature = "gpu")]
|
||||
const SHORTINT_MULTI_BIT_BENCH_PARAMS: [MultiBitPBSParameters; 6] = [
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_1_CARRY_1_KS_PBS_TUNIFORM_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_2_CARRY_2_KS_PBS_TUNIFORM_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_3_CARRY_3_KS_PBS_TUNIFORM_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_1_CARRY_1_KS_PBS_GAUSSIAN_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_2_CARRY_2_KS_PBS_GAUSSIAN_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_3_CARRY_3_KS_PBS_GAUSSIAN_2M64,
|
||||
];
|
||||
|
||||
#[cfg(not(feature = "gpu"))]
|
||||
const SHORTINT_MULTI_BIT_BENCH_PARAMS: [MultiBitPBSParameters; 6] = [
|
||||
V1_0_PARAM_MULTI_BIT_GROUP_2_MESSAGE_1_CARRY_1_KS_PBS_GAUSSIAN_2M64,
|
||||
V1_0_PARAM_MULTI_BIT_GROUP_2_MESSAGE_2_CARRY_2_KS_PBS_GAUSSIAN_2M64,
|
||||
V1_0_PARAM_MULTI_BIT_GROUP_2_MESSAGE_3_CARRY_3_KS_PBS_GAUSSIAN_2M64,
|
||||
V1_0_PARAM_MULTI_BIT_GROUP_3_MESSAGE_1_CARRY_1_KS_PBS_GAUSSIAN_2M64,
|
||||
V1_0_PARAM_MULTI_BIT_GROUP_3_MESSAGE_2_CARRY_2_KS_PBS_GAUSSIAN_2M64,
|
||||
V1_0_PARAM_MULTI_BIT_GROUP_3_MESSAGE_3_CARRY_3_KS_PBS_GAUSSIAN_2M64,
|
||||
];
|
||||
|
||||
const BOOLEAN_BENCH_PARAMS: [(&str, BooleanParameters); 2] = [
|
||||
("BOOLEAN_DEFAULT_PARAMS", DEFAULT_PARAMETERS),
|
||||
(
|
||||
@@ -33,18 +61,35 @@ const BOOLEAN_BENCH_PARAMS: [(&str, BooleanParameters); 2] = [
|
||||
];
|
||||
|
||||
fn benchmark_parameters_64bits() -> Vec<(String, CryptoParametersRecord<u64>)> {
|
||||
SHORTINT_BENCH_PARAMS_TUNIFORM
|
||||
.iter()
|
||||
.chain(SHORTINT_BENCH_PARAMS_GAUSSIAN.iter())
|
||||
.map(|params| {
|
||||
match PARAMETERS_SET.get().unwrap() {
|
||||
ParametersSet::Default => SHORTINT_BENCH_PARAMS_TUNIFORM
|
||||
.iter()
|
||||
.chain(SHORTINT_BENCH_PARAMS_GAUSSIAN.iter())
|
||||
.map(|params| {
|
||||
(
|
||||
params.name(),
|
||||
<ClassicPBSParameters as Into<PBSParameters>>::into(*params)
|
||||
.to_owned()
|
||||
.into(),
|
||||
)
|
||||
})
|
||||
.collect(),
|
||||
ParametersSet::All => filter_parameters(
|
||||
&VEC_ALL_CLASSIC_PBS_PARAMETERS,
|
||||
DesiredNoiseDistribution::Both,
|
||||
DesiredBackend::Cpu, // No parameters set are specific to GPU in this vector
|
||||
)
|
||||
.into_iter()
|
||||
.map(|(params, name)| {
|
||||
(
|
||||
params.name(),
|
||||
name.to_string(),
|
||||
<ClassicPBSParameters as Into<PBSParameters>>::into(*params)
|
||||
.to_owned()
|
||||
.into(),
|
||||
)
|
||||
})
|
||||
.collect()
|
||||
.collect(),
|
||||
}
|
||||
}
|
||||
|
||||
fn benchmark_parameters_32bits() -> Vec<(String, CryptoParametersRecord<u32>)> {
|
||||
@@ -94,36 +139,43 @@ fn throughput_benchmark_parameters_32bits() -> Vec<(String, CryptoParametersReco
|
||||
|
||||
fn multi_bit_benchmark_parameters_64bits(
|
||||
) -> Vec<(String, CryptoParametersRecord<u64>, LweBskGroupingFactor)> {
|
||||
let parameters = if cfg!(feature = "gpu") {
|
||||
vec![
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_2_CARRY_2_KS_PBS_TUNIFORM_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_1_CARRY_1_KS_PBS_GAUSSIAN_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_2_CARRY_2_KS_PBS_GAUSSIAN_2M64,
|
||||
PARAM_GPU_MULTI_BIT_GROUP_3_MESSAGE_3_CARRY_3_KS_PBS_GAUSSIAN_2M64,
|
||||
]
|
||||
} else {
|
||||
vec![
|
||||
V1_0_PARAM_MULTI_BIT_GROUP_2_MESSAGE_1_CARRY_1_KS_PBS_GAUSSIAN_2M64,
|
||||
V1_0_PARAM_MULTI_BIT_GROUP_2_MESSAGE_2_CARRY_2_KS_PBS_GAUSSIAN_2M64,
|
||||
V1_0_PARAM_MULTI_BIT_GROUP_2_MESSAGE_3_CARRY_3_KS_PBS_GAUSSIAN_2M64,
|
||||
V1_0_PARAM_MULTI_BIT_GROUP_3_MESSAGE_1_CARRY_1_KS_PBS_GAUSSIAN_2M64,
|
||||
V1_0_PARAM_MULTI_BIT_GROUP_3_MESSAGE_2_CARRY_2_KS_PBS_GAUSSIAN_2M64,
|
||||
V1_0_PARAM_MULTI_BIT_GROUP_3_MESSAGE_3_CARRY_3_KS_PBS_GAUSSIAN_2M64,
|
||||
]
|
||||
};
|
||||
|
||||
parameters
|
||||
.iter()
|
||||
.map(|params| {
|
||||
(
|
||||
params.name(),
|
||||
<MultiBitPBSParameters as Into<PBSParameters>>::into(*params)
|
||||
.to_owned()
|
||||
.into(),
|
||||
params.grouping_factor,
|
||||
match PARAMETERS_SET.get().unwrap() {
|
||||
ParametersSet::Default => SHORTINT_MULTI_BIT_BENCH_PARAMS
|
||||
.iter()
|
||||
.map(|params| {
|
||||
(
|
||||
params.name(),
|
||||
<MultiBitPBSParameters as Into<PBSParameters>>::into(*params)
|
||||
.to_owned()
|
||||
.into(),
|
||||
params.grouping_factor,
|
||||
)
|
||||
})
|
||||
.collect(),
|
||||
ParametersSet::All => {
|
||||
let desired_backend = if cfg!(feature = "gpu") {
|
||||
DesiredBackend::Gpu
|
||||
} else {
|
||||
DesiredBackend::Cpu
|
||||
};
|
||||
filter_parameters(
|
||||
&VEC_ALL_MULTI_BIT_PBS_PARAMETERS,
|
||||
DesiredNoiseDistribution::Both,
|
||||
desired_backend,
|
||||
)
|
||||
})
|
||||
.collect()
|
||||
.into_iter()
|
||||
.map(|(params, name)| {
|
||||
(
|
||||
name.to_string(),
|
||||
<MultiBitPBSParameters as Into<PBSParameters>>::into(*params)
|
||||
.to_owned()
|
||||
.into(),
|
||||
params.grouping_factor,
|
||||
)
|
||||
})
|
||||
.collect()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn mem_optimized_pbs<Scalar: UnsignedTorus + CastInto<usize> + Serialize>(
|
||||
@@ -133,8 +185,8 @@ fn mem_optimized_pbs<Scalar: UnsignedTorus + CastInto<usize> + Serialize>(
|
||||
let bench_name = "core_crypto::pbs_mem_optimized";
|
||||
let mut bench_group = c.benchmark_group(bench_name);
|
||||
bench_group
|
||||
.sample_size(15)
|
||||
.measurement_time(std::time::Duration::from_secs(60));
|
||||
.sample_size(10)
|
||||
.measurement_time(std::time::Duration::from_secs(30));
|
||||
|
||||
// Create the PRNG
|
||||
let mut seeder = new_seeder();
|
||||
@@ -359,12 +411,17 @@ fn multi_bit_pbs<
|
||||
>(
|
||||
c: &mut Criterion,
|
||||
parameters: &[(String, CryptoParametersRecord<Scalar>, LweBskGroupingFactor)],
|
||||
deterministic_pbs: bool,
|
||||
) {
|
||||
let bench_name = "core_crypto::multi_bit_pbs";
|
||||
let bench_name = if deterministic_pbs {
|
||||
"core_crypto::multi_bit_deterministic_pbs"
|
||||
} else {
|
||||
"core_crypto::multi_bit_pbs"
|
||||
};
|
||||
let mut bench_group = c.benchmark_group(bench_name);
|
||||
bench_group
|
||||
.sample_size(15)
|
||||
.measurement_time(std::time::Duration::from_secs(60));
|
||||
.sample_size(10)
|
||||
.measurement_time(std::time::Duration::from_secs(30));
|
||||
|
||||
// Create the PRNG
|
||||
let mut seeder = new_seeder();
|
||||
@@ -419,98 +476,12 @@ fn multi_bit_pbs<
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
);
|
||||
|
||||
let id = format!("{bench_name}::{name}::parallelized");
|
||||
bench_group.bench_function(&id, |b| {
|
||||
b.iter(|| {
|
||||
multi_bit_programmable_bootstrap_lwe_ciphertext(
|
||||
&lwe_ciphertext_in,
|
||||
&mut out_pbs_ct,
|
||||
&accumulator.as_view(),
|
||||
&multi_bit_bsk,
|
||||
ThreadCount(10),
|
||||
false,
|
||||
);
|
||||
black_box(&mut out_pbs_ct);
|
||||
})
|
||||
});
|
||||
|
||||
let bit_size = params.message_modulus.unwrap().ilog2();
|
||||
write_to_json(
|
||||
&id,
|
||||
*params,
|
||||
name,
|
||||
"pbs",
|
||||
&OperatorType::Atomic,
|
||||
bit_size,
|
||||
vec![bit_size],
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
fn multi_bit_deterministic_pbs<
|
||||
Scalar: UnsignedTorus + CastInto<usize> + CastFrom<usize> + Default + Serialize + Sync,
|
||||
>(
|
||||
c: &mut Criterion,
|
||||
parameters: &[(String, CryptoParametersRecord<Scalar>, LweBskGroupingFactor)],
|
||||
) {
|
||||
let bench_name = "core_crypto::multi_bit_deterministic_pbs";
|
||||
let mut bench_group = c.benchmark_group(bench_name);
|
||||
bench_group
|
||||
.sample_size(15)
|
||||
.measurement_time(std::time::Duration::from_secs(60));
|
||||
|
||||
// Create the PRNG
|
||||
let mut seeder = new_seeder();
|
||||
let seeder = seeder.as_mut();
|
||||
let mut encryption_generator =
|
||||
EncryptionRandomGenerator::<DefaultRandomGenerator>::new(seeder.seed(), seeder);
|
||||
let mut secret_generator = SecretRandomGenerator::<DefaultRandomGenerator>::new(seeder.seed());
|
||||
|
||||
for (name, params, grouping_factor) in parameters.iter() {
|
||||
// Create the LweSecretKey
|
||||
let input_lwe_secret_key = allocate_and_generate_new_binary_lwe_secret_key(
|
||||
params.lwe_dimension.unwrap(),
|
||||
&mut secret_generator,
|
||||
);
|
||||
let output_glwe_secret_key: GlweSecretKeyOwned<Scalar> =
|
||||
allocate_and_generate_new_binary_glwe_secret_key(
|
||||
params.glwe_dimension.unwrap(),
|
||||
params.polynomial_size.unwrap(),
|
||||
&mut secret_generator,
|
||||
);
|
||||
let output_lwe_secret_key = output_glwe_secret_key.into_lwe_secret_key();
|
||||
|
||||
let multi_bit_bsk = FourierLweMultiBitBootstrapKey::new(
|
||||
params.lwe_dimension.unwrap(),
|
||||
params.glwe_dimension.unwrap().to_glwe_size(),
|
||||
params.polynomial_size.unwrap(),
|
||||
params.pbs_base_log.unwrap(),
|
||||
params.pbs_level.unwrap(),
|
||||
*grouping_factor,
|
||||
);
|
||||
|
||||
// Allocate a new LweCiphertext and encrypt our plaintext
|
||||
let lwe_ciphertext_in = allocate_and_encrypt_new_lwe_ciphertext(
|
||||
&input_lwe_secret_key,
|
||||
Plaintext(Scalar::ZERO),
|
||||
params.lwe_noise_distribution.unwrap(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
&mut encryption_generator,
|
||||
);
|
||||
|
||||
let accumulator = GlweCiphertext::new(
|
||||
Scalar::ZERO,
|
||||
params.glwe_dimension.unwrap().to_glwe_size(),
|
||||
params.polynomial_size.unwrap(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
);
|
||||
|
||||
// Allocate the LweCiphertext to store the result of the PBS
|
||||
let mut out_pbs_ct = LweCiphertext::new(
|
||||
Scalar::ZERO,
|
||||
output_lwe_secret_key.lwe_dimension().to_lwe_size(),
|
||||
params.ciphertext_modulus.unwrap(),
|
||||
);
|
||||
let thread_count = multi_bit_num_threads(
|
||||
params.message_modulus.unwrap(),
|
||||
params.carry_modulus.unwrap(),
|
||||
grouping_factor.0,
|
||||
)
|
||||
.unwrap() as usize;
|
||||
|
||||
let id = format!("{bench_name}::{name}::parallelized");
|
||||
bench_group.bench_function(&id, |b| {
|
||||
@@ -520,8 +491,8 @@ fn multi_bit_deterministic_pbs<
|
||||
&mut out_pbs_ct,
|
||||
&accumulator.as_view(),
|
||||
&multi_bit_bsk,
|
||||
ThreadCount(10),
|
||||
true,
|
||||
ThreadCount(thread_count),
|
||||
deterministic_pbs,
|
||||
);
|
||||
black_box(&mut out_pbs_ct);
|
||||
})
|
||||
@@ -544,8 +515,8 @@ fn mem_optimized_pbs_ntt(c: &mut Criterion) {
|
||||
let bench_name = "core_crypto::pbs_ntt";
|
||||
let mut bench_group = c.benchmark_group(bench_name);
|
||||
bench_group
|
||||
.sample_size(15)
|
||||
.measurement_time(std::time::Duration::from_secs(60));
|
||||
.sample_size(10)
|
||||
.measurement_time(std::time::Duration::from_secs(30));
|
||||
|
||||
// Create the PRNG
|
||||
let mut seeder = new_seeder();
|
||||
@@ -698,8 +669,8 @@ fn pbs_throughput<Scalar: UnsignedTorus + CastInto<usize> + Sync + Send + Serial
|
||||
let bench_name = "core_crypto::pbs_throughput";
|
||||
let mut bench_group = c.benchmark_group(bench_name);
|
||||
bench_group
|
||||
.sample_size(15)
|
||||
.measurement_time(std::time::Duration::from_secs(60));
|
||||
.sample_size(10)
|
||||
.measurement_time(std::time::Duration::from_secs(30));
|
||||
|
||||
// Create the PRNG
|
||||
let mut seeder = new_seeder();
|
||||
@@ -817,8 +788,14 @@ fn pbs_throughput<Scalar: UnsignedTorus + CastInto<usize> + Sync + Send + Serial
|
||||
|
||||
#[cfg(feature = "gpu")]
|
||||
mod cuda {
|
||||
use super::{multi_bit_benchmark_parameters_64bits, throughput_benchmark_parameters_64bits};
|
||||
use crate::utilities::{write_to_json, CryptoParametersRecord, EnvConfig, OperatorType};
|
||||
use super::{
|
||||
benchmark_parameters_64bits, multi_bit_benchmark_parameters_64bits,
|
||||
throughput_benchmark_parameters_64bits,
|
||||
};
|
||||
use crate::utilities::{
|
||||
write_to_json, CryptoParametersRecord, EnvConfig, OperatorType,
|
||||
GPU_MAX_SUPPORTED_POLYNOMIAL_SIZE,
|
||||
};
|
||||
use criterion::{black_box, Criterion};
|
||||
use serde::Serialize;
|
||||
use tfhe::core_crypto::gpu::glwe_ciphertext_list::CudaGlweCiphertextList;
|
||||
@@ -831,43 +808,6 @@ mod cuda {
|
||||
cuda_programmable_bootstrap_lwe_ciphertext, CudaStreams,
|
||||
};
|
||||
use tfhe::core_crypto::prelude::*;
|
||||
use tfhe::keycache::NamedParam;
|
||||
use tfhe::shortint::parameters::current_params::*;
|
||||
use tfhe::shortint::parameters::*;
|
||||
use tfhe::shortint::{ClassicPBSParameters, PBSParameters};
|
||||
|
||||
const SHORTINT_CUDA_BENCH_PARAMS: [ClassicPBSParameters; 14] = [
|
||||
// TUniform
|
||||
PARAM_MESSAGE_2_CARRY_2_KS_PBS_TUNIFORM_2M128,
|
||||
// Gaussian
|
||||
V1_0_PARAM_MESSAGE_1_CARRY_0_KS_PBS_GAUSSIAN_2M128,
|
||||
V1_0_PARAM_MESSAGE_1_CARRY_1_KS_PBS_GAUSSIAN_2M128,
|
||||
V1_0_PARAM_MESSAGE_2_CARRY_0_KS_PBS_GAUSSIAN_2M128,
|
||||
V1_0_PARAM_MESSAGE_2_CARRY_1_KS_PBS_GAUSSIAN_2M128,
|
||||
V1_0_PARAM_MESSAGE_2_CARRY_2_KS_PBS_GAUSSIAN_2M128,
|
||||
V1_0_PARAM_MESSAGE_3_CARRY_0_KS_PBS_GAUSSIAN_2M128,
|
||||
V1_0_PARAM_MESSAGE_3_CARRY_2_KS_PBS_GAUSSIAN_2M128,
|
||||
V1_0_PARAM_MESSAGE_3_CARRY_3_KS_PBS_GAUSSIAN_2M128,
|
||||
V1_0_PARAM_MESSAGE_4_CARRY_0_KS_PBS_GAUSSIAN_2M128,
|
||||
V1_0_PARAM_MESSAGE_4_CARRY_3_KS_PBS_GAUSSIAN_2M128,
|
||||
V1_0_PARAM_MESSAGE_5_CARRY_0_KS_PBS_GAUSSIAN_2M128,
|
||||
V1_0_PARAM_MESSAGE_6_CARRY_0_KS_PBS_GAUSSIAN_2M128,
|
||||
V1_0_PARAM_MESSAGE_7_CARRY_0_KS_PBS_GAUSSIAN_2M128,
|
||||
];
|
||||
|
||||
fn cuda_benchmark_parameters_64bits() -> Vec<(String, CryptoParametersRecord<u64>)> {
|
||||
SHORTINT_CUDA_BENCH_PARAMS
|
||||
.iter()
|
||||
.map(|params| {
|
||||
(
|
||||
params.name(),
|
||||
<ClassicPBSParameters as Into<PBSParameters>>::into(*params)
|
||||
.to_owned()
|
||||
.into(),
|
||||
)
|
||||
})
|
||||
.collect()
|
||||
}
|
||||
|
||||
fn cuda_pbs<Scalar: UnsignedTorus + CastInto<usize> + Serialize>(
|
||||
c: &mut Criterion,
|
||||
@@ -876,8 +816,8 @@ mod cuda {
|
||||
let bench_name = "core_crypto::cuda::pbs";
|
||||
let mut bench_group = c.benchmark_group(bench_name);
|
||||
bench_group
|
||||
.sample_size(15)
|
||||
.measurement_time(std::time::Duration::from_secs(60));
|
||||
.sample_size(10)
|
||||
.measurement_time(std::time::Duration::from_secs(30));
|
||||
|
||||
// Create the PRNG
|
||||
let mut seeder = new_seeder();
|
||||
@@ -891,6 +831,11 @@ mod cuda {
|
||||
let stream = CudaStreams::new_single_gpu(GpuIndex::new(gpu_index));
|
||||
|
||||
for (name, params) in parameters.iter() {
|
||||
if params.polynomial_size.unwrap().0 > GPU_MAX_SUPPORTED_POLYNOMIAL_SIZE {
|
||||
println!("[WARNING] polynomial size is too large for parameters set '{}' (max: {}, got: {})", name, GPU_MAX_SUPPORTED_POLYNOMIAL_SIZE, params.polynomial_size.unwrap().0);
|
||||
continue;
|
||||
}
|
||||
|
||||
// Create the LweSecretKey
|
||||
let input_lwe_secret_key = allocate_and_generate_new_binary_lwe_secret_key(
|
||||
params.lwe_dimension.unwrap(),
|
||||
@@ -997,8 +942,8 @@ mod cuda {
|
||||
let bench_name = "core_crypto::cuda::multi_bit_pbs";
|
||||
let mut bench_group = c.benchmark_group(bench_name);
|
||||
bench_group
|
||||
.sample_size(15)
|
||||
.measurement_time(std::time::Duration::from_secs(60));
|
||||
.sample_size(10)
|
||||
.measurement_time(std::time::Duration::from_secs(30));
|
||||
|
||||
// Create the PRNG
|
||||
let mut seeder = new_seeder();
|
||||
@@ -1012,6 +957,11 @@ mod cuda {
|
||||
let stream = CudaStreams::new_single_gpu(GpuIndex::new(gpu_index));
|
||||
|
||||
for (name, params, grouping_factor) in parameters.iter() {
|
||||
if params.polynomial_size.unwrap().0 > GPU_MAX_SUPPORTED_POLYNOMIAL_SIZE {
|
||||
println!("[WARNING] polynomial size is too large for parameters set '{}' (max: {}, got: {})", name, GPU_MAX_SUPPORTED_POLYNOMIAL_SIZE, params.polynomial_size.unwrap().0);
|
||||
continue;
|
||||
}
|
||||
|
||||
// Create the LweSecretKey
|
||||
let input_lwe_secret_key = allocate_and_generate_new_binary_lwe_secret_key(
|
||||
params.lwe_dimension.unwrap(),
|
||||
@@ -1119,8 +1069,8 @@ mod cuda {
|
||||
let bench_name = "core_crypto::cuda::pbs_throughput";
|
||||
let mut bench_group = c.benchmark_group(bench_name);
|
||||
bench_group
|
||||
.sample_size(15)
|
||||
.measurement_time(std::time::Duration::from_secs(60));
|
||||
.sample_size(10)
|
||||
.measurement_time(std::time::Duration::from_secs(30));
|
||||
|
||||
// Create the PRNG
|
||||
let mut seeder = new_seeder();
|
||||
@@ -1134,6 +1084,11 @@ mod cuda {
|
||||
let stream = CudaStreams::new_single_gpu(GpuIndex::new(gpu_index));
|
||||
|
||||
for (name, params) in parameters.iter() {
|
||||
if params.polynomial_size.unwrap().0 > GPU_MAX_SUPPORTED_POLYNOMIAL_SIZE {
|
||||
println!("[WARNING] polynomial size is too large for parameters set '{}' (max: {}, got: {})", name, GPU_MAX_SUPPORTED_POLYNOMIAL_SIZE, params.polynomial_size.unwrap().0);
|
||||
continue;
|
||||
}
|
||||
|
||||
let input_lwe_secret_key = allocate_and_generate_new_binary_lwe_secret_key(
|
||||
params.lwe_dimension.unwrap(),
|
||||
&mut secret_generator,
|
||||
@@ -1259,8 +1214,8 @@ mod cuda {
|
||||
let bench_name = "core_crypto::cuda::multi_bit_pbs_throughput";
|
||||
let mut bench_group = c.benchmark_group(bench_name);
|
||||
bench_group
|
||||
.sample_size(15)
|
||||
.measurement_time(std::time::Duration::from_secs(60));
|
||||
.sample_size(10)
|
||||
.measurement_time(std::time::Duration::from_secs(30));
|
||||
|
||||
// Create the PRNG
|
||||
let mut seeder = new_seeder();
|
||||
@@ -1274,6 +1229,11 @@ mod cuda {
|
||||
let stream = CudaStreams::new_single_gpu(GpuIndex::new(gpu_index));
|
||||
|
||||
for (name, params, grouping_factor) in parameters.iter() {
|
||||
if params.polynomial_size.unwrap().0 > GPU_MAX_SUPPORTED_POLYNOMIAL_SIZE {
|
||||
println!("[WARNING] polynomial size is too large for parameters set '{}' (max: {}, got: {})", name, GPU_MAX_SUPPORTED_POLYNOMIAL_SIZE, params.polynomial_size.unwrap().0);
|
||||
continue;
|
||||
}
|
||||
|
||||
let input_lwe_secret_key = allocate_and_generate_new_binary_lwe_secret_key(
|
||||
params.lwe_dimension.unwrap(),
|
||||
&mut secret_generator,
|
||||
@@ -1399,7 +1359,7 @@ mod cuda {
|
||||
|
||||
pub fn cuda_pbs_group() {
|
||||
let mut criterion: Criterion<_> = (Criterion::default()).configure_from_args();
|
||||
cuda_pbs(&mut criterion, &cuda_benchmark_parameters_64bits());
|
||||
cuda_pbs(&mut criterion, &benchmark_parameters_64bits());
|
||||
}
|
||||
|
||||
pub fn cuda_pbs_throughput_group() {
|
||||
@@ -1434,8 +1394,16 @@ pub fn pbs_group() {
|
||||
|
||||
pub fn multi_bit_pbs_group() {
|
||||
let mut criterion: Criterion<_> = (Criterion::default()).configure_from_args();
|
||||
multi_bit_pbs(&mut criterion, &multi_bit_benchmark_parameters_64bits());
|
||||
multi_bit_deterministic_pbs(&mut criterion, &multi_bit_benchmark_parameters_64bits());
|
||||
multi_bit_pbs(
|
||||
&mut criterion,
|
||||
&multi_bit_benchmark_parameters_64bits(),
|
||||
false,
|
||||
);
|
||||
multi_bit_pbs(
|
||||
&mut criterion,
|
||||
&multi_bit_benchmark_parameters_64bits(),
|
||||
true,
|
||||
);
|
||||
}
|
||||
|
||||
pub fn pbs_throughput_group() {
|
||||
@@ -1444,12 +1412,28 @@ pub fn pbs_throughput_group() {
|
||||
pbs_throughput(&mut criterion, &throughput_benchmark_parameters_32bits());
|
||||
}
|
||||
|
||||
#[cfg(not(feature = "gpu"))]
|
||||
criterion_main!(pbs_group, multi_bit_pbs_group, pbs_throughput_group);
|
||||
#[cfg(feature = "gpu")]
|
||||
criterion_main!(
|
||||
cuda_pbs_group,
|
||||
cuda_multi_bit_pbs_group,
|
||||
cuda_pbs_throughput_group,
|
||||
cuda_multi_bit_pbs_throughput_group
|
||||
);
|
||||
fn go_through_gpu_bench_groups() {
|
||||
cuda_pbs_group();
|
||||
cuda_multi_bit_pbs_group();
|
||||
cuda_pbs_throughput_group();
|
||||
cuda_multi_bit_pbs_throughput_group();
|
||||
}
|
||||
|
||||
#[cfg(not(feature = "gpu"))]
|
||||
fn go_through_cpu_bench_groups() {
|
||||
pbs_group();
|
||||
multi_bit_pbs_group();
|
||||
pbs_throughput_group();
|
||||
}
|
||||
|
||||
fn main() {
|
||||
init_parameters_set();
|
||||
|
||||
#[cfg(feature = "gpu")]
|
||||
go_through_gpu_bench_groups();
|
||||
#[cfg(not(feature = "gpu"))]
|
||||
go_through_cpu_bench_groups();
|
||||
|
||||
Criterion::default().configure_from_args().final_summary();
|
||||
}
|
||||
|
||||
@@ -1,5 +1,7 @@
|
||||
use serde::Serialize;
|
||||
use std::collections::HashMap;
|
||||
use std::path::PathBuf;
|
||||
use std::sync::OnceLock;
|
||||
use std::{env, fs};
|
||||
use tfhe::core_crypto::prelude::*;
|
||||
|
||||
@@ -46,7 +48,8 @@ pub mod shortint_utils {
|
||||
ShortintKeySwitchingParameters, PARAM_MESSAGE_2_CARRY_2_KS_PBS_TUNIFORM_2M128,
|
||||
};
|
||||
use tfhe::shortint::{
|
||||
ClassicPBSParameters, MultiBitPBSParameters, PBSParameters, ShortintParameterSet,
|
||||
CarryModulus, ClassicPBSParameters, MessageModulus, MultiBitPBSParameters, PBSParameters,
|
||||
ShortintParameterSet,
|
||||
};
|
||||
|
||||
/// An iterator that yields a succession of combinations
|
||||
@@ -185,6 +188,181 @@ pub mod shortint_utils {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// This array has been built according to performance benchmarks measuring latency over a
|
||||
// matrix of 4 parameters set, 3 grouping factor and a wide range of threads values.
|
||||
// The values available here as u64 are the optimal number of threads to use for a given triplet
|
||||
// representing one or more parameters set.
|
||||
const MULTI_BIT_THREADS_ARRAY: [((MessageModulus, CarryModulus, LweBskGroupingFactor), u64);
|
||||
12] = [
|
||||
(
|
||||
(MessageModulus(2), CarryModulus(2), LweBskGroupingFactor(2)),
|
||||
5,
|
||||
),
|
||||
(
|
||||
(MessageModulus(4), CarryModulus(4), LweBskGroupingFactor(2)),
|
||||
5,
|
||||
),
|
||||
(
|
||||
(MessageModulus(8), CarryModulus(8), LweBskGroupingFactor(2)),
|
||||
5,
|
||||
),
|
||||
(
|
||||
(
|
||||
MessageModulus(16),
|
||||
CarryModulus(16),
|
||||
LweBskGroupingFactor(2),
|
||||
),
|
||||
5,
|
||||
),
|
||||
(
|
||||
(MessageModulus(2), CarryModulus(2), LweBskGroupingFactor(3)),
|
||||
7,
|
||||
),
|
||||
(
|
||||
(MessageModulus(4), CarryModulus(4), LweBskGroupingFactor(3)),
|
||||
9,
|
||||
),
|
||||
(
|
||||
(MessageModulus(8), CarryModulus(8), LweBskGroupingFactor(3)),
|
||||
10,
|
||||
),
|
||||
(
|
||||
(
|
||||
MessageModulus(16),
|
||||
CarryModulus(16),
|
||||
LweBskGroupingFactor(3),
|
||||
),
|
||||
10,
|
||||
),
|
||||
(
|
||||
(MessageModulus(2), CarryModulus(2), LweBskGroupingFactor(4)),
|
||||
11,
|
||||
),
|
||||
(
|
||||
(MessageModulus(4), CarryModulus(4), LweBskGroupingFactor(4)),
|
||||
13,
|
||||
),
|
||||
(
|
||||
(MessageModulus(8), CarryModulus(8), LweBskGroupingFactor(4)),
|
||||
11,
|
||||
),
|
||||
(
|
||||
(
|
||||
MessageModulus(16),
|
||||
CarryModulus(16),
|
||||
LweBskGroupingFactor(4),
|
||||
),
|
||||
11,
|
||||
),
|
||||
];
|
||||
|
||||
/// Define the number of threads to use for parameters doing multithreaded programmable
|
||||
/// bootstrapping.
|
||||
///
|
||||
/// Parameters must have the same values between message and carry modulus.
|
||||
/// Grouping factor 2, 3 and 4 are the only ones that are supported.
|
||||
#[allow(dead_code)]
|
||||
pub fn multi_bit_num_threads(
|
||||
message_modulus: u64,
|
||||
carry_modulus: u64,
|
||||
grouping_factor: usize,
|
||||
) -> Option<u64> {
|
||||
// TODO Implement an interpolation mechanism for X_Y parameters set
|
||||
if message_modulus != carry_modulus || [2, 3, 4].contains(&(grouping_factor as i32)) {
|
||||
return None;
|
||||
}
|
||||
let thread_map: HashMap<(MessageModulus, CarryModulus, LweBskGroupingFactor), u64> =
|
||||
HashMap::from_iter(MULTI_BIT_THREADS_ARRAY);
|
||||
thread_map
|
||||
.get(&(
|
||||
MessageModulus(message_modulus),
|
||||
CarryModulus(carry_modulus),
|
||||
LweBskGroupingFactor(grouping_factor),
|
||||
))
|
||||
.copied()
|
||||
}
|
||||
|
||||
#[allow(dead_code)]
|
||||
pub static PARAMETERS_SET: OnceLock<ParametersSet> = OnceLock::new();
|
||||
|
||||
pub enum ParametersSet {
|
||||
Default,
|
||||
All,
|
||||
}
|
||||
|
||||
#[allow(dead_code)]
|
||||
impl ParametersSet {
|
||||
pub fn from_env() -> Result<Self, String> {
|
||||
let raw_value = env::var("__TFHE_RS_PARAMS_SET").unwrap_or("default".to_string());
|
||||
match raw_value.to_lowercase().as_str() {
|
||||
"default" => Ok(ParametersSet::Default),
|
||||
"all" => Ok(ParametersSet::All),
|
||||
_ => Err(format!("parameters set '{raw_value}' is not supported")),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[allow(dead_code)]
|
||||
pub fn init_parameters_set() {
|
||||
PARAMETERS_SET.get_or_init(|| ParametersSet::from_env().unwrap());
|
||||
}
|
||||
|
||||
#[allow(dead_code)]
|
||||
#[derive(Clone, Copy, Debug)]
|
||||
pub enum DesiredNoiseDistribution {
|
||||
Gaussian,
|
||||
TUniform,
|
||||
Both,
|
||||
}
|
||||
|
||||
#[allow(dead_code)]
|
||||
#[derive(Clone, Copy, Debug)]
|
||||
pub enum DesiredBackend {
|
||||
Cpu,
|
||||
Gpu,
|
||||
}
|
||||
|
||||
#[allow(dead_code)]
|
||||
impl DesiredBackend {
|
||||
fn matches_parameter_name_backend(&self, param_name: &str) -> bool {
|
||||
matches!(
|
||||
(self, param_name.to_lowercase().contains("gpu")),
|
||||
(DesiredBackend::Cpu, false) | (DesiredBackend::Gpu, true)
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
#[allow(dead_code)]
|
||||
pub fn filter_parameters<'a, P: Copy + Into<PBSParameters>>(
|
||||
params: &[(&'a P, &'a str)],
|
||||
desired_noise_distribution: DesiredNoiseDistribution,
|
||||
desired_backend: DesiredBackend,
|
||||
) -> Vec<(&'a P, &'a str)> {
|
||||
params
|
||||
.iter()
|
||||
.filter_map(|(p, name)| {
|
||||
let temp_param: PBSParameters = (**p).into();
|
||||
|
||||
match (
|
||||
temp_param.lwe_noise_distribution(),
|
||||
desired_noise_distribution,
|
||||
) {
|
||||
// If it's one of the pairs, we continue the process.
|
||||
(DynamicDistribution::Gaussian(_), DesiredNoiseDistribution::Gaussian)
|
||||
| (DynamicDistribution::TUniform(_), DesiredNoiseDistribution::TUniform)
|
||||
| (_, DesiredNoiseDistribution::Both) => (),
|
||||
_ => return None,
|
||||
}
|
||||
|
||||
if !desired_backend.matches_parameter_name_backend(name) {
|
||||
return None;
|
||||
};
|
||||
|
||||
Some((*p, *name))
|
||||
})
|
||||
.collect()
|
||||
}
|
||||
}
|
||||
|
||||
#[allow(unused_imports)]
|
||||
@@ -357,6 +535,10 @@ pub fn write_to_json<
|
||||
fs::write(params_directory, serde_json::to_string(&record).unwrap()).unwrap();
|
||||
}
|
||||
|
||||
#[allow(dead_code)]
|
||||
#[cfg(feature = "gpu")]
|
||||
pub const GPU_MAX_SUPPORTED_POLYNOMIAL_SIZE: usize = 16384;
|
||||
|
||||
const FAST_BENCH_BIT_SIZES: [usize; 1] = [64];
|
||||
const BENCH_BIT_SIZES: [usize; 8] = [4, 8, 16, 32, 40, 64, 128, 256];
|
||||
const MULTI_BIT_CPU_SIZES: [usize; 6] = [4, 8, 16, 32, 40, 64];
|
||||
|
||||
@@ -22,18 +22,27 @@ layout:
|
||||
|
||||
Learn the basics of TFHE-rs, set it up, and make it run with ease.
|
||||
|
||||
<table data-view="cards"><thead><tr><th></th><th></th><th data-hidden data-card-target data-type="content-ref"></th><th data-hidden data-card-cover data-type="files"></th></tr></thead><tbody><tr><td><strong>What is TFHE-rs?</strong></td><td>Understand TFHE-rs library and basic cryptographic concepts</td><td><a href="getting_started/readme.md">getting_started.md</a></td><td><a href=".gitbook/assets/start1.png">start1.png</a></td></tr><tr><td><strong>Installation</strong></td><td>Follow the step by step guide to import TFHE-rs in your project</td><td><a href="getting_started/installation.md">installation.md</a></td><td><a href=".gitbook/assets/start2.png">start2.png</a></td></tr><tr><td><strong>Quick start</strong></td><td>See a full example of using TFHE-rs to compute on encrypted data</td><td><a href="getting_started/quick_start.md">quick_start.md</a></td><td><a href=".gitbook/assets/start3.png">start3.png</a></td></tr></tbody></table>
|
||||
<table data-view="cards"><thead><tr><th></th><th></th><th data-hidden data-card-target data-type="content-ref"></th><th data-hidden data-card-cover data-type="files"></th></tr></thead><tbody><tr><td><strong>What is TFHE-rs?</strong></td><td>Understand TFHE-rs library and basic cryptographic concepts</td><td><a href="getting_started/README.md">getting_started</a></td><td><a href=".gitbook/assets/start1.png">start1.png</a></td></tr><tr><td><strong>Installation</strong></td><td>Follow the step by step guide to import TFHE-rs in your project</td><td><a href="getting_started/installation.md">installation.md</a></td><td><a href=".gitbook/assets/start2.png">start2.png</a></td></tr><tr><td><strong>Quick start</strong></td><td>See a full example of using TFHE-rs to compute on encrypted data</td><td><a href="getting_started/quick_start.md">quick_start.md</a></td><td><a href=".gitbook/assets/start3.png">start3.png</a></td></tr></tbody></table>
|
||||
|
||||
## Build with TFHE-rs
|
||||
|
||||
Start building with TFHE-rs by exploring its core features, discovering essential guides, and learning more with user-friendly tutorials.
|
||||
|
||||
<table data-view="cards"><thead><tr><th></th><th></th><th></th><th data-hidden data-card-cover data-type="files"></th></tr></thead><tbody><tr><td><strong>Fundamentals</strong></td><td>Explore the core features.</td><td><ul><li><a href="fundamentals/configure-and-generate-keys.md">Configure</a></li><li><a href="fundamentals/encrypt-data.md">Encrypt data</a></li></ul></td><td><a href=".gitbook/assets/build1.png">build1.png</a></td></tr><tr><td><strong>Guides</strong></td><td>Deploy your project.</td><td><ul><li><a href="guides/run_on_gpu.md">Run on GPU</a></li><li><a href="guides/rust_configuration.md">Configure Rust</a></li></ul></td><td><a href=".gitbook/assets/build2.png">build2.png</a></td></tr><tr><td><strong>Tutorials</strong></td><td>Learn more with tutorials.</td><td><ul><li><a href="tutorials/see-all-tutorials.md#start-here">Start here</a></li><li><a href="tutorials/see-all-tutorials.md#go-further">Go further</a></li></ul></td><td><a href=".gitbook/assets/build3.png">build3.png</a></td></tr></tbody></table>
|
||||
<table data-view="cards"><thead><tr><th></th><th></th><th></th><th data-hidden data-card-cover data-type="files"></th></tr></thead><tbody><tr><td><strong>FHE Computations</strong></td><td>Run FHE computation on encrypted data.</td><td><ul><li><a href="fhe-computation/types/">Types </a></li><li><a href="fhe-computation/operations/">Operations</a></li></ul></td><td><a href=".gitbook/assets/build1.png">build1.png</a></td></tr><tr><td><strong>Configuration</strong></td><td>Advanced configuration for better performance.</td><td><ul><li><a href="configuration/rust_configuration.md">Advanced Rust </a></li><li><a href="configuration/run_on_gpu.md">GPU acceleration</a></li></ul></td><td><a href=".gitbook/assets/build2.png">build2.png</a></td></tr><tr><td><strong>Integration</strong></td><td>Use TFHE-rs in different contexts or platforms..</td><td><ul><li><a href="integration/c_api.md">C API</a></li><li><a href="integration/js_on_wasm_api.md">JS on WASM API</a></li></ul></td><td><a href=".gitbook/assets/build3.png">build3.png</a></td></tr></tbody></table>
|
||||
|
||||
## Explore more
|
||||
|
||||
Access to additional resources and join the Zama community.
|
||||
|
||||
### Tutorials
|
||||
|
||||
Explore step-by-step guides that walk you through real-world uses of TFHE-rs. 
|
||||
|
||||
* [Homomorphic parity bit](tutorials/parity_bit.md): Learn how to implement a parity bit calculation over encrypted data
|
||||
* [Homomorphic case changing on ASCII string](tutorials/ascii_fhe_string.md): See how to process string data securely by changing cases while keeping the data encrypted.
|
||||
* [SHA256 with Boolean API](tutorials/sha256_bool.md): Delve into a more complex example: implementing the SHA256 hash function entirely on encrypted boolean values.
|
||||
* [All tutorials](tutorials/see-all-tutorials.md): A complete list of all available tutorials in one place.tutorials: A complete list of all available tutorials in one place.
|
||||
|
||||
### References & Explanations
|
||||
|
||||
Take a deep dive into TFHE-rs, exploring APIs from the highest to the lowest level of abstraction and accessing additional resources for in-depth explanations.
|
||||
@@ -54,10 +63,10 @@ Ask technical questions and discuss with the community. Our team of experts usua
|
||||
|
||||
Collaborate with us to advance the FHE spaces and drive innovation together.
|
||||
|
||||
* [Contribute to TFHE-rs](dev/contributing.md)
|
||||
* [Contribute to TFHE-rs](../../CONTRIBUTING.md)
|
||||
* [Check the latest release note](https://github.com/zama-ai/tfhe-rs/releases)
|
||||
* [Request a feature](https://github.com/zama-ai/tfhe-rs/issues/new?assignees=\&labels=feature\_request\&projects=\&template=feature\_request.md\&title=)
|
||||
* [Report a bug](https://github.com/zama-ai/tfhe-rs/issues/new?assignees=\&labels=triage\_required\&projects=\&template=bug\_report.md\&title=)
|
||||
* [Request a feature](https://github.com/zama-ai/tfhe-rs/issues/new?assignees=\&labels=feature_request\&projects=\&template=feature_request.md\&title=)
|
||||
* [Report a bug](https://github.com/zama-ai/tfhe-rs/issues/new?assignees=\&labels=triage_required\&projects=\&template=bug_report.md\&title=)
|
||||
|
||||
***
|
||||
|
||||
|
||||
@@ -4,58 +4,79 @@
|
||||
|
||||
## Get Started
|
||||
|
||||
* [What is TFHE-rs?](getting\_started/readme.md)
|
||||
* [Installation](getting\_started/installation.md)
|
||||
* [Quick start](getting\_started/quick\_start.md)
|
||||
* [Types & Operations](getting\_started/operations.md)
|
||||
* [Benchmarks](getting\_started/benchmarks/summary.md)
|
||||
* [CPU Benchmarks](getting\_started/benchmarks/cpu\_benchmarks.md)
|
||||
* [GPU Benchmarks](getting\_started/benchmarks/gpu\_benchmarks.md)
|
||||
* [What is TFHE-rs?](getting_started/README.md)
|
||||
* [Installation](getting_started/installation.md)
|
||||
* [Quick start](getting_started/quick_start.md)
|
||||
* [Benchmarks](getting_started/benchmarks/README.md)
|
||||
* [CPU Benchmarks](getting_started/benchmarks/cpu/README.md)
|
||||
* [Integer](getting_started/benchmarks/cpu/cpu_integer_operations.md)
|
||||
* [Programmable bootstrapping](getting_started/benchmarks/cpu/cpu_programmable_bootstrapping.md)
|
||||
* [GPU Benchmarks](getting_started/benchmarks/gpu/README.md)
|
||||
* [Integer](getting_started/benchmarks/gpu/gpu_integer_operations.md)
|
||||
* [Programmable bootstrapping](getting_started/benchmarks/gpu/gpu_programmable_bootstrapping.md)
|
||||
* [Zero-knowledge proof benchmarks](getting_started/benchmarks/zk_proof_benchmarks.md)
|
||||
* [Security and cryptography](getting\_started/security\_and\_cryptography.md)
|
||||
* [Security and cryptography](getting_started/security_and_cryptography.md)
|
||||
|
||||
## Fundamentals
|
||||
## FHE Computation
|
||||
|
||||
* [Configuration and key generation](fundamentals/configure-and-generate-keys.md)
|
||||
* [Server key](fundamentals/set-the-server-key.md)
|
||||
* [Encryption](fundamentals/encrypt-data.md)
|
||||
* [Computation on encrypted data](fundamentals/compute.md)
|
||||
* [Decryption](fundamentals/decrypt-data.md)
|
||||
* [Encrypted pseudo random values](fundamentals/encrypted-prf.md)
|
||||
* [Serialization/deserialization](fundamentals/serialization.md)
|
||||
* [Compressing ciphertexts/keys](fundamentals/compress.md)
|
||||
* [Debugging](fundamentals/debug.md)
|
||||
* [Types](fhe-computation/types/README.md)
|
||||
* [Integer](fhe-computation/types/integer.md)
|
||||
* [Strings](fhe-computation/types/strings.md)
|
||||
* [Array](fhe-computation/types/array.md)
|
||||
* [Operations](fhe-computation/operations/README.md)
|
||||
* [Arithmetic operations](fhe-computation/operations/arithmetic-operations.md)
|
||||
* [Bitwise operations](fhe-computation/operations/bitwise-operations.md)
|
||||
* [Comparison operations](fhe-computation/operations/comparison-operations.md)
|
||||
* [Min/Max operations](fhe-computation/operations/min-max-operations.md)
|
||||
* [Ternary conditional operations](fhe-computation/operations/ternary-conditional-operations.md)
|
||||
* [Casting operations](fhe-computation/operations/casting-operations.md)
|
||||
* [Boolean Operations](fhe-computation/operations/boolean-operations.md)
|
||||
* [String Operations](fhe-computation/operations/string-operations.md)
|
||||
* [Core workflow](fhe-computation/compute/README.md)
|
||||
* [Configuration and key generation](fhe-computation/compute/configure-and-generate-keys.md)
|
||||
* [Server key](fhe-computation/compute/set-the-server-key.md)
|
||||
* [Encryption](fhe-computation/compute/encrypt-data.md)
|
||||
* [Decryption](fhe-computation/compute/decrypt-data.md)
|
||||
* [Parameters](fhe-computation/compute/parameters.md)
|
||||
* [Data handling](fhe-computation/data-handling/README.md)
|
||||
* [Compressing ciphertexts/keys](fhe-computation/data-handling/compress.md)
|
||||
* [Serialization/deserialization](fhe-computation/data-handling/serialization.md)
|
||||
* [Data versioning](fhe-computation/data-handling/data_versioning.md)
|
||||
* [Advanced features](fhe-computation/advanced-features/README.md)
|
||||
* [Encrypted pseudo random values](fhe-computation/advanced-features/encrypted-prf.md)
|
||||
* [Overflow detection](fhe-computation/advanced-features/overflow_operations.md)
|
||||
* [Public key encryption](fhe-computation/advanced-features/public_key.md)
|
||||
* [Trivial ciphertexts](fhe-computation/advanced-features/trivial_ciphertext.md)
|
||||
* [Zero-knowledge proofs](fhe-computation/advanced-features/zk-pok.md)
|
||||
* [Multi-threading with Rayon crate](fhe-computation/advanced-features/rayon_crate.md)
|
||||
* [Tooling](fhe-computation/tooling/README.md)
|
||||
* [PBS statistics](fhe-computation/tooling/pbs-stats.md)
|
||||
* [Generic trait bounds](fhe-computation/tooling/trait_bounds.md)
|
||||
* [Debugging](fhe-computation/tooling/debug.md)
|
||||
|
||||
## Guides
|
||||
## Configuration
|
||||
|
||||
* [Rust configuration](guides/rust\_configuration.md)
|
||||
* [GPU acceleration](guides/run\_on\_gpu.md)
|
||||
* [Overflow detection](guides/overflow\_operations.md)
|
||||
* [Data versioning](guides/data\_versioning.md)
|
||||
* [Public key encryption](guides/public\_key.md)
|
||||
* [Zero-knowledge proofs](guides/zk-pok.md)
|
||||
* [Generic trait bounds](guides/trait\_bounds.md)
|
||||
* [Parallelized PBS](guides/parallelized\_pbs.md)
|
||||
* [High-level API in C](guides/c\_api.md)
|
||||
* [JS on WASM API](guides/js\_on\_wasm\_api.md)
|
||||
* [Multi-threading with Rayon crate](guides/rayon\_crate.md)
|
||||
* [Trivial ciphertexts](guides/trivial\_ciphertext.md)
|
||||
* [PBS statistics](guides/pbs-stats.md)
|
||||
* [Array](guides/array.md)
|
||||
* [Strings](guides/strings.md)
|
||||
* [Advanced Rust setup](configuration/rust_configuration.md)
|
||||
* [GPU acceleration](configuration/run_on_gpu.md)
|
||||
* [Parallelized PBS](configuration/parallelized_pbs.md)
|
||||
|
||||
## Integration
|
||||
|
||||
* [JS on WASM API](integration/js_on_wasm_api.md)
|
||||
* [High-level API in C](integration/c_api.md)
|
||||
|
||||
## Tutorials
|
||||
|
||||
* [Homomorphic parity bit](tutorials/parity_bit.md)
|
||||
* [Homomorphic case changing on Ascii string](tutorials/ascii_fhe_string.md)
|
||||
* [SHA256 with Boolean API](tutorials/sha256_bool.md)
|
||||
* [All tutorials](tutorials/see-all-tutorials.md)
|
||||
* [Homomorphic parity bit](tutorials/parity\_bit.md)
|
||||
* [Homomorphic case changing on Ascii string](tutorials/ascii\_fhe\_string.md)
|
||||
* [SHA256 with Boolean API](tutorials/sha256\_bool.md)
|
||||
|
||||
## References
|
||||
|
||||
* [API references](https://docs.rs/tfhe/latest/tfhe/)
|
||||
* [Fine-grained APIs](references/fine-grained-apis/README.md)
|
||||
* [Quick start](references/fine-grained-apis/quick\_start.md)
|
||||
* [Quick start](references/fine-grained-apis/quick_start.md)
|
||||
* [Boolean](references/fine-grained-apis/boolean/README.md)
|
||||
* [Operations](references/fine-grained-apis/boolean/operations.md)
|
||||
* [Cryptographic parameters](references/fine-grained-apis/boolean/parameters.md)
|
||||
@@ -78,7 +99,7 @@
|
||||
|
||||
## Developers
|
||||
|
||||
* [Contributing](dev/contributing.md)
|
||||
* [Contributing](../../CONTRIBUTING.md)
|
||||
* [Release note](https://github.com/zama-ai/tfhe-rs/releases)
|
||||
* [Feature request](https://github.com/zama-ai/tfhe-rs/issues/new?assignees=\&labels=feature\_request\&projects=\&template=feature\_request.md\&title=)
|
||||
* [Bug report](https://github.com/zama-ai/tfhe-rs/issues/new?assignees=\&labels=triage\_required\&projects=\&template=bug\_report.md\&title=)
|
||||
* [Feature request](https://github.com/zama-ai/tfhe-rs/issues/new?assignees=\&labels=feature_request\&projects=\&template=feature_request.md\&title=)
|
||||
* [Bug report](https://github.com/zama-ai/tfhe-rs/issues/new?assignees=\&labels=triage_required\&projects=\&template=bug_report.md\&title=)
|
||||
|
||||
66
tfhe/docs/_static/cpu_gpu_integer_benchmark_fheuint64_tuniform_2m64_ciphertext.svg
vendored
Normal file
@@ -0,0 +1,66 @@
|
||||
<?xml version="1.0" ?>
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 720 560" preserveAspectRatio="meet" width="100%" height="560">
|
||||
<rect x="0" y="0" width="720" height="40" fill="black"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="6" y="20.0">Operation \ Size</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="405.0" y="20.0">CPU</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="615.0" y="20.0">GPU</text>
|
||||
<rect x="0" y="40" width="300" height="520" fill="#fbbc04"/>
|
||||
<rect x="300" y="40" width="420" height="520" fill="#f3f3f3"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="60.0">Negation (-)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="405.0" y="60.0">106 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="615.0" y="60.0">25.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="100.0">Add / Sub (+,-)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="405.0" y="100.0">105 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="615.0" y="100.0">25.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="140.0">Mul (x)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="405.0" y="140.0">401 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="615.0" y="140.0">237 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="180.0">Equal / Not Equal (eq, ne)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="405.0" y="180.0">81.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="615.0" y="180.0">17.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="220.0">Comparisons (ge, gt, le, lt)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="405.0" y="220.0">102 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="615.0" y="220.0">26.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="260.0">Max / Min (max, min)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="405.0" y="260.0">145 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="615.0" y="260.0">43.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="300.0">Bitwise operations (&, |, ^)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="405.0" y="300.0">20.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="615.0" y="300.0">5.97 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="340.0">Div / Rem (/, %)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="405.0" y="340.0">8.22 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="615.0" y="340.0">2.05 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="380.0">Left / Right Shifts (<<, >>)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="405.0" y="380.0">134 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="615.0" y="380.0">86.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="420.0">Left / Right Rotations (left_rotate, right_rotate)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="405.0" y="420.0">133 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="615.0" y="420.0">86.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="460.0">Leading / Trailing zeros/ones</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="405.0" y="460.0">247 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="615.0" y="460.0">62.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="500.0">Log2</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="405.0" y="500.0">267 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="615.0" y="500.0">73.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="540.0">Select</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="405.0" y="540.0">32.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="615.0" y="540.0">17.5 ms</text>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="720" y2="0"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="40" x2="720" y2="40"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="80" x2="720" y2="80"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="120" x2="720" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="160" x2="720" y2="160"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="200" x2="720" y2="200"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="240" x2="720" y2="240"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="280" x2="720" y2="280"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="320" x2="720" y2="320"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="360" x2="720" y2="360"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="400" x2="720" y2="400"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="440" x2="720" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="480" x2="720" y2="480"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="520" x2="720" y2="520"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="300.0" y1="0" x2="300.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="510.0" y1="0" x2="510.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="720.0" y1="0" x2="720.0" y2="560"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 8.3 KiB |
116
tfhe/docs/_static/cpu_integer_benchmark_tuniform_2m128_ciphertext.svg
vendored
Normal file
@@ -0,0 +1,116 @@
|
||||
<?xml version="1.0" ?>
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 720 560" preserveAspectRatio="meet" width="100%" height="560">
|
||||
<rect x="0" y="0" width="720" height="40" fill="black"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="6" y="20.0">Operation \ Size</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="342.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="342.0" y="29.666666666666668">8</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="426.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="426.0" y="29.666666666666668">16</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="510.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="510.0" y="29.666666666666668">32</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="594.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="594.0" y="29.666666666666668">64</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="678.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="678.0" y="29.666666666666668">128</text>
|
||||
<rect x="0" y="40" width="300" height="520" fill="#fbbc04"/>
|
||||
<rect x="300" y="40" width="420" height="520" fill="#f3f3f3"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="60.0">Negation (-)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="60.0">48.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="60.0">57.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="60.0">79.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="60.0">105 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="60.0">159 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="100.0">Add / Sub (+,-)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="100.0">53.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="100.0">59.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="100.0">82.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="100.0">109 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="100.0">165 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="140.0">Mul (x)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="140.0">97.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="140.0">141 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="140.0">213 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="140.0">400 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="140.0">1.14 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="180.0">Equal / Not Equal (eq, ne)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="180.0">36.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="180.0">56.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="180.0">56.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="180.0">81.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="180.0">82.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="220.0">Comparisons (ge, gt, le, lt)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="220.0">37.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="220.0">54.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="220.0">76.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="220.0">99.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="220.0">145 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="260.0">Max / Min (max, min)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="260.0">76.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="260.0">97.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="260.0">121 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="260.0">148 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="260.0">194 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="300.0">Bitwise operations (&, |, ^)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="300.0">18.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="300.0">19.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="300.0">20.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="300.0">22.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="300.0">23.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="340.0">Div / Rem (/, %)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="340.0">644 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="340.0">1.49 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="340.0">3.44 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="340.0">8.49 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="340.0">20.9 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="380.0">Left / Right Shifts (<<, >>)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="380.0">58.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="380.0">81.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="380.0">107 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="380.0">142 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="380.0">178 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="420.0">Left / Right Rotations (left_rotate, right_rotate)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="420.0">59.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="420.0">81.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="420.0">107 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="420.0">142 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="420.0">186 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="460.0">Leading / Trailing zeros/ones</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="460.0">95.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="460.0">159 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="460.0">182 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="460.0">255 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="460.0">304 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="500.0">Log2</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="500.0">114 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="500.0">173 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="500.0">199 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="500.0">280 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="500.0">327 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="540.0">Select</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="540.0">29.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="540.0">32.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="540.0">33.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="540.0">36.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="540.0">37.2 ms</text>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="720" y2="0"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="40" x2="720" y2="40"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="80" x2="720" y2="80"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="120" x2="720" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="160" x2="720" y2="160"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="200" x2="720" y2="200"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="240" x2="720" y2="240"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="280" x2="720" y2="280"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="320" x2="720" y2="320"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="360" x2="720" y2="360"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="400" x2="720" y2="400"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="440" x2="720" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="480" x2="720" y2="480"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="520" x2="720" y2="520"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="300.0" y1="0" x2="300.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="384.0" y1="0" x2="384.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="468.0" y1="0" x2="468.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="552.0" y1="0" x2="552.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="636.0" y1="0" x2="636.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="720.0" y1="0" x2="720.0" y2="560"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 16 KiB |
95
tfhe/docs/_static/cpu_integer_benchmark_tuniform_2m128_plaintext.svg
vendored
Normal file
@@ -0,0 +1,95 @@
|
||||
<?xml version="1.0" ?>
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 720 440" preserveAspectRatio="meet" width="100%" height="440">
|
||||
<rect x="0" y="0" width="720" height="40" fill="black"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="6" y="20.0">Operation \ Size</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="342.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="342.0" y="29.666666666666668">8</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="426.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="426.0" y="29.666666666666668">16</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="510.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="510.0" y="29.666666666666668">32</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="594.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="594.0" y="29.666666666666668">64</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="678.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="678.0" y="29.666666666666668">128</text>
|
||||
<rect x="0" y="40" width="300" height="400" fill="#fbbc04"/>
|
||||
<rect x="300" y="40" width="420" height="400" fill="#f3f3f3"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="60.0">Add / Sub (+,-)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="60.0">52.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="60.0">60.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="60.0">64.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="60.0">89.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="60.0">111 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="100.0">Mul (x)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="100.0">74.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="100.0">125 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="100.0">175 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="100.0">242 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="100.0">453 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="140.0">Equal / Not Equal (eq, ne)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="140.0">32.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="140.0">35.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="140.0">55.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="140.0">58.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="140.0">79.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="180.0">Comparisons (ge, gt, le, lt)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="180.0">37.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="180.0">36.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="180.0">56.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="180.0">78.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="180.0">101 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="220.0">Max / Min (max, min)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="220.0">52.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="220.0">57.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="220.0">78.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="220.0">103 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="220.0">123 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="260.0">Bitwise operations (&, |, ^)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="260.0">18.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="260.0">19.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="260.0">21.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="260.0">23.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="260.0">24.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="300.0">Div (/)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="300.0">139 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="300.0">202 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="300.0">280 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="300.0">456 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="300.0">912 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="340.0">Rem (%)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="340.0">275 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="340.0">366 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="340.0">536 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="340.0">778 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="340.0">1.37 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="380.0">Left / Right Shifts (<<, >>)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="380.0">20.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="380.0">20.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="380.0">21.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="380.0">23.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="380.0">24.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="420.0">Left / Right Rotations (left_rotate, right_rotate)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="420.0">19.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="420.0">20.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="420.0">21.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="420.0">23.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="420.0">24.1 ms</text>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="720" y2="0"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="40" x2="720" y2="40"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="80" x2="720" y2="80"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="120" x2="720" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="160" x2="720" y2="160"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="200" x2="720" y2="200"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="240" x2="720" y2="240"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="280" x2="720" y2="280"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="320" x2="720" y2="320"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="360" x2="720" y2="360"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="400" x2="720" y2="400"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="300.0" y1="0" x2="300.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="384.0" y1="0" x2="384.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="468.0" y1="0" x2="468.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="552.0" y1="0" x2="552.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="636.0" y1="0" x2="636.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="720.0" y1="0" x2="720.0" y2="440"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 13 KiB |
116
tfhe/docs/_static/cpu_integer_benchmark_tuniform_2m64_ciphertext.svg
vendored
Normal file
@@ -0,0 +1,116 @@
|
||||
<?xml version="1.0" ?>
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 720 560" preserveAspectRatio="meet" width="100%" height="560">
|
||||
<rect x="0" y="0" width="720" height="40" fill="black"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="6" y="20.0">Operation \ Size</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="342.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="342.0" y="29.666666666666668">8</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="426.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="426.0" y="29.666666666666668">16</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="510.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="510.0" y="29.666666666666668">32</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="594.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="594.0" y="29.666666666666668">64</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="678.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="678.0" y="29.666666666666668">128</text>
|
||||
<rect x="0" y="40" width="300" height="520" fill="#fbbc04"/>
|
||||
<rect x="300" y="40" width="420" height="520" fill="#f3f3f3"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="60.0">Negation (-)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="60.0">48.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="60.0">57.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="60.0">78.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="60.0">103 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="60.0">162 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="100.0">Add / Sub (+,-)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="100.0">52.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="100.0">58.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="100.0">79.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="100.0">101 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="100.0">161 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="140.0">Mul (x)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="140.0">94.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="140.0">136 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="140.0">210 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="140.0">381 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="140.0">1.1 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="180.0">Equal / Not Equal (eq, ne)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="180.0">36.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="180.0">55.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="180.0">55.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="180.0">76.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="180.0">77.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="220.0">Comparisons (ge, gt, le, lt)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="220.0">36.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="220.0">54.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="220.0">73.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="220.0">94.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="220.0">136 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="260.0">Max / Min (max, min)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="260.0">74.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="260.0">94.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="260.0">115 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="260.0">138 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="260.0">183 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="300.0">Bitwise operations (&, |, ^)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="300.0">18.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="300.0">19.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="300.0">19.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="300.0">20.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="300.0">22.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="340.0">Div / Rem (/, %)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="340.0">667 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="340.0">1.49 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="340.0">3.39 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="340.0">7.87 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="340.0">19.6 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="380.0">Left / Right Shifts (<<, >>)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="380.0">59.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="380.0">79.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="380.0">100 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="380.0">128 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="380.0">169 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="420.0">Left / Right Rotations (left_rotate, right_rotate)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="420.0">57.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="420.0">77.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="420.0">98.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="420.0">128 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="420.0">178 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="460.0">Leading / Trailing zeros/ones</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="460.0">96.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="460.0">153 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="460.0">172 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="460.0">234 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="460.0">291 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="500.0">Log2</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="500.0">114 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="500.0">170 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="500.0">195 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="500.0">256 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="500.0">312 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="540.0">Select</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="540.0">28.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="540.0">29.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="540.0">31.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="540.0">31.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="540.0">34.3 ms</text>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="720" y2="0"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="40" x2="720" y2="40"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="80" x2="720" y2="80"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="120" x2="720" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="160" x2="720" y2="160"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="200" x2="720" y2="200"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="240" x2="720" y2="240"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="280" x2="720" y2="280"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="320" x2="720" y2="320"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="360" x2="720" y2="360"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="400" x2="720" y2="400"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="440" x2="720" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="480" x2="720" y2="480"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="520" x2="720" y2="520"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="300.0" y1="0" x2="300.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="384.0" y1="0" x2="384.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="468.0" y1="0" x2="468.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="552.0" y1="0" x2="552.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="636.0" y1="0" x2="636.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="720.0" y1="0" x2="720.0" y2="560"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 16 KiB |
95
tfhe/docs/_static/cpu_integer_benchmark_tuniform_2m64_plaintext.svg
vendored
Normal file
@@ -0,0 +1,95 @@
|
||||
<?xml version="1.0" ?>
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 720 440" preserveAspectRatio="meet" width="100%" height="440">
|
||||
<rect x="0" y="0" width="720" height="40" fill="black"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="6" y="20.0">Operation \ Size</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="342.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="342.0" y="29.666666666666668">8</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="426.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="426.0" y="29.666666666666668">16</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="510.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="510.0" y="29.666666666666668">32</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="594.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="594.0" y="29.666666666666668">64</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="678.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="678.0" y="29.666666666666668">128</text>
|
||||
<rect x="0" y="40" width="300" height="400" fill="#fbbc04"/>
|
||||
<rect x="300" y="40" width="420" height="400" fill="#f3f3f3"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="60.0">Add / Sub (+,-)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="60.0">51.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="60.0">56.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="60.0">57.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="60.0">78.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="60.0">104 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="100.0">Mul (x)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="100.0">75.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="100.0">118 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="100.0">161 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="100.0">222 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="100.0">419 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="140.0">Equal / Not Equal (eq, ne)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="140.0">34.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="140.0">35.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="140.0">56.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="140.0">54.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="140.0">75.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="180.0">Comparisons (ge, gt, le, lt)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="180.0">36.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="180.0">35.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="180.0">53.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="180.0">73.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="180.0">94.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="220.0">Max / Min (max, min)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="220.0">55.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="220.0">55.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="220.0">74.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="220.0">95.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="220.0">117 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="260.0">Bitwise operations (&, |, ^)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="260.0">19.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="260.0">19.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="260.0">19.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="260.0">21.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="260.0">22.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="300.0">Div (/)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="300.0">137 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="300.0">189 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="300.0">269 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="300.0">451 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="300.0">833 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="340.0">Rem (%)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="340.0">268 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="340.0">344 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="340.0">492 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="340.0">719 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="340.0">1.27 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="380.0">Left / Right Shifts (<<, >>)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="380.0">18.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="380.0">19.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="380.0">19.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="380.0">20.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="380.0">21.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="420.0">Left / Right Rotations (left_rotate, right_rotate)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="420.0">19.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="420.0">19.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="420.0">19.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="420.0">21.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="420.0">22.7 ms</text>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="720" y2="0"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="40" x2="720" y2="40"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="80" x2="720" y2="80"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="120" x2="720" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="160" x2="720" y2="160"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="200" x2="720" y2="200"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="240" x2="720" y2="240"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="280" x2="720" y2="280"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="320" x2="720" y2="320"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="360" x2="720" y2="360"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="400" x2="720" y2="400"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="300.0" y1="0" x2="300.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="384.0" y1="0" x2="384.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="468.0" y1="0" x2="468.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="552.0" y1="0" x2="552.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="636.0" y1="0" x2="636.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="720.0" y1="0" x2="720.0" y2="440"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 13 KiB |
30
tfhe/docs/_static/cpu_pbs_benchmark_tuniform_2m128.svg
vendored
Normal file
@@ -0,0 +1,30 @@
|
||||
<?xml version="1.0" ?>
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 720 120" preserveAspectRatio="meet" width="100%" height="120">
|
||||
<rect x="0" y="0" width="720" height="40" fill="black"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="6" y="20.0">Operation \ Precision (bits)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="352.5" y="20.0">2</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="457.5" y="20.0">4</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="562.5" y="20.0">6</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="667.5" y="20.0">8</text>
|
||||
<rect x="0" y="40" width="300" height="80" fill="#fbbc04"/>
|
||||
<rect x="300" y="40" width="420" height="80" fill="#f3f3f3"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="60.0">PBS</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="352.5" y="60.0">9.61 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="457.5" y="60.0">12.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="562.5" y="60.0">111 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="667.5" y="60.0">1.5 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="100.0">KS - PBS</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="352.5" y="100.0">10.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="457.5" y="100.0">14.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="562.5" y="100.0">129 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="667.5" y="100.0">1.44 s</text>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="720" y2="0"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="40" x2="720" y2="40"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="80" x2="720" y2="80"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="0" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="300.0" y1="0" x2="300.0" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="405.0" y1="0" x2="405.0" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="510.0" y1="0" x2="510.0" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="615.0" y1="0" x2="615.0" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="720.0" y1="0" x2="720.0" y2="120"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 3.3 KiB |
42
tfhe/docs/_static/cpu_pbs_benchmark_tuniform_2m40.svg
vendored
Normal file
@@ -0,0 +1,42 @@
|
||||
<?xml version="1.0" ?>
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 720 200" preserveAspectRatio="meet" width="100%" height="200">
|
||||
<rect x="0" y="0" width="720" height="40" fill="black"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="6" y="20.0">Operation \ Precision (bits)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="352.5" y="20.0">2</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="457.5" y="20.0">4</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="562.5" y="20.0">6</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="667.5" y="20.0">8</text>
|
||||
<rect x="0" y="40" width="300" height="160" fill="#fbbc04"/>
|
||||
<rect x="300" y="40" width="420" height="160" fill="#f3f3f3"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="60.0">PBS</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="352.5" y="60.0">6.04 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="457.5" y="60.0">11.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="562.5" y="60.0">98.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="667.5" y="60.0">458 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="100.0">MB-PBS</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="352.5" y="100.0">3.41 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="457.5" y="100.0">4.58 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="562.5" y="100.0">37.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="667.5" y="100.0">156 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="140.0">KS-PBS</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="352.5" y="140.0">7.79 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="457.5" y="140.0">14.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="562.5" y="140.0">114 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="667.5" y="140.0">536 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="180.0">KS-MB-PBS</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="352.5" y="180.0">5.53 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="457.5" y="180.0">7.51 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="562.5" y="180.0">47.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="667.5" y="180.0">244 ms</text>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="720" y2="0"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="40" x2="720" y2="40"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="80" x2="720" y2="80"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="120" x2="720" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="160" x2="720" y2="160"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="0" y2="200"/>
|
||||
<line stroke="white" stroke-width="2" x1="300.0" y1="0" x2="300.0" y2="200"/>
|
||||
<line stroke="white" stroke-width="2" x1="405.0" y1="0" x2="405.0" y2="200"/>
|
||||
<line stroke="white" stroke-width="2" x1="510.0" y1="0" x2="510.0" y2="200"/>
|
||||
<line stroke="white" stroke-width="2" x1="615.0" y1="0" x2="615.0" y2="200"/>
|
||||
<line stroke="white" stroke-width="2" x1="720.0" y1="0" x2="720.0" y2="200"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 5.0 KiB |
42
tfhe/docs/_static/cpu_pbs_benchmark_tuniform_2m64.svg
vendored
Normal file
@@ -0,0 +1,42 @@
|
||||
<?xml version="1.0" ?>
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 720 200" preserveAspectRatio="meet" width="100%" height="200">
|
||||
<rect x="0" y="0" width="720" height="40" fill="black"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="6" y="20.0">Operation \ Precision (bits)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="352.5" y="20.0">2</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="457.5" y="20.0">4</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="562.5" y="20.0">6</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="667.5" y="20.0">8</text>
|
||||
<rect x="0" y="40" width="300" height="160" fill="#fbbc04"/>
|
||||
<rect x="300" y="40" width="420" height="160" fill="#f3f3f3"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="60.0">PBS</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="352.5" y="60.0">8.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="457.5" y="60.0">11.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="562.5" y="60.0">102 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="667.5" y="60.0">649 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="100.0">MB-PBS</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="352.5" y="100.0">4.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="457.5" y="100.0">4.43 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="562.5" y="100.0">27.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="667.5" y="100.0">248 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="140.0">KS-PBS</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="352.5" y="140.0">11.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="457.5" y="140.0">14.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="562.5" y="140.0">118 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="667.5" y="140.0">873 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="180.0">KS-MB-PBS</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="352.5" y="180.0">5.97 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="457.5" y="180.0">7.55 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="562.5" y="180.0">44.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="667.5" y="180.0">453 ms</text>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="720" y2="0"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="40" x2="720" y2="40"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="80" x2="720" y2="80"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="120" x2="720" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="160" x2="720" y2="160"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="0" y2="200"/>
|
||||
<line stroke="white" stroke-width="2" x1="300.0" y1="0" x2="300.0" y2="200"/>
|
||||
<line stroke="white" stroke-width="2" x1="405.0" y1="0" x2="405.0" y2="200"/>
|
||||
<line stroke="white" stroke-width="2" x1="510.0" y1="0" x2="510.0" y2="200"/>
|
||||
<line stroke="white" stroke-width="2" x1="615.0" y1="0" x2="615.0" y2="200"/>
|
||||
<line stroke="white" stroke-width="2" x1="720.0" y1="0" x2="720.0" y2="200"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 5.0 KiB |
116
tfhe/docs/_static/gpu_integer_benchmark_h100x1_multi_bit_tuniform_2m64_ciphertext.svg
vendored
Normal file
@@ -0,0 +1,116 @@
|
||||
<?xml version="1.0" ?>
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 720 560" preserveAspectRatio="meet" width="100%" height="560">
|
||||
<rect x="0" y="0" width="720" height="40" fill="black"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="6" y="20.0">Operation \ Size</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="342.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="342.0" y="29.666666666666668">8</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="426.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="426.0" y="29.666666666666668">16</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="510.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="510.0" y="29.666666666666668">32</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="594.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="594.0" y="29.666666666666668">64</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="678.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="678.0" y="29.666666666666668">128</text>
|
||||
<rect x="0" y="40" width="300" height="520" fill="#fbbc04"/>
|
||||
<rect x="300" y="40" width="420" height="520" fill="#f3f3f3"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="60.0">Negation (-)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="60.0">11.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="60.0">12.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="60.0">17.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="60.0">25.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="60.0">51.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="100.0">Add / Sub (+,-)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="100.0">11.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="100.0">12.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="100.0">17.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="100.0">25.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="100.0">51.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="140.0">Mul (x)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="140.0">23.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="140.0">37.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="140.0">76.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="140.0">237 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="140.0">830 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="180.0">Equal / Not Equal (eq, ne)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="180.0">7.65 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="180.0">11.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="180.0">12.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="180.0">17.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="180.0">24.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="220.0">Comparisons (ge, gt, le, lt)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="220.0">11.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="220.0">15.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="220.0">20.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="220.0">26.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="220.0">38.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="260.0">Max / Min (max, min)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="260.0">18.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="260.0">24.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="260.0">30.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="260.0">43.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="260.0">68.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="300.0">Bitwise operations (&, |, ^)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="300.0">3.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="300.0">4.01 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="300.0">4.58 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="300.0">5.97 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="300.0">11.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="340.0">Div / Rem (/, %)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="340.0">154 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="340.0">318 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="340.0">763 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="340.0">2.05 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="340.0">6.35 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="380.0">Left / Right Shifts (<<, >>)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="380.0">22.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="380.0">30.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="380.0">43.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="380.0">86.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="380.0">162 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="420.0">Left / Right Rotations (left_rotate, right_rotate)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="420.0">22.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="420.0">30.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="420.0">43.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="420.0">86.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="420.0">162 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="460.0">Leading / Trailing zeros/ones</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="460.0">25.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="460.0">33.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="460.0">44.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="460.0">62.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="460.0">105 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="500.0">Log2</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="500.0">35.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="500.0">48.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="500.0">55.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="500.0">73.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="500.0">113 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="540.0">Select</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="540.0">7.76 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="540.0">8.72 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="540.0">10.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="540.0">17.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="540.0">30.5 ms</text>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="720" y2="0"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="40" x2="720" y2="40"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="80" x2="720" y2="80"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="120" x2="720" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="160" x2="720" y2="160"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="200" x2="720" y2="200"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="240" x2="720" y2="240"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="280" x2="720" y2="280"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="320" x2="720" y2="320"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="360" x2="720" y2="360"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="400" x2="720" y2="400"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="440" x2="720" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="480" x2="720" y2="480"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="520" x2="720" y2="520"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="300.0" y1="0" x2="300.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="384.0" y1="0" x2="384.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="468.0" y1="0" x2="468.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="552.0" y1="0" x2="552.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="636.0" y1="0" x2="636.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="720.0" y1="0" x2="720.0" y2="560"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 16 KiB |
95
tfhe/docs/_static/gpu_integer_benchmark_h100x1_multi_bit_tuniform_2m64_plaintext.svg
vendored
Normal file
@@ -0,0 +1,95 @@
|
||||
<?xml version="1.0" ?>
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 720 440" preserveAspectRatio="meet" width="100%" height="440">
|
||||
<rect x="0" y="0" width="720" height="40" fill="black"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="6" y="20.0">Operation \ Size</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="342.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="342.0" y="29.666666666666668">8</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="426.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="426.0" y="29.666666666666668">16</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="510.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="510.0" y="29.666666666666668">32</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="594.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="594.0" y="29.666666666666668">64</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="678.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="678.0" y="29.666666666666668">128</text>
|
||||
<rect x="0" y="40" width="300" height="400" fill="#fbbc04"/>
|
||||
<rect x="300" y="40" width="420" height="400" fill="#f3f3f3"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="60.0">Add / Sub (+,-)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="60.0">11.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="60.0">12.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="60.0">17.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="60.0">25.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="60.0">51.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="100.0">Mul (x)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="100.0">18.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="100.0">26.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="100.0">46.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="100.0">109 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="100.0">330 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="140.0">Equal / Not Equal (eq, ne)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="140.0">7.81 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="140.0">8.08 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="140.0">12.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="140.0">13.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="140.0">18.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="180.0">Comparisons (ge, gt, le, lt)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="180.0">9.61 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="180.0">13.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="180.0">17.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="180.0">22.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="180.0">29.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="220.0">Max / Min (max, min)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="220.0">17.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="220.0">21.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="220.0">28.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="220.0">39.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="220.0">59.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="260.0">Bitwise operations (&, |, ^)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="260.0">3.63 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="260.0">4.11 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="260.0">4.65 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="260.0">6.03 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="260.0">11.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="300.0">Div (/)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="300.0">28.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="300.0">41.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="300.0">83.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="300.0">214 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="300.0">664 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="340.0">Rem (%)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="340.0">56.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="340.0">80.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="340.0">149 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="340.0">351 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="340.0">1.04 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="380.0">Left / Right Shifts (<<, >>)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="380.0">3.63 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="380.0">4.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="380.0">4.63 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="380.0">6.03 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="380.0">11.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="420.0">Left / Right Rotations (left_rotate, right_rotate)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="420.0">3.63 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="420.0">4.11 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="420.0">4.64 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="420.0">6.03 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="420.0">11.3 ms</text>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="720" y2="0"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="40" x2="720" y2="40"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="80" x2="720" y2="80"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="120" x2="720" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="160" x2="720" y2="160"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="200" x2="720" y2="200"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="240" x2="720" y2="240"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="280" x2="720" y2="280"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="320" x2="720" y2="320"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="360" x2="720" y2="360"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="400" x2="720" y2="400"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="300.0" y1="0" x2="300.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="384.0" y1="0" x2="384.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="468.0" y1="0" x2="468.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="552.0" y1="0" x2="552.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="636.0" y1="0" x2="636.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="720.0" y1="0" x2="720.0" y2="440"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 13 KiB |
116
tfhe/docs/_static/gpu_integer_benchmark_h100x2_multi_bit_tuniform_2m64_ciphertext.svg
vendored
Normal file
@@ -0,0 +1,116 @@
|
||||
<?xml version="1.0" ?>
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 720 560" preserveAspectRatio="meet" width="100%" height="560">
|
||||
<rect x="0" y="0" width="720" height="40" fill="black"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="6" y="20.0">Operation \ Size</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="342.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="342.0" y="29.666666666666668">8</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="426.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="426.0" y="29.666666666666668">16</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="510.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="510.0" y="29.666666666666668">32</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="594.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="594.0" y="29.666666666666668">64</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="678.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="678.0" y="29.666666666666668">128</text>
|
||||
<rect x="0" y="40" width="300" height="520" fill="#fbbc04"/>
|
||||
<rect x="300" y="40" width="420" height="520" fill="#f3f3f3"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="60.0">Negation (-)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="60.0">11.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="60.0">11.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="60.0">16.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="60.0">21.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="60.0">36.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="100.0">Add / Sub (+,-)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="100.0">11.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="100.0">11.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="100.0">16.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="100.0">21.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="100.0">36.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="140.0">Mul (x)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="140.0">22.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="140.0">31.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="140.0">63.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="140.0">164 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="140.0">545 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="180.0">Equal / Not Equal (eq, ne)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="180.0">7.95 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="180.0">11.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="180.0">12.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="180.0">16.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="180.0">19.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="220.0">Comparisons (ge, gt, le, lt)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="220.0">11.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="220.0">15.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="220.0">19.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="220.0">24.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="220.0">31.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="260.0">Max / Min (max, min)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="260.0">18.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="260.0">23.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="260.0">28.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="260.0">35.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="260.0">50.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="300.0">Bitwise operations (&, |, ^)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="300.0">3.54 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="300.0">3.66 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="300.0">4.24 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="300.0">4.82 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="300.0">6.43 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="340.0">Div / Rem (/, %)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="340.0">273 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="340.0">580 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="340.0">1.28 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="340.0">2.97 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="340.0">7.41 s</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="380.0">Left / Right Shifts (<<, >>)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="380.0">21.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="380.0">27.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="380.0">36.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="380.0">53.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="380.0">106 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="420.0">Left / Right Rotations (left_rotate, right_rotate)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="420.0">21.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="420.0">27.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="420.0">36.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="420.0">53.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="420.0">106 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="460.0">Leading / Trailing zeros/ones</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="460.0">25.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="460.0">32.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="460.0">42.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="460.0">56.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="460.0">78.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="500.0">Log2</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="500.0">43.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="500.0">57.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="500.0">99.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="500.0">280 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="500.0">962 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="540.0">Select</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="540.0">7.38 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="540.0">7.98 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="540.0">9.02 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="540.0">11.3 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="540.0">18.6 ms</text>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="720" y2="0"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="40" x2="720" y2="40"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="80" x2="720" y2="80"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="120" x2="720" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="160" x2="720" y2="160"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="200" x2="720" y2="200"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="240" x2="720" y2="240"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="280" x2="720" y2="280"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="320" x2="720" y2="320"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="360" x2="720" y2="360"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="400" x2="720" y2="400"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="440" x2="720" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="480" x2="720" y2="480"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="520" x2="720" y2="520"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="300.0" y1="0" x2="300.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="384.0" y1="0" x2="384.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="468.0" y1="0" x2="468.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="552.0" y1="0" x2="552.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="636.0" y1="0" x2="636.0" y2="560"/>
|
||||
<line stroke="white" stroke-width="2" x1="720.0" y1="0" x2="720.0" y2="560"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 16 KiB |
95
tfhe/docs/_static/gpu_integer_benchmark_h100x2_multi_bit_tuniform_2m64_plaintext.svg
vendored
Normal file
@@ -0,0 +1,95 @@
|
||||
<?xml version="1.0" ?>
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 720 440" preserveAspectRatio="meet" width="100%" height="440">
|
||||
<rect x="0" y="0" width="720" height="40" fill="black"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="6" y="20.0">Operation \ Size</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="342.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="342.0" y="29.666666666666668">8</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="426.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="426.0" y="29.666666666666668">16</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="510.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="510.0" y="29.666666666666668">32</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="594.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="594.0" y="29.666666666666668">64</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="678.0" y="13.333333333333334">FheUint</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="678.0" y="29.666666666666668">128</text>
|
||||
<rect x="0" y="40" width="300" height="400" fill="#fbbc04"/>
|
||||
<rect x="300" y="40" width="420" height="400" fill="#f3f3f3"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="60.0">Add / Sub (+,-)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="60.0">11.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="60.0">11.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="60.0">16.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="60.0">22.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="60.0">36.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="100.0">Mul (x)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="100.0">18.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="100.0">24.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="100.0">41.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="100.0">93.5 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="100.0">271 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="140.0">Equal / Not Equal (eq, ne)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="140.0">8.26 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="140.0">8.53 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="140.0">12.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="140.0">13.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="140.0">18.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="180.0">Comparisons (ge, gt, le, lt)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="180.0">9.95 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="180.0">13.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="180.0">17.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="180.0">21.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="180.0">27.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="220.0">Max / Min (max, min)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="220.0">17.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="220.0">21.6 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="220.0">26.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="220.0">33.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="220.0">46.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="260.0">Bitwise operations (&, |, ^)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="260.0">3.64 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="260.0">3.79 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="260.0">4.36 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="260.0">4.91 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="260.0">6.54 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="300.0">Div (/)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="300.0">26.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="300.0">39.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="300.0">71.8 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="300.0">176 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="300.0">544 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="340.0">Rem (%)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="340.0">56.9 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="340.0">77.4 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="340.0">131 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="340.0">292 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="340.0">839 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="380.0">Left / Right Shifts (<<, >>)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="380.0">3.55 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="380.0">3.7 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="380.0">4.28 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="380.0">4.82 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="380.0">6.45 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="420.0">Left / Right Rotations (left_rotate, right_rotate)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="342.0" y="420.0">3.55 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="426.0" y="420.0">3.71 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="510.0" y="420.0">4.28 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="594.0" y="420.0">4.82 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="678.0" y="420.0">6.46 ms</text>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="720" y2="0"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="40" x2="720" y2="40"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="80" x2="720" y2="80"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="120" x2="720" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="160" x2="720" y2="160"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="200" x2="720" y2="200"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="240" x2="720" y2="240"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="280" x2="720" y2="280"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="320" x2="720" y2="320"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="360" x2="720" y2="360"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="400" x2="720" y2="400"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="300.0" y1="0" x2="300.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="384.0" y1="0" x2="384.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="468.0" y1="0" x2="468.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="552.0" y1="0" x2="552.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="636.0" y1="0" x2="636.0" y2="440"/>
|
||||
<line stroke="white" stroke-width="2" x1="720.0" y1="0" x2="720.0" y2="440"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 13 KiB |
30
tfhe/docs/_static/gpu_pbs_benchmark_tuniform_2m40.svg
vendored
Normal file
@@ -0,0 +1,30 @@
|
||||
<?xml version="1.0" ?>
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 720 120" preserveAspectRatio="meet" width="100%" height="120">
|
||||
<rect x="0" y="0" width="720" height="40" fill="black"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="6" y="20.0">Operation \ Precision (bits)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="352.5" y="20.0">2</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="457.5" y="20.0">4</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="562.5" y="20.0">6</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="667.5" y="20.0">8</text>
|
||||
<rect x="0" y="40" width="300" height="80" fill="#fbbc04"/>
|
||||
<rect x="300" y="40" width="420" height="80" fill="#f3f3f3"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="60.0">MB-PBS</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="352.5" y="60.0">3.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="457.5" y="60.0">4.03 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="562.5" y="60.0">22.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="667.5" y="60.0">N/A</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="100.0">KS - MB-PBS</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="352.5" y="100.0">3.22 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="457.5" y="100.0">4.02 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="562.5" y="100.0">22.2 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="667.5" y="100.0">N/A</text>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="720" y2="0"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="40" x2="720" y2="40"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="80" x2="720" y2="80"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="0" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="300.0" y1="0" x2="300.0" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="405.0" y1="0" x2="405.0" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="510.0" y1="0" x2="510.0" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="615.0" y1="0" x2="615.0" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="720.0" y1="0" x2="720.0" y2="120"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 3.3 KiB |
30
tfhe/docs/_static/gpu_pbs_benchmark_tuniform_2m64.svg
vendored
Normal file
@@ -0,0 +1,30 @@
|
||||
<?xml version="1.0" ?>
|
||||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 720 120" preserveAspectRatio="meet" width="100%" height="120">
|
||||
<rect x="0" y="0" width="720" height="40" fill="black"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="6" y="20.0">Operation \ Precision (bits)</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="352.5" y="20.0">2</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="457.5" y="20.0">4</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="562.5" y="20.0">6</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="bold" fill="white" x="667.5" y="20.0">8</text>
|
||||
<rect x="0" y="40" width="300" height="80" fill="#fbbc04"/>
|
||||
<rect x="300" y="40" width="420" height="80" fill="#f3f3f3"/>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="60.0">MB-PBS</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="352.5" y="60.0">3.38 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="457.5" y="60.0">4.22 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="562.5" y="60.0">23.0 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="667.5" y="60.0">N/A</text>
|
||||
<text dominant-baseline="middle" text-anchor="start" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="6" y="100.0">KS - MB-PBS</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="352.5" y="100.0">3.38 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="457.5" y="100.0">4.22 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="562.5" y="100.0">23.1 ms</text>
|
||||
<text dominant-baseline="middle" text-anchor="middle" font-family="Arial" font-size="14" font-weight="normal" fill="black" x="667.5" y="100.0">N/A</text>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="720" y2="0"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="40" x2="720" y2="40"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="80" x2="720" y2="80"/>
|
||||
<line stroke="white" stroke-width="2" x1="0" y1="0" x2="0" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="300.0" y1="0" x2="300.0" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="405.0" y1="0" x2="405.0" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="510.0" y1="0" x2="510.0" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="615.0" y1="0" x2="615.0" y2="120"/>
|
||||
<line stroke="white" stroke-width="2" x1="720.0" y1="0" x2="720.0" y2="120"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 3.3 KiB |
@@ -1,6 +1,6 @@
|
||||
# Parallelized PBS
|
||||
|
||||
This document describes the implementation and benefits of parallelized [Programmable Bootstrapping](../getting\_started/security\_and\_cryptography.md) (PBS) in **TFHE-rs**, including code examples for using multi-bit PBS parameters and ensuring deterministic execution.
|
||||
This document describes the implementation and benefits of parallelized [Programmable Bootstrapping](../getting_started/security_and_cryptography.md) (PBS) in **TFHE-rs**, including code examples for using multi-bit PBS parameters and ensuring deterministic execution.
|
||||
|
||||
## Parallelized Programmable Bootstrapping
|
||||
|
||||
@@ -11,15 +11,14 @@ This guide explains how to update your existing program to leverage GPU accelera
|
||||
* [gcc](https://gcc.gnu.org/) >= 8.0 - check this [page](https://gist.github.com/ax3l/9489132) for more details about nvcc/gcc compatible versions
|
||||
* [cmake](https://cmake.org/) >= 3.24
|
||||
* libclang, to match Rust bingen [requirements](https://rust-lang.github.io/rust-bindgen/requirements.html) >= 9.0
|
||||
* Rust version - check this [page](rust\_configuration.md)
|
||||
* Rust version - check this [page](rust_configuration.md)
|
||||
|
||||
## Importing to your project
|
||||
|
||||
To use the **TFHE-rs** GPU backend in your project, add the following dependency in your `Cargo.toml`.
|
||||
|
||||
|
||||
```toml
|
||||
tfhe = { version = "1.0.0", features = ["boolean", "shortint", "integer", "gpu"] }
|
||||
tfhe = { version = "~1.0.1", features = ["boolean", "shortint", "integer", "gpu"] }
|
||||
```
|
||||
|
||||
{% hint style="success" %}
|
||||
@@ -31,7 +30,7 @@ For optimal performance when using **TFHE-rs**, run your code in release mode wi
|
||||
**TFHE-rs** GPU backend is supported on Linux (x86, aarch64).
|
||||
|
||||
| OS | x86 | aarch64 |
|
||||
|---------|-------------|---------------|
|
||||
| ------- | ----------- | ------------- |
|
||||
| Linux | Supported | Supported\* |
|
||||
| macOS | Unsupported | Unsupported\* |
|
||||
| Windows | Unsupported | Unsupported |
|
||||
@@ -40,7 +39,7 @@ For optimal performance when using **TFHE-rs**, run your code in release mode wi
|
||||
|
||||
### Configuring and creating keys.
|
||||
|
||||
Comparing to the [CPU example](../getting\_started/quick\_start.md), GPU set up differs in the key creation, as detailed [here](run\_on\_gpu.md#Setting-the-keys)
|
||||
Comparing to the [CPU example](../getting_started/quick_start.md), GPU set up differs in the key creation, as detailed [here](run\_on\_gpu.md#setting-the-keys)
|
||||
|
||||
Here is a full example (combining the client and server parts):
|
||||
|
||||
@@ -77,9 +76,7 @@ fn main() {
|
||||
}
|
||||
```
|
||||
|
||||
Beware that when the GPU feature is activated, when calling: `let config = ConfigBuilder::default().build();`,
|
||||
the cryptographic parameters differ from the CPU ones, used when the GPU feature is not activated.
|
||||
Indeed, TFHE-rs uses dedicated parameters for the GPU in order to achieve better performance.
|
||||
Beware that when the GPU feature is activated, when calling: `let config = ConfigBuilder::default().build();`, the cryptographic parameters differ from the CPU ones, used when the GPU feature is not activated. Indeed, TFHE-rs uses dedicated parameters for the GPU in order to achieve better performance.
|
||||
|
||||
### Setting the keys
|
||||
|
||||
@@ -103,7 +100,7 @@ On the client-side, the method to encrypt the data is exactly the same than the
|
||||
|
||||
The server first need to set up its keys with `set_server_key(gpu_key)`.
|
||||
|
||||
Then, homomorphic computations are performed using the same approach as the [CPU operations](../getting\_started/operations.md).
|
||||
Then, homomorphic computations are performed using the same approach as the [CPU operations](../fhe-computation/operations/README.md).
|
||||
|
||||
```Rust
|
||||
//Server-side
|
||||
@@ -131,7 +128,7 @@ Finally, the client decrypts the results using:
|
||||
The GPU backend includes the following operations for both signed and unsigned encrypted integers:
|
||||
|
||||
| name | symbol | `Enc`/`Enc` | `Enc`/ `Int` |
|
||||
|-----------------------|----------------|----------------------------|----------------------------|
|
||||
| --------------------- | -------------- | -------------------------- | -------------------------- |
|
||||
| Neg | `-` | :heavy\_check\_mark: | N/A |
|
||||
| Add | `+` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| Sub | `-` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
@@ -157,31 +154,32 @@ The GPU backend includes the following operations for both signed and unsigned e
|
||||
| Cast (from src type) | `cast_from` | :heavy\_multiplication\_x: | N/A |
|
||||
| Ternary operator | `select` | :heavy\_check\_mark: | :heavy\_multiplication\_x: |
|
||||
|
||||
|
||||
{% hint style="info" %}
|
||||
All operations follow the same syntax than the one described in [here](../getting\_started/operations.md).
|
||||
All operations follow the same syntax than the one described in [here](../fhe-computation/operations/README.md).
|
||||
{% endhint %}
|
||||
|
||||
## Multi-GPU support
|
||||
|
||||
TFHE-rs supports platforms with multiple GPUs. There is **nothing to change in the code to execute on such platforms**. To keep the API as user-friendly as possible, the configuration is automatically set, i.e., the user has no fine-grained control over the number of GPUs to be used.
|
||||
|
||||
## Benchmark
|
||||
Please refer to the [GPU benchmarks](../getting_started/benchmarks/gpu_benchmarks.md) for detailed performance benchmark results.
|
||||
## Benchmark
|
||||
|
||||
Please refer to the [GPU benchmarks](../getting_started/benchmarks/gpu/README.md) for detailed performance benchmark results.
|
||||
|
||||
## Warning
|
||||
|
||||
When measuring GPU times on your own on Linux, set the environment variable `CUDA_MODULE_LOADING=EAGER` to avoid CUDA API overheads during the first kernel execution.
|
||||
|
||||
## Compressing ciphertexts after some homomorphic computation on the GPU
|
||||
|
||||
You can compress ciphertexts using the GPU, even after computations, just like on the [CPU](../fundamentals/compress.md#compression-ciphertexts-after-some-homomorphic-computation).
|
||||
You can compress ciphertexts using the GPU, even after computations, just like on the [CPU](../fhe-computation/data-handling/compress.md#compression-ciphertexts-after-some-homomorphic-computation).
|
||||
|
||||
The way to do it is very similar to how it's done on the CPU.
|
||||
The following example shows how to compress and decompress a list containing 4 messages:
|
||||
- One 32-bits integer
|
||||
- One 64-bit integer
|
||||
- One Boolean
|
||||
- One 2-bit integer
|
||||
The way to do it is very similar to how it's done on the CPU. The following example shows how to compress and decompress a list containing 4 messages:
|
||||
|
||||
* One 32-bits integer
|
||||
* One 64-bit integer
|
||||
* One Boolean
|
||||
* One 2-bit integer
|
||||
|
||||
```rust
|
||||
use tfhe::prelude::*;
|
||||
@@ -246,7 +244,8 @@ fn main() {
|
||||
|
||||
## Array types
|
||||
|
||||
It is possible to use array types on GPU, just as [on CPU](array.md). Here is an example showing how to do it:
|
||||
It is possible to use array types on GPU, just as [on CPU](../fhe-computation/types/array.md). Here is an example showing how to do it:
|
||||
|
||||
```rust
|
||||
use tfhe::{ConfigBuilder, set_server_key, ClearArray, ClientKey, CompressedServerKey};
|
||||
use tfhe::array::GpuFheUint32Array;
|
||||
@@ -64,7 +64,7 @@ This crate provides 3 kinds of data types. Each kind is enabled by activating th
|
||||
|
||||
### AVX-512
|
||||
|
||||
While the library generally selects automatically the best instruction sets available by the host, in the case of 'AVX-512', you have to choose it explicitly. This requires to use a [nightly toolchain](rust\_configuration.md#using-tfhe-rs-with-nightly-toolchain) with the feature `nightly-avx512`.
|
||||
While the library generally selects automatically the best instruction sets available by the host, in the case of 'AVX-512', you have to choose it explicitly. This requires to use a nightly toolchain with the feature `nightly-avx512`.
|
||||
|
||||
```shell
|
||||
cargo +nightly build --release --features=nightly-avx512
|
||||
@@ -1,6 +0,0 @@
|
||||
# Contributing
|
||||
|
||||
There are two ways to contribute to `TFHE-rs`. You can:
|
||||
|
||||
* open issues to report bugs and typos and to suggest ideas;
|
||||
* ask to become an official contributor by emailing hello@zama.ai. Only approved contributors can send pull requests, so get in touch before you do.
|
||||
1
tfhe/docs/fhe-computation/advanced-features/README.md
Normal file
@@ -0,0 +1 @@
|
||||
# Advanced features
|
||||
@@ -17,10 +17,10 @@ Here's the list of operations supported along with their symbol:
|
||||
The usage of these operations is similar to the standard ones. The key difference is in the decryption process, as shown in following example:
|
||||
|
||||
```rust
|
||||
/// Adds two [FheUint] and returns a boolean indicating overflow.
|
||||
///
|
||||
/// * The operation is modular, i.e on overflow the result wraps around.
|
||||
/// * On overflow the [FheBool] is true, otherwise false
|
||||
// Adds two [FheUint] and returns a boolean indicating overflow.
|
||||
//
|
||||
// * The operation is modular, i.e on overflow the result wraps around.
|
||||
// * On overflow the [FheBool] is true, otherwise false
|
||||
|
||||
use tfhe::prelude::*;
|
||||
use tfhe::{generate_keys, set_server_key, ConfigBuilder, FheUint16};
|
||||
@@ -40,21 +40,3 @@ assert_eq!(
|
||||
);
|
||||
assert!(overflowed.decrypt(&client_key));
|
||||
```
|
||||
|
||||
The following tables show the current benchmarks result.
|
||||
|
||||
Unsigned homomorphic integers:
|
||||
|
||||
| Operation\Size | FheUint8 | FheUint16 | FheUint32 | FheUint64 | FheUint128 | FheUint256 |
|
||||
| -------------------------- | --------- | --------- | --------- | --------- | ---------- | ---------- |
|
||||
| unsigned\_overflowing\_add | 63.67 ms | 84.11 ms | 107.95 ms | 120.8 ms | 147.38 ms | 191.28 ms |
|
||||
| unsigned\_overflowing\_sub | 68.89 ms | 81.83 ms | 107.63 ms | 120.38 ms | 150.21 ms | 190.39 ms |
|
||||
| unsigned\_overflowing\_mul | 140.76 ms | 191.85 ms | 272.65 ms | 510.61 ms | 1.34 s | 4.51 s |
|
||||
|
||||
Signed homomorphic integers:
|
||||
|
||||
| Operation\Size | FheInt8 | FheInt16 | FheInt32 | FheInt64 | FheInt128 | FheInt256 |
|
||||
| ------------------------ | --------- | --------- | --------- | --------- | --------- | --------- |
|
||||
| signed\_overflowing\_add | 76.54 ms | 84.78 ms | 104.23 ms | 134.38 ms | 162.99 ms | 202.56 ms |
|
||||
| signed\_overflowing\_sub | 82.46 ms | 86.92 ms | 104.41 ms | 132.21 ms | 168.06 ms | 201.17 ms |
|
||||
| signed\_overflowing\_mul | 277.91 ms | 365.67 ms | 571.22 ms | 1.21 s | 3.57 s | 12.84 s |
|
||||
@@ -7,7 +7,7 @@ Public key encryption refers to the cryptographic paradigm where the encryption
|
||||
* **Classical public key**: the first method involves the public key containing many encryptions of zero, as detailed in [Guide to Fully Homomorphic Encryption over the \[Discretized\] Torus, Appendix A.](https://eprint.iacr.org/2021/1402)
|
||||
* **Compact public key**: the second method is based on the paper [TFHE Public-Key Encryption Revisited](https://eprint.iacr.org/2023/603), allowing for significantly smaller key sizes compared to the first method.
|
||||
|
||||
Public keys can also be [compressed](../fundamentals/compress.md) to reduce size.
|
||||
Public keys can also be [compressed](../data-handling/compress.md) to reduce size.
|
||||
|
||||
## Classical public key
|
||||
|
||||
@@ -74,25 +74,29 @@ pub fn main() -> Result<(), Box<dyn std::error::Error>> {
|
||||
```
|
||||
|
||||
Performance can be improved by setting `lto="fat"` in `Cargo.toml`
|
||||
|
||||
```toml
|
||||
[profile.release]
|
||||
lto = "fat"
|
||||
```
|
||||
|
||||
and by building the code for the native CPU architecture and in release mode, e.g. by calling `RUSTFLAGS="-C target-cpu=native" cargo run --release`.
|
||||
|
||||
{% hint style="info" %}
|
||||
You can choose a more costly proof with `ZkComputeLoad::Proof`, which has a faster verification time. Alternatively, you can select `ZkComputeLoad::Verify` for a faster proof and slower verification.
|
||||
You can choose a more costly proof with `ZkComputeLoad::Proof`, which has a faster verification time. Alternatively, you can select `ZkComputeLoad::Verify` for a faster proof and slower verification.
|
||||
{% endhint %}
|
||||
|
||||
## Scheme version
|
||||
|
||||
The ZK scheme used to generate and verify proofs is available in two versions:
|
||||
|
||||
- ZKV1: This version is close to the original paper from [Libert](https://eprint.iacr.org/2023/800).
|
||||
- ZKV2: Differing from the paper, this version provides better performance for provers and verifiers.
|
||||
* ZKV1: This version is close to the original paper from [Libert](https://eprint.iacr.org/2023/800).
|
||||
* ZKV2: Differing from the paper, this version provides better performance for provers and verifiers.
|
||||
|
||||
**TFHE-rs** selects automatically the scheme to use based on the encryption parameters during the CRS generation. With default parameters, ZKV2 is selected.
|
||||
|
||||
The following example shows how to generate a CRS and proofs for ZKV1. Compared to the previous example, only the parameters are changed:
|
||||
|
||||
```rust
|
||||
use rand::prelude::*;
|
||||
use tfhe::prelude::*;
|
||||
@@ -150,5 +154,6 @@ pub fn main() -> Result<(), Box<dyn std::error::Error>> {
|
||||
}
|
||||
```
|
||||
|
||||
## Benchmark
|
||||
Please refer to the [Zero-knowledge proof benchmarks](../getting_started/benchmarks/zk_proof_benchmarks.md) for detailed performance benchmark results.
|
||||
## Benchmark
|
||||
|
||||
Please refer to the [Zero-knowledge proof benchmarks](../../getting_started/benchmarks/zk_proof_benchmarks.md) for detailed performance benchmark results.
|
||||
@@ -4,7 +4,7 @@ This document explains how to initialize the configuration and generate keys.
|
||||
|
||||
The configuration specifies the selected data types and their custom crypto-parameters. You should only use custom parameters for advanced usage and/or testing.
|
||||
|
||||
To create a configuration, use the `ConfigBuilder` type. The following example shows the setup using 8-bit unsigned integers with default parameters. Additionally, ensure the `integers` feature is enabled, as indicated in the table on [this page](../guides/rust\_configuration.md#homomorphic-types).
|
||||
To create a configuration, use the `ConfigBuilder` type. The following example shows the setup using 8-bit unsigned integers with default parameters. Additionally, ensure the `integers` feature is enabled, as indicated in the table on [this page](../../configuration/rust_configuration.md#homomorphic-types).
|
||||
|
||||
The configuration is initialized by creating a builder with all types deactivated. Then, the integer types with default parameters are activated, for using `FheUint8` values.
|
||||
|
||||
66
tfhe/docs/fhe-computation/compute/parameters.md
Normal file
@@ -0,0 +1,66 @@
|
||||
# Cryptographic Parameters
|
||||
|
||||
This document explains how the choice of cryptographic parameters impacts both the security and efficiency of FHE algorithms. The chosen parameters determine the error probability (sometimes referred to failure probability) and overall performance of computations using fully homomorphic encryption. This error probability is due to the noisy nature of FHE computations (see [here](../../getting\_started/security\_and\_cryptography.md) for more details about the encryption process).
|
||||
|
||||
All parameter sets provide at least 128-bits of security according to the [Lattice-Estimator](https://github.com/malb/lattice-estimator).
|
||||
|
||||
## Default parameters
|
||||
Currently, the default parameters use blocks that contain 2 bits of message and 2 bits of carry - a tweaked uniform (TUniform, defined [here](../../getting_started/security_and_cryptography.md#noise)) noise distribution, and have a bootstrapping failure probability $$p_{error} \le 2^{-128}$$.
|
||||
These are particularly suitable for applications that need to be secure in the IND-CPA^D model (see [here](../../getting_started/security_and_cryptography.md) for more details).
|
||||
The GPU backend still uses an error probability smaller than $$2^{-64}$$ by default. Those will be updated soon.
|
||||
|
||||
When using the high-level API of **TFHE-rs**, you can create a key pair using the default recommended set of parameters. For example:
|
||||
|
||||
```rust
|
||||
use tfhe::{ConfigBuilder, generate_keys};
|
||||
|
||||
fn main() {
|
||||
let config = ConfigBuilder::default().build();
|
||||
|
||||
// Client-side
|
||||
let (client_key, server_key) = generate_keys(config);
|
||||
|
||||
// encryption and FHE operations
|
||||
}
|
||||
```
|
||||
|
||||
{% hint style="info" %}
|
||||
These default parameters may be updated with in future releases of **TFHE-rs**, potentially causing incompatibilities between versions. For production systems, it is therefore recommended to specify a fixed parameter set.
|
||||
{% endhint %}
|
||||
|
||||
## Parameters versioning and naming scheme
|
||||
|
||||
Parameter sets are versioned for backward compatibility. This means that each set of parameters can be tied to a specific version of **TFHE-rs**, so that they remain unchanged and compatible after an upgrade.
|
||||
|
||||
All parameter sets are stored as variables inside the `tfhe::shortint::parameters` module, with submodules named after the versions of **TFHE-rs** in which these parameters where added. For example, parameters added in **TFHE-rs** v1.0 can be found inside `tfhe::shortint::parameters::v1_0`.
|
||||
|
||||
The naming convention of these parameters indicates their capabilities. Taking `tfhe::parameters::v1_0::V1_0_PARAM_MESSAGE_2_CARRY_2_KS_PBS_TUNIFORM_2M128` as an example:
|
||||
- `V1_0`: these parameters were introduced in **TFHE-rs** v1.0
|
||||
- `MESSAGE_2`: LWE blocks include 2 bits of message
|
||||
- `CARRY_2`: LWE blocks include 2 bits of carry
|
||||
- `KS_PBS`: the keyswitch is computed before the bootstrap
|
||||
- `TUNIFORM`: the tweaked uniform noise distribution is used
|
||||
- `2M128`: the probability of failure for the bootstrap is $$2^{-128}$$
|
||||
|
||||
For convenience, aliases are provided for the most used sets of parameters and stored in the module `tfhe::shortint::parameters::aliases`. Note, however, that these parameters are not stable over time and are always updated to the latest **TFHE-rs** version. For this reason, they should only be used for prototyping and are not suitable for production use cases.
|
||||
|
||||
|
||||
## How to choose the parameter sets
|
||||
You can override the default parameters with the `with_custom_parameters(block_parameters)` method of the `Config` object. For example, to use a Gaussian distribution instead of the TUniform one, you can modify your configuration as follows:
|
||||
|
||||
```rust
|
||||
use tfhe::{ConfigBuilder, generate_keys};
|
||||
use tfhe::shortint::parameters::v1_0::V1_0_PARAM_MESSAGE_2_CARRY_2_KS_PBS_GAUSSIAN_2M128;
|
||||
|
||||
fn main() {
|
||||
let config =
|
||||
ConfigBuilder::with_custom_parameters(V1_0_PARAM_MESSAGE_2_CARRY_2_KS_PBS_GAUSSIAN_2M128)
|
||||
.build();
|
||||
|
||||
// Client-side
|
||||
let (client_key, server_key) = generate_keys(config);
|
||||
|
||||
// encryption and FHE operations
|
||||
}
|
||||
|
||||
```
|
||||
1
tfhe/docs/fhe-computation/data-handling/README.md
Normal file
@@ -0,0 +1 @@
|
||||
# Data handling
|
||||
@@ -16,8 +16,8 @@ You can load serialized data with the `unversionize` function, even in newer ver
|
||||
|
||||
[dependencies]
|
||||
# ...
|
||||
tfhe = { version = "1.0.0", features = ["integer"] }
|
||||
tfhe-versionable = "0.4.0"
|
||||
tfhe = { version = "~1.0.1", features = ["integer"] }
|
||||
tfhe-versionable = "0.5.0"
|
||||
bincode = "1.3.3"
|
||||
```
|
||||
|
||||
@@ -7,6 +7,7 @@ This document explains the `serialization` and `deserialization` features that a
|
||||
When dealing with sensitive types, it's important to implement safe serialization and safe deserialization functions to prevent runtime errors and enhance security. **TFHE-rs** provide easy to use functions for this purpose, such as `safe_serialize`, `safe_deserialize` and `safe_deserialize_conformant`.
|
||||
|
||||
Here is a basic example on how to use it:
|
||||
|
||||
```rust
|
||||
// main.rs
|
||||
|
||||
@@ -35,7 +36,7 @@ fn main() {
|
||||
The safe deserialization must take the output of a safe-serialization as input. During the process, the following validation occurs:
|
||||
|
||||
* **Type match**: deserializing `type A` from a serialized `type B` raises an error indicating "On deserialization, expected type A, got type B".
|
||||
* **Version compatibility**: data serialized in previous versions of **TFHE-rs** are automatically upgraded to the latest version using the [data versioning](../guides/data\_versioning.md) feature.
|
||||
* **Version compatibility**: data serialized in previous versions of **TFHE-rs** are automatically upgraded to the latest version using the [data versioning](data_versioning.md) feature.
|
||||
* **Parameter compatibility**: deserializing an object of `type A` with one set of crypto parameters from an object of `type A` with another set of crypto parameters raises an error indicating "Deserialized object of type A not conformant with given parameter set"
|
||||
* If both parameter sets have the same LWE dimension for ciphertexts, a ciphertext from param 1 may not fail this deserialization check with param 2.
|
||||
* This check can't distinguish ciphertexts/server keys from independent client keys with the same parameters.
|
||||
@@ -120,8 +121,7 @@ fn main() {
|
||||
|
||||
The safe serialization and deserialization use `bincode` internally.
|
||||
|
||||
To selectively disable some of the features of the safe serialization, you can use `SerializationConfig`/`DeserializationConfig` builders.
|
||||
For example, it is possible to disable the data versioning:
|
||||
To selectively disable some of the features of the safe serialization, you can use `SerializationConfig`/`DeserializationConfig` builders. For example, it is possible to disable the data versioning:
|
||||
|
||||
```rust
|
||||
// main.rs
|
||||
@@ -152,8 +152,7 @@ fn main() {
|
||||
|
||||
**TFHE-rs** uses the [Serde](https://crates.io/crates/serde) framework and implements Serde's `Serialize` and `Deserialize` traits.
|
||||
|
||||
This allows you to serialize into any [data format](https://serde.rs/#data-formats) supported by serde.
|
||||
However, this is a more bare bone approach as none of the checks described in the previous section will be performed for you.
|
||||
This allows you to serialize into any [data format](https://serde.rs/#data-formats) supported by serde. However, this is a more bare bone approach as none of the checks described in the previous section will be performed for you.
|
||||
|
||||
In the following example, we use [bincode](https://crates.io/crates/bincode) for its binary format:
|
||||
|
||||
@@ -162,7 +161,7 @@ In the following example, we use [bincode](https://crates.io/crates/bincode) for
|
||||
|
||||
[dependencies]
|
||||
# ...
|
||||
tfhe = { version = "1.0.0", features = ["integer"] }
|
||||
tfhe = { version = "~1.0.1", features = ["integer"] }
|
||||
bincode = "1.3.3"
|
||||
```
|
||||
|
||||
30
tfhe/docs/fhe-computation/operations/README.md
Normal file
@@ -0,0 +1,30 @@
|
||||
# Operations
|
||||
|
||||
This document gives a high-level overview of various operations on encrypted integers supported by **TFHE-rs.**
|
||||
|
||||
**TFHE-rs** supports various operations on encrypted integers (`Enc`) of any size between 1 and 256 bits. These operations can also work between encrypted integers and clear integers (`Int`).
|
||||
|
||||
| name | symbol | `Enc`/`Enc` | `Enc`/ `Int` |
|
||||
| --------------------- | ----------- | -------------------- | -------------------------- |
|
||||
| Neg | `-` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| Add | `+` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| Sub | `-` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| Mul | `*` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| Div | `/` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| Rem | `%` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| Not | `!` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| BitAnd | `&` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| BitOr | `\|` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| BitXor | `^` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| Shr | `>>` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| Shl | `<<` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| Min | `min` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| Max | `max` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| Greater than | `gt` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| Greater or equal than | `ge` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| Less than | `lt` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| Less or equal than | `le` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| Equal | `eq` | :heavy\_check\_mark: | :heavy\_check\_mark: |
|
||||
| Cast (into dest type) | `cast_into` | :heavy\_check\_mark: | :heavy\_multiplication\_x: |
|
||||
| Cast (from src type) | `cast_from` | :heavy\_check\_mark: | :heavy\_multiplication\_x: |
|
||||
| Ternary operator | `select` | :heavy\_check\_mark: | :heavy\_multiplication\_x: |
|
||||
@@ -0,0 +1,60 @@
|
||||
# Arithmetic operations
|
||||
|
||||
This document details the arithmetic operations supported by **TFHE-rs**.
|
||||
|
||||
Homomorphic integer types (`FheUint` and `FheInt`) support the following arithmetic operations:
|
||||
|
||||
| name | symbol | type |
|
||||
| --------------------------------------------------------- | ------ | ------ |
|
||||
| [Neg](https://doc.rust-lang.org/std/ops/trait.Neg.html) | `-` | Unary |
|
||||
| [Add](https://doc.rust-lang.org/std/ops/trait.Add.html) | `+` | Binary |
|
||||
| [Sub](https://doc.rust-lang.org/std/ops/trait.Sub.html) | `-` | Binary |
|
||||
| [Mul](https://doc.rust-lang.org/std/ops/trait.Mul.html) | `*` | Binary |
|
||||
| [Div](https://doc.rust-lang.org/std/ops/trait.Div.html)\* | `/` | Binary |
|
||||
| [Rem](https://doc.rust-lang.org/std/ops/trait.Rem.html)\* | `%` | Binary |
|
||||
|
||||
Specifications for operations with zero:
|
||||
|
||||
* **Division by zero**: returns modulus - 1.
|
||||
* Example: for FheUint8 (modulus = $$2^8=256$$), dividing by zero returns an encryption of 255.
|
||||
* **Remainder operator**: returns the first input unchanged.
|
||||
* Example: if `ct1 = FheUint8(63)` and `ct2 = FheUint8(0)`, then ct1 % ct2 returns FheUint8(63).
|
||||
|
||||
The following example shows how to perform arithmetic operations:
|
||||
|
||||
```rust
|
||||
use tfhe::prelude::*;
|
||||
use tfhe::{generate_keys, set_server_key, ConfigBuilder, FheInt8, FheUint8};
|
||||
|
||||
fn main() -> Result<(), Box<dyn std::error::Error>> {
|
||||
let config = ConfigBuilder::default().build();
|
||||
let (keys, server_keys) = generate_keys(config);
|
||||
set_server_key(server_keys);
|
||||
|
||||
let clear_a = 15_u64;
|
||||
let clear_b = 27_u64;
|
||||
let clear_c = 43_u64;
|
||||
let clear_d = -87_i64;
|
||||
|
||||
let mut a = FheUint8::try_encrypt(clear_a, &keys)?;
|
||||
let mut b = FheUint8::try_encrypt(clear_b, &keys)?;
|
||||
let c = FheUint8::try_encrypt(clear_c, &keys)?;
|
||||
let mut d = FheInt8::try_encrypt(clear_d, &keys)?;
|
||||
|
||||
|
||||
a *= &b; // Clear equivalent computations: 15 * 27 mod 256 = 149
|
||||
b = &b + &c; // Clear equivalent computations: 27 + 43 mod 256 = 70
|
||||
b -= 76u8; // Clear equivalent computations: 70 - 76 mod 256 = 250
|
||||
d -= 13i8; // Clear equivalent computations: -87 - 13 = 100 in [-128, 128[
|
||||
|
||||
let dec_a: u8 = a.decrypt(&keys);
|
||||
let dec_b: u8 = b.decrypt(&keys);
|
||||
let dec_d: i8 = d.decrypt(&keys);
|
||||
|
||||
assert_eq!(dec_a, ((clear_a * clear_b) % 256_u64) as u8);
|
||||
assert_eq!(dec_b, (((clear_b + clear_c).wrapping_sub(76_u64)) % 256_u64) as u8);
|
||||
assert_eq!(dec_d, (clear_d - 13) as i8);
|
||||
|
||||
Ok(())
|
||||
}
|
||||
```
|
||||
39
tfhe/docs/fhe-computation/operations/bitwise-operations.md
Normal file
@@ -0,0 +1,39 @@
|
||||
# Bitwise operations
|
||||
|
||||
This document details the bitwise operations supported by **TFHE-rs**.
|
||||
|
||||
Homomorphic integer types support the following bitwise operations:
|
||||
|
||||
<table><thead><tr><th width="242">name</th><th>symbol</th><th>type</th></tr></thead><tbody><tr><td><a href="https://doc.rust-lang.org/std/ops/trait.Not.html">Not</a></td><td><code>!</code></td><td>Unary</td></tr><tr><td><a href="https://doc.rust-lang.org/std/ops/trait.BitAnd.html">BitAnd</a></td><td><code>&</code></td><td>Binary</td></tr><tr><td><a href="https://doc.rust-lang.org/std/ops/trait.BitOr.html">BitOr</a></td><td><code>|</code></td><td>Binary</td></tr><tr><td><a href="https://doc.rust-lang.org/std/ops/trait.BitXor.html">BitXor</a></td><td><code>^</code></td><td>Binary</td></tr><tr><td><a href="https://doc.rust-lang.org/std/ops/trait.Shr.html">Shr</a></td><td><code>>></code></td><td>Binary</td></tr><tr><td><a href="https://doc.rust-lang.org/std/ops/trait.Shl.html">Shl</a></td><td><code><<</code></td><td>Binary</td></tr><tr><td><a href="https://doc.rust-lang.org/std/primitive.u32.html#method.rotate_right">Rotate Right</a></td><td><code>rotate_right</code></td><td>Binary</td></tr><tr><td><a href="https://doc.rust-lang.org/std/primitive.u32.html#method.rotate_left">Rotate Left</a></td><td><code>rotate_left</code></td><td>Binary</td></tr></tbody></table>
|
||||
|
||||
The following example shows how to perform bitwise operations:
|
||||
|
||||
```rust
|
||||
use tfhe::prelude::*;
|
||||
use tfhe::{generate_keys, set_server_key, ConfigBuilder, FheUint8};
|
||||
|
||||
fn main() -> Result<(), Box<dyn std::error::Error>> {
|
||||
let config = ConfigBuilder::default().build();
|
||||
let (keys, server_keys) = generate_keys(config);
|
||||
set_server_key(server_keys);
|
||||
|
||||
let clear_a = 164;
|
||||
let clear_b = 212;
|
||||
|
||||
let mut a = FheUint8::try_encrypt(clear_a, &keys)?;
|
||||
let mut b = FheUint8::try_encrypt(clear_b, &keys)?;
|
||||
|
||||
a ^= &b;
|
||||
b ^= &a;
|
||||
a ^= &b;
|
||||
|
||||
let dec_a: u8 = a.decrypt(&keys);
|
||||
let dec_b: u8 = b.decrypt(&keys);
|
||||
|
||||
// We homomorphically swapped values using bitwise operations
|
||||
assert_eq!(dec_a, clear_b);
|
||||
assert_eq!(dec_b, clear_a);
|
||||
|
||||
Ok(())
|
||||
}
|
||||
```
|
||||