| // Copyright 2019 The Fuchsia Authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| |
| #include <fidl/fuchsia.kernel/cpp/wire.h> |
| #include <lib/kernel-debug/kernel-debug.h> |
| #include <lib/zircon-internal/ktrace.h> |
| #include <lib/zx/resource.h> |
| |
| namespace { |
| |
| class DebugBroker : public fidl::WireServer<fuchsia_kernel::DebugBroker> { |
| public: |
| explicit DebugBroker(zx::unowned_resource debug_resource) |
| : debug_resource_(std::move(debug_resource)) {} |
| |
| private: |
| void SendDebugCommand(SendDebugCommandRequestView request, |
| SendDebugCommandCompleter::Sync& completer) override { |
| completer.Reply(zx_debug_send_command(debug_resource_->get(), request->command.data(), |
| request->command.size())); |
| } |
| |
| void SetTracingEnabled(SetTracingEnabledRequestView request, |
| SetTracingEnabledCompleter::Sync& completer) override { |
| zx_status_t status; |
| if (request->enabled) { |
| status = |
| zx_ktrace_control(debug_resource_->get(), KTRACE_ACTION_START, KTRACE_GRP_ALL, nullptr); |
| } else { |
| status = zx_ktrace_control(debug_resource_->get(), KTRACE_ACTION_STOP, 0, nullptr); |
| if (status == ZX_OK) { |
| status = zx_ktrace_control(debug_resource_->get(), KTRACE_ACTION_REWIND, 0, nullptr); |
| } |
| } |
| completer.Reply(status); |
| } |
| |
| const zx::unowned_resource debug_resource_; |
| }; |
| |
| zx_status_t Connect(void* ctx, async_dispatcher_t* dispatcher, const char* service_name, |
| zx_handle_t request) { |
| zx::channel channel{request}; |
| if (fidl::DiscoverableProtocolName<fuchsia_kernel::DebugBroker> == service_name) { |
| const zx_handle_t resource = static_cast<zx_handle_t>(reinterpret_cast<uintptr_t>(ctx)); |
| fidl::BindServer(dispatcher, fidl::ServerEnd<fuchsia_kernel::DebugBroker>{std::move(channel)}, |
| std::make_unique<DebugBroker>(zx::unowned_resource{resource})); |
| return ZX_OK; |
| } |
| |
| return ZX_ERR_NOT_SUPPORTED; |
| } |
| |
| constexpr const char* kServices[] = { |
| fidl::DiscoverableProtocolName<fuchsia_kernel::DebugBroker>, |
| nullptr, |
| }; |
| |
| constexpr zx_service_ops_t kServiceOps = { |
| .init = nullptr, |
| .connect = Connect, |
| .release = nullptr, |
| }; |
| |
| constexpr zx_service_provider_t kDebugBrokerServiceProvider = { |
| .version = SERVICE_PROVIDER_VERSION, |
| .services = kServices, |
| .ops = &kServiceOps, |
| }; |
| |
| } // namespace |
| |
| const zx_service_provider_t* kernel_debug_get_service_provider() { |
| return &kDebugBrokerServiceProvider; |
| } |