Source code

Revision control

Copy as Markdown

Other Tools

/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim:set ts=2 sw=2 sts=2 et cindent: */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
#ifndef mozilla_dom_SerialPortParent_h
#define mozilla_dom_SerialPortParent_h
#include "mozilla/dom/PSerialPortParent.h"
#include "mozilla/dom/SerialPlatformService.h"
#include "mozilla/ipc/DataPipe.h"
#include "nsISupports.h"
namespace mozilla::dom {
class SerialDeviceChangeProxy;
namespace webserial {
class SerialPortReadPump;
class SerialPortWritePump;
} // namespace webserial
// Parent-side actor for a serial port. Bound to the SerialPlatformService IO
// thread so const that I/O operations can be performed directly without
// dispatching to a separate thread. Data flows through DataPipes; control
// messages (Drain, Flush, Close) use IPC. Note that non-const members are only
// safe to access on the SerialPlatformService's IOThread.
class SerialPortParent final : public PSerialPortParent {
public:
NS_INLINE_DECL_THREADSAFE_REFCOUNTING(SerialPortParent, override)
mozilla::ipc::IPCResult RecvOpen(const IPCSerialOptions& aOptions,
OpenResolver&& aResolver);
mozilla::ipc::IPCResult RecvClose(CloseResolver&& aResolver);
mozilla::ipc::IPCResult RecvSetSignals(const IPCSerialOutputSignals& aSignals,
SetSignalsResolver&& aResolver);
mozilla::ipc::IPCResult RecvGetSignals(GetSignalsResolver&& aResolver);
mozilla::ipc::IPCResult RecvDrain(DrainResolver&& aResolver);
mozilla::ipc::IPCResult RecvFlush(bool aReceive, FlushResolver&& aResolver);
mozilla::ipc::IPCResult RecvAttachReadPipe(
const RefPtr<mozilla::ipc::DataPipeSender>& aReadPipeSender);
mozilla::ipc::IPCResult RecvAttachWritePipe(
const RefPtr<mozilla::ipc::DataPipeReceiver>& aWritePipeReceiver);
mozilla::ipc::IPCResult RecvUpdateSharingState(bool aConnected);
mozilla::ipc::IPCResult RecvClone(
mozilla::ipc::Endpoint<PSerialPortParent>&& aEndpoint);
void ActorDestroy(ActorDestroyReason aWhy) override;
bool PortIdMatches(const nsAString& aPortId) const {
return mPortId == aPortId;
}
// Called by SerialManagerParent when device connection state changes.
void NotifyConnected();
void NotifyDisconnected();
SerialPortParent(const nsString& aPortId, uint64_t aBrowserId,
SerialDeviceChangeProxy* aProxy = nullptr);
private:
~SerialPortParent();
void StopPumps();
void StopReadPump();
void StopWritePump();
void NotifySharingStateChanged(bool aConnected);
void StartReadPump(
already_AddRefed<mozilla::ipc::DataPipeSender> aReadPipeSender);
void StartWritePump(
already_AddRefed<mozilla::ipc::DataPipeReceiver> aWritePipeReceiver);
const nsString mPortId;
const uint64_t mBrowserId;
bool mIsOpen = false;
// Whether we have forwarded a connected=true sharing state notification
// without a corresponding connected=false. Used by ActorDestroy to send the
// missing disconnect so the browser sharing indicator count stays in sync.
bool mSharingConnected = false;
uint32_t mPipeCapacity = 0;
// DataPipe endpoints held by the parent: the read pump writes device data
// to mReadPipeSender, and the write pump reads JS data from
// mWritePipeReceiver.
RefPtr<mozilla::ipc::DataPipeSender> mReadPipeSender;
RefPtr<mozilla::ipc::DataPipeReceiver> mWritePipeReceiver;
RefPtr<webserial::SerialPortReadPump> mReadPump;
RefPtr<webserial::SerialPortWritePump> mWritePump;
RefPtr<SerialDeviceChangeProxy> mDeviceChangeProxy;
// Cloned actors sharing the same underlying port. When we get a
// connect/disconnect notification, we forward it to all clones too.
nsTArray<RefPtr<SerialPortParent>> mClones;
};
} // namespace mozilla::dom
#endif // mozilla_dom_SerialPortParent_h