/**
 *
 * Licensed to the Apache Software Foundation (ASF) under one or more
 * contributor license agreements.  See the NOTICE file distributed with
 * this work for additional information regarding copyright ownership.
 * The ASF licenses this file to You 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.
 */
#include "io/Serializable.h"
#include <arpa/inet.h>
#include <cstdio>
#include <iostream>
#include <vector>
#include <string>
#include <algorithm>
#include "io/DataStream.h"
namespace org {
namespace apache {
namespace nifi {
namespace minifi {
namespace io {

#define htonll_r(x) ((((uint64_t)htonl(x)) << 32) + htonl((x) >> 32))
#define IS_ASCII(c) __builtin_expect(!!((c >= 1) && (c <= 127)), 1)

template<typename T>
int Serializable::writeData(const T &t, DataStream *stream) {
  uint8_t bytes[sizeof t];
  std::copy(static_cast<const char*>(static_cast<const void*>(&t)), static_cast<const char*>(static_cast<const void*>(&t)) + sizeof t, bytes);
  return stream->writeData(bytes, sizeof t);
}

template<typename T>
int Serializable::writeData(const T &t, uint8_t *to_vec) {
  std::copy(static_cast<const char*>(static_cast<const void*>(&t)), static_cast<const char*>(static_cast<const void*>(&t)) + sizeof t, to_vec);
  return sizeof t;
}

template<typename T>
int Serializable::writeData(const T &t, std::vector<uint8_t> &to_vec) {
  uint8_t bytes[sizeof t];
  std::copy(static_cast<const char*>(static_cast<const void*>(&t)), static_cast<const char*>(static_cast<const void*>(&t)) + sizeof t, bytes);
  to_vec.insert(to_vec.end(), &bytes[0], &bytes[sizeof t]);
  return sizeof t;
}

int Serializable::write(uint8_t value, DataStream *stream) {
  return stream->writeData(&value, 1);
}
int Serializable::write(char value, DataStream *stream) {
  return stream->writeData(reinterpret_cast<uint8_t *>(&value), 1);
}

int Serializable::write(uint8_t *value, int len, DataStream *stream) {
  return stream->writeData(value, len);
}

int Serializable::write(bool value, DataStream *stream) {
  uint8_t temp = value;
  return stream->writeData(&temp, 1);
}

int Serializable::read(uint8_t &value, DataStream *stream) {
  uint8_t buf;

  int ret = stream->readData(&buf, 1);
  if (ret == 1)
    value = buf;
  return ret;
}

int Serializable::read(char &value, DataStream *stream) {
  uint8_t buf;

  int ret = stream->readData(&buf, 1);
  if (ret == 1)
    value = buf;
  return ret;
}

int Serializable::read(uint8_t *value, int len, DataStream *stream) {
  return stream->readData(value, len);
}

int Serializable::read(uint16_t &value, DataStream *stream, bool is_little_endian) {
  return stream->read(value, is_little_endian);
}

int Serializable::read(uint32_t &value, DataStream *stream, bool is_little_endian) {
  return stream->read(value, is_little_endian);
}
int Serializable::read(uint64_t &value, DataStream *stream, bool is_little_endian) {
  return stream->read(value, is_little_endian);
}

int Serializable::write(uint32_t base_value, DataStream *stream, bool is_little_endian) {
  const uint32_t value = is_little_endian ? htonl(base_value) : base_value;

  return writeData(value, stream);
}

int Serializable::write(uint64_t base_value, DataStream *stream, bool is_little_endian) {
  const uint64_t value = is_little_endian == 1 ? htonll_r(base_value) : base_value;
  return writeData(value, stream);
}

int Serializable::write(uint16_t base_value, DataStream *stream, bool is_little_endian) {
  const uint16_t value = is_little_endian == 1 ? htons(base_value) : base_value;

  return writeData(value, stream);
}

int Serializable::readUTF(std::string &str, DataStream *stream, bool widen) {
  uint32_t utflen = 0;
  int ret = 1;
  if (!widen) {
    uint16_t shortLength = 0;
    ret = read(shortLength, stream);
    utflen = shortLength;
    if (ret <= 0)
      return ret;
  } else {
    uint32_t len;
    ret = read(len, stream);
    if (ret <= 0)
      return ret;
    utflen = len;
  }

  if (utflen == 0) {
    str = "";
    return 1;
  }

  std::vector<uint8_t> buf;
  ret = stream->readData(buf, utflen);

  // The number of chars produced may be less than utflen
  str = std::string((const char*) &buf[0], utflen);
  return utflen;
}

int Serializable::writeUTF(std::string str, DataStream *stream, bool widen) {
  uint32_t utflen = 0;

  utflen = str.length();

  if (utflen > 65535)
    return -1;

  if (utflen == 0) {
    if (!widen) {
      uint16_t shortLen = utflen;
      write(shortLen, stream);
    } else {
      write(utflen, stream);
    }
    return 1;
  }

  std::vector<uint8_t> utf_to_write;
  if (!widen) {
    utf_to_write.resize(utflen);
  } else {
    utf_to_write.resize(utflen);
  }

  uint8_t *underlyingPtr = &utf_to_write[0];
  for (auto c : str) {
    writeData(c, underlyingPtr++);
  }
  int ret;

  if (!widen) {
    uint16_t short_length = utflen;
    write(short_length, stream);
    ret = stream->writeData(utf_to_write.data(), utflen);
  } else {
    write(utflen, stream);
    ret = stream->writeData(utf_to_write.data(), utflen);
  }
  return ret;
}

} /* namespace io */
} /* namespace minifi */
} /* namespace nifi */
} /* namespace apache */
} /* namespace org */
