Add support for result tensors composed of uint8_t, uint16_t, uint32_t
and uint64_t elements, replacing the current implementation, which
only supports uint64_t tensors.
Add a new method `JITLambda::Arguments::getResultWidth` returning the
width of a scalar result or the element type of a tensor result at a
given position.
Currently, `JITLambda::Arguments` assumes result tensors are always
composed of `uint64_t` elements. This change adds support for
arbitrary scalar element types.
Set the make variable `CCACHE` to `ON` in order to force the use of
`ccache` during compilation of the code. For unknown reasons, the
build directory must also be removed. Otherwise, a complete rebuild
circumventing the cache is triggered and `ccache` does not have any
effect on compilation time.
Debug information printing `ccache` statistics before and after the
build has also been added.
Fix compiler warnings in `end_to_end_jit_clear_tensor.cc` and
`end_to_end_jit_encrypted_tensor.cc` due to the comparison of integer
expressions of different signedness.
Lambda::operator()<unique_ptr<LambdaArgument>> was giving bad results
when using tensors due to bad references. Now it's fixed and we want to
spot that in the future.
`TensorLambdaArgument` uses an `llvm::MutableArrayRef` to reference
the tensor values. This prevents temporary tensors from being used as
an argument, due to the data of the `TensorLambdaArgument` being
accessed after the destruction of the temporary.
This patch changes the type of the data field of
`TensorLambdaArgument` from `llvm::MutableArrayRef` to `std::vector`
and causes input data to be copied in order to guarantee that all data
remains available until invocation of the destructor.
All results in code compiled by zamacompiler are passed as return
values, which means that all tensors passed as function arguments are
constant inputs that are never written.
This patch changes the arguments used as data pointers for input
tensors in `JITLambda::Arguments::setArg()` from `void*` to `const
void*` to emphasize their use as inputs and to allow for constant
arrays to be passed as function inputs.
In some cases, even small changes in zamacompiler lead to the
recompilation of the LLVM / MLIR sources, causing significant delay in
the CI. This change forces the use of ccache to speed up recompilation
after the project has been built at least once.
This adds a new variable `CCACHE` to `Makefile` that specifies whether
CMake is instructed upon configuration of the project to use the
default, plain C++ compiler or ccache as a wrapper.
By default, ccache is not used. To override the default value and
force the use of ccache, the variable `CCACHE` must be set to `ON`,
e.g., using `make CCACHE=ON`.
This adds a new overload for `JitCompilerEngine::Lambda::operator()`,
returning a result wrapped in a `std::unique_ptr<LambdaArgument>` with
meta information about the result. This allows for generic invocations
of JitCompilerEngine::Lambda::operator(), where the result type is
unknown before the invocation.
By default, `mlir::SourceMgrDiagnosticVerifierHandler` used by
`CompilerEngine::compile()` prints parse errors to
`llvm::errs()`. This makes it impossible for a caller of
`CompilerEngine::compile()` to process parse errors or to suppress the
emission of error messages to the standard error stream altogether.
This change captures parse errors in a string via a string-backed
output stream and forwards the error message in the `llvm::Error`
instance of the return value.
The code in `lib/CAPI/Support/CompilerEngine.cpp` invokes several
functions returning an `llvm::Expected<T>`. When those fail, the error
message retrieved from the error object the `llvm::Expected<T>`
instance is written to the standard error stream via
`mlir::zamalang::log_error()` and an exception with a more generic
error message is thrown.
This causes errors to show up on the standard error stream in tests
generating errors on purpose and checking them, e.g.:
```
tests/python/test_compiler_engine.py::test_compile_invalid[not
@main] Compilation failed: cannot find the function for generate
client parameters PASSED
```
This patch forwards the error message from an `llvm::Expected<T>`
instance in a runtime exception rather than writing it to the standard
error stream. Since exceptions are properly caught by the tests, no
errors show up during testing.
This commit contains several incremental improvements towards a clear
interface for lambdas:
- Unification of static and JIT compilation by using the static
compilation path of `CompilerEngine` within a new subclass
`JitCompilerEngine`.
- Clear ownership for compilation artefacts through
`CompilationContext`, making it impossible to destroy objects used
directly or indirectly before destruction of their users.
- Clear interface for lambdas generated by the compiler through
`JitCompilerEngine::Lambda` with a templated call operator,
encapsulating otherwise manual orchestration of `CompilerEngine`,
`JITLambda`, and `CompilerEngine::Argument`.
- Improved error handling through `llvm::Expected<T>` and proper
error checking following the conventions for `llvm::Expected<T>`
and `llvm::Error`.
Co-authored-by: youben11 <ayoub.benaissa@zama.ai>
As we store the funcname for the entrypoint for later use, a pointer
might point to some random memory when used as there is no special
management for that name at the higher levels.
LLVM and MLIR are compiled without runtime type information
(RTTI). Use the same restrictions for unit tests to avoid linker
errors related to typeinfo when building the test executable.
Composing error messages for `llvm::Error` is either done by using
`llvm::createStringError()` with an appropriate format string and
arguments or by writing to a `std::string`-backed
`llvm::raw_string_ostream` and passing the result to
`llvm::make_error<llvm::StringError>()` verbatim.
The new class `StreamStringError` encapsulates the latter solution
into a class with an appropriate stream operator and implicit cast
operators to `llvm::Error` and `llvm::Expected`.
Example usage:
llvm::Error foo(int i, size_t s, ...) {
...
if(...) {
return StreamStringError()
<< "Some error message with an integer: "
<< i << " and a size_t: " << s;
}
...
}