title: Vivado HLS class with member of type hls::stream<int>& leads to error: "Constant '' has an unsynthesizable type ..."
body: <p>I'm trying to see if it is possible to instantiate a class in vivado_hls that has hls::stream&lt;> reference members so that I can directly read/write the stream without having to pass the stream as an argument down the call chain.</p>
  
  <p>NOTE: This is in vivado_hls 2018.2 and the top level module for this project is "ModuleX"
  Consider the simplified scenario below:</p>
  
  <pre><code>#include &lt;hls_stream.h&gt;
  #include &lt;ap_int.h&gt;
  
  using hls_int = ap_uint&lt;32&gt;;
  
  class X
  {
    private:
      hls::stream&lt;hls_int&gt; &amp;s1;
      hls::stream&lt;hls_int&gt; &amp;s2;
  
    public:
      X(hls::stream&lt;hls_int&gt; &amp;_s1, hls::stream&lt;hls_int&gt; &amp;_s2) :
          s1(_s1), s2(_s2)
      {}
  
      void Run()
      {
          hls_int s = s2.read();
          hls_int out = s * 2;
          s1.write(out);
      }
  };
  
  void ModuleX(hls::stream&lt;hls_int&gt; &amp;s1, hls::stream&lt;hls_int&gt; &amp;s2)
  {
      #pragma HLS INTERFACE ap_ctrl_none PORT=return
      #pragma HLS STREAM VARIABLE=s1 DEPTH=1
      #pragma HLS STREAM VARIABLE=s2 DEPTH=1
  
      static X x {s1, s2};
  
      x.Run();
  }
  </code></pre>
  
  <p>With this approach, I get the following error: <code>ERROR: [SYNCHK 200-11] ClassWithStreamRefs.cpp:18: Constant 'x.s2.V.V' has an unsynthesizable type 'i32P*' (possible cause(s): pointer to pointer or global pointer).</code></p>
  
  <p>I understand that under-the-hood, the compiler is probably storing the reference as a pointer-to the stream, but that should be a bug with the tooling for this scenario as far as I'm considered since it is blocking, what I see as valid HLS.</p>
  
  <p>Hopefully there is another way to implement what I'm looking for (references, not values are stored in the class).</p>
  
  <p>Something else I tried that worked is below. However, it's highly undesirable because the approach adds 2 clock cycles of latency (1 each at the ingress and egress - for no good reason).</p>
  
  <pre><code>#include &lt;hls_stream.h&gt;
  #include &lt;ap_int.h&gt;
  
  using hls_int = ap_uint&lt;32&gt;;
  
  class X
  {
    public:
      hls::stream&lt;hls_int&gt; s1;
      hls::stream&lt;hls_int&gt; s2;
      X()
      {
          #pragma HLS STREAM VARIABLE=s1 DEPTH=1
          #pragma HLS STREAM VARIABLE=s2 DEPTH=1
      }
  
      void Run()
      {
          hls_int s = s2.read();
          hls_int out = s * 2;
          s1.write(out);
      }
  };
  
  void ModuleX(hls::stream&lt;hls_int&gt; &amp;s1, hls::stream&lt;hls_int&gt; &amp;s2)
  {
      #pragma HLS INTERFACE ap_ctrl_none PORT=return
      #pragma HLS INLINE
      static X x;
  
      x.s2.write(s2.read());
      x.Run();
      s1.write(x.s1.read());
  }
  </code></pre>
  
  <p>Here's a sample tcl script (although it's basically just autogenerated by vivado_hls)</p>
  
  <pre><code>open_project ClassWithStreamRef
  set_top ModuleX
  add_files ClassWithStreamRefs.cpp -cflags "-std=c++11"
  open_solution "solution1"
  set_part {xczu19eg-ffvc1760-2-i} -tool vivado
  create_clock -period 10 -name default
  csynth_design
  </code></pre>