tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

RemoteTextureMap.h (19335B)


      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
      5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
      6 
      7 #ifndef MOZILLA_GFX_RemoteTextureMap_H
      8 #define MOZILLA_GFX_RemoteTextureMap_H
      9 
     10 #include <deque>
     11 #include <functional>
     12 #include <list>
     13 #include <map>
     14 #include <memory>
     15 #include <queue>
     16 #include <unordered_set>
     17 #include <utility>
     18 
     19 #include "mozilla/gfx/Point.h"  // for IntSize
     20 #include "mozilla/gfx/Types.h"  // for SurfaceFormat
     21 #include "mozilla/ipc/Shmem.h"
     22 #include "mozilla/layers/CompositorTypes.h"  // for TextureFlags, etc
     23 #include "mozilla/layers/LayersSurfaces.h"   // for SurfaceDescriptor
     24 #include "mozilla/layers/TextureHost.h"
     25 #include "mozilla/Monitor.h"
     26 #include "mozilla/StaticPtr.h"
     27 #include "mozilla/UniquePtr.h"
     28 #include "mozilla/webrender/WebRenderTypes.h"
     29 
     30 class nsISerialEventTarget;
     31 
     32 namespace mozilla {
     33 
     34 namespace ipc {
     35 class IProtocol;
     36 }
     37 
     38 namespace gl {
     39 class SharedSurface;
     40 }
     41 
     42 namespace webgpu {
     43 class SharedTexture;
     44 }
     45 
     46 namespace layers {
     47 
     48 class CompositableHost;
     49 class RemoteTextureHostWrapper;
     50 class TextureData;
     51 class TextureHost;
     52 
     53 struct RemoteTextureInfo {
     54  RemoteTextureInfo(const RemoteTextureId aTextureId,
     55                    const RemoteTextureOwnerId aOwnerId,
     56                    const base::ProcessId aForPid)
     57      : mTextureId(aTextureId),
     58        mOwnerId(aOwnerId),
     59        mForPid(aForPid),
     60        mWaitForRemoteTextureOwner(false) {}
     61 
     62  RemoteTextureInfo(const RemoteTextureId aTextureId,
     63                    const RemoteTextureOwnerId aOwnerId,
     64                    const base::ProcessId aForPid,
     65                    const bool aWaitForRemoteTextureOwner)
     66      : mTextureId(aTextureId),
     67        mOwnerId(aOwnerId),
     68        mForPid(aForPid),
     69        mWaitForRemoteTextureOwner(aWaitForRemoteTextureOwner) {}
     70 
     71  const RemoteTextureId mTextureId;
     72  const RemoteTextureOwnerId mOwnerId;
     73  const base::ProcessId mForPid;
     74  const bool mWaitForRemoteTextureOwner;
     75 };
     76 
     77 struct RemoteTextureInfoList {
     78  std::queue<RemoteTextureInfo> mList;
     79 };
     80 
     81 class SharedResourceWrapper {
     82 public:
     83  enum class Tag { SharedSurface, SharedTexture };
     84  const Tag mTag;
     85 
     86  static UniquePtr<SharedResourceWrapper> SharedSurface(
     87      const std::shared_ptr<gl::SharedSurface>& aSharedSurface) {
     88    return MakeUnique<SharedResourceWrapper>(Tag::SharedSurface,
     89                                             aSharedSurface);
     90  }
     91 
     92  static UniquePtr<SharedResourceWrapper> SharedTexture(
     93      const std::shared_ptr<webgpu::SharedTexture>& aSharedTexture) {
     94    return MakeUnique<SharedResourceWrapper>(Tag::SharedTexture,
     95                                             aSharedTexture);
     96  }
     97 
     98  SharedResourceWrapper(
     99      const Tag aTag, const std::shared_ptr<gl::SharedSurface>& aSharedSurface)
    100      : mTag(aTag), mSharedSurface(aSharedSurface) {
    101    MOZ_ASSERT(mTag == Tag::SharedSurface);
    102  }
    103  SharedResourceWrapper(
    104      const Tag aTag,
    105      const std::shared_ptr<webgpu::SharedTexture>& aSharedTexture)
    106      : mTag(aTag), mSharedTexture(aSharedTexture) {
    107    MOZ_ASSERT(mTag == Tag::SharedTexture);
    108  }
    109 
    110  const std::shared_ptr<gl::SharedSurface> mSharedSurface;
    111  const std::shared_ptr<webgpu::SharedTexture> mSharedTexture;
    112 
    113  std::shared_ptr<gl::SharedSurface> SharedSurface() {
    114    if (mTag == Tag::SharedSurface) {
    115      return mSharedSurface;
    116    }
    117    MOZ_ASSERT_UNREACHABLE("unexpected to be called");
    118    return nullptr;
    119  }
    120 
    121  std::shared_ptr<webgpu::SharedTexture> SharedTexture() {
    122    if (mTag == Tag::SharedTexture) {
    123      return mSharedTexture;
    124    }
    125    MOZ_ASSERT_UNREACHABLE("unexpected to be called");
    126    return nullptr;
    127  }
    128 };
    129 
    130 class RemoteTextureRecycleBin final {
    131 public:
    132  NS_INLINE_DECL_THREADSAFE_REFCOUNTING(RemoteTextureRecycleBin)
    133 
    134  explicit RemoteTextureRecycleBin(bool aIsShared);
    135 
    136 private:
    137  friend class RemoteTextureMap;
    138 
    139  ~RemoteTextureRecycleBin();
    140 
    141  struct RecycledTextureHolder {
    142    gfx::IntSize mSize;
    143    gfx::SurfaceFormat mFormat = gfx::SurfaceFormat::UNKNOWN;
    144    SurfaceDescriptor::Type mType = SurfaceDescriptor::Tnull_t;
    145    UniquePtr<TextureData> mTextureData;
    146    UniquePtr<SharedResourceWrapper> mResourceWrapper;
    147  };
    148 
    149  bool mIsShared = false;
    150  std::list<RecycledTextureHolder> mRecycledTextures;
    151 };
    152 
    153 /**
    154 * RemoteTextureTxnScheduler manages dependencies on transaction numbers for a
    155 * given top-level protocol ("type"). It expects that transaction numbers are
    156 * all sequenced and comparable for this top-level protocol. Dependencies may
    157 * then be issued on a given future transaction number. Clients must notify the
    158 * scheduler when transactions are completed, so that any dependencies can be
    159 * cleared as the transaction number advances. Generally, transaction numbers
    160 * will be generated by a FwdTransactionCounter on a top-level protocol child,
    161 * and there should be a RemoteTextureTxnScheduler instantiated on the top-level
    162 * protocol parent that corresponds to the same protocol lifetime as the child.
    163 * To ease sharing in sub-protocols, RemoteTextureTxnScheduler is ref-counted
    164 * and may be multiply-registered by the various sub-protocols that derive from
    165 * a given top-level protocol, without having to directly refer to the original
    166 * top-level protocol.
    167 */
    168 class RemoteTextureTxnScheduler final {
    169 public:
    170  NS_INLINE_DECL_THREADSAFE_REFCOUNTING(RemoteTextureTxnScheduler)
    171 
    172  static already_AddRefed<RemoteTextureTxnScheduler> Create(
    173      mozilla::ipc::IProtocol* aProtocol);
    174 
    175  void NotifyTxn(RemoteTextureTxnId aTxnId);
    176 
    177 private:
    178  friend class RemoteTextureMap;
    179 
    180  RemoteTextureTxnScheduler(base::ProcessId aForPid, RemoteTextureTxnType aType)
    181      : mForPid(aForPid), mType(aType) {}
    182  ~RemoteTextureTxnScheduler();
    183 
    184  bool WaitForTxn(const MonitorAutoLock& aProofOfLock,
    185                  RemoteTextureOwnerId aOwnerId, RemoteTextureTxnId aTxnId);
    186 
    187  struct Wait {
    188    RemoteTextureOwnerId mOwnerId;
    189    RemoteTextureTxnId mTxnId;
    190 
    191    friend bool operator<(RemoteTextureTxnId aTxnId, const Wait& aWait) {
    192      return aTxnId < aWait.mTxnId;
    193    }
    194  };
    195 
    196  base::ProcessId mForPid = base::kInvalidProcessId;
    197  RemoteTextureTxnType mType = 0;
    198  RemoteTextureTxnId mLastTxnId = 0;
    199  std::deque<Wait> mWaits;
    200 };
    201 
    202 typedef std::unordered_set<RemoteTextureOwnerId, RemoteTextureOwnerId::HashFn>
    203    RemoteTextureOwnerIdSet;
    204 
    205 /**
    206 * A class provides API for remote texture owners.
    207 */
    208 class RemoteTextureOwnerClient final {
    209 public:
    210  NS_INLINE_DECL_THREADSAFE_REFCOUNTING(RemoteTextureOwnerClient)
    211 
    212  explicit RemoteTextureOwnerClient(const base::ProcessId aForPid);
    213 
    214  bool IsRegistered(const RemoteTextureOwnerId aOwnerId);
    215  void RegisterTextureOwner(const RemoteTextureOwnerId aOwnerId,
    216                            bool aSharedRecycling = false);
    217  void UnregisterTextureOwner(const RemoteTextureOwnerId aOwnerId);
    218  void UnregisterAllTextureOwners();
    219  bool WaitForTxn(const RemoteTextureOwnerId aOwnerId,
    220                  RemoteTextureTxnType aTxnType, RemoteTextureTxnId aTxnId);
    221  void ClearRecycledTextures();
    222  void NotifyContextLost(const RemoteTextureOwnerIdSet* aOwnerIds = nullptr);
    223  void NotifyContextRestored(
    224      const RemoteTextureOwnerIdSet* aOwnerIds = nullptr);
    225  void PushTexture(const RemoteTextureId aTextureId,
    226                   const RemoteTextureOwnerId aOwnerId,
    227                   UniquePtr<TextureData>&& aTextureData);
    228  void PushTexture(const RemoteTextureId aTextureId,
    229                   const RemoteTextureOwnerId aOwnerId,
    230                   const std::shared_ptr<gl::SharedSurface>& aSharedSurface,
    231                   const gfx::IntSize& aSize, gfx::SurfaceFormat aFormat,
    232                   const SurfaceDescriptor& aDesc);
    233  void PushTexture(const RemoteTextureId aTextureId,
    234                   const RemoteTextureOwnerId aOwnerId,
    235                   const std::shared_ptr<webgpu::SharedTexture>& aSharedTexture,
    236                   const gfx::IntSize& aSize, gfx::SurfaceFormat aFormat,
    237                   const SurfaceDescriptor& aDesc);
    238  void PushDummyTexture(const RemoteTextureId aTextureId,
    239                        const RemoteTextureOwnerId aOwnerId);
    240  void GetLatestBufferSnapshot(const RemoteTextureOwnerId aOwnerId,
    241                               const mozilla::ipc::Shmem& aDestShmem,
    242                               const gfx::IntSize& aSize);
    243  UniquePtr<TextureData> GetRecycledTextureData(
    244      const gfx::IntSize& aSize, gfx::SurfaceFormat aFormat,
    245      TextureType aTextureType,
    246      RemoteTextureOwnerId aOwnerId = RemoteTextureOwnerId());
    247  UniquePtr<TextureData> CreateOrRecycleBufferTextureData(
    248      const gfx::IntSize& aSize, gfx::SurfaceFormat aFormat,
    249      RemoteTextureOwnerId aOwnerId = RemoteTextureOwnerId());
    250  std::shared_ptr<gl::SharedSurface> GetRecycledSharedSurface(
    251      const gfx::IntSize& aSize, gfx::SurfaceFormat aFormat,
    252      SurfaceDescriptor::Type aType,
    253      RemoteTextureOwnerId aOwnerId = RemoteTextureOwnerId());
    254  std::shared_ptr<webgpu::SharedTexture> GetRecycledSharedTexture(
    255      const gfx::IntSize& aSize, gfx::SurfaceFormat aFormat,
    256      SurfaceDescriptor::Type aType,
    257      RemoteTextureOwnerId aOwnerId = RemoteTextureOwnerId());
    258 
    259  const base::ProcessId mForPid;
    260 
    261 protected:
    262  ~RemoteTextureOwnerClient();
    263 
    264  RemoteTextureOwnerIdSet mOwnerIds;
    265  RefPtr<RemoteTextureRecycleBin> mSharedRecycleBin;
    266 };
    267 
    268 /**
    269 * A class to map RemoteTextureId to remote texture(TextureHost).
    270 * Remote textures are provided by texture owner.
    271 */
    272 class RemoteTextureMap {
    273 public:
    274  static void Init();
    275  static void Shutdown();
    276  static RemoteTextureMap* Get() { return sInstance; }
    277 
    278  RemoteTextureMap();
    279  ~RemoteTextureMap();
    280 
    281  // Push remote texture data and gl::SharedSurface from texture owner.
    282  // The texture data is used for creating TextureHost.
    283  // gl::SharedSurface is pushed only when the surface needs to be kept alive
    284  // during TextureHost usage. The texture data and the surface might be
    285  // recycled when TextureHost is destroyed.
    286  void PushTexture(const RemoteTextureId aTextureId,
    287                   const RemoteTextureOwnerId aOwnerId,
    288                   const base::ProcessId aForPid,
    289                   UniquePtr<TextureData>&& aTextureData,
    290                   RefPtr<TextureHost>& aTextureHost,
    291                   UniquePtr<SharedResourceWrapper>&& aResourceWrapper);
    292 
    293  // Remove waiting texture that will not be used.
    294  bool RemoveTexture(const RemoteTextureId aTextureId,
    295                     const RemoteTextureOwnerId aOwnerId,
    296                     const base::ProcessId aForPid);
    297 
    298  void GetLatestBufferSnapshot(const RemoteTextureOwnerId aOwnerId,
    299                               const base::ProcessId aForPid,
    300                               const mozilla::ipc::Shmem& aDestShmem,
    301                               const gfx::IntSize& aSize);
    302 
    303  void RegisterTextureOwner(
    304      const RemoteTextureOwnerId aOwnerId, const base::ProcessId aForPid,
    305      const RefPtr<RemoteTextureRecycleBin>& aRecycleBin = nullptr);
    306  void UnregisterTextureOwner(const RemoteTextureOwnerId aOwnerId,
    307                              const base::ProcessId aForPid);
    308  void UnregisterTextureOwners(const RemoteTextureOwnerIdSet& aOwnerIds,
    309                               const base::ProcessId aForPid);
    310 
    311  void ClearRecycledTextures(
    312      const RemoteTextureOwnerIdSet& aOwnerIds, const base::ProcessId aForPid,
    313      const RefPtr<RemoteTextureRecycleBin>& aRecycleBin = nullptr);
    314  void NotifyContextLost(const RemoteTextureOwnerIdSet& aOwnerIds,
    315                         const base::ProcessId aForPid);
    316  void NotifyContextRestored(const RemoteTextureOwnerIdSet& aOwnerIds,
    317                             const base::ProcessId aForPid);
    318 
    319  bool WaitForRemoteTextureOwner(RemoteTextureHostWrapper* aTextureHostWrapper);
    320 
    321  // Get remote texture's TextureHost for RemoteTextureHostWrapper.
    322  void GetRemoteTexture(RemoteTextureHostWrapper* aTextureHostWrapper);
    323 
    324  bool WaitForTxn(const RemoteTextureOwnerId aOwnerId,
    325                  const base::ProcessId aForPid, RemoteTextureTxnType aTxnType,
    326                  RemoteTextureTxnId aTxnId);
    327 
    328  void ReleaseRemoteTextureHost(RemoteTextureHostWrapper* aTextureHostWrapper);
    329 
    330  RefPtr<TextureHost> GetOrCreateRemoteTextureHostWrapper(
    331      const RemoteTextureId aTextureId, const RemoteTextureOwnerId aOwnerId,
    332      const base::ProcessId aForPid, const gfx::IntSize& aSize,
    333      const TextureFlags aFlags);
    334 
    335  void UnregisterRemoteTextureHostWrapper(const RemoteTextureId aTextureId,
    336                                          const RemoteTextureOwnerId aOwnerId,
    337                                          const base::ProcessId aForPid);
    338 
    339  bool CheckRemoteTextureReady(
    340      const RemoteTextureInfo& aInfo,
    341      std::function<void(const RemoteTextureInfo&)>&& aCallback);
    342 
    343  bool WaitRemoteTextureReady(const RemoteTextureInfo& aInfo);
    344 
    345  void SuppressRemoteTextureReadyCheck(const RemoteTextureInfo& aInfo);
    346 
    347  UniquePtr<TextureData> GetRecycledTextureData(
    348      const RemoteTextureOwnerId aOwnerId, const base::ProcessId aForPid,
    349      const RefPtr<RemoteTextureRecycleBin>& aRecycleBin,
    350      const gfx::IntSize& aSize, gfx::SurfaceFormat aFormat,
    351      TextureType aTextureType);
    352 
    353  UniquePtr<SharedResourceWrapper> GetRecycledSharedTexture(
    354      const RemoteTextureOwnerId aOwnerId, const base::ProcessId aForPid,
    355      const RefPtr<RemoteTextureRecycleBin>& aRecycleBin,
    356      const gfx::IntSize& aSize, gfx::SurfaceFormat aFormat,
    357      SurfaceDescriptor::Type aType);
    358 
    359  static RefPtr<TextureHost> CreateRemoteTexture(TextureData* aTextureData,
    360                                                 TextureFlags aTextureFlags);
    361 
    362  already_AddRefed<RemoteTextureTxnScheduler> RegisterTxnScheduler(
    363      base::ProcessId aForPid, RemoteTextureTxnType aType);
    364 
    365 protected:
    366  friend class RemoteTextureTxnScheduler;
    367 
    368  // Holds data related to remote texture
    369  struct TextureDataHolder {
    370    TextureDataHolder(const RemoteTextureId aTextureId,
    371                      RefPtr<TextureHost> aTextureHost,
    372                      UniquePtr<TextureData>&& aTextureData,
    373                      UniquePtr<SharedResourceWrapper>&& aResourceWrapper);
    374 
    375    const RemoteTextureId mTextureId;
    376    // TextureHost of remote texture
    377    // Compositable ref of the mTextureHost should be updated within mMonitor.
    378    // The compositable ref is used to check if TextureHost(remote texture) is
    379    // still in use by WebRender.
    380    RefPtr<TextureHost> mTextureHost;
    381    // Holds BufferTextureData of TextureHost
    382    UniquePtr<TextureData> mTextureData;
    383    // Holds gl::SharedSurface of TextureHost
    384    UniquePtr<SharedResourceWrapper> mResourceWrapper;
    385  };
    386 
    387  struct RenderingReadyCallbackHolder {
    388    RenderingReadyCallbackHolder(
    389        const RemoteTextureId aTextureId,
    390        std::function<void(const RemoteTextureInfo&)>&& aCallback);
    391 
    392    const RemoteTextureId mTextureId;
    393    // callback of RemoteTexture ready
    394    std::function<void(const RemoteTextureInfo&)> mCallback;
    395  };
    396 
    397  struct WaitingTextureOwner {
    398    std::deque<UniquePtr<RenderingReadyCallbackHolder>>
    399        mRenderingReadyCallbackHolders;
    400  };
    401 
    402  struct TextureOwner {
    403    bool mIsContextLost = false;
    404    // Whether to wait for a transaction to complete before unregistering.
    405    bool mWaitForTxn = false;
    406    // The thread on which to finally unregister when ready.
    407    RefPtr<nsISerialEventTarget> mDeferUnregister;
    408 
    409    // Holds TextureDataHolders that wait to be used for building wr display
    410    // list.
    411    std::deque<UniquePtr<TextureDataHolder>> mWaitingTextureDataHolders;
    412    // Holds TextureDataHolders that are used for building wr display list.
    413    std::deque<UniquePtr<TextureDataHolder>> mUsingTextureDataHolders;
    414    std::deque<UniquePtr<TextureDataHolder>> mReleasingTextureDataHolders;
    415    // Holds RemoteTexture ready callbacks.
    416    std::deque<UniquePtr<RenderingReadyCallbackHolder>>
    417        mRenderingReadyCallbackHolders;
    418 
    419    RemoteTextureId mLatestPushedTextureId = {0};
    420    RemoteTextureId mLatestUsingTextureId = {0};
    421    CompositableTextureHostRef mLatestTextureHost;
    422    CompositableTextureHostRef mLatestRenderedTextureHost;
    423    // Holds compositable refs to TextureHosts of RenderTextureHosts that are
    424    // waiting to be released in non-RenderThread.
    425    std::deque<CompositableTextureHostRef> mReleasingRenderedTextureHosts;
    426    RefPtr<RemoteTextureRecycleBin> mRecycleBin;
    427  };
    428 
    429  // Holds data related to remote texture wrapper
    430  struct RemoteTextureHostWrapperHolder {
    431    explicit RemoteTextureHostWrapperHolder(
    432        RefPtr<TextureHost> aRemoteTextureHostWrapper);
    433 
    434    const RefPtr<TextureHost> mRemoteTextureHostWrapper;
    435    // Hold compositable ref of remote texture of the RemoteTextureId.
    436    CompositableTextureHostRef mRemoteTextureHost;
    437    bool mReadyCheckSuppressed = false;
    438  };
    439 
    440  void UpdateTexture(const MonitorAutoLock& aProofOfLock,
    441                     RemoteTextureMap::TextureOwner* aOwner,
    442                     const RemoteTextureId aTextureId);
    443 
    444  UniquePtr<TextureOwner> UnregisterTextureOwner(
    445      MonitorAutoLock& aProofOfLock, const RemoteTextureOwnerId aOwnerId,
    446      const base::ProcessId aForPid,
    447      std::vector<RefPtr<TextureHost>>& aReleasingTextures,
    448      std::vector<std::function<void(const RemoteTextureInfo&)>>&
    449          aRenderingReadyCallbacks);
    450 
    451  void GetRenderingReadyCallbacks(
    452      const MonitorAutoLock& aProofOfLock,
    453      RemoteTextureMap::TextureOwner* aOwner, const RemoteTextureId aTextureId,
    454      std::vector<std::function<void(const RemoteTextureInfo&)>>& aFunctions);
    455 
    456  void GetAllRenderingReadyCallbacks(
    457      const MonitorAutoLock& aProofOfLock,
    458      RemoteTextureMap::TextureOwner* aOwner,
    459      std::vector<std::function<void(const RemoteTextureInfo&)>>& aFunctions);
    460 
    461  void KeepTextureDataAliveForTextureHostIfNecessary(
    462      const MonitorAutoLock& aProofOfLock,
    463      RemoteTextureMap::TextureOwner* aOwner,
    464      std::deque<UniquePtr<TextureDataHolder>>& aHolders);
    465 
    466  bool RecycleTexture(const RefPtr<RemoteTextureRecycleBin>& aRecycleBin,
    467                      TextureDataHolder& aHolder, bool aExpireOldTextures);
    468 
    469  RemoteTextureMap::TextureOwner* GetTextureOwner(
    470      const MonitorAutoLock& aProofOfLock, const RemoteTextureOwnerId aOwnerId,
    471      const base::ProcessId aForPid);
    472 
    473  void NotifyTxn(const MonitorAutoLock& aProofOfLock,
    474                 const RemoteTextureOwnerId aOwnerId,
    475                 const base::ProcessId aForPid);
    476 
    477  void UnregisterTxnScheduler(base::ProcessId aForPid,
    478                              RemoteTextureTxnType aType);
    479 
    480  Monitor mMonitor MOZ_UNANNOTATED;
    481 
    482  std::map<std::pair<base::ProcessId, RemoteTextureOwnerId>,
    483           UniquePtr<WaitingTextureOwner>>
    484      mWaitingTextureOwners;
    485 
    486  std::map<std::pair<base::ProcessId, RemoteTextureOwnerId>,
    487           UniquePtr<TextureOwner>>
    488      mTextureOwners;
    489 
    490  std::map<std::pair<base::ProcessId, RemoteTextureId>,
    491           UniquePtr<RemoteTextureHostWrapperHolder>>
    492      mRemoteTextureHostWrapperHolders;
    493 
    494  std::map<std::pair<base::ProcessId, RemoteTextureTxnType>,
    495           RemoteTextureTxnScheduler*>
    496      mTxnSchedulers;
    497 
    498  static StaticAutoPtr<RemoteTextureMap> sInstance;
    499 };
    500 
    501 }  // namespace layers
    502 }  // namespace mozilla
    503 
    504 #endif  // MOZILLA_GFX_RemoteTextureMap_H