Here, you'll prepare a build target, that your host code will make use of.
Start by preparing a
sapi_library() target in your
For reference, you can take a peek at a working example from the zlib example.
load( "//sandboxed_api/tools/generator:sapi_generator.bzl", "sapi_library", ) sapi_library( name = "zlib-sapi", srcs = , # Extra code compiled with the SAPI library hdrs = , # Leave empty if embedded SAPI libraries are used, and the # default sandbox policy is sufficient. embed = True, # This is the default functions = [ "deflateInit_", "deflate", "deflateEnd", ], lib = "@zlib//:zlibonly", lib_name = "Zlib", namespace = "sapi::zlib", )
name- name for your SAPI target
srcs- any additional sources that you'd like to include with your Sandboxed API library - typically, it's not necessary, unless you want to provide your SAPI Library sandbox definition in a .cc file, and not in the
hdrs- as with
srcs. Typically your sandbox definition (sandbox.h) should go here, or empty, if embedded SAPI library is used, and the default sandbox policy is sufficient.
functions- a list of functions that you'd like to use in your host code. Leaving this list empty will try to export and wrap all functions found in the library.
embed- whether the SAPI library should be embedded inside host code, so the SAPI Sandbox can be initialized with the
::sapi::Sandbox::Sandbox(FileToc*)constructor. This is the default.
lib- (mandatory) the library target you want to sandbox and expose to the host code.
lib_name- (mandatory) name of the object which is proxying your library functions from the
functionslist. You will call functions from the sandboxed library via this object.
input_files- list of source files, which SAPI interface generator should scan for library's function declarations. Library's exported headers are always scanned, so
input_filescan usually be left empty.
namespace- a C++ namespace identifier to place API object defined in
lib_nameinto. Defaults to
deps**- a list of any additional dependency targets to add. Typically not necessary.
header- name of the header file to use instead of the generated one. Do not use if you want to auto-generate the code.
sapi_library() Rule Targets
For the above definition,
sapi_library() build rule provides the following
zlib-sapi- sandboxed library, substitution for normal cc_library; consists of
zlib_sapi.binand sandbox dependencies
zlib-sapi.interface- generated library interface
cc_embed_data()target used to embed sandboxee in the binary. See
zlib-sapi.bin- sandboxee binary, consists of small communication stub and the library that is being sandboxed.
zlib-sapi target creates target library with small communication stub
wrapped in Sandbox2. To be able to use the stub and code
within the sandbox, you should generate the interface file.
There are two options:
- Add dependency on
zlib-sapi.interface. This will auto-generate a header that you can include in your code - the header name is of the form:
bazel build TARGET_NAME.interface, save generated header in your project and include it in the code. You will also need to add the
headerargument to the
sapi_library()rule to indicate that you will skip code generation.
Sandbox Description (
In this step you will prepare the sandbox definition file (typically named
sandbox.h) for your library.
The goal of this is to tell the SAPI code where the sandboxed library can be found, and how it should be contained.
At first, you should tell the SAPI code what your sandboxed library should be allowed to do in terms of security policies and other process constraints. In order to do that, you will have to implement and instantiate an object based on the ::sapi::Sandbox class.
This object will also specify where your SAPI Library can be found and how it should be executed (though you can depend on default settings).
A working example of such SAPI object definition file can be found here.
In order to familiarize yourself with the Sandbox2 policies, you might want to take a look at the Sandbox2_documentation.