Files
fhevm-solidity/codegen/common.ts
Joseph-André Turk 45e860d577 feat: updated TFHEExecutor to support new types
chore: eq-neq  bool support and bitwise scalar support

chore: overloads for fheEq and fheNe

fix: reverts onchain when rhs is 0 in fheDiv-fheRem

feat: added support for scalar and,or,xor

chore: cleanup codegen

feat: adds euint128 and euint256 types

chore: removes ebool fheRandBounded and adds manual tests

feat: adds new types for fheRand

feat: adds trivialEncrypt for ebytesXXX

feat: adds fheEq fheNe ifThenElse for new types

chore: rename asyncDecrypt() to initGateway()
2024-10-18 02:33:10 +02:00

263 lines
5.9 KiB
TypeScript

import { strict as assert } from 'node:assert';
export enum Network {
Evmos,
Network1,
}
export type Operator = {
name: string;
// express left scalar operation as different operation with arguments swapped
leftScalarInvertOp?: string;
precompileName: string;
hasScalar: boolean;
hasEncrypted: boolean;
arguments: OperatorArguments;
returnType: ReturnType;
// if true do trivial encryption for left scalar operand, this is workaround until tfhe-rs supports left scalar operands
leftScalarEncrypt?: boolean;
// disable left scalar operator
leftScalarDisable?: boolean;
fheLibName?: string;
binarySolidityOperator?: string;
unarySolidityOperator?: string;
shiftOperator?: boolean;
rotateOperator?: boolean;
};
export type CodegenContext = {
libFheAddress: string;
};
export enum OperatorArguments {
Binary,
Unary,
}
export enum ReturnType {
Uint,
Ebool,
}
export const SUPPORTED_BITS: number[] = [4, 8, 16, 32, 64, 128, 256];
export const ALL_OPERATORS: Operator[] = [
{
name: 'add',
precompileName: 'Add',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Uint,
binarySolidityOperator: '+',
},
{
name: 'sub',
precompileName: 'Subtract',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Uint,
leftScalarEncrypt: true,
binarySolidityOperator: '-',
},
{
name: 'mul',
precompileName: 'Multiply',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Uint,
binarySolidityOperator: '*',
},
{
name: 'div',
precompileName: 'Divide',
hasScalar: true,
hasEncrypted: false,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Uint,
leftScalarDisable: true,
},
{
name: 'rem',
precompileName: 'Rem',
hasScalar: true,
hasEncrypted: false,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Uint,
leftScalarDisable: true,
},
{
name: 'and',
precompileName: 'BitwiseAnd',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Uint,
fheLibName: 'fheBitAnd',
binarySolidityOperator: '&',
},
{
name: 'or',
precompileName: 'BitwiseOr',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Uint,
fheLibName: 'fheBitOr',
binarySolidityOperator: '|',
},
{
name: 'xor',
precompileName: 'BitwiseXor',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Uint,
fheLibName: 'fheBitXor',
binarySolidityOperator: '^',
},
{
name: 'shl',
precompileName: 'ShiftLeft',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Uint,
leftScalarEncrypt: true,
shiftOperator: true,
},
{
name: 'shr',
precompileName: 'ShiftRight',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Uint,
leftScalarEncrypt: true,
shiftOperator: true,
},
{
name: 'rotl',
precompileName: 'RotateLeft',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Uint,
leftScalarEncrypt: true,
rotateOperator: true,
},
{
name: 'rotr',
precompileName: 'RotateRight',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Uint,
leftScalarEncrypt: true,
rotateOperator: true,
},
{
name: 'eq',
precompileName: 'Equal',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Ebool,
},
{
name: 'ne',
precompileName: 'NotEqual',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Ebool,
},
{
name: 'ge',
leftScalarInvertOp: 'le',
precompileName: 'GreaterThanOrEqual',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Ebool,
},
{
name: 'gt',
leftScalarInvertOp: 'lt',
precompileName: 'GreaterThan',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Ebool,
},
{
name: 'le',
leftScalarInvertOp: 'ge',
precompileName: 'LessThanOrEqual',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Ebool,
},
{
name: 'lt',
leftScalarInvertOp: 'gt',
precompileName: 'LessThan',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Ebool,
},
{
name: 'min',
precompileName: 'Min',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Uint,
},
{
name: 'max',
precompileName: 'Max',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Binary,
returnType: ReturnType.Uint,
},
{
name: 'neg',
precompileName: 'Negate',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Unary,
returnType: ReturnType.Uint,
unarySolidityOperator: '-',
},
{
name: 'not',
precompileName: 'Not',
hasScalar: true,
hasEncrypted: true,
arguments: OperatorArguments.Unary,
returnType: ReturnType.Uint,
unarySolidityOperator: '~',
},
];
export function checks(operators: Operator[]): Operator[] {
const nameMap: { [key: string]: boolean } = {};
const precompNameMap: { [key: string]: boolean } = {};
operators.forEach((op) => {
assert(nameMap[op.name] == null);
nameMap[op.name] = true;
assert(precompNameMap[op.precompileName] == null);
precompNameMap[op.precompileName] = true;
});
return operators;
}