1 // Copyright 2017 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 
7 #include "core/fpdfapi/page/cpdf_expintfunc.h"
8 
9 #include "core/fpdfapi/parser/cpdf_array.h"
10 #include "core/fpdfapi/parser/cpdf_dictionary.h"
11 #include "core/fxcrt/fx_memory.h"
12 
CPDF_ExpIntFunc()13 CPDF_ExpIntFunc::CPDF_ExpIntFunc()
14     : CPDF_Function(Type::kType2ExpotentialInterpolation),
15       m_pBeginValues(nullptr),
16       m_pEndValues(nullptr) {}
17 
~CPDF_ExpIntFunc()18 CPDF_ExpIntFunc::~CPDF_ExpIntFunc() {
19   FX_Free(m_pBeginValues);
20   FX_Free(m_pEndValues);
21 }
22 
v_Init(CPDF_Object * pObj)23 bool CPDF_ExpIntFunc::v_Init(CPDF_Object* pObj) {
24   CPDF_Dictionary* pDict = pObj->GetDict();
25   if (!pDict)
26     return false;
27 
28   CPDF_Array* pArray0 = pDict->GetArrayFor("C0");
29   if (m_nOutputs == 0) {
30     m_nOutputs = 1;
31     if (pArray0)
32       m_nOutputs = pArray0->GetCount();
33   }
34 
35   CPDF_Array* pArray1 = pDict->GetArrayFor("C1");
36   m_pBeginValues = FX_Alloc2D(float, m_nOutputs, 2);
37   m_pEndValues = FX_Alloc2D(float, m_nOutputs, 2);
38   for (uint32_t i = 0; i < m_nOutputs; i++) {
39     m_pBeginValues[i] = pArray0 ? pArray0->GetFloatAt(i) : 0.0f;
40     m_pEndValues[i] = pArray1 ? pArray1->GetFloatAt(i) : 1.0f;
41   }
42 
43   m_Exponent = pDict->GetFloatFor("N");
44   m_nOrigOutputs = m_nOutputs;
45   if (m_nOutputs && m_nInputs > INT_MAX / m_nOutputs)
46     return false;
47 
48   m_nOutputs *= m_nInputs;
49   return true;
50 }
51 
v_Call(float * inputs,float * results) const52 bool CPDF_ExpIntFunc::v_Call(float* inputs, float* results) const {
53   for (uint32_t i = 0; i < m_nInputs; i++)
54     for (uint32_t j = 0; j < m_nOrigOutputs; j++) {
55       results[i * m_nOrigOutputs + j] =
56           m_pBeginValues[j] + FXSYS_pow(inputs[i], m_Exponent) *
57                                   (m_pEndValues[j] - m_pBeginValues[j]);
58     }
59   return true;
60 }
61