<html><head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
  </head>
  <body>
    <div class="markdown-here-wrapper" data-md-url="" style="" markdown-here-wrapper-content-modified="true">
      <p style="margin: 0px 0px 1.2em !important;">Hi Mark,<br>
        I’ve read more about the documentation of the library you have
        linked. It seems that in this case <code style="font-size: 0.85em; font-family: Consolas, Inconsolata, Courier, monospace;margin: 0px 0.15em; padding: 0px 0.3em; white-space: pre-wrap; border: 1px solid rgb(234, 234, 234); background-color: rgb(248, 248, 248); border-radius: 3px; display: inline;">libevdev_device_log_func_t</code>
        is used by clients to set some logging function that should be
        used by the libevdev library. While it is possible for a client
        to plug in a 100% custom function into this, I would expect that
        most C clients would, in reality just write the logging function
        in a way that delegates to some other va_list accepting function
        (e.g. vprintf). After all there’s a format string to parse, so I
        don’t expect many clients to really want to do the processing
        themselves.</p>
      <p style="margin: 0px 0px 1.2em !important;">So, if one wants to
        write a logging callback in Panama that just calls vprintf with
        whatever format and va<em>list </em>parameter is passed, that
        is absolutely possible, and you don’t need VaList for that. That
        is, if an upcall takes a va_list parameter, you can still model
        it with the FFM API, but the va_list parameter becomes just a
        regular pointer (e.g. a memory segment, or memory address if you
        use JDK 17).<br>
        In this case (which is also the vastly common case), we say that
        the va_list is being received and passed <i>opaquely</i> (as a
        pointer) to some other function.</p>
      <p style="margin: 0px 0px 1.2em !important;">The problem only
        arises in two cases:</p>
      <ul style="margin: 1.2em 0px;padding-left: 2em;">
        <li style="margin: 0.5em 0px;">Java code wants to create a new
          va_list <i>from scratch</i>, and pass it to some library
          function that accepts va_list</li>
        <li style="margin: 0.5em 0px;">A Java upcall receives a va<em>list
            parameter and wants to manually</em> take it apart</li>
      </ul>
      <p style="margin: 0px 0px 1.2em !important;">(These were the use
        cases VaList was designed for).</p>
      <p style="margin: 0px 0px 1.2em !important;">While not ideal,
        these cases can still be served, by rolling in some helper C
        library. Something like:</p>
      <pre style="font-size: 0.85em; font-family: Consolas, Inconsolata, Courier, monospace;font-size: 1em; line-height: 1.2em;margin: 1.2em 0px;"><code class="hljs language-c" style="font-size: 0.85em; font-family: Consolas, Inconsolata, Courier, monospace;margin: 0px 0.15em; padding: 0px 0.3em; white-space: pre-wrap; border: 1px solid rgb(234, 234, 234); background-color: rgb(248, 248, 248); border-radius: 3px; display: inline;white-space: pre; overflow: auto; border-radius: 3px; border: 1px solid rgb(204, 204, 204); padding: 0.5em 0.7em; display: block !important;display: block; overflow-x: auto; padding: 0.5em; color: rgb(51, 51, 51); background: rgb(248, 248, 248) none repeat scroll 0% 0%; -moz-text-size-adjust: none;"><span class="hljs-preprocessor" style="color: rgb(153, 153, 153); font-weight: bold;">#<span class="hljs-keyword" style="color: rgb(51, 51, 51); font-weight: bold;">include</span> <stdarg.h></span>

<span class="hljs-keyword" style="color: rgb(51, 51, 51); font-weight: bold;">void</span> with_valist(<span class="hljs-keyword" style="color: rgb(51, 51, 51); font-weight: bold;">void</span> (*func)(va_list), <span class="hljs-keyword" style="color: rgb(51, 51, 51); font-weight: bold;">int</span> num, ...) {
    va_list arguments;
    va_start(arguments, num);
    func(arguments);
    va_end (arguments);
}

<span class="hljs-keyword" style="color: rgb(51, 51, 51); font-weight: bold;">int</span> getInt(va_list arguments) {
    <span class="hljs-keyword" style="color: rgb(51, 51, 51); font-weight: bold;">return</span> va_arg(arguments, <span class="hljs-keyword" style="color: rgb(51, 51, 51); font-weight: bold;">int</span>);
}

<span class="hljs-keyword" style="color: rgb(51, 51, 51); font-weight: bold;">long</span> getLong(va_list arguments) {
    <span class="hljs-keyword" style="color: rgb(51, 51, 51); font-weight: bold;">return</span> va_arg(arguments, <span class="hljs-keyword" style="color: rgb(51, 51, 51); font-weight: bold;">long</span>);
}

<span class="hljs-keyword" style="color: rgb(51, 51, 51); font-weight: bold;">long</span> getDouble(va_list arguments) {
    <span class="hljs-keyword" style="color: rgb(51, 51, 51); font-weight: bold;">return</span> va_arg(arguments, <span class="hljs-keyword" style="color: rgb(51, 51, 51); font-weight: bold;">double</span>);
}
</code></pre>
      <p style="margin: 0px 0px 1.2em !important;">Which can be used
        like this:</p>
      <pre style="font-size: 0.85em; font-family: Consolas, Inconsolata, Courier, monospace;font-size: 1em; line-height: 1.2em;margin: 1.2em 0px;"><code class="hljs language-c" style="font-size: 0.85em; font-family: Consolas, Inconsolata, Courier, monospace;margin: 0px 0.15em; padding: 0px 0.3em; white-space: pre-wrap; border: 1px solid rgb(234, 234, 234); background-color: rgb(248, 248, 248); border-radius: 3px; display: inline;white-space: pre; overflow: auto; border-radius: 3px; border: 1px solid rgb(204, 204, 204); padding: 0.5em 0.7em; display: block !important;display: block; overflow-x: auto; padding: 0.5em; color: rgb(51, 51, 51); background: rgb(248, 248, 248) none repeat scroll 0% 0%; -moz-text-size-adjust: none;"><span class="hljs-preprocessor" style="color: rgb(153, 153, 153); font-weight: bold;">#<span class="hljs-keyword" style="color: rgb(51, 51, 51); font-weight: bold;">include</span> <stdio.h></span>

<span class="hljs-keyword" style="color: rgb(51, 51, 51); font-weight: bold;">void</span> someFunction(va_list arguments) {
    <span class="hljs-keyword" style="color: rgb(51, 51, 51); font-weight: bold;">int</span> x = getInt(arguments);
    <span class="hljs-keyword" style="color: rgb(51, 51, 51); font-weight: bold;">int</span> y = getInt(arguments);
    <span class="hljs-built_in" style="color: rgb(0, 134, 179);">printf</span>(<span class="hljs-string" style="color: rgb(221, 17, 68);">"args = %d, %d\n"</span>, x, y);
}

<span class="hljs-keyword" style="color: rgb(51, 51, 51); font-weight: bold;">void</span> main(<span class="hljs-keyword" style="color: rgb(51, 51, 51); font-weight: bold;">void</span>) {
    with_valist(someFunction, <span class="hljs-number" style="color: rgb(0, 128, 128);">2</span>, <span class="hljs-number" style="color: rgb(0, 128, 128);">1</span>, <span class="hljs-number" style="color: rgb(0, 128, 128);">2</span>);
}
</code></pre>
      <p style="margin: 0px 0px 1.2em !important;">Note how this shim
        library allows creation of a va_list (from a variadic function,
        which FFM supports) which is passed opaquely to a function
        pointer (which can then pass it along, or process it directly).
        This feature is crucial to correctness: a va_list might hold
        onto memory in the current stack, so a va_list must only be
        accessed in the context of the function in which the va_list was
        created. The library also adds some basic functions to
        (opaquely) read different types from the va_list. I believe such
        a simple library should work well with the FFM API - and should
        be much simpler/portable than replicating the entire VaList code
        we used to have. Of course I’m not saying you should do this -
        I’m just thinking (aloud) about alternate approaches you might
        find useful if you do decide to keep VaList support in SlinC.<br>
      </p>
      <p style="margin: 0px 0px 1.2em !important;">(There is one
        limitation in the above approach: the shim library can only
        expose getters for types it knows about - so it cannot e.g.
        provide a getter for a user-defined struct).</p>
      <p style="margin: 0px 0px 1.2em !important;">Maurizio</p>
      <p style="margin: 0px 0px 1.2em !important;">On 20/04/2023 12:18,
        Mark Hammons wrote:</p>
      <p style="margin: 0px 0px 1.2em !important;"></p>
      <div class="markdown-here-exclude">
        <p></p>
        <blockquote type="cite" cite="mid:CA+QhayqTeTSEhDuP-bBBauYb_QMJHmFdmAdmaf54J2hXcWBdMA@mail.gmail.com">
          
          <div dir="ltr">Hi Maurizio, 
            <div><br>
            </div>
            <div>The main reason I was looking at VaList support is
              because I had a request from someone wanting to use my
              library that wants to bind to a function that takes this
              as a parameter: </div>
            <div><br>
            </div>
            <div><a href="https://urldefense.com/v3/__https://www.freedesktop.org/software/libevdev/doc/latest/group__logging.html*gab7eb997be2b701cc6f42e7b4c3478269__;Iw!!ACWV5N9M2RV99hQ!LsJDJl_0sVJwkTjYLgu459mq_VPbzCOu-aM_qNvUDsC9JX9x1htJ_KOAUGBG77u5mWhLSq5fQ6Zdtm_pwYc34Mc8r5ElWw$" moz-do-not-send="true">https://www.freedesktop.org/software/libevdev/doc/latest/group__logging.html#gab7eb997be2b701cc6f42e7b4c3478269</a><br>
            </div>
            <div><a href="https://urldefense.com/v3/__https://www.freedesktop.org/software/libevdev/doc/latest/group__logging.html*gaa60be86b83b3a6c82d8e536ba89ff955__;Iw!!ACWV5N9M2RV99hQ!LsJDJl_0sVJwkTjYLgu459mq_VPbzCOu-aM_qNvUDsC9JX9x1htJ_KOAUGBG77u5mWhLSq5fQ6Zdtm_pwYc34MfBqHQG3Q$" moz-do-not-send="true">https://www.freedesktop.org/software/libevdev/doc/latest/group__logging.html#gaa60be86b83b3a6c82d8e536ba89ff955</a><br>
            </div>
            <div><br>
            </div>
            <div>Considering VaList is being removed in Java 21, is
              there any way for an upcall to be defined that would be
              compatible with a va_list argument? I suppose it would be
              possible to add va_list support to my library manually
              using the methods you were using in java 19, but that adds
              some additional complexity to my library.</div>
            <div><br>
            </div>
            <div>Re int vs long, the test there doesn't attempt with
              Long, but changing `CInt` to `CLongLong` is how I do it.
              When that's done, the test starts passing without issues
              on java 17. It's very odd behavior. </div>
            <div><br>
            </div>
            <div>All in all, I'm a bit saddened to hear about VaList
              support being removed seeing as I just spent the better
              part of a week and a half adding support for it to my
              library, but I'll live should that be the final decision
              on VaList. That being said, it's one of the few things
              I've been asked for from people wanting to test my
              library, so I worry that it may be something that's wanted
              when the foreign api is no longer a preview feature. That
              being said, maybe I'm just one of the few users of the raw
              foreign API and everyone else will just use jextract ;)</div>
            <div><br>
            </div>
            <div>Thanks again for your hard work,</div>
            <div>Mark</div>
          </div>
          <br>
          <div class="gmail_quote">
            <div dir="ltr" class="gmail_attr">On Thu, Apr 20, 2023 at
              11:19 AM Maurizio Cimadamore <<a href="mailto:maurizio.cimadamore@oracle.com" moz-do-not-send="true" class="moz-txt-link-freetext">maurizio.cimadamore@oracle.com</a>>
              wrote:<br>
            </div>
            <blockquote class="gmail_quote" style="margin:0px 0px 0px
              0.8ex;border-left:1px solid
              rgb(204,204,204);padding-left:1ex">Hi Mark,<br>
              the implementation of VaList has been ironed out a lot
              around 19 (when <br>
              the API became preview) - that said, I don't recall a
              specific fix for <br>
              the issue you mention.<br>
              <br>
              Also, as mentioned here [1, 2], VaList is no longer part
              of the API <br>
              since 21, as the interaction with a VaList is hopelessly
              platform <br>
              dependent (since different platforms use different
              encoding for <br>
              va_list), meaning that it is very problematic, from a
              javadoc <br>
              perspective, to specify which exception will be issued and
              when.<br>
              <br>
              Regarding int vs. long, the C language defines a set of
              default argument <br>
              promotion that should be applied when using variadic
              functions and <br>
              va_lists. The builder methods and getters of the VaList
              class were <br>
              designed with these constraints in mind, which means the
              calls to the <br>
              valist builder have to "match" the calls to the getters
              (or undefined <br>
              behavior will ensue). From the Scala code you paste below,
              it is not <br>
              clear to me is such a mismatch occurs (I do no see `long`
              anywhere, but <br>
              I do see `get[CInt]`).<br>
              <br>
              Maurizio<br>
              <br>
              [1] - <br>
              <a href="https://mail.openjdk.org/pipermail/panama-dev/2022-November/018096.html" rel="noreferrer" target="_blank" moz-do-not-send="true" class="moz-txt-link-freetext">https://mail.openjdk.org/pipermail/panama-dev/2022-November/018096.html</a><br>
              [2] - <a href="https://git.openjdk.org/panama-foreign/pull/763" rel="noreferrer" target="_blank" moz-do-not-send="true" class="moz-txt-link-freetext">https://git.openjdk.org/panama-foreign/pull/763</a><br>
              <br>
              <br>
              On 20/04/2023 08:00, Mark Hammons wrote:<br>
              > Hi all,<br>
              ><br>
              > I know that the panama project is pushing forward on
              java 20 and 21 <br>
              > right now, and java 17 is probably not a great
              concern for you all at <br>
              > the moment, but I was testing VaList support in my
              library, Slinc, and <br>
              > it seems to be flaky on Java 17.0.5. The test in
              question goes like so:<br>
              ><br>
              >   property("varargs can be embedded in structs"):<br>
              >       forAll: (ints: Seq[CInt]) =><br>
              >         val numTake = 8<br>
              >         Scope.confined:<br>
              >           val va = VarArgsBuilder.fromIterable<br>
              >             (<br>
              >               ints.map(a => a:
              Variadic).take(numTake)<br>
              >             )<br>
              >             .build<br>
              ><br>
              >           val x = va.copy()<br>
              ><br>
              >           val p = Ptr.copy(E(x))<br>
              ><br>
              >           ints.take(numTake).foreach: value =><br>
              >             assertEquals(va.get[CInt], value,
              "conversion test")<br>
              ><br>
              >           ints.take(numTake).foreach: value =><br>
              >             assertEquals((!p).list.get[CInt], value)<br>
              > Originally in this test I was testing if I could
              write a VaList to a <br>
              > struct and get it back out and pull the values out of
              it <br>
              > appropriately. What I noticed is that if the number
              of integer values <br>
              > in a row passed into VaList is 8 or greater, my test
              fails. 7 or less <br>
              > ints and the test passes. On the Java 19
              implementation, this does not <br>
              > happen, nor does this happen when I pass a great deal
              more parameters <br>
              > (but more varied in types, some longs, some pointers,
              some structs). <br>
              > This test passes if I randomly generate Long values
              and pass those <br>
              > into the VaList.<br>
              ><br>
              > This is not a critical bug by any means. I can
              sidestep the issue by <br>
              > encoding all lower integral types into Long in the
              java 17 runtime for <br>
              > my library. I just wanted to bring this to your
              attention because it's <br>
              > a weird issue that java 17 users of the foreign api
              may hit.<br>
              ><br>
              > Thanks for your time,<br>
              > Mark Hammons<br>
            </blockquote>
          </div>
        </blockquote>
        <p></p>
      </div>
      <p style="margin: 0px 0px 1.2em !important;"></p>
      <div title="MDH:PHA+SGkgTWFyayw8YnI+SSd2ZSByZWFkIG1vcmUgYWJvdXQgdGhlIGRvY3VtZW50YXRpb24gb2YgdGhlIGxpYnJhcnkgeW91IGhhdmUgbGlua2VkLiBJdCBzZWVtcyB0aGF0IGluIHRoaXMgY2FzZSBg
bGliZXZkZXZfZGV2aWNlX2xvZ19mdW5jX3RgIGlzIHVzZWQgYnkgY2xpZW50cyB0byBzZXQgc29t
ZSBsb2dnaW5nIGZ1bmN0aW9uIHRoYXQgc2hvdWxkIGJlIHVzZWQgYnkgdGhlIDxhIGNsYXNzPSJu
YXZiYXItYnJhbmQiPmxpYmV2ZGV2IGxpYnJhcnkuIFdoaWxlIGl0IGlzIHBvc3NpYmxlIGZvciBh
IGNsaWVudCBwbHVnIGluIGEgY3VzdG9tIGZ1bmN0aW9uIGludG8gdGhpcywgSSB3b3VsZCBleHBl
Y3QgdGhhdCBtb3N0IEMgY2xpZW50cyB3b3VsZCwgaW4gcmVhbGl0eSBqdXN0IHdyaXRlIHRoZSBs
b2dnaW5nIGZ1bmN0aW9uIGluIGEgd2F5IHRoYXQgZGVsZWdhdGVzIHRvIHNvbWUgb3RoZXIgdmFf
bGlzdCBhY2NlcHRpbmcgZnVuY3Rpb24gKGUuZy4gdnByaW50ZikuIEFmdGVyIGFsbCB0aGVyZSdz
IGEgZm9ybWF0IHN0cmluZyB0byBwYXJzZSwgc28gSSBkb24ndCBleHBlY3QgbWFueSBjbGllbnRz
IHRvIHJlYWxseSB3YW50IHRvIGRvIHRoZSBwcm9jZXNzaW5nIHRoZW1zZWx2ZXMuPC9hPjwvcD48
cD48YSBjbGFzcz0ibmF2YmFyLWJyYW5kIj5TbywgaWYgb25lIHdhbnRzIHRvIHdyaXRlIGEgbG9n
Z2luZyBjYWxsYmFjayBpbiBQYW5hbWEgdGhhdCBqdXN0IGNhbGxzIHZwcmludGYgd2l0aCB3aGF0
ZXZlciBmb3JtYXQgYW5kIHZhX2xpc3QgcGFyYW1ldGVyIGlzIHBhc3NlZCwgdGhhdCBpcyBhYnNv
bHV0ZWx5IHBvc3NpYmxlLCBhbmQgeW91IGRvbid0IG5lZWQgVmFMaXN0IGZvciB0aGF0LiBUaGF0
IGlzLCBpZiBhbiB1cGNhbGwgdGFrZXMgYSB2YV9saXN0IHBhcmFtZXRlciwgeW91IGNhbiBzdGls
bCBtb2RlbCBpdCB3aXRoIHRoZSAKRkZNIEFQSSwgYnV0IHRoZSB2YV9saXN0IHBhcmFtZXRlciBu
ZWVkcyB0byBiZWNvbWUganVzdCBhIHJlZ3VsYXIgCnBvaW50ZXIgKGUuZy4gYSBtZW1vcnkgc2Vn
bWVudCwgb3IgbWVtb3J5IGFkZHJlc3MgaWYgeW91IHVzZSBKREsgMTcpLjxicj5JbiB0aGlzIGNh
c2UgKHdoaWNoIGlzIGFsc28gdGhlIHZhc3RseSBjb21tb24gY2FzZSksIHdlIHNheSB0aGF0IHRo
ZSB2YV9saXN0IGlzIGJlaW5nIHJlY2VpdmVkIGFuZCBwYXNzZWQgX29wYXF1ZWx5XyAoYXMgYSBw
b2ludGVyKSB0byBzb21lIG90aGVyIGZ1bmN0aW9uLjxicj48L2E+PC9wPjxwPjxhIGNsYXNzPSJu
YXZiYXItYnJhbmQiPlRoZSBwcm9ibGVtIG9ubHkgYXJpc2VzIGluIHR3byBjYXNlczo8YnI+PGJy
PiogSmF2YSBjb2RlIHdhbnRzIHRvIGNyZWF0ZSBhIG5ldyB2YV9saXN0IGZyb20gc2NyYXRjaCwg
YW5kIHBhc3MgaXQgdG8gc29tZSBsaWJyYXJ5IGZ1bmN0aW9uIHRoYXQgYWNjZXB0cyB2YV9saXN0
PGJyPiogQSBKYXZhIHVwY2FsbCByZWNlaXZlcyBhIHZhX2xpc3QgcGFyYW1ldGVyIGFuZCB3YW50
cyB0byBfbWFudWFsbHlfIHRha2UgaXQgYXBhcnQ8L2E+PC9wPjxwPihUaGVzZSB3ZXJlIHRoZSB1
c2UgY2FzZXMgVmFMaXN0IHdhcyBkZXNpZ25lZCBmb3IpLjwvcD48cD5XaGlsZSBub3QgaWRlYWws
IHRoZXNlIGNhc2VzIGNhbiBzdGlsbCBiZSBzZXJ2ZWQsIGJ5IHJvbGxpbmcgaW4gc29tZSBoZWxw
ZXIgQyBsaWJyYXJ5LiBTb21ldGhpbmcgbGlrZTo8L3A+PHA+YGBgYzxicj4vLyB2YWxpc3QuYzxi
cj4jaW5jbHVkZSAmbHQ7c3RkYXJnLmgmZ3Q7PGJyPjxicj52b2lkIHdpdGhfdmFsaXN0KHZvaWQg
KCpmdW5jKSh2YV9saXN0KSwgaW50IG51bSwgLi4uKSB7PGJyPiZuYnNwOyZuYnNwOyZuYnNwOyB2
YV9saXN0IGFyZ3VtZW50czs8YnI+Jm5ic3A7Jm5ic3A7Jm5ic3A7IHZhX3N0YXJ0KGFyZ3VtZW50
cywgbnVtKTs8YnI+Jm5ic3A7Jm5ic3A7Jm5ic3A7IGZ1bmMoYXJndW1lbnRzKTs8YnI+Jm5ic3A7
Jm5ic3A7Jm5ic3A7IHZhX2VuZCAoYXJndW1lbnRzKTs8YnI+fTxicj48YnI+aW50IGdldEludCh2
YV9saXN0IGFyZ3VtZW50cykgezxicj4mbmJzcDsmbmJzcDsmbmJzcDsgcmV0dXJuIHZhX2FyZyhh
cmd1bWVudHMsIGludCk7PGJyPn08YnI+PGJyPmxvbmcgZ2V0TG9uZyh2YV9saXN0IGFyZ3VtZW50
cykgezxicj4mbmJzcDsmbmJzcDsmbmJzcDsgcmV0dXJuIHZhX2FyZyhhcmd1bWVudHMsIGxvbmcp
Ozxicj59PGJyPjxicj5sb25nIGdldERvdWJsZSh2YV9saXN0IGFyZ3VtZW50cykgezxicj4mbmJz
cDsmbmJzcDsmbmJzcDsgcmV0dXJuIHZhX2FyZyhhcmd1bWVudHMsIGRvdWJsZSk7PGJyPn08YnI+
YGBgPGJyPjwvcD48cD5XaGljaCBjYW4gYmUgdXNlZCBsaWtlIHRoaXM6PGJyPjxicj5gYGBjPGJy
PiNpbmNsdWRlICZsdDtzdGRpby5oJmd0Ozxicj48YnI+dm9pZCBzb21lRnVuY3Rpb24odmFfbGlz
dCBhcmd1bWVudHMpIHs8YnI+Jm5ic3A7Jm5ic3A7Jm5ic3A7IGludCB4ID0gZ2V0SW50KGFyZ3Vt
ZW50cyk7PGJyPiZuYnNwOyZuYnNwOyZuYnNwOyBpbnQgeSA9IGdldEludChhcmd1bWVudHMpOzxi
cj4mbmJzcDsmbmJzcDsmbmJzcDsgcHJpbnRmKCJhcmdzID0gJWQsICVkXG4iLCB4LCB5KTs8YnI+
fTxicj48YnI+dm9pZCBtYWluKHZvaWQpIHs8YnI+Jm5ic3A7Jm5ic3A7Jm5ic3A7IHdpdGhfdmFs
aXN0KHNvbWVGdW5jdGlvbiwgMiwgMSwgMik7PGJyPn08YnI+YGBgPGJyPjxicj5Ob3RlIGhvdyB0
aGlzIHNoaW0gbGlicmFyeSBhbGxvd3MgY3JlYXRpb24gb2YgYSB2YV9saXN0IHdoaWNoIGlzIHBh
c3NlZCBvcGFxdWVseSB0byBhIGZ1bmN0aW9uIHBvaW50ZXIgKHdoaWNoIGNhbiB0aGVuIHBhc3Mg
aXQgYWxvbmcsIG9yIHByb2Nlc3MgaXQgZGlyZWN0bHkpLiBUaGUgbGlicmFyeSBhbHNvIGFkZHMg
c29tZSBiYXNpYyBmdW5jdGlvbnMgdG8gKG9wYXF1ZWx5KSByZWFkIGRpZmZlcmVudCB0eXBlcyBm
cm9tIHRoZSB2YV9saXN0LiBJIGJlbGlldmUgc3VjaCBhIHNpbXBsZSBsaWJyYXJ5IHNob3VsZCB3
b3JrIHdlbGwgd2l0aCB0aGUgRkZNIEFQSSAtIGFuZCBzaG91bGQgYmUgbXVjaCBzaW1wbGVyL3Bv
cnRhYmxlIHRoYW4gcmVwbGljYXRpbmcgdGhlIFZhTGlzdCBjb2RlIHdlIHVzZWQgdG8gaGF2ZS4g
T2YgY291cnNlIEknbSBub3Qgc2F5aW5nIHlvdSBzaG91bGQgZG8gdGhpcyAtIEknbSBqdXN0IHRo
aW5raW5nIGFib3V0IGFsdGVybmF0ZSBhcHByb2FjaGVzIHdoaWNoIHlvdSBtaWdodCBmaW5kIHVz
ZWZ1bC48YnI+PC9wPjxwPihUaGVyZSBpcyBvbmUgbGltaXRhdGlvbiBpbiB0aGlzIGFwcHJvYWNo
OiB0aGUgc2hpbSBsaWJyYXJ5IGNhbiBvbmx5IGV4cG9zZSBnZXR0ZXJzIGZvciB0eXBlcyBpdCBr
bm93cyBhYm91dCAtIHNvIGl0IGNhbm5vdCBlLmcuIHByb3ZpZGUgYSBnZXR0ZXIgZm9yIGEgdXNl
ci1kZWZpbmVkIHN0cnVjdCkuPGJyPjwvcD48cD5NYXVyaXppbzxicj48L3A+PHA+PGJyPjwvcD48
ZGl2IGNsYXNzPSJtb3otY2l0ZS1wcmVmaXgiPk9uIDIwLzA0LzIwMjMgMTI6MTgsIE1hcmsgSGFt
bW9ucyB3cm90ZTo8YnI+PC9kaXY+PGJsb2NrcXVvdGUgdHlwZT0iY2l0ZSIgY2l0ZT0ibWlkOkNB
K1FoYXlxVGVUU0VoRHVQLWJCQmF1WWJfUU1KSG1GZG1BZG1hZjU0SjJoWGNXQmRNQUBtYWlsLmdt
YWlsLmNvbSI+PG1ldGEgaHR0cC1lcXVpdj0iQ29udGVudC1UeXBlIiBjb250ZW50PSJ0ZXh0L2h0
bWw7ICI+PGRpdiBkaXI9Imx0ciI+SGkgTWF1cml6aW8sJm5ic3A7PGRpdj48YnI+PC9kaXY+PGRp
dj5UaGUgbWFpbiByZWFzb24gSSB3YXMgbG9va2luZyBhdCBWYUxpc3Qgc3VwcG9ydCBpcyBiZWNh
dXNlIEkgaGFkIGEgcmVxdWVzdCBmcm9tIHNvbWVvbmUgd2FudGluZyB0byB1c2UgbXkgbGlicmFy
eSB0aGF0IHdhbnRzIHRvIGJpbmQgdG8gYSBmdW5jdGlvbiB0aGF0IHRha2VzIHRoaXMgYXMgYSBw
YXJhbWV0ZXI6Jm5ic3A7PC9kaXY+PGRpdj48YnI+PC9kaXY+PGRpdj48YSBocmVmPSJodHRwczov
L3VybGRlZmVuc2UuY29tL3YzL19faHR0cHM6Ly93d3cuZnJlZWRlc2t0b3Aub3JnL3NvZnR3YXJl
L2xpYmV2ZGV2L2RvYy9sYXRlc3QvZ3JvdXBfX2xvZ2dpbmcuaHRtbCpnYWI3ZWI5OTdiZTJiNzAx
Y2M2ZjQyZTdiNGMzNDc4MjY5X187SXchIUFDV1Y1TjlNMlJWOTloUSFMc0pESmxfMHNWSndrVGpZ
TGd1NDU5bXFfVlBiekNPdS1hTV9xTnZVRHNDOUpYOXgxaHRKX0tPQVVHQkc3N3U1bVdoTFNxNWZR
NlpkdG1fcHdZYzM0TWM4cjVFbFd3JCIgbW96LWRvLW5vdC1zZW5kPSJ0cnVlIj5odHRwczovL3d3
dy5mcmVlZGVza3RvcC5vcmcvc29mdHdhcmUvbGliZXZkZXYvZG9jL2xhdGVzdC9ncm91cF9fbG9n
Z2luZy5odG1sI2dhYjdlYjk5N2JlMmI3MDFjYzZmNDJlN2I0YzM0NzgyNjk8L2E+PGJyPjwvZGl2
PjxkaXY+PGEgaHJlZj0iaHR0cHM6Ly91cmxkZWZlbnNlLmNvbS92My9fX2h0dHBzOi8vd3d3LmZy
ZWVkZXNrdG9wLm9yZy9zb2Z0d2FyZS9saWJldmRldi9kb2MvbGF0ZXN0L2dyb3VwX19sb2dnaW5n
Lmh0bWwqZ2FhNjBiZTg2YjgzYjNhNmM4MmQ4ZTUzNmJhODlmZjk1NV9fO0l3ISFBQ1dWNU45TTJS
Vjk5aFEhTHNKREpsXzBzVkp3a1RqWUxndTQ1OW1xX1ZQYnpDT3UtYU1fcU52VURzQzlKWDl4MWh0
Sl9LT0FVR0JHNzd1NW1XaExTcTVmUTZaZHRtX3B3WWMzNE1mQnFIUUczUSQiIG1vei1kby1ub3Qt
c2VuZD0idHJ1ZSI+aHR0cHM6Ly93d3cuZnJlZWRlc2t0b3Aub3JnL3NvZnR3YXJlL2xpYmV2ZGV2
L2RvYy9sYXRlc3QvZ3JvdXBfX2xvZ2dpbmcuaHRtbCNnYWE2MGJlODZiODNiM2E2YzgyZDhlNTM2
YmE4OWZmOTU1PC9hPjxicj48L2Rpdj48ZGl2Pjxicj48L2Rpdj48ZGl2PkNvbnNpZGVyaW5nIFZh
TGlzdCBpcyBiZWluZyByZW1vdmVkIGluIEphdmEgMjEsIGlzIHRoZXJlIGFueSB3YXkgZm9yIGFu
IHVwY2FsbCB0byBiZSBkZWZpbmVkIHRoYXQgd291bGQgYmUgY29tcGF0aWJsZSB3aXRoIGEgdmFf
bGlzdCBhcmd1bWVudD8gSSBzdXBwb3NlIGl0IHdvdWxkIGJlIHBvc3NpYmxlIHRvIGFkZCB2YV9s
aXN0IHN1cHBvcnQgdG8gbXkgbGlicmFyeSBtYW51YWxseSB1c2luZyB0aGUgbWV0aG9kcyB5b3Ug
d2VyZSB1c2luZyBpbiBqYXZhIDE5LCBidXQgdGhhdCBhZGRzIHNvbWUgYWRkaXRpb25hbCBjb21w
bGV4aXR5IHRvIG15IGxpYnJhcnkuPC9kaXY+PGRpdj48YnI+PC9kaXY+PGRpdj5SZSBpbnQgdnMg
bG9uZywgdGhlIHRlc3QgdGhlcmUgZG9lc24ndCBhdHRlbXB0IHdpdGggTG9uZywgYnV0IGNoYW5n
aW5nIGBDSW50YCB0byBgQ0xvbmdMb25nYCBpcyBob3cgSSBkbyBpdC4gV2hlbiB0aGF0J3MgZG9u
ZSwgdGhlIHRlc3Qgc3RhcnRzIHBhc3Npbmcgd2l0aG91dCBpc3N1ZXMgb24gamF2YSAxNy4gSXQn
cyB2ZXJ5IG9kZCBiZWhhdmlvci4mbmJzcDs8L2Rpdj48ZGl2Pjxicj48L2Rpdj48ZGl2PkFsbCBp
biBhbGwsIEknbSBhIGJpdCBzYWRkZW5lZCB0byBoZWFyIGFib3V0IFZhTGlzdCBzdXBwb3J0IGJl
aW5nIHJlbW92ZWQgc2VlaW5nIGFzIEkganVzdCBzcGVudCB0aGUgYmV0dGVyIHBhcnQgb2YgYSB3
ZWVrIGFuZCBhIGhhbGYgYWRkaW5nIHN1cHBvcnQgZm9yIGl0IHRvIG15IGxpYnJhcnksIGJ1dCBJ
J2xsIGxpdmUgc2hvdWxkIHRoYXQgYmUgdGhlIGZpbmFsIGRlY2lzaW9uIG9uIFZhTGlzdC4gVGhh
dCBiZWluZyBzYWlkLCBpdCdzIG9uZSBvZiB0aGUgZmV3IHRoaW5ncyBJJ3ZlIGJlZW4gYXNrZWQg
Zm9yIGZyb20gcGVvcGxlIHdhbnRpbmcgdG8gdGVzdCBteSBsaWJyYXJ5LCBzbyBJIHdvcnJ5IHRo
YXQgaXQgbWF5IGJlIHNvbWV0aGluZyB0aGF0J3Mgd2FudGVkIHdoZW4gdGhlIGZvcmVpZ24gYXBp
IGlzIG5vIGxvbmdlciBhIHByZXZpZXcgZmVhdHVyZS4gVGhhdCBiZWluZyBzYWlkLCBtYXliZSBJ
J20ganVzdCBvbmUgb2YgdGhlIGZldyB1c2VycyBvZiB0aGUgcmF3IGZvcmVpZ24gQVBJIGFuZCBl
dmVyeW9uZSBlbHNlIHdpbGwganVzdCB1c2UgamV4dHJhY3QgOyk8L2Rpdj48ZGl2Pjxicj48L2Rp
dj48ZGl2PlRoYW5rcyBhZ2FpbiBmb3IgeW91ciBoYXJkIHdvcmssPC9kaXY+PGRpdj5NYXJrPC9k
aXY+PC9kaXY+PGJyPjxkaXYgY2xhc3M9ImdtYWlsX3F1b3RlIj48ZGl2IGRpcj0ibHRyIiBjbGFz
cz0iZ21haWxfYXR0ciI+T24gVGh1LCBBcHIgMjAsIDIwMjMgYXQgMTE6MTnigK9BTSBNYXVyaXpp
byBDaW1hZGFtb3JlICZsdDs8YSBocmVmPSJtYWlsdG86bWF1cml6aW8uY2ltYWRhbW9yZUBvcmFj
bGUuY29tIiBtb3otZG8tbm90LXNlbmQ9InRydWUiIGNsYXNzPSJtb3otdHh0LWxpbmstZnJlZXRl
eHQiPm1hdXJpemlvLmNpbWFkYW1vcmVAb3JhY2xlLmNvbTwvYT4mZ3Q7IHdyb3RlOjxicj48L2Rp
dj48YmxvY2txdW90ZSBjbGFzcz0iZ21haWxfcXVvdGUiIHN0eWxlPSJtYXJnaW46MHB4IDBweCAw
cHggMC44ZXg7Ym9yZGVyLWxlZnQ6MXB4IHNvbGlkIHJnYigyMDQsMjA0LDIwNCk7cGFkZGluZy1s
ZWZ0OjFleCI+SGkgTWFyayw8YnI+CnRoZSBpbXBsZW1lbnRhdGlvbiBvZiBWYUxpc3QgaGFzIGJl
ZW4gaXJvbmVkIG91dCBhIGxvdCBhcm91bmQgMTkgKHdoZW4gPGJyPgp0aGUgQVBJIGJlY2FtZSBw
cmV2aWV3KSAtIHRoYXQgc2FpZCwgSSBkb24ndCByZWNhbGwgYSBzcGVjaWZpYyBmaXggZm9yIDxi
cj4KdGhlIGlzc3VlIHlvdSBtZW50aW9uLjxicj4KPGJyPgpBbHNvLCBhcyBtZW50aW9uZWQgaGVy
ZSBbMSwgMl0sIFZhTGlzdCBpcyBubyBsb25nZXIgcGFydCBvZiB0aGUgQVBJIDxicj4Kc2luY2Ug
MjEsIGFzIHRoZSBpbnRlcmFjdGlvbiB3aXRoIGEgVmFMaXN0IGlzIGhvcGVsZXNzbHkgcGxhdGZv
cm0gPGJyPgpkZXBlbmRlbnQgKHNpbmNlIGRpZmZlcmVudCBwbGF0Zm9ybXMgdXNlIGRpZmZlcmVu
dCBlbmNvZGluZyBmb3IgPGJyPgp2YV9saXN0KSwgbWVhbmluZyB0aGF0IGl0IGlzIHZlcnkgcHJv
YmxlbWF0aWMsIGZyb20gYSBqYXZhZG9jIDxicj4KcGVyc3BlY3RpdmUsIHRvIHNwZWNpZnkgd2hp
Y2ggZXhjZXB0aW9uIHdpbGwgYmUgaXNzdWVkIGFuZCB3aGVuLjxicj4KPGJyPgpSZWdhcmRpbmcg
aW50IHZzLiBsb25nLCB0aGUgQyBsYW5ndWFnZSBkZWZpbmVzIGEgc2V0IG9mIGRlZmF1bHQgYXJn
dW1lbnQgPGJyPgpwcm9tb3Rpb24gdGhhdCBzaG91bGQgYmUgYXBwbGllZCB3aGVuIHVzaW5nIHZh
cmlhZGljIGZ1bmN0aW9ucyBhbmQgPGJyPgp2YV9saXN0cy4gVGhlIGJ1aWxkZXIgbWV0aG9kcyBh
bmQgZ2V0dGVycyBvZiB0aGUgVmFMaXN0IGNsYXNzIHdlcmUgPGJyPgpkZXNpZ25lZCB3aXRoIHRo
ZXNlIGNvbnN0cmFpbnRzIGluIG1pbmQsIHdoaWNoIG1lYW5zIHRoZSBjYWxscyB0byB0aGUgPGJy
Pgp2YWxpc3QgYnVpbGRlciBoYXZlIHRvICJtYXRjaCIgdGhlIGNhbGxzIHRvIHRoZSBnZXR0ZXJz
IChvciB1bmRlZmluZWQgPGJyPgpiZWhhdmlvciB3aWxsIGVuc3VlKS4gRnJvbSB0aGUgU2NhbGEg
Y29kZSB5b3UgcGFzdGUgYmVsb3csIGl0IGlzIG5vdCA8YnI+CmNsZWFyIHRvIG1lIGlzIHN1Y2gg
YSBtaXNtYXRjaCBvY2N1cnMgKEkgZG8gbm8gc2VlIGBsb25nYCBhbnl3aGVyZSwgYnV0IDxicj4K
SSBkbyBzZWUgYGdldFtDSW50XWApLjxicj4KPGJyPgpNYXVyaXppbzxicj4KPGJyPgpbMV0gLSA8
YnI+CjxhIGhyZWY9Imh0dHBzOi8vbWFpbC5vcGVuamRrLm9yZy9waXBlcm1haWwvcGFuYW1hLWRl
di8yMDIyLU5vdmVtYmVyLzAxODA5Ni5odG1sIiByZWw9Im5vcmVmZXJyZXIiIHRhcmdldD0iX2Js
YW5rIiBtb3otZG8tbm90LXNlbmQ9InRydWUiIGNsYXNzPSJtb3otdHh0LWxpbmstZnJlZXRleHQi
Pmh0dHBzOi8vbWFpbC5vcGVuamRrLm9yZy9waXBlcm1haWwvcGFuYW1hLWRldi8yMDIyLU5vdmVt
YmVyLzAxODA5Ni5odG1sPC9hPjxicj4KWzJdIC0gPGEgaHJlZj0iaHR0cHM6Ly9naXQub3Blbmpk
ay5vcmcvcGFuYW1hLWZvcmVpZ24vcHVsbC83NjMiIHJlbD0ibm9yZWZlcnJlciIgdGFyZ2V0PSJf
YmxhbmsiIG1vei1kby1ub3Qtc2VuZD0idHJ1ZSIgY2xhc3M9Im1vei10eHQtbGluay1mcmVldGV4
dCI+aHR0cHM6Ly9naXQub3Blbmpkay5vcmcvcGFuYW1hLWZvcmVpZ24vcHVsbC83NjM8L2E+PGJy
Pgo8YnI+Cjxicj4KT24gMjAvMDQvMjAyMyAwODowMCwgTWFyayBIYW1tb25zIHdyb3RlOjxicj4K
Jmd0OyBIaSBhbGwsPGJyPgomZ3Q7PGJyPgomZ3Q7IEkga25vdyB0aGF0IHRoZSBwYW5hbWEgcHJv
amVjdCBpcyBwdXNoaW5nIGZvcndhcmQgb24gamF2YSAyMCBhbmQgMjEgPGJyPgomZ3Q7IHJpZ2h0
IG5vdywgYW5kIGphdmEgMTcgaXMgcHJvYmFibHkgbm90IGEgZ3JlYXQgY29uY2VybiBmb3IgeW91
IGFsbCBhdCA8YnI+CiZndDsgdGhlIG1vbWVudCwgYnV0IEkgd2FzIHRlc3RpbmcgVmFMaXN0IHN1
cHBvcnQgaW4gbXkgbGlicmFyeSwgU2xpbmMsIGFuZCA8YnI+CiZndDsgaXQgc2VlbXMgdG8gYmUg
Zmxha3kgb24gSmF2YSAxNy4wLjUuIFRoZSB0ZXN0IGluIHF1ZXN0aW9uIGdvZXMgbGlrZSBzbzo8
YnI+CiZndDs8YnI+CiZndDsgJm5ic3A7IHByb3BlcnR5KCJ2YXJhcmdzIGNhbiBiZSBlbWJlZGRl
ZCBpbiBzdHJ1Y3RzIik6PGJyPgomZ3Q7ICZuYnNwOyAmbmJzcDsgJm5ic3A7IGZvckFsbDogKGlu
dHM6IFNlcVtDSW50XSkgPSZndDs8YnI+CiZndDsgJm5ic3A7ICZuYnNwOyAmbmJzcDsgJm5ic3A7
IHZhbCBudW1UYWtlID0gODxicj4KJmd0OyAmbmJzcDsgJm5ic3A7ICZuYnNwOyAmbmJzcDsgU2Nv
cGUuY29uZmluZWQ6PGJyPgomZ3Q7ICZuYnNwOyAmbmJzcDsgJm5ic3A7ICZuYnNwOyAmbmJzcDsg
dmFsIHZhID0gVmFyQXJnc0J1aWxkZXIuZnJvbUl0ZXJhYmxlPGJyPgomZ3Q7ICZuYnNwOyAmbmJz
cDsgJm5ic3A7ICZuYnNwOyAmbmJzcDsgJm5ic3A7ICg8YnI+CiZndDsgJm5ic3A7ICZuYnNwOyAm
bmJzcDsgJm5ic3A7ICZuYnNwOyAmbmJzcDsgJm5ic3A7IGludHMubWFwKGEgPSZndDsgYTogVmFy
aWFkaWMpLnRha2UobnVtVGFrZSk8YnI+CiZndDsgJm5ic3A7ICZuYnNwOyAmbmJzcDsgJm5ic3A7
ICZuYnNwOyAmbmJzcDsgKTxicj4KJmd0OyAmbmJzcDsgJm5ic3A7ICZuYnNwOyAmbmJzcDsgJm5i
c3A7ICZuYnNwOyAuYnVpbGQ8YnI+CiZndDs8YnI+CiZndDsgJm5ic3A7ICZuYnNwOyAmbmJzcDsg
Jm5ic3A7ICZuYnNwOyB2YWwgeCA9IHZhLmNvcHkoKTxicj4KJmd0Ozxicj4KJmd0OyAmbmJzcDsg
Jm5ic3A7ICZuYnNwOyAmbmJzcDsgJm5ic3A7IHZhbCBwID0gUHRyLmNvcHkoRSh4KSk8YnI+CiZn
dDs8YnI+CiZndDsgJm5ic3A7ICZuYnNwOyAmbmJzcDsgJm5ic3A7ICZuYnNwOyBpbnRzLnRha2Uo
bnVtVGFrZSkuZm9yZWFjaDogdmFsdWUgPSZndDs8YnI+CiZndDsgJm5ic3A7ICZuYnNwOyAmbmJz
cDsgJm5ic3A7ICZuYnNwOyAmbmJzcDsgYXNzZXJ0RXF1YWxzKHZhLmdldFtDSW50XSwgdmFsdWUs
ICJjb252ZXJzaW9uIHRlc3QiKTxicj4KJmd0Ozxicj4KJmd0OyAmbmJzcDsgJm5ic3A7ICZuYnNw
OyAmbmJzcDsgJm5ic3A7IGludHMudGFrZShudW1UYWtlKS5mb3JlYWNoOiB2YWx1ZSA9Jmd0Ozxi
cj4KJmd0OyAmbmJzcDsgJm5ic3A7ICZuYnNwOyAmbmJzcDsgJm5ic3A7ICZuYnNwOyBhc3NlcnRF
cXVhbHMoKCFwKS5saXN0LmdldFtDSW50XSwgdmFsdWUpPGJyPgomZ3Q7IE9yaWdpbmFsbHkgaW4g
dGhpcyB0ZXN0IEkgd2FzIHRlc3RpbmcgaWYgSSBjb3VsZCB3cml0ZSBhIFZhTGlzdCB0byBhIDxi
cj4KJmd0OyBzdHJ1Y3QgYW5kIGdldCBpdCBiYWNrIG91dCBhbmQgcHVsbCB0aGUgdmFsdWVzIG91
dCBvZiBpdCA8YnI+CiZndDsgYXBwcm9wcmlhdGVseS4gV2hhdCBJIG5vdGljZWQgaXMgdGhhdCBp
ZiB0aGUgbnVtYmVyIG9mIGludGVnZXIgdmFsdWVzIDxicj4KJmd0OyBpbiBhIHJvdyBwYXNzZWQg
aW50byBWYUxpc3QgaXMgOCBvciBncmVhdGVyLCBteSB0ZXN0IGZhaWxzLiA3IG9yIGxlc3MgPGJy
PgomZ3Q7IGludHMgYW5kIHRoZSB0ZXN0IHBhc3Nlcy4gT24gdGhlIEphdmEgMTkgaW1wbGVtZW50
YXRpb24sIHRoaXMgZG9lcyBub3QgPGJyPgomZ3Q7IGhhcHBlbiwgbm9yIGRvZXMgdGhpcyBoYXBw
ZW4gd2hlbiBJIHBhc3MgYSBncmVhdCBkZWFsIG1vcmUgcGFyYW1ldGVycyA8YnI+CiZndDsgKGJ1
dCBtb3JlIHZhcmllZCBpbiB0eXBlcywgc29tZSBsb25ncywgc29tZSBwb2ludGVycywgc29tZSBz
dHJ1Y3RzKS4gPGJyPgomZ3Q7IFRoaXMgdGVzdCBwYXNzZXMgaWYgSSByYW5kb21seSBnZW5lcmF0
ZSBMb25nIHZhbHVlcyBhbmQgcGFzcyB0aG9zZSA8YnI+CiZndDsgaW50byB0aGUgVmFMaXN0Ljxi
cj4KJmd0Ozxicj4KJmd0OyBUaGlzIGlzIG5vdCBhIGNyaXRpY2FsIGJ1ZyBieSBhbnkgbWVhbnMu
IEkgY2FuIHNpZGVzdGVwIHRoZSBpc3N1ZSBieSA8YnI+CiZndDsgZW5jb2RpbmcgYWxsIGxvd2Vy
IGludGVncmFsIHR5cGVzIGludG8gTG9uZyBpbiB0aGUgamF2YSAxNyBydW50aW1lIGZvciA8YnI+
CiZndDsgbXkgbGlicmFyeS4gSSBqdXN0IHdhbnRlZCB0byBicmluZyB0aGlzIHRvIHlvdXIgYXR0
ZW50aW9uIGJlY2F1c2UgaXQncyA8YnI+CiZndDsgYSB3ZWlyZCBpc3N1ZSB0aGF0IGphdmEgMTcg
dXNlcnMgb2YgdGhlIGZvcmVpZ24gYXBpIG1heSBoaXQuPGJyPgomZ3Q7PGJyPgomZ3Q7IFRoYW5r
cyBmb3IgeW91ciB0aW1lLDxicj4KJmd0OyBNYXJrIEhhbW1vbnM8YnI+CjwvYmxvY2txdW90ZT48
        L2Rpdj4KCjwvYmxvY2txdW90ZT4=" style="height:0;width:0;max-height:0;max-width:0;overflow:hidden;font-size:0em;padding:0;margin:0;">​</div>
    </div>
  </body>
</html>