// Copyright 2021 The Fuchsia Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#ifndef SRC_STORAGE_F2FS_F2FS_LIB_H_
#define SRC_STORAGE_F2FS_F2FS_LIB_H_

namespace f2fs {

// Checkpoint
inline bool VerAfter(uint64_t a, uint64_t b) { return a > b; }

// CRC
inline uint32_t F2fsCalCrc32(uint32_t crc, void *buff, uint32_t len) {
  unsigned char *p = static_cast<unsigned char *>(buff);
  while (len-- > 0) {
    crc ^= *p++;
    for (int i = 0; i < 8; ++i)
      crc = (crc >> 1) ^ ((crc & 1) ? kCrcPolyLe : 0);
  }
  return crc;
}

inline uint32_t F2fsCrc32(void *buff, uint32_t len) {
  return F2fsCalCrc32(kF2fsSuperMagic, (unsigned char *)buff, len);
}

inline bool F2fsCrcValid(uint32_t blk_crc, void *buff, uint32_t buff_size) {
  return F2fsCrc32(buff, buff_size) == blk_crc;
}

// Bitmap operations
inline size_t DivRoundUp(size_t n, size_t d) { return (((n) + (d)-1) / (d)); }
inline size_t BitsToLongs(size_t nr) { return DivRoundUp(nr, kBitsPerByte * sizeof(long)); }

inline void SetBit(uint32_t nr, void *addr) {
  uint8_t *bitmap = static_cast<uint8_t *>(addr);
  uint32_t size_per_iter = kBitsPerByte;

  uint32_t iter = nr / size_per_iter;
  uint32_t offset_in_iter = nr % size_per_iter;

  bitmap[iter] |= static_cast<uint8_t>(1U << offset_in_iter);
}

inline void ClearBit(uint32_t nr, void *addr) {
  uint8_t *bitmap = static_cast<uint8_t *>(addr);
  uint32_t size_per_iter = kBitsPerByte;

  uint32_t iter = nr / size_per_iter;
  uint32_t offset_in_iter = nr % size_per_iter;

  bitmap[iter] &= ~static_cast<uint8_t>(1U << offset_in_iter);
}

inline bool TestBit(uint32_t nr, const void *addr) {
  const uint8_t *bitmap = static_cast<const uint8_t *>(addr);
  uint32_t size_per_iter = kBitsPerByte;

  uint32_t iter = nr / size_per_iter;
  uint32_t offset_in_iter = nr % size_per_iter;

  bool ret = ((bitmap[iter] & static_cast<uint8_t>(1U << offset_in_iter)) != 0);

  return ret;
}

inline uint32_t FindNextZeroBit(const void *addr, uint32_t size, uint32_t offset) {
  const uint8_t *bitmap = static_cast<const uint8_t *>(addr);
  uint32_t size_per_iter = kBitsPerByte;

  while (offset < size) {
    uint32_t iter = offset / size_per_iter;
    uint32_t offset_in_iter = offset % size_per_iter;

    uint8_t mask = static_cast<uint8_t>(~0U << offset_in_iter);
    uint8_t res = bitmap[iter] & mask;
    if (res != mask) {  // found
      for (; offset_in_iter < size_per_iter; ++offset_in_iter) {
        if ((bitmap[iter] & static_cast<uint8_t>(1U << offset_in_iter)) == 0) {
          return std::min(iter * size_per_iter + offset_in_iter, size);
        }
      }
    }

    offset = (iter + 1) * size_per_iter;
  }

  return size;
}

inline uint32_t FindNextBit(const void *addr, uint32_t size, uint32_t offset) {
  const uint8_t *bitmap = static_cast<const uint8_t *>(addr);
  uint32_t size_per_iter = kBitsPerByte;

  while (offset < size) {
    uint32_t iter = offset / size_per_iter;
    uint32_t offset_in_iter = offset % size_per_iter;

    uint8_t mask = static_cast<uint8_t>(~0U << offset_in_iter);
    uint8_t res = bitmap[iter] & mask;
    if (res != 0) {  // found
      for (; offset_in_iter < size_per_iter; ++offset_in_iter) {
        if ((bitmap[iter] & static_cast<uint8_t>(1U << offset_in_iter)) != 0) {
          return std::min(iter * size_per_iter + offset_in_iter, size);
        }
      }
    }

    offset = (iter + 1) * size_per_iter;
  }

  return size;
}

inline bool TestAndSetBit(uint32_t nr, void *addr) {
  uint8_t *bitmap = static_cast<uint8_t *>(addr);
  uint32_t size_per_iter = kBitsPerByte;
  uint32_t iter = nr / size_per_iter;
  uint32_t offset_in_iter = nr % size_per_iter;

  bool ret = ((bitmap[iter] & static_cast<uint8_t>(1U << offset_in_iter)) != 0);

  bitmap[iter] |= static_cast<uint8_t>(1U << offset_in_iter);

  return ret;
}

inline bool TestAndClearBit(uint32_t nr, void *addr) {
  uint8_t *bitmap = static_cast<uint8_t *>(addr);
  uint32_t size_per_iter = kBitsPerByte;

  uint32_t iter = nr / size_per_iter;
  uint32_t offset_in_iter = nr % size_per_iter;

  bool ret = ((bitmap[iter] & static_cast<uint8_t>(1U << offset_in_iter)) != 0);

  bitmap[iter] &= ~static_cast<uint8_t>((1U << offset_in_iter));

  return ret;
}

inline void list_add(list_node_t *list, list_node_t *item) {
  list->next->prev = item;
  item->next = list->next;
  item->prev = list;
  list->next = item;
}

inline bool IsDotOrDotDot(std::string_view name) { return (name == "." || name == ".."); }

}  // namespace f2fs

#endif  // SRC_STORAGE_F2FS_F2FS_LIB_H_
