// Copyright 2021 The Dawn Authors
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#ifndef DAWNWIRE_CLIENT_REQUESTTRACKER_H_
#define DAWNWIRE_CLIENT_REQUESTTRACKER_H_

#include "common/Assert.h"
#include "common/NonCopyable.h"

#include <cstdint>
#include <map>

namespace dawn_wire::client {

    class Device;
    class MemoryTransferService;

    template <typename Request>
    class RequestTracker : NonCopyable {
      public:
        ~RequestTracker() {
            ASSERT(mRequests.empty());
        }

        uint64_t Add(Request&& request) {
            mSerial++;
            mRequests.emplace(mSerial, request);
            return mSerial;
        }

        bool Acquire(uint64_t serial, Request* request) {
            auto it = mRequests.find(serial);
            if (it == mRequests.end()) {
                return false;
            }
            *request = std::move(it->second);
            mRequests.erase(it);
            return true;
        }

        template <typename CloseFunc>
        void CloseAll(CloseFunc&& closeFunc) {
            // Call closeFunc on all requests while handling reentrancy where the callback of some
            // requests may add some additional requests. We guarantee all callbacks for requests
            // are called exactly onces, so keep closing new requests if the first batch added more.
            // It is fine to loop infinitely here if that's what the application makes use do.
            while (!mRequests.empty()) {
                // Move mRequests to a local variable so that further reentrant modifications of
                // mRequests don't invalidate the iterators.
                auto allRequests = std::move(mRequests);
                for (auto& [_, request] : allRequests) {
                    closeFunc(&request);
                }
            }
        }

        template <typename F>
        void ForAll(F&& f) {
            for (auto& [_, request] : mRequests) {
                f(&request);
            }
        }

      private:
        uint64_t mSerial;
        std::map<uint64_t, Request> mRequests;
    };

}  // namespace dawn_wire::client

#endif  // DAWNWIRE_CLIENT_REQUESTTRACKER_H_
