# module `concrete.fhe.mlir.context` Declaration of `Context` class. **Global Variables** --------------- - **MAX_EXTRACTABLE_BIT** - **MIN_EXTRACTABLE_BIT** - **MAXIMUM_TLU_BIT_WIDTH** - **LUT_COSTS_V0_NORM2_0** --- ## class `Context` Context class, to perform operations on conversions. ### method `__init__` ```python __init__(context: Context, graph: Graph, configuration: Configuration) ``` --- ### method `add` ```python add(resulting_type: ConversionType, x: Conversion, y: Conversion) → Conversion ``` --- ### method `array` ```python array(resulting_type: ConversionType, elements: List[Conversion]) → Conversion ``` --- ### method `assign` ```python assign( resulting_type: ConversionType, x: Conversion, y: Conversion, index: Sequence[Union[int, integer, slice, ndarray, list, Conversion]] ) ``` --- ### method `attribute` ```python attribute(resulting_type: ConversionType, value: Any) → Attribute ``` Create an MLIR attribute. **Args:** resulting_type (ConversionType): type of the attribute value (Any): value of the attribute **Returns:** MlirAttribute: resulting MLIR attribute --- ### method `best_chunk_ranges` ```python best_chunk_ranges( x: Conversion, x_offset: int, y: Conversion, y_offset: int ) → List[Tuple[int, int]] ``` Calculate best chunk ranges for given operands. **Args:** x (Conversion) lhs of the operation x_offset (int) lhs offset y (Conversion) rhs of the operation y_offset (int) rhs offset **Returns:** List[Tuple[int, int]]: best chunk ranges for the arguments --- ### method `bitwise` ```python bitwise( resulting_type: ConversionType, x: Conversion, y: Conversion, operation: Callable[[int, int], int] ) → Conversion ``` --- ### method `bitwise_and` ```python bitwise_and( resulting_type: ConversionType, x: Conversion, y: Conversion ) → Conversion ``` --- ### method `bitwise_or` ```python bitwise_or( resulting_type: ConversionType, x: Conversion, y: Conversion ) → Conversion ``` --- ### method `bitwise_xor` ```python bitwise_xor( resulting_type: ConversionType, x: Conversion, y: Conversion ) → Conversion ``` --- ### method `broadcast_to` ```python broadcast_to(x: Conversion, shape: Tuple[int, ]) ``` --- ### method `cast` ```python cast(resulting_type: ConversionType, x: Conversion) → Conversion ``` --- ### method `cast_to_original_bit_width` ```python cast_to_original_bit_width(value: Conversion) → Conversion ``` Cast a value to its original bit width using multiplication and reinterpretation. --- ### method `compare_with_subtraction` ```python compare_with_subtraction( resulting_type: ConversionType, subtraction: Conversion, accept: Set[Comparison] ) → Conversion ``` Apply the final comparison table and return comparison result. --- ### method `comparison` ```python comparison( resulting_type: ConversionType, x: Conversion, y: Conversion, accept: Set[Comparison] ) → Conversion ``` Compare two encrypted values. **Args:** resulting_type (ConversionType): resulting type x (Conversion): lhs of comparison y (Conversion): rhs of comparison accept (Set[Comparison]): set of accepted comparison outcomes **Returns:** Conversion: result of comparison --- ### method `comparison_with_chunks` ```python comparison_with_chunks( resulting_type: ConversionType, x: Conversion, y: Conversion, accept: Set[Comparison] ) → Conversion ``` Compare encrypted values using chunks. Idea: split x and y into small chunks compare the chunks using table lookups reduce chunk comparisons to a final result --- ### method `comparison_with_chunks_equals` ```python comparison_with_chunks_equals( resulting_type: ConversionType, x: Conversion, y: Conversion, accept: Set[Comparison], x_offset: int, y_offset: int, x_was_signed: bool, y_was_signed: bool, chunk_ranges: List[Tuple[int, int]] ) → Conversion ``` Check equality of encrypted values using chunks. --- ### method `comparison_with_subtraction_trick` ```python comparison_with_subtraction_trick( resulting_type: ConversionType, x: Conversion, y: Conversion, accept: Set[Comparison], x_minus_y_dtype: Integer ) → Conversion ``` Compare encrypted values using subtraction trick. Idea: x [.] y <==> (x - y) [.] 0 where [.] is one of <,<=,==,!=,>=,> Additional Args: x_minus_y_dtype (Integer): minimal dtype that can be used to store x - y without overflows --- ### method `concatenate` ```python concatenate( resulting_type: ConversionType, xs: List[Conversion], axis: Optional[int] ) → Conversion ``` --- ### method `conditional` ```python conditional( resulting_type: Optional[ConversionType], condition: Conversion, then_builder: Callable[[], Optional[Conversion]], else_builder: Optional[Callable[[], Optional[Conversion]]] = None ) → Optional[Conversion] ``` Create an if conditional. **Args:** resulting_type (Optional[ConversionType]): resulting type of the operation condition (Conversion): condition of conditional then_builder (Callable[[], Optional[Conversion]]): builder of then block of conditional else_builder (Optional[Callable[[], Optional[Conversion]]], default = None): optional builder of else block of conditional **Returns:** Optional[Conversion]: None if resulting type is None conversion of the created operation otherwise **Notes:** > - if resulting type is not None both then and else builders need to return a conversion with the same type as resulting type --- ### method `constant` ```python constant( resulting_type: ConversionType, data: Any, use_cache: bool = True ) → Conversion ``` --- ### method `conv2d` ```python conv2d( resulting_type: ConversionType, x: Conversion, weight: Conversion, bias: Optional[Conversion], strides: Sequence[int], dilations: Sequence[int], pads: Sequence[int], group: int ) ``` --- ### method `convert_to_chunks_and_map` ```python convert_to_chunks_and_map( resulting_scalar_type: ConversionType, resulting_shape: Tuple[int, ], chunk_ranges: List[Tuple[int, int]], x: Conversion, x_offset: int, y: Conversion, y_offset: int, mapper: Callable ) → List[Conversion] ``` Extract the chunks of two values, pack them in a single integer and map the integer. **Args:** resulting_scalar_type (ConversionType): scalar type of the results resulting_shape (ConversionType): shape of the output of the operation chunk_ranges (List[Tuple[int, int]]): chunks ranges for the operation x (Conversion): first operand y (Conversion): second operand mapper (Callable): mapping function x_offset (int, default = 0): optional offset for x during chunk extraction y_offset (int, default = 0): optional offset for x during chunk extraction **Returns:** List[Conversion]: result of mapping chunks of x and y --- ### method `dot` ```python dot(resulting_type: ConversionType, x: Conversion, y: Conversion) → Conversion ``` --- ### method `dynamic_tlu` ```python dynamic_tlu( resulting_type: ConversionType, on: Conversion, table: Conversion ) → Conversion ``` --- ### method `eint` ```python eint(width: int) → ConversionType ``` Get encrypted unsigned integer type (e.g., !FHE.eint<3>, !FHE.eint<5>). --- ### method `element_typeof` ```python element_typeof(value: Union[Conversion, ConversionType]) → ConversionType ``` Get type corresponding to the elements of a tensor type. --- ### method `encrypt` ```python encrypt(resulting_type: ConversionType, x: Conversion) → Conversion ``` --- ### method `equal` ```python equal(resulting_type: ConversionType, x: Conversion, y: Conversion) → Conversion ``` --- ### method `error` ```python error(highlights: Mapping[Node, Union[str, List[str]]]) ``` Fail compilation with an error. **Args:** highlights (Mapping[Node, Union[str, List[str]]]): nodes to highlight along with messages --- ### method `esint` ```python esint(width: int) → ConversionType ``` Get encrypted signed integer type (e.g., !FHE.esint<3>, !FHE.esint<5>). --- ### method `extract_bits` ```python extract_bits( resulting_type: ConversionType, x: Conversion, bits: Union[int, integer, slice] ) → Conversion ``` --- ### method `flatten` ```python flatten(x: Conversion) → Conversion ``` --- ### method `for_loop` ```python for_loop( lower_bound: int, upper_bound: int, body: Union[Callable[[Conversion], Optional[Conversion]], Callable[[Conversion, Conversion], Optional[Conversion]]], output: Optional[Conversion] = None, step: int = 1 ) → Optional[Conversion] ``` Create a for loop. **Args:** lower_bound (int): starting position of the for loop upper_bound (int): upper bound of the for loop body (Union[ Callable[[Conversion], Optional[Conversion]], Callable[[Conversion, Conversion], Optional[Conversion]], ]): body of the for loop output (Optional[Conversion], default = None): initial value of the output of the for loop step (int, default = 1): step between the iterations of the for loop **Returns:** Optional[Conversion]: None if output is None conversion of the created operation otherwise **Notes:** > - if output is None body builder must take a single indexing variable argument - if output is not None body builder must take an indexing variable and output arguments and body must end with an scf yield operation with the updated output --- ### method `fork_type` ```python fork_type( type_: ConversionType, bit_width: Optional[int] = None, is_signed: Optional[bool] = None, shape: Optional[Tuple[int, ]] = None ) → ConversionType ``` Fork a type with some properties update. --- ### method `greater` ```python greater( resulting_type: ConversionType, x: Conversion, y: Conversion ) → Conversion ``` --- ### method `greater_equal` ```python greater_equal( resulting_type: ConversionType, x: Conversion, y: Conversion ) → Conversion ``` --- ### method `i` ```python i(width: int) → ConversionType ``` Get clear signless integer type (e.g., i3, i5). --- ### method `identity` ```python identity(resulting_type: ConversionType, x: Conversion) → Conversion ``` --- ### method `index` ```python index( resulting_type: ConversionType, x: Conversion, index: Sequence[Union[int, integer, slice, ndarray, list, Conversion]] ) → Conversion ``` --- ### method `index_type` ```python index_type() → ConversionType ``` Get index type. --- ### method `is_bit_width_compatible` ```python is_bit_width_compatible(*args: Optional[ConversionType, Conversion]) → bool ``` Check if conversion types are compatible in terms of bit-width. --- ### method `less` ```python less(resulting_type: ConversionType, x: Conversion, y: Conversion) → Conversion ``` --- ### method `less_equal` ```python less_equal( resulting_type: ConversionType, x: Conversion, y: Conversion ) → Conversion ``` --- ### method `location` ```python location() → Location ``` Create an MLIR location from the node that is being converted. --- ### method `lsb` ```python lsb(resulting_type: ConversionType, x: Conversion) → Conversion ``` --- ### method `matmul` ```python matmul( resulting_type: ConversionType, x: Conversion, y: Conversion ) → Conversion ``` --- ### method `maximum` ```python maximum( resulting_type: ConversionType, x: Conversion, y: Conversion ) → Conversion ``` --- ### method `maxpool2d` ```python maxpool2d( resulting_type: ConversionType, x: Conversion, kernel_shape: Tuple[int, ], strides: Sequence[int], dilations: Sequence[int] ) ``` --- ### method `minimum` ```python minimum( resulting_type: ConversionType, x: Conversion, y: Conversion ) → Conversion ``` --- ### method `minimum_maximum_with_chunks` ```python minimum_maximum_with_chunks( resulting_type: ConversionType, x: Conversion, y: Conversion, operation: str ) → Conversion ``` Calculate minimum or maximum between two encrypted values using chunks. --- ### method `minimum_maximum_with_trick` ```python minimum_maximum_with_trick( resulting_type: ConversionType, x: Conversion, y: Conversion, x_minus_y_dtype: Integer, intermediate_table: List[int] ) → Conversion ``` Calculate minimum or maximum between two encrypted values using minimum or maximum trick. Idea: min(x, y) <==> min(x - y, 0) + y max(x, y) <==> max(x - y, 0) + y Additional Args: x_minus_y_dtype (Integer): minimal dtype that can be used to store x - y without overflows --- ### method `mul` ```python mul(resulting_type: ConversionType, x: Conversion, y: Conversion) → Conversion ``` --- ### method `multi_tlu` ```python multi_tlu( resulting_type: ConversionType, on: Conversion, tables: Any, mapping: Any ) ``` --- ### method `multiplication_with_boolean` ```python multiplication_with_boolean( boolean: Conversion, value: Conversion, resulting_bit_width: int, chunk_size: int, inverted: bool = False ) ``` Calculate boolean * value using bits. --- ### method `multivariate_multi_tlu` ```python multivariate_multi_tlu( resulting_type: ConversionType, xs: List[Conversion], tables: Any, mapping: Any ) ``` --- ### method `multivariate_tlu` ```python multivariate_tlu( resulting_type: ConversionType, xs: List[Conversion], table: Sequence[int] ) → Conversion ``` --- ### method `neg` ```python neg(resulting_type: ConversionType, x: Conversion) → Conversion ``` --- ### method `none_type` ```python none_type() → ConversionType ``` Get none type. --- ### method `not_equal` ```python not_equal( resulting_type: ConversionType, x: Conversion, y: Conversion ) → Conversion ``` --- ### method `ones` ```python ones(resulting_type: ConversionType) → Conversion ``` --- ### method `operation` ```python operation( operation: Callable, resulting_type: Optional[ConversionType], *args, original_bit_width: Optional[int] = None, use_cache: bool = True, **kwargs ) → Conversion ``` Create a conversion from an MLIR operation. **Args:** operation (Callable): MLIR operation to create (e.g., fhe.AddEintOp) resulting_type (Optional[ConversionType]): optional type of the output of the operation *args (Any): args to pass to the operation original_bit_width (Optional[int], default = None): original bit width of the resulting conversion use_cache (bool, default = True): whether to use the operation cache or not *kwargs (Any): kwargs to pass to the operation **Returns:** Conversion: resulting conversion --- ### method `pack_multivariate_inputs` ```python pack_multivariate_inputs(xs: List[Conversion]) → Conversion ``` Packs inputs of multivariate table lookups. **Args:** xs (List[Conversion]): operands **Returns:** Conversion: packed operands --- ### method `reinterpret` ```python reinterpret( x: Conversion, bit_width: int, signed: Optional[bool] = None ) → Conversion ``` --- ### method `relu` ```python relu(resulting_type: ConversionType, x: Conversion) → Conversion ``` --- ### method `reshape` ```python reshape(x: Conversion, shape: Tuple[int, ]) → Conversion ``` --- ### method `round_bit_pattern` ```python round_bit_pattern( resulting_type: ConversionType, x: Conversion, lsbs_to_remove: int, exactness: Exactness, overflow_detected: bool ) → Conversion ``` --- ### method `safe_reduce_precision` ```python safe_reduce_precision(x: Conversion, bit_width: int) → Conversion ``` --- ### method `shift` ```python shift( resulting_type: ConversionType, x: Conversion, b: Conversion, orientation: str, original_resulting_bit_width: int ) → Conversion ``` --- ### method `shift_left_at_constant_precision` ```python shift_left_at_constant_precision(x: Conversion, rank: int) → Conversion ``` --- ### method `sub` ```python sub(resulting_type: ConversionType, x: Conversion, y: Conversion) → Conversion ``` --- ### method `sum` ```python sum( resulting_type: ConversionType, x: Conversion, axes: Optional[int, Sequence[int]] = (), keep_dims: bool = False ) → Conversion ``` --- ### method `tensor` ```python tensor(element_type: ConversionType, shape: Tuple[int, ]) → ConversionType ``` Get tensor type (e.g., tensor<5xi3>, tensor<3x2x!FHE.eint<5>>). --- ### method `tensorize` ```python tensorize(x: Conversion) → Conversion ``` --- ### method `tlu` ```python tlu(resulting_type: ConversionType, on: Conversion, table: Sequence[int]) ``` --- ### method `to_signed` ```python to_signed(x: Conversion) → Conversion ``` --- ### method `to_signedness` ```python to_signedness(x: Conversion, of: ConversionType) → Conversion ``` --- ### method `to_unsigned` ```python to_unsigned(x: Conversion) → Conversion ``` --- ### method `transpose` ```python transpose( resulting_type: ConversionType, x: Conversion, axes: Sequence[int] = () ) ``` --- ### method `tree_add` ```python tree_add(resulting_type: ConversionType, xs: List[Conversion]) → Conversion ``` --- ### method `truncate_bit_pattern` ```python truncate_bit_pattern(x: Conversion, lsbs_to_remove: int) → Conversion ``` --- ### method `try_comparison_with_clipping_trick` ```python try_comparison_with_clipping_trick( resulting_type: ConversionType, x: Conversion, y: Conversion, accept: Set[Comparison] ) → Optional[Conversion] ``` Compare encrypted values using clipping trick. Idea: x [.] y <==> (clipped(x) - y) [.] 0 where [.] is one of <,<=,==,!=,>=,> or x [.] y <==> (x - clipped(y)) [.] 0 where [.] is one of <,<=,==,!=,>=,> where clipped(value) = np.clip(value, smaller.min() - 1, smaller.max() + 1) Additional Args: smaller_minus_clipped_bigger_dtype (Integer): minimal dtype that can be used to store smaller - clipped(bigger) without overflows clipped_bigger_minus_smaller_dtype (Integer): minimal dtype that can be used to store clipped(bigger) - smaller without overflows smaller_bounds (Tuple[int, int]): bounds of smaller smaller_is_lhs (bool): whether smaller is lhs of the comparison smaller_is_rhs (bool): whether smaller is rhs of the comparison --- ### method `typeof` ```python typeof(value: Optional[ValueDescription, Node]) → ConversionType ``` Get type corresponding to a value or a node. --- ### method `where` ```python where( resulting_type: ConversionType, condition: Conversion, when_true: Conversion, when_false: Conversion ) → Conversion ``` --- ### method `zeros` ```python zeros(resulting_type: ConversionType) → Conversion ```