matchers.html 16.7 KB
Newer Older
Chris Austen's avatar
Chris Austen committed
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
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
<!DOCTYPE html>
<html class="writer-html5" lang="en" >
<head>
  <meta charset="utf-8" /><meta name="generator" content="Docutils 0.17.1: http://docutils.sourceforge.net/" />

  <meta name="viewport" content="width=device-width, initial-scale=1.0" />
  <title>Matchers &mdash; MIGraphX 2.1 documentation</title>
      <link rel="stylesheet" href="../_static/pygments.css" type="text/css" />
      <link rel="stylesheet" href="../_static/css/theme.css" type="text/css" />
  <!--[if lt IE 9]>
    <script src="../_static/js/html5shiv.min.js"></script>
  <![endif]-->
  
        <script data-url_root="../" id="documentation_options" src="../_static/documentation_options.js"></script>
        <script src="../_static/jquery.js"></script>
        <script src="../_static/underscore.js"></script>
        <script src="../_static/doctools.js"></script>
    <script src="../_static/js/theme.js"></script>
    <link rel="index" title="Index" href="../genindex.html" />
    <link rel="search" title="Search" href="../search.html" />
    <link rel="next" title="Tools" href="tools.html" />
    <link rel="prev" title="Passes" href="pass.html" /> 
</head>

<body class="wy-body-for-nav"> 
  <div class="wy-grid-for-nav">
    <nav data-toggle="wy-nav-shift" class="wy-nav-side">
      <div class="wy-side-scroll">
        <div class="wy-side-nav-search" >
            <a href="../index.html" class="icon icon-home"> MIGraphX
          </a>
              <div class="version">
                2.1
              </div>
<div role="search">
  <form id="rtd-search-form" class="wy-form" action="../search.html" method="get">
    <input type="text" name="q" placeholder="Search docs" />
    <input type="hidden" name="check_keywords" value="yes" />
    <input type="hidden" name="area" value="default" />
  </form>
</div>
        </div><div class="wy-menu wy-menu-vertical" data-spy="affix" role="navigation" aria-label="Navigation menu">
              <p class="caption" role="heading"><span class="caption-text">Contents:</span></p>
<ul class="current">
<li class="toctree-l1"><a class="reference internal" href="../py_user_guide.html">Python User Guide</a></li>
<li class="toctree-l1"><a class="reference internal" href="../cpp_user_guide.html">C++ User Guide</a></li>
<li class="toctree-l1"><a class="reference internal" href="../driver.html">MIGraphX Driver</a></li>
<li class="toctree-l1 current"><a class="reference internal" href="../contributor_guide.html">Contributor Guide</a><ul class="current">
<li class="toctree-l2"><a class="reference internal" href="../dev_intro.html">MIGraphX Fundamentals</a></li>
<li class="toctree-l2"><a class="reference internal" href="data.html">Data types</a></li>
<li class="toctree-l2"><a class="reference internal" href="operators.html">Operators</a></li>
<li class="toctree-l2"><a class="reference internal" href="program.html">Program</a></li>
<li class="toctree-l2"><a class="reference internal" href="targets.html">Targets</a></li>
<li class="toctree-l2"><a class="reference internal" href="quantization.html">Quantization</a></li>
<li class="toctree-l2"><a class="reference internal" href="pass.html">Passes</a></li>
<li class="toctree-l2 current"><a class="current reference internal" href="#">Matchers</a><ul>
<li class="toctree-l3"><a class="reference internal" href="#introduction">Introduction</a></li>
<li class="toctree-l3"><a class="reference internal" href="#arguments">Arguments</a></li>
<li class="toctree-l3"><a class="reference internal" href="#binding">Binding</a></li>
<li class="toctree-l3"><a class="reference internal" href="#finding-matches">Finding matches</a></li>
<li class="toctree-l3"><a class="reference internal" href="#creating-matchers">Creating matchers</a></li>
</ul>
</li>
<li class="toctree-l2"><a class="reference internal" href="tools.html">Tools</a></li>
</ul>
</li>
</ul>

        </div>
      </div>
    </nav>

    <section data-toggle="wy-nav-shift" class="wy-nav-content-wrap"><nav class="wy-nav-top" aria-label="Mobile navigation menu" >
          <i data-toggle="wy-nav-top" class="fa fa-bars"></i>
          <a href="../index.html">MIGraphX</a>
      </nav>

      <div class="wy-nav-content">
        <div class="rst-content">
          <div role="navigation" aria-label="Page navigation">
  <ul class="wy-breadcrumbs">
      <li><a href="../index.html" class="icon icon-home"></a> &raquo;</li>
          <li><a href="../contributor_guide.html">Contributor Guide</a> &raquo;</li>
      <li>Matchers</li>
      <li class="wy-breadcrumbs-aside">
            <a href="../_sources/dev/matchers.rst.txt" rel="nofollow"> View page source</a>
      </li>
  </ul>
  <hr/>
</div>
          <div role="main" class="document" itemscope="itemscope" itemtype="http://schema.org/Article">
           <div itemprop="articleBody">
             
  <section id="matchers">
<h1>Matchers<a class="headerlink" href="#matchers" title="Permalink to this headline"></a></h1>
<section id="introduction">
<h2>Introduction<a class="headerlink" href="#introduction" title="Permalink to this headline"></a></h2>
<p>The matchers provide a way compose several predicates together. Many of the matchers can be composed so that <code class="docutils literal notranslate"><span class="pre">m(m1,</span> <span class="pre">m2)</span></code> will first check that <code class="docutils literal notranslate"><span class="pre">m</span></code> matches and then it will check that <code class="docutils literal notranslate"><span class="pre">m1</span></code> and <code class="docutils literal notranslate"><span class="pre">m2</span></code> will match.</p>
<p>The most commonly-used matcher is the <code class="docutils literal notranslate"><span class="pre">name</span></code> matcher. It will match the instruction that have the operator that is equal to the name specified:</p>
<div class="highlight-cpp notranslate"><div class="highlight"><pre><span></span><span class="k">auto</span><span class="w"> </span><span class="n">match_sum</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="n">name</span><span class="p">(</span><span class="s">&quot;sum&quot;</span><span class="p">);</span><span class="w"></span>
</pre></div>
</div>
<p>This will find <code class="docutils literal notranslate"><span class="pre">sum</span></code> operators. We can also find <code class="docutils literal notranslate"><span class="pre">sum</span></code> operators which the output is <code class="docutils literal notranslate"><span class="pre">standard_shape</span></code>:</p>
<blockquote>
<div><p>auto match_sum = name(“sum”)(standard_shape());</p>
</div></blockquote>
</section>
<section id="arguments">
<h2>Arguments<a class="headerlink" href="#arguments" title="Permalink to this headline"></a></h2>
<p>We also want to match arguments to the instructions as well. One way, is to match each argument using the <code class="docutils literal notranslate"><span class="pre">arg</span></code> matcher:</p>
<div class="highlight-cpp notranslate"><div class="highlight"><pre><span></span><span class="k">auto</span><span class="w"> </span><span class="n">match_sum</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="n">name</span><span class="p">(</span><span class="s">&quot;sum&quot;</span><span class="p">)(</span><span class="n">arg</span><span class="p">(</span><span class="mi">0</span><span class="p">)(</span><span class="n">name</span><span class="p">(</span><span class="s">&quot;@literal&quot;</span><span class="p">),</span><span class="w"> </span><span class="n">arg</span><span class="p">(</span><span class="mi">1</span><span class="p">)(</span><span class="n">name</span><span class="p">(</span><span class="s">&quot;@literal&quot;</span><span class="p">))));</span><span class="w"></span>
</pre></div>
</div>
<p>This will match a <code class="docutils literal notranslate"><span class="pre">sum</span></code> operator with the two arguments that are literals. Of course, instead of writing <code class="docutils literal notranslate"><span class="pre">arg(0)</span></code> and <code class="docutils literal notranslate"><span class="pre">arg(1)</span></code> everytime, the <code class="docutils literal notranslate"><span class="pre">args</span></code> matcher can be used:</p>
<div class="highlight-cpp notranslate"><div class="highlight"><pre><span></span><span class="k">auto</span><span class="w"> </span><span class="n">match_sum</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="n">name</span><span class="p">(</span><span class="s">&quot;sum&quot;</span><span class="p">)(</span><span class="n">args</span><span class="p">(</span><span class="n">name</span><span class="p">(</span><span class="s">&quot;@literal&quot;</span><span class="p">),</span><span class="w"> </span><span class="n">name</span><span class="p">(</span><span class="s">&quot;@literal&quot;</span><span class="p">)));</span><span class="w"></span>
</pre></div>
</div>
</section>
<section id="binding">
<h2>Binding<a class="headerlink" href="#binding" title="Permalink to this headline"></a></h2>
<p>As we traverse through the instructions we may want reference some of the instructions we find along the way. We can do this by calling <code class="docutils literal notranslate"><span class="pre">.bind</span></code>:</p>
<div class="highlight-cpp notranslate"><div class="highlight"><pre><span></span><span class="k">auto</span><span class="w"> </span><span class="n">match_sum</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="n">name</span><span class="p">(</span><span class="s">&quot;sum&quot;</span><span class="p">)(</span><span class="n">args</span><span class="p">(</span><span class="w"></span>
<span class="w">                                </span><span class="n">name</span><span class="p">(</span><span class="s">&quot;@literal&quot;</span><span class="p">).</span><span class="n">bind</span><span class="p">(</span><span class="s">&quot;one&quot;</span><span class="p">),</span><span class="w"></span>
<span class="w">                                </span><span class="n">name</span><span class="p">(</span><span class="s">&quot;@literal&quot;</span><span class="p">).</span><span class="n">bind</span><span class="p">(</span><span class="s">&quot;two&quot;</span><span class="p">)</span><span class="w"></span>
<span class="w">                            </span><span class="p">)).</span><span class="n">bind</span><span class="p">(</span><span class="s">&quot;sum&quot;</span><span class="p">);</span><span class="w"></span>
</pre></div>
</div>
<p>This will associate the instruction to a name that can be read from the <code class="docutils literal notranslate"><span class="pre">matcher_result</span></code> when it matches.</p>
</section>
<section id="finding-matches">
<h2>Finding matches<a class="headerlink" href="#finding-matches" title="Permalink to this headline"></a></h2>
<p>Finally, when you want to use the matchers to find instructions a callback object can be written which has the matcher and an <code class="docutils literal notranslate"><span class="pre">apply</span></code> function which will take the <code class="docutils literal notranslate"><span class="pre">matcher_result</span></code> when the match is found:</p>
<div class="highlight-cpp notranslate"><div class="highlight"><pre><span></span><span class="k">struct</span><span class="w"> </span><span class="nc">match_find_sum</span><span class="w"></span>
<span class="p">{</span><span class="w"></span>
<span class="w">    </span><span class="k">auto</span><span class="w"> </span><span class="n">matcher</span><span class="p">()</span><span class="w"> </span><span class="k">const</span><span class="w"> </span><span class="p">{</span><span class="w"> </span><span class="k">return</span><span class="w"> </span><span class="n">name</span><span class="p">(</span><span class="s">&quot;sum&quot;</span><span class="p">);</span><span class="w"> </span><span class="p">}</span><span class="w"></span>

<span class="w">    </span><span class="kt">void</span><span class="w"> </span><span class="n">apply</span><span class="p">(</span><span class="n">program</span><span class="o">&amp;</span><span class="w"> </span><span class="n">p</span><span class="p">,</span><span class="w"> </span><span class="n">matcher_result</span><span class="w"> </span><span class="n">r</span><span class="p">)</span><span class="w"> </span><span class="k">const</span><span class="w"></span>
<span class="w">    </span><span class="p">{</span><span class="w"></span>
<span class="w">        </span><span class="c1">// Do something with the result</span>
<span class="w">    </span><span class="p">}</span><span class="w"></span>
<span class="p">};</span><span class="w"></span>

<span class="n">find_matches</span><span class="p">(</span><span class="n">prog</span><span class="p">,</span><span class="w"> </span><span class="n">match_find_sum</span><span class="p">{});</span><span class="w"></span>
</pre></div>
</div>
</section>
<section id="creating-matchers">
<h2>Creating matchers<a class="headerlink" href="#creating-matchers" title="Permalink to this headline"></a></h2>
<p>There are several ways to create matchers. The macros <code class="docutils literal notranslate"><span class="pre">MIGRAPH_BASIC_MATCHER</span></code> and <code class="docutils literal notranslate"><span class="pre">MIGRAPH_PRED_MATCHER</span></code> help with creating matchers. For example, we can create a matcher for shapes that are broadcasted:</p>
<div class="highlight-cpp notranslate"><div class="highlight"><pre><span></span><span class="n">MIGRAPH_PRED_MATCHER</span><span class="p">(</span><span class="n">broadcasted_shape</span><span class="p">,</span><span class="w"> </span><span class="n">instruction_ref</span><span class="w"> </span><span class="n">ins</span><span class="p">)</span><span class="w"></span>
<span class="p">{</span><span class="w"></span>
<span class="w">    </span><span class="k">return</span><span class="w"> </span><span class="n">ins</span><span class="o">-&gt;</span><span class="n">get_shape</span><span class="p">().</span><span class="n">broadcasted</span><span class="p">();</span><span class="w"></span>
<span class="p">}</span><span class="w"></span>
</pre></div>
</div>
<p>If we want parameters to the predicate, then we will need to use the <code class="docutils literal notranslate"><span class="pre">make_basic_pred_matcher</span></code> to create the matcher. For example, here is how we would create a matcher to check the number of dimensions of the shape:</p>
<div class="highlight-cpp notranslate"><div class="highlight"><pre><span></span><span class="kr">inline</span><span class="w"> </span><span class="k">auto</span><span class="w"> </span><span class="n">number_of_dims</span><span class="p">(</span><span class="n">std</span><span class="o">::</span><span class="kt">size_t</span><span class="w"> </span><span class="n">n</span><span class="p">)</span><span class="w"></span>
<span class="p">{</span><span class="w"></span>
<span class="w">    </span><span class="k">return</span><span class="w"> </span><span class="n">make_basic_pred_matcher</span><span class="p">([</span><span class="o">=</span><span class="p">](</span><span class="n">instruction_ref</span><span class="w"> </span><span class="n">ins</span><span class="p">)</span><span class="w"> </span><span class="p">{</span><span class="w"></span>
<span class="w">        </span><span class="k">return</span><span class="w"> </span><span class="n">ins</span><span class="o">-&gt;</span><span class="n">get_shape</span><span class="p">().</span><span class="n">lens</span><span class="p">().</span><span class="n">size</span><span class="p">()</span><span class="w"> </span><span class="o">==</span><span class="w"> </span><span class="n">n</span><span class="p">;</span><span class="w"></span>
<span class="w">    </span><span class="p">});</span><span class="w"></span>
<span class="p">}</span><span class="w"></span>
</pre></div>
</div>
</section>
</section>


           </div>
          </div>
          <footer><div class="rst-footer-buttons" role="navigation" aria-label="Footer">
        <a href="pass.html" class="btn btn-neutral float-left" title="Passes" accesskey="p" rel="prev"><span class="fa fa-arrow-circle-left" aria-hidden="true"></span> Previous</a>
        <a href="tools.html" class="btn btn-neutral float-right" title="Tools" accesskey="n" rel="next">Next <span class="fa fa-arrow-circle-right" aria-hidden="true"></span></a>
    </div>

  <hr/>

  <div role="contentinfo">
    <p>&#169; Copyright 2018-2022, AMD.</p>
  </div>

  Built with <a href="https://www.sphinx-doc.org/">Sphinx</a> using a
    <a href="https://github.com/readthedocs/sphinx_rtd_theme">theme</a>
    provided by <a href="https://readthedocs.org">Read the Docs</a>.
   

</footer>
        </div>
      </div>
    </section>
  </div>
  <script>
      jQuery(function () {
          SphinxRtdTheme.Navigation.enable(true);
      });
  </script> 

</body>
</html>