1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
|
using Ryujinx.Graphics.Shader.IntermediateRepresentation;
using System;
using System.Collections;
using System.Collections.Generic;
using static Ryujinx.Graphics.Shader.StructuredIr.AstHelper;
namespace Ryujinx.Graphics.Shader.StructuredIr
{
class AstBlock : AstNode, IEnumerable<IAstNode>
{
public AstBlockType Type { get; private set; }
private IAstNode _condition;
public IAstNode Condition
{
get
{
return _condition;
}
set
{
RemoveUse(_condition, this);
AddUse(value, this);
_condition = value;
}
}
private readonly LinkedList<IAstNode> _nodes;
public IAstNode First => _nodes.First?.Value;
public IAstNode Last => _nodes.Last?.Value;
public int Count => _nodes.Count;
public AstBlock(AstBlockType type, IAstNode condition = null)
{
Type = type;
Condition = condition;
_nodes = new LinkedList<IAstNode>();
}
public void Add(IAstNode node)
{
Add(node, _nodes.AddLast(node));
}
public void AddFirst(IAstNode node)
{
Add(node, _nodes.AddFirst(node));
}
public void AddBefore(IAstNode next, IAstNode node)
{
Add(node, _nodes.AddBefore(next.LLNode, node));
}
public void AddAfter(IAstNode prev, IAstNode node)
{
Add(node, _nodes.AddAfter(prev.LLNode, node));
}
private void Add(IAstNode node, LinkedListNode<IAstNode> newNode)
{
if (node.Parent != null)
{
throw new ArgumentException("Node already belongs to a block.");
}
node.Parent = this;
node.LLNode = newNode;
}
public void Remove(IAstNode node)
{
_nodes.Remove(node.LLNode);
node.Parent = null;
node.LLNode = null;
}
public void AndCondition(IAstNode cond)
{
Condition = new AstOperation(Instruction.LogicalAnd, Condition, cond);
}
public void OrCondition(IAstNode cond)
{
Condition = new AstOperation(Instruction.LogicalOr, Condition, cond);
}
public void TurnIntoIf(IAstNode cond)
{
Condition = cond;
Type = AstBlockType.If;
}
public void TurnIntoElseIf()
{
Type = AstBlockType.ElseIf;
}
public IEnumerator<IAstNode> GetEnumerator()
{
return _nodes.GetEnumerator();
}
IEnumerator IEnumerable.GetEnumerator()
{
return GetEnumerator();
}
}
}
|