blob: 96e619c10d9bddeb1e94bf23f9716ee820bc5813 [file] [log] [blame]
/*
* Copyright 2024 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#pragma once
#include "InputTracerInterface.h"
#include <memory>
#include "../Entry.h"
#include "InputTracingBackendInterface.h"
namespace android::inputdispatcher::trace::impl {
/**
* The tracer implementation for InputDispatcher.
*
* InputTracer's responsibility is to keep track of events as they are processed by InputDispatcher,
* and to write the events to the tracing backend when enough information is collected. InputTracer
* is not thread-safe.
*
* See the documentation in InputTracerInterface for the API surface.
*/
class InputTracer : public InputTracerInterface {
public:
explicit InputTracer(std::unique_ptr<InputTracingBackendInterface>);
~InputTracer() = default;
InputTracer(const InputTracer&) = delete;
InputTracer& operator=(const InputTracer&) = delete;
std::unique_ptr<EventTrackerInterface> traceInboundEvent(const EventEntry&) override;
std::unique_ptr<EventTrackerInterface> createTrackerForSyntheticEvent() override;
void dispatchToTargetHint(const EventTrackerInterface&, const InputTarget&) override;
void eventProcessingComplete(const EventTrackerInterface&,
nsecs_t processingTimestamp) override;
std::unique_ptr<EventTrackerInterface> traceDerivedEvent(const EventEntry&,
const EventTrackerInterface&) override;
void traceEventDispatch(const DispatchEntry&, const EventTrackerInterface&) override;
void setInputMethodConnectionIsActive(bool isActive) override {
mIsImeConnectionActive = isActive;
}
private:
std::unique_ptr<InputTracingBackendInterface> mBackend;
bool mIsImeConnectionActive{false};
// The state of a tracked event, shared across all events derived from the original event.
struct EventState {
explicit inline EventState(InputTracer& tracer) : tracer(tracer){};
~EventState();
void onEventProcessingComplete(nsecs_t processingTimestamp);
InputTracer& tracer;
std::vector<TracedEvent> events;
bool isEventProcessingComplete{false};
// A queue to hold dispatch args from being traced until event processing is complete.
std::vector<WindowDispatchArgs> pendingDispatchArgs;
// The metadata should not be modified after event processing is complete.
TracedEventMetadata metadata{};
};
// Get the event state associated with a tracking cookie.
std::shared_ptr<EventState>& getState(const EventTrackerInterface&);
bool isDerivedCookie(const EventTrackerInterface&);
// Implementation of the event tracker cookie. The cookie holds the event state directly for
// convenience to avoid the overhead of tracking the state separately in InputTracer.
class EventTrackerImpl : public EventTrackerInterface {
public:
inline EventTrackerImpl(const std::shared_ptr<EventState>& state, bool isDerivedEvent)
: mState(state), mIsDerived(isDerivedEvent) {}
EventTrackerImpl(const EventTrackerImpl&) = default;
private:
mutable std::shared_ptr<EventState> mState;
const bool mIsDerived;
friend std::shared_ptr<EventState>& InputTracer::getState(const EventTrackerInterface&);
friend bool InputTracer::isDerivedCookie(const EventTrackerInterface&);
};
};
} // namespace android::inputdispatcher::trace::impl