1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ 2 /* vim: set ts=8 sts=2 et sw=2 tw=80: */ 3 /* This Source Code Form is subject to the terms of the Mozilla Public 4 * License, v. 2.0. If a copy of the MPL was not distributed with this file, 5 * You can obtain one at http://mozilla.org/MPL/2.0/. */ 6 7 #ifndef mozilla_extensions_StreamFilterChild_h 8 #define mozilla_extensions_StreamFilterChild_h 9 10 #include "StreamFilterBase.h" 11 #include "mozilla/extensions/PStreamFilterChild.h" 12 #include "mozilla/extensions/StreamFilter.h" 13 14 #include "mozilla/LinkedList.h" 15 #include "mozilla/dom/StreamFilterBinding.h" 16 #include "nsISupportsImpl.h" 17 18 namespace mozilla { 19 class ErrorResult; 20 21 namespace extensions { 22 23 using mozilla::dom::StreamFilterStatus; 24 using mozilla::ipc::IPCResult; 25 26 class StreamFilter; 27 28 class StreamFilterChild final : public PStreamFilterChild, 29 public StreamFilterBase { 30 friend class StreamFilter; 31 friend class PStreamFilterChild; 32 33 public: NS_INLINE_DECL_REFCOUNTING(StreamFilterChild)34 NS_INLINE_DECL_REFCOUNTING(StreamFilterChild) 35 36 StreamFilterChild() : mState(State::Uninitialized), mReceivedOnStop(false) {} 37 38 enum class State { 39 // Uninitialized, waiting for constructor response from parent. 40 Uninitialized, 41 // Initialized, but channel has not begun transferring data. 42 Initialized, 43 // The stream's OnStartRequest event has been dispatched, and the channel is 44 // transferring data. 45 TransferringData, 46 // The channel's OnStopRequest event has been dispatched, and the channel is 47 // no longer transferring data. Data may still be written to the output 48 // stream listener. 49 FinishedTransferringData, 50 // The channel is being suspended, and we're waiting for confirmation of 51 // suspension from the parent. 52 Suspending, 53 // The channel has been suspended in the parent. Data may still be written 54 // to the output stream listener in this state. 55 Suspended, 56 // The channel is suspended. Resume has been called, and we are waiting for 57 // confirmation of resumption from the parent. 58 Resuming, 59 // The close() method has been called, and no further output may be written. 60 // We are waiting for confirmation from the parent. 61 Closing, 62 // The close() method has been called, and we have been disconnected from 63 // our parent. 64 Closed, 65 // The channel is being disconnected from the parent, and all further events 66 // and data will pass unfiltered. Data received by the child in this state 67 // will be automatically written to the output stream listener. No data may 68 // be explicitly written. 69 Disconnecting, 70 // The channel has been disconnected from the parent, and all further data 71 // and events will be transparently passed to the output stream listener 72 // without passing through the child. 73 Disconnected, 74 // An error has occurred and the child is disconnected from the parent. 75 Error, 76 }; 77 78 void Suspend(ErrorResult& aRv); 79 void Resume(ErrorResult& aRv); 80 void Disconnect(ErrorResult& aRv); 81 void Close(ErrorResult& aRv); 82 void Cleanup(); 83 84 void Write(Data&& aData, ErrorResult& aRv); 85 GetState()86 State GetState() const { return mState; } 87 88 StreamFilterStatus Status() const; 89 90 void RecvInitialized(bool aSuccess); 91 92 protected: 93 IPCResult RecvStartRequest(); 94 IPCResult RecvData(Data&& data); 95 IPCResult RecvStopRequest(const nsresult& aStatus); 96 IPCResult RecvError(const nsCString& aError); 97 98 IPCResult RecvClosed(); 99 IPCResult RecvSuspended(); 100 IPCResult RecvResumed(); 101 IPCResult RecvFlushData(); 102 103 virtual void ActorDealloc() override; 104 SetStreamFilter(StreamFilter * aStreamFilter)105 void SetStreamFilter(StreamFilter* aStreamFilter) { 106 mStreamFilter = aStreamFilter; 107 } 108 109 private: 110 ~StreamFilterChild() = default; 111 112 void SetNextState(); 113 114 void MaybeStopRequest(); 115 116 void EmitData(const Data& aData); 117 CanFlushData()118 bool CanFlushData() { 119 return (mState == State::TransferringData || mState == State::Resuming); 120 } 121 122 void FlushBufferedData(); 123 void WriteBufferedData(); 124 125 virtual void ActorDestroy(ActorDestroyReason aWhy) override; 126 127 State mState; 128 State mNextState; 129 bool mReceivedOnStop; 130 131 RefPtr<StreamFilter> mStreamFilter; 132 }; 133 134 } // namespace extensions 135 } // namespace mozilla 136 137 #endif // mozilla_extensions_StreamFilterChild_h 138