Bug 1760657 - nsHttpResponseHead thread-safety annotations r=necko-reviewers,kershaw

Differential Revision: https://phabricator.services.mozilla.com/D141667
This commit is contained in:
Randell Jesup 2022-03-22 13:57:20 +00:00
Родитель 2a3a2f2c85
Коммит a7371f587e
4 изменённых файлов: 74 добавлений и 60 удалений

Просмотреть файл

@ -181,7 +181,8 @@ template <>
struct ParamTraits<mozilla::net::nsHttpRequestHead> {
typedef mozilla::net::nsHttpRequestHead paramType;
static void Write(MessageWriter* aWriter, const paramType& aParam) {
static void Write(MessageWriter* aWriter,
const paramType& aParam) NO_THREAD_SAFETY_ANALYSIS {
aParam.Enter();
WriteParam(aWriter, aParam.mHeaders);
WriteParam(aWriter, aParam.mMethod);
@ -223,7 +224,8 @@ template <>
struct ParamTraits<mozilla::net::nsHttpResponseHead> {
typedef mozilla::net::nsHttpResponseHead paramType;
static void Write(MessageWriter* aWriter, const paramType& aParam) {
static void Write(MessageWriter* aWriter,
const paramType& aParam) NO_THREAD_SAFETY_ANALYSIS {
aParam.Enter();
WriteParam(aWriter, aParam.mHeaders);
WriteParam(aWriter, static_cast<uint32_t>(aParam.mVersion));

Просмотреть файл

@ -40,11 +40,12 @@ class nsHttpRequestHead {
// copying headers. If you use it be careful to do it only under
// nsHttpRequestHead lock!!!
const nsHttpHeaderArray& Headers() const;
PUSH_IGNORE_THREAD_SAFETY
void Enter() const { mRecursiveMutex.Lock(); }
void Exit() const { mRecursiveMutex.Unlock(); }
POP_THREAD_SAFETY
void Enter() const CAPABILITY_ACQUIRE(mRecursiveMutex) {
mRecursiveMutex.Lock();
}
void Exit() const CAPABILITY_RELEASE(mRecursiveMutex) {
mRecursiveMutex.Unlock();
}
void SetHeaders(const nsHttpHeaderArray& aHeaders);
@ -122,26 +123,26 @@ class nsHttpRequestHead {
private:
// All members must be copy-constructable and assignable
nsHttpHeaderArray mHeaders;
nsCString mMethod{"GET"_ns};
HttpVersion mVersion{HttpVersion::v1_1};
nsHttpHeaderArray mHeaders GUARDED_BY(mRecursiveMutex);
nsCString mMethod GUARDED_BY(mRecursiveMutex){"GET"_ns};
HttpVersion mVersion GUARDED_BY(mRecursiveMutex){HttpVersion::v1_1};
// mRequestURI and mPath are strings instead of an nsIURI
// because this is used off the main thread
nsCString mRequestURI;
nsCString mPath;
nsCString mRequestURI GUARDED_BY(mRecursiveMutex);
nsCString mPath GUARDED_BY(mRecursiveMutex);
nsCString mOrigin;
ParsedMethodType mParsedMethod{kMethod_Get};
bool mHTTPS{false};
nsCString mOrigin GUARDED_BY(mRecursiveMutex);
ParsedMethodType mParsedMethod GUARDED_BY(mRecursiveMutex){kMethod_Get};
bool mHTTPS GUARDED_BY(mRecursiveMutex){false};
// We are using RecursiveMutex instead of a Mutex because VisitHeader
// function calls nsIHttpHeaderVisitor::VisitHeader while under lock.
mutable RecursiveMutex mRecursiveMutex MOZ_UNANNOTATED{
"nsHttpRequestHead.mRecursiveMutex"};
// During VisitHeader we sould not allow cal to SetHeader.
bool mInVisitHeaders{false};
// During VisitHeader we sould not allow call to SetHeader.
bool mInVisitHeaders GUARDED_BY(mRecursiveMutex){false};
friend struct IPC::ParamTraits<nsHttpRequestHead>;
};

Просмотреть файл

@ -1045,7 +1045,8 @@ nsresult nsHttpResponseHead::GetLastModifiedValue(uint32_t* result) {
return ParseDateHeader(nsHttp::Last_Modified, result);
}
bool nsHttpResponseHead::operator==(const nsHttpResponseHead& aOther) const {
bool nsHttpResponseHead::operator==(const nsHttpResponseHead& aOther) const
NO_THREAD_SAFETY_ANALYSIS {
nsHttpResponseHead& curr = const_cast<nsHttpResponseHead&>(*this);
nsHttpResponseHead& other = const_cast<nsHttpResponseHead&>(aOther);
RecursiveMutexAutoLock monitorOther(other.mRecursiveMutex);

Просмотреть файл

@ -43,10 +43,13 @@ class nsHttpResponseHead {
nsHttpResponseHead(const nsHttpResponseHead& aOther);
nsHttpResponseHead& operator=(const nsHttpResponseHead& aOther);
PUSH_IGNORE_THREAD_SAFETY
void Enter() const { mRecursiveMutex.Lock(); }
void Exit() const { mRecursiveMutex.Unlock(); }
POP_THREAD_SAFETY
void Enter() const CAPABILITY_ACQUIRE(mRecursiveMutex) {
mRecursiveMutex.Lock();
}
void Exit() const CAPABILITY_RELEASE(mRecursiveMutex) {
mRecursiveMutex.Unlock();
}
void AssertMutexOwned() const { mRecursiveMutex.AssertCurrentThreadIn(); }
HttpVersion Version();
uint16_t Status() const;
@ -146,41 +149,49 @@ class nsHttpResponseHead {
private:
[[nodiscard]] nsresult SetHeader_locked(const nsHttpAtom& atom,
const nsACString& h,
const nsACString& v, bool m = false);
void AssignDefaultStatusText();
void ParseVersion(const char*);
void ParseCacheControl(const char*);
void ParsePragma(const char*);
const nsACString& v, bool m = false)
REQUIRES(mRecursiveMutex);
void AssignDefaultStatusText() REQUIRES(mRecursiveMutex);
void ParseVersion(const char*) REQUIRES(mRecursiveMutex);
void ParseCacheControl(const char*) REQUIRES(mRecursiveMutex);
void ParsePragma(const char*) REQUIRES(mRecursiveMutex);
void ParseStatusLine_locked(const nsACString& line);
void ParseStatusLine_locked(const nsACString& line) REQUIRES(mRecursiveMutex);
[[nodiscard]] nsresult ParseHeaderLine_locked(const nsACString& line,
bool originalFromNetHeaders);
bool originalFromNetHeaders)
REQUIRES(mRecursiveMutex);
// these return failure if the header does not exist.
[[nodiscard]] nsresult ParseDateHeader(const nsHttpAtom& header,
uint32_t* result) const;
uint32_t* result) const
REQUIRES(mRecursiveMutex);
[[nodiscard]] nsresult GetAgeValue(uint32_t* result);
[[nodiscard]] nsresult GetMaxAgeValue(uint32_t* result);
[[nodiscard]] nsresult GetStaleWhileRevalidateValue(uint32_t* result);
[[nodiscard]] nsresult GetDateValue(uint32_t* result);
[[nodiscard]] nsresult GetExpiresValue(uint32_t* result);
bool ExpiresInPast_locked() const;
[[nodiscard]] nsresult GetAgeValue_locked(uint32_t* result) const;
[[nodiscard]] nsresult GetExpiresValue_locked(uint32_t* result) const;
[[nodiscard]] nsresult GetMaxAgeValue_locked(uint32_t* result) const;
bool ExpiresInPast_locked() const REQUIRES(mRecursiveMutex);
[[nodiscard]] nsresult GetAgeValue_locked(uint32_t* result) const
REQUIRES(mRecursiveMutex);
[[nodiscard]] nsresult GetExpiresValue_locked(uint32_t* result) const
REQUIRES(mRecursiveMutex);
[[nodiscard]] nsresult GetMaxAgeValue_locked(uint32_t* result) const
REQUIRES(mRecursiveMutex);
[[nodiscard]] nsresult GetStaleWhileRevalidateValue_locked(
uint32_t* result) const;
uint32_t* result) const REQUIRES(mRecursiveMutex);
[[nodiscard]] nsresult GetDateValue_locked(uint32_t* result) const {
[[nodiscard]] nsresult GetDateValue_locked(uint32_t* result) const
REQUIRES(mRecursiveMutex) {
return ParseDateHeader(nsHttp::Date, result);
}
[[nodiscard]] nsresult GetLastModifiedValue_locked(uint32_t* result) const {
[[nodiscard]] nsresult GetLastModifiedValue_locked(uint32_t* result) const
REQUIRES(mRecursiveMutex) {
return ParseDateHeader(nsHttp::Last_Modified, result);
}
bool NoCache_locked() const {
bool NoCache_locked() const REQUIRES(mRecursiveMutex) {
// We ignore Pragma: no-cache if Cache-Control is set.
MOZ_ASSERT_IF(mCacheControlNoCache, mHasCacheControl);
return mHasCacheControl ? mCacheControlNoCache : mPragmaNoCache;
@ -188,31 +199,30 @@ class nsHttpResponseHead {
private:
// All members must be copy-constructable and assignable
nsHttpHeaderArray mHeaders;
HttpVersion mVersion{HttpVersion::v1_1};
uint16_t mStatus{200};
nsCString mStatusText;
int64_t mContentLength{-1};
nsCString mContentType;
nsCString mContentCharset;
bool mHasCacheControl{false};
bool mCacheControlPublic{false};
bool mCacheControlPrivate{false};
bool mCacheControlNoStore{false};
bool mCacheControlNoCache{false};
bool mCacheControlImmutable{false};
bool mCacheControlStaleWhileRevalidateSet{false};
uint32_t mCacheControlStaleWhileRevalidate{0};
bool mCacheControlMaxAgeSet{false};
uint32_t mCacheControlMaxAge{0};
bool mPragmaNoCache{false};
nsHttpHeaderArray mHeaders GUARDED_BY(mRecursiveMutex);
HttpVersion mVersion GUARDED_BY(mRecursiveMutex){HttpVersion::v1_1};
uint16_t mStatus GUARDED_BY(mRecursiveMutex){200};
nsCString mStatusText GUARDED_BY(mRecursiveMutex);
int64_t mContentLength GUARDED_BY(mRecursiveMutex){-1};
nsCString mContentType GUARDED_BY(mRecursiveMutex);
nsCString mContentCharset GUARDED_BY(mRecursiveMutex);
bool mHasCacheControl GUARDED_BY(mRecursiveMutex){false};
bool mCacheControlPublic GUARDED_BY(mRecursiveMutex){false};
bool mCacheControlPrivate GUARDED_BY(mRecursiveMutex){false};
bool mCacheControlNoStore GUARDED_BY(mRecursiveMutex){false};
bool mCacheControlNoCache GUARDED_BY(mRecursiveMutex){false};
bool mCacheControlImmutable GUARDED_BY(mRecursiveMutex){false};
bool mCacheControlStaleWhileRevalidateSet GUARDED_BY(mRecursiveMutex){false};
uint32_t mCacheControlStaleWhileRevalidate GUARDED_BY(mRecursiveMutex){0};
bool mCacheControlMaxAgeSet GUARDED_BY(mRecursiveMutex){false};
uint32_t mCacheControlMaxAge GUARDED_BY(mRecursiveMutex){0};
bool mPragmaNoCache GUARDED_BY(mRecursiveMutex){false};
// We are using RecursiveMutex instead of a Mutex because VisitHeader
// function calls nsIHttpHeaderVisitor::VisitHeader while under lock.
mutable RecursiveMutex mRecursiveMutex MOZ_UNANNOTATED{
"nsHttpResponseHead.mRecursiveMutex"};
// During VisitHeader we sould not allow cal to SetHeader.
bool mInVisitHeaders{false};
mutable RecursiveMutex mRecursiveMutex{"nsHttpResponseHead.mRecursiveMutex"};
// During VisitHeader we sould not allow call to SetHeader.
bool mInVisitHeaders GUARDED_BY(mRecursiveMutex){false};
friend struct IPC::ParamTraits<nsHttpResponseHead>;
};