diff --git a/docs/SUMMARY.md b/docs/SUMMARY.md index 0616f7ac9..f671b0844 100644 --- a/docs/SUMMARY.md +++ b/docs/SUMMARY.md @@ -4,36 +4,47 @@ ## Getting Started -* [Basics of FHE programs](getting-started/fhe_basics.md) * [Installation](getting-started/installing.md) * [Quick Start](getting-started/quick\_start.md) * [Compatibility](getting-started/compatibility.md) -* [Exactness](getting-started/exactness.md) -* [Performance](getting-started/performance.md) -* [Terminology and Structure](getting-started/terminology_and_structure.md) +* [Terminology](getting-started/terminology.md) -## Tutorials +## Feature + +* [Overview](getting-started/fhe_basics.md) + +* [Table Lookups](tutorial/table\_lookups.md) + +* [Bit Extraction](tutorial/bit\_extraction.md) +* [Rounding](tutorial/rounding.md) +* [Truncating](tutorial/truncating.md) +* [Floating Points](tutorial/floating\_points.md) -* [Decorator](tutorial/decorator.md) -* [Progressbar](tutorial/progressbar.md) -* [Formatting and Drawing](tutorial/formatting\_and\_drawing.md) -* [Tagging](tutorial/tagging.md) -* [Extensions](tutorial/extensions.md) * [Comparisons](tutorial/comparisons.md) * [Min/Max Operations](tutorial/minmax.md) * [Bitwise Operations](tutorial/bitwise.md) -* [Table Lookups](tutorial/table\_lookups.md) -* [Bit Extraction](tutorial/bit\_extraction.md) -* [Truncating](tutorial/truncating.md) -* [Rounding](tutorial/rounding.md) -* [Floating Points](tutorial/floating\_points.md) + +* [Common Tricks](tutorial/workarounds.md) +* [Extensions](tutorial/extensions.md) + +* [Tagging](tutorial/tagging.md) + +## Compilation + +* [Composition](tutorial/composition.md) +* [Reuse Arguments](howto/reuse\_arguments.md) * [Multi Precision](tutorial/multi\_precision.md) * [Multi Parameters](tutorial/multi\_parameters.md) -* [Simulation](tutorial/simulation.md) +* [Decorator](tutorial/decorator.md) * [Direct Circuits](tutorial/direct\_circuits.md) * [Statistics](tutorial/statistics.md) -* [Common Workarounds](tutorial/workarounds.md) -* [Composition](tutorial/composition.md) + +## Execution / Analysis + +* [Simulation](tutorial/simulation.md) +* [Progressbar](tutorial/progressbar.md) +* [Formatting and Drawing](tutorial/formatting\_and\_drawing.md) +* [Debug](howto/debug.md) ## Application Tutorials @@ -42,29 +53,26 @@ * [Game of Life](application-tutorial/game_of_life.md) * [XOR Distance](application-tutorial/xor_distance.md) -## How To +## Guide * [Configure](howto/configure.md) * [Manage Keys](howto/manage\_keys.md) * [Deploy](howto/deploy.md) -* [Reuse Arguments](howto/reuse\_arguments.md) -* [Debug](howto/debug.md) -* [Call FHE circuits from other languages](howto/call_from_other_language.md) ## Explanations * [Frontend fusing](dev/fusing.md) -* [Compilation](dev/compilation/README.md) - * [Automatic Crypto Parameters choice](dev/compilation/optimizer.md) - * [MLIR FHE Dialects](dev/compilation/dialects.md) - * [FHELinalg Dialect](dev/compilation/FHELinalgDialect.md) - * [FHE Dialect](dev/compilation/FHEDialect.md) - * [TFHE Dialect](dev/compilation/TFHEDialect.md) - * [Concrete Dialect](dev/compilation/ConcreteDialect.md) - * [Tracing Dialect](dev/compilation/TracingDialect.md) - * [Runtime Dialect](dev/compilation/RTDialect.md) - * [SDFG Dialect](dev/compilation/SDFGDialect.md) -* [Security curves](dev/security/security_curves.md) +* [Optimizer](dev/compilation/optimizer.md) +* [MLIR FHE Dialects](dev/compilation/dialects.md) + * [FHELinalg Dialect](dev/compilation/FHELinalgDialect.md) + * [FHE Dialect](dev/compilation/FHEDialect.md) + * [TFHE Dialect](dev/compilation/TFHEDialect.md) + * [Concrete Dialect](dev/compilation/ConcreteDialect.md) + * [Tracing Dialect](dev/compilation/TracingDialect.md) + * [Runtime Dialect](dev/compilation/RTDialect.md) + * [SDFG Dialect](dev/compilation/SDFGDialect.md) +* [Security](dev/security/security_curves.md) +* [Call FHE circuits from other languages](howto/call_from_other_language.md) ## Developer diff --git a/docs/dev/setup/layout.md b/docs/dev/setup/layout.md index 74e1b026a..afd462800 100644 --- a/docs/dev/setup/layout.md +++ b/docs/dev/setup/layout.md @@ -1,4 +1,6 @@ -# Concrete projects layout +# Projects layout + +## Concrete layout Concrete is a modular framework composed by sub-projects using different technologies, all having theirs own build system and test suite. Each sub-project have is own README that explain how to setup the developer environment, how to build it and how to run tests commands. @@ -10,3 +12,17 @@ Concrete is made of 4 main categories of sub-project that are organized in subdi - `concrete-cpu`, using TFHE-rs that implement the fastest implementation of TFHE on CPU. - `concrete-cuda` that provides a GPU acceleration of TFHE primitives. - `tools` are basically every other sub-projects that cannot be classified in the three previous categories and which are used as a common support by the others. + +## Concrete Python layout + +The module structure of **Concrete Python**. You are encouraged to check individual `.py` files to learn more. + +* concrete + * fhe + * **dtypes:** data type specifications (e.g., int4, uint5, float32) + * **values:** value specifications (i.e., data type + shape + encryption status) + * **representation:** representation of computation (e.g., computation graphs, nodes) + * **tracing:** tracing of python functions + * **extensions:** custom functionality (see [Extensions](../../tutorial/extensions.md)) + * **mlir:** computation graph to mlir conversion + * **compilation:** configuration, compiler, artifacts, circuit, client/server, and anything else related to compilation diff --git a/docs/getting-started/exactness.md b/docs/getting-started/exactness.md deleted file mode 100644 index c61654ecb..000000000 --- a/docs/getting-started/exactness.md +++ /dev/null @@ -1,27 +0,0 @@ -# Exactness - -One of the most common operations in Concrete is `Table Lookups` (TLUs). TLUs are performed with an FHE operation called `Programmable Bootstrapping` (PBS). PBS's have a certain probability of error, which, when triggered, result in inaccurate results. - -Let's say you have the table: - -```python -lut = [0, 1, 4, 9, 16, 25, 36, 49, 64] -``` - -And you perform a Table Lookup using `4`. The result you should get is `lut[4] = 16`, but because of the possibility of error, you could get any other value in the table. - -The probability of this error can be configured through the `p_error` and `global_p_error` configuration options. The difference between these two options is that, `p_error` is for individual TLUs but `global_p_error` is for the whole circuit. - -If you set `p_error` to `0.01`, for example, it means every TLU in the circuit will have a 99% chance of being exact with a 1% probability of error. If you have a single TLU in the circuit, `global_p_error` would be 1% as well. But if you have 2 TLUs for example, `global_p_error` would be almost 2% (`1 - (0.99 * 0.99)`). - -However, if you set `global_p_error` to `0.01`, the whole circuit will have 1% probability of error, no matter how many Table Lookups are included. - -If you set both of them, both will be satisfied. Essentially, the stricter one will be used. - -By default, both `p_error` and `global_p_error` is set to `None`, which results in a `global_p_error` of `1 / 100_000` being used. - -Feel free to play with these configuration options to pick the one best suited for your needs! See [How to Configure](../howto/configure.md) to learn how you can set a custom `p_error` and/or `global_p_error`. - -{% hint style="info" %} -Configuring either of those variables impacts computation time (compilation, keys generation, circuit execution) and space requirements (size of the keys on disk and in memory). Lower error probabilities would result in longer computation times and larger space requirements. -{% endhint %} diff --git a/docs/getting-started/performance.md b/docs/getting-started/performance.md deleted file mode 100644 index 206427c2f..000000000 --- a/docs/getting-started/performance.md +++ /dev/null @@ -1,35 +0,0 @@ -# Performance - -One of the most common operations in **Concrete** is `Table Lookups` (TLUs). All operations except addition, subtraction, multiplication with non-encrypted values, tensor manipulation operations, and a few operations built with those primitive operations (e.g. matmul, conv) are converted to Table Lookups under the hood: - -```python -from concrete import fhe - -@fhe.compiler({"x": "encrypted"}) -def f(x): - return x ** 2 - -inputset = range(2 ** 4) -circuit = f.compile(inputset) -``` - -is exactly the same as - -```python -from concrete import fhe - -table = fhe.LookupTable([x ** 2 for x in range(2 ** 4)]) - -@fhe.compiler({"x": "encrypted"}) -def f(x): - return table[x] - -inputset = range(2 ** 4) -circuit = f.compile(inputset) -``` - -Table Lookups are very flexible. They allow Concrete to support many operations, but they are expensive. The exact cost depends on many variables (hardware used, error probability, etc.), but they are always much more expensive compared to other operations. You should try to avoid them as much as possible. It's not always possible to avoid them completely, but you might remove the number of TLUs or replace some of them with other primitive operations. - -{% hint style="info" %} -Concrete automatically parallelizes TLUs if they are applied to tensors. -{% endhint %} diff --git a/docs/getting-started/terminology_and_structure.md b/docs/getting-started/terminology.md similarity index 55% rename from docs/getting-started/terminology_and_structure.md rename to docs/getting-started/terminology.md index 1fc1f704a..5787c45eb 100644 --- a/docs/getting-started/terminology_and_structure.md +++ b/docs/getting-started/terminology.md @@ -9,16 +9,3 @@ Some terms used throughout the project include: * **bounds:** Before computation graphs are converted to MLIR, we need to know which value should have which type (e.g., uint3 vs int5). We use inputsets for this purpose. We simulate the graph with the inputs in the inputset to remember the minimum and the maximum value for each node, which is what we call bounds, and use bounds to determine the appropriate type for each node. * **circuit:** The result of compilation. A circuit is made of the client and server components. It has methods for everything from printing to evaluation. -## Module structure - -In this section, we briefly discuss the module structure of **Concrete Python**. You are encouraged to check individual `.py` files to learn more. - -* concrete - * fhe - * **dtypes:** data type specifications (e.g., int4, uint5, float32) - * **values:** value specifications (i.e., data type + shape + encryption status) - * **representation:** representation of computation (e.g., computation graphs, nodes) - * **tracing:** tracing of python functions - * **extensions:** custom functionality (see [Extensions](../tutorial/extensions.md)) - * **mlir:** computation graph to mlir conversion - * **compilation:** configuration, compiler, artifacts, circuit, client/server, and anything else related to compilation diff --git a/docs/howto/configure.md b/docs/howto/configure.md index 616ef274b..c998e5e46 100644 --- a/docs/howto/configure.md +++ b/docs/howto/configure.md @@ -67,9 +67,9 @@ Additional kwargs to `compile` functions take higher precedence. So if you set t * **auto\_adjust\_rounders**: bool = False * Adjust rounders automatically. * **p\_error**: Optional\[float] = None - * Error probability for individual table lookups. If set, all table lookups will have the probability of a non-exact result smaller than the set value. See [Exactness](../getting-started/exactness.md) to learn more. + * Error probability for individual table lookups. If set, all table lookups will have the probability of a non-exact result smaller than the set value. See [Exactness](../tutorial/table\_lookups.md#table-lookup-exactness) to learn more. * **global\_p\_error**: Optional\[float] = None - * Global error probability for the whole circuit. If set, the whole circuit will have the probability of a non-exact result smaller than the set value. See [Exactness](../getting-started/exactness.md) to learn more. + * Global error probability for the whole circuit. If set, the whole circuit will have the probability of a non-exact result smaller than the set value. See [Exactness](../tutorial/table\_lookups.md#table-lookup-exactness) to learn more. * **single\_precision**: bool = False * Use single precision for the whole circuit. * **parameter\_selection\_strategy**: (fhe.ParameterSelectionStrategy) = fhe.ParameterSelectionStrategy.MULTI diff --git a/docs/tutorial/simulation.md b/docs/tutorial/simulation.md index 7608ddd47..14063f5f8 100644 --- a/docs/tutorial/simulation.md +++ b/docs/tutorial/simulation.md @@ -1,6 +1,6 @@ # Simulation -During development, the speed of homomorphic execution can be a blocker for fast prototyping. You could call the function you're trying to compile directly, of course, but it won't be exactly the same as FHE execution, which has a certain probability of error (see [Exactness](../getting-started/exactness.md)). +During development, the speed of homomorphic execution can be a blocker for fast prototyping. You could call the function you're trying to compile directly, of course, but it won't be exactly the same as FHE execution, which has a certain probability of error (see [Exactness](./table\_lookups.md#table-lookup-exactness)). To overcome this issue, simulation is introduced: diff --git a/docs/tutorial/table_lookups.md b/docs/tutorial/table_lookups.md index ab39ba5b9..7271247a7 100644 --- a/docs/tutorial/table_lookups.md +++ b/docs/tutorial/table_lookups.md @@ -1,6 +1,12 @@ # Table Lookups -In this tutorial, we will review how to perform direct table lookups in **Concrete**. +One of the most common operations in **Concrete** is `Table Lookups` (TLUs). All operations except addition, subtraction, multiplication with non-encrypted values, tensor manipulation operations, and a few operations built with those primitive operations (e.g. matmul, conv) are converted to Table Lookups under the hood: + +Table Lookups are very flexible. They allow Concrete to support many operations, but they are expensive. The exact cost depends on many variables (hardware used, error probability, etc.), but they are always much more expensive compared to other operations. You should try to avoid them as much as possible. It's not always possible to avoid them completely, but you might remove the number of TLUs or replace some of them with other primitive operations. + +{% hint style="info" %} +Concrete automatically parallelizes TLUs if they are applied to tensors. +{% endhint %} ## Direct table lookup @@ -172,3 +178,47 @@ The function is first traced into: {% hint style="info" %} Fusing makes the code more readable and easier to modify, so try to utilize it over manual `LookupTable`s as much as possible. {% endhint %} + +## Using automatically created table lookup + +We refer the users to [this page](./extensions.md) for explanations about +`fhe.univariate(function)` and `fhe.multivariate(function)` features, which are convenient ways to +use automatically created table lookup. + +## Table lookup exactness + +TLUs are performed with an FHE operation called `Programmable Bootstrapping` (PBS). PBS's have a certain probability of error, which, when triggered, result in inaccurate results. + +Let's say you have the table: + +```python +lut = [0, 1, 4, 9, 16, 25, 36, 49, 64] +``` + +And you perform a Table Lookup using `4`. The result you should get is `lut[4] = 16`, but because of the possibility of error, you could get any other value in the table. + +The probability of this error can be configured through the `p_error` and `global_p_error` configuration options. The difference between these two options is that, `p_error` is for individual TLUs but `global_p_error` is for the whole circuit. + +If you set `p_error` to `0.01`, for example, it means every TLU in the circuit will have a 99% chance of being exact with a 1% probability of error. If you have a single TLU in the circuit, `global_p_error` would be 1% as well. But if you have 2 TLUs for example, `global_p_error` would be almost 2% (`1 - (0.99 * 0.99)`). + +However, if you set `global_p_error` to `0.01`, the whole circuit will have 1% probability of error, no matter how many Table Lookups are included. + +If you set both of them, both will be satisfied. Essentially, the stricter one will be used. + +By default, both `p_error` and `global_p_error` is set to `None`, which results in a `global_p_error` of `1 / 100_000` being used. + +Feel free to play with these configuration options to pick the one best suited for your needs! See [How to Configure](../howto/configure.md) to learn how you can set a custom `p_error` and/or `global_p_error`. + +{% hint style="info" %} +Configuring either of those variables impacts computation time (compilation, keys generation, circuit execution) and space requirements (size of the keys on disk and in memory). Lower error probabilities would result in longer computation times and larger space requirements. +{% endhint %} + +## Table lookup performance + +PBS are very expensive, in terms of computations. Fortunately, it is sometimes possible to replace +PBS by [rounded PBS](./rounding.md), [truncate PBS](./truncating.md) or even +[approximate PBS](./rounding.md). These TLU have a slightly different semantic, but are very useful in +cases like machine learning for more efficiency without drop of accuracy. + + +