nsAsyncRedirectVerifyHelper.h 3.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130
  1. /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
  2. /* This Source Code Form is subject to the terms of the Mozilla Public
  3. * License, v. 2.0. If a copy of the MPL was not distributed with this
  4. * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
  5. #ifndef nsAsyncRedirectVerifyHelper_h
  6. #define nsAsyncRedirectVerifyHelper_h
  7. #include "nsIRunnable.h"
  8. #include "nsIThread.h"
  9. #include "nsIChannelEventSink.h"
  10. #include "nsIInterfaceRequestor.h"
  11. #include "nsIAsyncVerifyRedirectCallback.h"
  12. #include "nsCOMPtr.h"
  13. #include "nsAutoPtr.h"
  14. #include "nsCycleCollectionParticipant.h"
  15. #include "mozilla/Attributes.h"
  16. class nsIChannel;
  17. namespace mozilla {
  18. namespace net {
  19. /**
  20. * This class simplifies call of OnChannelRedirect of IOService and
  21. * the sink bound with the channel being redirected while the result of
  22. * redirect decision is returned through the callback.
  23. */
  24. class nsAsyncRedirectVerifyHelper final : public nsIRunnable,
  25. public nsIAsyncVerifyRedirectCallback
  26. {
  27. NS_DECL_THREADSAFE_ISUPPORTS
  28. NS_DECL_NSIRUNNABLE
  29. NS_DECL_NSIASYNCVERIFYREDIRECTCALLBACK
  30. public:
  31. nsAsyncRedirectVerifyHelper();
  32. /*
  33. * Calls AsyncOnChannelRedirect() on the given sink with the given
  34. * channels and flags. Keeps track of number of async callbacks to expect.
  35. */
  36. nsresult DelegateOnChannelRedirect(nsIChannelEventSink *sink,
  37. nsIChannel *oldChannel,
  38. nsIChannel *newChannel,
  39. uint32_t flags);
  40. /**
  41. * Initialize and run the chain of AsyncOnChannelRedirect calls. OldChannel
  42. * is QI'ed for nsIAsyncVerifyRedirectCallback. The result of the redirect
  43. * decision is passed through this interface back to the oldChannel.
  44. *
  45. * @param oldChan
  46. * channel being redirected, MUST implement
  47. * nsIAsyncVerifyRedirectCallback
  48. * @param newChan
  49. * target of the redirect channel
  50. * @param flags
  51. * redirect flags
  52. * @param synchronize
  53. * set to TRUE if you want the Init method wait synchronously for
  54. * all redirect callbacks
  55. */
  56. nsresult Init(nsIChannel* oldChan,
  57. nsIChannel* newChan,
  58. uint32_t flags,
  59. bool synchronize = false);
  60. protected:
  61. nsCOMPtr<nsIChannel> mOldChan;
  62. nsCOMPtr<nsIChannel> mNewChan;
  63. uint32_t mFlags;
  64. bool mWaitingForRedirectCallback;
  65. nsCOMPtr<nsIThread> mCallbackThread;
  66. bool mCallbackInitiated;
  67. int32_t mExpectedCallbacks;
  68. nsresult mResult; // value passed to callback
  69. void InitCallback();
  70. /**
  71. * Calls back to |oldChan| as described in Init()
  72. */
  73. void ExplicitCallback(nsresult result);
  74. private:
  75. ~nsAsyncRedirectVerifyHelper();
  76. bool IsOldChannelCanceled();
  77. };
  78. /*
  79. * Helper to make the call-stack handle some control-flow for us
  80. */
  81. class nsAsyncRedirectAutoCallback
  82. {
  83. public:
  84. explicit nsAsyncRedirectAutoCallback(nsIAsyncVerifyRedirectCallback* aCallback)
  85. : mCallback(aCallback)
  86. {
  87. mResult = NS_OK;
  88. }
  89. ~nsAsyncRedirectAutoCallback()
  90. {
  91. if (mCallback)
  92. mCallback->OnRedirectVerifyCallback(mResult);
  93. }
  94. /*
  95. * Call this is you want it to call back with a different result-code
  96. */
  97. void SetResult(nsresult aRes)
  98. {
  99. mResult = aRes;
  100. }
  101. /*
  102. * Call this is you want to avoid the callback
  103. */
  104. void DontCallback()
  105. {
  106. mCallback = nullptr;
  107. }
  108. private:
  109. nsIAsyncVerifyRedirectCallback* mCallback;
  110. nsresult mResult;
  111. };
  112. } // namespace net
  113. } // namespace mozilla
  114. #endif