1//===- TernaryOp.cpp ------------------------------------------------------===//
2//
3//                     The MCLinker Project
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9#include "mcld/Script/TernaryOp.h"
10
11#include "mcld/ADT/SizeTraits.h"
12#include "mcld/Script/Operand.h"
13
14namespace mcld {
15
16//===----------------------------------------------------------------------===//
17// TernaryOp
18//===----------------------------------------------------------------------===//
19template <>
20IntOperand* TernaryOp<Operator::TERNARY_IF>::eval(
21    const Module& pModule,
22    const TargetLDBackend& pBackend) {
23  IntOperand* res = result();
24  if (m_pOperand[0]->value())
25    res->setValue(m_pOperand[1]->value());
26  else
27    res->setValue(m_pOperand[2]->value());
28  return res;
29}
30
31/* DATA_SEGMENT_ALIGN(maxpagesize, commonpagesize) */
32template <>
33IntOperand* TernaryOp<Operator::DATA_SEGMENT_ALIGN>::eval(
34    const Module& pModule,
35    const TargetLDBackend& pBackend) {
36  /* This is equivalent to either
37       (ALIGN(maxpagesize) + (. & (maxpagesize - 1)))
38     or
39       (ALIGN(maxpagesize) + (. & (maxpagesize - commonpagesize)))
40   */
41  IntOperand* res = result();
42  uint64_t dot = m_pOperand[0]->value();
43  uint64_t maxPageSize = m_pOperand[1]->value();
44  uint64_t commonPageSize = m_pOperand[2]->value();
45  uint64_t form1 = 0, form2 = 0;
46
47  alignAddress(dot, maxPageSize);
48
49  form1 = dot + (dot & (maxPageSize - 1));
50  form2 = dot + (dot & (maxPageSize - commonPageSize));
51
52  if (form1 <= form2)
53    res->setValue(form1);
54  else
55    res->setValue(form2);
56  return res;
57}
58
59}  // namespace mcld
60