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

// Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com
// Original code is licensed as follows:
/*
 * Copyright 2007 ZXing 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.
 */

#include "xfa/fxbarcode/common/reedsolomon/BC_ReedSolomonGF256.h"

#include "third_party/base/ptr_util.h"
#include "xfa/fxbarcode/common/reedsolomon/BC_ReedSolomonGF256Poly.h"

CBC_ReedSolomonGF256* CBC_ReedSolomonGF256::QRCodeField = nullptr;
CBC_ReedSolomonGF256* CBC_ReedSolomonGF256::DataMatrixField = nullptr;

void CBC_ReedSolomonGF256::Initialize() {
  QRCodeField = new CBC_ReedSolomonGF256(0x011D);
  QRCodeField->Init();
  DataMatrixField = new CBC_ReedSolomonGF256(0x012D);
  DataMatrixField->Init();
}

void CBC_ReedSolomonGF256::Finalize() {
  delete QRCodeField;
  QRCodeField = nullptr;
  delete DataMatrixField;
  DataMatrixField = nullptr;
}

CBC_ReedSolomonGF256::CBC_ReedSolomonGF256(int32_t primitive) {
  int32_t x = 1;
  for (int32_t j = 0; j < 256; j++) {
    m_expTable[j] = x;
    x <<= 1;
    if (x >= 0x100) {
      x ^= primitive;
    }
  }
  for (int32_t i = 0; i < 255; i++) {
    m_logTable[m_expTable[i]] = i;
  }
  m_logTable[0] = 0;
}

void CBC_ReedSolomonGF256::Init() {
  m_zero = pdfium::MakeUnique<CBC_ReedSolomonGF256Poly>(this, 0);
  m_one = pdfium::MakeUnique<CBC_ReedSolomonGF256Poly>(this, 1);
}

CBC_ReedSolomonGF256::~CBC_ReedSolomonGF256() {}

CBC_ReedSolomonGF256Poly* CBC_ReedSolomonGF256::GetZero() const {
  return m_zero.get();
}

CBC_ReedSolomonGF256Poly* CBC_ReedSolomonGF256::GetOne() const {
  return m_one.get();
}

CBC_ReedSolomonGF256Poly* CBC_ReedSolomonGF256::BuildMonomial(
    int32_t degree,
    int32_t coefficient,
    int32_t& e) {
  if (degree < 0) {
    e = BCExceptionDegreeIsNegative;
    BC_EXCEPTION_CHECK_ReturnValue(e, nullptr);
  }
  if (coefficient == 0) {
    CBC_ReedSolomonGF256Poly* temp = m_zero->Clone(e);
    BC_EXCEPTION_CHECK_ReturnValue(e, nullptr);
    return temp;
  }
  CFX_ArrayTemplate<int32_t> coefficients;
  coefficients.SetSize(degree + 1);
  coefficients[0] = coefficient;
  CBC_ReedSolomonGF256Poly* temp = new CBC_ReedSolomonGF256Poly();
  temp->Init(this, &coefficients, e);
  BC_EXCEPTION_CHECK_ReturnValue(e, nullptr);
  return temp;
}

int32_t CBC_ReedSolomonGF256::AddOrSubtract(int32_t a, int32_t b) {
  return a ^ b;
}

int32_t CBC_ReedSolomonGF256::Exp(int32_t a) {
  return m_expTable[a];
}

int32_t CBC_ReedSolomonGF256::Log(int32_t a, int32_t& e) {
  if (a == 0) {
    e = BCExceptionAIsZero;
    BC_EXCEPTION_CHECK_ReturnValue(e, 0);
  }
  return m_logTable[a];
}

int32_t CBC_ReedSolomonGF256::Inverse(int32_t a, int32_t& e) {
  if (a == 0) {
    e = BCExceptionAIsZero;
    BC_EXCEPTION_CHECK_ReturnValue(e, 0);
  }
  return m_expTable[255 - m_logTable[a]];
}

int32_t CBC_ReedSolomonGF256::Multiply(int32_t a, int32_t b) {
  if (a == 0 || b == 0) {
    return 0;
  }
  if (a == 1) {
    return b;
  }
  if (b == 1) {
    return a;
  }
  return m_expTable[(m_logTable[a] + m_logTable[b]) % 255];
}
