1// Copyright 2014 PDFium Authors. All rights reserved. 2// Use of this source code is governed by a BSD-style license that can be 3// found in the LICENSE file. 4 5// Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com 6// Original code is licensed as follows: 7/* 8 * Copyright 2007 ZXing authors 9 * 10 * Licensed under the Apache License, Version 2.0 (the "License"); 11 * you may not use this file except in compliance with the License. 12 * You may obtain a copy of the License at 13 * 14 * http://www.apache.org/licenses/LICENSE-2.0 15 * 16 * Unless required by applicable law or agreed to in writing, software 17 * distributed under the License is distributed on an "AS IS" BASIS, 18 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 19 * See the License for the specific language governing permissions and 20 * limitations under the License. 21 */ 22 23#include "xfa/src/fxbarcode/barcode.h" 24#include "BC_ReedSolomonGF256.h" 25#include "BC_ReedSolomonGF256Poly.h" 26#include "BC_ReedSolomon.h" 27CBC_ReedSolomonEncoder::CBC_ReedSolomonEncoder(CBC_ReedSolomonGF256* field) { 28 m_field = field; 29} 30void CBC_ReedSolomonEncoder::Init() { 31 m_cachedGenerators.Add(new CBC_ReedSolomonGF256Poly(m_field, 1)); 32} 33CBC_ReedSolomonGF256Poly* CBC_ReedSolomonEncoder::BuildGenerator(int32_t degree, 34 int32_t& e) { 35 if (degree >= m_cachedGenerators.GetSize()) { 36 CBC_ReedSolomonGF256Poly* lastGenerator = 37 (CBC_ReedSolomonGF256Poly*)(m_cachedGenerators 38 [m_cachedGenerators.GetSize() - 1]); 39 for (int32_t d = m_cachedGenerators.GetSize(); d <= degree; d++) { 40 CFX_Int32Array temp; 41 temp.Add(1); 42 temp.Add(m_field->Exp(d - 1)); 43 CBC_ReedSolomonGF256Poly temp_poly; 44 temp_poly.Init(m_field, &temp, e); 45 BC_EXCEPTION_CHECK_ReturnValue(e, NULL); 46 CBC_ReedSolomonGF256Poly* nextGenerator = 47 lastGenerator->Multiply(&temp_poly, e); 48 BC_EXCEPTION_CHECK_ReturnValue(e, NULL); 49 m_cachedGenerators.Add(nextGenerator); 50 lastGenerator = nextGenerator; 51 } 52 } 53 return (CBC_ReedSolomonGF256Poly*)(m_cachedGenerators[degree]); 54} 55void CBC_ReedSolomonEncoder::Encode(CFX_Int32Array* toEncode, 56 int32_t ecBytes, 57 int32_t& e) { 58 if (ecBytes == 0) { 59 e = BCExceptionNoCorrectionBytes; 60 BC_EXCEPTION_CHECK_ReturnVoid(e); 61 } 62 int32_t dataBytes = toEncode->GetSize() - ecBytes; 63 if (dataBytes <= 0) { 64 e = BCExceptionNoDataBytesProvided; 65 BC_EXCEPTION_CHECK_ReturnVoid(e); 66 } 67 CBC_ReedSolomonGF256Poly* generator = BuildGenerator(ecBytes, e); 68 BC_EXCEPTION_CHECK_ReturnVoid(e); 69 CFX_Int32Array infoCoefficients; 70 infoCoefficients.SetSize(dataBytes); 71 for (int32_t x = 0; x < dataBytes; x++) { 72 infoCoefficients[x] = toEncode->operator[](x); 73 } 74 CBC_ReedSolomonGF256Poly info; 75 info.Init(m_field, &infoCoefficients, e); 76 BC_EXCEPTION_CHECK_ReturnVoid(e); 77 CBC_ReedSolomonGF256Poly* rsg = info.MultiplyByMonomial(ecBytes, 1, e); 78 BC_EXCEPTION_CHECK_ReturnVoid(e); 79 CBC_AutoPtr<CBC_ReedSolomonGF256Poly> infoTemp(rsg); 80 CFX_PtrArray* pa = infoTemp->Divide(generator, e); 81 BC_EXCEPTION_CHECK_ReturnVoid(e); 82 CBC_AutoPtr<CFX_PtrArray> temp(pa); 83 CBC_ReedSolomonGF256Poly* remainder = 84 (CBC_ReedSolomonGF256Poly*)(temp->operator[](1)); 85 CFX_Int32Array* coefficients = remainder->GetCoefficients(); 86 int32_t numZeroCoefficients = ecBytes - coefficients->GetSize(); 87 for (int32_t i = 0; i < numZeroCoefficients; i++) { 88 (*toEncode)[dataBytes + i] = 0; 89 } 90 for (int32_t y = 0; y < coefficients->GetSize(); y++) { 91 (*toEncode)[dataBytes + numZeroCoefficients + y] = 92 coefficients->operator[](y); 93 } 94 for (int32_t k = 0; k < temp->GetSize(); k++) { 95 delete (CBC_ReedSolomonGF256Poly*)(*temp)[k]; 96 } 97} 98CBC_ReedSolomonEncoder::~CBC_ReedSolomonEncoder() { 99 for (int32_t i = 0; i < m_cachedGenerators.GetSize(); i++) { 100 delete (CBC_ReedSolomonGF256Poly*)m_cachedGenerators[i]; 101 } 102} 103