Skip to content

Commit

Permalink
Differentiate VM configuration and filter configuration. (#91)
Browse files Browse the repository at this point in the history
Signed-off-by: John Plevyak <[email protected]>
  • Loading branch information
jplevyak authored Jul 31, 2019
1 parent 89200de commit 3504b4e
Show file tree
Hide file tree
Showing 56 changed files with 3,952 additions and 3,742 deletions.
2 changes: 1 addition & 1 deletion api/envoy/config/wasm/v2/wasm.proto
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ message VmConfig {
// The Wasm code that Envoy will execute.
envoy.api.v2.core.DataSource code = 2;
// The Wasm configuration string used on initialization of a new VM.
string initial_configuration = 3;
string configuration = 3;
// Allow the wasm_file to include pre-compiled code.
bool allow_precompiled = 4;
}
Expand Down
3 changes: 2 additions & 1 deletion api/wasm/cpp/proxy_wasm_externs.h
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,8 @@
// Non-stream calls.
extern "C" EMSCRIPTEN_KEEPALIVE void proxy_onStart(uint32_t root_context_id, uint32_t root_id_ptr, uint32_t root_id_size);
extern "C" EMSCRIPTEN_KEEPALIVE void proxy_onStart(uint32_t root_context_id, uint32_t root_id_ptr, uint32_t root_id_size,
uint32_t vm_configuration_ptr, uint32_t vm_configuration_size);
extern "C" EMSCRIPTEN_KEEPALIVE void proxy_onConfigure(uint32_t root_context_id, uint32_t configuration_ptr, uint32_t configuration_size);
extern "C" EMSCRIPTEN_KEEPALIVE void proxy_onTick(uint32_t root_context_id);
extern "C" EMSCRIPTEN_KEEPALIVE void proxy_onQueueReady(uint32_t root_context_id, uint32_t token);
Expand Down
2 changes: 1 addition & 1 deletion api/wasm/cpp/proxy_wasm_impl.h
Original file line number Diff line number Diff line change
Expand Up @@ -285,7 +285,7 @@ class RootContext : public ContextBase {
// Called once when the VM loads and once when each hook loads and whenever configuration changes.
virtual void onConfigure(std::unique_ptr<WasmData> /* configuration */) {}
// Called when each hook loads.
virtual void onStart() {}
virtual void onStart(WasmDataPtr /* vm_configuration */) {}
// Called when the timer goes off.
virtual void onTick() {}
// Called when data arrives on a SharedQueue.
Expand Down
6 changes: 4 additions & 2 deletions api/wasm/cpp/proxy_wasm_intrinsics.cc
Original file line number Diff line number Diff line change
Expand Up @@ -97,8 +97,10 @@ RootContext* getRoot(StringView root_id) {
return nullptr;
}

extern "C" EMSCRIPTEN_KEEPALIVE void proxy_onStart(uint32_t root_context_id, uint32_t root_id_ptr, uint32_t root_id_size) {
ensureRootContext(root_context_id, std::make_unique<WasmData>(reinterpret_cast<char*>(root_id_ptr), root_id_size))->onStart();
extern "C" EMSCRIPTEN_KEEPALIVE void proxy_onStart(uint32_t root_context_id, uint32_t root_id_ptr, uint32_t root_id_size,
uint32_t vm_configuration_ptr, uint32_t vm_configuration_size) {
ensureRootContext(root_context_id, std::make_unique<WasmData>(reinterpret_cast<char*>(root_id_ptr), root_id_size))->onStart(
std::make_unique<WasmData>(reinterpret_cast<char*>(vm_configuration_ptr), vm_configuration_size));
}

extern "C" EMSCRIPTEN_KEEPALIVE void proxy_onConfigure(uint32_t root_context_id, uint32_t ptr, uint32_t size) {
Expand Down
4 changes: 2 additions & 2 deletions examples/wasm/envoy_filter_http_wasm_example.cc
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ class ExampleRootContext : public RootContext {
public:
explicit ExampleRootContext(uint32_t id, StringView root_id) : RootContext(id, root_id) {}

void onStart() override;
void onStart(WasmDataPtr) override;
};

class ExampleContext : public Context {
Expand All @@ -26,7 +26,7 @@ class ExampleContext : public Context {
static RegisterContextFactory register_ExampleContext(CONTEXT_FACTORY(ExampleContext),
ROOT_FACTORY(ExampleRootContext));

void ExampleRootContext::onStart() { logTrace("onStart"); }
void ExampleRootContext::onStart(WasmDataPtr) { logTrace("onStart"); }

void ExampleContext::onCreate() { logWarn(std::string("onCreate " + std::to_string(id()))); }

Expand Down
Binary file modified examples/wasm/envoy_filter_http_wasm_example.wasm
Binary file not shown.
920 changes: 466 additions & 454 deletions examples/wasm/envoy_filter_http_wasm_example.wat

Large diffs are not rendered by default.

21 changes: 12 additions & 9 deletions source/extensions/common/wasm/null/null.cc
Original file line number Diff line number Diff line change
Expand Up @@ -236,13 +236,6 @@ void NullVm::getFunction(absl::string_view functionName, WasmCall3Void* f) {
SaveRestoreContext saved_context(context);
plugin->onConfigure(context_id.u64, ptr.u64, size.u64);
};
} else if (functionName == "_proxy_onStart") {
auto plugin = plugin_.get();
*f = [plugin](Common::Wasm::Context* context, Word context_id, Word root_id_ptr,
Word root_id_size) {
SaveRestoreContext saved_context(context);
plugin->onStart(context_id.u64, root_id_ptr.u64, root_id_size.u64);
};
} else {
throw WasmVmException(fmt::format("Missing getFunction for: {}", functionName));
}
Expand Down Expand Up @@ -270,6 +263,14 @@ void NullVm::getFunction(absl::string_view functionName, WasmCall5Void* f) {
plugin->onGrpcClose(context_id.u64, token.u64, status_code.u64, status_message_ptr.u64,
status_message_size.u64);
};
} else if (functionName == "_proxy_onStart") {
auto plugin = plugin_.get();
*f = [plugin](Common::Wasm::Context* context, Word context_id, Word root_id_ptr,
Word root_id_size, Word vm_configuration_ptr, Word vm_configuration_size) {
SaveRestoreContext saved_context(context);
plugin->onStart(context_id.u64, root_id_ptr.u64, root_id_size.u64, vm_configuration_ptr.u64,
vm_configuration_size.u64);
};
} else {
throw WasmVmException(fmt::format("Missing getFunction for: {}", functionName));
}
Expand Down Expand Up @@ -428,10 +429,12 @@ Plugin::RootContext* NullVmPlugin::getRoot(absl::string_view root_id) {
return it->second;
}

void NullVmPlugin::onStart(uint64_t root_context_id, uint64_t root_id_ptr, uint64_t root_id_size) {
void NullVmPlugin::onStart(uint64_t root_context_id, uint64_t root_id_ptr, uint64_t root_id_size,
uint64_t vm_configuration_ptr, uint64_t vm_configuration_size) {
ensureRootContext(root_context_id,
std::make_unique<WasmData>(reinterpret_cast<char*>(root_id_ptr), root_id_size))
->onStart();
->onStart(std::make_unique<WasmData>(reinterpret_cast<char*>(vm_configuration_ptr),
vm_configuration_size));
}

void NullVmPlugin::onConfigure(uint64_t root_context_id, uint64_t ptr, uint64_t size) {
Expand Down
3 changes: 2 additions & 1 deletion source/extensions/common/wasm/null/null.h
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,8 @@ class NullVmPlugin {
NullVmPlugin(const NullVmPlugin& other) : registry_(other.registry_) {}

void start() {}
void onStart(uint64_t root_context_id, uint64_t root_id_ptr, uint64_t root_id_size);
void onStart(uint64_t root_context_id, uint64_t root_id_ptr, uint64_t root_id_size,
uint64_t vm_configuration_ptr, uint64_t vm_configuration_size);
void onConfigure(uint64_t root_context_id, uint64_t ptr, uint64_t size);
void onTick(uint64_t root_context_id);
void onQueueReady(uint64_t root_context_id, uint64_t token);
Expand Down
35 changes: 17 additions & 18 deletions source/extensions/common/wasm/wasm.cc
Original file line number Diff line number Diff line change
Expand Up @@ -1444,10 +1444,11 @@ bool Context::isSsl() { return decoder_callbacks_->connection()->ssl() != nullpt
//
// Calls into the WASM code.
//
void Context::onStart(absl::string_view root_id) {
void Context::onStart(absl::string_view root_id, absl::string_view vm_configuration) {
if (wasm_->onStart_) {
auto root_id_addr = wasm_->copyString(root_id);
wasm_->onStart_(this, id_, root_id_addr, root_id.size());
auto config_addr = wasm_->copyString(vm_configuration);
wasm_->onStart_(this, id_, root_id_addr, root_id.size(), config_addr, vm_configuration.size());
}
}

Expand Down Expand Up @@ -1688,14 +1689,14 @@ uint64_t Context::getMetric(uint32_t metric_id) {
return 0;
}

Wasm::Wasm(absl::string_view vm, absl::string_view id, absl::string_view initial_configuration,
Wasm::Wasm(absl::string_view vm, absl::string_view id, absl::string_view vm_configuration,
Upstream::ClusterManager& cluster_manager, Event::Dispatcher& dispatcher,
Stats::Scope& scope, const LocalInfo::LocalInfo& local_info,
const envoy::api::v2::core::Metadata* listener_metadata,
Stats::ScopeSharedPtr owned_scope)
: cluster_manager_(cluster_manager), dispatcher_(dispatcher), scope_(scope),
local_info_(local_info), listener_metadata_(listener_metadata), owned_scope_(owned_scope),
time_source_(dispatcher.timeSource()), initial_configuration_(initial_configuration) {
time_source_(dispatcher.timeSource()), vm_configuration_(vm_configuration) {
wasm_vm_ = Common::Wasm::createWasmVm(vm);
id_ = std::string(id);
}
Expand Down Expand Up @@ -1928,16 +1929,16 @@ void Wasm::configure(Context* root_context, absl::string_view configuration) {
}
}

Context* Wasm::start(absl::string_view root_id) {
Context* Wasm::start(absl::string_view root_id, absl::string_view vm_configuration) {
auto it = root_contexts_.find(root_id);
if (it != root_contexts_.end()) {
it->second->onStart(root_id);
it->second->onStart(root_id, vm_configuration);
return it->second.get();
}
auto context = std::make_unique<Context>(this, root_id);
auto context_ptr = context.get();
root_contexts_[root_id] = std::move(context);
context_ptr->onStart(root_id);
context_ptr->onStart(root_id, vm_configuration);
return context_ptr;
};

Expand All @@ -1950,7 +1951,7 @@ void Wasm::startForTesting(std::unique_ptr<Context> context) {
contexts_[context->id_] = context.get();
}
root_contexts_[""] = std::move(context);
context_ptr->onStart("");
context_ptr->onStart("", "");
}

void Wasm::setTickPeriod(uint32_t context_id, std::chrono::milliseconds new_tick_period) {
Expand Down Expand Up @@ -2297,9 +2298,9 @@ createWasmInternal(absl::string_view vm_id, const envoy::config::wasm::v2::VmCon
const envoy::api::v2::core::Metadata* listener_metadata,
Stats::ScopeSharedPtr scope_ptr,
std::unique_ptr<Context> root_context_for_testing) {
auto wasm = std::make_shared<Wasm>(vm_config.vm(), vm_id, vm_config.initial_configuration(),
cluster_manager, dispatcher, scope, local_info,
listener_metadata, scope_ptr);
auto wasm =
std::make_shared<Wasm>(vm_config.vm(), vm_id, vm_config.configuration(), cluster_manager,
dispatcher, scope, local_info, listener_metadata, scope_ptr);
const auto& code = Config::DataSource::read(vm_config.code(), true, api);
const auto& path = Config::DataSource::getPath(vm_config.code())
.value_or(code.empty() ? EMPTY_STRING : INLINE_STRING);
Expand All @@ -2311,12 +2312,11 @@ createWasmInternal(absl::string_view vm_id, const envoy::config::wasm::v2::VmCon
}
Context* context;
if (!root_context_for_testing) {
context = wasm->start(root_id);
context = wasm->start(root_id, vm_config.configuration());
} else {
context = root_context_for_testing.get();
wasm->startForTesting(std::move(root_context_for_testing));
}
wasm->configure(context, vm_config.initial_configuration());
return wasm;
}

Expand Down Expand Up @@ -2352,17 +2352,16 @@ std::shared_ptr<Wasm> createThreadLocalWasm(Wasm& base_wasm, absl::string_view r
Context* root_context;
if (base_wasm.wasmVm()->clonable()) {
wasm = std::make_shared<Wasm>(base_wasm, dispatcher);
root_context = wasm->start(root_id);
root_context = wasm->start(root_id, base_wasm.vm_configuration());
} else {
wasm = std::make_shared<Wasm>(base_wasm.wasmVm()->vm(), base_wasm.id(),
base_wasm.initial_configuration(), base_wasm.clusterManager(),
base_wasm.vm_configuration(), base_wasm.clusterManager(),
dispatcher, base_wasm.scope(), base_wasm.localInfo(),
base_wasm.listenerMetadata(), nullptr /* owned scope */);
if (!wasm->initialize(base_wasm.code(), base_wasm.id(), base_wasm.allow_precompiled())) {
throw WasmException("Failed to initialize WASM code");
}
root_context = wasm->start(root_id);
wasm->configure(root_context, base_wasm.initial_configuration());
root_context = wasm->start(root_id, base_wasm.vm_configuration());
}
wasm->configure(root_context, configuration);
if (!wasm->id().empty()) {
Expand All @@ -2378,7 +2377,7 @@ std::shared_ptr<Wasm> getThreadLocalWasm(absl::string_view vm_id, absl::string_v
throw WasmException(fmt::format("Failed to find WASM vm_id {}", vm_id));
}
auto wasm = it->second;
auto root_context = wasm->start(id);
auto root_context = wasm->start(id, wasm->vm_configuration());
wasm->configure(root_context, configuration);
return wasm;
}
Expand Down
17 changes: 9 additions & 8 deletions source/extensions/common/wasm/wasm.h
Original file line number Diff line number Diff line change
Expand Up @@ -314,7 +314,7 @@ class Context : public Http::StreamFilter,
//
// VM level downcalls into the WASM code on Context(id == 0).
//
virtual void onStart(absl::string_view root_id);
virtual void onStart(absl::string_view root_id, absl::string_view vm_configuration);
virtual void onConfigure(absl::string_view configuration);

//
Expand Down Expand Up @@ -571,7 +571,7 @@ class Wasm : public Envoy::Server::Wasm,
public Logger::Loggable<Logger::Id::wasm>,
public std::enable_shared_from_this<Wasm> {
public:
Wasm(absl::string_view vm, absl::string_view id, absl::string_view initial_configuration,
Wasm(absl::string_view vm, absl::string_view id, absl::string_view vm_configuration,
Upstream::ClusterManager& cluster_manager, Event::Dispatcher& dispatcher,
Stats::Scope& scope, const LocalInfo::LocalInfo& local_info,
const envoy::api::v2::core::Metadata* listener_metadata,
Expand All @@ -581,7 +581,8 @@ class Wasm : public Envoy::Server::Wasm,

bool initialize(const std::string& code, absl::string_view name, bool allow_precompiled);
void configure(Context* root_context, absl::string_view configuration);
Context* start(absl::string_view root_id); // returns the root Context.
Context* start(absl::string_view root_id,
absl::string_view vm_configuration); // returns the root Context.

const std::string& context_id_filter_state_data_name() {
return context_id_filter_state_data_name_;
Expand All @@ -608,10 +609,10 @@ class Wasm : public Envoy::Server::Wasm,
uint32_t allocContextId();

const std::string& code() const { return code_; }
const std::string& initial_configuration() const { return initial_configuration_; }
const std::string& vm_configuration() const { return vm_configuration_; }
bool allow_precompiled() const { return allow_precompiled_; }
void setInitialConfiguration(const std::string& initial_configuration) {
initial_configuration_ = initial_configuration;
void setInitialConfiguration(const std::string& vm_configuration) {
vm_configuration_ = vm_configuration;
}

//
Expand Down Expand Up @@ -707,7 +708,7 @@ class Wasm : public Envoy::Server::Wasm,
WasmCall1Void free_;

// Calls into the VM.
WasmContextCall2Void onStart_;
WasmContextCall4Void onStart_;
WasmContextCall2Void onConfigure_;
WasmContextCall0Void onTick_;

Expand Down Expand Up @@ -739,7 +740,7 @@ class Wasm : public Envoy::Server::Wasm,

// Used by the base_wasm to enable non-clonable thread local Wasm(s) to be constructed.
std::string code_;
std::string initial_configuration_;
std::string vm_configuration_;
bool allow_precompiled_ = false;

bool is_emscripten_ = false;
Expand Down
2 changes: 1 addition & 1 deletion source/extensions/wasm/config.cc
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ Server::WasmSharedPtr WasmFactory::createWasm(const envoy::config::wasm::v2::Was
nullptr /* listener_metadata */, context.scope());
if (config.singleton()) {
// Return the WASM VM which will be stored as a singleton by the Server.
auto root_context = base_wasm->start(root_id);
auto root_context = base_wasm->start(root_id, config.vm_config().configuration());
base_wasm->configure(root_context, config.configuration());
return base_wasm;
}
Expand Down
Binary file modified test/extensions/access_loggers/wasm/test_data/logging.wasm
Binary file not shown.
Loading

0 comments on commit 3504b4e

Please sign in to comment.