6#ifndef JLM_LLVM_IR_OPERATORS_STDLIBINTRINSICOPERATIONS_HPP
7#define JLM_LLVM_IR_OPERATORS_STDLIBINTRINSICOPERATIONS_HPP
27 const std::vector<std::shared_ptr<const rvsdg::Type>> & operandTypes,
28 const std::vector<std::shared_ptr<const rvsdg::Type>> & resultTypes)
33 auto & dstAddressType = *operandTypes[0];
36 auto & srcAddressType = *operandTypes[1];
39 auto & lengthType = *operandTypes[2];
42 throw util::Error(
"Expected 32 bit or 64 bit integer type.");
50 auto type = std::dynamic_pointer_cast<const rvsdg::BitType>(
argument(2));
55 [[nodiscard]]
virtual size_t
62 [[nodiscard]] static rvsdg::Input &
66 const auto input = node.input(0);
79 const auto input = node.input(1);
92 const auto input = node.input(2);
104 auto [memCpyNode, memCpyOperation] =
107 const auto numNonMemoryStateOutputs =
108 memCpyNode->noutputs() - memCpyOperation->NumMemoryStates();
110 const auto numNonMemoryStateInputs = memCpyNode->ninputs() - memCpyOperation->NumMemoryStates();
111 const auto inputIndex = numNonMemoryStateInputs + (output.
index() - numNonMemoryStateOutputs);
112 const auto input = memCpyNode->input(inputIndex);
113 JLM_ASSERT(is<MemoryStateType>(input->Type()));
124 auto [memCpyNode, memCpyOperation] =
127 const auto numNonMemoryStateInputs = memCpyNode->ninputs() - memCpyOperation->NumMemoryStates();
129 const auto numNonMemoryStateOutputs =
130 memCpyNode->noutputs() - memCpyOperation->NumMemoryStates();
131 const auto outputIndex = numNonMemoryStateOutputs + (input.
index() - numNonMemoryStateInputs);
132 const auto output = memCpyNode->output(outputIndex);
133 JLM_ASSERT(is<MemoryStateType>(output->Type()));
148 const auto memCpyOperation = util::assertedCast<const MemCpyOperation>(&node.GetOperation());
149 if (memCpyOperation->NumMemoryStates() == 0)
154 const auto firstMemoryStateOutput =
155 node.output(memCpyOperation->nresults() - memCpyOperation->NumMemoryStates());
156 JLM_ASSERT(is<MemoryStateType>(firstMemoryStateOutput->Type()));
178 operator==(
const Operation & other)
const noexcept override;
180 [[nodiscard]] std::string
183 [[nodiscard]] std::unique_ptr<Operation>
184 copy()
const override;
194 const std::vector<const
Variable *> & memoryStates)
196 std::vector<const Variable *> operands = { destination, source, length };
197 operands.insert(operands.end(), memoryStates.begin(), memoryStates.end());
200 std::make_unique<MemCpyNonVolatileOperation>(length->Type(), memoryStates.size());
209 const std::vector<rvsdg::Output *> & memoryStates)
211 std::vector operands = { &destination, &source, &length };
212 operands.insert(operands.end(), memoryStates.begin(), memoryStates.end());
217 memoryStates.size());
220 static std::vector<rvsdg::Output *>
225 const std::vector<rvsdg::Output *> & memoryStates)
227 std::vector operands = { destination, source, length };
228 operands.insert(operands.end(), memoryStates.begin(), memoryStates.end());
233 memoryStates.size()));
237 static std::vector<std::shared_ptr<const rvsdg::Type>>
241 std::vector<std::shared_ptr<const rvsdg::Type>> types = { pointerType, pointerType, length };
246 static std::vector<std::shared_ptr<const rvsdg::Type>>
282 operator==(
const Operation & other)
const noexcept override;
284 [[nodiscard]] std::string
287 [[nodiscard]] std::unique_ptr<Operation>
288 copy()
const override;
293 [[nodiscard]] static rvsdg::Input &
296 JLM_ASSERT(is<MemCpyVolatileOperation>(&node));
297 const auto input = node.input(3);
305 JLM_ASSERT(is<MemCpyVolatileOperation>(&node));
306 const auto output = node.
output(0);
311 static std::unique_ptr<llvm::ThreeAddressCode>
317 const std::vector<const Variable *> & memoryStates)
319 std::vector<const Variable *> operands = { &destination, &source, &length, &ioState };
320 operands.insert(operands.end(), memoryStates.begin(), memoryStates.end());
322 auto operation = std::make_unique<MemCpyVolatileOperation>(length.
Type(), memoryStates.size());
332 const std::vector<rvsdg::Output *> & memoryStates)
334 std::vector operands = { &destination, &source, &length, &ioState };
335 operands.insert(operands.end(), memoryStates.begin(), memoryStates.end());
340 memoryStates.size());
344 static std::vector<std::shared_ptr<const rvsdg::Type>>
348 std::vector<std::shared_ptr<const rvsdg::Type>> types = { pointerType,
350 std::move(lengthType),
356 static std::vector<std::shared_ptr<const rvsdg::Type>>
380 const std::vector<std::shared_ptr<const rvsdg::Type>> & operandTypes,
381 const std::vector<std::shared_ptr<const rvsdg::Type>> & resultTypes)
386 auto & dstAddressType = *operandTypes[0];
391 throw std::runtime_error(
"Expected 8 bit integer type.");
397 throw util::Error(
"Expected 32 bit or 64 bit integer type.");
408 const auto type = std::dynamic_pointer_cast<const rvsdg::BitType>(
argument(2));
410 JLM_ASSERT(type->nbits() == 32 || type->nbits() == 64);
417 [[nodiscard]]
virtual size_t
424 [[nodiscard]] static rvsdg::Input &
428 const auto input = node.input(0);
441 const auto input = node.input(1);
454 const auto input = node.input(2);
468 auto [memsetNode, memsetOperation] =
471 const auto numNonMemoryStateOutputs =
472 memsetNode->noutputs() - memsetOperation->numMemoryStates();
474 const auto numNonMemoryStateInputs = memsetNode->ninputs() - memsetOperation->numMemoryStates();
475 const auto inputIndex = numNonMemoryStateInputs + (output.
index() - numNonMemoryStateOutputs);
476 const auto input = memsetNode->input(inputIndex);
477 JLM_ASSERT(is<MemoryStateType>(input->Type()));
488 auto [memsetNode, memsetOperation] =
491 const auto numNonMemoryStateInputs = memsetNode->ninputs() - memsetOperation->numMemoryStates();
493 const auto numNonMemoryStateOutputs =
494 memsetNode->noutputs() - memsetOperation->numMemoryStates();
495 const auto outputIndex = numNonMemoryStateOutputs + (input.
index() - numNonMemoryStateInputs);
496 const auto output = memsetNode->output(outputIndex);
497 JLM_ASSERT(is<MemoryStateType>(output->Type()));
512 const auto memSetOperation = util::assertedCast<const MemSetOperation>(&node.GetOperation());
513 if (memSetOperation->numMemoryStates() == 0)
518 const auto firstMemoryStateOutput =
519 node.output(memSetOperation->nresults() - memSetOperation->numMemoryStates());
520 JLM_ASSERT(is<MemoryStateType>(firstMemoryStateOutput->Type()));
543 operator==(
const Operation & other)
const noexcept override;
545 [[nodiscard]] std::string
548 [[nodiscard]] std::unique_ptr<Operation>
549 copy()
const override;
559 const std::vector<const
Variable *> & memoryStates)
561 std::vector operands = { &destination, &value, &length };
562 operands.insert(operands.end(), memoryStates.begin(), memoryStates.end());
565 std::make_unique<MemSetNonVolatileOperation>(length.Type(), memoryStates.size());
574 const std::vector<rvsdg::Output *> & memoryStates)
576 std::vector operands = { &destination, &value, &length };
577 operands.insert(operands.end(), memoryStates.begin(), memoryStates.end());
582 memoryStates.size());
586 static std::vector<std::shared_ptr<const rvsdg::Type>>
588 const std::shared_ptr<const rvsdg::Type> &
lengthType,
593 std::vector<std::shared_ptr<const rvsdg::Type>> types = { pointerType, valueType,
lengthType };
598 static std::vector<std::shared_ptr<const rvsdg::Type>>
623 const std::vector<std::shared_ptr<const rvsdg::Type>> & operandTypes,
624 const std::vector<std::shared_ptr<const rvsdg::Type>> & resultTypes)
629 auto & destAddressType = *operandTypes[0];
632 auto & srcAddressType = *operandTypes[1];
647 const auto type = std::dynamic_pointer_cast<const rvsdg::BitType>(
argument(2));
649 JLM_ASSERT(type->nbits() == 32 || type->nbits() == 64);
656 [[nodiscard]]
virtual size_t
663 [[nodiscard]] static rvsdg::Input &
667 const auto input = node.input(0);
680 const auto input = node.input(1);
693 const auto input = node.input(2);
694 const auto type = std::dynamic_pointer_cast<const rvsdg::BitType>(node.input(2)->Type());
696 JLM_ASSERT(type->nbits() == 32 || type->nbits() == 64);
707 auto [memmoveNode, memmoveOperation] =
710 const auto numNonMemoryStateOutputs =
711 memmoveNode->noutputs() - memmoveOperation->numMemoryStates();
713 const auto numNonMemoryStateInputs =
714 memmoveNode->ninputs() - memmoveOperation->numMemoryStates();
715 const auto inputIndex = numNonMemoryStateInputs + (output.
index() - numNonMemoryStateOutputs);
716 const auto input = memmoveNode->input(inputIndex);
717 JLM_ASSERT(is<MemoryStateType>(input->Type()));
728 auto [memmoveNode, memmoveOperation] =
731 const auto numNonMemoryStateInputs =
732 memmoveNode->ninputs() - memmoveOperation->numMemoryStates();
734 const auto numNonMemoryStateOutputs =
735 memmoveNode->noutputs() - memmoveOperation->numMemoryStates();
736 const auto outputIndex = numNonMemoryStateOutputs + (input.
index() - numNonMemoryStateInputs);
737 const auto output = memmoveNode->output(outputIndex);
738 JLM_ASSERT(is<MemoryStateType>(output->Type()));
753 const auto memMoveOperation = util::assertedCast<const MemMoveOperation>(&node.GetOperation());
754 if (memMoveOperation->numMemoryStates() == 0)
759 const auto firstMemoryStateOutput =
760 node.output(memMoveOperation->nresults() - memMoveOperation->numMemoryStates());
761 JLM_ASSERT(is<MemoryStateType>(firstMemoryStateOutput->Type()));
784 operator==(
const Operation & other)
const noexcept override;
786 [[nodiscard]] std::string
789 [[nodiscard]] std::unique_ptr<Operation>
790 copy()
const override;
800 const std::vector<const
Variable *> & memoryStates)
802 std::vector operands = { &dest, &src, &length };
803 operands.insert(operands.end(), memoryStates.begin(), memoryStates.end());
806 std::make_unique<MemMoveNonVolatileOperation>(length.Type(), memoryStates.size());
815 const std::vector<rvsdg::Output *> & memoryStates)
817 std::vector operands = { &dest, &src, &length };
818 operands.insert(operands.end(), memoryStates.begin(), memoryStates.end());
823 memoryStates.size());
827 static std::vector<std::shared_ptr<const rvsdg::Type>>
829 const std::shared_ptr<const rvsdg::Type> &
lengthType,
832 const auto bitType = std::dynamic_pointer_cast<const rvsdg::BitType>(
lengthType);
833 if (!bitType || (bitType->nbits() != 32 && bitType->nbits() != 64))
835 throw std::runtime_error(
"lengthType must be a 32-bit or 64-bit integer type");
845 static std::vector<std::shared_ptr<const rvsdg::Type>>
876 operator==(
const Operation & other)
const noexcept override;
881 [[nodiscard]] std::unique_ptr<Operation>
882 copy()
const override;
884 [[nodiscard]] std::shared_ptr<const rvsdg::Type>
890 static std::unique_ptr<ThreeAddressCode>
893 auto operation = std::make_unique<UMaxOperation>(operand1.
Type());
910 checkType(
const std::shared_ptr<const rvsdg::Type> & type);
931 operator==(
const Operation & other)
const noexcept override;
936 [[nodiscard]] std::unique_ptr<Operation>
937 copy()
const override;
939 [[nodiscard]] std::shared_ptr<const rvsdg::Type>
945 static std::unique_ptr<ThreeAddressCode>
948 auto operation = std::make_unique<SMinOperation>(operand1.
Type());
965 checkType(
const std::shared_ptr<const rvsdg::Type> & type);
986 operator==(
const Operation & other)
const noexcept override;
991 [[nodiscard]] std::unique_ptr<Operation>
992 copy()
const override;
994 [[nodiscard]] std::shared_ptr<const rvsdg::Type>
1000 static std::unique_ptr<ThreeAddressCode>
1003 auto operation = std::make_unique<UMinOperation>(operand1.
Type());
1020 checkType(
const std::shared_ptr<const rvsdg::Type> & type);
1041 operator==(
const Operation & other)
const noexcept override;
1046 [[nodiscard]] std::unique_ptr<Operation>
1047 copy()
const override;
1049 [[nodiscard]] std::shared_ptr<const rvsdg::Type>
1055 static std::unique_ptr<ThreeAddressCode>
1058 auto operation = std::make_unique<FAbsOperation>(operand.
Type());
1074 checkType(
const std::shared_ptr<const rvsdg::Type> & type);
1095 operator==(
const Operation & other)
const noexcept override;
1100 [[nodiscard]] std::unique_ptr<Operation>
1101 copy()
const override;
1103 [[nodiscard]] std::shared_ptr<const rvsdg::Type>
1109 static std::unique_ptr<ThreeAddressCode>
1112 auto operation = std::make_unique<AbsOperation>(operand1.
Type());
1129 checkType(
const std::shared_ptr<const rvsdg::Type> & type);
1150 operator==(
const Operation & other)
const noexcept override;
1155 [[nodiscard]] std::unique_ptr<Operation>
1156 copy()
const override;
1158 [[nodiscard]] std::shared_ptr<const rvsdg::Type>
1164 static std::unique_ptr<ThreeAddressCode>
1167 auto operation = std::make_unique<SMaxOperation>(operand1.
Type());
1184 checkType(
const std::shared_ptr<const rvsdg::Type> & type);
~AbsOperation() noexcept override
static rvsdg::SimpleNode & createNode(rvsdg::Output &operand1, rvsdg::Output &operand2)
bool operator==(const Operation &other) const noexcept override
std::shared_ptr< const rvsdg::Type > getType() const noexcept
static std::unique_ptr< ThreeAddressCode > createTac(const Variable &operand1, const Variable &operand2)
static void checkType(const std::shared_ptr< const rvsdg::Type > &type)
std::unique_ptr< Operation > copy() const override
std::string debug_string() const override
static std::unique_ptr< ThreeAddressCode > createTac(const Variable &operand)
std::string debug_string() const override
bool operator==(const Operation &other) const noexcept override
~FAbsOperation() noexcept override
std::unique_ptr< Operation > copy() const override
static void checkType(const std::shared_ptr< const rvsdg::Type > &type)
std::shared_ptr< const rvsdg::Type > getType() const noexcept
static rvsdg::SimpleNode & createNode(rvsdg::Output &operand)
static std::shared_ptr< const IOStateType > Create()
std::unique_ptr< Operation > copy() const override
MemCpyNonVolatileOperation(std::shared_ptr< const rvsdg::Type > lengthType, size_t numMemoryStates)
std::string debug_string() const override
static std::vector< std::shared_ptr< const rvsdg::Type > > CreateResultTypes(size_t numMemoryStates)
~MemCpyNonVolatileOperation() override
size_t NumMemoryStates() const noexcept override
static std::vector< rvsdg::Output * > create(rvsdg::Output *destination, rvsdg::Output *source, rvsdg::Output *length, const std::vector< rvsdg::Output * > &memoryStates)
static std::vector< std::shared_ptr< const rvsdg::Type > > CreateOperandTypes(std::shared_ptr< const rvsdg::Type > length, size_t numMemoryStates)
bool operator==(const Operation &other) const noexcept override
static rvsdg::SimpleNode & createNode(rvsdg::Output &destination, rvsdg::Output &source, rvsdg::Output &length, const std::vector< rvsdg::Output * > &memoryStates)
static std::unique_ptr< llvm::ThreeAddressCode > create(const Variable *destination, const Variable *source, const Variable *length, const std::vector< const Variable * > &memoryStates)
MemCpyOperation(const std::vector< std::shared_ptr< const rvsdg::Type > > &operandTypes, const std::vector< std::shared_ptr< const rvsdg::Type > > &resultTypes)
const rvsdg::BitType & LengthType() const noexcept
virtual size_t NumMemoryStates() const noexcept=0
static rvsdg::Input & sourceInput(const rvsdg::Node &node) noexcept
static rvsdg::Output & mapMemoryStateInputToOutput(const rvsdg::Input &input)
static rvsdg::Node::OutputIteratorRange memoryStateOutputs(const rvsdg::Node &node) noexcept
static rvsdg::Input & destinationInput(const rvsdg::Node &node) noexcept
static rvsdg::Input & countInput(const rvsdg::Node &node) noexcept
static rvsdg::Input & mapMemoryStateOutputToInput(const rvsdg::Output &output)
std::string debug_string() const override
static rvsdg::Input & getIOStateInput(const rvsdg::Node &node) noexcept
static std::vector< std::shared_ptr< const rvsdg::Type > > CreateResultTypes(size_t numMemoryStates)
std::unique_ptr< Operation > copy() const override
static rvsdg::Output & getIOStateOutput(const rvsdg::Node &node)
~MemCpyVolatileOperation() noexcept override
static rvsdg::SimpleNode & CreateNode(rvsdg::Output &destination, rvsdg::Output &source, rvsdg::Output &length, rvsdg::Output &ioState, const std::vector< rvsdg::Output * > &memoryStates)
static std::unique_ptr< llvm::ThreeAddressCode > CreateThreeAddressCode(const Variable &destination, const Variable &source, const Variable &length, const Variable &ioState, const std::vector< const Variable * > &memoryStates)
bool operator==(const Operation &other) const noexcept override
size_t NumMemoryStates() const noexcept override
static std::vector< std::shared_ptr< const rvsdg::Type > > CreateOperandTypes(std::shared_ptr< const rvsdg::Type > lengthType, size_t numMemoryStates)
static std::unique_ptr< ThreeAddressCode > createTac(const Variable &dest, const Variable &src, const Variable &length, const std::vector< const Variable * > &memoryStates)
static std::vector< std::shared_ptr< const rvsdg::Type > > createResultTypes(size_t numMemoryStates)
size_t numMemoryStates() const noexcept override
std::string debug_string() const override
std::unique_ptr< Operation > copy() const override
~MemMoveNonVolatileOperation() noexcept override
static std::vector< std::shared_ptr< const rvsdg::Type > > checkAndCreateOperandTypes(const std::shared_ptr< const rvsdg::Type > &lengthType, const size_t numMemoryStates)
static rvsdg::SimpleNode & createNode(rvsdg::Output &dest, rvsdg::Output &src, rvsdg::Output &length, const std::vector< rvsdg::Output * > &memoryStates)
bool operator==(const Operation &other) const noexcept override
virtual size_t numMemoryStates() const noexcept=0
static rvsdg::Input & destinationInput(const rvsdg::Node &node) noexcept
static rvsdg::Output & mapMemoryStateInputToOutput(const rvsdg::Input &input)
static rvsdg::Input & lengthInput(const rvsdg::Node &node) noexcept
static rvsdg::Node::OutputIteratorRange memoryStateOutputs(const rvsdg::Node &node) noexcept
const rvsdg::BitType & lengthType() const noexcept
static rvsdg::Input & mapMemoryStateOutputToInput(const rvsdg::Output &output)
MemMoveOperation(const std::vector< std::shared_ptr< const rvsdg::Type > > &operandTypes, const std::vector< std::shared_ptr< const rvsdg::Type > > &resultTypes)
static rvsdg::Input & sourceInput(const rvsdg::Node &node) noexcept
size_t numMemoryStates() const noexcept override
static std::vector< std::shared_ptr< const rvsdg::Type > > createOperandTypes(const std::shared_ptr< const rvsdg::Type > &lengthType, const size_t numMemoryStates)
~MemSetNonVolatileOperation() noexcept override
std::string debug_string() const override
static std::vector< std::shared_ptr< const rvsdg::Type > > createResultTypes(size_t numMemoryStates)
static rvsdg::SimpleNode & createNode(rvsdg::Output &destination, rvsdg::Output &value, rvsdg::Output &length, const std::vector< rvsdg::Output * > &memoryStates)
bool operator==(const Operation &other) const noexcept override
static std::unique_ptr< ThreeAddressCode > createTac(const Variable &destination, const Variable &value, const Variable &length, const std::vector< const Variable * > &memoryStates)
std::unique_ptr< Operation > copy() const override
MemSetOperation(const std::vector< std::shared_ptr< const rvsdg::Type > > &operandTypes, const std::vector< std::shared_ptr< const rvsdg::Type > > &resultTypes)
static rvsdg::Input & valueInput(const rvsdg::Node &node) noexcept
virtual size_t numMemoryStates() const noexcept=0
static rvsdg::Input & lengthInput(const rvsdg::Node &node) noexcept
const rvsdg::BitType & lengthType() const noexcept
static rvsdg::Output & mapMemoryStateInputToOutput(const rvsdg::Input &input)
static rvsdg::Node::OutputIteratorRange memoryStateOutputs(const rvsdg::Node &node) noexcept
static rvsdg::Input & mapMemoryStateOutputToInput(const rvsdg::Output &output)
static rvsdg::Input & destinationInput(const rvsdg::Node &node) noexcept
static std::shared_ptr< const MemoryStateType > Create()
static std::shared_ptr< const PointerType > Create()
static void checkType(const std::shared_ptr< const rvsdg::Type > &type)
std::string debug_string() const override
~SMaxOperation() noexcept override
std::unique_ptr< Operation > copy() const override
static rvsdg::SimpleNode & createNode(rvsdg::Output &operand1, rvsdg::Output &operand2)
bool operator==(const Operation &other) const noexcept override
static std::unique_ptr< ThreeAddressCode > createTac(const Variable &operand1, const Variable &operand2)
std::shared_ptr< const rvsdg::Type > getType() const noexcept
static std::unique_ptr< ThreeAddressCode > createTac(const Variable &operand1, const Variable &operand2)
~SMinOperation() noexcept override
bool operator==(const Operation &other) const noexcept override
std::string debug_string() const override
std::shared_ptr< const rvsdg::Type > getType() const noexcept
static rvsdg::SimpleNode & createNode(rvsdg::Output &operand1, rvsdg::Output &operand2)
std::unique_ptr< Operation > copy() const override
static void checkType(const std::shared_ptr< const rvsdg::Type > &type)
static std::unique_ptr< llvm::ThreeAddressCode > create(std::unique_ptr< rvsdg::SimpleOperation > operation, const std::vector< const Variable * > &operands)
std::shared_ptr< const rvsdg::Type > getType() const noexcept
static std::unique_ptr< ThreeAddressCode > createTac(const Variable &operand1, const Variable &operand2)
static void checkType(const std::shared_ptr< const rvsdg::Type > &type)
std::unique_ptr< Operation > copy() const override
std::string debug_string() const override
static rvsdg::SimpleNode & createNode(rvsdg::Output &operand1, rvsdg::Output &operand2)
bool operator==(const Operation &other) const noexcept override
~UMaxOperation() noexcept override
static std::unique_ptr< ThreeAddressCode > createTac(const Variable &operand1, const Variable &operand2)
std::unique_ptr< Operation > copy() const override
~UMinOperation() noexcept override
static rvsdg::SimpleNode & createNode(rvsdg::Output &operand1, rvsdg::Output &operand2)
std::string debug_string() const override
std::shared_ptr< const rvsdg::Type > getType() const noexcept
static void checkType(const std::shared_ptr< const rvsdg::Type > &type)
bool operator==(const Operation &other) const noexcept override
const std::shared_ptr< const jlm::rvsdg::Type > Type() const noexcept
static std::shared_ptr< const BitType > Create(std::size_t nbits)
Creates bit type of specified width.
NodeOutput * output(size_t index) const noexcept
size_t index() const noexcept
const std::shared_ptr< const rvsdg::Type > & Type() const noexcept
const std::shared_ptr< const rvsdg::Type > & argument(size_t index) const noexcept
const std::shared_ptr< const rvsdg::Type > & result(size_t index) const noexcept
SimpleOperation(std::vector< std::shared_ptr< const jlm::rvsdg::Type > > operands, std::vector< std::shared_ptr< const jlm::rvsdg::Type > > results)
UnaryOperation(std::shared_ptr< const Type > operand, std::shared_ptr< const Type > result)
Global memory state passed between functions.
NodeType * TryGetOwnerNode(const rvsdg::Input &input) noexcept
Checks if this is an input to a node of specified type.