<?xml version="1.0" encoding="UTF-8" standalone="yes" ?>
<!DOCTYPE bugzilla SYSTEM "https://bugs.webkit.org/page.cgi?id=bugzilla.dtd">

<bugzilla version="5.0.4.1"
          urlbase="https://bugs.webkit.org/"
          
          maintainer="admin@webkit.org"
>

    <bug>
          <bug_id>45251</bug_id>
          
          <creation_ts>2010-09-05 22:24:39 -0700</creation_ts>
          <short_desc>Add math utilities for cubic curve processing</short_desc>
          <delta_ts>2010-09-09 20:10:40 -0700</delta_ts>
          <reporter_accessible>1</reporter_accessible>
          <cclist_accessible>1</cclist_accessible>
          <classification_id>1</classification_id>
          <classification>Unclassified</classification>
          <product>WebKit</product>
          <component>Layout and Rendering</component>
          <version>528+ (Nightly build)</version>
          <rep_platform>All</rep_platform>
          <op_sys>All</op_sys>
          <bug_status>RESOLVED</bug_status>
          <resolution>FIXED</resolution>
          
          
          <bug_file_loc></bug_file_loc>
          <status_whiteboard></status_whiteboard>
          <keywords></keywords>
          <priority>P2</priority>
          <bug_severity>Normal</bug_severity>
          <target_milestone>---</target_milestone>
          
          <blocked>44729</blocked>
          <everconfirmed>1</everconfirmed>
          <reporter name="Kenneth Russell">kbr</reporter>
          <assigned_to name="Kenneth Russell">kbr</assigned_to>
          <cc>abarth</cc>
    
    <cc>cmarrin</cc>
    
    <cc>dglazkov</cc>
    
    <cc>eric</cc>
    
    <cc>fishd</cc>
    
    <cc>jamesr</cc>
    
    <cc>senorblanco</cc>
    
    <cc>simon.fraser</cc>
    
    <cc>webkit.review.bot</cc>
          

      

      

      

          <comment_sort_order>oldest_to_newest</comment_sort_order>  
          <long_desc isprivate="0" >
    <commentid>274482</commentid>
    <comment_count>0</comment_count>
    <who name="Kenneth Russell">kbr</who>
    <bug_when>2010-09-05 22:24:39 -0700</bug_when>
    <thetext>As part of the GPU accelerated path rendering algorithm in https://bugs.webkit.org/show_bug.cgi?id=44729 , several mathematical utilities are needed, mainly involving queries and subdivision of cubic curve segments, and some geometric queries on triangles.</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>274486</commentid>
    <comment_count>1</comment_count>
      <attachid>66610</attachid>
    <who name="Kenneth Russell">kbr</who>
    <bug_when>2010-09-05 22:40:18 -0700</bug_when>
    <thetext>Created attachment 66610
Patch

From the ChangeLog:

Adding mathematic utilities needed for the GPU accelerated path rendering algorithm from GPU Gems 3. No tests yet; will be tested in conjunction with later code.</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>276137</commentid>
    <comment_count>2</comment_count>
      <attachid>66610</attachid>
    <who name="James Robinson">jamesr</who>
    <bug_when>2010-09-08 15:53:59 -0700</bug_when>
    <thetext>Comment on attachment 66610
Patch

View in context: https://bugs.webkit.org/attachment.cgi?id=66610&amp;action=prettypatch

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:129
&gt; +    float x0 = c.x() - a.x();
&gt; +    float y0 = c.y() - a.y();
&gt; +    float x1 = b.x() - a.x();
&gt; +    float y1 = b.y() - a.y();
&gt; +    float x2 = point.x() - a.x();
&gt; +    float y2 = point.y() - a.y();
&gt; +
&gt; +    float dot00 = x0 * x0 + y0 * y0;
&gt; +    float dot01 = x0 * x1 + y0 * y1;
&gt; +    float dot02 = x0 * x2 + y0 * y2;
&gt; +    float dot11 = x1 * x1 + y1 * y1;
&gt; +    float dot12 = x1 * x2 + y1 * y2;
Could this use FloatPoint&apos;s dot product?

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:177
&gt; +// Helper routines for public XRay queries below.
Could you add a link to the original source of these routines (presumably skia)?

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:181
&gt; +bool nearlyZero(float x, float tolerance = NearlyZeroConstant)
Seems redundant with approxEqual()

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:190
&gt; +inline float interpolate(float a, float b, float t)
nit: drop the inline, I believe it&apos;ll be ignored.

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:196
&gt; +float evaluateCubic(float s0, float s2, float s4, float s6, float t)
nit: rename s0, s2, s4, s6 to something else.

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:217
&gt; +bool evaluateCubicAt(const FloatPoint cubic[4], float t, FloatPoint&amp; pt)
&gt; +{
&gt; +    pt.set(evaluateCubic(cubic[0].x(), cubic[1].x(), cubic[2].x(), cubic[3].x(), t),
&gt; +           evaluateCubic(cubic[0].y(), cubic[1].y(), cubic[2].y(), cubic[3].y(), t));
&gt; +}
This should return a FloatPoint.

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:262
&gt; +    FloatPoint evaluate;
evaluatedPoint? interpolatedPoint?

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:284
&gt; +    if (xRay.x() &lt;= evaluate.x()) {
Add a FIXME: here to check if this test should be fuzzy once we have more regression tests for this code.

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:291
&gt; +int validUnitDivide(float numer, float denom, float* ratio)
numerator, denominator

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:337
&gt; +        else if (roots[0] == roots[1]) // nearly-equal?
comment isn&apos;t a sentence.  Should this be a FIXME?

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:346
&gt; +    Solve for t, keeping only those that fit betwee 0 &lt; t &lt; 1
typo: between

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:421
&gt; +        memcpy(dst, src, 4*sizeof(FloatPoint));
should loop through here and do dst[i] = src[i] to invoke FloatPoint&apos;s copy constructor.

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:435
&gt; +        memcpy(tmp, dst, 4 * sizeof(FloatPoint));
same as above

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:438
&gt; +        // watch out in case the renormalized t isn&apos;t in range
Needs to be a sentence

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:440
&gt; +                             1 - tValues[i], &amp;t)) {
1.0f

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:442
&gt; +            dst[4] = dst[5] = dst[6] = src[3];
check the values here, the dst indices look off.

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:460
&gt; +    if (dst &amp;&amp; roots &gt; 0) {
the null check for dst isn&apos;t needed here.  Also, just check for &apos;roots&apos; rather than &apos;roots &gt; 0&apos;

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:492
&gt; +    // intersect, for symmetry with SkXRayCrossesMonotonicCubic.
SkXRayCross... -&gt; xRayCross..

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:530
&gt; +    return xRay.x() &lt;= x;
add a FIXME here to check if this should be a fuzzy check

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:533
&gt; +int numXRayCrossingsForCubic(const XRay&amp; pt, const FloatPoint cubic[4], bool&amp; ambiguous)
pt -&gt; xRay

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:550
&gt; +    if (xRayCrossesMonotonicCubic(pt, &amp;monotonicCubics[0], locallyAmbiguous))
&gt; +        ++numCrossings;
&gt; +    ambiguous |= locallyAmbiguous;
&gt; +    if (numMonotonicCubics &gt; 0)
&gt; +        if (xRayCrossesMonotonicCubic(pt, &amp;monotonicCubics[3], locallyAmbiguous))
&gt; +            ++numCrossings;
&gt; +    ambiguous |= locallyAmbiguous;
&gt; +    if (numMonotonicCubics &gt; 1)
&gt; +        if (xRayCrossesMonotonicCubic(pt, &amp;monotonicCubics[6], locallyAmbiguous))
&gt; +            ++numCrossings;
&gt; +    ambiguous |= locallyAmbiguous;
Make this a loop over [0,numMonotonicCubics) and early-out if it detects ambiguity.

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.h:34
&gt; +class FloatPoint;
This has to be pulled in via in #include explicitly rather than forward declared since we call functions on FloatPoints (like diagonalLengthSquared()).

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.h:43
&gt; +const float Epsilon = 5.0e-4f;
I think this needs a storage declaration in the .cpp.</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>276682</commentid>
    <comment_count>3</comment_count>
      <attachid>67082</attachid>
    <who name="Kenneth Russell">kbr</who>
    <bug_when>2010-09-09 12:47:18 -0700</bug_when>
    <thetext>Created attachment 67082
Revised patch

Revised patch addressing above code review feedback.</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>276686</commentid>
    <comment_count>4</comment_count>
    <who name="Kenneth Russell">kbr</who>
    <bug_when>2010-09-09 12:51:08 -0700</bug_when>
    <thetext>(In reply to comment #2)
&gt; (From update of attachment 66610 [details])
&gt; View in context: https://bugs.webkit.org/attachment.cgi?id=66610&amp;action=prettypatch
&gt; 
&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:129
&gt; &gt; +    float x0 = c.x() - a.x();
&gt; &gt; +    float y0 = c.y() - a.y();
&gt; &gt; +    float x1 = b.x() - a.x();
&gt; &gt; +    float y1 = b.y() - a.y();
&gt; &gt; +    float x2 = point.x() - a.x();
&gt; &gt; +    float y2 = point.y() - a.y();
&gt; &gt; +
&gt; &gt; +    float dot00 = x0 * x0 + y0 * y0;
&gt; &gt; +    float dot01 = x0 * x1 + y0 * y1;
&gt; &gt; +    float dot02 = x0 * x2 + y0 * y2;
&gt; &gt; +    float dot11 = x1 * x1 + y1 * y1;
&gt; &gt; +    float dot12 = x1 * x2 + y1 * y2;
&gt; Could this use FloatPoint&apos;s dot product?

Unfortunately not easily, because FloatPoint - FloatPoint yields a &quot;FloatSize&quot; and FloatSize doesn&apos;t have a dot product operation.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:177
&gt; &gt; +// Helper routines for public XRay queries below.
&gt; Could you add a link to the original source of these routines (presumably skia)?

Done.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:181
&gt; &gt; +bool nearlyZero(float x, float tolerance = NearlyZeroConstant)
&gt; Seems redundant with approxEqual()

Agreed, but I do not want to change these two independent tolerances at this point.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:190
&gt; &gt; +inline float interpolate(float a, float b, float t)
&gt; nit: drop the inline, I believe it&apos;ll be ignored.

Done.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:196
&gt; &gt; +float evaluateCubic(float s0, float s2, float s4, float s6, float t)
&gt; nit: rename s0, s2, s4, s6 to something else.

Done.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:217
&gt; &gt; +bool evaluateCubicAt(const FloatPoint cubic[4], float t, FloatPoint&amp; pt)
&gt; &gt; +{
&gt; &gt; +    pt.set(evaluateCubic(cubic[0].x(), cubic[1].x(), cubic[2].x(), cubic[3].x(), t),
&gt; &gt; +           evaluateCubic(cubic[0].y(), cubic[1].y(), cubic[2].y(), cubic[3].y(), t));
&gt; &gt; +}
&gt; This should return a FloatPoint.

Done.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:262
&gt; &gt; +    FloatPoint evaluate;
&gt; evaluatedPoint? interpolatedPoint?

Changed to evaluatedPoint.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:284
&gt; &gt; +    if (xRay.x() &lt;= evaluate.x()) {
&gt; Add a FIXME: here to check if this test should be fuzzy once we have more regression tests for this code.

Done.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:291
&gt; &gt; +int validUnitDivide(float numer, float denom, float* ratio)
&gt; numerator, denominator

Done.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:337
&gt; &gt; +        else if (roots[0] == roots[1]) // nearly-equal?
&gt; comment isn&apos;t a sentence.  Should this be a FIXME?

Changed to be a sentence. I think this case is desired this way and does not warrant a FIXME.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:346
&gt; &gt; +    Solve for t, keeping only those that fit betwee 0 &lt; t &lt; 1
&gt; typo: between

Fixed.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:421
&gt; &gt; +        memcpy(dst, src, 4*sizeof(FloatPoint));
&gt; should loop through here and do dst[i] = src[i] to invoke FloatPoint&apos;s copy constructor.

Done.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:435
&gt; &gt; +        memcpy(tmp, dst, 4 * sizeof(FloatPoint));
&gt; same as above

Done.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:438
&gt; &gt; +        // watch out in case the renormalized t isn&apos;t in range
&gt; Needs to be a sentence

Fixed.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:440
&gt; &gt; +                             1 - tValues[i], &amp;t)) {
&gt; 1.0f

Done.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:442
&gt; &gt; +            dst[4] = dst[5] = dst[6] = src[3];
&gt; check the values here, the dst indices look off.

I re-checked this against the original Skia sources and the indices have the same semantics, so I&apos;m leaving these as is.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:460
&gt; &gt; +    if (dst &amp;&amp; roots &gt; 0) {
&gt; the null check for dst isn&apos;t needed here.  Also, just check for &apos;roots&apos; rather than &apos;roots &gt; 0&apos;

Done.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:492
&gt; &gt; +    // intersect, for symmetry with SkXRayCrossesMonotonicCubic.
&gt; SkXRayCross... -&gt; xRayCross..

Done.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:530
&gt; &gt; +    return xRay.x() &lt;= x;
&gt; add a FIXME here to check if this should be a fuzzy check

Done.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:533
&gt; &gt; +int numXRayCrossingsForCubic(const XRay&amp; pt, const FloatPoint cubic[4], bool&amp; ambiguous)
&gt; pt -&gt; xRay

Done.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:550
&gt; &gt; +    if (xRayCrossesMonotonicCubic(pt, &amp;monotonicCubics[0], locallyAmbiguous))
&gt; &gt; +        ++numCrossings;
&gt; &gt; +    ambiguous |= locallyAmbiguous;
&gt; &gt; +    if (numMonotonicCubics &gt; 0)
&gt; &gt; +        if (xRayCrossesMonotonicCubic(pt, &amp;monotonicCubics[3], locallyAmbiguous))
&gt; &gt; +            ++numCrossings;
&gt; &gt; +    ambiguous |= locallyAmbiguous;
&gt; &gt; +    if (numMonotonicCubics &gt; 1)
&gt; &gt; +        if (xRayCrossesMonotonicCubic(pt, &amp;monotonicCubics[6], locallyAmbiguous))
&gt; &gt; +            ++numCrossings;
&gt; &gt; +    ambiguous |= locallyAmbiguous;
&gt; Make this a loop over [0,numMonotonicCubics) and early-out if it detects ambiguity.

Done.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.h:34
&gt; &gt; +class FloatPoint;
&gt; This has to be pulled in via in #include explicitly rather than forward declared since we call functions on FloatPoints (like diagonalLengthSquared()).

Done.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.h:43
&gt; &gt; +const float Epsilon = 5.0e-4f;
&gt; I think this needs a storage declaration in the .cpp.

No, that causes a compilation failure. Since this constant is only referenced from this header I&apos;ve renamed it ImplementationEpsilon and added a comment indicating that outside code shouldn&apos;t reference it, which should prevent problems on any platform.</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>276780</commentid>
    <comment_count>5</comment_count>
      <attachid>67082</attachid>
    <who name="James Robinson">jamesr</who>
    <bug_when>2010-09-09 14:55:25 -0700</bug_when>
    <thetext>Comment on attachment 67082
Revised patch

r- for various nits.  Overall, I want to make sure we feel really good about the math functions we check in regardless of what their history is.  We&apos;re going to have to maintain these indefinitely even if they did come from skia originally.

View in context: https://bugs.webkit.org/attachment.cgi?id=67082&amp;action=prettypatch

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:137
&gt; +    float denom = dot00 * dot11 - dot01 * dot01;
&gt; +    if (!denom)
&gt; +        // Triangle is zero-area. Treat query point as not being inside.
&gt; +        return false;
&gt; +    // Compute
&gt; +    float invDenom = 1.0f / denom;
&gt; +    float u = (dot11 * dot02 - dot01 * dot12) * invDenom;
&gt; +    float v = (dot00 * dot12 - dot01 * dot02) * invDenom;
denom -&gt; denominator, invDenom -&gt; inverseDenimonator.  Or just divide by the denominator

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:171
&gt; +    // Finally, test if tri1 is totally contained in tri2 or vice versa.
&gt; +    if (pointInTriangle(a1, a2, b2, c2)
&gt; +        || pointInTriangle(a2, a1, b1, c1))
&gt; +        return true;
&gt; +
&gt; +    // Because we define that triangles sharing a vertex or edge don&apos;t
&gt; +    // overlap, we must perform additional point-in-triangle tests to
&gt; +    // see whether one triangle is contained in the other.
&gt; +    if (pointInTriangle(b1, a2, b2, c2)
&gt; +        || pointInTriangle(c1, a2, b2, c2)
&gt; +        || pointInTriangle(b2, a1, b1, c1)
&gt; +        || pointInTriangle(c2, a1, b1, c1))
&gt; +        return true;
seems like it&apos;d be cleaner to unify these two sets of tests with a preceeding comment explaining why it diverges from the akpeters.com paper

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:198
&gt; +float evaluateCubic(float s0, float s2, float s4, float s6, float t)
s0, s2, s4, s6 still need a rename

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:200
&gt; +    ASSERT(t &gt;= 0 &amp;&amp; t &lt;= 1);
0.0f, 1.0f

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:275
&gt; +        upperT = 1;
&gt; +        lowerT = 0;
&gt; +    } else {
&gt; +        upperT = 0;
&gt; +        lowerT = 1;
0.0f, 1.0f

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:278
&gt; +        float t = 0.5 * (upperT + lowerT);
0.5f (0.5 is a double)

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:314
&gt; +    if (!denominator || !numerator || numerator &gt;= denominator)
&gt; +        return 0;
&gt; +
&gt; +    float r = numerator / denominator;
&gt; +    if (isnan(r))
&gt; +        return 0;
&gt; +    ASSERT(r &gt;= 0 &amp;&amp; r &lt; 1);
&gt; +    if (!r) // catch underflow if numerator &lt;&lt;&lt;&lt; denominator
&gt; +        return 0;
&gt; +    *ratio = r;
&gt; +    return 1;
I can&apos;t get past how bizarre this function is.  I would strongly suggest rewriting this and the root finding section below.  If we discover bugs introduced by the rewrite later on that&apos;s fine, we will be able to fix them.  If we find bugs in this code I&apos;m concerned that we&apos;ll just be SOL.

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:344
&gt; +    float* r = roots;
&gt; +
&gt; +    float R = b*b - 4*a*c;
&gt; +    if (R &lt; 0 || isnan(R)) // complex roots
&gt; +        return 0;
&gt; +    R = sqrtf(R);
&gt; +
&gt; +    float Q = (b &lt; 0) ? -(b - R) / 2 : -(b + R) / 2;
&gt; +    r += validUnitDivide(Q, a, r);
&gt; +    r += validUnitDivide(c, Q, r);
&gt; +    if (r - roots == 2)
&gt; +        if (roots[0] &gt; roots[1])
&gt; +            std::swap(roots[0], roots[1]);
&gt; +        else if (roots[0] == roots[1]) // are the roots nearly equal?
&gt; +            r -= 1; // skip the double root
&gt; +    return (int)(r - roots);
&gt; +}
This code is just insane.  I think it&apos;s correct, but it looks a long way from the simplest way to do this.

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:351
&gt; +/** Cubic&apos;(t) = pt^2 + qt + r, where
&gt; +    p = 3(-a + 3(b - c) + d)
&gt; +    q = 6(a - 2b + c)
&gt; +    r = 3(b - a)
&gt; +    Solve for t, keeping only those that fit between 0 &lt; t &lt; 1
&gt; +*/
Wrong comment style for WebKit.

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:354
&gt; +    // we divide p, q, and r by 3 to simplify
not a sentence and not very clear

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:357
&gt; +    float p = d - a + 3*(b - c);
&gt; +    float q = 2*(a - b - b + c);
&gt; +    float r = b - a;
&quot;- b - b&quot; -&gt; &quot;-2.0f * b&quot;
3 -&gt; 3.0f
2 -&gt; 2.0f

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:406
&gt; +    This test code would fail when we didn&apos;t check the return result of
&gt; +    valid_unit_divide in SkChopCubicAt(... tValues[], int roots). The reason is
&gt; +    that after the first chop, the parameters to valid_unit_divide are equal
&gt; +    (thanks to finite float precision and rounding in the subtracts). Thus
&gt; +    even though the 2nd tValue looks &lt; 1.0, after we renormalize it, we end
&gt; +    up with 1.0, hence the need to check and just return the last cubic as
&gt; +    a degenerate clump of 4 points in the same place.
&gt; +
&gt; +    static void test_cubic() {
&gt; +        SkPoint src[4] = {
&gt; +            { 556.25000, 523.03003 },
&gt; +            { 556.23999, 522.96002 },
&gt; +            { 556.21997, 522.89001 },
&gt; +            { 556.21997, 522.82001 }
&gt; +        };
&gt; +        SkPoint dst[10];
&gt; +        SkScalar tval[] = { 0.33333334f, 0.99999994f };
&gt; +        SkChopCubicAt(src, dst, tval, 2);
This comment doesn&apos;t make sense any more in this context.  It looks like something that should be encoded in a unit test instead of a comment.

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:410
&gt; +void chopCubicAt(const FloatPoint src[4], FloatPoint dst[], const float tValues[], int roots)
This function does something very different from what the other chopCubicAt() in this file does.  Maybe call it chopCubicAtRoots()?

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:422
&gt; +    if (!dst)
&gt; +        return;
&gt; +
This is unnecessary (we never pass NULL in for this parameter in this file and it&apos;s not a public API)

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:442
&gt; +        src = tmp;
This function mutates src as well?  That&apos;s a bit unexpected, and it means that the exposed function numXRayCrossingsForCubic() mutates its cubic parameter which seems suspicious.  I think this should only mutate temporaries

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:481
&gt; +    ASSERT(t &gt; 0 &amp;&amp; t &lt; 1);
0.0f, 1.0f.  Why aren&apos;t 0.0 and 1.0 valid inputs for this function?

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.h:71
&gt; +// A roundoff factor in the cubic classification and texture coordinate
&gt; +// generation algorithms. It is only an implementation detail and should
&gt; +// not be referenced by code outside this namespace. It primarily
&gt; +// determines the handling of corner cases during the classification
&gt; +// process. Be careful when adjusting this; it has been determined
&gt; +// empirically to work well. When changing it, you should look in
&gt; +// particular at shapes that contain quadratic curves and ensure they still
&gt; +// look smooth. Once pixel tests are running against this algorithm, they
&gt; +// should provide sufficient coverage to ensure that adjusting the constant
&gt; +// won&apos;t break anything.
&gt; +const float ImplementationEpsilon = 5.0e-4f;
&gt; +
&gt; +// Returns zero if value is within +/-ImplementationEpsilon of zero.
&gt; +inline float roundToZero(float val)
&gt; +{
&gt; +    if (val &lt; ImplementationEpsilon &amp;&amp; val &gt; -ImplementationEpsilon)
&gt; +        return 0;
&gt; +    return val;
&gt; +}
&gt; +
&gt; +inline bool approxEqual(const FloatPoint&amp; v0, const FloatPoint&amp; v1)
&gt; +{
&gt; +    return (v0 - v1).diagonalLengthSquared() &lt; ImplementationEpsilon * ImplementationEpsilon;
&gt; +}
&gt; +
&gt; +inline bool approxEqual(const FloatPoint3D&amp; v0, const FloatPoint3D&amp; v1)
&gt; +{
&gt; +    return (v0 - v1).lengthSquared() &lt; ImplementationEpsilon * ImplementationEpsilon;
&gt; +}
&gt; +
&gt; +inline bool approxEqual(float f0, float f1)
&gt; +{
&gt; +    return fabsf(f0 - f1) &lt; ImplementationEpsilon;
&gt; +}
Why not move the bodies of all of these functions over to the .cpp and not mention ImplementationEpsilon at all in the header?  The implementations will get inlined by an optimizing linker anyway.</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>276884</commentid>
    <comment_count>6</comment_count>
      <attachid>67126</attachid>
    <who name="Kenneth Russell">kbr</who>
    <bug_when>2010-09-09 17:47:14 -0700</bug_when>
    <thetext>Created attachment 67126
Revised patch

Addressed code review feedback above.</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>276890</commentid>
    <comment_count>7</comment_count>
    <who name="Kenneth Russell">kbr</who>
    <bug_when>2010-09-09 17:59:34 -0700</bug_when>
    <thetext>(In reply to comment #5)
&gt; (From update of attachment 67082 [details])
&gt; r- for various nits.  Overall, I want to make sure we feel really good about the math functions we check in regardless of what their history is.  We&apos;re going to have to maintain these indefinitely even if they did come from skia originally.
&gt; 
&gt; View in context: https://bugs.webkit.org/attachment.cgi?id=67082&amp;action=prettypatch
&gt; 
&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:137
&gt; &gt; +    float denom = dot00 * dot11 - dot01 * dot01;
&gt; &gt; +    if (!denom)
&gt; &gt; +        // Triangle is zero-area. Treat query point as not being inside.
&gt; &gt; +        return false;
&gt; &gt; +    // Compute
&gt; &gt; +    float invDenom = 1.0f / denom;
&gt; &gt; +    float u = (dot11 * dot02 - dot01 * dot12) * invDenom;
&gt; &gt; +    float v = (dot00 * dot12 - dot01 * dot02) * invDenom;
&gt; denom -&gt; denominator, invDenom -&gt; inverseDenimonator.  Or just divide by the denominator

Renamed. Want to retain the reduced number of divisions in the code.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:171
&gt; &gt; +    // Finally, test if tri1 is totally contained in tri2 or vice versa.
&gt; &gt; +    if (pointInTriangle(a1, a2, b2, c2)
&gt; &gt; +        || pointInTriangle(a2, a1, b1, c1))
&gt; &gt; +        return true;
&gt; &gt; +
&gt; &gt; +    // Because we define that triangles sharing a vertex or edge don&apos;t
&gt; &gt; +    // overlap, we must perform additional point-in-triangle tests to
&gt; &gt; +    // see whether one triangle is contained in the other.
&gt; &gt; +    if (pointInTriangle(b1, a2, b2, c2)
&gt; &gt; +        || pointInTriangle(c1, a2, b2, c2)
&gt; &gt; +        || pointInTriangle(b2, a1, b1, c1)
&gt; &gt; +        || pointInTriangle(c2, a1, b1, c1))
&gt; &gt; +        return true;
&gt; seems like it&apos;d be cleaner to unify these two sets of tests with a preceeding comment explaining why it diverges from the akpeters.com paper

OK, done.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:198
&gt; &gt; +float evaluateCubic(float s0, float s2, float s4, float s6, float t)
&gt; s0, s2, s4, s6 still need a rename

Oversight on my part. Done.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:200
&gt; &gt; +    ASSERT(t &gt;= 0 &amp;&amp; t &lt;= 1);
&gt; 0.0f, 1.0f

WebKit style specifies that when the floating-point suffix is not required on a floating-point constant, such as here, it should not be used. See &quot;Floating point literals&quot; on http://webkit.org/coding/coding-style.html . Left unchanged.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:275
&gt; &gt; +        upperT = 1;
&gt; &gt; +        lowerT = 0;
&gt; &gt; +    } else {
&gt; &gt; +        upperT = 0;
&gt; &gt; +        lowerT = 1;
&gt; 0.0f, 1.0f

No, per above.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:278
&gt; &gt; +        float t = 0.5 * (upperT + lowerT);
&gt; 0.5f (0.5 is a double)

This one I changed.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:314
&gt; &gt; +    if (!denominator || !numerator || numerator &gt;= denominator)
&gt; &gt; +        return 0;
&gt; &gt; +
&gt; &gt; +    float r = numerator / denominator;
&gt; &gt; +    if (isnan(r))
&gt; &gt; +        return 0;
&gt; &gt; +    ASSERT(r &gt;= 0 &amp;&amp; r &lt; 1);
&gt; &gt; +    if (!r) // catch underflow if numerator &lt;&lt;&lt;&lt; denominator
&gt; &gt; +        return 0;
&gt; &gt; +    *ratio = r;
&gt; &gt; +    return 1;
&gt; I can&apos;t get past how bizarre this function is.  I would strongly suggest rewriting this and the root finding section below.  If we discover bugs introduced by the rewrite later on that&apos;s fine, we will be able to fix them.  If we find bugs in this code I&apos;m concerned that we&apos;ll just be SOL.

I spent quite some time looking through Numerical Recipes in C and trying to simplify this and the root finding code below, but the conclusion I&apos;ve come to is that having this general function is a good idea. I&apos;ve renamed it to &quot;safeUnitDivide&quot; and made it more WebKit-style (bool return value, outgoing float&amp; rather than float*. I hope you will find it more palatable because I do not see a way to get rid of it completely without rewriting all of the math in this file.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:344
&gt; &gt; +    float* r = roots;
&gt; &gt; +
&gt; &gt; +    float R = b*b - 4*a*c;
&gt; &gt; +    if (R &lt; 0 || isnan(R)) // complex roots
&gt; &gt; +        return 0;
&gt; &gt; +    R = sqrtf(R);
&gt; &gt; +
&gt; &gt; +    float Q = (b &lt; 0) ? -(b - R) / 2 : -(b + R) / 2;
&gt; &gt; +    r += validUnitDivide(Q, a, r);
&gt; &gt; +    r += validUnitDivide(c, Q, r);
&gt; &gt; +    if (r - roots == 2)
&gt; &gt; +        if (roots[0] &gt; roots[1])
&gt; &gt; +            std::swap(roots[0], roots[1]);
&gt; &gt; +        else if (roots[0] == roots[1]) // are the roots nearly equal?
&gt; &gt; +            r -= 1; // skip the double root
&gt; &gt; +    return (int)(r - roots);
&gt; &gt; +}
&gt; This code is just insane.  I think it&apos;s correct, but it looks a long way from the simplest way to do this.

After trying to rewrite this to be closer to the pure Numerical Recipes in C algorithm, there are good reasons for the logic in here, specifically that the roots of the quadratic equations solved in this file are always supposed to be between 0 and 1 because those are the valid &quot;time&quot; parameters for the incoming cubics. However this is not automatically the case; it is necessary to detect when the roots are out of range and squelch them. I have rewritten the logic in this function, and hopefully it should be easier to read, but the algorithm is basically unchanged and needs to be.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:351
&gt; &gt; +/** Cubic&apos;(t) = pt^2 + qt + r, where
&gt; &gt; +    p = 3(-a + 3(b - c) + d)
&gt; &gt; +    q = 6(a - 2b + c)
&gt; &gt; +    r = 3(b - a)
&gt; &gt; +    Solve for t, keeping only those that fit between 0 &lt; t &lt; 1
&gt; &gt; +*/
&gt; Wrong comment style for WebKit.

Changed.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:354
&gt; &gt; +    // we divide p, q, and r by 3 to simplify
&gt; not a sentence and not very clear

Will upload another patch fixing this.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:357
&gt; &gt; +    float p = d - a + 3*(b - c);
&gt; &gt; +    float q = 2*(a - b - b + c);
&gt; &gt; +    float r = b - a;
&gt; &quot;- b - b&quot; -&gt; &quot;-2.0f * b&quot;
&gt; 3 -&gt; 3.0f
&gt; 2 -&gt; 2.0f

No, per above.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:406
&gt; &gt; +    This test code would fail when we didn&apos;t check the return result of
&gt; &gt; +    valid_unit_divide in SkChopCubicAt(... tValues[], int roots). The reason is
&gt; &gt; +    that after the first chop, the parameters to valid_unit_divide are equal
&gt; &gt; +    (thanks to finite float precision and rounding in the subtracts). Thus
&gt; &gt; +    even though the 2nd tValue looks &lt; 1.0, after we renormalize it, we end
&gt; &gt; +    up with 1.0, hence the need to check and just return the last cubic as
&gt; &gt; +    a degenerate clump of 4 points in the same place.
&gt; &gt; +
&gt; &gt; +    static void test_cubic() {
&gt; &gt; +        SkPoint src[4] = {
&gt; &gt; +            { 556.25000, 523.03003 },
&gt; &gt; +            { 556.23999, 522.96002 },
&gt; &gt; +            { 556.21997, 522.89001 },
&gt; &gt; +            { 556.21997, 522.82001 }
&gt; &gt; +        };
&gt; &gt; +        SkPoint dst[10];
&gt; &gt; +        SkScalar tval[] = { 0.33333334f, 0.99999994f };
&gt; &gt; +        SkChopCubicAt(src, dst, tval, 2);
&gt; This comment doesn&apos;t make sense any more in this context.  It looks like something that should be encoded in a unit test instead of a comment.

I&apos;ve removed the comment since the logic is taking care of the originally failing case.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:410
&gt; &gt; +void chopCubicAt(const FloatPoint src[4], FloatPoint dst[], const float tValues[], int roots)
&gt; This function does something very different from what the other chopCubicAt() in this file does.  Maybe call it chopCubicAtRoots()?

It actually chops at certain T values (the cubic extrema, not its roots) so I&apos;ve renamed it to chopCubicAtTValues.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:422
&gt; &gt; +    if (!dst)
&gt; &gt; +        return;
&gt; &gt; +
&gt; This is unnecessary (we never pass NULL in for this parameter in this file and it&apos;s not a public API)

OK, removed.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:442
&gt; &gt; +        src = tmp;
&gt; This function mutates src as well?  That&apos;s a bit unexpected, and it means that the exposed function numXRayCrossingsForCubic() mutates its cubic parameter which seems suspicious.  I think this should only mutate temporaries

It doesn&apos;t actually mutate src; it makes src point to tmp so that the next iteration comes from tmp rather than src. However I agree that this is confusing so I&apos;ve changed the code to always copy src to tmp and use tmp as the source in the loop, despite the fact that this may induce a copy where one isn&apos;t needed.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:481
&gt; &gt; +    ASSERT(t &gt; 0 &amp;&amp; t &lt; 1);
&gt; 0.0f, 1.0f.  Why aren&apos;t 0.0 and 1.0 valid inputs for this function?

Looking at the callees, 0 and 1 should be valid. I&apos;ve changed the assert to use &gt;= and &lt;=, but left the constants alone per above.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.h:71
&gt; &gt; +// A roundoff factor in the cubic classification and texture coordinate
&gt; &gt; +// generation algorithms. It is only an implementation detail and should
&gt; &gt; +// not be referenced by code outside this namespace. It primarily
&gt; &gt; +// determines the handling of corner cases during the classification
&gt; &gt; +// process. Be careful when adjusting this; it has been determined
&gt; &gt; +// empirically to work well. When changing it, you should look in
&gt; &gt; +// particular at shapes that contain quadratic curves and ensure they still
&gt; &gt; +// look smooth. Once pixel tests are running against this algorithm, they
&gt; &gt; +// should provide sufficient coverage to ensure that adjusting the constant
&gt; &gt; +// won&apos;t break anything.
&gt; &gt; +const float ImplementationEpsilon = 5.0e-4f;
&gt; &gt; +
&gt; &gt; +// Returns zero if value is within +/-ImplementationEpsilon of zero.
&gt; &gt; +inline float roundToZero(float val)
&gt; &gt; +{
&gt; &gt; +    if (val &lt; ImplementationEpsilon &amp;&amp; val &gt; -ImplementationEpsilon)
&gt; &gt; +        return 0;
&gt; &gt; +    return val;
&gt; &gt; +}
&gt; &gt; +
&gt; &gt; +inline bool approxEqual(const FloatPoint&amp; v0, const FloatPoint&amp; v1)
&gt; &gt; +{
&gt; &gt; +    return (v0 - v1).diagonalLengthSquared() &lt; ImplementationEpsilon * ImplementationEpsilon;
&gt; &gt; +}
&gt; &gt; +
&gt; &gt; +inline bool approxEqual(const FloatPoint3D&amp; v0, const FloatPoint3D&amp; v1)
&gt; &gt; +{
&gt; &gt; +    return (v0 - v1).lengthSquared() &lt; ImplementationEpsilon * ImplementationEpsilon;
&gt; &gt; +}
&gt; &gt; +
&gt; &gt; +inline bool approxEqual(float f0, float f1)
&gt; &gt; +{
&gt; &gt; +    return fabsf(f0 - f1) &lt; ImplementationEpsilon;
&gt; &gt; +}
&gt; Why not move the bodies of all of these functions over to the .cpp and not mention ImplementationEpsilon at all in the header?  The implementations will get inlined by an optimizing linker anyway.

OK, I&apos;ve moved these to the .cpp.</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>276893</commentid>
    <comment_count>8</comment_count>
      <attachid>67128</attachid>
    <who name="Kenneth Russell">kbr</who>
    <bug_when>2010-09-09 18:01:07 -0700</bug_when>
    <thetext>Created attachment 67128
Revised patch

Changed comment in findCubicExtrema per code review above.</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>276914</commentid>
    <comment_count>9</comment_count>
      <attachid>67128</attachid>
    <who name="James Robinson">jamesr</who>
    <bug_when>2010-09-09 18:28:42 -0700</bug_when>
    <thetext>Comment on attachment 67128
Revised patch

Almost there!

View in context: https://bugs.webkit.org/attachment.cgi?id=67128&amp;action=prettypatch

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:80
&gt; +bool edgeAgainstTriEdges(const FloatPoint&amp; v0,
nit: edgeAgainstTriEdges -&gt; edgeAgainstTriangleEdges() or something else without an abbreviation.

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:335
&gt; +    if (numerator &lt; 0) {
&gt; +        // Make the &quot;numerator &gt;= denominator&quot; check below work.
&gt; +        numerator = -numerator;
&gt; +        denominator = -denominator;
&gt; +    }
&gt; +    if (!numerator || !denominator || numerator &gt;= denominator)
nit: maybe change the check to fabs(numerator) &gt;= fabs(denominator) instead of flipping?

&gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:378
&gt; +    float* r = roots;
&gt; +    if (safeUnitDivide(q, a, *r))
&gt; +        ++r;
&gt; +    if (safeUnitDivide(c, q, *r))
&gt; +        ++r;
&gt; +    if (r - roots == 2) {
&gt; +        // Seemingly have two roots. Check for equality and sort.
&gt; +        if (roots[0] == roots[1])
&gt; +            return 1;
&gt; +        if (roots[0] &gt; roots[1])
&gt; +            std::swap(roots[0], roots[1]);
&gt; +    }
&gt; +    return r - roots;
This section looks worlds better now - thanks for tackling it.  One more thing, thought: instead of having r be a float* and using pointer math, this would be done better by keeping a numRoots count and using that to index into roots[].  The pointer math logic is tricky and the result of (float* - float*) will not necessarily fit into an int on a system with 64 bit pointers and 32 bit ints, so this may generate warnings.</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>276928</commentid>
    <comment_count>10</comment_count>
      <attachid>67134</attachid>
    <who name="Kenneth Russell">kbr</who>
    <bug_when>2010-09-09 18:44:36 -0700</bug_when>
    <thetext>Created attachment 67134
Revised patch

Addressed above review feedback.</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>276929</commentid>
    <comment_count>11</comment_count>
    <who name="Kenneth Russell">kbr</who>
    <bug_when>2010-09-09 18:45:42 -0700</bug_when>
    <thetext>(In reply to comment #9)
&gt; (From update of attachment 67128 [details])
&gt; Almost there!
&gt; 
&gt; View in context: https://bugs.webkit.org/attachment.cgi?id=67128&amp;action=prettypatch
&gt; 
&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:80
&gt; &gt; +bool edgeAgainstTriEdges(const FloatPoint&amp; v0,
&gt; nit: edgeAgainstTriEdges -&gt; edgeAgainstTriangleEdges() or something else without an abbreviation.

Renamed.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:335
&gt; &gt; +    if (numerator &lt; 0) {
&gt; &gt; +        // Make the &quot;numerator &gt;= denominator&quot; check below work.
&gt; &gt; +        numerator = -numerator;
&gt; &gt; +        denominator = -denominator;
&gt; &gt; +    }
&gt; &gt; +    if (!numerator || !denominator || numerator &gt;= denominator)
&gt; nit: maybe change the check to fabs(numerator) &gt;= fabs(denominator) instead of flipping?

This is not the same test and would defeat some of the assertions. I&apos;m leaving this as is.

&gt; &gt; WebCore/platform/graphics/gpu/LoopBlinnMathUtils.cpp:378
&gt; &gt; +    float* r = roots;
&gt; &gt; +    if (safeUnitDivide(q, a, *r))
&gt; &gt; +        ++r;
&gt; &gt; +    if (safeUnitDivide(c, q, *r))
&gt; &gt; +        ++r;
&gt; &gt; +    if (r - roots == 2) {
&gt; &gt; +        // Seemingly have two roots. Check for equality and sort.
&gt; &gt; +        if (roots[0] == roots[1])
&gt; &gt; +            return 1;
&gt; &gt; +        if (roots[0] &gt; roots[1])
&gt; &gt; +            std::swap(roots[0], roots[1]);
&gt; &gt; +    }
&gt; &gt; +    return r - roots;
&gt; This section looks worlds better now - thanks for tackling it.  One more thing, thought: instead of having r be a float* and using pointer math, this would be done better by keeping a numRoots count and using that to index into roots[].  The pointer math logic is tricky and the result of (float* - float*) will not necessarily fit into an int on a system with 64 bit pointers and 32 bit ints, so this may generate warnings.

OK, I&apos;ve changed this to use an explicit &quot;int numberOfRoots&quot; local variable.</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>276931</commentid>
    <comment_count>12</comment_count>
      <attachid>67134</attachid>
    <who name="James Robinson">jamesr</who>
    <bug_when>2010-09-09 18:47:39 -0700</bug_when>
    <thetext>Comment on attachment 67134
Revised patch

R=me</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>276954</commentid>
    <comment_count>13</comment_count>
    <who name="Kenneth Russell">kbr</who>
    <bug_when>2010-09-09 19:32:18 -0700</bug_when>
    <thetext>Committed r67150: &lt;http://trac.webkit.org/changeset/67150&gt;</thetext>
  </long_desc><long_desc isprivate="0" >
    <commentid>276973</commentid>
    <comment_count>14</comment_count>
    <who name="WebKit Review Bot">webkit.review.bot</who>
    <bug_when>2010-09-09 20:10:40 -0700</bug_when>
    <thetext>http://trac.webkit.org/changeset/67150 might have broken Chromium Mac Release
The following changes are on the blame list:
http://trac.webkit.org/changeset/67152
http://trac.webkit.org/changeset/67149
http://trac.webkit.org/changeset/67150
http://trac.webkit.org/changeset/67151</thetext>
  </long_desc>
      
          <attachment
              isobsolete="1"
              ispatch="1"
              isprivate="0"
          >
            <attachid>66610</attachid>
            <date>2010-09-05 22:40:18 -0700</date>
            <delta_ts>2010-09-09 12:47:18 -0700</delta_ts>
            <desc>Patch</desc>
            <filename>math-utils.patch</filename>
            <type>text/plain</type>
            <size>25097</size>
            <attacher name="Kenneth Russell">kbr</attacher>
            
              <data encoding="base64">SW5kZXg6IFdlYkNvcmUvQ2hhbmdlTG9nCj09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09
PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0KLS0tIFdlYkNvcmUvQ2hhbmdlTG9n
CShyZXZpc2lvbiA2NjgwOSkKKysrIFdlYkNvcmUvQ2hhbmdlTG9nCSh3b3JraW5nIGNvcHkpCkBA
IC0xLDMgKzEsMjUgQEAKKzIwMTAtMDktMDUgIEtlbm5ldGggUnVzc2VsbCAgPGtickBnb29nbGUu
Y29tPgorCisgICAgICAgIFJldmlld2VkIGJ5IE5PQk9EWSAoT09QUyEpLgorCisgICAgICAgIEFk
ZCBtYXRoIHV0aWxpdGllcyBmb3IgY3ViaWMgY3VydmUgcHJvY2Vzc2luZworICAgICAgICBodHRw
czovL2J1Z3Mud2Via2l0Lm9yZy9zaG93X2J1Zy5jZ2k/aWQ9NDUyNTEKKworICAgICAgICBBZGRp
bmcgbWF0aGVtYXRpYyB1dGlsaXRpZXMgbmVlZGVkIGZvciB0aGUgR1BVIGFjY2VsZXJhdGVkIHBh
dGgKKyAgICAgICAgcmVuZGVyaW5nIGFsZ29yaXRobSBmcm9tIEdQVSBHZW1zIDMuIE5vIHRlc3Rz
IHlldDsgd2lsbCBiZSB0ZXN0ZWQKKyAgICAgICAgaW4gY29uanVuY3Rpb24gd2l0aCBsYXRlciBj
b2RlLgorCisgICAgICAgICogcGxhdGZvcm0vZ3JhcGhpY3MvZ3B1L0xvb3BCbGlubk1hdGhVdGls
cy5jcHA6IEFkZGVkLgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxzOjpsaW5l
c0ludGVyc2VjdCk6CisgICAgICAgIChXZWJDb3JlOjpMb29wQmxpbm5NYXRoVXRpbHM6OnBvaW50
SW5UcmlhbmdsZSk6CisgICAgICAgIChXZWJDb3JlOjpMb29wQmxpbm5NYXRoVXRpbHM6OnRyaWFu
Z2xlc092ZXJsYXApOgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxzOjpjaG9w
Q3ViaWNBdCk6CisgICAgICAgIChXZWJDb3JlOjpMb29wQmxpbm5NYXRoVXRpbHM6OnhSYXlDcm9z
c2VzTGluZSk6CisgICAgICAgIChXZWJDb3JlOjpMb29wQmxpbm5NYXRoVXRpbHM6Om51bVhSYXlD
cm9zc2luZ3NGb3JDdWJpYyk6CisgICAgICAgICogcGxhdGZvcm0vZ3JhcGhpY3MvZ3B1L0xvb3BC
bGlubk1hdGhVdGlscy5oOiBBZGRlZC4KKyAgICAgICAgKFdlYkNvcmU6Okxvb3BCbGlubk1hdGhV
dGlsczo6cm91bmRUb1plcm8pOgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxz
OjphcHByb3hFcXVhbCk6CisKIDIwMTAtMDktMDUgIEtlbm5ldGggUnVzc2VsbCAgPGtickBnb29n
bGUuY29tPgogCiAgICAgICAgIFJldmlld2VkIGJ5IERhcmluIEZpc2hlci4KSW5kZXg6IFdlYkNv
cmUvcGxhdGZvcm0vZ3JhcGhpY3MvZ3B1L0xvb3BCbGlubk1hdGhVdGlscy5jcHAKPT09PT09PT09
PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09
PQotLS0gV2ViQ29yZS9wbGF0Zm9ybS9ncmFwaGljcy9ncHUvTG9vcEJsaW5uTWF0aFV0aWxzLmNw
cAkocmV2aXNpb24gMCkKKysrIFdlYkNvcmUvcGxhdGZvcm0vZ3JhcGhpY3MvZ3B1L0xvb3BCbGlu
bk1hdGhVdGlscy5jcHAJKHJldmlzaW9uIDApCkBAIC0wLDAgKzEsNTU1IEBACisvKgorICogQ29w
eXJpZ2h0IChDKSAyMDEwIEdvb2dsZSBJbmMuIEFsbCByaWdodHMgcmVzZXJ2ZWQuCisgKgorICog
UmVkaXN0cmlidXRpb24gYW5kIHVzZSBpbiBzb3VyY2UgYW5kIGJpbmFyeSBmb3Jtcywgd2l0aCBv
ciB3aXRob3V0CisgKiBtb2RpZmljYXRpb24sIGFyZSBwZXJtaXR0ZWQgcHJvdmlkZWQgdGhhdCB0
aGUgZm9sbG93aW5nIGNvbmRpdGlvbnMKKyAqIGFyZSBtZXQ6CisgKgorICogMS4gIFJlZGlzdHJp
YnV0aW9ucyBvZiBzb3VyY2UgY29kZSBtdXN0IHJldGFpbiB0aGUgYWJvdmUgY29weXJpZ2h0Cisg
KiAgICAgbm90aWNlLCB0aGlzIGxpc3Qgb2YgY29uZGl0aW9ucyBhbmQgdGhlIGZvbGxvd2luZyBk
aXNjbGFpbWVyLgorICogMi4gIFJlZGlzdHJpYnV0aW9ucyBpbiBiaW5hcnkgZm9ybSBtdXN0IHJl
cHJvZHVjZSB0aGUgYWJvdmUgY29weXJpZ2h0CisgKiAgICAgbm90aWNlLCB0aGlzIGxpc3Qgb2Yg
Y29uZGl0aW9ucyBhbmQgdGhlIGZvbGxvd2luZyBkaXNjbGFpbWVyIGluIHRoZQorICogICAgIGRv
Y3VtZW50YXRpb24gYW5kL29yIG90aGVyIG1hdGVyaWFscyBwcm92aWRlZCB3aXRoIHRoZSBkaXN0
cmlidXRpb24uCisgKgorICogVEhJUyBTT0ZUV0FSRSBJUyBQUk9WSURFRCBCWSBBUFBMRSBBTkQg
SVRTIENPTlRSSUJVVE9SUyAiQVMgSVMiIEFORCBBTlkKKyAqIEVYUFJFU1MgT1IgSU1QTElFRCBX
QVJSQU5USUVTLCBJTkNMVURJTkcsIEJVVCBOT1QgTElNSVRFRCBUTywgVEhFIElNUExJRUQKKyAq
IFdBUlJBTlRJRVMgT0YgTUVSQ0hBTlRBQklMSVRZIEFORCBGSVRORVNTIEZPUiBBIFBBUlRJQ1VM
QVIgUFVSUE9TRSBBUkUKKyAqIERJU0NMQUlNRUQuIElOIE5PIEVWRU5UIFNIQUxMIEFQUExFIE9S
IElUUyBDT05UUklCVVRPUlMgQkUgTElBQkxFIEZPUiBBTlkKKyAqIERJUkVDVCwgSU5ESVJFQ1Qs
IElOQ0lERU5UQUwsIFNQRUNJQUwsIEVYRU1QTEFSWSwgT1IgQ09OU0VRVUVOVElBTCBEQU1BR0VT
CisgKiAoSU5DTFVESU5HLCBCVVQgTk9UIExJTUlURUQgVE8sIFBST0NVUkVNRU5UIE9GIFNVQlNU
SVRVVEUgR09PRFMgT1IgU0VSVklDRVM7CisgKiBMT1NTIE9GIFVTRSwgREFUQSwgT1IgUFJPRklU
UzsgT1IgQlVTSU5FU1MgSU5URVJSVVBUSU9OKSBIT1dFVkVSIENBVVNFRCBBTkQKKyAqIE9OIEFO
WSBUSEVPUlkgT0YgTElBQklMSVRZLCBXSEVUSEVSIElOIENPTlRSQUNULCBTVFJJQ1QgTElBQklM
SVRZLCBPUiBUT1JUCisgKiAoSU5DTFVESU5HIE5FR0xJR0VOQ0UgT1IgT1RIRVJXSVNFKSBBUklT
SU5HIElOIEFOWSBXQVkgT1VUIE9GIFRIRSBVU0UgT0YKKyAqIFRISVMgU09GVFdBUkUsIEVWRU4g
SUYgQURWSVNFRCBPRiBUSEUgUE9TU0lCSUxJVFkgT0YgU1VDSCBEQU1BR0UuCisgKi8KKworI2lu
Y2x1ZGUgImNvbmZpZy5oIgorCisjaW5jbHVkZSAiTG9vcEJsaW5uTWF0aFV0aWxzLmgiCisKKyNp
bmNsdWRlICJGbG9hdFBvaW50LmgiCisjaW5jbHVkZSAiTWF0aEV4dHJhcy5oIgorI2luY2x1ZGUg
PGFsZ29yaXRobT4KKyNpbmNsdWRlIDxzdHJpbmcuaD4gLy8gZm9yIG1lbWNweQorCituYW1lc3Bh
Y2UgV2ViQ29yZSB7CituYW1lc3BhY2UgTG9vcEJsaW5uTWF0aFV0aWxzIHsKKworbmFtZXNwYWNl
IHsKKworLy8gVXRpbGl0eSBmdW5jdGlvbnMgbG9jYWwgdG8gdGhpcyBmaWxlLgoraW50IG9yaWVu
dGF0aW9uKGNvbnN0IEZsb2F0UG9pbnQmIHAxLAorICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0
UG9pbnQmIHAyLAorICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIHAzKQoreworICAg
IGZsb2F0IGNyb3NzUHJvZHVjdCA9IChwMi55KCkgLSBwMS55KCkpICogKHAzLngoKSAtIHAyLngo
KSkgLSAocDMueSgpIC0gcDIueSgpKSAqIChwMi54KCkgLSBwMS54KCkpOworICAgIHJldHVybiAo
Y3Jvc3NQcm9kdWN0IDwgMC4wZikgPyAtMSA6ICgoY3Jvc3NQcm9kdWN0ID4gMC4wZikgPyAxIDog
MCk7Cit9CisKK2Jvb2wgZWRnZUVkZ2VUZXN0KGNvbnN0IEZsb2F0U2l6ZSYgdjBEZWx0YSwKKyAg
ICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIHYwLAorICAgICAgICAgICAgICAgICAg
Y29uc3QgRmxvYXRQb2ludCYgdTAsCisgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50
JiB1MSkKK3sKKyAgICAvLyBUaGlzIGVkZ2UgdG8gZWRnZSB0ZXN0IGlzIGJhc2VkIG9uIEZyYW5s
aW4gQW50b25pbydzIGdlbTogIkZhc3RlcgorICAgIC8vIExpbmUgU2VnbWVudCBJbnRlcnNlY3Rp
b24iLCBpbiBHcmFwaGljcyBHZW1zIElJSSwgcHAuIDE5OS0yMDIuCisgICAgZmxvYXQgYXggPSB2
MERlbHRhLndpZHRoKCk7CisgICAgZmxvYXQgYXkgPSB2MERlbHRhLmhlaWdodCgpOworICAgIGZs
b2F0IGJ4ID0gdTAueCgpIC0gdTEueCgpOworICAgIGZsb2F0IGJ5ID0gdTAueSgpIC0gdTEueSgp
OworICAgIGZsb2F0IGN4ID0gdjAueCgpIC0gdTAueCgpOworICAgIGZsb2F0IGN5ID0gdjAueSgp
IC0gdTAueSgpOworICAgIGZsb2F0IGYgPSBheSAqIGJ4IC0gYXggKiBieTsKKyAgICBmbG9hdCBk
ID0gYnkgKiBjeCAtIGJ4ICogY3k7CisgICAgaWYgKChmID4gMCAmJiBkID49IDAgJiYgZCA8PSBm
KSB8fCAoZiA8IDAgJiYgZCA8PSAwICYmIGQgPj0gZikpIHsKKyAgICAgICAgZmxvYXQgZSA9IGF4
ICogY3kgLSBheSAqIGN4OworCisgICAgICAgIC8vIFRoaXMgYWRkaXRpb25hbCB0ZXN0IGF2b2lk
cyByZXBvcnRpbmcgY29pbmNpZGVudCBlZGdlcywgd2hpY2gKKyAgICAgICAgLy8gaXMgdGhlIGJl
aGF2aW9yIHdlIHdhbnQuCisgICAgICAgIGlmIChhcHByb3hFcXVhbChlLCAwKSB8fCBhcHByb3hF
cXVhbChmLCAwKSB8fCBhcHByb3hFcXVhbChlLCBmKSkKKyAgICAgICAgICAgIHJldHVybiBmYWxz
ZTsKKworICAgICAgICBpZiAoZiA+IDApCisgICAgICAgICAgICByZXR1cm4gZSA+PSAwICYmIGUg
PD0gZjsKKworICAgICAgICByZXR1cm4gZSA8PSAwICYmIGUgPj0gZjsKKyAgICB9CisgICAgcmV0
dXJuIGZhbHNlOworfQorCitib29sIGVkZ2VBZ2FpbnN0VHJpRWRnZXMoY29uc3QgRmxvYXRQb2lu
dCYgdjAsCisgICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgdjEsCisg
ICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgdTAsCisgICAgICAgICAg
ICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgdTEsCisgICAgICAgICAgICAgICAgICAg
ICAgICAgY29uc3QgRmxvYXRQb2ludCYgdTIpCit7CisgICAgRmxvYXRTaXplIGRlbHRhID0gdjEg
LSB2MDsKKyAgICAvLyBUZXN0IGVkZ2UgdTAsIHUxIGFnYWluc3QgdjAsIHYxLgorICAgIGlmIChl
ZGdlRWRnZVRlc3QoZGVsdGEsIHYwLCB1MCwgdTEpKQorICAgICAgICByZXR1cm4gdHJ1ZTsKKyAg
ICAvLyBUZXN0IGVkZ2UgdTEsIHUyIGFnYWluc3QgdjAsIHYxLgorICAgIGlmIChlZGdlRWRnZVRl
c3QoZGVsdGEsIHYwLCB1MSwgdTIpKQorICAgICAgICByZXR1cm4gdHJ1ZTsKKyAgICAvLyBUZXN0
IGVkZ2UgdTIsIHUxIGFnYWluc3QgdjAsIHYxLgorICAgIGlmIChlZGdlRWRnZVRlc3QoZGVsdGEs
IHYwLCB1MiwgdTApKQorICAgICAgICByZXR1cm4gdHJ1ZTsKKyAgICByZXR1cm4gZmFsc2U7Cit9
CisKK30gLy8gYW5vbnltb3VzIG5hbWVzcGFjZQorCisvLyBFeHBvcnRlZCByb3V0aW5lcworCiti
b29sIGxpbmVzSW50ZXJzZWN0KGNvbnN0IEZsb2F0UG9pbnQmIHAxLAorICAgICAgICAgICAgICAg
ICAgICBjb25zdCBGbG9hdFBvaW50JiBxMSwKKyAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxv
YXRQb2ludCYgcDIsCisgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIHEyKQor
eworICAgIHJldHVybiAob3JpZW50YXRpb24ocDEsIHExLCBwMikgIT0gb3JpZW50YXRpb24ocDEs
IHExLCBxMikKKyAgICAgICAgICAgICYmIG9yaWVudGF0aW9uKHAyLCBxMiwgcDEpICE9IG9yaWVu
dGF0aW9uKHAyLCBxMiwgcTEpKTsKK30KKworYm9vbCBwb2ludEluVHJpYW5nbGUoY29uc3QgRmxv
YXRQb2ludCYgcG9pbnQsCisgICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBh
LAorICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgYiwKKyAgICAgICAgICAg
ICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIGMpCit7CisgICAgLy8gQWxnb3JpdGhtIGZyb20g
aHR0cDovL3d3dy5ibGFja3Bhd24uY29tL3RleHRzL3BvaW50aW5wb2x5L2RlZmF1bHQuaHRtbAor
ICAgIGZsb2F0IHgwID0gYy54KCkgLSBhLngoKTsKKyAgICBmbG9hdCB5MCA9IGMueSgpIC0gYS55
KCk7CisgICAgZmxvYXQgeDEgPSBiLngoKSAtIGEueCgpOworICAgIGZsb2F0IHkxID0gYi55KCkg
LSBhLnkoKTsKKyAgICBmbG9hdCB4MiA9IHBvaW50LngoKSAtIGEueCgpOworICAgIGZsb2F0IHky
ID0gcG9pbnQueSgpIC0gYS55KCk7CisKKyAgICBmbG9hdCBkb3QwMCA9IHgwICogeDAgKyB5MCAq
IHkwOworICAgIGZsb2F0IGRvdDAxID0geDAgKiB4MSArIHkwICogeTE7CisgICAgZmxvYXQgZG90
MDIgPSB4MCAqIHgyICsgeTAgKiB5MjsKKyAgICBmbG9hdCBkb3QxMSA9IHgxICogeDEgKyB5MSAq
IHkxOworICAgIGZsb2F0IGRvdDEyID0geDEgKiB4MiArIHkxICogeTI7CisgICAgZmxvYXQgZGVu
b20gPSBkb3QwMCAqIGRvdDExIC0gZG90MDEgKiBkb3QwMTsKKyAgICBpZiAoIWRlbm9tKQorICAg
ICAgICAvLyBUcmlhbmdsZSBpcyB6ZXJvLWFyZWEuIFRyZWF0IHF1ZXJ5IHBvaW50IGFzIG5vdCBi
ZWluZyBpbnNpZGUuCisgICAgICAgIHJldHVybiBmYWxzZTsKKyAgICAvLyBDb21wdXRlCisgICAg
ZmxvYXQgaW52RGVub20gPSAxLjBmIC8gZGVub207CisgICAgZmxvYXQgdSA9IChkb3QxMSAqIGRv
dDAyIC0gZG90MDEgKiBkb3QxMikgKiBpbnZEZW5vbTsKKyAgICBmbG9hdCB2ID0gKGRvdDAwICog
ZG90MTIgLSBkb3QwMSAqIGRvdDAyKSAqIGludkRlbm9tOworCisgICAgcmV0dXJuICh1ID4gMC4w
ZikgJiYgKHYgPiAwLjBmKSAmJiAodSArIHYgPCAxLjBmKTsKK30KKworYm9vbCB0cmlhbmdsZXNP
dmVybGFwKGNvbnN0IEZsb2F0UG9pbnQmIGExLAorICAgICAgICAgICAgICAgICAgICAgIGNvbnN0
IEZsb2F0UG9pbnQmIGIxLAorICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQm
IGMxLAorICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIGEyLAorICAgICAg
ICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIGIyLAorICAgICAgICAgICAgICAgICAg
ICAgIGNvbnN0IEZsb2F0UG9pbnQmIGMyKQoreworICAgIC8vIERlcml2ZWQgZnJvbSBjb3BsYW5h
cl90cmlfdHJpKCkgYXQKKyAgICAvLyBodHRwOi8vamd0LmFrcGV0ZXJzLmNvbS9wYXBlcnMvU2hl
bkhlbmdUYW5nMDMvdHJpX3RyaS5odG1sICwKKyAgICAvLyBzaW1wbGlmaWVkIGZvciB0aGUgMkQg
Y2FzZSBhbmQgbW9kaWZpZWQgc28gdGhhdCBvdmVybGFwcGluZyBlZGdlcworICAgIC8vIGRvIG5v
dCByZXBvcnQgb3ZlcmxhcHBpbmcgdHJpYW5nbGVzLgorCisgICAgLy8gVGVzdCBhbGwgZWRnZXMg
b2YgdHJpYW5nbGUgMSBhZ2FpbnN0IHRoZSBlZGdlcyBvZiB0cmlhbmdsZSAyLgorICAgIGlmIChl
ZGdlQWdhaW5zdFRyaUVkZ2VzKGExLCBiMSwgYTIsIGIyLCBjMikKKyAgICAgICAgfHwgZWRnZUFn
YWluc3RUcmlFZGdlcyhiMSwgYzEsIGEyLCBiMiwgYzIpCisgICAgICAgIHx8IGVkZ2VBZ2FpbnN0
VHJpRWRnZXMoYzEsIGExLCBhMiwgYjIsIGMyKSkKKyAgICAgICAgcmV0dXJuIHRydWU7CisgICAg
Ly8gRmluYWxseSwgdGVzdCBpZiB0cmkxIGlzIHRvdGFsbHkgY29udGFpbmVkIGluIHRyaTIgb3Ig
dmljZSB2ZXJzYS4KKyAgICBpZiAocG9pbnRJblRyaWFuZ2xlKGExLCBhMiwgYjIsIGMyKQorICAg
ICAgICB8fCBwb2ludEluVHJpYW5nbGUoYTIsIGExLCBiMSwgYzEpKQorICAgICAgICByZXR1cm4g
dHJ1ZTsKKworICAgIC8vIEJlY2F1c2Ugd2UgZGVmaW5lIHRoYXQgdHJpYW5nbGVzIHNoYXJpbmcg
YSB2ZXJ0ZXggb3IgZWRnZSBkb24ndAorICAgIC8vIG92ZXJsYXAsIHdlIG11c3QgcGVyZm9ybSBh
ZGRpdGlvbmFsIHBvaW50LWluLXRyaWFuZ2xlIHRlc3RzIHRvCisgICAgLy8gc2VlIHdoZXRoZXIg
b25lIHRyaWFuZ2xlIGlzIGNvbnRhaW5lZCBpbiB0aGUgb3RoZXIuCisgICAgaWYgKHBvaW50SW5U
cmlhbmdsZShiMSwgYTIsIGIyLCBjMikKKyAgICAgICAgfHwgcG9pbnRJblRyaWFuZ2xlKGMxLCBh
MiwgYjIsIGMyKQorICAgICAgICB8fCBwb2ludEluVHJpYW5nbGUoYjIsIGExLCBiMSwgYzEpCisg
ICAgICAgIHx8IHBvaW50SW5UcmlhbmdsZShjMiwgYTEsIGIxLCBjMSkpCisgICAgICAgIHJldHVy
biB0cnVlOworICAgIHJldHVybiBmYWxzZTsKK30KKworbmFtZXNwYWNlIHsKKworLy8gSGVscGVy
IHJvdXRpbmVzIGZvciBwdWJsaWMgWFJheSBxdWVyaWVzIGJlbG93LgorCitjb25zdCBmbG9hdCBO
ZWFybHlaZXJvQ29uc3RhbnQgPSAoMS4wZiAvICgxIDw8IDEyKSk7CisKK2Jvb2wgbmVhcmx5WmVy
byhmbG9hdCB4LCBmbG9hdCB0b2xlcmFuY2UgPSBOZWFybHlaZXJvQ29uc3RhbnQpCit7CisgICAg
QVNTRVJUKHRvbGVyYW5jZSA+IDAuMCk7CisgICAgcmV0dXJuIDo6ZmFic2YoeCkgPCB0b2xlcmFu
Y2U7Cit9CisKKy8vIExpbmVhcmx5IGludGVycG9sYXRlIGJldHdlZW4gYSBhbmQgYiwgYmFzZWQg
b24gdC4KKy8vIElmIHQgaXMgMCwgcmV0dXJuIGE7IGlmIHQgaXMgMSwgcmV0dXJuIGI7IGVsc2Ug
aW50ZXJwb2xhdGUuCisvLyB0IG11c3QgYmUgWzAuLjFdLgoraW5saW5lIGZsb2F0IGludGVycG9s
YXRlKGZsb2F0IGEsIGZsb2F0IGIsIGZsb2F0IHQpCit7CisgICAgQVNTRVJUKHQgPj0gMCAmJiB0
IDw9IDEpOworICAgIHJldHVybiBhICsgKGIgLSBhKSAqIHQ7Cit9CisKK2Zsb2F0IGV2YWx1YXRl
Q3ViaWMoZmxvYXQgczAsIGZsb2F0IHMyLCBmbG9hdCBzNCwgZmxvYXQgczYsIGZsb2F0IHQpCit7
CisgICAgQVNTRVJUKHQgPj0gMCAmJiB0IDw9IDEpOworCisgICAgaWYgKCF0KQorICAgICAgICBy
ZXR1cm4gczA7CisKKyAgICBmbG9hdCBhYiA9IGludGVycG9sYXRlKHMwLCBzMiwgdCk7CisgICAg
ZmxvYXQgYmMgPSBpbnRlcnBvbGF0ZShzMiwgczQsIHQpOworICAgIGZsb2F0IGNkID0gaW50ZXJw
b2xhdGUoczQsIHM2LCB0KTsKKyAgICBmbG9hdCBhYmMgPSBpbnRlcnBvbGF0ZShhYiwgYmMsIHQp
OworICAgIGZsb2F0IGJjZCA9IGludGVycG9sYXRlKGJjLCBjZCwgdCk7CisgICAgcmV0dXJuIGlu
dGVycG9sYXRlKGFiYywgYmNkLCB0KTsKK30KKworLy8gU2V0IHB0IHRvIHRoZSBwb2ludCBvbiB0
aGUgc291cmNlIGN1YmljIHNwZWNpZmllZCBieSB0LgorLy8gdCBtdXN0IGJlIDAgPD0gdCA8PSAx
LjAuCitib29sIGV2YWx1YXRlQ3ViaWNBdChjb25zdCBGbG9hdFBvaW50IGN1YmljWzRdLCBmbG9h
dCB0LCBGbG9hdFBvaW50JiBwdCkKK3sKKyAgICBwdC5zZXQoZXZhbHVhdGVDdWJpYyhjdWJpY1sw
XS54KCksIGN1YmljWzFdLngoKSwgY3ViaWNbMl0ueCgpLCBjdWJpY1szXS54KCksIHQpLAorICAg
ICAgICAgICBldmFsdWF0ZUN1YmljKGN1YmljWzBdLnkoKSwgY3ViaWNbMV0ueSgpLCBjdWJpY1sy
XS55KCksIGN1YmljWzNdLnkoKSwgdCkpOworfQorCitib29sIHhSYXlDcm9zc2VzTW9ub3Rvbmlj
Q3ViaWMoY29uc3QgWFJheSYgeFJheSwgY29uc3QgRmxvYXRQb2ludCBjdWJpY1s0XSwgYm9vbCYg
YW1iaWd1b3VzKQoreworICAgIGFtYmlndW91cyA9IGZhbHNlOworCisgICAgLy8gRmluZCB0aGUg
bWluaW11bSBhbmQgbWF4aW11bSB5IG9mIHRoZSBleHRyZW1hLCB3aGljaCBhcmUgdGhlCisgICAg
Ly8gZmlyc3QgYW5kIGxhc3QgcG9pbnRzIHNpbmNlIHRoaXMgY3ViaWMgaXMgbW9ub3RvbmljCisg
ICAgZmxvYXQgbWluWSA9IHN0ZDo6bWluKGN1YmljWzBdLnkoKSwgY3ViaWNbM10ueSgpKTsKKyAg
ICBmbG9hdCBtYXhZID0gc3RkOjptYXgoY3ViaWNbMF0ueSgpLCBjdWJpY1szXS55KCkpOworCisg
ICAgaWYgKHhSYXkueSgpID09IGN1YmljWzBdLnkoKQorICAgICAgICB8fCB4UmF5LnkoKSA8IG1p
blkKKyAgICAgICAgfHwgeFJheS55KCkgPiBtYXhZKSB7CisgICAgICAgIC8vIFRoZSBxdWVyeSBs
aW5lIGRlZmluaXRlbHkgZG9lcyBub3QgY3Jvc3MgdGhlIGN1cnZlCisgICAgICAgIGFtYmlndW91
cyA9ICh4UmF5LnkoKSA9PSBjdWJpY1swXS55KCkpOworICAgICAgICByZXR1cm4gZmFsc2U7Cisg
ICAgfQorCisgICAgY29uc3QgYm9vbCBwb2ludEF0RXh0cmVtdW0gPSAoeFJheS55KCkgPT0gY3Vi
aWNbM10ueSgpKTsKKworICAgIGZsb2F0IG1pblggPSBzdGQ6Om1pbihzdGQ6Om1pbihzdGQ6Om1p
bihjdWJpY1swXS54KCksIGN1YmljWzFdLngoKSksCisgICAgICAgICAgICAgICAgICAgICAgICAg
ICAgICAgICAgIGN1YmljWzJdLngoKSksCisgICAgICAgICAgICAgICAgICAgICAgICAgIGN1Ymlj
WzNdLngoKSk7CisgICAgaWYgKHhSYXkueCgpIDwgbWluWCkgeworICAgICAgICAvLyBUaGUgcXVl
cnkgbGluZSBkZWZpbml0ZWx5IGNyb3NzZXMgdGhlIGN1cnZlCisgICAgICAgIGFtYmlndW91cyA9
IHBvaW50QXRFeHRyZW11bTsKKyAgICAgICAgcmV0dXJuIHRydWU7CisgICAgfQorCisgICAgZmxv
YXQgbWF4WCA9IHN0ZDo6bWF4KHN0ZDo6bWF4KHN0ZDo6bWF4KGN1YmljWzBdLngoKSwgY3ViaWNb
MV0ueCgpKSwKKyAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY3ViaWNbMl0ueCgp
KSwKKyAgICAgICAgICAgICAgICAgICAgICAgICAgY3ViaWNbM10ueCgpKTsKKyAgICBpZiAoeFJh
eS54KCkgPiBtYXhYKQorICAgICAgICAvLyBUaGUgcXVlcnkgbGluZSBkZWZpbml0ZWx5IGRvZXMg
bm90IGNyb3NzIHRoZSBjdXJ2ZQorICAgICAgICByZXR1cm4gZmFsc2U7CisKKyAgICAvLyBEbyBh
IGJpbmFyeSBzZWFyY2ggdG8gZmluZCB0aGUgcGFyYW1ldGVyIHZhbHVlIHdoaWNoIG1ha2VzIHkg
YXMKKyAgICAvLyBjbG9zZSBhcyBwb3NzaWJsZSB0byB0aGUgcXVlcnkgcG9pbnQuIFNlZSB3aGV0
aGVyIHRoZSBxdWVyeQorICAgIC8vIGxpbmUncyBvcmlnaW4gaXMgdG8gdGhlIGxlZnQgb2YgdGhl
IGFzc29jaWF0ZWQgeCBjb29yZGluYXRlLgorCisgICAgLy8gTWF4SXRlciBpcyBjaG9zZW4gYXMg
dGhlIG51bWJlciBvZiBtYW50aXNzYSBiaXRzIGZvciBhIGZsb2F0LAorICAgIC8vIHNpbmNlIHRo
ZXJlJ3Mgbm8gd2F5IHdlIGFyZSBnb2luZyB0byBnZXQgbW9yZSBwcmVjaXNpb24gYnkKKyAgICAv
LyBpdGVyYXRpbmcgbW9yZSB0aW1lcyB0aGFuIHRoYXQuCisgICAgY29uc3QgaW50IE1heEl0ZXIg
PSAyMzsKKyAgICBGbG9hdFBvaW50IGV2YWx1YXRlOworICAgIGludCBpdGVyID0gMDsKKyAgICBm
bG9hdCB1cHBlclQ7CisgICAgZmxvYXQgbG93ZXJUOworICAgIC8vIE5lZWQgdG8gaW52ZXJ0IGRp
cmVjdGlvbiBvZiB0IHBhcmFtZXRlciBpZiBjdWJpYyBnb2VzIHVwCisgICAgLy8gaW5zdGVhZCBv
ZiBkb3duCisgICAgaWYgKGN1YmljWzNdLnkoKSA+IGN1YmljWzBdLnkoKSkgeworICAgICAgICB1
cHBlclQgPSAxOworICAgICAgICBsb3dlclQgPSAwOworICAgIH0gZWxzZSB7CisgICAgICAgIHVw
cGVyVCA9IDA7CisgICAgICAgIGxvd2VyVCA9IDE7CisgICAgfQorICAgIGRvIHsKKyAgICAgICAg
ZmxvYXQgdCA9IDAuNSAqICh1cHBlclQgKyBsb3dlclQpOworICAgICAgICBldmFsdWF0ZUN1Ymlj
QXQoY3ViaWMsIHQsIGV2YWx1YXRlKTsKKyAgICAgICAgaWYgKHhSYXkueSgpID4gZXZhbHVhdGUu
eSgpKQorICAgICAgICAgICAgbG93ZXJUID0gdDsKKyAgICAgICAgZWxzZQorICAgICAgICAgICAg
dXBwZXJUID0gdDsKKyAgICB9IHdoaWxlICgrK2l0ZXIgPCBNYXhJdGVyICYmICFuZWFybHlaZXJv
KGV2YWx1YXRlLnkoKSAtIHhSYXkueSgpKSk7CisKKyAgICBpZiAoeFJheS54KCkgPD0gZXZhbHVh
dGUueCgpKSB7CisgICAgICAgIGFtYmlndW91cyA9IHBvaW50QXRFeHRyZW11bTsKKyAgICAgICAg
cmV0dXJuIHRydWU7CisgICAgfQorICAgIHJldHVybiBmYWxzZTsKK30KKworaW50IHZhbGlkVW5p
dERpdmlkZShmbG9hdCBudW1lciwgZmxvYXQgZGVub20sIGZsb2F0KiByYXRpbykKK3sKKyAgICBB
U1NFUlQocmF0aW8pOworCisgICAgaWYgKG51bWVyIDwgMCkgeworICAgICAgICBudW1lciA9IC1u
dW1lcjsKKyAgICAgICAgZGVub20gPSAtZGVub207CisgICAgfQorCisgICAgaWYgKCFkZW5vbSB8
fCAhbnVtZXIgfHwgbnVtZXIgPj0gZGVub20pCisgICAgICAgIHJldHVybiAwOworCisgICAgZmxv
YXQgciA9IG51bWVyIC8gZGVub207CisgICAgaWYgKGlzbmFuKHIpKQorICAgICAgICByZXR1cm4g
MDsKKyAgICBBU1NFUlQociA+PSAwICYmIHIgPCAxKTsKKyAgICBpZiAoIXIpIC8vIGNhdGNoIHVu
ZGVyZmxvdyBpZiBudW1lciA8PDw8IGRlbm9tCisgICAgICAgIHJldHVybiAwOworICAgICpyYXRp
byA9IHI7CisgICAgcmV0dXJuIDE7Cit9CisKKy8qKiBGcm9tIE51bWVyaWNhbCBSZWNpcGVzIGlu
IEMuCisKKyAgICBxID0gLTEvMiAoYiArIHNpZ24oYikgc3FydFtiKmIgLSA0KmEqY10pCisgICAg
eDEgPSBxIC8gYQorICAgIHgyID0gYyAvIHEKKyovCitpbnQgZmluZFVuaXRRdWFkUm9vdHMoZmxv
YXQgYSwgZmxvYXQgYiwgZmxvYXQgYywgZmxvYXQgcm9vdHNbMl0pCit7CisgICAgaWYgKCFhKQor
ICAgICAgICByZXR1cm4gdmFsaWRVbml0RGl2aWRlKC1jLCBiLCByb290cyk7CisKKyAgICBmbG9h
dCogciA9IHJvb3RzOworCisgICAgZmxvYXQgUiA9IGIqYiAtIDQqYSpjOworICAgIGlmIChSIDwg
MCB8fCBpc25hbihSKSkgLy8gY29tcGxleCByb290cworICAgICAgICByZXR1cm4gMDsKKyAgICBS
ID0gc3FydGYoUik7CisKKyAgICBmbG9hdCBRID0gKGIgPCAwKSA/IC0oYiAtIFIpIC8gMiA6IC0o
YiArIFIpIC8gMjsKKyAgICByICs9IHZhbGlkVW5pdERpdmlkZShRLCBhLCByKTsKKyAgICByICs9
IHZhbGlkVW5pdERpdmlkZShjLCBRLCByKTsKKyAgICBpZiAociAtIHJvb3RzID09IDIpCisgICAg
ICAgIGlmIChyb290c1swXSA+IHJvb3RzWzFdKQorICAgICAgICAgICAgc3RkOjpzd2FwKHJvb3Rz
WzBdLCByb290c1sxXSk7CisgICAgICAgIGVsc2UgaWYgKHJvb3RzWzBdID09IHJvb3RzWzFdKSAv
LyBuZWFybHktZXF1YWw/CisgICAgICAgICAgICByIC09IDE7IC8vIHNraXAgdGhlIGRvdWJsZSBy
b290CisgICAgcmV0dXJuIChpbnQpKHIgLSByb290cyk7Cit9CisKKy8qKiBDdWJpYycodCkgPSBw
dF4yICsgcXQgKyByLCB3aGVyZQorICAgIHAgPSAzKC1hICsgMyhiIC0gYykgKyBkKQorICAgIHEg
PSA2KGEgLSAyYiArIGMpCisgICAgciA9IDMoYiAtIGEpCisgICAgU29sdmUgZm9yIHQsIGtlZXBp
bmcgb25seSB0aG9zZSB0aGF0IGZpdCBiZXR3ZWUgMCA8IHQgPCAxCisqLworaW50IGZpbmRDdWJp
Y0V4dHJlbWEoZmxvYXQgYSwgZmxvYXQgYiwgZmxvYXQgYywgZmxvYXQgZCwgZmxvYXQgdFZhbHVl
c1syXSkKK3sKKyAgICAvLyB3ZSBkaXZpZGUgcCwgcSwgYW5kIHIgYnkgMyB0byBzaW1wbGlmeQor
ICAgIGZsb2F0IHAgPSBkIC0gYSArIDMqKGIgLSBjKTsKKyAgICBmbG9hdCBxID0gMiooYSAtIGIg
LSBiICsgYyk7CisgICAgZmxvYXQgciA9IGIgLSBhOworCisgICAgcmV0dXJuIGZpbmRVbml0UXVh
ZFJvb3RzKHAsIHEsIHIsIHRWYWx1ZXMpOworfQorCit2b2lkIGludGVycG9sYXRlQ3ViaWNDb29y
ZHMoZmxvYXQgczAsIGZsb2F0IHMyLCBmbG9hdCBzNCwgZmxvYXQgczYsIGZsb2F0KiBkc3QsIGZs
b2F0IHQpCit7CisgICAgZmxvYXQgYWIgPSBpbnRlcnBvbGF0ZShzMCwgczIsIHQpOworICAgIGZs
b2F0IGJjID0gaW50ZXJwb2xhdGUoczIsIHM0LCB0KTsKKyAgICBmbG9hdCBjZCA9IGludGVycG9s
YXRlKHM0LCBzNiwgdCk7CisgICAgZmxvYXQgYWJjID0gaW50ZXJwb2xhdGUoYWIsIGJjLCB0KTsK
KyAgICBmbG9hdCBiY2QgPSBpbnRlcnBvbGF0ZShiYywgY2QsIHQpOworICAgIGZsb2F0IGFiY2Qg
PSBpbnRlcnBvbGF0ZShhYmMsIGJjZCwgdCk7CisKKyAgICBkc3RbMF0gPSBzMDsKKyAgICBkc3Rb
Ml0gPSBhYjsKKyAgICBkc3RbNF0gPSBhYmM7CisgICAgZHN0WzZdID0gYWJjZDsKKyAgICBkc3Rb
OF0gPSBiY2Q7CisgICAgZHN0WzEwXSA9IGNkOworICAgIGRzdFsxMl0gPSBzNjsKK30KKworI2lm
bmRlZiBOREVCVUcKK2Jvb2wgaXNVbml0SW50ZXJ2YWwoZmxvYXQgeCkKK3sKKyAgICByZXR1cm4g
eCA+IDAgJiYgeCA8IDE7Cit9CisjZW5kaWYKKworLyogIGh0dHA6Ly9jb2RlLmdvb2dsZS5jb20v
cC9za2lhL2lzc3Vlcy9kZXRhaWw/aWQ9MzIKKworICAgIFRoaXMgdGVzdCBjb2RlIHdvdWxkIGZh
aWwgd2hlbiB3ZSBkaWRuJ3QgY2hlY2sgdGhlIHJldHVybiByZXN1bHQgb2YKKyAgICB2YWxpZF91
bml0X2RpdmlkZSBpbiBTa0Nob3BDdWJpY0F0KC4uLiB0VmFsdWVzW10sIGludCByb290cykuIFRo
ZSByZWFzb24gaXMKKyAgICB0aGF0IGFmdGVyIHRoZSBmaXJzdCBjaG9wLCB0aGUgcGFyYW1ldGVy
cyB0byB2YWxpZF91bml0X2RpdmlkZSBhcmUgZXF1YWwKKyAgICAodGhhbmtzIHRvIGZpbml0ZSBm
bG9hdCBwcmVjaXNpb24gYW5kIHJvdW5kaW5nIGluIHRoZSBzdWJ0cmFjdHMpLiBUaHVzCisgICAg
ZXZlbiB0aG91Z2ggdGhlIDJuZCB0VmFsdWUgbG9va3MgPCAxLjAsIGFmdGVyIHdlIHJlbm9ybWFs
aXplIGl0LCB3ZSBlbmQKKyAgICB1cCB3aXRoIDEuMCwgaGVuY2UgdGhlIG5lZWQgdG8gY2hlY2sg
YW5kIGp1c3QgcmV0dXJuIHRoZSBsYXN0IGN1YmljIGFzCisgICAgYSBkZWdlbmVyYXRlIGNsdW1w
IG9mIDQgcG9pbnRzIGluIHRoZSBzYW1lIHBsYWNlLgorCisgICAgc3RhdGljIHZvaWQgdGVzdF9j
dWJpYygpIHsKKyAgICAgICAgU2tQb2ludCBzcmNbNF0gPSB7CisgICAgICAgICAgICB7IDU1Ni4y
NTAwMCwgNTIzLjAzMDAzIH0sCisgICAgICAgICAgICB7IDU1Ni4yMzk5OSwgNTIyLjk2MDAyIH0s
CisgICAgICAgICAgICB7IDU1Ni4yMTk5NywgNTIyLjg5MDAxIH0sCisgICAgICAgICAgICB7IDU1
Ni4yMTk5NywgNTIyLjgyMDAxIH0KKyAgICAgICAgfTsKKyAgICAgICAgU2tQb2ludCBkc3RbMTBd
OworICAgICAgICBTa1NjYWxhciB0dmFsW10gPSB7IDAuMzMzMzMzMzRmLCAwLjk5OTk5OTk0ZiB9
OworICAgICAgICBTa0Nob3BDdWJpY0F0KHNyYywgZHN0LCB0dmFsLCAyKTsKKyAgICB9CisqLwor
Cit2b2lkIGNob3BDdWJpY0F0KGNvbnN0IEZsb2F0UG9pbnQgc3JjWzRdLCBGbG9hdFBvaW50IGRz
dFtdLCBjb25zdCBmbG9hdCB0VmFsdWVzW10sIGludCByb290cykKK3sKKyNpZm5kZWYgTkRFQlVH
CisgICAgZm9yIChpbnQgaSA9IDA7IGkgPCByb290cyAtIDE7ICsraSkgeworICAgICAgICBBU1NF
UlQoaXNVbml0SW50ZXJ2YWwodFZhbHVlc1tpXSkpOworICAgICAgICBBU1NFUlQoaXNVbml0SW50
ZXJ2YWwodFZhbHVlc1tpKzFdKSk7CisgICAgICAgIEFTU0VSVCh0VmFsdWVzW2ldIDwgdFZhbHVl
c1tpKzFdKTsKKyAgICB9CisjZW5kaWYKKworICAgIGlmICghZHN0KQorICAgICAgICByZXR1cm47
CisKKyAgICBpZiAoIXJvb3RzKSB7CisgICAgICAgIC8vIG5vdGhpbmcgdG8gY2hvcAorICAgICAg
ICBtZW1jcHkoZHN0LCBzcmMsIDQqc2l6ZW9mKEZsb2F0UG9pbnQpKTsKKyAgICAgICAgcmV0dXJu
OworICAgIH0KKworICAgIGZsb2F0IHQgPSB0VmFsdWVzWzBdOworICAgIEZsb2F0UG9pbnQgdG1w
WzRdOworCisgICAgZm9yIChpbnQgaSA9IDA7IGkgPCByb290czsgKytpKSB7CisgICAgICAgIExv
b3BCbGlubk1hdGhVdGlsczo6Y2hvcEN1YmljQXQoc3JjLCBkc3QsIHQpOworICAgICAgICBpZiAo
aSA9PSByb290cyAtIDEpCisgICAgICAgICAgICBicmVhazsKKworICAgICAgICBkc3QgKz0gMzsK
KyAgICAgICAgLy8gaGF2ZSBzcmMgcG9pbnQgdG8gdGhlIHJlbWFpbmluZyBjdWJpYyAoYWZ0ZXIg
dGhlIGNob3ApCisgICAgICAgIG1lbWNweSh0bXAsIGRzdCwgNCAqIHNpemVvZihGbG9hdFBvaW50
KSk7CisgICAgICAgIHNyYyA9IHRtcDsKKworICAgICAgICAvLyB3YXRjaCBvdXQgaW4gY2FzZSB0
aGUgcmVub3JtYWxpemVkIHQgaXNuJ3QgaW4gcmFuZ2UKKyAgICAgICAgaWYgKCF2YWxpZFVuaXRE
aXZpZGUodFZhbHVlc1tpKzFdIC0gdFZhbHVlc1tpXSwKKyAgICAgICAgICAgICAgICAgICAgICAg
ICAgICAgMSAtIHRWYWx1ZXNbaV0sICZ0KSkgeworICAgICAgICAgICAgLy8gaWYgd2UgY2FuJ3Qs
IGp1c3QgY3JlYXRlIGEgZGVnZW5lcmF0ZSBjdWJpYworICAgICAgICAgICAgZHN0WzRdID0gZHN0
WzVdID0gZHN0WzZdID0gc3JjWzNdOworICAgICAgICAgICAgYnJlYWs7CisgICAgICAgIH0KKyAg
ICB9Cit9CisKK3ZvaWQgZmxhdHRlbkRvdWJsZUN1YmljWUV4dHJlbWEoRmxvYXRQb2ludCBjb29y
ZHNbN10pCit7CisgICAgY29vcmRzWzJdLnNldFkoY29vcmRzWzNdLnkoKSk7CisgICAgY29vcmRz
WzRdLnNldFkoY29vcmRzWzNdLnkoKSk7Cit9CisKK2ludCBjaG9wQ3ViaWNBdFlFeHRyZW1hKGNv
bnN0IEZsb2F0UG9pbnQgc3JjWzRdLCBGbG9hdFBvaW50IGRzdFsxMF0pCit7CisgICAgZmxvYXQg
dFZhbHVlc1syXTsKKyAgICBpbnQgcm9vdHMgPSBmaW5kQ3ViaWNFeHRyZW1hKHNyY1swXS55KCks
IHNyY1sxXS55KCksIHNyY1syXS55KCksIHNyY1szXS55KCksIHRWYWx1ZXMpOworCisgICAgY2hv
cEN1YmljQXQoc3JjLCBkc3QsIHRWYWx1ZXMsIHJvb3RzKTsKKyAgICBpZiAoZHN0ICYmIHJvb3Rz
ID4gMCkgeworICAgICAgICAvLyB3ZSBkbyBzb21lIGNsZWFudXAgdG8gZW5zdXJlIG91ciBZIGV4
dHJlbWEgYXJlIGZsYXQKKyAgICAgICAgZmxhdHRlbkRvdWJsZUN1YmljWUV4dHJlbWEoJmRzdFsw
XSk7CisgICAgICAgIGlmIChyb290cyA9PSAyKQorICAgICAgICAgICAgZmxhdHRlbkRvdWJsZUN1
YmljWUV4dHJlbWEoJmRzdFszXSk7CisgICAgfQorICAgIHJldHVybiByb290czsKK30KKworfSAv
LyBhbm9ueW1vdXMgbmFtZXNwYWNlCisKKy8vIFB1YmxpYyBjdWJpYyBvcGVyYXRpb25zLgorCit2
b2lkIGNob3BDdWJpY0F0KGNvbnN0IEZsb2F0UG9pbnQgc3JjWzRdLCBGbG9hdFBvaW50IGRzdFs3
XSwgZmxvYXQgdCkKK3sKKyAgICBBU1NFUlQodCA+IDAgJiYgdCA8IDEpOworCisgICAgZmxvYXQg
b3V0cHV0WzE0XTsKKyAgICBpbnRlcnBvbGF0ZUN1YmljQ29vcmRzKHNyY1swXS54KCksIHNyY1sx
XS54KCksIHNyY1syXS54KCksIHNyY1szXS54KCksICZvdXRwdXRbMF0sIHQpOworICAgIGludGVy
cG9sYXRlQ3ViaWNDb29yZHMoc3JjWzBdLnkoKSwgc3JjWzFdLnkoKSwgc3JjWzJdLnkoKSwgc3Jj
WzNdLnkoKSwgJm91dHB1dFsxXSwgdCk7CisgICAgZm9yIChpbnQgaSA9IDA7IGkgPCA3OyBpKysp
CisgICAgICAgIGRzdFtpXS5zZXQob3V0cHV0WzIgKiBpXSwgb3V0cHV0WzIgKiBpICsgMV0pOwor
fQorCisvLyBQdWJsaWMgWFJheSBxdWVyaWVzLgorCitib29sIHhSYXlDcm9zc2VzTGluZShjb25z
dCBYUmF5JiB4UmF5LCBjb25zdCBGbG9hdFBvaW50IHB0c1syXSwgYm9vbCYgYW1iaWd1b3VzKQor
eworICAgIGFtYmlndW91cyA9IGZhbHNlOworCisgICAgLy8gRGV0ZXJtaW5lIHF1aWNrIGRpc2Nh
cmRzLgorICAgIC8vIENvbnNpZGVyIHF1ZXJ5IGxpbmUgZ29pbmcgZXhhY3RseSB0aHJvdWdoIHBv
aW50IDAgdG8gbm90CisgICAgLy8gaW50ZXJzZWN0LCBmb3Igc3ltbWV0cnkgd2l0aCBTa1hSYXlD
cm9zc2VzTW9ub3RvbmljQ3ViaWMuCisgICAgaWYgKHhSYXkueSgpID09IHB0c1swXS55KCkpIHsK
KyAgICAgICAgYW1iaWd1b3VzID0gdHJ1ZTsKKyAgICAgICAgcmV0dXJuIGZhbHNlOworICAgIH0K
KyAgICBpZiAoeFJheS55KCkgPCBwdHNbMF0ueSgpICYmIHhSYXkueSgpIDwgcHRzWzFdLnkoKSkK
KyAgICAgICAgcmV0dXJuIGZhbHNlOworICAgIGlmICh4UmF5LnkoKSA+IHB0c1swXS55KCkgJiYg
eFJheS55KCkgPiBwdHNbMV0ueSgpKQorICAgICAgICByZXR1cm4gZmFsc2U7CisgICAgaWYgKHhS
YXkueCgpID4gcHRzWzBdLngoKSAmJiB4UmF5LngoKSA+IHB0c1sxXS54KCkpCisgICAgICAgIHJl
dHVybiBmYWxzZTsKKyAgICAvLyBEZXRlcm1pbmUgZGVnZW5lcmF0ZSBjYXNlcworICAgIGlmIChu
ZWFybHlaZXJvKHB0c1swXS55KCkgLSBwdHNbMV0ueSgpKSkKKyAgICAgICAgcmV0dXJuIGZhbHNl
OworICAgIGlmIChuZWFybHlaZXJvKHB0c1swXS54KCkgLSBwdHNbMV0ueCgpKSkgeworICAgICAg
ICAvLyBXZSd2ZSBhbHJlYWR5IGRldGVybWluZWQgdGhlIHF1ZXJ5IHBvaW50IGxpZXMgd2l0aGlu
IHRoZQorICAgICAgICAvLyB2ZXJ0aWNhbCByYW5nZSBvZiB0aGUgbGluZSBzZWdtZW50LgorICAg
ICAgICBpZiAoeFJheS54KCkgPD0gcHRzWzBdLngoKSkgeworICAgICAgICAgICAgYW1iaWd1b3Vz
ID0gKHhSYXkueSgpID09IHB0c1sxXS55KCkpOworICAgICAgICAgICAgcmV0dXJuIHRydWU7Cisg
ICAgICAgIH0KKyAgICAgICAgcmV0dXJuIGZhbHNlOworICAgIH0KKyAgICAvLyBBbWJpZ3VpdHkg
Y2hlY2sKKyAgICBpZiAoeFJheS55KCkgPT0gcHRzWzFdLnkoKSkgeworICAgICAgICBpZiAoeFJh
eS54KCkgPD0gcHRzWzFdLngoKSkgeworICAgICAgICAgICAgYW1iaWd1b3VzID0gdHJ1ZTsKKyAg
ICAgICAgICAgIHJldHVybiB0cnVlOworICAgICAgICB9CisgICAgICAgIHJldHVybiBmYWxzZTsK
KyAgICB9CisgICAgLy8gRnVsbCBsaW5lIHNlZ21lbnQgZXZhbHVhdGlvbgorICAgIGZsb2F0IGRl
bHRhWSA9IHB0c1sxXS55KCkgLSBwdHNbMF0ueSgpOworICAgIGZsb2F0IGRlbHRhWCA9IHB0c1sx
XS54KCkgLSBwdHNbMF0ueCgpOworICAgIGZsb2F0IHNsb3BlID0gZGVsdGFZIC8gZGVsdGFYOwor
ICAgIGZsb2F0IGIgPSBwdHNbMF0ueSgpIC0gc2xvcGUgKiBwdHNbMF0ueCgpOworICAgIC8vIFNv
bHZlIGZvciB4IGNvb3JkaW5hdGUgYXQgeSA9IHhSYXkueSgpCisgICAgZmxvYXQgeCA9ICh4UmF5
LnkoKSAtIGIpIC8gc2xvcGU7CisgICAgcmV0dXJuIHhSYXkueCgpIDw9IHg7Cit9CisKK2ludCBu
dW1YUmF5Q3Jvc3NpbmdzRm9yQ3ViaWMoY29uc3QgWFJheSYgcHQsIGNvbnN0IEZsb2F0UG9pbnQg
Y3ViaWNbNF0sIGJvb2wmIGFtYmlndW91cykKK3sKKyAgICBpbnQgbnVtQ3Jvc3NpbmdzID0gMDsK
KyAgICBGbG9hdFBvaW50IG1vbm90b25pY0N1Ymljc1sxMF07CisgICAgaW50IG51bU1vbm90b25p
Y0N1YmljcyA9IGNob3BDdWJpY0F0WUV4dHJlbWEoY3ViaWMsIG1vbm90b25pY0N1Ymljcyk7Cisg
ICAgYW1iaWd1b3VzID0gZmFsc2U7CisgICAgYm9vbCBsb2NhbGx5QW1iaWd1b3VzOworICAgIGlm
ICh4UmF5Q3Jvc3Nlc01vbm90b25pY0N1YmljKHB0LCAmbW9ub3RvbmljQ3ViaWNzWzBdLCBsb2Nh
bGx5QW1iaWd1b3VzKSkKKyAgICAgICAgKytudW1Dcm9zc2luZ3M7CisgICAgYW1iaWd1b3VzIHw9
IGxvY2FsbHlBbWJpZ3VvdXM7CisgICAgaWYgKG51bU1vbm90b25pY0N1YmljcyA+IDApCisgICAg
ICAgIGlmICh4UmF5Q3Jvc3Nlc01vbm90b25pY0N1YmljKHB0LCAmbW9ub3RvbmljQ3ViaWNzWzNd
LCBsb2NhbGx5QW1iaWd1b3VzKSkKKyAgICAgICAgICAgICsrbnVtQ3Jvc3NpbmdzOworICAgIGFt
YmlndW91cyB8PSBsb2NhbGx5QW1iaWd1b3VzOworICAgIGlmIChudW1Nb25vdG9uaWNDdWJpY3Mg
PiAxKQorICAgICAgICBpZiAoeFJheUNyb3NzZXNNb25vdG9uaWNDdWJpYyhwdCwgJm1vbm90b25p
Y0N1Ymljc1s2XSwgbG9jYWxseUFtYmlndW91cykpCisgICAgICAgICAgICArK251bUNyb3NzaW5n
czsKKyAgICBhbWJpZ3VvdXMgfD0gbG9jYWxseUFtYmlndW91czsKKyAgICByZXR1cm4gbnVtQ3Jv
c3NpbmdzOworfQorCit9IC8vIG5hbWVzcGFjZSBMb29wQmxpbm5NYXRoVXRpbHMKK30gLy8gbmFt
ZXNwYWNlIFdlYkNvcmUKSW5kZXg6IFdlYkNvcmUvcGxhdGZvcm0vZ3JhcGhpY3MvZ3B1L0xvb3BC
bGlubk1hdGhVdGlscy5oCj09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09
PT09PT09PT09PT09PT09PT09PT09PT09PT0KLS0tIFdlYkNvcmUvcGxhdGZvcm0vZ3JhcGhpY3Mv
Z3B1L0xvb3BCbGlubk1hdGhVdGlscy5oCShyZXZpc2lvbiAwKQorKysgV2ViQ29yZS9wbGF0Zm9y
bS9ncmFwaGljcy9ncHUvTG9vcEJsaW5uTWF0aFV0aWxzLmgJKHJldmlzaW9uIDApCkBAIC0wLDAg
KzEsMTMzIEBACisvKgorICogQ29weXJpZ2h0IChDKSAyMDEwIEdvb2dsZSBJbmMuIEFsbCByaWdo
dHMgcmVzZXJ2ZWQuCisgKgorICogUmVkaXN0cmlidXRpb24gYW5kIHVzZSBpbiBzb3VyY2UgYW5k
IGJpbmFyeSBmb3Jtcywgd2l0aCBvciB3aXRob3V0CisgKiBtb2RpZmljYXRpb24sIGFyZSBwZXJt
aXR0ZWQgcHJvdmlkZWQgdGhhdCB0aGUgZm9sbG93aW5nIGNvbmRpdGlvbnMKKyAqIGFyZSBtZXQ6
CisgKgorICogMS4gIFJlZGlzdHJpYnV0aW9ucyBvZiBzb3VyY2UgY29kZSBtdXN0IHJldGFpbiB0
aGUgYWJvdmUgY29weXJpZ2h0CisgKiAgICAgbm90aWNlLCB0aGlzIGxpc3Qgb2YgY29uZGl0aW9u
cyBhbmQgdGhlIGZvbGxvd2luZyBkaXNjbGFpbWVyLgorICogMi4gIFJlZGlzdHJpYnV0aW9ucyBp
biBiaW5hcnkgZm9ybSBtdXN0IHJlcHJvZHVjZSB0aGUgYWJvdmUgY29weXJpZ2h0CisgKiAgICAg
bm90aWNlLCB0aGlzIGxpc3Qgb2YgY29uZGl0aW9ucyBhbmQgdGhlIGZvbGxvd2luZyBkaXNjbGFp
bWVyIGluIHRoZQorICogICAgIGRvY3VtZW50YXRpb24gYW5kL29yIG90aGVyIG1hdGVyaWFscyBw
cm92aWRlZCB3aXRoIHRoZSBkaXN0cmlidXRpb24uCisgKgorICogVEhJUyBTT0ZUV0FSRSBJUyBQ
Uk9WSURFRCBCWSBBUFBMRSBBTkQgSVRTIENPTlRSSUJVVE9SUyAiQVMgSVMiIEFORCBBTlkKKyAq
IEVYUFJFU1MgT1IgSU1QTElFRCBXQVJSQU5USUVTLCBJTkNMVURJTkcsIEJVVCBOT1QgTElNSVRF
RCBUTywgVEhFIElNUExJRUQKKyAqIFdBUlJBTlRJRVMgT0YgTUVSQ0hBTlRBQklMSVRZIEFORCBG
SVRORVNTIEZPUiBBIFBBUlRJQ1VMQVIgUFVSUE9TRSBBUkUKKyAqIERJU0NMQUlNRUQuIElOIE5P
IEVWRU5UIFNIQUxMIEFQUExFIE9SIElUUyBDT05UUklCVVRPUlMgQkUgTElBQkxFIEZPUiBBTlkK
KyAqIERJUkVDVCwgSU5ESVJFQ1QsIElOQ0lERU5UQUwsIFNQRUNJQUwsIEVYRU1QTEFSWSwgT1Ig
Q09OU0VRVUVOVElBTCBEQU1BR0VTCisgKiAoSU5DTFVESU5HLCBCVVQgTk9UIExJTUlURUQgVE8s
IFBST0NVUkVNRU5UIE9GIFNVQlNUSVRVVEUgR09PRFMgT1IgU0VSVklDRVM7CisgKiBMT1NTIE9G
IFVTRSwgREFUQSwgT1IgUFJPRklUUzsgT1IgQlVTSU5FU1MgSU5URVJSVVBUSU9OKSBIT1dFVkVS
IENBVVNFRCBBTkQKKyAqIE9OIEFOWSBUSEVPUlkgT0YgTElBQklMSVRZLCBXSEVUSEVSIElOIENP
TlRSQUNULCBTVFJJQ1QgTElBQklMSVRZLCBPUiBUT1JUCisgKiAoSU5DTFVESU5HIE5FR0xJR0VO
Q0UgT1IgT1RIRVJXSVNFKSBBUklTSU5HIElOIEFOWSBXQVkgT1VUIE9GIFRIRSBVU0UgT0YKKyAq
IFRISVMgU09GVFdBUkUsIEVWRU4gSUYgQURWSVNFRCBPRiBUSEUgUE9TU0lCSUxJVFkgT0YgU1VD
SCBEQU1BR0UuCisgKi8KKworI2lmbmRlZiBMb29wQmxpbm5NYXRoVXRpbHNfaAorI2RlZmluZSBM
b29wQmxpbm5NYXRoVXRpbHNfaAorCisjaW5jbHVkZSAiRmxvYXRQb2ludDNELmgiCisjaW5jbHVk
ZSA8bWF0aC5oPgorCituYW1lc3BhY2UgV2ViQ29yZSB7CisKK2NsYXNzIEZsb2F0UG9pbnQ7CisK
Ky8vIFVzZSBhIG5hbWVzcGFjZSBmb3IgdGhlc2Ugc28gd2UgY2FuIGVhc2lseSBpbXBvcnQgdGhl
bS4KK25hbWVzcGFjZSBMb29wQmxpbm5NYXRoVXRpbHMgeworCisvLyBBIHJvdW5kb2ZmIGZhY3Rv
ciBpbiB0aGUgY3ViaWMgY2xhc3NpZmljYXRpb24gYW5kIHRleHR1cmUgY29vcmRpbmF0ZQorLy8g
Z2VuZXJhdGlvbiBhbGdvcml0aG1zLiBUaGlzIHByaW1hcmlseSBkZXRlcm1pbmVzIHRoZSBoYW5k
bGluZyBvZiBjb3JuZXIKKy8vIGNhc2VzIGR1cmluZyB0aGUgY2xhc3NpZmljYXRpb24gcHJvY2Vz
cy4gQmUgY2FyZWZ1bCB3aGVuIGFkanVzdGluZyB0aGlzOworLy8gaXQgaGFzIGJlZW4gZGV0ZXJt
aW5lZCBlbXBpcmljYWxseSB0byB3b3JrIHdlbGwuCitjb25zdCBmbG9hdCBFcHNpbG9uID0gNS4w
ZS00ZjsKKworLy8gUmV0dXJucyB6ZXJvIGlmIHZhbHVlIGlzIHdpdGhpbiArLy1FcHNpbG9uIG9m
IHplcm8uCitpbmxpbmUgZmxvYXQgcm91bmRUb1plcm8oZmxvYXQgdmFsKQoreworICAgIGlmICh2
YWwgPCBFcHNpbG9uICYmIHZhbCA+IC1FcHNpbG9uKQorICAgICAgICByZXR1cm4gMDsKKyAgICBy
ZXR1cm4gdmFsOworfQorCitpbmxpbmUgYm9vbCBhcHByb3hFcXVhbChjb25zdCBGbG9hdFBvaW50
JiB2MCwgY29uc3QgRmxvYXRQb2ludCYgdjEpCit7CisgICAgcmV0dXJuICh2MCAtIHYxKS5kaWFn
b25hbExlbmd0aFNxdWFyZWQoKSA8IEVwc2lsb24gKiBFcHNpbG9uOworfQorCitpbmxpbmUgYm9v
bCBhcHByb3hFcXVhbChjb25zdCBGbG9hdFBvaW50M0QmIHYwLCBjb25zdCBGbG9hdFBvaW50M0Qm
IHYxKQoreworICAgIHJldHVybiAodjAgLSB2MSkubGVuZ3RoU3F1YXJlZCgpIDwgRXBzaWxvbiAq
IEVwc2lsb247Cit9CisKK2lubGluZSBib29sIGFwcHJveEVxdWFsKGZsb2F0IGYwLCBmbG9hdCBm
MSkKK3sKKyAgICByZXR1cm4gZmFic2YoZjAgLSBmMSkgPCBFcHNpbG9uOworfQorCisvLyBEZXRl
cm1pbmVzIHdoZXRoZXIgdGhlIGxpbmUgc2VnbWVudCBiZXR3ZWVuIChwMSwgcTEpIGludGVyc2Vj
dHMKKy8vIHRoYXQgYmV0d2VlbiAocDIsIHEyKS4KK2Jvb2wgbGluZXNJbnRlcnNlY3QoY29uc3Qg
RmxvYXRQb2ludCYgcDEsCisgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIHEx
LAorICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBwMiwKKyAgICAgICAgICAg
ICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgcTIpOworCisvLyBEZXRlcm1pbmVzIHdoZXRoZXIg
InBvaW50IiBpcyBpbnNpZGUgdGhlIDJEIHRyaWFuZ2xlIGRlZmluZWQgYnkKKy8vIHZlcnRpY2Vz
IGEsIGIsIGFuZCBjLiBUaGlzIHRlc3QgZGVmaW5lcyB0aGF0IHBvaW50cyBleGFjdGx5IG9uIGFu
CisvLyBlZGdlIGFyZSBub3QgY29uc2lkZXJlZCB0byBiZSBpbnNpZGUgdGhlIHRyaWFuZ2xlLgor
Ym9vbCBwb2ludEluVHJpYW5nbGUoY29uc3QgRmxvYXRQb2ludCYgcG9pbnQsCisgICAgICAgICAg
ICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBhLAorICAgICAgICAgICAgICAgICAgICAgY29u
c3QgRmxvYXRQb2ludCYgYiwKKyAgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQm
IGMpOworCisvLyBEZXRlcm1pbmVzIHdoZXRoZXIgdGhlIHRyaWFuZ2xlcyBkZWZpbmVkIGJ5IHRo
ZSBwb2ludHMgKGExLCBiMSwgYzEpCisvLyBhbmQgKGEyLCBiMiwgYzIpIG92ZXJsYXAuIFRoZSBk
ZWZpbml0aW9uIG9mIHRoaXMgZnVuY3Rpb24gaXMgdGhhdAorLy8gaWYgdGhlIHR3byB0cmlhbmds
ZXMgb25seSBzaGFyZSBhbiBhZGphY2VudCBlZGdlIG9yIHZlcnRleCwgdGhleQorLy8gYXJlIG5v
dCBjb25zaWRlcmVkIHRvIG92ZXJsYXAuCitib29sIHRyaWFuZ2xlc092ZXJsYXAoY29uc3QgRmxv
YXRQb2ludCYgYTEsCisgICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgYjEs
CisgICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgYzEsCisgICAgICAgICAg
ICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgYTIsCisgICAgICAgICAgICAgICAgICAgICAg
Y29uc3QgRmxvYXRQb2ludCYgYjIsCisgICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQ
b2ludCYgYzIpOworCisvLyBHaXZlbiBhIHNyYyBjdWJpYyBiZXppZXIsIGNob3BzIGl0IGF0IHRo
ZSBzcGVjaWZpZWQgdCB2YWx1ZSwKKy8vIHdoZXJlIDAgPCB0IDwgMSwgYW5kIHJldHVybnMgdGhl
IHR3byBuZXcgY3ViaWNzIGluIGRzdFswLi4zXQorLy8gYW5kIGRzdFszLi42XS4KK3ZvaWQgY2hv
cEN1YmljQXQoY29uc3QgRmxvYXRQb2ludCBzcmNbNF0sIEZsb2F0UG9pbnQgZHN0WzddLCBmbG9h
dCB0KTsKKworLy8gIlgtUmF5IiBxdWVyaWVzLiBBbiBYUmF5IGlzIGEgaGFsZi1saW5lIG9yaWdp
bmF0aW5nIGF0IHRoZSBnaXZlbgorLy8gcG9pbnQgYW5kIGV4dGVuZGluZyB0byB4PStpbmZpbml0
eS4KK3R5cGVkZWYgRmxvYXRQb2ludCBYUmF5OworCisvLyBHaXZlbiBhbiBhcmJpdHJhcnkgY3Vi
aWMgYmV6aWVyLCByZXR1cm4gdGhlIG51bWJlciBvZiB0aW1lcyBhbiBYUmF5CisvLyBjcm9zc2Vz
IHRoZSBjdWJpYy4gVmFsaWQgcmV0dXJuIHZhbHVlcyBhcmUgWzAuLjNdLgorLy8KKy8vIEJ5IGRl
ZmluaXRpb24gdGhlIGN1YmljIGlzIG9wZW4gYXQgdGhlIHN0YXJ0aW5nIHBvaW50OyBpbiBvdGhl
cgorLy8gd29yZHMsIGlmIHB0LmZZIGlzIGVxdWl2YWxlbnQgdG8gY3ViaWNbMF0uZlksIGFuZCBw
dC5mWCBpcyB0byB0aGUKKy8vIGxlZnQgb2YgdGhlIGN1cnZlLCB0aGUgbGluZSBpcyBub3QgY29u
c2lkZXJlZCB0byBjcm9zcyB0aGUgY3VydmUsCisvLyBidXQgaWYgaXQgaXMgZXF1YWwgdG8gY3Vi
aWNbM10uZlkgdGhlbiBpdCBpcyBjb25zaWRlcmVkIHRvCisvLyBjcm9zcy4KKy8vCisvLyBPdXRn
b2luZyAiYW1iaWd1b3VzIiBhcmd1bWVudCBpbmRpY2F0ZXMgd2hldGhlciB0aGUgYW5zd2VyIGlz
IGFtYmlndW91cworLy8gYmVjYXVzZSB0aGUgcXVlcnkgb2NjdXJyZWQgZXhhY3RseSBhdCBvbmUg
b2YgdGhlIGVuZHBvaW50cycgeQorLy8gY29vcmRpbmF0ZXMgb3IgYXQgYSB0YW5nZW50IHBvaW50
LCBpbmRpY2F0aW5nIHRoYXQgYW5vdGhlciBxdWVyeSB5CisvLyBjb29yZGluYXRlIGlzIHByZWZl
cnJlZCBmb3Igcm9idXN0bmVzcy4KK2ludCBudW1YUmF5Q3Jvc3NpbmdzRm9yQ3ViaWMoY29uc3Qg
WFJheSYgeFJheSwKKyAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2lu
dCBjdWJpY1s0XSwKKyAgICAgICAgICAgICAgICAgICAgICAgICAgICAgYm9vbCYgYW1iaWd1b3Vz
KTsKKworLy8gR2l2ZW4gYSBsaW5lIHNlZ21lbnQgZnJvbSBsaW5lRW5kcG9pbnRzWzBdIHRvIGxp
bmVFbmRwb2ludHNbMV0sIGFuZCBhbgorLy8gWFJheSwgcmV0dXJucyB0cnVlIGlmIHRoZXkgaW50
ZXJzZWN0LiBPdXRnb2luZyAiYW1iaWd1b3VzIiBhcmd1bWVudAorLy8gaW5kaWNhdGVzIHdoZXRo
ZXIgdGhlIGFuc3dlciBpcyBhbWJpZ3VvdXMgYmVjYXVzZSB0aGUgcXVlcnkgb2NjdXJyZWQKKy8v
IGV4YWN0bHkgYXQgb25lIG9mIHRoZSBlbmRwb2ludHMnIHkgY29vcmRpbmF0ZXMsIGluZGljYXRp
bmcgdGhhdCBhbm90aGVyCisvLyBxdWVyeSB5IGNvb3JkaW5hdGUgaXMgcHJlZmVycmVkIGZvciBy
b2J1c3RuZXNzLgorYm9vbCB4UmF5Q3Jvc3Nlc0xpbmUoY29uc3QgWFJheSYgeFJheSwKKyAgICAg
ICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQgbGluZUVuZHBvaW50c1syXSwKKyAgICAg
ICAgICAgICAgICAgICAgIGJvb2wmIGFtYmlndW91cyk7CisKK30gLy8gbmFtZXNwYWNlIExvb3BC
bGlubk1hdGhVdGlscworCit9IC8vIG5hbWVzcGFjZSBXZWJDb3JlCisKKyNlbmRpZiAvLyBMb29w
Qmxpbm5NYXRoVXRpbHNfaAo=
</data>
<flag name="review"
          id="55663"
          type_id="1"
          status="-"
          setter="jamesr"
    />
    <flag name="commit-queue"
          id="55664"
          type_id="3"
          status="-"
          setter="kbr"
    />
          </attachment>
          <attachment
              isobsolete="1"
              ispatch="1"
              isprivate="0"
          >
            <attachid>67082</attachid>
            <date>2010-09-09 12:47:18 -0700</date>
            <delta_ts>2010-09-09 17:47:14 -0700</delta_ts>
            <desc>Revised patch</desc>
            <filename>math-utils.patch</filename>
            <type>text/plain</type>
            <size>25968</size>
            <attacher name="Kenneth Russell">kbr</attacher>
            
              <data encoding="base64">SW5kZXg6IFdlYkNvcmUvQ2hhbmdlTG9nCj09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09
PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0KLS0tIFdlYkNvcmUvQ2hhbmdlTG9n
CShyZXZpc2lvbiA2NzEwNCkKKysrIFdlYkNvcmUvQ2hhbmdlTG9nCSh3b3JraW5nIGNvcHkpCkBA
IC0xLDMgKzEsMjUgQEAKKzIwMTAtMDktMDkgIEtlbm5ldGggUnVzc2VsbCAgPGtickBnb29nbGUu
Y29tPgorCisgICAgICAgIFJldmlld2VkIGJ5IE5PQk9EWSAoT09QUyEpLgorCisgICAgICAgIEFk
ZCBtYXRoIHV0aWxpdGllcyBmb3IgY3ViaWMgY3VydmUgcHJvY2Vzc2luZworICAgICAgICBodHRw
czovL2J1Z3Mud2Via2l0Lm9yZy9zaG93X2J1Zy5jZ2k/aWQ9NDUyNTEKKworICAgICAgICBBZGRp
bmcgbWF0aGVtYXRpYyB1dGlsaXRpZXMgbmVlZGVkIGZvciB0aGUgR1BVIGFjY2VsZXJhdGVkIHBh
dGgKKyAgICAgICAgcmVuZGVyaW5nIGFsZ29yaXRobSBmcm9tIEdQVSBHZW1zIDMuIE5vIHRlc3Rz
IHlldDsgd2lsbCBiZSB0ZXN0ZWQKKyAgICAgICAgaW4gY29uanVuY3Rpb24gd2l0aCBsYXRlciBj
b2RlLgorCisgICAgICAgICogcGxhdGZvcm0vZ3JhcGhpY3MvZ3B1L0xvb3BCbGlubk1hdGhVdGls
cy5jcHA6IEFkZGVkLgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxzOjpsaW5l
c0ludGVyc2VjdCk6CisgICAgICAgIChXZWJDb3JlOjpMb29wQmxpbm5NYXRoVXRpbHM6OnBvaW50
SW5UcmlhbmdsZSk6CisgICAgICAgIChXZWJDb3JlOjpMb29wQmxpbm5NYXRoVXRpbHM6OnRyaWFu
Z2xlc092ZXJsYXApOgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxzOjpjaG9w
Q3ViaWNBdCk6CisgICAgICAgIChXZWJDb3JlOjpMb29wQmxpbm5NYXRoVXRpbHM6OnhSYXlDcm9z
c2VzTGluZSk6CisgICAgICAgIChXZWJDb3JlOjpMb29wQmxpbm5NYXRoVXRpbHM6Om51bVhSYXlD
cm9zc2luZ3NGb3JDdWJpYyk6CisgICAgICAgICogcGxhdGZvcm0vZ3JhcGhpY3MvZ3B1L0xvb3BC
bGlubk1hdGhVdGlscy5oOiBBZGRlZC4KKyAgICAgICAgKFdlYkNvcmU6Okxvb3BCbGlubk1hdGhV
dGlsczo6cm91bmRUb1plcm8pOgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxz
OjphcHByb3hFcXVhbCk6CisKIDIwMTAtMDktMDkgIEtlbm5ldGggUnVzc2VsbCAgPGtickBnb29n
bGUuY29tPgogCiAgICAgICAgIFJldmlld2VkIGJ5IEphbWVzIFJvYmluc29uLgpJbmRleDogV2Vi
Q29yZS9wbGF0Zm9ybS9ncmFwaGljcy9ncHUvTG9vcEJsaW5uTWF0aFV0aWxzLmNwcAo9PT09PT09
PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09
PT09Ci0tLSBXZWJDb3JlL3BsYXRmb3JtL2dyYXBoaWNzL2dwdS9Mb29wQmxpbm5NYXRoVXRpbHMu
Y3BwCShyZXZpc2lvbiAwKQorKysgV2ViQ29yZS9wbGF0Zm9ybS9ncmFwaGljcy9ncHUvTG9vcEJs
aW5uTWF0aFV0aWxzLmNwcAkocmV2aXNpb24gMCkKQEAgLTAsMCArMSw1NTcgQEAKKy8qCisgKiBD
b3B5cmlnaHQgKEMpIDIwMTAgR29vZ2xlIEluYy4gQWxsIHJpZ2h0cyByZXNlcnZlZC4KKyAqCisg
KiBSZWRpc3RyaWJ1dGlvbiBhbmQgdXNlIGluIHNvdXJjZSBhbmQgYmluYXJ5IGZvcm1zLCB3aXRo
IG9yIHdpdGhvdXQKKyAqIG1vZGlmaWNhdGlvbiwgYXJlIHBlcm1pdHRlZCBwcm92aWRlZCB0aGF0
IHRoZSBmb2xsb3dpbmcgY29uZGl0aW9ucworICogYXJlIG1ldDoKKyAqCisgKiAxLiAgUmVkaXN0
cmlidXRpb25zIG9mIHNvdXJjZSBjb2RlIG11c3QgcmV0YWluIHRoZSBhYm92ZSBjb3B5cmlnaHQK
KyAqICAgICBub3RpY2UsIHRoaXMgbGlzdCBvZiBjb25kaXRpb25zIGFuZCB0aGUgZm9sbG93aW5n
IGRpc2NsYWltZXIuCisgKiAyLiAgUmVkaXN0cmlidXRpb25zIGluIGJpbmFyeSBmb3JtIG11c3Qg
cmVwcm9kdWNlIHRoZSBhYm92ZSBjb3B5cmlnaHQKKyAqICAgICBub3RpY2UsIHRoaXMgbGlzdCBv
ZiBjb25kaXRpb25zIGFuZCB0aGUgZm9sbG93aW5nIGRpc2NsYWltZXIgaW4gdGhlCisgKiAgICAg
ZG9jdW1lbnRhdGlvbiBhbmQvb3Igb3RoZXIgbWF0ZXJpYWxzIHByb3ZpZGVkIHdpdGggdGhlIGRp
c3RyaWJ1dGlvbi4KKyAqCisgKiBUSElTIFNPRlRXQVJFIElTIFBST1ZJREVEIEJZIEFQUExFIEFO
RCBJVFMgQ09OVFJJQlVUT1JTICJBUyBJUyIgQU5EIEFOWQorICogRVhQUkVTUyBPUiBJTVBMSUVE
IFdBUlJBTlRJRVMsIElOQ0xVRElORywgQlVUIE5PVCBMSU1JVEVEIFRPLCBUSEUgSU1QTElFRAor
ICogV0FSUkFOVElFUyBPRiBNRVJDSEFOVEFCSUxJVFkgQU5EIEZJVE5FU1MgRk9SIEEgUEFSVElD
VUxBUiBQVVJQT1NFIEFSRQorICogRElTQ0xBSU1FRC4gSU4gTk8gRVZFTlQgU0hBTEwgQVBQTEUg
T1IgSVRTIENPTlRSSUJVVE9SUyBCRSBMSUFCTEUgRk9SIEFOWQorICogRElSRUNULCBJTkRJUkVD
VCwgSU5DSURFTlRBTCwgU1BFQ0lBTCwgRVhFTVBMQVJZLCBPUiBDT05TRVFVRU5USUFMIERBTUFH
RVMKKyAqIChJTkNMVURJTkcsIEJVVCBOT1QgTElNSVRFRCBUTywgUFJPQ1VSRU1FTlQgT0YgU1VC
U1RJVFVURSBHT09EUyBPUiBTRVJWSUNFUzsKKyAqIExPU1MgT0YgVVNFLCBEQVRBLCBPUiBQUk9G
SVRTOyBPUiBCVVNJTkVTUyBJTlRFUlJVUFRJT04pIEhPV0VWRVIgQ0FVU0VEIEFORAorICogT04g
QU5ZIFRIRU9SWSBPRiBMSUFCSUxJVFksIFdIRVRIRVIgSU4gQ09OVFJBQ1QsIFNUUklDVCBMSUFC
SUxJVFksIE9SIFRPUlQKKyAqIChJTkNMVURJTkcgTkVHTElHRU5DRSBPUiBPVEhFUldJU0UpIEFS
SVNJTkcgSU4gQU5ZIFdBWSBPVVQgT0YgVEhFIFVTRSBPRgorICogVEhJUyBTT0ZUV0FSRSwgRVZF
TiBJRiBBRFZJU0VEIE9GIFRIRSBQT1NTSUJJTElUWSBPRiBTVUNIIERBTUFHRS4KKyAqLworCisj
aW5jbHVkZSAiY29uZmlnLmgiCisKKyNpbmNsdWRlICJMb29wQmxpbm5NYXRoVXRpbHMuaCIKKwor
I2luY2x1ZGUgIkZsb2F0UG9pbnQuaCIKKyNpbmNsdWRlICJNYXRoRXh0cmFzLmgiCisjaW5jbHVk
ZSA8YWxnb3JpdGhtPgorI2luY2x1ZGUgPHN0cmluZy5oPiAvLyBmb3IgbWVtY3B5CisKK25hbWVz
cGFjZSBXZWJDb3JlIHsKK25hbWVzcGFjZSBMb29wQmxpbm5NYXRoVXRpbHMgeworCituYW1lc3Bh
Y2UgeworCisvLyBVdGlsaXR5IGZ1bmN0aW9ucyBsb2NhbCB0byB0aGlzIGZpbGUuCitpbnQgb3Jp
ZW50YXRpb24oY29uc3QgRmxvYXRQb2ludCYgcDEsCisgICAgICAgICAgICAgICAgY29uc3QgRmxv
YXRQb2ludCYgcDIsCisgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgcDMpCit7Cisg
ICAgZmxvYXQgY3Jvc3NQcm9kdWN0ID0gKHAyLnkoKSAtIHAxLnkoKSkgKiAocDMueCgpIC0gcDIu
eCgpKSAtIChwMy55KCkgLSBwMi55KCkpICogKHAyLngoKSAtIHAxLngoKSk7CisgICAgcmV0dXJu
IChjcm9zc1Byb2R1Y3QgPCAwLjBmKSA/IC0xIDogKChjcm9zc1Byb2R1Y3QgPiAwLjBmKSA/IDEg
OiAwKTsKK30KKworYm9vbCBlZGdlRWRnZVRlc3QoY29uc3QgRmxvYXRTaXplJiB2MERlbHRhLAor
ICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgdjAsCisgICAgICAgICAgICAgICAg
ICBjb25zdCBGbG9hdFBvaW50JiB1MCwKKyAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9p
bnQmIHUxKQoreworICAgIC8vIFRoaXMgZWRnZSB0byBlZGdlIHRlc3QgaXMgYmFzZWQgb24gRnJh
bmxpbiBBbnRvbmlvJ3MgZ2VtOiAiRmFzdGVyCisgICAgLy8gTGluZSBTZWdtZW50IEludGVyc2Vj
dGlvbiIsIGluIEdyYXBoaWNzIEdlbXMgSUlJLCBwcC4gMTk5LTIwMi4KKyAgICBmbG9hdCBheCA9
IHYwRGVsdGEud2lkdGgoKTsKKyAgICBmbG9hdCBheSA9IHYwRGVsdGEuaGVpZ2h0KCk7CisgICAg
ZmxvYXQgYnggPSB1MC54KCkgLSB1MS54KCk7CisgICAgZmxvYXQgYnkgPSB1MC55KCkgLSB1MS55
KCk7CisgICAgZmxvYXQgY3ggPSB2MC54KCkgLSB1MC54KCk7CisgICAgZmxvYXQgY3kgPSB2MC55
KCkgLSB1MC55KCk7CisgICAgZmxvYXQgZiA9IGF5ICogYnggLSBheCAqIGJ5OworICAgIGZsb2F0
IGQgPSBieSAqIGN4IC0gYnggKiBjeTsKKyAgICBpZiAoKGYgPiAwICYmIGQgPj0gMCAmJiBkIDw9
IGYpIHx8IChmIDwgMCAmJiBkIDw9IDAgJiYgZCA+PSBmKSkgeworICAgICAgICBmbG9hdCBlID0g
YXggKiBjeSAtIGF5ICogY3g7CisKKyAgICAgICAgLy8gVGhpcyBhZGRpdGlvbmFsIHRlc3QgYXZv
aWRzIHJlcG9ydGluZyBjb2luY2lkZW50IGVkZ2VzLCB3aGljaAorICAgICAgICAvLyBpcyB0aGUg
YmVoYXZpb3Igd2Ugd2FudC4KKyAgICAgICAgaWYgKGFwcHJveEVxdWFsKGUsIDApIHx8IGFwcHJv
eEVxdWFsKGYsIDApIHx8IGFwcHJveEVxdWFsKGUsIGYpKQorICAgICAgICAgICAgcmV0dXJuIGZh
bHNlOworCisgICAgICAgIGlmIChmID4gMCkKKyAgICAgICAgICAgIHJldHVybiBlID49IDAgJiYg
ZSA8PSBmOworCisgICAgICAgIHJldHVybiBlIDw9IDAgJiYgZSA+PSBmOworICAgIH0KKyAgICBy
ZXR1cm4gZmFsc2U7Cit9CisKK2Jvb2wgZWRnZUFnYWluc3RUcmlFZGdlcyhjb25zdCBGbG9hdFBv
aW50JiB2MCwKKyAgICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiB2MSwK
KyAgICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiB1MCwKKyAgICAgICAg
ICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiB1MSwKKyAgICAgICAgICAgICAgICAg
ICAgICAgICBjb25zdCBGbG9hdFBvaW50JiB1MikKK3sKKyAgICBGbG9hdFNpemUgZGVsdGEgPSB2
MSAtIHYwOworICAgIC8vIFRlc3QgZWRnZSB1MCwgdTEgYWdhaW5zdCB2MCwgdjEuCisgICAgaWYg
KGVkZ2VFZGdlVGVzdChkZWx0YSwgdjAsIHUwLCB1MSkpCisgICAgICAgIHJldHVybiB0cnVlOwor
ICAgIC8vIFRlc3QgZWRnZSB1MSwgdTIgYWdhaW5zdCB2MCwgdjEuCisgICAgaWYgKGVkZ2VFZGdl
VGVzdChkZWx0YSwgdjAsIHUxLCB1MikpCisgICAgICAgIHJldHVybiB0cnVlOworICAgIC8vIFRl
c3QgZWRnZSB1MiwgdTEgYWdhaW5zdCB2MCwgdjEuCisgICAgaWYgKGVkZ2VFZGdlVGVzdChkZWx0
YSwgdjAsIHUyLCB1MCkpCisgICAgICAgIHJldHVybiB0cnVlOworICAgIHJldHVybiBmYWxzZTsK
K30KKworfSAvLyBhbm9ueW1vdXMgbmFtZXNwYWNlCisKKy8vIEV4cG9ydGVkIHJvdXRpbmVzCisK
K2Jvb2wgbGluZXNJbnRlcnNlY3QoY29uc3QgRmxvYXRQb2ludCYgcDEsCisgICAgICAgICAgICAg
ICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIHExLAorICAgICAgICAgICAgICAgICAgICBjb25zdCBG
bG9hdFBvaW50JiBwMiwKKyAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgcTIp
Cit7CisgICAgcmV0dXJuIChvcmllbnRhdGlvbihwMSwgcTEsIHAyKSAhPSBvcmllbnRhdGlvbihw
MSwgcTEsIHEyKQorICAgICAgICAgICAgJiYgb3JpZW50YXRpb24ocDIsIHEyLCBwMSkgIT0gb3Jp
ZW50YXRpb24ocDIsIHEyLCBxMSkpOworfQorCitib29sIHBvaW50SW5UcmlhbmdsZShjb25zdCBG
bG9hdFBvaW50JiBwb2ludCwKKyAgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQm
IGEsCisgICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBiLAorICAgICAgICAg
ICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgYykKK3sKKyAgICAvLyBBbGdvcml0aG0gZnJv
bSBodHRwOi8vd3d3LmJsYWNrcGF3bi5jb20vdGV4dHMvcG9pbnRpbnBvbHkvZGVmYXVsdC5odG1s
CisgICAgZmxvYXQgeDAgPSBjLngoKSAtIGEueCgpOworICAgIGZsb2F0IHkwID0gYy55KCkgLSBh
LnkoKTsKKyAgICBmbG9hdCB4MSA9IGIueCgpIC0gYS54KCk7CisgICAgZmxvYXQgeTEgPSBiLnko
KSAtIGEueSgpOworICAgIGZsb2F0IHgyID0gcG9pbnQueCgpIC0gYS54KCk7CisgICAgZmxvYXQg
eTIgPSBwb2ludC55KCkgLSBhLnkoKTsKKworICAgIGZsb2F0IGRvdDAwID0geDAgKiB4MCArIHkw
ICogeTA7CisgICAgZmxvYXQgZG90MDEgPSB4MCAqIHgxICsgeTAgKiB5MTsKKyAgICBmbG9hdCBk
b3QwMiA9IHgwICogeDIgKyB5MCAqIHkyOworICAgIGZsb2F0IGRvdDExID0geDEgKiB4MSArIHkx
ICogeTE7CisgICAgZmxvYXQgZG90MTIgPSB4MSAqIHgyICsgeTEgKiB5MjsKKyAgICBmbG9hdCBk
ZW5vbSA9IGRvdDAwICogZG90MTEgLSBkb3QwMSAqIGRvdDAxOworICAgIGlmICghZGVub20pCisg
ICAgICAgIC8vIFRyaWFuZ2xlIGlzIHplcm8tYXJlYS4gVHJlYXQgcXVlcnkgcG9pbnQgYXMgbm90
IGJlaW5nIGluc2lkZS4KKyAgICAgICAgcmV0dXJuIGZhbHNlOworICAgIC8vIENvbXB1dGUKKyAg
ICBmbG9hdCBpbnZEZW5vbSA9IDEuMGYgLyBkZW5vbTsKKyAgICBmbG9hdCB1ID0gKGRvdDExICog
ZG90MDIgLSBkb3QwMSAqIGRvdDEyKSAqIGludkRlbm9tOworICAgIGZsb2F0IHYgPSAoZG90MDAg
KiBkb3QxMiAtIGRvdDAxICogZG90MDIpICogaW52RGVub207CisKKyAgICByZXR1cm4gKHUgPiAw
LjBmKSAmJiAodiA+IDAuMGYpICYmICh1ICsgdiA8IDEuMGYpOworfQorCitib29sIHRyaWFuZ2xl
c092ZXJsYXAoY29uc3QgRmxvYXRQb2ludCYgYTEsCisgICAgICAgICAgICAgICAgICAgICAgY29u
c3QgRmxvYXRQb2ludCYgYjEsCisgICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2lu
dCYgYzEsCisgICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgYTIsCisgICAg
ICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgYjIsCisgICAgICAgICAgICAgICAg
ICAgICAgY29uc3QgRmxvYXRQb2ludCYgYzIpCit7CisgICAgLy8gRGVyaXZlZCBmcm9tIGNvcGxh
bmFyX3RyaV90cmkoKSBhdAorICAgIC8vIGh0dHA6Ly9qZ3QuYWtwZXRlcnMuY29tL3BhcGVycy9T
aGVuSGVuZ1RhbmcwMy90cmlfdHJpLmh0bWwgLAorICAgIC8vIHNpbXBsaWZpZWQgZm9yIHRoZSAy
RCBjYXNlIGFuZCBtb2RpZmllZCBzbyB0aGF0IG92ZXJsYXBwaW5nIGVkZ2VzCisgICAgLy8gZG8g
bm90IHJlcG9ydCBvdmVybGFwcGluZyB0cmlhbmdsZXMuCisKKyAgICAvLyBUZXN0IGFsbCBlZGdl
cyBvZiB0cmlhbmdsZSAxIGFnYWluc3QgdGhlIGVkZ2VzIG9mIHRyaWFuZ2xlIDIuCisgICAgaWYg
KGVkZ2VBZ2FpbnN0VHJpRWRnZXMoYTEsIGIxLCBhMiwgYjIsIGMyKQorICAgICAgICB8fCBlZGdl
QWdhaW5zdFRyaUVkZ2VzKGIxLCBjMSwgYTIsIGIyLCBjMikKKyAgICAgICAgfHwgZWRnZUFnYWlu
c3RUcmlFZGdlcyhjMSwgYTEsIGEyLCBiMiwgYzIpKQorICAgICAgICByZXR1cm4gdHJ1ZTsKKyAg
ICAvLyBGaW5hbGx5LCB0ZXN0IGlmIHRyaTEgaXMgdG90YWxseSBjb250YWluZWQgaW4gdHJpMiBv
ciB2aWNlIHZlcnNhLgorICAgIGlmIChwb2ludEluVHJpYW5nbGUoYTEsIGEyLCBiMiwgYzIpCisg
ICAgICAgIHx8IHBvaW50SW5UcmlhbmdsZShhMiwgYTEsIGIxLCBjMSkpCisgICAgICAgIHJldHVy
biB0cnVlOworCisgICAgLy8gQmVjYXVzZSB3ZSBkZWZpbmUgdGhhdCB0cmlhbmdsZXMgc2hhcmlu
ZyBhIHZlcnRleCBvciBlZGdlIGRvbid0CisgICAgLy8gb3ZlcmxhcCwgd2UgbXVzdCBwZXJmb3Jt
IGFkZGl0aW9uYWwgcG9pbnQtaW4tdHJpYW5nbGUgdGVzdHMgdG8KKyAgICAvLyBzZWUgd2hldGhl
ciBvbmUgdHJpYW5nbGUgaXMgY29udGFpbmVkIGluIHRoZSBvdGhlci4KKyAgICBpZiAocG9pbnRJ
blRyaWFuZ2xlKGIxLCBhMiwgYjIsIGMyKQorICAgICAgICB8fCBwb2ludEluVHJpYW5nbGUoYzEs
IGEyLCBiMiwgYzIpCisgICAgICAgIHx8IHBvaW50SW5UcmlhbmdsZShiMiwgYTEsIGIxLCBjMSkK
KyAgICAgICAgfHwgcG9pbnRJblRyaWFuZ2xlKGMyLCBhMSwgYjEsIGMxKSkKKyAgICAgICAgcmV0
dXJuIHRydWU7CisgICAgcmV0dXJuIGZhbHNlOworfQorCituYW1lc3BhY2UgeworCisvLyBIZWxw
ZXIgcm91dGluZXMgZm9yIHB1YmxpYyBYUmF5IHF1ZXJpZXMgYmVsb3cuIEFsbCBvZiB0aGlzIGNv
ZGUKKy8vIG9yaWdpbmF0ZWQgaW4gU2tpYTsgc2VlIGluY2x1ZGUvY29yZS8gYW5kIHNyYy9jb3Jl
LywgU2tTY2FsYXIuaCBhbmQKKy8vIFNrR2VvbWV0cnkue2NwcCxofS4KKworY29uc3QgZmxvYXQg
TmVhcmx5WmVyb0NvbnN0YW50ID0gKDEuMGYgLyAoMSA8PCAxMikpOworCitib29sIG5lYXJseVpl
cm8oZmxvYXQgeCwgZmxvYXQgdG9sZXJhbmNlID0gTmVhcmx5WmVyb0NvbnN0YW50KQoreworICAg
IEFTU0VSVCh0b2xlcmFuY2UgPiAwLjApOworICAgIHJldHVybiA6OmZhYnNmKHgpIDwgdG9sZXJh
bmNlOworfQorCisvLyBMaW5lYXJseSBpbnRlcnBvbGF0ZSBiZXR3ZWVuIGEgYW5kIGIsIGJhc2Vk
IG9uIHQuCisvLyBJZiB0IGlzIDAsIHJldHVybiBhOyBpZiB0IGlzIDEsIHJldHVybiBiOyBlbHNl
IGludGVycG9sYXRlLgorLy8gdCBtdXN0IGJlIFswLi4xXS4KK2Zsb2F0IGludGVycG9sYXRlKGZs
b2F0IGEsIGZsb2F0IGIsIGZsb2F0IHQpCit7CisgICAgQVNTRVJUKHQgPj0gMCAmJiB0IDw9IDEp
OworICAgIHJldHVybiBhICsgKGIgLSBhKSAqIHQ7Cit9CisKK2Zsb2F0IGV2YWx1YXRlQ3ViaWMo
ZmxvYXQgczAsIGZsb2F0IHMyLCBmbG9hdCBzNCwgZmxvYXQgczYsIGZsb2F0IHQpCit7CisgICAg
QVNTRVJUKHQgPj0gMCAmJiB0IDw9IDEpOworCisgICAgaWYgKCF0KQorICAgICAgICByZXR1cm4g
czA7CisKKyAgICBmbG9hdCBhYiA9IGludGVycG9sYXRlKHMwLCBzMiwgdCk7CisgICAgZmxvYXQg
YmMgPSBpbnRlcnBvbGF0ZShzMiwgczQsIHQpOworICAgIGZsb2F0IGNkID0gaW50ZXJwb2xhdGUo
czQsIHM2LCB0KTsKKyAgICBmbG9hdCBhYmMgPSBpbnRlcnBvbGF0ZShhYiwgYmMsIHQpOworICAg
IGZsb2F0IGJjZCA9IGludGVycG9sYXRlKGJjLCBjZCwgdCk7CisgICAgcmV0dXJuIGludGVycG9s
YXRlKGFiYywgYmNkLCB0KTsKK30KKworLy8gU2V0IHB0IHRvIHRoZSBwb2ludCBvbiB0aGUgc291
cmNlIGN1YmljIHNwZWNpZmllZCBieSB0LgorLy8gdCBtdXN0IGJlIDAgPD0gdCA8PSAxLjAuCitG
bG9hdFBvaW50IGV2YWx1YXRlQ3ViaWNBdChjb25zdCBGbG9hdFBvaW50IGN1YmljWzRdLCBmbG9h
dCB0KQoreworICAgIHJldHVybiBGbG9hdFBvaW50KGV2YWx1YXRlQ3ViaWMoY3ViaWNbMF0ueCgp
LCBjdWJpY1sxXS54KCksIGN1YmljWzJdLngoKSwgY3ViaWNbM10ueCgpLCB0KSwKKyAgICAgICAg
ICAgICAgICAgICAgICBldmFsdWF0ZUN1YmljKGN1YmljWzBdLnkoKSwgY3ViaWNbMV0ueSgpLCBj
dWJpY1syXS55KCksIGN1YmljWzNdLnkoKSwgdCkpOworfQorCitib29sIHhSYXlDcm9zc2VzTW9u
b3RvbmljQ3ViaWMoY29uc3QgWFJheSYgeFJheSwgY29uc3QgRmxvYXRQb2ludCBjdWJpY1s0XSwg
Ym9vbCYgYW1iaWd1b3VzKQoreworICAgIGFtYmlndW91cyA9IGZhbHNlOworCisgICAgLy8gRmlu
ZCB0aGUgbWluaW11bSBhbmQgbWF4aW11bSB5IG9mIHRoZSBleHRyZW1hLCB3aGljaCBhcmUgdGhl
CisgICAgLy8gZmlyc3QgYW5kIGxhc3QgcG9pbnRzIHNpbmNlIHRoaXMgY3ViaWMgaXMgbW9ub3Rv
bmljCisgICAgZmxvYXQgbWluWSA9IHN0ZDo6bWluKGN1YmljWzBdLnkoKSwgY3ViaWNbM10ueSgp
KTsKKyAgICBmbG9hdCBtYXhZID0gc3RkOjptYXgoY3ViaWNbMF0ueSgpLCBjdWJpY1szXS55KCkp
OworCisgICAgaWYgKHhSYXkueSgpID09IGN1YmljWzBdLnkoKQorICAgICAgICB8fCB4UmF5Lnko
KSA8IG1pblkKKyAgICAgICAgfHwgeFJheS55KCkgPiBtYXhZKSB7CisgICAgICAgIC8vIFRoZSBx
dWVyeSBsaW5lIGRlZmluaXRlbHkgZG9lcyBub3QgY3Jvc3MgdGhlIGN1cnZlCisgICAgICAgIGFt
YmlndW91cyA9ICh4UmF5LnkoKSA9PSBjdWJpY1swXS55KCkpOworICAgICAgICByZXR1cm4gZmFs
c2U7CisgICAgfQorCisgICAgY29uc3QgYm9vbCBwb2ludEF0RXh0cmVtdW0gPSAoeFJheS55KCkg
PT0gY3ViaWNbM10ueSgpKTsKKworICAgIGZsb2F0IG1pblggPSBzdGQ6Om1pbihzdGQ6Om1pbihz
dGQ6Om1pbihjdWJpY1swXS54KCksIGN1YmljWzFdLngoKSksCisgICAgICAgICAgICAgICAgICAg
ICAgICAgICAgICAgICAgIGN1YmljWzJdLngoKSksCisgICAgICAgICAgICAgICAgICAgICAgICAg
IGN1YmljWzNdLngoKSk7CisgICAgaWYgKHhSYXkueCgpIDwgbWluWCkgeworICAgICAgICAvLyBU
aGUgcXVlcnkgbGluZSBkZWZpbml0ZWx5IGNyb3NzZXMgdGhlIGN1cnZlCisgICAgICAgIGFtYmln
dW91cyA9IHBvaW50QXRFeHRyZW11bTsKKyAgICAgICAgcmV0dXJuIHRydWU7CisgICAgfQorCisg
ICAgZmxvYXQgbWF4WCA9IHN0ZDo6bWF4KHN0ZDo6bWF4KHN0ZDo6bWF4KGN1YmljWzBdLngoKSwg
Y3ViaWNbMV0ueCgpKSwKKyAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY3ViaWNb
Ml0ueCgpKSwKKyAgICAgICAgICAgICAgICAgICAgICAgICAgY3ViaWNbM10ueCgpKTsKKyAgICBp
ZiAoeFJheS54KCkgPiBtYXhYKQorICAgICAgICAvLyBUaGUgcXVlcnkgbGluZSBkZWZpbml0ZWx5
IGRvZXMgbm90IGNyb3NzIHRoZSBjdXJ2ZQorICAgICAgICByZXR1cm4gZmFsc2U7CisKKyAgICAv
LyBEbyBhIGJpbmFyeSBzZWFyY2ggdG8gZmluZCB0aGUgcGFyYW1ldGVyIHZhbHVlIHdoaWNoIG1h
a2VzIHkgYXMKKyAgICAvLyBjbG9zZSBhcyBwb3NzaWJsZSB0byB0aGUgcXVlcnkgcG9pbnQuIFNl
ZSB3aGV0aGVyIHRoZSBxdWVyeQorICAgIC8vIGxpbmUncyBvcmlnaW4gaXMgdG8gdGhlIGxlZnQg
b2YgdGhlIGFzc29jaWF0ZWQgeCBjb29yZGluYXRlLgorCisgICAgLy8gTWF4SXRlcmF0aW9ucyBp
cyBjaG9zZW4gYXMgdGhlIG51bWJlciBvZiBtYW50aXNzYSBiaXRzIGZvciBhIGZsb2F0LAorICAg
IC8vIHNpbmNlIHRoZXJlJ3Mgbm8gd2F5IHdlIGFyZSBnb2luZyB0byBnZXQgbW9yZSBwcmVjaXNp
b24gYnkKKyAgICAvLyBpdGVyYXRpbmcgbW9yZSB0aW1lcyB0aGFuIHRoYXQuCisgICAgY29uc3Qg
aW50IE1heEl0ZXJhdGlvbnMgPSAyMzsKKyAgICBGbG9hdFBvaW50IGV2YWx1YXRlZFBvaW50Owor
ICAgIGludCBpdGVyID0gMDsKKyAgICBmbG9hdCB1cHBlclQ7CisgICAgZmxvYXQgbG93ZXJUOwor
ICAgIC8vIE5lZWQgdG8gaW52ZXJ0IGRpcmVjdGlvbiBvZiB0IHBhcmFtZXRlciBpZiBjdWJpYyBn
b2VzIHVwCisgICAgLy8gaW5zdGVhZCBvZiBkb3duCisgICAgaWYgKGN1YmljWzNdLnkoKSA+IGN1
YmljWzBdLnkoKSkgeworICAgICAgICB1cHBlclQgPSAxOworICAgICAgICBsb3dlclQgPSAwOwor
ICAgIH0gZWxzZSB7CisgICAgICAgIHVwcGVyVCA9IDA7CisgICAgICAgIGxvd2VyVCA9IDE7Cisg
ICAgfQorICAgIGRvIHsKKyAgICAgICAgZmxvYXQgdCA9IDAuNSAqICh1cHBlclQgKyBsb3dlclQp
OworICAgICAgICBldmFsdWF0ZWRQb2ludCA9IGV2YWx1YXRlQ3ViaWNBdChjdWJpYywgdCk7Cisg
ICAgICAgIGlmICh4UmF5LnkoKSA+IGV2YWx1YXRlZFBvaW50LnkoKSkKKyAgICAgICAgICAgIGxv
d2VyVCA9IHQ7CisgICAgICAgIGVsc2UKKyAgICAgICAgICAgIHVwcGVyVCA9IHQ7CisgICAgfSB3
aGlsZSAoKytpdGVyIDwgTWF4SXRlcmF0aW9ucyAmJiAhbmVhcmx5WmVybyhldmFsdWF0ZWRQb2lu
dC55KCkgLSB4UmF5LnkoKSkpOworCisgICAgLy8gRklYTUU6IG9uY2Ugd2UgaGF2ZSBtb3JlIHJl
Z3Jlc3Npb24gdGVzdHMgZm9yIHRoaXMgY29kZSwKKyAgICAvLyBkZXRlcm1pbmUgd2hldGhlciB0
aGlzIHNob3VsZCBiZSB1c2luZyBhIGZ1enp5IHRlc3QuCisgICAgaWYgKHhSYXkueCgpIDw9IGV2
YWx1YXRlZFBvaW50LngoKSkgeworICAgICAgICBhbWJpZ3VvdXMgPSBwb2ludEF0RXh0cmVtdW07
CisgICAgICAgIHJldHVybiB0cnVlOworICAgIH0KKyAgICByZXR1cm4gZmFsc2U7Cit9CisKK2lu
dCB2YWxpZFVuaXREaXZpZGUoZmxvYXQgbnVtZXJhdG9yLCBmbG9hdCBkZW5vbWluYXRvciwgZmxv
YXQqIHJhdGlvKQoreworICAgIEFTU0VSVChyYXRpbyk7CisKKyAgICBpZiAobnVtZXJhdG9yIDwg
MCkgeworICAgICAgICBudW1lcmF0b3IgPSAtbnVtZXJhdG9yOworICAgICAgICBkZW5vbWluYXRv
ciA9IC1kZW5vbWluYXRvcjsKKyAgICB9CisKKyAgICBpZiAoIWRlbm9taW5hdG9yIHx8ICFudW1l
cmF0b3IgfHwgbnVtZXJhdG9yID49IGRlbm9taW5hdG9yKQorICAgICAgICByZXR1cm4gMDsKKwor
ICAgIGZsb2F0IHIgPSBudW1lcmF0b3IgLyBkZW5vbWluYXRvcjsKKyAgICBpZiAoaXNuYW4ocikp
CisgICAgICAgIHJldHVybiAwOworICAgIEFTU0VSVChyID49IDAgJiYgciA8IDEpOworICAgIGlm
ICghcikgLy8gY2F0Y2ggdW5kZXJmbG93IGlmIG51bWVyYXRvciA8PDw8IGRlbm9taW5hdG9yCisg
ICAgICAgIHJldHVybiAwOworICAgICpyYXRpbyA9IHI7CisgICAgcmV0dXJuIDE7Cit9CisKKy8q
KiBGcm9tIE51bWVyaWNhbCBSZWNpcGVzIGluIEMuCisKKyAgICBxID0gLTEvMiAoYiArIHNpZ24o
Yikgc3FydFtiKmIgLSA0KmEqY10pCisgICAgeDEgPSBxIC8gYQorICAgIHgyID0gYyAvIHEKKyov
CitpbnQgZmluZFVuaXRRdWFkUm9vdHMoZmxvYXQgYSwgZmxvYXQgYiwgZmxvYXQgYywgZmxvYXQg
cm9vdHNbMl0pCit7CisgICAgaWYgKCFhKQorICAgICAgICByZXR1cm4gdmFsaWRVbml0RGl2aWRl
KC1jLCBiLCByb290cyk7CisKKyAgICBmbG9hdCogciA9IHJvb3RzOworCisgICAgZmxvYXQgUiA9
IGIqYiAtIDQqYSpjOworICAgIGlmIChSIDwgMCB8fCBpc25hbihSKSkgLy8gY29tcGxleCByb290
cworICAgICAgICByZXR1cm4gMDsKKyAgICBSID0gc3FydGYoUik7CisKKyAgICBmbG9hdCBRID0g
KGIgPCAwKSA/IC0oYiAtIFIpIC8gMiA6IC0oYiArIFIpIC8gMjsKKyAgICByICs9IHZhbGlkVW5p
dERpdmlkZShRLCBhLCByKTsKKyAgICByICs9IHZhbGlkVW5pdERpdmlkZShjLCBRLCByKTsKKyAg
ICBpZiAociAtIHJvb3RzID09IDIpCisgICAgICAgIGlmIChyb290c1swXSA+IHJvb3RzWzFdKQor
ICAgICAgICAgICAgc3RkOjpzd2FwKHJvb3RzWzBdLCByb290c1sxXSk7CisgICAgICAgIGVsc2Ug
aWYgKHJvb3RzWzBdID09IHJvb3RzWzFdKSAvLyBhcmUgdGhlIHJvb3RzIG5lYXJseSBlcXVhbD8K
KyAgICAgICAgICAgIHIgLT0gMTsgLy8gc2tpcCB0aGUgZG91YmxlIHJvb3QKKyAgICByZXR1cm4g
KGludCkociAtIHJvb3RzKTsKK30KKworLyoqIEN1YmljJyh0KSA9IHB0XjIgKyBxdCArIHIsIHdo
ZXJlCisgICAgcCA9IDMoLWEgKyAzKGIgLSBjKSArIGQpCisgICAgcSA9IDYoYSAtIDJiICsgYykK
KyAgICByID0gMyhiIC0gYSkKKyAgICBTb2x2ZSBmb3IgdCwga2VlcGluZyBvbmx5IHRob3NlIHRo
YXQgZml0IGJldHdlZW4gMCA8IHQgPCAxCisqLworaW50IGZpbmRDdWJpY0V4dHJlbWEoZmxvYXQg
YSwgZmxvYXQgYiwgZmxvYXQgYywgZmxvYXQgZCwgZmxvYXQgdFZhbHVlc1syXSkKK3sKKyAgICAv
LyB3ZSBkaXZpZGUgcCwgcSwgYW5kIHIgYnkgMyB0byBzaW1wbGlmeQorICAgIGZsb2F0IHAgPSBk
IC0gYSArIDMqKGIgLSBjKTsKKyAgICBmbG9hdCBxID0gMiooYSAtIGIgLSBiICsgYyk7CisgICAg
ZmxvYXQgciA9IGIgLSBhOworCisgICAgcmV0dXJuIGZpbmRVbml0UXVhZFJvb3RzKHAsIHEsIHIs
IHRWYWx1ZXMpOworfQorCit2b2lkIGludGVycG9sYXRlQ3ViaWNDb29yZHMoZmxvYXQgY29udHJv
bFBvaW50MCwgZmxvYXQgY29udHJvbFBvaW50MSwgZmxvYXQgY29udHJvbFBvaW50MiwgZmxvYXQg
Y29udHJvbFBvaW50MywgZmxvYXQqIGRzdCwgZmxvYXQgdCkKK3sKKyAgICBmbG9hdCBhYiA9IGlu
dGVycG9sYXRlKGNvbnRyb2xQb2ludDAsIGNvbnRyb2xQb2ludDEsIHQpOworICAgIGZsb2F0IGJj
ID0gaW50ZXJwb2xhdGUoY29udHJvbFBvaW50MSwgY29udHJvbFBvaW50MiwgdCk7CisgICAgZmxv
YXQgY2QgPSBpbnRlcnBvbGF0ZShjb250cm9sUG9pbnQyLCBjb250cm9sUG9pbnQzLCB0KTsKKyAg
ICBmbG9hdCBhYmMgPSBpbnRlcnBvbGF0ZShhYiwgYmMsIHQpOworICAgIGZsb2F0IGJjZCA9IGlu
dGVycG9sYXRlKGJjLCBjZCwgdCk7CisgICAgZmxvYXQgYWJjZCA9IGludGVycG9sYXRlKGFiYywg
YmNkLCB0KTsKKworICAgIGRzdFswXSA9IGNvbnRyb2xQb2ludDA7CisgICAgZHN0WzJdID0gYWI7
CisgICAgZHN0WzRdID0gYWJjOworICAgIGRzdFs2XSA9IGFiY2Q7CisgICAgZHN0WzhdID0gYmNk
OworICAgIGRzdFsxMF0gPSBjZDsKKyAgICBkc3RbMTJdID0gY29udHJvbFBvaW50MzsKK30KKwor
I2lmbmRlZiBOREVCVUcKK2Jvb2wgaXNVbml0SW50ZXJ2YWwoZmxvYXQgeCkKK3sKKyAgICByZXR1
cm4geCA+IDAgJiYgeCA8IDE7Cit9CisjZW5kaWYKKworLyogIGh0dHA6Ly9jb2RlLmdvb2dsZS5j
b20vcC9za2lhL2lzc3Vlcy9kZXRhaWw/aWQ9MzIKKworICAgIFRoaXMgdGVzdCBjb2RlIHdvdWxk
IGZhaWwgd2hlbiB3ZSBkaWRuJ3QgY2hlY2sgdGhlIHJldHVybiByZXN1bHQgb2YKKyAgICB2YWxp
ZF91bml0X2RpdmlkZSBpbiBTa0Nob3BDdWJpY0F0KC4uLiB0VmFsdWVzW10sIGludCByb290cyku
IFRoZSByZWFzb24gaXMKKyAgICB0aGF0IGFmdGVyIHRoZSBmaXJzdCBjaG9wLCB0aGUgcGFyYW1l
dGVycyB0byB2YWxpZF91bml0X2RpdmlkZSBhcmUgZXF1YWwKKyAgICAodGhhbmtzIHRvIGZpbml0
ZSBmbG9hdCBwcmVjaXNpb24gYW5kIHJvdW5kaW5nIGluIHRoZSBzdWJ0cmFjdHMpLiBUaHVzCisg
ICAgZXZlbiB0aG91Z2ggdGhlIDJuZCB0VmFsdWUgbG9va3MgPCAxLjAsIGFmdGVyIHdlIHJlbm9y
bWFsaXplIGl0LCB3ZSBlbmQKKyAgICB1cCB3aXRoIDEuMCwgaGVuY2UgdGhlIG5lZWQgdG8gY2hl
Y2sgYW5kIGp1c3QgcmV0dXJuIHRoZSBsYXN0IGN1YmljIGFzCisgICAgYSBkZWdlbmVyYXRlIGNs
dW1wIG9mIDQgcG9pbnRzIGluIHRoZSBzYW1lIHBsYWNlLgorCisgICAgc3RhdGljIHZvaWQgdGVz
dF9jdWJpYygpIHsKKyAgICAgICAgU2tQb2ludCBzcmNbNF0gPSB7CisgICAgICAgICAgICB7IDU1
Ni4yNTAwMCwgNTIzLjAzMDAzIH0sCisgICAgICAgICAgICB7IDU1Ni4yMzk5OSwgNTIyLjk2MDAy
IH0sCisgICAgICAgICAgICB7IDU1Ni4yMTk5NywgNTIyLjg5MDAxIH0sCisgICAgICAgICAgICB7
IDU1Ni4yMTk5NywgNTIyLjgyMDAxIH0KKyAgICAgICAgfTsKKyAgICAgICAgU2tQb2ludCBkc3Rb
MTBdOworICAgICAgICBTa1NjYWxhciB0dmFsW10gPSB7IDAuMzMzMzMzMzRmLCAwLjk5OTk5OTk0
ZiB9OworICAgICAgICBTa0Nob3BDdWJpY0F0KHNyYywgZHN0LCB0dmFsLCAyKTsKKyAgICB9Cisq
LworCit2b2lkIGNob3BDdWJpY0F0KGNvbnN0IEZsb2F0UG9pbnQgc3JjWzRdLCBGbG9hdFBvaW50
IGRzdFtdLCBjb25zdCBmbG9hdCB0VmFsdWVzW10sIGludCByb290cykKK3sKKyNpZm5kZWYgTkRF
QlVHCisgICAgZm9yIChpbnQgaSA9IDA7IGkgPCByb290cyAtIDE7ICsraSkgeworICAgICAgICBB
U1NFUlQoaXNVbml0SW50ZXJ2YWwodFZhbHVlc1tpXSkpOworICAgICAgICBBU1NFUlQoaXNVbml0
SW50ZXJ2YWwodFZhbHVlc1tpKzFdKSk7CisgICAgICAgIEFTU0VSVCh0VmFsdWVzW2ldIDwgdFZh
bHVlc1tpKzFdKTsKKyAgICB9CisjZW5kaWYKKworICAgIGlmICghZHN0KQorICAgICAgICByZXR1
cm47CisKKyAgICBpZiAoIXJvb3RzKSB7CisgICAgICAgIC8vIG5vdGhpbmcgdG8gY2hvcAorICAg
ICAgICBmb3IgKGludCBqID0gMDsgaiA8IDQ7ICsraikKKyAgICAgICAgICAgIGRzdFtqXSA9IHNy
Y1tqXTsKKyAgICAgICAgcmV0dXJuOworICAgIH0KKworICAgIGZsb2F0IHQgPSB0VmFsdWVzWzBd
OworICAgIEZsb2F0UG9pbnQgdG1wWzRdOworCisgICAgZm9yIChpbnQgaSA9IDA7IGkgPCByb290
czsgKytpKSB7CisgICAgICAgIExvb3BCbGlubk1hdGhVdGlsczo6Y2hvcEN1YmljQXQoc3JjLCBk
c3QsIHQpOworICAgICAgICBpZiAoaSA9PSByb290cyAtIDEpCisgICAgICAgICAgICBicmVhazsK
KworICAgICAgICBkc3QgKz0gMzsKKyAgICAgICAgLy8gTWFrZSBzcmMgcG9pbnQgdG8gdGhlIHJl
bWFpbmluZyBjdWJpYyAoYWZ0ZXIgdGhlIGNob3ApLgorICAgICAgICBmb3IgKGludCBqID0gMDsg
aiA8IDQ7ICsraikKKyAgICAgICAgICAgIHRtcFtqXSA9IGRzdFtqXTsKKyAgICAgICAgc3JjID0g
dG1wOworCisgICAgICAgIC8vIFdhdGNoIG91dCBmb3IgdGhlIGNhc2UgdGhhdCB0aGUgcmVub3Jt
YWxpemVkIHQgaXNuJ3QgaW4gcmFuZ2UuCisgICAgICAgIGlmICghdmFsaWRVbml0RGl2aWRlKHRW
YWx1ZXNbaSsxXSAtIHRWYWx1ZXNbaV0sCisgICAgICAgICAgICAgICAgICAgICAgICAgICAgIDEu
MGYgLSB0VmFsdWVzW2ldLCAmdCkpIHsKKyAgICAgICAgICAgIC8vIElmIGl0IGlzbid0LCBqdXN0
IGNyZWF0ZSBhIGRlZ2VuZXJhdGUgY3ViaWMuCisgICAgICAgICAgICBkc3RbNF0gPSBkc3RbNV0g
PSBkc3RbNl0gPSBzcmNbM107CisgICAgICAgICAgICBicmVhazsKKyAgICAgICAgfQorICAgIH0K
K30KKwordm9pZCBmbGF0dGVuRG91YmxlQ3ViaWNZRXh0cmVtYShGbG9hdFBvaW50IGNvb3Jkc1s3
XSkKK3sKKyAgICBjb29yZHNbMl0uc2V0WShjb29yZHNbM10ueSgpKTsKKyAgICBjb29yZHNbNF0u
c2V0WShjb29yZHNbM10ueSgpKTsKK30KKworaW50IGNob3BDdWJpY0F0WUV4dHJlbWEoY29uc3Qg
RmxvYXRQb2ludCBzcmNbNF0sIEZsb2F0UG9pbnQgZHN0WzEwXSkKK3sKKyAgICBmbG9hdCB0VmFs
dWVzWzJdOworICAgIGludCByb290cyA9IGZpbmRDdWJpY0V4dHJlbWEoc3JjWzBdLnkoKSwgc3Jj
WzFdLnkoKSwgc3JjWzJdLnkoKSwgc3JjWzNdLnkoKSwgdFZhbHVlcyk7CisKKyAgICBjaG9wQ3Vi
aWNBdChzcmMsIGRzdCwgdFZhbHVlcywgcm9vdHMpOworICAgIGlmIChyb290cykgeworICAgICAg
ICAvLyB3ZSBkbyBzb21lIGNsZWFudXAgdG8gZW5zdXJlIG91ciBZIGV4dHJlbWEgYXJlIGZsYXQK
KyAgICAgICAgZmxhdHRlbkRvdWJsZUN1YmljWUV4dHJlbWEoJmRzdFswXSk7CisgICAgICAgIGlm
IChyb290cyA9PSAyKQorICAgICAgICAgICAgZmxhdHRlbkRvdWJsZUN1YmljWUV4dHJlbWEoJmRz
dFszXSk7CisgICAgfQorICAgIHJldHVybiByb290czsKK30KKworfSAvLyBhbm9ueW1vdXMgbmFt
ZXNwYWNlCisKKy8vIFB1YmxpYyBjdWJpYyBvcGVyYXRpb25zLgorCit2b2lkIGNob3BDdWJpY0F0
KGNvbnN0IEZsb2F0UG9pbnQgc3JjWzRdLCBGbG9hdFBvaW50IGRzdFs3XSwgZmxvYXQgdCkKK3sK
KyAgICBBU1NFUlQodCA+IDAgJiYgdCA8IDEpOworCisgICAgZmxvYXQgb3V0cHV0WzE0XTsKKyAg
ICBpbnRlcnBvbGF0ZUN1YmljQ29vcmRzKHNyY1swXS54KCksIHNyY1sxXS54KCksIHNyY1syXS54
KCksIHNyY1szXS54KCksICZvdXRwdXRbMF0sIHQpOworICAgIGludGVycG9sYXRlQ3ViaWNDb29y
ZHMoc3JjWzBdLnkoKSwgc3JjWzFdLnkoKSwgc3JjWzJdLnkoKSwgc3JjWzNdLnkoKSwgJm91dHB1
dFsxXSwgdCk7CisgICAgZm9yIChpbnQgaSA9IDA7IGkgPCA3OyBpKyspCisgICAgICAgIGRzdFtp
XS5zZXQob3V0cHV0WzIgKiBpXSwgb3V0cHV0WzIgKiBpICsgMV0pOworfQorCisvLyBQdWJsaWMg
WFJheSBxdWVyaWVzLgorCitib29sIHhSYXlDcm9zc2VzTGluZShjb25zdCBYUmF5JiB4UmF5LCBj
b25zdCBGbG9hdFBvaW50IHB0c1syXSwgYm9vbCYgYW1iaWd1b3VzKQoreworICAgIGFtYmlndW91
cyA9IGZhbHNlOworCisgICAgLy8gRGV0ZXJtaW5lIHF1aWNrIGRpc2NhcmRzLgorICAgIC8vIENv
bnNpZGVyIHF1ZXJ5IGxpbmUgZ29pbmcgZXhhY3RseSB0aHJvdWdoIHBvaW50IDAgdG8gbm90Cisg
ICAgLy8gaW50ZXJzZWN0LCBmb3Igc3ltbWV0cnkgd2l0aCB4UmF5Q3Jvc3Nlc01vbm90b25pY0N1
YmljLgorICAgIGlmICh4UmF5LnkoKSA9PSBwdHNbMF0ueSgpKSB7CisgICAgICAgIGFtYmlndW91
cyA9IHRydWU7CisgICAgICAgIHJldHVybiBmYWxzZTsKKyAgICB9CisgICAgaWYgKHhSYXkueSgp
IDwgcHRzWzBdLnkoKSAmJiB4UmF5LnkoKSA8IHB0c1sxXS55KCkpCisgICAgICAgIHJldHVybiBm
YWxzZTsKKyAgICBpZiAoeFJheS55KCkgPiBwdHNbMF0ueSgpICYmIHhSYXkueSgpID4gcHRzWzFd
LnkoKSkKKyAgICAgICAgcmV0dXJuIGZhbHNlOworICAgIGlmICh4UmF5LngoKSA+IHB0c1swXS54
KCkgJiYgeFJheS54KCkgPiBwdHNbMV0ueCgpKQorICAgICAgICByZXR1cm4gZmFsc2U7CisgICAg
Ly8gRGV0ZXJtaW5lIGRlZ2VuZXJhdGUgY2FzZXMKKyAgICBpZiAobmVhcmx5WmVybyhwdHNbMF0u
eSgpIC0gcHRzWzFdLnkoKSkpCisgICAgICAgIHJldHVybiBmYWxzZTsKKyAgICBpZiAobmVhcmx5
WmVybyhwdHNbMF0ueCgpIC0gcHRzWzFdLngoKSkpIHsKKyAgICAgICAgLy8gV2UndmUgYWxyZWFk
eSBkZXRlcm1pbmVkIHRoZSBxdWVyeSBwb2ludCBsaWVzIHdpdGhpbiB0aGUKKyAgICAgICAgLy8g
dmVydGljYWwgcmFuZ2Ugb2YgdGhlIGxpbmUgc2VnbWVudC4KKyAgICAgICAgaWYgKHhSYXkueCgp
IDw9IHB0c1swXS54KCkpIHsKKyAgICAgICAgICAgIGFtYmlndW91cyA9ICh4UmF5LnkoKSA9PSBw
dHNbMV0ueSgpKTsKKyAgICAgICAgICAgIHJldHVybiB0cnVlOworICAgICAgICB9CisgICAgICAg
IHJldHVybiBmYWxzZTsKKyAgICB9CisgICAgLy8gQW1iaWd1aXR5IGNoZWNrCisgICAgaWYgKHhS
YXkueSgpID09IHB0c1sxXS55KCkpIHsKKyAgICAgICAgaWYgKHhSYXkueCgpIDw9IHB0c1sxXS54
KCkpIHsKKyAgICAgICAgICAgIGFtYmlndW91cyA9IHRydWU7CisgICAgICAgICAgICByZXR1cm4g
dHJ1ZTsKKyAgICAgICAgfQorICAgICAgICByZXR1cm4gZmFsc2U7CisgICAgfQorICAgIC8vIEZ1
bGwgbGluZSBzZWdtZW50IGV2YWx1YXRpb24KKyAgICBmbG9hdCBkZWx0YVkgPSBwdHNbMV0ueSgp
IC0gcHRzWzBdLnkoKTsKKyAgICBmbG9hdCBkZWx0YVggPSBwdHNbMV0ueCgpIC0gcHRzWzBdLngo
KTsKKyAgICBmbG9hdCBzbG9wZSA9IGRlbHRhWSAvIGRlbHRhWDsKKyAgICBmbG9hdCBiID0gcHRz
WzBdLnkoKSAtIHNsb3BlICogcHRzWzBdLngoKTsKKyAgICAvLyBTb2x2ZSBmb3IgeCBjb29yZGlu
YXRlIGF0IHkgPSB4UmF5LnkoKQorICAgIGZsb2F0IHggPSAoeFJheS55KCkgLSBiKSAvIHNsb3Bl
OworICAgIHJldHVybiB4UmF5LngoKSA8PSB4OworfQorCitpbnQgbnVtWFJheUNyb3NzaW5nc0Zv
ckN1YmljKGNvbnN0IFhSYXkmIHhSYXksIGNvbnN0IEZsb2F0UG9pbnQgY3ViaWNbNF0sIGJvb2wm
IGFtYmlndW91cykKK3sKKyAgICBpbnQgbnVtQ3Jvc3NpbmdzID0gMDsKKyAgICBGbG9hdFBvaW50
IG1vbm90b25pY0N1Ymljc1sxMF07CisgICAgaW50IG51bU1vbm90b25pY0N1YmljcyA9IDEgKyBj
aG9wQ3ViaWNBdFlFeHRyZW1hKGN1YmljLCBtb25vdG9uaWNDdWJpY3MpOworICAgIGFtYmlndW91
cyA9IGZhbHNlOworICAgIEZsb2F0UG9pbnQqIG1vbm90b25pY0N1Ymljc1BvaW50ZXIgPSAmbW9u
b3RvbmljQ3ViaWNzWzBdOworICAgIGZvciAoaW50IGkgPSAwOyBpIDwgbnVtTW9ub3RvbmljQ3Vi
aWNzOyArK2kpIHsKKyAgICAgICAgaWYgKHhSYXlDcm9zc2VzTW9ub3RvbmljQ3ViaWMoeFJheSwg
bW9ub3RvbmljQ3ViaWNzUG9pbnRlciwgYW1iaWd1b3VzKSkKKyAgICAgICAgICAgICsrbnVtQ3Jv
c3NpbmdzOworICAgICAgICBpZiAoYW1iaWd1b3VzKQorICAgICAgICAgICAgcmV0dXJuIDA7Cisg
ICAgICAgIG1vbm90b25pY0N1Ymljc1BvaW50ZXIgKz0gMzsKKyAgICB9CisgICAgcmV0dXJuIG51
bUNyb3NzaW5nczsKK30KKworfSAvLyBuYW1lc3BhY2UgTG9vcEJsaW5uTWF0aFV0aWxzCit9IC8v
IG5hbWVzcGFjZSBXZWJDb3JlCkluZGV4OiBXZWJDb3JlL3BsYXRmb3JtL2dyYXBoaWNzL2dwdS9M
b29wQmxpbm5NYXRoVXRpbHMuaAo9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09
PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ci0tLSBXZWJDb3JlL3BsYXRmb3JtL2dyYXBo
aWNzL2dwdS9Mb29wQmxpbm5NYXRoVXRpbHMuaAkocmV2aXNpb24gMCkKKysrIFdlYkNvcmUvcGxh
dGZvcm0vZ3JhcGhpY3MvZ3B1L0xvb3BCbGlubk1hdGhVdGlscy5oCShyZXZpc2lvbiAwKQpAQCAt
MCwwICsxLDEzOCBAQAorLyoKKyAqIENvcHlyaWdodCAoQykgMjAxMCBHb29nbGUgSW5jLiBBbGwg
cmlnaHRzIHJlc2VydmVkLgorICoKKyAqIFJlZGlzdHJpYnV0aW9uIGFuZCB1c2UgaW4gc291cmNl
IGFuZCBiaW5hcnkgZm9ybXMsIHdpdGggb3Igd2l0aG91dAorICogbW9kaWZpY2F0aW9uLCBhcmUg
cGVybWl0dGVkIHByb3ZpZGVkIHRoYXQgdGhlIGZvbGxvd2luZyBjb25kaXRpb25zCisgKiBhcmUg
bWV0OgorICoKKyAqIDEuICBSZWRpc3RyaWJ1dGlvbnMgb2Ygc291cmNlIGNvZGUgbXVzdCByZXRh
aW4gdGhlIGFib3ZlIGNvcHlyaWdodAorICogICAgIG5vdGljZSwgdGhpcyBsaXN0IG9mIGNvbmRp
dGlvbnMgYW5kIHRoZSBmb2xsb3dpbmcgZGlzY2xhaW1lci4KKyAqIDIuICBSZWRpc3RyaWJ1dGlv
bnMgaW4gYmluYXJ5IGZvcm0gbXVzdCByZXByb2R1Y2UgdGhlIGFib3ZlIGNvcHlyaWdodAorICog
ICAgIG5vdGljZSwgdGhpcyBsaXN0IG9mIGNvbmRpdGlvbnMgYW5kIHRoZSBmb2xsb3dpbmcgZGlz
Y2xhaW1lciBpbiB0aGUKKyAqICAgICBkb2N1bWVudGF0aW9uIGFuZC9vciBvdGhlciBtYXRlcmlh
bHMgcHJvdmlkZWQgd2l0aCB0aGUgZGlzdHJpYnV0aW9uLgorICoKKyAqIFRISVMgU09GVFdBUkUg
SVMgUFJPVklERUQgQlkgQVBQTEUgQU5EIElUUyBDT05UUklCVVRPUlMgIkFTIElTIiBBTkQgQU5Z
CisgKiBFWFBSRVNTIE9SIElNUExJRUQgV0FSUkFOVElFUywgSU5DTFVESU5HLCBCVVQgTk9UIExJ
TUlURUQgVE8sIFRIRSBJTVBMSUVECisgKiBXQVJSQU5USUVTIE9GIE1FUkNIQU5UQUJJTElUWSBB
TkQgRklUTkVTUyBGT1IgQSBQQVJUSUNVTEFSIFBVUlBPU0UgQVJFCisgKiBESVNDTEFJTUVELiBJ
TiBOTyBFVkVOVCBTSEFMTCBBUFBMRSBPUiBJVFMgQ09OVFJJQlVUT1JTIEJFIExJQUJMRSBGT1Ig
QU5ZCisgKiBESVJFQ1QsIElORElSRUNULCBJTkNJREVOVEFMLCBTUEVDSUFMLCBFWEVNUExBUlks
IE9SIENPTlNFUVVFTlRJQUwgREFNQUdFUworICogKElOQ0xVRElORywgQlVUIE5PVCBMSU1JVEVE
IFRPLCBQUk9DVVJFTUVOVCBPRiBTVUJTVElUVVRFIEdPT0RTIE9SIFNFUlZJQ0VTOworICogTE9T
UyBPRiBVU0UsIERBVEEsIE9SIFBST0ZJVFM7IE9SIEJVU0lORVNTIElOVEVSUlVQVElPTikgSE9X
RVZFUiBDQVVTRUQgQU5ECisgKiBPTiBBTlkgVEhFT1JZIE9GIExJQUJJTElUWSwgV0hFVEhFUiBJ
TiBDT05UUkFDVCwgU1RSSUNUIExJQUJJTElUWSwgT1IgVE9SVAorICogKElOQ0xVRElORyBORUdM
SUdFTkNFIE9SIE9USEVSV0lTRSkgQVJJU0lORyBJTiBBTlkgV0FZIE9VVCBPRiBUSEUgVVNFIE9G
CisgKiBUSElTIFNPRlRXQVJFLCBFVkVOIElGIEFEVklTRUQgT0YgVEhFIFBPU1NJQklMSVRZIE9G
IFNVQ0ggREFNQUdFLgorICovCisKKyNpZm5kZWYgTG9vcEJsaW5uTWF0aFV0aWxzX2gKKyNkZWZp
bmUgTG9vcEJsaW5uTWF0aFV0aWxzX2gKKworI2luY2x1ZGUgIkZsb2F0UG9pbnQuaCIKKyNpbmNs
dWRlICJGbG9hdFBvaW50M0QuaCIKKyNpbmNsdWRlIDxtYXRoLmg+CisKK25hbWVzcGFjZSBXZWJD
b3JlIHsKKworLy8gVXNlIGEgbmFtZXNwYWNlIGZvciB0aGVzZSBzbyB3ZSBjYW4gZWFzaWx5IGlt
cG9ydCB0aGVtLgorbmFtZXNwYWNlIExvb3BCbGlubk1hdGhVdGlscyB7CisKKy8vIEEgcm91bmRv
ZmYgZmFjdG9yIGluIHRoZSBjdWJpYyBjbGFzc2lmaWNhdGlvbiBhbmQgdGV4dHVyZSBjb29yZGlu
YXRlCisvLyBnZW5lcmF0aW9uIGFsZ29yaXRobXMuIEl0IGlzIG9ubHkgYW4gaW1wbGVtZW50YXRp
b24gZGV0YWlsIGFuZCBzaG91bGQKKy8vIG5vdCBiZSByZWZlcmVuY2VkIGJ5IGNvZGUgb3V0c2lk
ZSB0aGlzIG5hbWVzcGFjZS4gSXQgcHJpbWFyaWx5CisvLyBkZXRlcm1pbmVzIHRoZSBoYW5kbGlu
ZyBvZiBjb3JuZXIgY2FzZXMgZHVyaW5nIHRoZSBjbGFzc2lmaWNhdGlvbgorLy8gcHJvY2Vzcy4g
QmUgY2FyZWZ1bCB3aGVuIGFkanVzdGluZyB0aGlzOyBpdCBoYXMgYmVlbiBkZXRlcm1pbmVkCisv
LyBlbXBpcmljYWxseSB0byB3b3JrIHdlbGwuIFdoZW4gY2hhbmdpbmcgaXQsIHlvdSBzaG91bGQg
bG9vayBpbgorLy8gcGFydGljdWxhciBhdCBzaGFwZXMgdGhhdCBjb250YWluIHF1YWRyYXRpYyBj
dXJ2ZXMgYW5kIGVuc3VyZSB0aGV5IHN0aWxsCisvLyBsb29rIHNtb290aC4gT25jZSBwaXhlbCB0
ZXN0cyBhcmUgcnVubmluZyBhZ2FpbnN0IHRoaXMgYWxnb3JpdGhtLCB0aGV5CisvLyBzaG91bGQg
cHJvdmlkZSBzdWZmaWNpZW50IGNvdmVyYWdlIHRvIGVuc3VyZSB0aGF0IGFkanVzdGluZyB0aGUg
Y29uc3RhbnQKKy8vIHdvbid0IGJyZWFrIGFueXRoaW5nLgorY29uc3QgZmxvYXQgSW1wbGVtZW50
YXRpb25FcHNpbG9uID0gNS4wZS00ZjsKKworLy8gUmV0dXJucyB6ZXJvIGlmIHZhbHVlIGlzIHdp
dGhpbiArLy1JbXBsZW1lbnRhdGlvbkVwc2lsb24gb2YgemVyby4KK2lubGluZSBmbG9hdCByb3Vu
ZFRvWmVybyhmbG9hdCB2YWwpCit7CisgICAgaWYgKHZhbCA8IEltcGxlbWVudGF0aW9uRXBzaWxv
biAmJiB2YWwgPiAtSW1wbGVtZW50YXRpb25FcHNpbG9uKQorICAgICAgICByZXR1cm4gMDsKKyAg
ICByZXR1cm4gdmFsOworfQorCitpbmxpbmUgYm9vbCBhcHByb3hFcXVhbChjb25zdCBGbG9hdFBv
aW50JiB2MCwgY29uc3QgRmxvYXRQb2ludCYgdjEpCit7CisgICAgcmV0dXJuICh2MCAtIHYxKS5k
aWFnb25hbExlbmd0aFNxdWFyZWQoKSA8IEltcGxlbWVudGF0aW9uRXBzaWxvbiAqIEltcGxlbWVu
dGF0aW9uRXBzaWxvbjsKK30KKworaW5saW5lIGJvb2wgYXBwcm94RXF1YWwoY29uc3QgRmxvYXRQ
b2ludDNEJiB2MCwgY29uc3QgRmxvYXRQb2ludDNEJiB2MSkKK3sKKyAgICByZXR1cm4gKHYwIC0g
djEpLmxlbmd0aFNxdWFyZWQoKSA8IEltcGxlbWVudGF0aW9uRXBzaWxvbiAqIEltcGxlbWVudGF0
aW9uRXBzaWxvbjsKK30KKworaW5saW5lIGJvb2wgYXBwcm94RXF1YWwoZmxvYXQgZjAsIGZsb2F0
IGYxKQoreworICAgIHJldHVybiBmYWJzZihmMCAtIGYxKSA8IEltcGxlbWVudGF0aW9uRXBzaWxv
bjsKK30KKworLy8gRGV0ZXJtaW5lcyB3aGV0aGVyIHRoZSBsaW5lIHNlZ21lbnQgYmV0d2VlbiAo
cDEsIHExKSBpbnRlcnNlY3RzCisvLyB0aGF0IGJldHdlZW4gKHAyLCBxMikuCitib29sIGxpbmVz
SW50ZXJzZWN0KGNvbnN0IEZsb2F0UG9pbnQmIHAxLAorICAgICAgICAgICAgICAgICAgICBjb25z
dCBGbG9hdFBvaW50JiBxMSwKKyAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYg
cDIsCisgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIHEyKTsKKworLy8gRGV0
ZXJtaW5lcyB3aGV0aGVyICJwb2ludCIgaXMgaW5zaWRlIHRoZSAyRCB0cmlhbmdsZSBkZWZpbmVk
IGJ5CisvLyB2ZXJ0aWNlcyBhLCBiLCBhbmQgYy4gVGhpcyB0ZXN0IGRlZmluZXMgdGhhdCBwb2lu
dHMgZXhhY3RseSBvbiBhbgorLy8gZWRnZSBhcmUgbm90IGNvbnNpZGVyZWQgdG8gYmUgaW5zaWRl
IHRoZSB0cmlhbmdsZS4KK2Jvb2wgcG9pbnRJblRyaWFuZ2xlKGNvbnN0IEZsb2F0UG9pbnQmIHBv
aW50LAorICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgYSwKKyAgICAgICAg
ICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIGIsCisgICAgICAgICAgICAgICAgICAgICBj
b25zdCBGbG9hdFBvaW50JiBjKTsKKworLy8gRGV0ZXJtaW5lcyB3aGV0aGVyIHRoZSB0cmlhbmds
ZXMgZGVmaW5lZCBieSB0aGUgcG9pbnRzIChhMSwgYjEsIGMxKQorLy8gYW5kIChhMiwgYjIsIGMy
KSBvdmVybGFwLiBUaGUgZGVmaW5pdGlvbiBvZiB0aGlzIGZ1bmN0aW9uIGlzIHRoYXQKKy8vIGlm
IHRoZSB0d28gdHJpYW5nbGVzIG9ubHkgc2hhcmUgYW4gYWRqYWNlbnQgZWRnZSBvciB2ZXJ0ZXgs
IHRoZXkKKy8vIGFyZSBub3QgY29uc2lkZXJlZCB0byBvdmVybGFwLgorYm9vbCB0cmlhbmdsZXNP
dmVybGFwKGNvbnN0IEZsb2F0UG9pbnQmIGExLAorICAgICAgICAgICAgICAgICAgICAgIGNvbnN0
IEZsb2F0UG9pbnQmIGIxLAorICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQm
IGMxLAorICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIGEyLAorICAgICAg
ICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIGIyLAorICAgICAgICAgICAgICAgICAg
ICAgIGNvbnN0IEZsb2F0UG9pbnQmIGMyKTsKKworLy8gR2l2ZW4gYSBzcmMgY3ViaWMgYmV6aWVy
LCBjaG9wcyBpdCBhdCB0aGUgc3BlY2lmaWVkIHQgdmFsdWUsCisvLyB3aGVyZSAwIDwgdCA8IDEs
IGFuZCByZXR1cm5zIHRoZSB0d28gbmV3IGN1YmljcyBpbiBkc3RbMC4uM10KKy8vIGFuZCBkc3Rb
My4uNl0uCit2b2lkIGNob3BDdWJpY0F0KGNvbnN0IEZsb2F0UG9pbnQgc3JjWzRdLCBGbG9hdFBv
aW50IGRzdFs3XSwgZmxvYXQgdCk7CisKKy8vICJYLVJheSIgcXVlcmllcy4gQW4gWFJheSBpcyBh
IGhhbGYtbGluZSBvcmlnaW5hdGluZyBhdCB0aGUgZ2l2ZW4KKy8vIHBvaW50IGFuZCBleHRlbmRp
bmcgdG8geD0raW5maW5pdHkuCit0eXBlZGVmIEZsb2F0UG9pbnQgWFJheTsKKworLy8gR2l2ZW4g
YW4gYXJiaXRyYXJ5IGN1YmljIGJlemllciwgcmV0dXJuIHRoZSBudW1iZXIgb2YgdGltZXMgYW4g
WFJheQorLy8gY3Jvc3NlcyB0aGUgY3ViaWMuIFZhbGlkIHJldHVybiB2YWx1ZXMgYXJlIFswLi4z
XS4KKy8vCisvLyBCeSBkZWZpbml0aW9uIHRoZSBjdWJpYyBpcyBvcGVuIGF0IHRoZSBzdGFydGlu
ZyBwb2ludDsgaW4gb3RoZXIKKy8vIHdvcmRzLCBpZiBwdC5mWSBpcyBlcXVpdmFsZW50IHRvIGN1
YmljWzBdLmZZLCBhbmQgcHQuZlggaXMgdG8gdGhlCisvLyBsZWZ0IG9mIHRoZSBjdXJ2ZSwgdGhl
IGxpbmUgaXMgbm90IGNvbnNpZGVyZWQgdG8gY3Jvc3MgdGhlIGN1cnZlLAorLy8gYnV0IGlmIGl0
IGlzIGVxdWFsIHRvIGN1YmljWzNdLmZZIHRoZW4gaXQgaXMgY29uc2lkZXJlZCB0bworLy8gY3Jv
c3MuCisvLworLy8gT3V0Z29pbmcgImFtYmlndW91cyIgYXJndW1lbnQgaW5kaWNhdGVzIHdoZXRo
ZXIgdGhlIGFuc3dlciBpcyBhbWJpZ3VvdXMKKy8vIGJlY2F1c2UgdGhlIHF1ZXJ5IG9jY3VycmVk
IGV4YWN0bHkgYXQgb25lIG9mIHRoZSBlbmRwb2ludHMnIHkKKy8vIGNvb3JkaW5hdGVzIG9yIGF0
IGEgdGFuZ2VudCBwb2ludCwgaW5kaWNhdGluZyB0aGF0IGFub3RoZXIgcXVlcnkgeQorLy8gY29v
cmRpbmF0ZSBpcyBwcmVmZXJyZWQgZm9yIHJvYnVzdG5lc3MuCitpbnQgbnVtWFJheUNyb3NzaW5n
c0ZvckN1YmljKGNvbnN0IFhSYXkmIHhSYXksCisgICAgICAgICAgICAgICAgICAgICAgICAgICAg
IGNvbnN0IEZsb2F0UG9pbnQgY3ViaWNbNF0sCisgICAgICAgICAgICAgICAgICAgICAgICAgICAg
IGJvb2wmIGFtYmlndW91cyk7CisKKy8vIEdpdmVuIGEgbGluZSBzZWdtZW50IGZyb20gbGluZUVu
ZHBvaW50c1swXSB0byBsaW5lRW5kcG9pbnRzWzFdLCBhbmQgYW4KKy8vIFhSYXksIHJldHVybnMg
dHJ1ZSBpZiB0aGV5IGludGVyc2VjdC4gT3V0Z29pbmcgImFtYmlndW91cyIgYXJndW1lbnQKKy8v
IGluZGljYXRlcyB3aGV0aGVyIHRoZSBhbnN3ZXIgaXMgYW1iaWd1b3VzIGJlY2F1c2UgdGhlIHF1
ZXJ5IG9jY3VycmVkCisvLyBleGFjdGx5IGF0IG9uZSBvZiB0aGUgZW5kcG9pbnRzJyB5IGNvb3Jk
aW5hdGVzLCBpbmRpY2F0aW5nIHRoYXQgYW5vdGhlcgorLy8gcXVlcnkgeSBjb29yZGluYXRlIGlz
IHByZWZlcnJlZCBmb3Igcm9idXN0bmVzcy4KK2Jvb2wgeFJheUNyb3NzZXNMaW5lKGNvbnN0IFhS
YXkmIHhSYXksCisgICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50IGxpbmVFbmRw
b2ludHNbMl0sCisgICAgICAgICAgICAgICAgICAgICBib29sJiBhbWJpZ3VvdXMpOworCit9IC8v
IG5hbWVzcGFjZSBMb29wQmxpbm5NYXRoVXRpbHMKKworfSAvLyBuYW1lc3BhY2UgV2ViQ29yZQor
CisjZW5kaWYgLy8gTG9vcEJsaW5uTWF0aFV0aWxzX2gK
</data>
<flag name="review"
          id="56288"
          type_id="1"
          status="-"
          setter="jamesr"
    />
    <flag name="commit-queue"
          id="56289"
          type_id="3"
          status="-"
          setter="kbr"
    />
          </attachment>
          <attachment
              isobsolete="1"
              ispatch="1"
              isprivate="0"
          >
            <attachid>67126</attachid>
            <date>2010-09-09 17:47:14 -0700</date>
            <delta_ts>2010-09-09 18:01:07 -0700</delta_ts>
            <desc>Revised patch</desc>
            <filename>math-utils.patch</filename>
            <type>text/plain</type>
            <size>25547</size>
            <attacher name="Kenneth Russell">kbr</attacher>
            
              <data encoding="base64">SW5kZXg6IFdlYkNvcmUvQ2hhbmdlTG9nCj09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09
PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0KLS0tIFdlYkNvcmUvQ2hhbmdlTG9n
CShyZXZpc2lvbiA2NzEzMykKKysrIFdlYkNvcmUvQ2hhbmdlTG9nCSh3b3JraW5nIGNvcHkpCkBA
IC0xLDMgKzEsMjUgQEAKKzIwMTAtMDktMDkgIEtlbm5ldGggUnVzc2VsbCAgPGtickBnb29nbGUu
Y29tPgorCisgICAgICAgIFJldmlld2VkIGJ5IE5PQk9EWSAoT09QUyEpLgorCisgICAgICAgIEFk
ZCBtYXRoIHV0aWxpdGllcyBmb3IgY3ViaWMgY3VydmUgcHJvY2Vzc2luZworICAgICAgICBodHRw
czovL2J1Z3Mud2Via2l0Lm9yZy9zaG93X2J1Zy5jZ2k/aWQ9NDUyNTEKKworICAgICAgICBBZGRp
bmcgbWF0aGVtYXRpYyB1dGlsaXRpZXMgbmVlZGVkIGZvciB0aGUgR1BVIGFjY2VsZXJhdGVkIHBh
dGgKKyAgICAgICAgcmVuZGVyaW5nIGFsZ29yaXRobSBmcm9tIEdQVSBHZW1zIDMuIE5vIHRlc3Rz
IHlldDsgd2lsbCBiZSB0ZXN0ZWQKKyAgICAgICAgaW4gY29uanVuY3Rpb24gd2l0aCBsYXRlciBj
b2RlLgorCisgICAgICAgICogcGxhdGZvcm0vZ3JhcGhpY3MvZ3B1L0xvb3BCbGlubk1hdGhVdGls
cy5jcHA6IEFkZGVkLgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxzOjpyb3Vu
ZFRvWmVybyk6CisgICAgICAgIChXZWJDb3JlOjpMb29wQmxpbm5NYXRoVXRpbHM6OmFwcHJveEVx
dWFsKToKKyAgICAgICAgKFdlYkNvcmU6Okxvb3BCbGlubk1hdGhVdGlsczo6bGluZXNJbnRlcnNl
Y3QpOgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxzOjpwb2ludEluVHJpYW5n
bGUpOgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxzOjp0cmlhbmdsZXNPdmVy
bGFwKToKKyAgICAgICAgKFdlYkNvcmU6Okxvb3BCbGlubk1hdGhVdGlsczo6Y2hvcEN1YmljQXQp
OgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxzOjp4UmF5Q3Jvc3Nlc0xpbmUp
OgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxzOjpudW1YUmF5Q3Jvc3Npbmdz
Rm9yQ3ViaWMpOgorICAgICAgICAqIHBsYXRmb3JtL2dyYXBoaWNzL2dwdS9Mb29wQmxpbm5NYXRo
VXRpbHMuaDogQWRkZWQuCisKIDIwMTAtMDktMDkgIENocmlzIFJvZ2VycyAgPGNyb2dlcnNAZ29v
Z2xlLmNvbT4KIAogICAgICAgICBSZXZpZXdlZCBieSBLZW5uZXRoIFJ1c3NlbGwuCkluZGV4OiBX
ZWJDb3JlL3BsYXRmb3JtL2dyYXBoaWNzL2dwdS9Mb29wQmxpbm5NYXRoVXRpbHMuY3BwCj09PT09
PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09
PT09PT0KLS0tIFdlYkNvcmUvcGxhdGZvcm0vZ3JhcGhpY3MvZ3B1L0xvb3BCbGlubk1hdGhVdGls
cy5jcHAJKHJldmlzaW9uIDApCisrKyBXZWJDb3JlL3BsYXRmb3JtL2dyYXBoaWNzL2dwdS9Mb29w
Qmxpbm5NYXRoVXRpbHMuY3BwCShyZXZpc2lvbiAwKQpAQCAtMCwwICsxLDU2NSBAQAorLyoKKyAq
IENvcHlyaWdodCAoQykgMjAxMCBHb29nbGUgSW5jLiBBbGwgcmlnaHRzIHJlc2VydmVkLgorICoK
KyAqIFJlZGlzdHJpYnV0aW9uIGFuZCB1c2UgaW4gc291cmNlIGFuZCBiaW5hcnkgZm9ybXMsIHdp
dGggb3Igd2l0aG91dAorICogbW9kaWZpY2F0aW9uLCBhcmUgcGVybWl0dGVkIHByb3ZpZGVkIHRo
YXQgdGhlIGZvbGxvd2luZyBjb25kaXRpb25zCisgKiBhcmUgbWV0OgorICoKKyAqIDEuICBSZWRp
c3RyaWJ1dGlvbnMgb2Ygc291cmNlIGNvZGUgbXVzdCByZXRhaW4gdGhlIGFib3ZlIGNvcHlyaWdo
dAorICogICAgIG5vdGljZSwgdGhpcyBsaXN0IG9mIGNvbmRpdGlvbnMgYW5kIHRoZSBmb2xsb3dp
bmcgZGlzY2xhaW1lci4KKyAqIDIuICBSZWRpc3RyaWJ1dGlvbnMgaW4gYmluYXJ5IGZvcm0gbXVz
dCByZXByb2R1Y2UgdGhlIGFib3ZlIGNvcHlyaWdodAorICogICAgIG5vdGljZSwgdGhpcyBsaXN0
IG9mIGNvbmRpdGlvbnMgYW5kIHRoZSBmb2xsb3dpbmcgZGlzY2xhaW1lciBpbiB0aGUKKyAqICAg
ICBkb2N1bWVudGF0aW9uIGFuZC9vciBvdGhlciBtYXRlcmlhbHMgcHJvdmlkZWQgd2l0aCB0aGUg
ZGlzdHJpYnV0aW9uLgorICoKKyAqIFRISVMgU09GVFdBUkUgSVMgUFJPVklERUQgQlkgQVBQTEUg
QU5EIElUUyBDT05UUklCVVRPUlMgIkFTIElTIiBBTkQgQU5ZCisgKiBFWFBSRVNTIE9SIElNUExJ
RUQgV0FSUkFOVElFUywgSU5DTFVESU5HLCBCVVQgTk9UIExJTUlURUQgVE8sIFRIRSBJTVBMSUVE
CisgKiBXQVJSQU5USUVTIE9GIE1FUkNIQU5UQUJJTElUWSBBTkQgRklUTkVTUyBGT1IgQSBQQVJU
SUNVTEFSIFBVUlBPU0UgQVJFCisgKiBESVNDTEFJTUVELiBJTiBOTyBFVkVOVCBTSEFMTCBBUFBM
RSBPUiBJVFMgQ09OVFJJQlVUT1JTIEJFIExJQUJMRSBGT1IgQU5ZCisgKiBESVJFQ1QsIElORElS
RUNULCBJTkNJREVOVEFMLCBTUEVDSUFMLCBFWEVNUExBUlksIE9SIENPTlNFUVVFTlRJQUwgREFN
QUdFUworICogKElOQ0xVRElORywgQlVUIE5PVCBMSU1JVEVEIFRPLCBQUk9DVVJFTUVOVCBPRiBT
VUJTVElUVVRFIEdPT0RTIE9SIFNFUlZJQ0VTOworICogTE9TUyBPRiBVU0UsIERBVEEsIE9SIFBS
T0ZJVFM7IE9SIEJVU0lORVNTIElOVEVSUlVQVElPTikgSE9XRVZFUiBDQVVTRUQgQU5ECisgKiBP
TiBBTlkgVEhFT1JZIE9GIExJQUJJTElUWSwgV0hFVEhFUiBJTiBDT05UUkFDVCwgU1RSSUNUIExJ
QUJJTElUWSwgT1IgVE9SVAorICogKElOQ0xVRElORyBORUdMSUdFTkNFIE9SIE9USEVSV0lTRSkg
QVJJU0lORyBJTiBBTlkgV0FZIE9VVCBPRiBUSEUgVVNFIE9GCisgKiBUSElTIFNPRlRXQVJFLCBF
VkVOIElGIEFEVklTRUQgT0YgVEhFIFBPU1NJQklMSVRZIE9GIFNVQ0ggREFNQUdFLgorICovCisK
KyNpbmNsdWRlICJjb25maWcuaCIKKworI2luY2x1ZGUgIkxvb3BCbGlubk1hdGhVdGlscy5oIgor
CisjaW5jbHVkZSAiRmxvYXRQb2ludC5oIgorI2luY2x1ZGUgIk1hdGhFeHRyYXMuaCIKKyNpbmNs
dWRlIDxhbGdvcml0aG0+CisjaW5jbHVkZSA8c3RyaW5nLmg+IC8vIGZvciBtZW1jcHkKKworbmFt
ZXNwYWNlIFdlYkNvcmUgeworbmFtZXNwYWNlIExvb3BCbGlubk1hdGhVdGlscyB7CisKK25hbWVz
cGFjZSB7CisKKy8vIFV0aWxpdHkgZnVuY3Rpb25zIGxvY2FsIHRvIHRoaXMgZmlsZS4KK2ludCBv
cmllbnRhdGlvbihjb25zdCBGbG9hdFBvaW50JiBwMSwKKyAgICAgICAgICAgICAgICBjb25zdCBG
bG9hdFBvaW50JiBwMiwKKyAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBwMykKK3sK
KyAgICBmbG9hdCBjcm9zc1Byb2R1Y3QgPSAocDIueSgpIC0gcDEueSgpKSAqIChwMy54KCkgLSBw
Mi54KCkpIC0gKHAzLnkoKSAtIHAyLnkoKSkgKiAocDIueCgpIC0gcDEueCgpKTsKKyAgICByZXR1
cm4gKGNyb3NzUHJvZHVjdCA8IDAuMGYpID8gLTEgOiAoKGNyb3NzUHJvZHVjdCA+IDAuMGYpID8g
MSA6IDApOworfQorCitib29sIGVkZ2VFZGdlVGVzdChjb25zdCBGbG9hdFNpemUmIHYwRGVsdGEs
CisgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiB2MCwKKyAgICAgICAgICAgICAg
ICAgIGNvbnN0IEZsb2F0UG9pbnQmIHUwLAorICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQ
b2ludCYgdTEpCit7CisgICAgLy8gVGhpcyBlZGdlIHRvIGVkZ2UgdGVzdCBpcyBiYXNlZCBvbiBG
cmFubGluIEFudG9uaW8ncyBnZW06ICJGYXN0ZXIKKyAgICAvLyBMaW5lIFNlZ21lbnQgSW50ZXJz
ZWN0aW9uIiwgaW4gR3JhcGhpY3MgR2VtcyBJSUksIHBwLiAxOTktMjAyLgorICAgIGZsb2F0IGF4
ID0gdjBEZWx0YS53aWR0aCgpOworICAgIGZsb2F0IGF5ID0gdjBEZWx0YS5oZWlnaHQoKTsKKyAg
ICBmbG9hdCBieCA9IHUwLngoKSAtIHUxLngoKTsKKyAgICBmbG9hdCBieSA9IHUwLnkoKSAtIHUx
LnkoKTsKKyAgICBmbG9hdCBjeCA9IHYwLngoKSAtIHUwLngoKTsKKyAgICBmbG9hdCBjeSA9IHYw
LnkoKSAtIHUwLnkoKTsKKyAgICBmbG9hdCBmID0gYXkgKiBieCAtIGF4ICogYnk7CisgICAgZmxv
YXQgZCA9IGJ5ICogY3ggLSBieCAqIGN5OworICAgIGlmICgoZiA+IDAgJiYgZCA+PSAwICYmIGQg
PD0gZikgfHwgKGYgPCAwICYmIGQgPD0gMCAmJiBkID49IGYpKSB7CisgICAgICAgIGZsb2F0IGUg
PSBheCAqIGN5IC0gYXkgKiBjeDsKKworICAgICAgICAvLyBUaGlzIGFkZGl0aW9uYWwgdGVzdCBh
dm9pZHMgcmVwb3J0aW5nIGNvaW5jaWRlbnQgZWRnZXMsIHdoaWNoCisgICAgICAgIC8vIGlzIHRo
ZSBiZWhhdmlvciB3ZSB3YW50LgorICAgICAgICBpZiAoYXBwcm94RXF1YWwoZSwgMCkgfHwgYXBw
cm94RXF1YWwoZiwgMCkgfHwgYXBwcm94RXF1YWwoZSwgZikpCisgICAgICAgICAgICByZXR1cm4g
ZmFsc2U7CisKKyAgICAgICAgaWYgKGYgPiAwKQorICAgICAgICAgICAgcmV0dXJuIGUgPj0gMCAm
JiBlIDw9IGY7CisKKyAgICAgICAgcmV0dXJuIGUgPD0gMCAmJiBlID49IGY7CisgICAgfQorICAg
IHJldHVybiBmYWxzZTsKK30KKworYm9vbCBlZGdlQWdhaW5zdFRyaUVkZ2VzKGNvbnN0IEZsb2F0
UG9pbnQmIHYwLAorICAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIHYx
LAorICAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIHUwLAorICAgICAg
ICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIHUxLAorICAgICAgICAgICAgICAg
ICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIHUyKQoreworICAgIEZsb2F0U2l6ZSBkZWx0YSA9
IHYxIC0gdjA7CisgICAgLy8gVGVzdCBlZGdlIHUwLCB1MSBhZ2FpbnN0IHYwLCB2MS4KKyAgICBp
ZiAoZWRnZUVkZ2VUZXN0KGRlbHRhLCB2MCwgdTAsIHUxKSkKKyAgICAgICAgcmV0dXJuIHRydWU7
CisgICAgLy8gVGVzdCBlZGdlIHUxLCB1MiBhZ2FpbnN0IHYwLCB2MS4KKyAgICBpZiAoZWRnZUVk
Z2VUZXN0KGRlbHRhLCB2MCwgdTEsIHUyKSkKKyAgICAgICAgcmV0dXJuIHRydWU7CisgICAgLy8g
VGVzdCBlZGdlIHUyLCB1MSBhZ2FpbnN0IHYwLCB2MS4KKyAgICBpZiAoZWRnZUVkZ2VUZXN0KGRl
bHRhLCB2MCwgdTIsIHUwKSkKKyAgICAgICAgcmV0dXJuIHRydWU7CisgICAgcmV0dXJuIGZhbHNl
OworfQorCisvLyBBIHJvdW5kb2ZmIGZhY3RvciBpbiB0aGUgY3ViaWMgY2xhc3NpZmljYXRpb24g
YW5kIHRleHR1cmUgY29vcmRpbmF0ZQorLy8gZ2VuZXJhdGlvbiBhbGdvcml0aG1zLiBJdCBwcmlt
YXJpbHkgZGV0ZXJtaW5lcyB0aGUgaGFuZGxpbmcgb2YgY29ybmVyCisvLyBjYXNlcyBkdXJpbmcg
dGhlIGNsYXNzaWZpY2F0aW9uIHByb2Nlc3MuIEJlIGNhcmVmdWwgd2hlbiBhZGp1c3RpbmcgaXQ7
CisvLyBpdCBoYXMgYmVlbiBkZXRlcm1pbmVkIGVtcGlyaWNhbGx5IHRvIHdvcmsgd2VsbC4gV2hl
biBjaGFuZ2luZyBpdCwgeW91CisvLyBzaG91bGQgbG9vayBpbiBwYXJ0aWN1bGFyIGF0IHNoYXBl
cyB0aGF0IGNvbnRhaW4gcXVhZHJhdGljIGN1cnZlcyBhbmQKKy8vIGVuc3VyZSB0aGV5IHN0aWxs
IGxvb2sgc21vb3RoLiBPbmNlIHBpeGVsIHRlc3RzIGFyZSBydW5uaW5nIGFnYWluc3QgdGhpcwor
Ly8gYWxnb3JpdGhtLCB0aGV5IHNob3VsZCBwcm92aWRlIHN1ZmZpY2llbnQgY292ZXJhZ2UgdG8g
ZW5zdXJlIHRoYXQKKy8vIGFkanVzdGluZyB0aGUgY29uc3RhbnQgd29uJ3QgYnJlYWsgYW55dGhp
bmcuCitjb25zdCBmbG9hdCBFcHNpbG9uID0gNS4wZS00ZjsKKworfSAvLyBhbm9ueW1vdXMgbmFt
ZXNwYWNlCisKKy8vIEV4cG9ydGVkIHJvdXRpbmVzCisKK2Zsb2F0IHJvdW5kVG9aZXJvKGZsb2F0
IHZhbCkKK3sKKyAgICBpZiAodmFsIDwgRXBzaWxvbiAmJiB2YWwgPiAtRXBzaWxvbikKKyAgICAg
ICAgcmV0dXJuIDA7CisgICAgcmV0dXJuIHZhbDsKK30KKworYm9vbCBhcHByb3hFcXVhbChjb25z
dCBGbG9hdFBvaW50JiB2MCwgY29uc3QgRmxvYXRQb2ludCYgdjEpCit7CisgICAgcmV0dXJuICh2
MCAtIHYxKS5kaWFnb25hbExlbmd0aFNxdWFyZWQoKSA8IEVwc2lsb24gKiBFcHNpbG9uOworfQor
Citib29sIGFwcHJveEVxdWFsKGNvbnN0IEZsb2F0UG9pbnQzRCYgdjAsIGNvbnN0IEZsb2F0UG9p
bnQzRCYgdjEpCit7CisgICAgcmV0dXJuICh2MCAtIHYxKS5sZW5ndGhTcXVhcmVkKCkgPCBFcHNp
bG9uICogRXBzaWxvbjsKK30KKworYm9vbCBhcHByb3hFcXVhbChmbG9hdCBmMCwgZmxvYXQgZjEp
Cit7CisgICAgcmV0dXJuIGZhYnNmKGYwIC0gZjEpIDwgRXBzaWxvbjsKK30KKworYm9vbCBsaW5l
c0ludGVyc2VjdChjb25zdCBGbG9hdFBvaW50JiBwMSwKKyAgICAgICAgICAgICAgICAgICAgY29u
c3QgRmxvYXRQb2ludCYgcTEsCisgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQm
IHAyLAorICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBxMikKK3sKKyAgICBy
ZXR1cm4gKG9yaWVudGF0aW9uKHAxLCBxMSwgcDIpICE9IG9yaWVudGF0aW9uKHAxLCBxMSwgcTIp
CisgICAgICAgICAgICAmJiBvcmllbnRhdGlvbihwMiwgcTIsIHAxKSAhPSBvcmllbnRhdGlvbihw
MiwgcTIsIHExKSk7Cit9CisKK2Jvb2wgcG9pbnRJblRyaWFuZ2xlKGNvbnN0IEZsb2F0UG9pbnQm
IHBvaW50LAorICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgYSwKKyAgICAg
ICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIGIsCisgICAgICAgICAgICAgICAgICAg
ICBjb25zdCBGbG9hdFBvaW50JiBjKQoreworICAgIC8vIEFsZ29yaXRobSBmcm9tIGh0dHA6Ly93
d3cuYmxhY2twYXduLmNvbS90ZXh0cy9wb2ludGlucG9seS9kZWZhdWx0Lmh0bWwKKyAgICBmbG9h
dCB4MCA9IGMueCgpIC0gYS54KCk7CisgICAgZmxvYXQgeTAgPSBjLnkoKSAtIGEueSgpOworICAg
IGZsb2F0IHgxID0gYi54KCkgLSBhLngoKTsKKyAgICBmbG9hdCB5MSA9IGIueSgpIC0gYS55KCk7
CisgICAgZmxvYXQgeDIgPSBwb2ludC54KCkgLSBhLngoKTsKKyAgICBmbG9hdCB5MiA9IHBvaW50
LnkoKSAtIGEueSgpOworCisgICAgZmxvYXQgZG90MDAgPSB4MCAqIHgwICsgeTAgKiB5MDsKKyAg
ICBmbG9hdCBkb3QwMSA9IHgwICogeDEgKyB5MCAqIHkxOworICAgIGZsb2F0IGRvdDAyID0geDAg
KiB4MiArIHkwICogeTI7CisgICAgZmxvYXQgZG90MTEgPSB4MSAqIHgxICsgeTEgKiB5MTsKKyAg
ICBmbG9hdCBkb3QxMiA9IHgxICogeDIgKyB5MSAqIHkyOworICAgIGZsb2F0IGRlbm9taW5hdG9y
ID0gZG90MDAgKiBkb3QxMSAtIGRvdDAxICogZG90MDE7CisgICAgaWYgKCFkZW5vbWluYXRvcikK
KyAgICAgICAgLy8gVHJpYW5nbGUgaXMgemVyby1hcmVhLiBUcmVhdCBxdWVyeSBwb2ludCBhcyBu
b3QgYmVpbmcgaW5zaWRlLgorICAgICAgICByZXR1cm4gZmFsc2U7CisgICAgLy8gQ29tcHV0ZQor
ICAgIGZsb2F0IGludmVyc2VEZW5vbWluYXRvciA9IDEuMGYgLyBkZW5vbWluYXRvcjsKKyAgICBm
bG9hdCB1ID0gKGRvdDExICogZG90MDIgLSBkb3QwMSAqIGRvdDEyKSAqIGludmVyc2VEZW5vbWlu
YXRvcjsKKyAgICBmbG9hdCB2ID0gKGRvdDAwICogZG90MTIgLSBkb3QwMSAqIGRvdDAyKSAqIGlu
dmVyc2VEZW5vbWluYXRvcjsKKworICAgIHJldHVybiAodSA+IDAuMGYpICYmICh2ID4gMC4wZikg
JiYgKHUgKyB2IDwgMS4wZik7Cit9CisKK2Jvb2wgdHJpYW5nbGVzT3ZlcmxhcChjb25zdCBGbG9h
dFBvaW50JiBhMSwKKyAgICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBiMSwK
KyAgICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBjMSwKKyAgICAgICAgICAg
ICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBhMiwKKyAgICAgICAgICAgICAgICAgICAgICBj
b25zdCBGbG9hdFBvaW50JiBiMiwKKyAgICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBv
aW50JiBjMikKK3sKKyAgICAvLyBEZXJpdmVkIGZyb20gY29wbGFuYXJfdHJpX3RyaSgpIGF0Cisg
ICAgLy8gaHR0cDovL2pndC5ha3BldGVycy5jb20vcGFwZXJzL1NoZW5IZW5nVGFuZzAzL3RyaV90
cmkuaHRtbCAsCisgICAgLy8gc2ltcGxpZmllZCBmb3IgdGhlIDJEIGNhc2UgYW5kIG1vZGlmaWVk
IHNvIHRoYXQgb3ZlcmxhcHBpbmcgZWRnZXMKKyAgICAvLyBkbyBub3QgcmVwb3J0IG92ZXJsYXBw
aW5nIHRyaWFuZ2xlcy4KKworICAgIC8vIFRlc3QgYWxsIGVkZ2VzIG9mIHRyaWFuZ2xlIDEgYWdh
aW5zdCB0aGUgZWRnZXMgb2YgdHJpYW5nbGUgMi4KKyAgICBpZiAoZWRnZUFnYWluc3RUcmlFZGdl
cyhhMSwgYjEsIGEyLCBiMiwgYzIpCisgICAgICAgIHx8IGVkZ2VBZ2FpbnN0VHJpRWRnZXMoYjEs
IGMxLCBhMiwgYjIsIGMyKQorICAgICAgICB8fCBlZGdlQWdhaW5zdFRyaUVkZ2VzKGMxLCBhMSwg
YTIsIGIyLCBjMikpCisgICAgICAgIHJldHVybiB0cnVlOworICAgIC8vIEZpbmFsbHksIHRlc3Qg
aWYgdHJpMSBpcyB0b3RhbGx5IGNvbnRhaW5lZCBpbiB0cmkyIG9yIHZpY2UgdmVyc2EuCisgICAg
Ly8gVGhlIHBhcGVyIGFib3ZlIG9ubHkgcGVyZm9ybXMgdGhlIGZpcnN0IHR3byBwb2ludC1pbi10
cmlhbmdsZSB0ZXN0cy4KKyAgICAvLyBCZWNhdXNlIHdlIGRlZmluZSB0aGF0IHRyaWFuZ2xlcyBz
aGFyaW5nIGEgdmVydGV4IG9yIGVkZ2UgZG9uJ3QKKyAgICAvLyBvdmVybGFwLCB3ZSBtdXN0IHBl
cmZvcm0gYWRkaXRpb25hbCB0ZXN0cyB0byBzZWUgd2hldGhlciBvbmUKKyAgICAvLyB0cmlhbmds
ZSBpcyBjb250YWluZWQgaW4gdGhlIG90aGVyLgorICAgIGlmIChwb2ludEluVHJpYW5nbGUoYTEs
IGEyLCBiMiwgYzIpCisgICAgICAgIHx8IHBvaW50SW5UcmlhbmdsZShhMiwgYTEsIGIxLCBjMSkK
KyAgICAgICAgfHwgcG9pbnRJblRyaWFuZ2xlKGIxLCBhMiwgYjIsIGMyKQorICAgICAgICB8fCBw
b2ludEluVHJpYW5nbGUoYjIsIGExLCBiMSwgYzEpCisgICAgICAgIHx8IHBvaW50SW5Ucmlhbmds
ZShjMSwgYTIsIGIyLCBjMikKKyAgICAgICAgfHwgcG9pbnRJblRyaWFuZ2xlKGMyLCBhMSwgYjEs
IGMxKSkKKyAgICAgICAgcmV0dXJuIHRydWU7CisgICAgcmV0dXJuIGZhbHNlOworfQorCituYW1l
c3BhY2UgeworCisvLyBIZWxwZXIgcm91dGluZXMgZm9yIHB1YmxpYyBYUmF5IHF1ZXJpZXMgYmVs
b3cuIEFsbCBvZiB0aGlzIGNvZGUKKy8vIG9yaWdpbmF0ZWQgaW4gU2tpYTsgc2VlIGluY2x1ZGUv
Y29yZS8gYW5kIHNyYy9jb3JlLywgU2tTY2FsYXIuaCBhbmQKKy8vIFNrR2VvbWV0cnkue2NwcCxo
fS4KKworY29uc3QgZmxvYXQgTmVhcmx5WmVyb0NvbnN0YW50ID0gKDEuMGYgLyAoMSA8PCAxMikp
OworCitib29sIG5lYXJseVplcm8oZmxvYXQgeCwgZmxvYXQgdG9sZXJhbmNlID0gTmVhcmx5WmVy
b0NvbnN0YW50KQoreworICAgIEFTU0VSVCh0b2xlcmFuY2UgPiAwLjBmKTsKKyAgICByZXR1cm4g
OjpmYWJzZih4KSA8IHRvbGVyYW5jZTsKK30KKworLy8gTGluZWFybHkgaW50ZXJwb2xhdGUgYmV0
d2VlbiBhIGFuZCBiLCBiYXNlZCBvbiB0LgorLy8gSWYgdCBpcyAwLCByZXR1cm4gYTsgaWYgdCBp
cyAxLCByZXR1cm4gYjsgZWxzZSBpbnRlcnBvbGF0ZS4KKy8vIHQgbXVzdCBiZSBbMC4uMV0uCitm
bG9hdCBpbnRlcnBvbGF0ZShmbG9hdCBhLCBmbG9hdCBiLCBmbG9hdCB0KQoreworICAgIEFTU0VS
VCh0ID49IDAgJiYgdCA8PSAxKTsKKyAgICByZXR1cm4gYSArIChiIC0gYSkgKiB0OworfQorCitm
bG9hdCBldmFsdWF0ZUN1YmljKGZsb2F0IGNvbnRyb2xQb2ludDAsIGZsb2F0IGNvbnRyb2xQb2lu
dDEsIGZsb2F0IGNvbnRyb2xQb2ludDIsIGZsb2F0IGNvbnRyb2xQb2ludDMsIGZsb2F0IHQpCit7
CisgICAgQVNTRVJUKHQgPj0gMCAmJiB0IDw9IDEpOworCisgICAgaWYgKCF0KQorICAgICAgICBy
ZXR1cm4gY29udHJvbFBvaW50MDsKKworICAgIGZsb2F0IGFiID0gaW50ZXJwb2xhdGUoY29udHJv
bFBvaW50MCwgY29udHJvbFBvaW50MSwgdCk7CisgICAgZmxvYXQgYmMgPSBpbnRlcnBvbGF0ZShj
b250cm9sUG9pbnQxLCBjb250cm9sUG9pbnQyLCB0KTsKKyAgICBmbG9hdCBjZCA9IGludGVycG9s
YXRlKGNvbnRyb2xQb2ludDIsIGNvbnRyb2xQb2ludDMsIHQpOworICAgIGZsb2F0IGFiYyA9IGlu
dGVycG9sYXRlKGFiLCBiYywgdCk7CisgICAgZmxvYXQgYmNkID0gaW50ZXJwb2xhdGUoYmMsIGNk
LCB0KTsKKyAgICByZXR1cm4gaW50ZXJwb2xhdGUoYWJjLCBiY2QsIHQpOworfQorCisvLyBFdmFs
dWF0ZXMgdGhlIHBvaW50IG9uIHRoZSBzb3VyY2UgY3ViaWMgc3BlY2lmaWVkIGJ5IHQsIDAgPD0g
dCA8PSAxLjAuCitGbG9hdFBvaW50IGV2YWx1YXRlQ3ViaWNBdChjb25zdCBGbG9hdFBvaW50IGN1
YmljWzRdLCBmbG9hdCB0KQoreworICAgIHJldHVybiBGbG9hdFBvaW50KGV2YWx1YXRlQ3ViaWMo
Y3ViaWNbMF0ueCgpLCBjdWJpY1sxXS54KCksIGN1YmljWzJdLngoKSwgY3ViaWNbM10ueCgpLCB0
KSwKKyAgICAgICAgICAgICAgICAgICAgICBldmFsdWF0ZUN1YmljKGN1YmljWzBdLnkoKSwgY3Vi
aWNbMV0ueSgpLCBjdWJpY1syXS55KCksIGN1YmljWzNdLnkoKSwgdCkpOworfQorCitib29sIHhS
YXlDcm9zc2VzTW9ub3RvbmljQ3ViaWMoY29uc3QgWFJheSYgeFJheSwgY29uc3QgRmxvYXRQb2lu
dCBjdWJpY1s0XSwgYm9vbCYgYW1iaWd1b3VzKQoreworICAgIGFtYmlndW91cyA9IGZhbHNlOwor
CisgICAgLy8gRmluZCB0aGUgbWluaW11bSBhbmQgbWF4aW11bSB5IG9mIHRoZSBleHRyZW1hLCB3
aGljaCBhcmUgdGhlCisgICAgLy8gZmlyc3QgYW5kIGxhc3QgcG9pbnRzIHNpbmNlIHRoaXMgY3Vi
aWMgaXMgbW9ub3RvbmljCisgICAgZmxvYXQgbWluWSA9IHN0ZDo6bWluKGN1YmljWzBdLnkoKSwg
Y3ViaWNbM10ueSgpKTsKKyAgICBmbG9hdCBtYXhZID0gc3RkOjptYXgoY3ViaWNbMF0ueSgpLCBj
dWJpY1szXS55KCkpOworCisgICAgaWYgKHhSYXkueSgpID09IGN1YmljWzBdLnkoKQorICAgICAg
ICB8fCB4UmF5LnkoKSA8IG1pblkKKyAgICAgICAgfHwgeFJheS55KCkgPiBtYXhZKSB7CisgICAg
ICAgIC8vIFRoZSBxdWVyeSBsaW5lIGRlZmluaXRlbHkgZG9lcyBub3QgY3Jvc3MgdGhlIGN1cnZl
CisgICAgICAgIGFtYmlndW91cyA9ICh4UmF5LnkoKSA9PSBjdWJpY1swXS55KCkpOworICAgICAg
ICByZXR1cm4gZmFsc2U7CisgICAgfQorCisgICAgY29uc3QgYm9vbCBwb2ludEF0RXh0cmVtdW0g
PSAoeFJheS55KCkgPT0gY3ViaWNbM10ueSgpKTsKKworICAgIGZsb2F0IG1pblggPSBzdGQ6Om1p
bihzdGQ6Om1pbihzdGQ6Om1pbihjdWJpY1swXS54KCksIGN1YmljWzFdLngoKSksCisgICAgICAg
ICAgICAgICAgICAgICAgICAgICAgICAgICAgIGN1YmljWzJdLngoKSksCisgICAgICAgICAgICAg
ICAgICAgICAgICAgIGN1YmljWzNdLngoKSk7CisgICAgaWYgKHhSYXkueCgpIDwgbWluWCkgewor
ICAgICAgICAvLyBUaGUgcXVlcnkgbGluZSBkZWZpbml0ZWx5IGNyb3NzZXMgdGhlIGN1cnZlCisg
ICAgICAgIGFtYmlndW91cyA9IHBvaW50QXRFeHRyZW11bTsKKyAgICAgICAgcmV0dXJuIHRydWU7
CisgICAgfQorCisgICAgZmxvYXQgbWF4WCA9IHN0ZDo6bWF4KHN0ZDo6bWF4KHN0ZDo6bWF4KGN1
YmljWzBdLngoKSwgY3ViaWNbMV0ueCgpKSwKKyAgICAgICAgICAgICAgICAgICAgICAgICAgICAg
ICAgICAgY3ViaWNbMl0ueCgpKSwKKyAgICAgICAgICAgICAgICAgICAgICAgICAgY3ViaWNbM10u
eCgpKTsKKyAgICBpZiAoeFJheS54KCkgPiBtYXhYKQorICAgICAgICAvLyBUaGUgcXVlcnkgbGlu
ZSBkZWZpbml0ZWx5IGRvZXMgbm90IGNyb3NzIHRoZSBjdXJ2ZQorICAgICAgICByZXR1cm4gZmFs
c2U7CisKKyAgICAvLyBEbyBhIGJpbmFyeSBzZWFyY2ggdG8gZmluZCB0aGUgcGFyYW1ldGVyIHZh
bHVlIHdoaWNoIG1ha2VzIHkgYXMKKyAgICAvLyBjbG9zZSBhcyBwb3NzaWJsZSB0byB0aGUgcXVl
cnkgcG9pbnQuIFNlZSB3aGV0aGVyIHRoZSBxdWVyeQorICAgIC8vIGxpbmUncyBvcmlnaW4gaXMg
dG8gdGhlIGxlZnQgb2YgdGhlIGFzc29jaWF0ZWQgeCBjb29yZGluYXRlLgorCisgICAgLy8gTWF4
SXRlcmF0aW9ucyBpcyBjaG9zZW4gYXMgdGhlIG51bWJlciBvZiBtYW50aXNzYSBiaXRzIGZvciBh
IGZsb2F0LAorICAgIC8vIHNpbmNlIHRoZXJlJ3Mgbm8gd2F5IHdlIGFyZSBnb2luZyB0byBnZXQg
bW9yZSBwcmVjaXNpb24gYnkKKyAgICAvLyBpdGVyYXRpbmcgbW9yZSB0aW1lcyB0aGFuIHRoYXQu
CisgICAgY29uc3QgaW50IE1heEl0ZXJhdGlvbnMgPSAyMzsKKyAgICBGbG9hdFBvaW50IGV2YWx1
YXRlZFBvaW50OworICAgIGludCBpdGVyID0gMDsKKyAgICBmbG9hdCB1cHBlclQ7CisgICAgZmxv
YXQgbG93ZXJUOworICAgIC8vIE5lZWQgdG8gaW52ZXJ0IGRpcmVjdGlvbiBvZiB0IHBhcmFtZXRl
ciBpZiBjdWJpYyBnb2VzIHVwCisgICAgLy8gaW5zdGVhZCBvZiBkb3duCisgICAgaWYgKGN1Ymlj
WzNdLnkoKSA+IGN1YmljWzBdLnkoKSkgeworICAgICAgICB1cHBlclQgPSAxOworICAgICAgICBs
b3dlclQgPSAwOworICAgIH0gZWxzZSB7CisgICAgICAgIHVwcGVyVCA9IDA7CisgICAgICAgIGxv
d2VyVCA9IDE7CisgICAgfQorICAgIGRvIHsKKyAgICAgICAgZmxvYXQgdCA9IDAuNWYgKiAodXBw
ZXJUICsgbG93ZXJUKTsKKyAgICAgICAgZXZhbHVhdGVkUG9pbnQgPSBldmFsdWF0ZUN1YmljQXQo
Y3ViaWMsIHQpOworICAgICAgICBpZiAoeFJheS55KCkgPiBldmFsdWF0ZWRQb2ludC55KCkpCisg
ICAgICAgICAgICBsb3dlclQgPSB0OworICAgICAgICBlbHNlCisgICAgICAgICAgICB1cHBlclQg
PSB0OworICAgIH0gd2hpbGUgKCsraXRlciA8IE1heEl0ZXJhdGlvbnMgJiYgIW5lYXJseVplcm8o
ZXZhbHVhdGVkUG9pbnQueSgpIC0geFJheS55KCkpKTsKKworICAgIC8vIEZJWE1FOiBvbmNlIHdl
IGhhdmUgbW9yZSByZWdyZXNzaW9uIHRlc3RzIGZvciB0aGlzIGNvZGUsCisgICAgLy8gZGV0ZXJt
aW5lIHdoZXRoZXIgdGhpcyBzaG91bGQgYmUgdXNpbmcgYSBmdXp6eSB0ZXN0LgorICAgIGlmICh4
UmF5LngoKSA8PSBldmFsdWF0ZWRQb2ludC54KCkpIHsKKyAgICAgICAgYW1iaWd1b3VzID0gcG9p
bnRBdEV4dHJlbXVtOworICAgICAgICByZXR1cm4gdHJ1ZTsKKyAgICB9CisgICAgcmV0dXJuIGZh
bHNlOworfQorCisvLyBEaXZpZGVzIHRoZSBudW1lcmF0b3IgYnkgdGhlIGRlbm9taW5hdG9yIHNh
ZmVseSBmb3IgdGhlIGNhc2Ugd2hlcmUKKy8vIHRoZSByZXN1bHQgbXVzdCBsaWUgaW4gdGhlIHJh
bmdlICgwLi4xKS4gUmVzdWx0IGluZGljYXRlcyB3aGV0aGVyCisvLyB0aGUgcmVzdWx0IGlzIHZh
bGlkLgorYm9vbCBzYWZlVW5pdERpdmlkZShmbG9hdCBudW1lcmF0b3IsIGZsb2F0IGRlbm9taW5h
dG9yLCBmbG9hdCYgcmF0aW8pCit7CisgICAgaWYgKG51bWVyYXRvciA8IDApIHsKKyAgICAgICAg
Ly8gTWFrZSB0aGUgIm51bWVyYXRvciA+PSBkZW5vbWluYXRvciIgY2hlY2sgYmVsb3cgd29yay4K
KyAgICAgICAgbnVtZXJhdG9yID0gLW51bWVyYXRvcjsKKyAgICAgICAgZGVub21pbmF0b3IgPSAt
ZGVub21pbmF0b3I7CisgICAgfQorICAgIGlmICghbnVtZXJhdG9yIHx8ICFkZW5vbWluYXRvciB8
fCBudW1lcmF0b3IgPj0gZGVub21pbmF0b3IpCisgICAgICAgIHJldHVybiBmYWxzZTsKKyAgICBm
bG9hdCByID0gbnVtZXJhdG9yIC8gZGVub21pbmF0b3I7CisgICAgaWYgKGlzbmFuKHIpKQorICAg
ICAgICByZXR1cm4gZmFsc2U7CisgICAgQVNTRVJUKHIgPj0gMCAmJiByIDwgMSk7CisgICAgaWYg
KCFyKSAvLyBjYXRjaCB1bmRlcmZsb3cgaWYgbnVtZXJhdG9yIDw8PDwgZGVub21pbmF0b3IKKyAg
ICAgICAgcmV0dXJuIGZhbHNlOworICAgIHJhdGlvID0gcjsKKyAgICByZXR1cm4gdHJ1ZTsKK30K
KworLy8gRnJvbSBOdW1lcmljYWwgUmVjaXBlcyBpbiBDLgorLy8KKy8vICAgcSA9IC0xLzIgKGIg
KyBzaWduKGIpIHNxcnRbYipiIC0gNCphKmNdKQorLy8gICB4MSA9IHEgLyBhCisvLyAgIHgyID0g
YyAvIHEKKy8vCisvLyBSZXR1cm5zIHRoZSBudW1iZXIgb2YgcmVhbCByb290cyBvZiB0aGUgZXF1
YXRpb24gWzAuLjJdLiBSb290cyBhcmUKKy8vIHJldHVybmVkIGluIHNvcnRlZCBvcmRlciwgc21h
bGxlciByb290IGZpcnN0LgoraW50IGZpbmRVbml0UXVhZFJvb3RzKGZsb2F0IGEsIGZsb2F0IGIs
IGZsb2F0IGMsIGZsb2F0IHJvb3RzWzJdKQoreworICAgIGlmICghYSkKKyAgICAgICAgcmV0dXJu
IHNhZmVVbml0RGl2aWRlKC1jLCBiLCByb290c1swXSkgPyAxIDogMDsKKworICAgIGZsb2F0IGRp
c2NyaW1pbmFudCA9IGIqYiAtIDQqYSpjOworICAgIGlmIChkaXNjcmltaW5hbnQgPCAwIHx8IGlz
bmFuKGRpc2NyaW1pbmFudCkpIC8vIGNvbXBsZXggcm9vdHMKKyAgICAgICAgcmV0dXJuIDA7Cisg
ICAgZGlzY3JpbWluYW50ID0gc3FydGYoZGlzY3JpbWluYW50KTsKKworICAgIGZsb2F0IHEgPSAo
YiA8IDApID8gLShiIC0gZGlzY3JpbWluYW50KSAvIDIgOiAtKGIgKyBkaXNjcmltaW5hbnQpIC8g
MjsKKyAgICBmbG9hdCogciA9IHJvb3RzOworICAgIGlmIChzYWZlVW5pdERpdmlkZShxLCBhLCAq
cikpCisgICAgICAgICsrcjsKKyAgICBpZiAoc2FmZVVuaXREaXZpZGUoYywgcSwgKnIpKQorICAg
ICAgICArK3I7CisgICAgaWYgKHIgLSByb290cyA9PSAyKSB7CisgICAgICAgIC8vIFNlZW1pbmds
eSBoYXZlIHR3byByb290cy4gQ2hlY2sgZm9yIGVxdWFsaXR5IGFuZCBzb3J0LgorICAgICAgICBp
ZiAocm9vdHNbMF0gPT0gcm9vdHNbMV0pCisgICAgICAgICAgICByZXR1cm4gMTsKKyAgICAgICAg
aWYgKHJvb3RzWzBdID4gcm9vdHNbMV0pCisgICAgICAgICAgICBzdGQ6OnN3YXAocm9vdHNbMF0s
IHJvb3RzWzFdKTsKKyAgICB9CisgICAgcmV0dXJuIHIgLSByb290czsKK30KKworLy8gQ3ViaWMn
KHQpID0gcHReMiArIHF0ICsgciwgd2hlcmUKKy8vICAgcCA9IDMoLWEgKyAzKGIgLSBjKSArIGQp
CisvLyAgIHEgPSA2KGEgLSAyYiArIGMpCisvLyAgIHIgPSAzKGIgLSBhKQorLy8gU29sdmUgZm9y
IHQsIGtlZXBpbmcgb25seSB0aG9zZSB0aGF0IGZpdCBiZXR3ZWVuIDAgPCB0IDwgMS4KK2ludCBm
aW5kQ3ViaWNFeHRyZW1hKGZsb2F0IGEsIGZsb2F0IGIsIGZsb2F0IGMsIGZsb2F0IGQsIGZsb2F0
IHRWYWx1ZXNbMl0pCit7CisgICAgLy8gd2UgZGl2aWRlIHAsIHEsIGFuZCByIGJ5IDMgdG8gc2lt
cGxpZnkKKyAgICBmbG9hdCBwID0gZCAtIGEgKyAzKihiIC0gYyk7CisgICAgZmxvYXQgcSA9IDIq
KGEgLSBiIC0gYiArIGMpOworICAgIGZsb2F0IHIgPSBiIC0gYTsKKworICAgIHJldHVybiBmaW5k
VW5pdFF1YWRSb290cyhwLCBxLCByLCB0VmFsdWVzKTsKK30KKwordm9pZCBpbnRlcnBvbGF0ZUN1
YmljQ29vcmRzKGZsb2F0IGNvbnRyb2xQb2ludDAsIGZsb2F0IGNvbnRyb2xQb2ludDEsIGZsb2F0
IGNvbnRyb2xQb2ludDIsIGZsb2F0IGNvbnRyb2xQb2ludDMsIGZsb2F0KiBkc3QsIGZsb2F0IHQp
Cit7CisgICAgZmxvYXQgYWIgPSBpbnRlcnBvbGF0ZShjb250cm9sUG9pbnQwLCBjb250cm9sUG9p
bnQxLCB0KTsKKyAgICBmbG9hdCBiYyA9IGludGVycG9sYXRlKGNvbnRyb2xQb2ludDEsIGNvbnRy
b2xQb2ludDIsIHQpOworICAgIGZsb2F0IGNkID0gaW50ZXJwb2xhdGUoY29udHJvbFBvaW50Miwg
Y29udHJvbFBvaW50MywgdCk7CisgICAgZmxvYXQgYWJjID0gaW50ZXJwb2xhdGUoYWIsIGJjLCB0
KTsKKyAgICBmbG9hdCBiY2QgPSBpbnRlcnBvbGF0ZShiYywgY2QsIHQpOworICAgIGZsb2F0IGFi
Y2QgPSBpbnRlcnBvbGF0ZShhYmMsIGJjZCwgdCk7CisKKyAgICBkc3RbMF0gPSBjb250cm9sUG9p
bnQwOworICAgIGRzdFsyXSA9IGFiOworICAgIGRzdFs0XSA9IGFiYzsKKyAgICBkc3RbNl0gPSBh
YmNkOworICAgIGRzdFs4XSA9IGJjZDsKKyAgICBkc3RbMTBdID0gY2Q7CisgICAgZHN0WzEyXSA9
IGNvbnRyb2xQb2ludDM7Cit9CisKKyNpZm5kZWYgTkRFQlVHCitib29sIGlzVW5pdEludGVydmFs
KGZsb2F0IHgpCit7CisgICAgcmV0dXJuIHggPiAwICYmIHggPCAxOworfQorI2VuZGlmCisKK3Zv
aWQgY2hvcEN1YmljQXRUVmFsdWVzKGNvbnN0IEZsb2F0UG9pbnQgc3JjWzRdLCBGbG9hdFBvaW50
IGRzdFtdLCBjb25zdCBmbG9hdCB0VmFsdWVzW10sIGludCByb290cykKK3sKKyNpZm5kZWYgTkRF
QlVHCisgICAgZm9yIChpbnQgaSA9IDA7IGkgPCByb290cyAtIDE7ICsraSkgeworICAgICAgICBB
U1NFUlQoaXNVbml0SW50ZXJ2YWwodFZhbHVlc1tpXSkpOworICAgICAgICBBU1NFUlQoaXNVbml0
SW50ZXJ2YWwodFZhbHVlc1tpKzFdKSk7CisgICAgICAgIEFTU0VSVCh0VmFsdWVzW2ldIDwgdFZh
bHVlc1tpKzFdKTsKKyAgICB9CisjZW5kaWYKKworICAgIGlmICghcm9vdHMpIHsKKyAgICAgICAg
Ly8gbm90aGluZyB0byBjaG9wCisgICAgICAgIGZvciAoaW50IGogPSAwOyBqIDwgNDsgKytqKQor
ICAgICAgICAgICAgZHN0W2pdID0gc3JjW2pdOworICAgICAgICByZXR1cm47CisgICAgfQorCisg
ICAgZmxvYXQgdCA9IHRWYWx1ZXNbMF07CisgICAgRmxvYXRQb2ludCB0bXBbNF07CisgICAgZm9y
IChpbnQgaiA9IDA7IGogPCA0OyArK2opCisgICAgICAgIHRtcFtqXSA9IHNyY1tqXTsKKworICAg
IGZvciAoaW50IGkgPSAwOyBpIDwgcm9vdHM7ICsraSkgeworICAgICAgICBjaG9wQ3ViaWNBdCh0
bXAsIGRzdCwgdCk7CisgICAgICAgIGlmIChpID09IHJvb3RzIC0gMSkKKyAgICAgICAgICAgIGJy
ZWFrOworCisgICAgICAgIGRzdCArPSAzOworICAgICAgICAvLyBNYWtlIHRtcCBjb250YWluIHRo
ZSByZW1haW5pbmcgY3ViaWMgKGFmdGVyIHRoZSBmaXJzdCBjaG9wKS4KKyAgICAgICAgZm9yIChp
bnQgaiA9IDA7IGogPCA0OyArK2opCisgICAgICAgICAgICB0bXBbal0gPSBkc3Rbal07CisKKyAg
ICAgICAgLy8gV2F0Y2ggb3V0IGZvciB0aGUgY2FzZSB0aGF0IHRoZSByZW5vcm1hbGl6ZWQgdCBp
c24ndCBpbiByYW5nZS4KKyAgICAgICAgaWYgKCFzYWZlVW5pdERpdmlkZSh0VmFsdWVzW2krMV0g
LSB0VmFsdWVzW2ldLCAxLjBmIC0gdFZhbHVlc1tpXSwgdCkpIHsKKyAgICAgICAgICAgIC8vIElm
IGl0IGlzbid0LCBqdXN0IGNyZWF0ZSBhIGRlZ2VuZXJhdGUgY3ViaWMuCisgICAgICAgICAgICBk
c3RbNF0gPSBkc3RbNV0gPSBkc3RbNl0gPSB0bXBbM107CisgICAgICAgICAgICBicmVhazsKKyAg
ICAgICAgfQorICAgIH0KK30KKwordm9pZCBmbGF0dGVuRG91YmxlQ3ViaWNZRXh0cmVtYShGbG9h
dFBvaW50IGNvb3Jkc1s3XSkKK3sKKyAgICBjb29yZHNbMl0uc2V0WShjb29yZHNbM10ueSgpKTsK
KyAgICBjb29yZHNbNF0uc2V0WShjb29yZHNbM10ueSgpKTsKK30KKworaW50IGNob3BDdWJpY0F0
WUV4dHJlbWEoY29uc3QgRmxvYXRQb2ludCBzcmNbNF0sIEZsb2F0UG9pbnQgZHN0WzEwXSkKK3sK
KyAgICBmbG9hdCB0VmFsdWVzWzJdOworICAgIGludCByb290cyA9IGZpbmRDdWJpY0V4dHJlbWEo
c3JjWzBdLnkoKSwgc3JjWzFdLnkoKSwgc3JjWzJdLnkoKSwgc3JjWzNdLnkoKSwgdFZhbHVlcyk7
CisKKyAgICBjaG9wQ3ViaWNBdFRWYWx1ZXMoc3JjLCBkc3QsIHRWYWx1ZXMsIHJvb3RzKTsKKyAg
ICBpZiAocm9vdHMpIHsKKyAgICAgICAgLy8gd2UgZG8gc29tZSBjbGVhbnVwIHRvIGVuc3VyZSBv
dXIgWSBleHRyZW1hIGFyZSBmbGF0CisgICAgICAgIGZsYXR0ZW5Eb3VibGVDdWJpY1lFeHRyZW1h
KCZkc3RbMF0pOworICAgICAgICBpZiAocm9vdHMgPT0gMikKKyAgICAgICAgICAgIGZsYXR0ZW5E
b3VibGVDdWJpY1lFeHRyZW1hKCZkc3RbM10pOworICAgIH0KKyAgICByZXR1cm4gcm9vdHM7Cit9
CisKK30gLy8gYW5vbnltb3VzIG5hbWVzcGFjZQorCisvLyBQdWJsaWMgY3ViaWMgb3BlcmF0aW9u
cy4KKwordm9pZCBjaG9wQ3ViaWNBdChjb25zdCBGbG9hdFBvaW50IHNyY1s0XSwgRmxvYXRQb2lu
dCBkc3RbN10sIGZsb2F0IHQpCit7CisgICAgQVNTRVJUKHQgPj0gMCAmJiB0IDw9IDEpOworCisg
ICAgZmxvYXQgb3V0cHV0WzE0XTsKKyAgICBpbnRlcnBvbGF0ZUN1YmljQ29vcmRzKHNyY1swXS54
KCksIHNyY1sxXS54KCksIHNyY1syXS54KCksIHNyY1szXS54KCksICZvdXRwdXRbMF0sIHQpOwor
ICAgIGludGVycG9sYXRlQ3ViaWNDb29yZHMoc3JjWzBdLnkoKSwgc3JjWzFdLnkoKSwgc3JjWzJd
LnkoKSwgc3JjWzNdLnkoKSwgJm91dHB1dFsxXSwgdCk7CisgICAgZm9yIChpbnQgaSA9IDA7IGkg
PCA3OyBpKyspCisgICAgICAgIGRzdFtpXS5zZXQob3V0cHV0WzIgKiBpXSwgb3V0cHV0WzIgKiBp
ICsgMV0pOworfQorCisvLyBQdWJsaWMgWFJheSBxdWVyaWVzLgorCitib29sIHhSYXlDcm9zc2Vz
TGluZShjb25zdCBYUmF5JiB4UmF5LCBjb25zdCBGbG9hdFBvaW50IHB0c1syXSwgYm9vbCYgYW1i
aWd1b3VzKQoreworICAgIGFtYmlndW91cyA9IGZhbHNlOworCisgICAgLy8gRGV0ZXJtaW5lIHF1
aWNrIGRpc2NhcmRzLgorICAgIC8vIENvbnNpZGVyIHF1ZXJ5IGxpbmUgZ29pbmcgZXhhY3RseSB0
aHJvdWdoIHBvaW50IDAgdG8gbm90CisgICAgLy8gaW50ZXJzZWN0LCBmb3Igc3ltbWV0cnkgd2l0
aCB4UmF5Q3Jvc3Nlc01vbm90b25pY0N1YmljLgorICAgIGlmICh4UmF5LnkoKSA9PSBwdHNbMF0u
eSgpKSB7CisgICAgICAgIGFtYmlndW91cyA9IHRydWU7CisgICAgICAgIHJldHVybiBmYWxzZTsK
KyAgICB9CisgICAgaWYgKHhSYXkueSgpIDwgcHRzWzBdLnkoKSAmJiB4UmF5LnkoKSA8IHB0c1sx
XS55KCkpCisgICAgICAgIHJldHVybiBmYWxzZTsKKyAgICBpZiAoeFJheS55KCkgPiBwdHNbMF0u
eSgpICYmIHhSYXkueSgpID4gcHRzWzFdLnkoKSkKKyAgICAgICAgcmV0dXJuIGZhbHNlOworICAg
IGlmICh4UmF5LngoKSA+IHB0c1swXS54KCkgJiYgeFJheS54KCkgPiBwdHNbMV0ueCgpKQorICAg
ICAgICByZXR1cm4gZmFsc2U7CisgICAgLy8gRGV0ZXJtaW5lIGRlZ2VuZXJhdGUgY2FzZXMKKyAg
ICBpZiAobmVhcmx5WmVybyhwdHNbMF0ueSgpIC0gcHRzWzFdLnkoKSkpCisgICAgICAgIHJldHVy
biBmYWxzZTsKKyAgICBpZiAobmVhcmx5WmVybyhwdHNbMF0ueCgpIC0gcHRzWzFdLngoKSkpIHsK
KyAgICAgICAgLy8gV2UndmUgYWxyZWFkeSBkZXRlcm1pbmVkIHRoZSBxdWVyeSBwb2ludCBsaWVz
IHdpdGhpbiB0aGUKKyAgICAgICAgLy8gdmVydGljYWwgcmFuZ2Ugb2YgdGhlIGxpbmUgc2VnbWVu
dC4KKyAgICAgICAgaWYgKHhSYXkueCgpIDw9IHB0c1swXS54KCkpIHsKKyAgICAgICAgICAgIGFt
YmlndW91cyA9ICh4UmF5LnkoKSA9PSBwdHNbMV0ueSgpKTsKKyAgICAgICAgICAgIHJldHVybiB0
cnVlOworICAgICAgICB9CisgICAgICAgIHJldHVybiBmYWxzZTsKKyAgICB9CisgICAgLy8gQW1i
aWd1aXR5IGNoZWNrCisgICAgaWYgKHhSYXkueSgpID09IHB0c1sxXS55KCkpIHsKKyAgICAgICAg
aWYgKHhSYXkueCgpIDw9IHB0c1sxXS54KCkpIHsKKyAgICAgICAgICAgIGFtYmlndW91cyA9IHRy
dWU7CisgICAgICAgICAgICByZXR1cm4gdHJ1ZTsKKyAgICAgICAgfQorICAgICAgICByZXR1cm4g
ZmFsc2U7CisgICAgfQorICAgIC8vIEZ1bGwgbGluZSBzZWdtZW50IGV2YWx1YXRpb24KKyAgICBm
bG9hdCBkZWx0YVkgPSBwdHNbMV0ueSgpIC0gcHRzWzBdLnkoKTsKKyAgICBmbG9hdCBkZWx0YVgg
PSBwdHNbMV0ueCgpIC0gcHRzWzBdLngoKTsKKyAgICBmbG9hdCBzbG9wZSA9IGRlbHRhWSAvIGRl
bHRhWDsKKyAgICBmbG9hdCBiID0gcHRzWzBdLnkoKSAtIHNsb3BlICogcHRzWzBdLngoKTsKKyAg
ICAvLyBTb2x2ZSBmb3IgeCBjb29yZGluYXRlIGF0IHkgPSB4UmF5LnkoKQorICAgIGZsb2F0IHgg
PSAoeFJheS55KCkgLSBiKSAvIHNsb3BlOworICAgIHJldHVybiB4UmF5LngoKSA8PSB4OworfQor
CitpbnQgbnVtWFJheUNyb3NzaW5nc0ZvckN1YmljKGNvbnN0IFhSYXkmIHhSYXksIGNvbnN0IEZs
b2F0UG9pbnQgY3ViaWNbNF0sIGJvb2wmIGFtYmlndW91cykKK3sKKyAgICBpbnQgbnVtQ3Jvc3Np
bmdzID0gMDsKKyAgICBGbG9hdFBvaW50IG1vbm90b25pY0N1Ymljc1sxMF07CisgICAgaW50IG51
bU1vbm90b25pY0N1YmljcyA9IDEgKyBjaG9wQ3ViaWNBdFlFeHRyZW1hKGN1YmljLCBtb25vdG9u
aWNDdWJpY3MpOworICAgIGFtYmlndW91cyA9IGZhbHNlOworICAgIEZsb2F0UG9pbnQqIG1vbm90
b25pY0N1Ymljc1BvaW50ZXIgPSAmbW9ub3RvbmljQ3ViaWNzWzBdOworICAgIGZvciAoaW50IGkg
PSAwOyBpIDwgbnVtTW9ub3RvbmljQ3ViaWNzOyArK2kpIHsKKyAgICAgICAgaWYgKHhSYXlDcm9z
c2VzTW9ub3RvbmljQ3ViaWMoeFJheSwgbW9ub3RvbmljQ3ViaWNzUG9pbnRlciwgYW1iaWd1b3Vz
KSkKKyAgICAgICAgICAgICsrbnVtQ3Jvc3NpbmdzOworICAgICAgICBpZiAoYW1iaWd1b3VzKQor
ICAgICAgICAgICAgcmV0dXJuIDA7CisgICAgICAgIG1vbm90b25pY0N1Ymljc1BvaW50ZXIgKz0g
MzsKKyAgICB9CisgICAgcmV0dXJuIG51bUNyb3NzaW5nczsKK30KKworfSAvLyBuYW1lc3BhY2Ug
TG9vcEJsaW5uTWF0aFV0aWxzCit9IC8vIG5hbWVzcGFjZSBXZWJDb3JlCkluZGV4OiBXZWJDb3Jl
L3BsYXRmb3JtL2dyYXBoaWNzL2dwdS9Mb29wQmxpbm5NYXRoVXRpbHMuaAo9PT09PT09PT09PT09
PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09Ci0t
LSBXZWJDb3JlL3BsYXRmb3JtL2dyYXBoaWNzL2dwdS9Mb29wQmxpbm5NYXRoVXRpbHMuaAkocmV2
aXNpb24gMCkKKysrIFdlYkNvcmUvcGxhdGZvcm0vZ3JhcGhpY3MvZ3B1L0xvb3BCbGlubk1hdGhV
dGlscy5oCShyZXZpc2lvbiAwKQpAQCAtMCwwICsxLDEwOCBAQAorLyoKKyAqIENvcHlyaWdodCAo
QykgMjAxMCBHb29nbGUgSW5jLiBBbGwgcmlnaHRzIHJlc2VydmVkLgorICoKKyAqIFJlZGlzdHJp
YnV0aW9uIGFuZCB1c2UgaW4gc291cmNlIGFuZCBiaW5hcnkgZm9ybXMsIHdpdGggb3Igd2l0aG91
dAorICogbW9kaWZpY2F0aW9uLCBhcmUgcGVybWl0dGVkIHByb3ZpZGVkIHRoYXQgdGhlIGZvbGxv
d2luZyBjb25kaXRpb25zCisgKiBhcmUgbWV0OgorICoKKyAqIDEuICBSZWRpc3RyaWJ1dGlvbnMg
b2Ygc291cmNlIGNvZGUgbXVzdCByZXRhaW4gdGhlIGFib3ZlIGNvcHlyaWdodAorICogICAgIG5v
dGljZSwgdGhpcyBsaXN0IG9mIGNvbmRpdGlvbnMgYW5kIHRoZSBmb2xsb3dpbmcgZGlzY2xhaW1l
ci4KKyAqIDIuICBSZWRpc3RyaWJ1dGlvbnMgaW4gYmluYXJ5IGZvcm0gbXVzdCByZXByb2R1Y2Ug
dGhlIGFib3ZlIGNvcHlyaWdodAorICogICAgIG5vdGljZSwgdGhpcyBsaXN0IG9mIGNvbmRpdGlv
bnMgYW5kIHRoZSBmb2xsb3dpbmcgZGlzY2xhaW1lciBpbiB0aGUKKyAqICAgICBkb2N1bWVudGF0
aW9uIGFuZC9vciBvdGhlciBtYXRlcmlhbHMgcHJvdmlkZWQgd2l0aCB0aGUgZGlzdHJpYnV0aW9u
LgorICoKKyAqIFRISVMgU09GVFdBUkUgSVMgUFJPVklERUQgQlkgQVBQTEUgQU5EIElUUyBDT05U
UklCVVRPUlMgIkFTIElTIiBBTkQgQU5ZCisgKiBFWFBSRVNTIE9SIElNUExJRUQgV0FSUkFOVElF
UywgSU5DTFVESU5HLCBCVVQgTk9UIExJTUlURUQgVE8sIFRIRSBJTVBMSUVECisgKiBXQVJSQU5U
SUVTIE9GIE1FUkNIQU5UQUJJTElUWSBBTkQgRklUTkVTUyBGT1IgQSBQQVJUSUNVTEFSIFBVUlBP
U0UgQVJFCisgKiBESVNDTEFJTUVELiBJTiBOTyBFVkVOVCBTSEFMTCBBUFBMRSBPUiBJVFMgQ09O
VFJJQlVUT1JTIEJFIExJQUJMRSBGT1IgQU5ZCisgKiBESVJFQ1QsIElORElSRUNULCBJTkNJREVO
VEFMLCBTUEVDSUFMLCBFWEVNUExBUlksIE9SIENPTlNFUVVFTlRJQUwgREFNQUdFUworICogKElO
Q0xVRElORywgQlVUIE5PVCBMSU1JVEVEIFRPLCBQUk9DVVJFTUVOVCBPRiBTVUJTVElUVVRFIEdP
T0RTIE9SIFNFUlZJQ0VTOworICogTE9TUyBPRiBVU0UsIERBVEEsIE9SIFBST0ZJVFM7IE9SIEJV
U0lORVNTIElOVEVSUlVQVElPTikgSE9XRVZFUiBDQVVTRUQgQU5ECisgKiBPTiBBTlkgVEhFT1JZ
IE9GIExJQUJJTElUWSwgV0hFVEhFUiBJTiBDT05UUkFDVCwgU1RSSUNUIExJQUJJTElUWSwgT1Ig
VE9SVAorICogKElOQ0xVRElORyBORUdMSUdFTkNFIE9SIE9USEVSV0lTRSkgQVJJU0lORyBJTiBB
TlkgV0FZIE9VVCBPRiBUSEUgVVNFIE9GCisgKiBUSElTIFNPRlRXQVJFLCBFVkVOIElGIEFEVklT
RUQgT0YgVEhFIFBPU1NJQklMSVRZIE9GIFNVQ0ggREFNQUdFLgorICovCisKKyNpZm5kZWYgTG9v
cEJsaW5uTWF0aFV0aWxzX2gKKyNkZWZpbmUgTG9vcEJsaW5uTWF0aFV0aWxzX2gKKworI2luY2x1
ZGUgIkZsb2F0UG9pbnQuaCIKKyNpbmNsdWRlICJGbG9hdFBvaW50M0QuaCIKKyNpbmNsdWRlIDxt
YXRoLmg+CisKK25hbWVzcGFjZSBXZWJDb3JlIHsKKworLy8gVXNlIGEgbmFtZXNwYWNlIGZvciB0
aGVzZSBzbyB3ZSBjYW4gZWFzaWx5IGltcG9ydCB0aGVtLgorbmFtZXNwYWNlIExvb3BCbGlubk1h
dGhVdGlscyB7CisKK2Zsb2F0IHJvdW5kVG9aZXJvKGZsb2F0IHZhbCk7Citib29sIGFwcHJveEVx
dWFsKGNvbnN0IEZsb2F0UG9pbnQmIHYwLCBjb25zdCBGbG9hdFBvaW50JiB2MSk7Citib29sIGFw
cHJveEVxdWFsKGNvbnN0IEZsb2F0UG9pbnQzRCYgdjAsIGNvbnN0IEZsb2F0UG9pbnQzRCYgdjEp
OworYm9vbCBhcHByb3hFcXVhbChmbG9hdCBmMCwgZmxvYXQgZjEpOworCisvLyBEZXRlcm1pbmVz
IHdoZXRoZXIgdGhlIGxpbmUgc2VnbWVudCBiZXR3ZWVuIChwMSwgcTEpIGludGVyc2VjdHMKKy8v
IHRoYXQgYmV0d2VlbiAocDIsIHEyKS4KK2Jvb2wgbGluZXNJbnRlcnNlY3QoY29uc3QgRmxvYXRQ
b2ludCYgcDEsCisgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIHExLAorICAg
ICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBwMiwKKyAgICAgICAgICAgICAgICAg
ICAgY29uc3QgRmxvYXRQb2ludCYgcTIpOworCisvLyBEZXRlcm1pbmVzIHdoZXRoZXIgInBvaW50
IiBpcyBpbnNpZGUgdGhlIDJEIHRyaWFuZ2xlIGRlZmluZWQgYnkKKy8vIHZlcnRpY2VzIGEsIGIs
IGFuZCBjLiBUaGlzIHRlc3QgZGVmaW5lcyB0aGF0IHBvaW50cyBleGFjdGx5IG9uIGFuCisvLyBl
ZGdlIGFyZSBub3QgY29uc2lkZXJlZCB0byBiZSBpbnNpZGUgdGhlIHRyaWFuZ2xlLgorYm9vbCBw
b2ludEluVHJpYW5nbGUoY29uc3QgRmxvYXRQb2ludCYgcG9pbnQsCisgICAgICAgICAgICAgICAg
ICAgICBjb25zdCBGbG9hdFBvaW50JiBhLAorICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxv
YXRQb2ludCYgYiwKKyAgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIGMpOwor
CisvLyBEZXRlcm1pbmVzIHdoZXRoZXIgdGhlIHRyaWFuZ2xlcyBkZWZpbmVkIGJ5IHRoZSBwb2lu
dHMgKGExLCBiMSwgYzEpCisvLyBhbmQgKGEyLCBiMiwgYzIpIG92ZXJsYXAuIFRoZSBkZWZpbml0
aW9uIG9mIHRoaXMgZnVuY3Rpb24gaXMgdGhhdAorLy8gaWYgdGhlIHR3byB0cmlhbmdsZXMgb25s
eSBzaGFyZSBhbiBhZGphY2VudCBlZGdlIG9yIHZlcnRleCwgdGhleQorLy8gYXJlIG5vdCBjb25z
aWRlcmVkIHRvIG92ZXJsYXAuCitib29sIHRyaWFuZ2xlc092ZXJsYXAoY29uc3QgRmxvYXRQb2lu
dCYgYTEsCisgICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgYjEsCisgICAg
ICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgYzEsCisgICAgICAgICAgICAgICAg
ICAgICAgY29uc3QgRmxvYXRQb2ludCYgYTIsCisgICAgICAgICAgICAgICAgICAgICAgY29uc3Qg
RmxvYXRQb2ludCYgYjIsCisgICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYg
YzIpOworCisvLyBHaXZlbiBhIHNyYyBjdWJpYyBiZXppZXIsIGNob3BzIGl0IGF0IHRoZSBzcGVj
aWZpZWQgdCB2YWx1ZSwKKy8vIHdoZXJlIDAgPCB0IDwgMSwgYW5kIHJldHVybnMgdGhlIHR3byBu
ZXcgY3ViaWNzIGluIGRzdFswLi4zXQorLy8gYW5kIGRzdFszLi42XS4KK3ZvaWQgY2hvcEN1Ymlj
QXQoY29uc3QgRmxvYXRQb2ludCBzcmNbNF0sIEZsb2F0UG9pbnQgZHN0WzddLCBmbG9hdCB0KTsK
KworLy8gIlgtUmF5IiBxdWVyaWVzLiBBbiBYUmF5IGlzIGEgaGFsZi1saW5lIG9yaWdpbmF0aW5n
IGF0IHRoZSBnaXZlbgorLy8gcG9pbnQgYW5kIGV4dGVuZGluZyB0byB4PStpbmZpbml0eS4KK3R5
cGVkZWYgRmxvYXRQb2ludCBYUmF5OworCisvLyBHaXZlbiBhbiBhcmJpdHJhcnkgY3ViaWMgYmV6
aWVyLCByZXR1cm4gdGhlIG51bWJlciBvZiB0aW1lcyBhbiBYUmF5CisvLyBjcm9zc2VzIHRoZSBj
dWJpYy4gVmFsaWQgcmV0dXJuIHZhbHVlcyBhcmUgWzAuLjNdLgorLy8KKy8vIEJ5IGRlZmluaXRp
b24gdGhlIGN1YmljIGlzIG9wZW4gYXQgdGhlIHN0YXJ0aW5nIHBvaW50OyBpbiBvdGhlcgorLy8g
d29yZHMsIGlmIHB0LmZZIGlzIGVxdWl2YWxlbnQgdG8gY3ViaWNbMF0uZlksIGFuZCBwdC5mWCBp
cyB0byB0aGUKKy8vIGxlZnQgb2YgdGhlIGN1cnZlLCB0aGUgbGluZSBpcyBub3QgY29uc2lkZXJl
ZCB0byBjcm9zcyB0aGUgY3VydmUsCisvLyBidXQgaWYgaXQgaXMgZXF1YWwgdG8gY3ViaWNbM10u
ZlkgdGhlbiBpdCBpcyBjb25zaWRlcmVkIHRvCisvLyBjcm9zcy4KKy8vCisvLyBPdXRnb2luZyAi
YW1iaWd1b3VzIiBhcmd1bWVudCBpbmRpY2F0ZXMgd2hldGhlciB0aGUgYW5zd2VyIGlzIGFtYmln
dW91cworLy8gYmVjYXVzZSB0aGUgcXVlcnkgb2NjdXJyZWQgZXhhY3RseSBhdCBvbmUgb2YgdGhl
IGVuZHBvaW50cycgeQorLy8gY29vcmRpbmF0ZXMgb3IgYXQgYSB0YW5nZW50IHBvaW50LCBpbmRp
Y2F0aW5nIHRoYXQgYW5vdGhlciBxdWVyeSB5CisvLyBjb29yZGluYXRlIGlzIHByZWZlcnJlZCBm
b3Igcm9idXN0bmVzcy4KK2ludCBudW1YUmF5Q3Jvc3NpbmdzRm9yQ3ViaWMoY29uc3QgWFJheSYg
eFJheSwKKyAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCBjdWJp
Y1s0XSwKKyAgICAgICAgICAgICAgICAgICAgICAgICAgICAgYm9vbCYgYW1iaWd1b3VzKTsKKwor
Ly8gR2l2ZW4gYSBsaW5lIHNlZ21lbnQgZnJvbSBsaW5lRW5kcG9pbnRzWzBdIHRvIGxpbmVFbmRw
b2ludHNbMV0sIGFuZCBhbgorLy8gWFJheSwgcmV0dXJucyB0cnVlIGlmIHRoZXkgaW50ZXJzZWN0
LiBPdXRnb2luZyAiYW1iaWd1b3VzIiBhcmd1bWVudAorLy8gaW5kaWNhdGVzIHdoZXRoZXIgdGhl
IGFuc3dlciBpcyBhbWJpZ3VvdXMgYmVjYXVzZSB0aGUgcXVlcnkgb2NjdXJyZWQKKy8vIGV4YWN0
bHkgYXQgb25lIG9mIHRoZSBlbmRwb2ludHMnIHkgY29vcmRpbmF0ZXMsIGluZGljYXRpbmcgdGhh
dCBhbm90aGVyCisvLyBxdWVyeSB5IGNvb3JkaW5hdGUgaXMgcHJlZmVycmVkIGZvciByb2J1c3Ru
ZXNzLgorYm9vbCB4UmF5Q3Jvc3Nlc0xpbmUoY29uc3QgWFJheSYgeFJheSwKKyAgICAgICAgICAg
ICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQgbGluZUVuZHBvaW50c1syXSwKKyAgICAgICAgICAg
ICAgICAgICAgIGJvb2wmIGFtYmlndW91cyk7CisKK30gLy8gbmFtZXNwYWNlIExvb3BCbGlubk1h
dGhVdGlscworCit9IC8vIG5hbWVzcGFjZSBXZWJDb3JlCisKKyNlbmRpZiAvLyBMb29wQmxpbm5N
YXRoVXRpbHNfaAo=
</data>
<flag name="commit-queue"
          id="56345"
          type_id="3"
          status="-"
          setter="kbr"
    />
          </attachment>
          <attachment
              isobsolete="1"
              ispatch="1"
              isprivate="0"
          >
            <attachid>67128</attachid>
            <date>2010-09-09 18:01:07 -0700</date>
            <delta_ts>2010-09-09 18:44:36 -0700</delta_ts>
            <desc>Revised patch</desc>
            <filename>math-utils.patch</filename>
            <type>text/plain</type>
            <size>25559</size>
            <attacher name="Kenneth Russell">kbr</attacher>
            
              <data encoding="base64">SW5kZXg6IFdlYkNvcmUvQ2hhbmdlTG9nCj09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09
PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0KLS0tIFdlYkNvcmUvQ2hhbmdlTG9n
CShyZXZpc2lvbiA2NzEzMykKKysrIFdlYkNvcmUvQ2hhbmdlTG9nCSh3b3JraW5nIGNvcHkpCkBA
IC0xLDMgKzEsMjUgQEAKKzIwMTAtMDktMDkgIEtlbm5ldGggUnVzc2VsbCAgPGtickBnb29nbGUu
Y29tPgorCisgICAgICAgIFJldmlld2VkIGJ5IE5PQk9EWSAoT09QUyEpLgorCisgICAgICAgIEFk
ZCBtYXRoIHV0aWxpdGllcyBmb3IgY3ViaWMgY3VydmUgcHJvY2Vzc2luZworICAgICAgICBodHRw
czovL2J1Z3Mud2Via2l0Lm9yZy9zaG93X2J1Zy5jZ2k/aWQ9NDUyNTEKKworICAgICAgICBBZGRp
bmcgbWF0aGVtYXRpYyB1dGlsaXRpZXMgbmVlZGVkIGZvciB0aGUgR1BVIGFjY2VsZXJhdGVkIHBh
dGgKKyAgICAgICAgcmVuZGVyaW5nIGFsZ29yaXRobSBmcm9tIEdQVSBHZW1zIDMuIE5vIHRlc3Rz
IHlldDsgd2lsbCBiZSB0ZXN0ZWQKKyAgICAgICAgaW4gY29uanVuY3Rpb24gd2l0aCBsYXRlciBj
b2RlLgorCisgICAgICAgICogcGxhdGZvcm0vZ3JhcGhpY3MvZ3B1L0xvb3BCbGlubk1hdGhVdGls
cy5jcHA6IEFkZGVkLgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxzOjpyb3Vu
ZFRvWmVybyk6CisgICAgICAgIChXZWJDb3JlOjpMb29wQmxpbm5NYXRoVXRpbHM6OmFwcHJveEVx
dWFsKToKKyAgICAgICAgKFdlYkNvcmU6Okxvb3BCbGlubk1hdGhVdGlsczo6bGluZXNJbnRlcnNl
Y3QpOgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxzOjpwb2ludEluVHJpYW5n
bGUpOgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxzOjp0cmlhbmdsZXNPdmVy
bGFwKToKKyAgICAgICAgKFdlYkNvcmU6Okxvb3BCbGlubk1hdGhVdGlsczo6Y2hvcEN1YmljQXQp
OgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxzOjp4UmF5Q3Jvc3Nlc0xpbmUp
OgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxzOjpudW1YUmF5Q3Jvc3Npbmdz
Rm9yQ3ViaWMpOgorICAgICAgICAqIHBsYXRmb3JtL2dyYXBoaWNzL2dwdS9Mb29wQmxpbm5NYXRo
VXRpbHMuaDogQWRkZWQuCisKIDIwMTAtMDktMDkgIENocmlzIFJvZ2VycyAgPGNyb2dlcnNAZ29v
Z2xlLmNvbT4KIAogICAgICAgICBSZXZpZXdlZCBieSBLZW5uZXRoIFJ1c3NlbGwuCkluZGV4OiBX
ZWJDb3JlL3BsYXRmb3JtL2dyYXBoaWNzL2dwdS9Mb29wQmxpbm5NYXRoVXRpbHMuY3BwCj09PT09
PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09
PT09PT0KLS0tIFdlYkNvcmUvcGxhdGZvcm0vZ3JhcGhpY3MvZ3B1L0xvb3BCbGlubk1hdGhVdGls
cy5jcHAJKHJldmlzaW9uIDApCisrKyBXZWJDb3JlL3BsYXRmb3JtL2dyYXBoaWNzL2dwdS9Mb29w
Qmxpbm5NYXRoVXRpbHMuY3BwCShyZXZpc2lvbiAwKQpAQCAtMCwwICsxLDU2NSBAQAorLyoKKyAq
IENvcHlyaWdodCAoQykgMjAxMCBHb29nbGUgSW5jLiBBbGwgcmlnaHRzIHJlc2VydmVkLgorICoK
KyAqIFJlZGlzdHJpYnV0aW9uIGFuZCB1c2UgaW4gc291cmNlIGFuZCBiaW5hcnkgZm9ybXMsIHdp
dGggb3Igd2l0aG91dAorICogbW9kaWZpY2F0aW9uLCBhcmUgcGVybWl0dGVkIHByb3ZpZGVkIHRo
YXQgdGhlIGZvbGxvd2luZyBjb25kaXRpb25zCisgKiBhcmUgbWV0OgorICoKKyAqIDEuICBSZWRp
c3RyaWJ1dGlvbnMgb2Ygc291cmNlIGNvZGUgbXVzdCByZXRhaW4gdGhlIGFib3ZlIGNvcHlyaWdo
dAorICogICAgIG5vdGljZSwgdGhpcyBsaXN0IG9mIGNvbmRpdGlvbnMgYW5kIHRoZSBmb2xsb3dp
bmcgZGlzY2xhaW1lci4KKyAqIDIuICBSZWRpc3RyaWJ1dGlvbnMgaW4gYmluYXJ5IGZvcm0gbXVz
dCByZXByb2R1Y2UgdGhlIGFib3ZlIGNvcHlyaWdodAorICogICAgIG5vdGljZSwgdGhpcyBsaXN0
IG9mIGNvbmRpdGlvbnMgYW5kIHRoZSBmb2xsb3dpbmcgZGlzY2xhaW1lciBpbiB0aGUKKyAqICAg
ICBkb2N1bWVudGF0aW9uIGFuZC9vciBvdGhlciBtYXRlcmlhbHMgcHJvdmlkZWQgd2l0aCB0aGUg
ZGlzdHJpYnV0aW9uLgorICoKKyAqIFRISVMgU09GVFdBUkUgSVMgUFJPVklERUQgQlkgQVBQTEUg
QU5EIElUUyBDT05UUklCVVRPUlMgIkFTIElTIiBBTkQgQU5ZCisgKiBFWFBSRVNTIE9SIElNUExJ
RUQgV0FSUkFOVElFUywgSU5DTFVESU5HLCBCVVQgTk9UIExJTUlURUQgVE8sIFRIRSBJTVBMSUVE
CisgKiBXQVJSQU5USUVTIE9GIE1FUkNIQU5UQUJJTElUWSBBTkQgRklUTkVTUyBGT1IgQSBQQVJU
SUNVTEFSIFBVUlBPU0UgQVJFCisgKiBESVNDTEFJTUVELiBJTiBOTyBFVkVOVCBTSEFMTCBBUFBM
RSBPUiBJVFMgQ09OVFJJQlVUT1JTIEJFIExJQUJMRSBGT1IgQU5ZCisgKiBESVJFQ1QsIElORElS
RUNULCBJTkNJREVOVEFMLCBTUEVDSUFMLCBFWEVNUExBUlksIE9SIENPTlNFUVVFTlRJQUwgREFN
QUdFUworICogKElOQ0xVRElORywgQlVUIE5PVCBMSU1JVEVEIFRPLCBQUk9DVVJFTUVOVCBPRiBT
VUJTVElUVVRFIEdPT0RTIE9SIFNFUlZJQ0VTOworICogTE9TUyBPRiBVU0UsIERBVEEsIE9SIFBS
T0ZJVFM7IE9SIEJVU0lORVNTIElOVEVSUlVQVElPTikgSE9XRVZFUiBDQVVTRUQgQU5ECisgKiBP
TiBBTlkgVEhFT1JZIE9GIExJQUJJTElUWSwgV0hFVEhFUiBJTiBDT05UUkFDVCwgU1RSSUNUIExJ
QUJJTElUWSwgT1IgVE9SVAorICogKElOQ0xVRElORyBORUdMSUdFTkNFIE9SIE9USEVSV0lTRSkg
QVJJU0lORyBJTiBBTlkgV0FZIE9VVCBPRiBUSEUgVVNFIE9GCisgKiBUSElTIFNPRlRXQVJFLCBF
VkVOIElGIEFEVklTRUQgT0YgVEhFIFBPU1NJQklMSVRZIE9GIFNVQ0ggREFNQUdFLgorICovCisK
KyNpbmNsdWRlICJjb25maWcuaCIKKworI2luY2x1ZGUgIkxvb3BCbGlubk1hdGhVdGlscy5oIgor
CisjaW5jbHVkZSAiRmxvYXRQb2ludC5oIgorI2luY2x1ZGUgIk1hdGhFeHRyYXMuaCIKKyNpbmNs
dWRlIDxhbGdvcml0aG0+CisjaW5jbHVkZSA8c3RyaW5nLmg+IC8vIGZvciBtZW1jcHkKKworbmFt
ZXNwYWNlIFdlYkNvcmUgeworbmFtZXNwYWNlIExvb3BCbGlubk1hdGhVdGlscyB7CisKK25hbWVz
cGFjZSB7CisKKy8vIFV0aWxpdHkgZnVuY3Rpb25zIGxvY2FsIHRvIHRoaXMgZmlsZS4KK2ludCBv
cmllbnRhdGlvbihjb25zdCBGbG9hdFBvaW50JiBwMSwKKyAgICAgICAgICAgICAgICBjb25zdCBG
bG9hdFBvaW50JiBwMiwKKyAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBwMykKK3sK
KyAgICBmbG9hdCBjcm9zc1Byb2R1Y3QgPSAocDIueSgpIC0gcDEueSgpKSAqIChwMy54KCkgLSBw
Mi54KCkpIC0gKHAzLnkoKSAtIHAyLnkoKSkgKiAocDIueCgpIC0gcDEueCgpKTsKKyAgICByZXR1
cm4gKGNyb3NzUHJvZHVjdCA8IDAuMGYpID8gLTEgOiAoKGNyb3NzUHJvZHVjdCA+IDAuMGYpID8g
MSA6IDApOworfQorCitib29sIGVkZ2VFZGdlVGVzdChjb25zdCBGbG9hdFNpemUmIHYwRGVsdGEs
CisgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiB2MCwKKyAgICAgICAgICAgICAg
ICAgIGNvbnN0IEZsb2F0UG9pbnQmIHUwLAorICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQ
b2ludCYgdTEpCit7CisgICAgLy8gVGhpcyBlZGdlIHRvIGVkZ2UgdGVzdCBpcyBiYXNlZCBvbiBG
cmFubGluIEFudG9uaW8ncyBnZW06ICJGYXN0ZXIKKyAgICAvLyBMaW5lIFNlZ21lbnQgSW50ZXJz
ZWN0aW9uIiwgaW4gR3JhcGhpY3MgR2VtcyBJSUksIHBwLiAxOTktMjAyLgorICAgIGZsb2F0IGF4
ID0gdjBEZWx0YS53aWR0aCgpOworICAgIGZsb2F0IGF5ID0gdjBEZWx0YS5oZWlnaHQoKTsKKyAg
ICBmbG9hdCBieCA9IHUwLngoKSAtIHUxLngoKTsKKyAgICBmbG9hdCBieSA9IHUwLnkoKSAtIHUx
LnkoKTsKKyAgICBmbG9hdCBjeCA9IHYwLngoKSAtIHUwLngoKTsKKyAgICBmbG9hdCBjeSA9IHYw
LnkoKSAtIHUwLnkoKTsKKyAgICBmbG9hdCBmID0gYXkgKiBieCAtIGF4ICogYnk7CisgICAgZmxv
YXQgZCA9IGJ5ICogY3ggLSBieCAqIGN5OworICAgIGlmICgoZiA+IDAgJiYgZCA+PSAwICYmIGQg
PD0gZikgfHwgKGYgPCAwICYmIGQgPD0gMCAmJiBkID49IGYpKSB7CisgICAgICAgIGZsb2F0IGUg
PSBheCAqIGN5IC0gYXkgKiBjeDsKKworICAgICAgICAvLyBUaGlzIGFkZGl0aW9uYWwgdGVzdCBh
dm9pZHMgcmVwb3J0aW5nIGNvaW5jaWRlbnQgZWRnZXMsIHdoaWNoCisgICAgICAgIC8vIGlzIHRo
ZSBiZWhhdmlvciB3ZSB3YW50LgorICAgICAgICBpZiAoYXBwcm94RXF1YWwoZSwgMCkgfHwgYXBw
cm94RXF1YWwoZiwgMCkgfHwgYXBwcm94RXF1YWwoZSwgZikpCisgICAgICAgICAgICByZXR1cm4g
ZmFsc2U7CisKKyAgICAgICAgaWYgKGYgPiAwKQorICAgICAgICAgICAgcmV0dXJuIGUgPj0gMCAm
JiBlIDw9IGY7CisKKyAgICAgICAgcmV0dXJuIGUgPD0gMCAmJiBlID49IGY7CisgICAgfQorICAg
IHJldHVybiBmYWxzZTsKK30KKworYm9vbCBlZGdlQWdhaW5zdFRyaUVkZ2VzKGNvbnN0IEZsb2F0
UG9pbnQmIHYwLAorICAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIHYx
LAorICAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIHUwLAorICAgICAg
ICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIHUxLAorICAgICAgICAgICAgICAg
ICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIHUyKQoreworICAgIEZsb2F0U2l6ZSBkZWx0YSA9
IHYxIC0gdjA7CisgICAgLy8gVGVzdCBlZGdlIHUwLCB1MSBhZ2FpbnN0IHYwLCB2MS4KKyAgICBp
ZiAoZWRnZUVkZ2VUZXN0KGRlbHRhLCB2MCwgdTAsIHUxKSkKKyAgICAgICAgcmV0dXJuIHRydWU7
CisgICAgLy8gVGVzdCBlZGdlIHUxLCB1MiBhZ2FpbnN0IHYwLCB2MS4KKyAgICBpZiAoZWRnZUVk
Z2VUZXN0KGRlbHRhLCB2MCwgdTEsIHUyKSkKKyAgICAgICAgcmV0dXJuIHRydWU7CisgICAgLy8g
VGVzdCBlZGdlIHUyLCB1MSBhZ2FpbnN0IHYwLCB2MS4KKyAgICBpZiAoZWRnZUVkZ2VUZXN0KGRl
bHRhLCB2MCwgdTIsIHUwKSkKKyAgICAgICAgcmV0dXJuIHRydWU7CisgICAgcmV0dXJuIGZhbHNl
OworfQorCisvLyBBIHJvdW5kb2ZmIGZhY3RvciBpbiB0aGUgY3ViaWMgY2xhc3NpZmljYXRpb24g
YW5kIHRleHR1cmUgY29vcmRpbmF0ZQorLy8gZ2VuZXJhdGlvbiBhbGdvcml0aG1zLiBJdCBwcmlt
YXJpbHkgZGV0ZXJtaW5lcyB0aGUgaGFuZGxpbmcgb2YgY29ybmVyCisvLyBjYXNlcyBkdXJpbmcg
dGhlIGNsYXNzaWZpY2F0aW9uIHByb2Nlc3MuIEJlIGNhcmVmdWwgd2hlbiBhZGp1c3RpbmcgaXQ7
CisvLyBpdCBoYXMgYmVlbiBkZXRlcm1pbmVkIGVtcGlyaWNhbGx5IHRvIHdvcmsgd2VsbC4gV2hl
biBjaGFuZ2luZyBpdCwgeW91CisvLyBzaG91bGQgbG9vayBpbiBwYXJ0aWN1bGFyIGF0IHNoYXBl
cyB0aGF0IGNvbnRhaW4gcXVhZHJhdGljIGN1cnZlcyBhbmQKKy8vIGVuc3VyZSB0aGV5IHN0aWxs
IGxvb2sgc21vb3RoLiBPbmNlIHBpeGVsIHRlc3RzIGFyZSBydW5uaW5nIGFnYWluc3QgdGhpcwor
Ly8gYWxnb3JpdGhtLCB0aGV5IHNob3VsZCBwcm92aWRlIHN1ZmZpY2llbnQgY292ZXJhZ2UgdG8g
ZW5zdXJlIHRoYXQKKy8vIGFkanVzdGluZyB0aGUgY29uc3RhbnQgd29uJ3QgYnJlYWsgYW55dGhp
bmcuCitjb25zdCBmbG9hdCBFcHNpbG9uID0gNS4wZS00ZjsKKworfSAvLyBhbm9ueW1vdXMgbmFt
ZXNwYWNlCisKKy8vIEV4cG9ydGVkIHJvdXRpbmVzCisKK2Zsb2F0IHJvdW5kVG9aZXJvKGZsb2F0
IHZhbCkKK3sKKyAgICBpZiAodmFsIDwgRXBzaWxvbiAmJiB2YWwgPiAtRXBzaWxvbikKKyAgICAg
ICAgcmV0dXJuIDA7CisgICAgcmV0dXJuIHZhbDsKK30KKworYm9vbCBhcHByb3hFcXVhbChjb25z
dCBGbG9hdFBvaW50JiB2MCwgY29uc3QgRmxvYXRQb2ludCYgdjEpCit7CisgICAgcmV0dXJuICh2
MCAtIHYxKS5kaWFnb25hbExlbmd0aFNxdWFyZWQoKSA8IEVwc2lsb24gKiBFcHNpbG9uOworfQor
Citib29sIGFwcHJveEVxdWFsKGNvbnN0IEZsb2F0UG9pbnQzRCYgdjAsIGNvbnN0IEZsb2F0UG9p
bnQzRCYgdjEpCit7CisgICAgcmV0dXJuICh2MCAtIHYxKS5sZW5ndGhTcXVhcmVkKCkgPCBFcHNp
bG9uICogRXBzaWxvbjsKK30KKworYm9vbCBhcHByb3hFcXVhbChmbG9hdCBmMCwgZmxvYXQgZjEp
Cit7CisgICAgcmV0dXJuIGZhYnNmKGYwIC0gZjEpIDwgRXBzaWxvbjsKK30KKworYm9vbCBsaW5l
c0ludGVyc2VjdChjb25zdCBGbG9hdFBvaW50JiBwMSwKKyAgICAgICAgICAgICAgICAgICAgY29u
c3QgRmxvYXRQb2ludCYgcTEsCisgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQm
IHAyLAorICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBxMikKK3sKKyAgICBy
ZXR1cm4gKG9yaWVudGF0aW9uKHAxLCBxMSwgcDIpICE9IG9yaWVudGF0aW9uKHAxLCBxMSwgcTIp
CisgICAgICAgICAgICAmJiBvcmllbnRhdGlvbihwMiwgcTIsIHAxKSAhPSBvcmllbnRhdGlvbihw
MiwgcTIsIHExKSk7Cit9CisKK2Jvb2wgcG9pbnRJblRyaWFuZ2xlKGNvbnN0IEZsb2F0UG9pbnQm
IHBvaW50LAorICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgYSwKKyAgICAg
ICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIGIsCisgICAgICAgICAgICAgICAgICAg
ICBjb25zdCBGbG9hdFBvaW50JiBjKQoreworICAgIC8vIEFsZ29yaXRobSBmcm9tIGh0dHA6Ly93
d3cuYmxhY2twYXduLmNvbS90ZXh0cy9wb2ludGlucG9seS9kZWZhdWx0Lmh0bWwKKyAgICBmbG9h
dCB4MCA9IGMueCgpIC0gYS54KCk7CisgICAgZmxvYXQgeTAgPSBjLnkoKSAtIGEueSgpOworICAg
IGZsb2F0IHgxID0gYi54KCkgLSBhLngoKTsKKyAgICBmbG9hdCB5MSA9IGIueSgpIC0gYS55KCk7
CisgICAgZmxvYXQgeDIgPSBwb2ludC54KCkgLSBhLngoKTsKKyAgICBmbG9hdCB5MiA9IHBvaW50
LnkoKSAtIGEueSgpOworCisgICAgZmxvYXQgZG90MDAgPSB4MCAqIHgwICsgeTAgKiB5MDsKKyAg
ICBmbG9hdCBkb3QwMSA9IHgwICogeDEgKyB5MCAqIHkxOworICAgIGZsb2F0IGRvdDAyID0geDAg
KiB4MiArIHkwICogeTI7CisgICAgZmxvYXQgZG90MTEgPSB4MSAqIHgxICsgeTEgKiB5MTsKKyAg
ICBmbG9hdCBkb3QxMiA9IHgxICogeDIgKyB5MSAqIHkyOworICAgIGZsb2F0IGRlbm9taW5hdG9y
ID0gZG90MDAgKiBkb3QxMSAtIGRvdDAxICogZG90MDE7CisgICAgaWYgKCFkZW5vbWluYXRvcikK
KyAgICAgICAgLy8gVHJpYW5nbGUgaXMgemVyby1hcmVhLiBUcmVhdCBxdWVyeSBwb2ludCBhcyBu
b3QgYmVpbmcgaW5zaWRlLgorICAgICAgICByZXR1cm4gZmFsc2U7CisgICAgLy8gQ29tcHV0ZQor
ICAgIGZsb2F0IGludmVyc2VEZW5vbWluYXRvciA9IDEuMGYgLyBkZW5vbWluYXRvcjsKKyAgICBm
bG9hdCB1ID0gKGRvdDExICogZG90MDIgLSBkb3QwMSAqIGRvdDEyKSAqIGludmVyc2VEZW5vbWlu
YXRvcjsKKyAgICBmbG9hdCB2ID0gKGRvdDAwICogZG90MTIgLSBkb3QwMSAqIGRvdDAyKSAqIGlu
dmVyc2VEZW5vbWluYXRvcjsKKworICAgIHJldHVybiAodSA+IDAuMGYpICYmICh2ID4gMC4wZikg
JiYgKHUgKyB2IDwgMS4wZik7Cit9CisKK2Jvb2wgdHJpYW5nbGVzT3ZlcmxhcChjb25zdCBGbG9h
dFBvaW50JiBhMSwKKyAgICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBiMSwK
KyAgICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBjMSwKKyAgICAgICAgICAg
ICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBhMiwKKyAgICAgICAgICAgICAgICAgICAgICBj
b25zdCBGbG9hdFBvaW50JiBiMiwKKyAgICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBv
aW50JiBjMikKK3sKKyAgICAvLyBEZXJpdmVkIGZyb20gY29wbGFuYXJfdHJpX3RyaSgpIGF0Cisg
ICAgLy8gaHR0cDovL2pndC5ha3BldGVycy5jb20vcGFwZXJzL1NoZW5IZW5nVGFuZzAzL3RyaV90
cmkuaHRtbCAsCisgICAgLy8gc2ltcGxpZmllZCBmb3IgdGhlIDJEIGNhc2UgYW5kIG1vZGlmaWVk
IHNvIHRoYXQgb3ZlcmxhcHBpbmcgZWRnZXMKKyAgICAvLyBkbyBub3QgcmVwb3J0IG92ZXJsYXBw
aW5nIHRyaWFuZ2xlcy4KKworICAgIC8vIFRlc3QgYWxsIGVkZ2VzIG9mIHRyaWFuZ2xlIDEgYWdh
aW5zdCB0aGUgZWRnZXMgb2YgdHJpYW5nbGUgMi4KKyAgICBpZiAoZWRnZUFnYWluc3RUcmlFZGdl
cyhhMSwgYjEsIGEyLCBiMiwgYzIpCisgICAgICAgIHx8IGVkZ2VBZ2FpbnN0VHJpRWRnZXMoYjEs
IGMxLCBhMiwgYjIsIGMyKQorICAgICAgICB8fCBlZGdlQWdhaW5zdFRyaUVkZ2VzKGMxLCBhMSwg
YTIsIGIyLCBjMikpCisgICAgICAgIHJldHVybiB0cnVlOworICAgIC8vIEZpbmFsbHksIHRlc3Qg
aWYgdHJpMSBpcyB0b3RhbGx5IGNvbnRhaW5lZCBpbiB0cmkyIG9yIHZpY2UgdmVyc2EuCisgICAg
Ly8gVGhlIHBhcGVyIGFib3ZlIG9ubHkgcGVyZm9ybXMgdGhlIGZpcnN0IHR3byBwb2ludC1pbi10
cmlhbmdsZSB0ZXN0cy4KKyAgICAvLyBCZWNhdXNlIHdlIGRlZmluZSB0aGF0IHRyaWFuZ2xlcyBz
aGFyaW5nIGEgdmVydGV4IG9yIGVkZ2UgZG9uJ3QKKyAgICAvLyBvdmVybGFwLCB3ZSBtdXN0IHBl
cmZvcm0gYWRkaXRpb25hbCB0ZXN0cyB0byBzZWUgd2hldGhlciBvbmUKKyAgICAvLyB0cmlhbmds
ZSBpcyBjb250YWluZWQgaW4gdGhlIG90aGVyLgorICAgIGlmIChwb2ludEluVHJpYW5nbGUoYTEs
IGEyLCBiMiwgYzIpCisgICAgICAgIHx8IHBvaW50SW5UcmlhbmdsZShhMiwgYTEsIGIxLCBjMSkK
KyAgICAgICAgfHwgcG9pbnRJblRyaWFuZ2xlKGIxLCBhMiwgYjIsIGMyKQorICAgICAgICB8fCBw
b2ludEluVHJpYW5nbGUoYjIsIGExLCBiMSwgYzEpCisgICAgICAgIHx8IHBvaW50SW5Ucmlhbmds
ZShjMSwgYTIsIGIyLCBjMikKKyAgICAgICAgfHwgcG9pbnRJblRyaWFuZ2xlKGMyLCBhMSwgYjEs
IGMxKSkKKyAgICAgICAgcmV0dXJuIHRydWU7CisgICAgcmV0dXJuIGZhbHNlOworfQorCituYW1l
c3BhY2UgeworCisvLyBIZWxwZXIgcm91dGluZXMgZm9yIHB1YmxpYyBYUmF5IHF1ZXJpZXMgYmVs
b3cuIEFsbCBvZiB0aGlzIGNvZGUKKy8vIG9yaWdpbmF0ZWQgaW4gU2tpYTsgc2VlIGluY2x1ZGUv
Y29yZS8gYW5kIHNyYy9jb3JlLywgU2tTY2FsYXIuaCBhbmQKKy8vIFNrR2VvbWV0cnkue2NwcCxo
fS4KKworY29uc3QgZmxvYXQgTmVhcmx5WmVyb0NvbnN0YW50ID0gKDEuMGYgLyAoMSA8PCAxMikp
OworCitib29sIG5lYXJseVplcm8oZmxvYXQgeCwgZmxvYXQgdG9sZXJhbmNlID0gTmVhcmx5WmVy
b0NvbnN0YW50KQoreworICAgIEFTU0VSVCh0b2xlcmFuY2UgPiAwLjBmKTsKKyAgICByZXR1cm4g
OjpmYWJzZih4KSA8IHRvbGVyYW5jZTsKK30KKworLy8gTGluZWFybHkgaW50ZXJwb2xhdGUgYmV0
d2VlbiBhIGFuZCBiLCBiYXNlZCBvbiB0LgorLy8gSWYgdCBpcyAwLCByZXR1cm4gYTsgaWYgdCBp
cyAxLCByZXR1cm4gYjsgZWxzZSBpbnRlcnBvbGF0ZS4KKy8vIHQgbXVzdCBiZSBbMC4uMV0uCitm
bG9hdCBpbnRlcnBvbGF0ZShmbG9hdCBhLCBmbG9hdCBiLCBmbG9hdCB0KQoreworICAgIEFTU0VS
VCh0ID49IDAgJiYgdCA8PSAxKTsKKyAgICByZXR1cm4gYSArIChiIC0gYSkgKiB0OworfQorCitm
bG9hdCBldmFsdWF0ZUN1YmljKGZsb2F0IGNvbnRyb2xQb2ludDAsIGZsb2F0IGNvbnRyb2xQb2lu
dDEsIGZsb2F0IGNvbnRyb2xQb2ludDIsIGZsb2F0IGNvbnRyb2xQb2ludDMsIGZsb2F0IHQpCit7
CisgICAgQVNTRVJUKHQgPj0gMCAmJiB0IDw9IDEpOworCisgICAgaWYgKCF0KQorICAgICAgICBy
ZXR1cm4gY29udHJvbFBvaW50MDsKKworICAgIGZsb2F0IGFiID0gaW50ZXJwb2xhdGUoY29udHJv
bFBvaW50MCwgY29udHJvbFBvaW50MSwgdCk7CisgICAgZmxvYXQgYmMgPSBpbnRlcnBvbGF0ZShj
b250cm9sUG9pbnQxLCBjb250cm9sUG9pbnQyLCB0KTsKKyAgICBmbG9hdCBjZCA9IGludGVycG9s
YXRlKGNvbnRyb2xQb2ludDIsIGNvbnRyb2xQb2ludDMsIHQpOworICAgIGZsb2F0IGFiYyA9IGlu
dGVycG9sYXRlKGFiLCBiYywgdCk7CisgICAgZmxvYXQgYmNkID0gaW50ZXJwb2xhdGUoYmMsIGNk
LCB0KTsKKyAgICByZXR1cm4gaW50ZXJwb2xhdGUoYWJjLCBiY2QsIHQpOworfQorCisvLyBFdmFs
dWF0ZXMgdGhlIHBvaW50IG9uIHRoZSBzb3VyY2UgY3ViaWMgc3BlY2lmaWVkIGJ5IHQsIDAgPD0g
dCA8PSAxLjAuCitGbG9hdFBvaW50IGV2YWx1YXRlQ3ViaWNBdChjb25zdCBGbG9hdFBvaW50IGN1
YmljWzRdLCBmbG9hdCB0KQoreworICAgIHJldHVybiBGbG9hdFBvaW50KGV2YWx1YXRlQ3ViaWMo
Y3ViaWNbMF0ueCgpLCBjdWJpY1sxXS54KCksIGN1YmljWzJdLngoKSwgY3ViaWNbM10ueCgpLCB0
KSwKKyAgICAgICAgICAgICAgICAgICAgICBldmFsdWF0ZUN1YmljKGN1YmljWzBdLnkoKSwgY3Vi
aWNbMV0ueSgpLCBjdWJpY1syXS55KCksIGN1YmljWzNdLnkoKSwgdCkpOworfQorCitib29sIHhS
YXlDcm9zc2VzTW9ub3RvbmljQ3ViaWMoY29uc3QgWFJheSYgeFJheSwgY29uc3QgRmxvYXRQb2lu
dCBjdWJpY1s0XSwgYm9vbCYgYW1iaWd1b3VzKQoreworICAgIGFtYmlndW91cyA9IGZhbHNlOwor
CisgICAgLy8gRmluZCB0aGUgbWluaW11bSBhbmQgbWF4aW11bSB5IG9mIHRoZSBleHRyZW1hLCB3
aGljaCBhcmUgdGhlCisgICAgLy8gZmlyc3QgYW5kIGxhc3QgcG9pbnRzIHNpbmNlIHRoaXMgY3Vi
aWMgaXMgbW9ub3RvbmljCisgICAgZmxvYXQgbWluWSA9IHN0ZDo6bWluKGN1YmljWzBdLnkoKSwg
Y3ViaWNbM10ueSgpKTsKKyAgICBmbG9hdCBtYXhZID0gc3RkOjptYXgoY3ViaWNbMF0ueSgpLCBj
dWJpY1szXS55KCkpOworCisgICAgaWYgKHhSYXkueSgpID09IGN1YmljWzBdLnkoKQorICAgICAg
ICB8fCB4UmF5LnkoKSA8IG1pblkKKyAgICAgICAgfHwgeFJheS55KCkgPiBtYXhZKSB7CisgICAg
ICAgIC8vIFRoZSBxdWVyeSBsaW5lIGRlZmluaXRlbHkgZG9lcyBub3QgY3Jvc3MgdGhlIGN1cnZl
CisgICAgICAgIGFtYmlndW91cyA9ICh4UmF5LnkoKSA9PSBjdWJpY1swXS55KCkpOworICAgICAg
ICByZXR1cm4gZmFsc2U7CisgICAgfQorCisgICAgY29uc3QgYm9vbCBwb2ludEF0RXh0cmVtdW0g
PSAoeFJheS55KCkgPT0gY3ViaWNbM10ueSgpKTsKKworICAgIGZsb2F0IG1pblggPSBzdGQ6Om1p
bihzdGQ6Om1pbihzdGQ6Om1pbihjdWJpY1swXS54KCksIGN1YmljWzFdLngoKSksCisgICAgICAg
ICAgICAgICAgICAgICAgICAgICAgICAgICAgIGN1YmljWzJdLngoKSksCisgICAgICAgICAgICAg
ICAgICAgICAgICAgIGN1YmljWzNdLngoKSk7CisgICAgaWYgKHhSYXkueCgpIDwgbWluWCkgewor
ICAgICAgICAvLyBUaGUgcXVlcnkgbGluZSBkZWZpbml0ZWx5IGNyb3NzZXMgdGhlIGN1cnZlCisg
ICAgICAgIGFtYmlndW91cyA9IHBvaW50QXRFeHRyZW11bTsKKyAgICAgICAgcmV0dXJuIHRydWU7
CisgICAgfQorCisgICAgZmxvYXQgbWF4WCA9IHN0ZDo6bWF4KHN0ZDo6bWF4KHN0ZDo6bWF4KGN1
YmljWzBdLngoKSwgY3ViaWNbMV0ueCgpKSwKKyAgICAgICAgICAgICAgICAgICAgICAgICAgICAg
ICAgICAgY3ViaWNbMl0ueCgpKSwKKyAgICAgICAgICAgICAgICAgICAgICAgICAgY3ViaWNbM10u
eCgpKTsKKyAgICBpZiAoeFJheS54KCkgPiBtYXhYKQorICAgICAgICAvLyBUaGUgcXVlcnkgbGlu
ZSBkZWZpbml0ZWx5IGRvZXMgbm90IGNyb3NzIHRoZSBjdXJ2ZQorICAgICAgICByZXR1cm4gZmFs
c2U7CisKKyAgICAvLyBEbyBhIGJpbmFyeSBzZWFyY2ggdG8gZmluZCB0aGUgcGFyYW1ldGVyIHZh
bHVlIHdoaWNoIG1ha2VzIHkgYXMKKyAgICAvLyBjbG9zZSBhcyBwb3NzaWJsZSB0byB0aGUgcXVl
cnkgcG9pbnQuIFNlZSB3aGV0aGVyIHRoZSBxdWVyeQorICAgIC8vIGxpbmUncyBvcmlnaW4gaXMg
dG8gdGhlIGxlZnQgb2YgdGhlIGFzc29jaWF0ZWQgeCBjb29yZGluYXRlLgorCisgICAgLy8gTWF4
SXRlcmF0aW9ucyBpcyBjaG9zZW4gYXMgdGhlIG51bWJlciBvZiBtYW50aXNzYSBiaXRzIGZvciBh
IGZsb2F0LAorICAgIC8vIHNpbmNlIHRoZXJlJ3Mgbm8gd2F5IHdlIGFyZSBnb2luZyB0byBnZXQg
bW9yZSBwcmVjaXNpb24gYnkKKyAgICAvLyBpdGVyYXRpbmcgbW9yZSB0aW1lcyB0aGFuIHRoYXQu
CisgICAgY29uc3QgaW50IE1heEl0ZXJhdGlvbnMgPSAyMzsKKyAgICBGbG9hdFBvaW50IGV2YWx1
YXRlZFBvaW50OworICAgIGludCBpdGVyID0gMDsKKyAgICBmbG9hdCB1cHBlclQ7CisgICAgZmxv
YXQgbG93ZXJUOworICAgIC8vIE5lZWQgdG8gaW52ZXJ0IGRpcmVjdGlvbiBvZiB0IHBhcmFtZXRl
ciBpZiBjdWJpYyBnb2VzIHVwCisgICAgLy8gaW5zdGVhZCBvZiBkb3duCisgICAgaWYgKGN1Ymlj
WzNdLnkoKSA+IGN1YmljWzBdLnkoKSkgeworICAgICAgICB1cHBlclQgPSAxOworICAgICAgICBs
b3dlclQgPSAwOworICAgIH0gZWxzZSB7CisgICAgICAgIHVwcGVyVCA9IDA7CisgICAgICAgIGxv
d2VyVCA9IDE7CisgICAgfQorICAgIGRvIHsKKyAgICAgICAgZmxvYXQgdCA9IDAuNWYgKiAodXBw
ZXJUICsgbG93ZXJUKTsKKyAgICAgICAgZXZhbHVhdGVkUG9pbnQgPSBldmFsdWF0ZUN1YmljQXQo
Y3ViaWMsIHQpOworICAgICAgICBpZiAoeFJheS55KCkgPiBldmFsdWF0ZWRQb2ludC55KCkpCisg
ICAgICAgICAgICBsb3dlclQgPSB0OworICAgICAgICBlbHNlCisgICAgICAgICAgICB1cHBlclQg
PSB0OworICAgIH0gd2hpbGUgKCsraXRlciA8IE1heEl0ZXJhdGlvbnMgJiYgIW5lYXJseVplcm8o
ZXZhbHVhdGVkUG9pbnQueSgpIC0geFJheS55KCkpKTsKKworICAgIC8vIEZJWE1FOiBvbmNlIHdl
IGhhdmUgbW9yZSByZWdyZXNzaW9uIHRlc3RzIGZvciB0aGlzIGNvZGUsCisgICAgLy8gZGV0ZXJt
aW5lIHdoZXRoZXIgdGhpcyBzaG91bGQgYmUgdXNpbmcgYSBmdXp6eSB0ZXN0LgorICAgIGlmICh4
UmF5LngoKSA8PSBldmFsdWF0ZWRQb2ludC54KCkpIHsKKyAgICAgICAgYW1iaWd1b3VzID0gcG9p
bnRBdEV4dHJlbXVtOworICAgICAgICByZXR1cm4gdHJ1ZTsKKyAgICB9CisgICAgcmV0dXJuIGZh
bHNlOworfQorCisvLyBEaXZpZGVzIHRoZSBudW1lcmF0b3IgYnkgdGhlIGRlbm9taW5hdG9yIHNh
ZmVseSBmb3IgdGhlIGNhc2Ugd2hlcmUKKy8vIHRoZSByZXN1bHQgbXVzdCBsaWUgaW4gdGhlIHJh
bmdlICgwLi4xKS4gUmVzdWx0IGluZGljYXRlcyB3aGV0aGVyCisvLyB0aGUgcmVzdWx0IGlzIHZh
bGlkLgorYm9vbCBzYWZlVW5pdERpdmlkZShmbG9hdCBudW1lcmF0b3IsIGZsb2F0IGRlbm9taW5h
dG9yLCBmbG9hdCYgcmF0aW8pCit7CisgICAgaWYgKG51bWVyYXRvciA8IDApIHsKKyAgICAgICAg
Ly8gTWFrZSB0aGUgIm51bWVyYXRvciA+PSBkZW5vbWluYXRvciIgY2hlY2sgYmVsb3cgd29yay4K
KyAgICAgICAgbnVtZXJhdG9yID0gLW51bWVyYXRvcjsKKyAgICAgICAgZGVub21pbmF0b3IgPSAt
ZGVub21pbmF0b3I7CisgICAgfQorICAgIGlmICghbnVtZXJhdG9yIHx8ICFkZW5vbWluYXRvciB8
fCBudW1lcmF0b3IgPj0gZGVub21pbmF0b3IpCisgICAgICAgIHJldHVybiBmYWxzZTsKKyAgICBm
bG9hdCByID0gbnVtZXJhdG9yIC8gZGVub21pbmF0b3I7CisgICAgaWYgKGlzbmFuKHIpKQorICAg
ICAgICByZXR1cm4gZmFsc2U7CisgICAgQVNTRVJUKHIgPj0gMCAmJiByIDwgMSk7CisgICAgaWYg
KCFyKSAvLyBjYXRjaCB1bmRlcmZsb3cgaWYgbnVtZXJhdG9yIDw8PDwgZGVub21pbmF0b3IKKyAg
ICAgICAgcmV0dXJuIGZhbHNlOworICAgIHJhdGlvID0gcjsKKyAgICByZXR1cm4gdHJ1ZTsKK30K
KworLy8gRnJvbSBOdW1lcmljYWwgUmVjaXBlcyBpbiBDLgorLy8KKy8vICAgcSA9IC0xLzIgKGIg
KyBzaWduKGIpIHNxcnRbYipiIC0gNCphKmNdKQorLy8gICB4MSA9IHEgLyBhCisvLyAgIHgyID0g
YyAvIHEKKy8vCisvLyBSZXR1cm5zIHRoZSBudW1iZXIgb2YgcmVhbCByb290cyBvZiB0aGUgZXF1
YXRpb24gWzAuLjJdLiBSb290cyBhcmUKKy8vIHJldHVybmVkIGluIHNvcnRlZCBvcmRlciwgc21h
bGxlciByb290IGZpcnN0LgoraW50IGZpbmRVbml0UXVhZFJvb3RzKGZsb2F0IGEsIGZsb2F0IGIs
IGZsb2F0IGMsIGZsb2F0IHJvb3RzWzJdKQoreworICAgIGlmICghYSkKKyAgICAgICAgcmV0dXJu
IHNhZmVVbml0RGl2aWRlKC1jLCBiLCByb290c1swXSkgPyAxIDogMDsKKworICAgIGZsb2F0IGRp
c2NyaW1pbmFudCA9IGIqYiAtIDQqYSpjOworICAgIGlmIChkaXNjcmltaW5hbnQgPCAwIHx8IGlz
bmFuKGRpc2NyaW1pbmFudCkpIC8vIGNvbXBsZXggcm9vdHMKKyAgICAgICAgcmV0dXJuIDA7Cisg
ICAgZGlzY3JpbWluYW50ID0gc3FydGYoZGlzY3JpbWluYW50KTsKKworICAgIGZsb2F0IHEgPSAo
YiA8IDApID8gLShiIC0gZGlzY3JpbWluYW50KSAvIDIgOiAtKGIgKyBkaXNjcmltaW5hbnQpIC8g
MjsKKyAgICBmbG9hdCogciA9IHJvb3RzOworICAgIGlmIChzYWZlVW5pdERpdmlkZShxLCBhLCAq
cikpCisgICAgICAgICsrcjsKKyAgICBpZiAoc2FmZVVuaXREaXZpZGUoYywgcSwgKnIpKQorICAg
ICAgICArK3I7CisgICAgaWYgKHIgLSByb290cyA9PSAyKSB7CisgICAgICAgIC8vIFNlZW1pbmds
eSBoYXZlIHR3byByb290cy4gQ2hlY2sgZm9yIGVxdWFsaXR5IGFuZCBzb3J0LgorICAgICAgICBp
ZiAocm9vdHNbMF0gPT0gcm9vdHNbMV0pCisgICAgICAgICAgICByZXR1cm4gMTsKKyAgICAgICAg
aWYgKHJvb3RzWzBdID4gcm9vdHNbMV0pCisgICAgICAgICAgICBzdGQ6OnN3YXAocm9vdHNbMF0s
IHJvb3RzWzFdKTsKKyAgICB9CisgICAgcmV0dXJuIHIgLSByb290czsKK30KKworLy8gQ3ViaWMn
KHQpID0gcHReMiArIHF0ICsgciwgd2hlcmUKKy8vICAgcCA9IDMoLWEgKyAzKGIgLSBjKSArIGQp
CisvLyAgIHEgPSA2KGEgLSAyYiArIGMpCisvLyAgIHIgPSAzKGIgLSBhKQorLy8gU29sdmUgZm9y
IHQsIGtlZXBpbmcgb25seSB0aG9zZSB0aGF0IGZpdCBiZXR3ZWVuIDAgPCB0IDwgMS4KK2ludCBm
aW5kQ3ViaWNFeHRyZW1hKGZsb2F0IGEsIGZsb2F0IGIsIGZsb2F0IGMsIGZsb2F0IGQsIGZsb2F0
IHRWYWx1ZXNbMl0pCit7CisgICAgLy8gRGl2aWRlIHAsIHEsIGFuZCByIGJ5IDMgdG8gc2ltcGxp
ZnkgdGhlIGVxdWF0aW9ucy4KKyAgICBmbG9hdCBwID0gZCAtIGEgKyAzKihiIC0gYyk7CisgICAg
ZmxvYXQgcSA9IDIqKGEgLSBiIC0gYiArIGMpOworICAgIGZsb2F0IHIgPSBiIC0gYTsKKworICAg
IHJldHVybiBmaW5kVW5pdFF1YWRSb290cyhwLCBxLCByLCB0VmFsdWVzKTsKK30KKwordm9pZCBp
bnRlcnBvbGF0ZUN1YmljQ29vcmRzKGZsb2F0IGNvbnRyb2xQb2ludDAsIGZsb2F0IGNvbnRyb2xQ
b2ludDEsIGZsb2F0IGNvbnRyb2xQb2ludDIsIGZsb2F0IGNvbnRyb2xQb2ludDMsIGZsb2F0KiBk
c3QsIGZsb2F0IHQpCit7CisgICAgZmxvYXQgYWIgPSBpbnRlcnBvbGF0ZShjb250cm9sUG9pbnQw
LCBjb250cm9sUG9pbnQxLCB0KTsKKyAgICBmbG9hdCBiYyA9IGludGVycG9sYXRlKGNvbnRyb2xQ
b2ludDEsIGNvbnRyb2xQb2ludDIsIHQpOworICAgIGZsb2F0IGNkID0gaW50ZXJwb2xhdGUoY29u
dHJvbFBvaW50MiwgY29udHJvbFBvaW50MywgdCk7CisgICAgZmxvYXQgYWJjID0gaW50ZXJwb2xh
dGUoYWIsIGJjLCB0KTsKKyAgICBmbG9hdCBiY2QgPSBpbnRlcnBvbGF0ZShiYywgY2QsIHQpOwor
ICAgIGZsb2F0IGFiY2QgPSBpbnRlcnBvbGF0ZShhYmMsIGJjZCwgdCk7CisKKyAgICBkc3RbMF0g
PSBjb250cm9sUG9pbnQwOworICAgIGRzdFsyXSA9IGFiOworICAgIGRzdFs0XSA9IGFiYzsKKyAg
ICBkc3RbNl0gPSBhYmNkOworICAgIGRzdFs4XSA9IGJjZDsKKyAgICBkc3RbMTBdID0gY2Q7Cisg
ICAgZHN0WzEyXSA9IGNvbnRyb2xQb2ludDM7Cit9CisKKyNpZm5kZWYgTkRFQlVHCitib29sIGlz
VW5pdEludGVydmFsKGZsb2F0IHgpCit7CisgICAgcmV0dXJuIHggPiAwICYmIHggPCAxOworfQor
I2VuZGlmCisKK3ZvaWQgY2hvcEN1YmljQXRUVmFsdWVzKGNvbnN0IEZsb2F0UG9pbnQgc3JjWzRd
LCBGbG9hdFBvaW50IGRzdFtdLCBjb25zdCBmbG9hdCB0VmFsdWVzW10sIGludCByb290cykKK3sK
KyNpZm5kZWYgTkRFQlVHCisgICAgZm9yIChpbnQgaSA9IDA7IGkgPCByb290cyAtIDE7ICsraSkg
eworICAgICAgICBBU1NFUlQoaXNVbml0SW50ZXJ2YWwodFZhbHVlc1tpXSkpOworICAgICAgICBB
U1NFUlQoaXNVbml0SW50ZXJ2YWwodFZhbHVlc1tpKzFdKSk7CisgICAgICAgIEFTU0VSVCh0VmFs
dWVzW2ldIDwgdFZhbHVlc1tpKzFdKTsKKyAgICB9CisjZW5kaWYKKworICAgIGlmICghcm9vdHMp
IHsKKyAgICAgICAgLy8gbm90aGluZyB0byBjaG9wCisgICAgICAgIGZvciAoaW50IGogPSAwOyBq
IDwgNDsgKytqKQorICAgICAgICAgICAgZHN0W2pdID0gc3JjW2pdOworICAgICAgICByZXR1cm47
CisgICAgfQorCisgICAgZmxvYXQgdCA9IHRWYWx1ZXNbMF07CisgICAgRmxvYXRQb2ludCB0bXBb
NF07CisgICAgZm9yIChpbnQgaiA9IDA7IGogPCA0OyArK2opCisgICAgICAgIHRtcFtqXSA9IHNy
Y1tqXTsKKworICAgIGZvciAoaW50IGkgPSAwOyBpIDwgcm9vdHM7ICsraSkgeworICAgICAgICBj
aG9wQ3ViaWNBdCh0bXAsIGRzdCwgdCk7CisgICAgICAgIGlmIChpID09IHJvb3RzIC0gMSkKKyAg
ICAgICAgICAgIGJyZWFrOworCisgICAgICAgIGRzdCArPSAzOworICAgICAgICAvLyBNYWtlIHRt
cCBjb250YWluIHRoZSByZW1haW5pbmcgY3ViaWMgKGFmdGVyIHRoZSBmaXJzdCBjaG9wKS4KKyAg
ICAgICAgZm9yIChpbnQgaiA9IDA7IGogPCA0OyArK2opCisgICAgICAgICAgICB0bXBbal0gPSBk
c3Rbal07CisKKyAgICAgICAgLy8gV2F0Y2ggb3V0IGZvciB0aGUgY2FzZSB0aGF0IHRoZSByZW5v
cm1hbGl6ZWQgdCBpc24ndCBpbiByYW5nZS4KKyAgICAgICAgaWYgKCFzYWZlVW5pdERpdmlkZSh0
VmFsdWVzW2krMV0gLSB0VmFsdWVzW2ldLCAxLjBmIC0gdFZhbHVlc1tpXSwgdCkpIHsKKyAgICAg
ICAgICAgIC8vIElmIGl0IGlzbid0LCBqdXN0IGNyZWF0ZSBhIGRlZ2VuZXJhdGUgY3ViaWMuCisg
ICAgICAgICAgICBkc3RbNF0gPSBkc3RbNV0gPSBkc3RbNl0gPSB0bXBbM107CisgICAgICAgICAg
ICBicmVhazsKKyAgICAgICAgfQorICAgIH0KK30KKwordm9pZCBmbGF0dGVuRG91YmxlQ3ViaWNZ
RXh0cmVtYShGbG9hdFBvaW50IGNvb3Jkc1s3XSkKK3sKKyAgICBjb29yZHNbMl0uc2V0WShjb29y
ZHNbM10ueSgpKTsKKyAgICBjb29yZHNbNF0uc2V0WShjb29yZHNbM10ueSgpKTsKK30KKworaW50
IGNob3BDdWJpY0F0WUV4dHJlbWEoY29uc3QgRmxvYXRQb2ludCBzcmNbNF0sIEZsb2F0UG9pbnQg
ZHN0WzEwXSkKK3sKKyAgICBmbG9hdCB0VmFsdWVzWzJdOworICAgIGludCByb290cyA9IGZpbmRD
dWJpY0V4dHJlbWEoc3JjWzBdLnkoKSwgc3JjWzFdLnkoKSwgc3JjWzJdLnkoKSwgc3JjWzNdLnko
KSwgdFZhbHVlcyk7CisKKyAgICBjaG9wQ3ViaWNBdFRWYWx1ZXMoc3JjLCBkc3QsIHRWYWx1ZXMs
IHJvb3RzKTsKKyAgICBpZiAocm9vdHMpIHsKKyAgICAgICAgLy8gd2UgZG8gc29tZSBjbGVhbnVw
IHRvIGVuc3VyZSBvdXIgWSBleHRyZW1hIGFyZSBmbGF0CisgICAgICAgIGZsYXR0ZW5Eb3VibGVD
dWJpY1lFeHRyZW1hKCZkc3RbMF0pOworICAgICAgICBpZiAocm9vdHMgPT0gMikKKyAgICAgICAg
ICAgIGZsYXR0ZW5Eb3VibGVDdWJpY1lFeHRyZW1hKCZkc3RbM10pOworICAgIH0KKyAgICByZXR1
cm4gcm9vdHM7Cit9CisKK30gLy8gYW5vbnltb3VzIG5hbWVzcGFjZQorCisvLyBQdWJsaWMgY3Vi
aWMgb3BlcmF0aW9ucy4KKwordm9pZCBjaG9wQ3ViaWNBdChjb25zdCBGbG9hdFBvaW50IHNyY1s0
XSwgRmxvYXRQb2ludCBkc3RbN10sIGZsb2F0IHQpCit7CisgICAgQVNTRVJUKHQgPj0gMCAmJiB0
IDw9IDEpOworCisgICAgZmxvYXQgb3V0cHV0WzE0XTsKKyAgICBpbnRlcnBvbGF0ZUN1YmljQ29v
cmRzKHNyY1swXS54KCksIHNyY1sxXS54KCksIHNyY1syXS54KCksIHNyY1szXS54KCksICZvdXRw
dXRbMF0sIHQpOworICAgIGludGVycG9sYXRlQ3ViaWNDb29yZHMoc3JjWzBdLnkoKSwgc3JjWzFd
LnkoKSwgc3JjWzJdLnkoKSwgc3JjWzNdLnkoKSwgJm91dHB1dFsxXSwgdCk7CisgICAgZm9yIChp
bnQgaSA9IDA7IGkgPCA3OyBpKyspCisgICAgICAgIGRzdFtpXS5zZXQob3V0cHV0WzIgKiBpXSwg
b3V0cHV0WzIgKiBpICsgMV0pOworfQorCisvLyBQdWJsaWMgWFJheSBxdWVyaWVzLgorCitib29s
IHhSYXlDcm9zc2VzTGluZShjb25zdCBYUmF5JiB4UmF5LCBjb25zdCBGbG9hdFBvaW50IHB0c1sy
XSwgYm9vbCYgYW1iaWd1b3VzKQoreworICAgIGFtYmlndW91cyA9IGZhbHNlOworCisgICAgLy8g
RGV0ZXJtaW5lIHF1aWNrIGRpc2NhcmRzLgorICAgIC8vIENvbnNpZGVyIHF1ZXJ5IGxpbmUgZ29p
bmcgZXhhY3RseSB0aHJvdWdoIHBvaW50IDAgdG8gbm90CisgICAgLy8gaW50ZXJzZWN0LCBmb3Ig
c3ltbWV0cnkgd2l0aCB4UmF5Q3Jvc3Nlc01vbm90b25pY0N1YmljLgorICAgIGlmICh4UmF5Lnko
KSA9PSBwdHNbMF0ueSgpKSB7CisgICAgICAgIGFtYmlndW91cyA9IHRydWU7CisgICAgICAgIHJl
dHVybiBmYWxzZTsKKyAgICB9CisgICAgaWYgKHhSYXkueSgpIDwgcHRzWzBdLnkoKSAmJiB4UmF5
LnkoKSA8IHB0c1sxXS55KCkpCisgICAgICAgIHJldHVybiBmYWxzZTsKKyAgICBpZiAoeFJheS55
KCkgPiBwdHNbMF0ueSgpICYmIHhSYXkueSgpID4gcHRzWzFdLnkoKSkKKyAgICAgICAgcmV0dXJu
IGZhbHNlOworICAgIGlmICh4UmF5LngoKSA+IHB0c1swXS54KCkgJiYgeFJheS54KCkgPiBwdHNb
MV0ueCgpKQorICAgICAgICByZXR1cm4gZmFsc2U7CisgICAgLy8gRGV0ZXJtaW5lIGRlZ2VuZXJh
dGUgY2FzZXMKKyAgICBpZiAobmVhcmx5WmVybyhwdHNbMF0ueSgpIC0gcHRzWzFdLnkoKSkpCisg
ICAgICAgIHJldHVybiBmYWxzZTsKKyAgICBpZiAobmVhcmx5WmVybyhwdHNbMF0ueCgpIC0gcHRz
WzFdLngoKSkpIHsKKyAgICAgICAgLy8gV2UndmUgYWxyZWFkeSBkZXRlcm1pbmVkIHRoZSBxdWVy
eSBwb2ludCBsaWVzIHdpdGhpbiB0aGUKKyAgICAgICAgLy8gdmVydGljYWwgcmFuZ2Ugb2YgdGhl
IGxpbmUgc2VnbWVudC4KKyAgICAgICAgaWYgKHhSYXkueCgpIDw9IHB0c1swXS54KCkpIHsKKyAg
ICAgICAgICAgIGFtYmlndW91cyA9ICh4UmF5LnkoKSA9PSBwdHNbMV0ueSgpKTsKKyAgICAgICAg
ICAgIHJldHVybiB0cnVlOworICAgICAgICB9CisgICAgICAgIHJldHVybiBmYWxzZTsKKyAgICB9
CisgICAgLy8gQW1iaWd1aXR5IGNoZWNrCisgICAgaWYgKHhSYXkueSgpID09IHB0c1sxXS55KCkp
IHsKKyAgICAgICAgaWYgKHhSYXkueCgpIDw9IHB0c1sxXS54KCkpIHsKKyAgICAgICAgICAgIGFt
YmlndW91cyA9IHRydWU7CisgICAgICAgICAgICByZXR1cm4gdHJ1ZTsKKyAgICAgICAgfQorICAg
ICAgICByZXR1cm4gZmFsc2U7CisgICAgfQorICAgIC8vIEZ1bGwgbGluZSBzZWdtZW50IGV2YWx1
YXRpb24KKyAgICBmbG9hdCBkZWx0YVkgPSBwdHNbMV0ueSgpIC0gcHRzWzBdLnkoKTsKKyAgICBm
bG9hdCBkZWx0YVggPSBwdHNbMV0ueCgpIC0gcHRzWzBdLngoKTsKKyAgICBmbG9hdCBzbG9wZSA9
IGRlbHRhWSAvIGRlbHRhWDsKKyAgICBmbG9hdCBiID0gcHRzWzBdLnkoKSAtIHNsb3BlICogcHRz
WzBdLngoKTsKKyAgICAvLyBTb2x2ZSBmb3IgeCBjb29yZGluYXRlIGF0IHkgPSB4UmF5LnkoKQor
ICAgIGZsb2F0IHggPSAoeFJheS55KCkgLSBiKSAvIHNsb3BlOworICAgIHJldHVybiB4UmF5Lngo
KSA8PSB4OworfQorCitpbnQgbnVtWFJheUNyb3NzaW5nc0ZvckN1YmljKGNvbnN0IFhSYXkmIHhS
YXksIGNvbnN0IEZsb2F0UG9pbnQgY3ViaWNbNF0sIGJvb2wmIGFtYmlndW91cykKK3sKKyAgICBp
bnQgbnVtQ3Jvc3NpbmdzID0gMDsKKyAgICBGbG9hdFBvaW50IG1vbm90b25pY0N1Ymljc1sxMF07
CisgICAgaW50IG51bU1vbm90b25pY0N1YmljcyA9IDEgKyBjaG9wQ3ViaWNBdFlFeHRyZW1hKGN1
YmljLCBtb25vdG9uaWNDdWJpY3MpOworICAgIGFtYmlndW91cyA9IGZhbHNlOworICAgIEZsb2F0
UG9pbnQqIG1vbm90b25pY0N1Ymljc1BvaW50ZXIgPSAmbW9ub3RvbmljQ3ViaWNzWzBdOworICAg
IGZvciAoaW50IGkgPSAwOyBpIDwgbnVtTW9ub3RvbmljQ3ViaWNzOyArK2kpIHsKKyAgICAgICAg
aWYgKHhSYXlDcm9zc2VzTW9ub3RvbmljQ3ViaWMoeFJheSwgbW9ub3RvbmljQ3ViaWNzUG9pbnRl
ciwgYW1iaWd1b3VzKSkKKyAgICAgICAgICAgICsrbnVtQ3Jvc3NpbmdzOworICAgICAgICBpZiAo
YW1iaWd1b3VzKQorICAgICAgICAgICAgcmV0dXJuIDA7CisgICAgICAgIG1vbm90b25pY0N1Ymlj
c1BvaW50ZXIgKz0gMzsKKyAgICB9CisgICAgcmV0dXJuIG51bUNyb3NzaW5nczsKK30KKworfSAv
LyBuYW1lc3BhY2UgTG9vcEJsaW5uTWF0aFV0aWxzCit9IC8vIG5hbWVzcGFjZSBXZWJDb3JlCklu
ZGV4OiBXZWJDb3JlL3BsYXRmb3JtL2dyYXBoaWNzL2dwdS9Mb29wQmxpbm5NYXRoVXRpbHMuaAo9
PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09
PT09PT09PT09Ci0tLSBXZWJDb3JlL3BsYXRmb3JtL2dyYXBoaWNzL2dwdS9Mb29wQmxpbm5NYXRo
VXRpbHMuaAkocmV2aXNpb24gMCkKKysrIFdlYkNvcmUvcGxhdGZvcm0vZ3JhcGhpY3MvZ3B1L0xv
b3BCbGlubk1hdGhVdGlscy5oCShyZXZpc2lvbiAwKQpAQCAtMCwwICsxLDEwOCBAQAorLyoKKyAq
IENvcHlyaWdodCAoQykgMjAxMCBHb29nbGUgSW5jLiBBbGwgcmlnaHRzIHJlc2VydmVkLgorICoK
KyAqIFJlZGlzdHJpYnV0aW9uIGFuZCB1c2UgaW4gc291cmNlIGFuZCBiaW5hcnkgZm9ybXMsIHdp
dGggb3Igd2l0aG91dAorICogbW9kaWZpY2F0aW9uLCBhcmUgcGVybWl0dGVkIHByb3ZpZGVkIHRo
YXQgdGhlIGZvbGxvd2luZyBjb25kaXRpb25zCisgKiBhcmUgbWV0OgorICoKKyAqIDEuICBSZWRp
c3RyaWJ1dGlvbnMgb2Ygc291cmNlIGNvZGUgbXVzdCByZXRhaW4gdGhlIGFib3ZlIGNvcHlyaWdo
dAorICogICAgIG5vdGljZSwgdGhpcyBsaXN0IG9mIGNvbmRpdGlvbnMgYW5kIHRoZSBmb2xsb3dp
bmcgZGlzY2xhaW1lci4KKyAqIDIuICBSZWRpc3RyaWJ1dGlvbnMgaW4gYmluYXJ5IGZvcm0gbXVz
dCByZXByb2R1Y2UgdGhlIGFib3ZlIGNvcHlyaWdodAorICogICAgIG5vdGljZSwgdGhpcyBsaXN0
IG9mIGNvbmRpdGlvbnMgYW5kIHRoZSBmb2xsb3dpbmcgZGlzY2xhaW1lciBpbiB0aGUKKyAqICAg
ICBkb2N1bWVudGF0aW9uIGFuZC9vciBvdGhlciBtYXRlcmlhbHMgcHJvdmlkZWQgd2l0aCB0aGUg
ZGlzdHJpYnV0aW9uLgorICoKKyAqIFRISVMgU09GVFdBUkUgSVMgUFJPVklERUQgQlkgQVBQTEUg
QU5EIElUUyBDT05UUklCVVRPUlMgIkFTIElTIiBBTkQgQU5ZCisgKiBFWFBSRVNTIE9SIElNUExJ
RUQgV0FSUkFOVElFUywgSU5DTFVESU5HLCBCVVQgTk9UIExJTUlURUQgVE8sIFRIRSBJTVBMSUVE
CisgKiBXQVJSQU5USUVTIE9GIE1FUkNIQU5UQUJJTElUWSBBTkQgRklUTkVTUyBGT1IgQSBQQVJU
SUNVTEFSIFBVUlBPU0UgQVJFCisgKiBESVNDTEFJTUVELiBJTiBOTyBFVkVOVCBTSEFMTCBBUFBM
RSBPUiBJVFMgQ09OVFJJQlVUT1JTIEJFIExJQUJMRSBGT1IgQU5ZCisgKiBESVJFQ1QsIElORElS
RUNULCBJTkNJREVOVEFMLCBTUEVDSUFMLCBFWEVNUExBUlksIE9SIENPTlNFUVVFTlRJQUwgREFN
QUdFUworICogKElOQ0xVRElORywgQlVUIE5PVCBMSU1JVEVEIFRPLCBQUk9DVVJFTUVOVCBPRiBT
VUJTVElUVVRFIEdPT0RTIE9SIFNFUlZJQ0VTOworICogTE9TUyBPRiBVU0UsIERBVEEsIE9SIFBS
T0ZJVFM7IE9SIEJVU0lORVNTIElOVEVSUlVQVElPTikgSE9XRVZFUiBDQVVTRUQgQU5ECisgKiBP
TiBBTlkgVEhFT1JZIE9GIExJQUJJTElUWSwgV0hFVEhFUiBJTiBDT05UUkFDVCwgU1RSSUNUIExJ
QUJJTElUWSwgT1IgVE9SVAorICogKElOQ0xVRElORyBORUdMSUdFTkNFIE9SIE9USEVSV0lTRSkg
QVJJU0lORyBJTiBBTlkgV0FZIE9VVCBPRiBUSEUgVVNFIE9GCisgKiBUSElTIFNPRlRXQVJFLCBF
VkVOIElGIEFEVklTRUQgT0YgVEhFIFBPU1NJQklMSVRZIE9GIFNVQ0ggREFNQUdFLgorICovCisK
KyNpZm5kZWYgTG9vcEJsaW5uTWF0aFV0aWxzX2gKKyNkZWZpbmUgTG9vcEJsaW5uTWF0aFV0aWxz
X2gKKworI2luY2x1ZGUgIkZsb2F0UG9pbnQuaCIKKyNpbmNsdWRlICJGbG9hdFBvaW50M0QuaCIK
KyNpbmNsdWRlIDxtYXRoLmg+CisKK25hbWVzcGFjZSBXZWJDb3JlIHsKKworLy8gVXNlIGEgbmFt
ZXNwYWNlIGZvciB0aGVzZSBzbyB3ZSBjYW4gZWFzaWx5IGltcG9ydCB0aGVtLgorbmFtZXNwYWNl
IExvb3BCbGlubk1hdGhVdGlscyB7CisKK2Zsb2F0IHJvdW5kVG9aZXJvKGZsb2F0IHZhbCk7Citi
b29sIGFwcHJveEVxdWFsKGNvbnN0IEZsb2F0UG9pbnQmIHYwLCBjb25zdCBGbG9hdFBvaW50JiB2
MSk7Citib29sIGFwcHJveEVxdWFsKGNvbnN0IEZsb2F0UG9pbnQzRCYgdjAsIGNvbnN0IEZsb2F0
UG9pbnQzRCYgdjEpOworYm9vbCBhcHByb3hFcXVhbChmbG9hdCBmMCwgZmxvYXQgZjEpOworCisv
LyBEZXRlcm1pbmVzIHdoZXRoZXIgdGhlIGxpbmUgc2VnbWVudCBiZXR3ZWVuIChwMSwgcTEpIGlu
dGVyc2VjdHMKKy8vIHRoYXQgYmV0d2VlbiAocDIsIHEyKS4KK2Jvb2wgbGluZXNJbnRlcnNlY3Qo
Y29uc3QgRmxvYXRQb2ludCYgcDEsCisgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9p
bnQmIHExLAorICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBwMiwKKyAgICAg
ICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgcTIpOworCisvLyBEZXRlcm1pbmVzIHdo
ZXRoZXIgInBvaW50IiBpcyBpbnNpZGUgdGhlIDJEIHRyaWFuZ2xlIGRlZmluZWQgYnkKKy8vIHZl
cnRpY2VzIGEsIGIsIGFuZCBjLiBUaGlzIHRlc3QgZGVmaW5lcyB0aGF0IHBvaW50cyBleGFjdGx5
IG9uIGFuCisvLyBlZGdlIGFyZSBub3QgY29uc2lkZXJlZCB0byBiZSBpbnNpZGUgdGhlIHRyaWFu
Z2xlLgorYm9vbCBwb2ludEluVHJpYW5nbGUoY29uc3QgRmxvYXRQb2ludCYgcG9pbnQsCisgICAg
ICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBhLAorICAgICAgICAgICAgICAgICAg
ICAgY29uc3QgRmxvYXRQb2ludCYgYiwKKyAgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0
UG9pbnQmIGMpOworCisvLyBEZXRlcm1pbmVzIHdoZXRoZXIgdGhlIHRyaWFuZ2xlcyBkZWZpbmVk
IGJ5IHRoZSBwb2ludHMgKGExLCBiMSwgYzEpCisvLyBhbmQgKGEyLCBiMiwgYzIpIG92ZXJsYXAu
IFRoZSBkZWZpbml0aW9uIG9mIHRoaXMgZnVuY3Rpb24gaXMgdGhhdAorLy8gaWYgdGhlIHR3byB0
cmlhbmdsZXMgb25seSBzaGFyZSBhbiBhZGphY2VudCBlZGdlIG9yIHZlcnRleCwgdGhleQorLy8g
YXJlIG5vdCBjb25zaWRlcmVkIHRvIG92ZXJsYXAuCitib29sIHRyaWFuZ2xlc092ZXJsYXAoY29u
c3QgRmxvYXRQb2ludCYgYTEsCisgICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2lu
dCYgYjEsCisgICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgYzEsCisgICAg
ICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgYTIsCisgICAgICAgICAgICAgICAg
ICAgICAgY29uc3QgRmxvYXRQb2ludCYgYjIsCisgICAgICAgICAgICAgICAgICAgICAgY29uc3Qg
RmxvYXRQb2ludCYgYzIpOworCisvLyBHaXZlbiBhIHNyYyBjdWJpYyBiZXppZXIsIGNob3BzIGl0
IGF0IHRoZSBzcGVjaWZpZWQgdCB2YWx1ZSwKKy8vIHdoZXJlIDAgPCB0IDwgMSwgYW5kIHJldHVy
bnMgdGhlIHR3byBuZXcgY3ViaWNzIGluIGRzdFswLi4zXQorLy8gYW5kIGRzdFszLi42XS4KK3Zv
aWQgY2hvcEN1YmljQXQoY29uc3QgRmxvYXRQb2ludCBzcmNbNF0sIEZsb2F0UG9pbnQgZHN0Wzdd
LCBmbG9hdCB0KTsKKworLy8gIlgtUmF5IiBxdWVyaWVzLiBBbiBYUmF5IGlzIGEgaGFsZi1saW5l
IG9yaWdpbmF0aW5nIGF0IHRoZSBnaXZlbgorLy8gcG9pbnQgYW5kIGV4dGVuZGluZyB0byB4PStp
bmZpbml0eS4KK3R5cGVkZWYgRmxvYXRQb2ludCBYUmF5OworCisvLyBHaXZlbiBhbiBhcmJpdHJh
cnkgY3ViaWMgYmV6aWVyLCByZXR1cm4gdGhlIG51bWJlciBvZiB0aW1lcyBhbiBYUmF5CisvLyBj
cm9zc2VzIHRoZSBjdWJpYy4gVmFsaWQgcmV0dXJuIHZhbHVlcyBhcmUgWzAuLjNdLgorLy8KKy8v
IEJ5IGRlZmluaXRpb24gdGhlIGN1YmljIGlzIG9wZW4gYXQgdGhlIHN0YXJ0aW5nIHBvaW50OyBp
biBvdGhlcgorLy8gd29yZHMsIGlmIHB0LmZZIGlzIGVxdWl2YWxlbnQgdG8gY3ViaWNbMF0uZlks
IGFuZCBwdC5mWCBpcyB0byB0aGUKKy8vIGxlZnQgb2YgdGhlIGN1cnZlLCB0aGUgbGluZSBpcyBu
b3QgY29uc2lkZXJlZCB0byBjcm9zcyB0aGUgY3VydmUsCisvLyBidXQgaWYgaXQgaXMgZXF1YWwg
dG8gY3ViaWNbM10uZlkgdGhlbiBpdCBpcyBjb25zaWRlcmVkIHRvCisvLyBjcm9zcy4KKy8vCisv
LyBPdXRnb2luZyAiYW1iaWd1b3VzIiBhcmd1bWVudCBpbmRpY2F0ZXMgd2hldGhlciB0aGUgYW5z
d2VyIGlzIGFtYmlndW91cworLy8gYmVjYXVzZSB0aGUgcXVlcnkgb2NjdXJyZWQgZXhhY3RseSBh
dCBvbmUgb2YgdGhlIGVuZHBvaW50cycgeQorLy8gY29vcmRpbmF0ZXMgb3IgYXQgYSB0YW5nZW50
IHBvaW50LCBpbmRpY2F0aW5nIHRoYXQgYW5vdGhlciBxdWVyeSB5CisvLyBjb29yZGluYXRlIGlz
IHByZWZlcnJlZCBmb3Igcm9idXN0bmVzcy4KK2ludCBudW1YUmF5Q3Jvc3NpbmdzRm9yQ3ViaWMo
Y29uc3QgWFJheSYgeFJheSwKKyAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxv
YXRQb2ludCBjdWJpY1s0XSwKKyAgICAgICAgICAgICAgICAgICAgICAgICAgICAgYm9vbCYgYW1i
aWd1b3VzKTsKKworLy8gR2l2ZW4gYSBsaW5lIHNlZ21lbnQgZnJvbSBsaW5lRW5kcG9pbnRzWzBd
IHRvIGxpbmVFbmRwb2ludHNbMV0sIGFuZCBhbgorLy8gWFJheSwgcmV0dXJucyB0cnVlIGlmIHRo
ZXkgaW50ZXJzZWN0LiBPdXRnb2luZyAiYW1iaWd1b3VzIiBhcmd1bWVudAorLy8gaW5kaWNhdGVz
IHdoZXRoZXIgdGhlIGFuc3dlciBpcyBhbWJpZ3VvdXMgYmVjYXVzZSB0aGUgcXVlcnkgb2NjdXJy
ZWQKKy8vIGV4YWN0bHkgYXQgb25lIG9mIHRoZSBlbmRwb2ludHMnIHkgY29vcmRpbmF0ZXMsIGlu
ZGljYXRpbmcgdGhhdCBhbm90aGVyCisvLyBxdWVyeSB5IGNvb3JkaW5hdGUgaXMgcHJlZmVycmVk
IGZvciByb2J1c3RuZXNzLgorYm9vbCB4UmF5Q3Jvc3Nlc0xpbmUoY29uc3QgWFJheSYgeFJheSwK
KyAgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQgbGluZUVuZHBvaW50c1syXSwK
KyAgICAgICAgICAgICAgICAgICAgIGJvb2wmIGFtYmlndW91cyk7CisKK30gLy8gbmFtZXNwYWNl
IExvb3BCbGlubk1hdGhVdGlscworCit9IC8vIG5hbWVzcGFjZSBXZWJDb3JlCisKKyNlbmRpZiAv
LyBMb29wQmxpbm5NYXRoVXRpbHNfaAo=
</data>
<flag name="review"
          id="56347"
          type_id="1"
          status="-"
          setter="jamesr"
    />
    <flag name="commit-queue"
          id="56348"
          type_id="3"
          status="-"
          setter="kbr"
    />
          </attachment>
          <attachment
              isobsolete="0"
              ispatch="1"
              isprivate="0"
          >
            <attachid>67134</attachid>
            <date>2010-09-09 18:44:36 -0700</date>
            <delta_ts>2010-09-09 18:47:39 -0700</delta_ts>
            <desc>Revised patch</desc>
            <filename>math-utils.patch</filename>
            <type>text/plain</type>
            <size>25683</size>
            <attacher name="Kenneth Russell">kbr</attacher>
            
              <data encoding="base64">SW5kZXg6IFdlYkNvcmUvQ2hhbmdlTG9nCj09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09
PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT0KLS0tIFdlYkNvcmUvQ2hhbmdlTG9n
CShyZXZpc2lvbiA2NzE0MSkKKysrIFdlYkNvcmUvQ2hhbmdlTG9nCSh3b3JraW5nIGNvcHkpCkBA
IC0xLDMgKzEsMjUgQEAKKzIwMTAtMDktMDkgIEtlbm5ldGggUnVzc2VsbCAgPGtickBnb29nbGUu
Y29tPgorCisgICAgICAgIFJldmlld2VkIGJ5IE5PQk9EWSAoT09QUyEpLgorCisgICAgICAgIEFk
ZCBtYXRoIHV0aWxpdGllcyBmb3IgY3ViaWMgY3VydmUgcHJvY2Vzc2luZworICAgICAgICBodHRw
czovL2J1Z3Mud2Via2l0Lm9yZy9zaG93X2J1Zy5jZ2k/aWQ9NDUyNTEKKworICAgICAgICBBZGRp
bmcgbWF0aGVtYXRpYyB1dGlsaXRpZXMgbmVlZGVkIGZvciB0aGUgR1BVIGFjY2VsZXJhdGVkIHBh
dGgKKyAgICAgICAgcmVuZGVyaW5nIGFsZ29yaXRobSBmcm9tIEdQVSBHZW1zIDMuIE5vIHRlc3Rz
IHlldDsgd2lsbCBiZSB0ZXN0ZWQKKyAgICAgICAgaW4gY29uanVuY3Rpb24gd2l0aCBsYXRlciBj
b2RlLgorCisgICAgICAgICogcGxhdGZvcm0vZ3JhcGhpY3MvZ3B1L0xvb3BCbGlubk1hdGhVdGls
cy5jcHA6IEFkZGVkLgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxzOjpyb3Vu
ZFRvWmVybyk6CisgICAgICAgIChXZWJDb3JlOjpMb29wQmxpbm5NYXRoVXRpbHM6OmFwcHJveEVx
dWFsKToKKyAgICAgICAgKFdlYkNvcmU6Okxvb3BCbGlubk1hdGhVdGlsczo6bGluZXNJbnRlcnNl
Y3QpOgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxzOjpwb2ludEluVHJpYW5n
bGUpOgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxzOjp0cmlhbmdsZXNPdmVy
bGFwKToKKyAgICAgICAgKFdlYkNvcmU6Okxvb3BCbGlubk1hdGhVdGlsczo6Y2hvcEN1YmljQXQp
OgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxzOjp4UmF5Q3Jvc3Nlc0xpbmUp
OgorICAgICAgICAoV2ViQ29yZTo6TG9vcEJsaW5uTWF0aFV0aWxzOjpudW1YUmF5Q3Jvc3Npbmdz
Rm9yQ3ViaWMpOgorICAgICAgICAqIHBsYXRmb3JtL2dyYXBoaWNzL2dwdS9Mb29wQmxpbm5NYXRo
VXRpbHMuaDogQWRkZWQuCisKIDIwMTAtMDktMDkgIFNoZXJpZmYgQm90ICA8d2Via2l0LnJldmll
dy5ib3RAZ21haWwuY29tPgogCiAgICAgICAgIFVucmV2aWV3ZWQsIHJvbGxpbmcgb3V0IHI2NzEy
Ni4KSW5kZXg6IFdlYkNvcmUvcGxhdGZvcm0vZ3JhcGhpY3MvZ3B1L0xvb3BCbGlubk1hdGhVdGls
cy5jcHAKPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09
PT09PT09PT09PT09PT09PQotLS0gV2ViQ29yZS9wbGF0Zm9ybS9ncmFwaGljcy9ncHUvTG9vcEJs
aW5uTWF0aFV0aWxzLmNwcAkocmV2aXNpb24gMCkKKysrIFdlYkNvcmUvcGxhdGZvcm0vZ3JhcGhp
Y3MvZ3B1L0xvb3BCbGlubk1hdGhVdGlscy5jcHAJKHJldmlzaW9uIDApCkBAIC0wLDAgKzEsNTY1
IEBACisvKgorICogQ29weXJpZ2h0IChDKSAyMDEwIEdvb2dsZSBJbmMuIEFsbCByaWdodHMgcmVz
ZXJ2ZWQuCisgKgorICogUmVkaXN0cmlidXRpb24gYW5kIHVzZSBpbiBzb3VyY2UgYW5kIGJpbmFy
eSBmb3Jtcywgd2l0aCBvciB3aXRob3V0CisgKiBtb2RpZmljYXRpb24sIGFyZSBwZXJtaXR0ZWQg
cHJvdmlkZWQgdGhhdCB0aGUgZm9sbG93aW5nIGNvbmRpdGlvbnMKKyAqIGFyZSBtZXQ6CisgKgor
ICogMS4gIFJlZGlzdHJpYnV0aW9ucyBvZiBzb3VyY2UgY29kZSBtdXN0IHJldGFpbiB0aGUgYWJv
dmUgY29weXJpZ2h0CisgKiAgICAgbm90aWNlLCB0aGlzIGxpc3Qgb2YgY29uZGl0aW9ucyBhbmQg
dGhlIGZvbGxvd2luZyBkaXNjbGFpbWVyLgorICogMi4gIFJlZGlzdHJpYnV0aW9ucyBpbiBiaW5h
cnkgZm9ybSBtdXN0IHJlcHJvZHVjZSB0aGUgYWJvdmUgY29weXJpZ2h0CisgKiAgICAgbm90aWNl
LCB0aGlzIGxpc3Qgb2YgY29uZGl0aW9ucyBhbmQgdGhlIGZvbGxvd2luZyBkaXNjbGFpbWVyIGlu
IHRoZQorICogICAgIGRvY3VtZW50YXRpb24gYW5kL29yIG90aGVyIG1hdGVyaWFscyBwcm92aWRl
ZCB3aXRoIHRoZSBkaXN0cmlidXRpb24uCisgKgorICogVEhJUyBTT0ZUV0FSRSBJUyBQUk9WSURF
RCBCWSBBUFBMRSBBTkQgSVRTIENPTlRSSUJVVE9SUyAiQVMgSVMiIEFORCBBTlkKKyAqIEVYUFJF
U1MgT1IgSU1QTElFRCBXQVJSQU5USUVTLCBJTkNMVURJTkcsIEJVVCBOT1QgTElNSVRFRCBUTywg
VEhFIElNUExJRUQKKyAqIFdBUlJBTlRJRVMgT0YgTUVSQ0hBTlRBQklMSVRZIEFORCBGSVRORVNT
IEZPUiBBIFBBUlRJQ1VMQVIgUFVSUE9TRSBBUkUKKyAqIERJU0NMQUlNRUQuIElOIE5PIEVWRU5U
IFNIQUxMIEFQUExFIE9SIElUUyBDT05UUklCVVRPUlMgQkUgTElBQkxFIEZPUiBBTlkKKyAqIERJ
UkVDVCwgSU5ESVJFQ1QsIElOQ0lERU5UQUwsIFNQRUNJQUwsIEVYRU1QTEFSWSwgT1IgQ09OU0VR
VUVOVElBTCBEQU1BR0VTCisgKiAoSU5DTFVESU5HLCBCVVQgTk9UIExJTUlURUQgVE8sIFBST0NV
UkVNRU5UIE9GIFNVQlNUSVRVVEUgR09PRFMgT1IgU0VSVklDRVM7CisgKiBMT1NTIE9GIFVTRSwg
REFUQSwgT1IgUFJPRklUUzsgT1IgQlVTSU5FU1MgSU5URVJSVVBUSU9OKSBIT1dFVkVSIENBVVNF
RCBBTkQKKyAqIE9OIEFOWSBUSEVPUlkgT0YgTElBQklMSVRZLCBXSEVUSEVSIElOIENPTlRSQUNU
LCBTVFJJQ1QgTElBQklMSVRZLCBPUiBUT1JUCisgKiAoSU5DTFVESU5HIE5FR0xJR0VOQ0UgT1Ig
T1RIRVJXSVNFKSBBUklTSU5HIElOIEFOWSBXQVkgT1VUIE9GIFRIRSBVU0UgT0YKKyAqIFRISVMg
U09GVFdBUkUsIEVWRU4gSUYgQURWSVNFRCBPRiBUSEUgUE9TU0lCSUxJVFkgT0YgU1VDSCBEQU1B
R0UuCisgKi8KKworI2luY2x1ZGUgImNvbmZpZy5oIgorCisjaW5jbHVkZSAiTG9vcEJsaW5uTWF0
aFV0aWxzLmgiCisKKyNpbmNsdWRlICJGbG9hdFBvaW50LmgiCisjaW5jbHVkZSAiTWF0aEV4dHJh
cy5oIgorI2luY2x1ZGUgPGFsZ29yaXRobT4KKyNpbmNsdWRlIDxzdHJpbmcuaD4gLy8gZm9yIG1l
bWNweQorCituYW1lc3BhY2UgV2ViQ29yZSB7CituYW1lc3BhY2UgTG9vcEJsaW5uTWF0aFV0aWxz
IHsKKworbmFtZXNwYWNlIHsKKworLy8gVXRpbGl0eSBmdW5jdGlvbnMgbG9jYWwgdG8gdGhpcyBm
aWxlLgoraW50IG9yaWVudGF0aW9uKGNvbnN0IEZsb2F0UG9pbnQmIHAxLAorICAgICAgICAgICAg
ICAgIGNvbnN0IEZsb2F0UG9pbnQmIHAyLAorICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9p
bnQmIHAzKQoreworICAgIGZsb2F0IGNyb3NzUHJvZHVjdCA9IChwMi55KCkgLSBwMS55KCkpICog
KHAzLngoKSAtIHAyLngoKSkgLSAocDMueSgpIC0gcDIueSgpKSAqIChwMi54KCkgLSBwMS54KCkp
OworICAgIHJldHVybiAoY3Jvc3NQcm9kdWN0IDwgMC4wZikgPyAtMSA6ICgoY3Jvc3NQcm9kdWN0
ID4gMC4wZikgPyAxIDogMCk7Cit9CisKK2Jvb2wgZWRnZUVkZ2VUZXN0KGNvbnN0IEZsb2F0U2l6
ZSYgdjBEZWx0YSwKKyAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIHYwLAorICAg
ICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgdTAsCisgICAgICAgICAgICAgICAgICBj
b25zdCBGbG9hdFBvaW50JiB1MSkKK3sKKyAgICAvLyBUaGlzIGVkZ2UgdG8gZWRnZSB0ZXN0IGlz
IGJhc2VkIG9uIEZyYW5saW4gQW50b25pbydzIGdlbTogIkZhc3RlcgorICAgIC8vIExpbmUgU2Vn
bWVudCBJbnRlcnNlY3Rpb24iLCBpbiBHcmFwaGljcyBHZW1zIElJSSwgcHAuIDE5OS0yMDIuCisg
ICAgZmxvYXQgYXggPSB2MERlbHRhLndpZHRoKCk7CisgICAgZmxvYXQgYXkgPSB2MERlbHRhLmhl
aWdodCgpOworICAgIGZsb2F0IGJ4ID0gdTAueCgpIC0gdTEueCgpOworICAgIGZsb2F0IGJ5ID0g
dTAueSgpIC0gdTEueSgpOworICAgIGZsb2F0IGN4ID0gdjAueCgpIC0gdTAueCgpOworICAgIGZs
b2F0IGN5ID0gdjAueSgpIC0gdTAueSgpOworICAgIGZsb2F0IGYgPSBheSAqIGJ4IC0gYXggKiBi
eTsKKyAgICBmbG9hdCBkID0gYnkgKiBjeCAtIGJ4ICogY3k7CisgICAgaWYgKChmID4gMCAmJiBk
ID49IDAgJiYgZCA8PSBmKSB8fCAoZiA8IDAgJiYgZCA8PSAwICYmIGQgPj0gZikpIHsKKyAgICAg
ICAgZmxvYXQgZSA9IGF4ICogY3kgLSBheSAqIGN4OworCisgICAgICAgIC8vIFRoaXMgYWRkaXRp
b25hbCB0ZXN0IGF2b2lkcyByZXBvcnRpbmcgY29pbmNpZGVudCBlZGdlcywgd2hpY2gKKyAgICAg
ICAgLy8gaXMgdGhlIGJlaGF2aW9yIHdlIHdhbnQuCisgICAgICAgIGlmIChhcHByb3hFcXVhbChl
LCAwKSB8fCBhcHByb3hFcXVhbChmLCAwKSB8fCBhcHByb3hFcXVhbChlLCBmKSkKKyAgICAgICAg
ICAgIHJldHVybiBmYWxzZTsKKworICAgICAgICBpZiAoZiA+IDApCisgICAgICAgICAgICByZXR1
cm4gZSA+PSAwICYmIGUgPD0gZjsKKworICAgICAgICByZXR1cm4gZSA8PSAwICYmIGUgPj0gZjsK
KyAgICB9CisgICAgcmV0dXJuIGZhbHNlOworfQorCitib29sIGVkZ2VBZ2FpbnN0VHJpYW5nbGVF
ZGdlcyhjb25zdCBGbG9hdFBvaW50JiB2MCwKKyAgICAgICAgICAgICAgICAgICAgICAgICAgICAg
IGNvbnN0IEZsb2F0UG9pbnQmIHYxLAorICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgY29u
c3QgRmxvYXRQb2ludCYgdTAsCisgICAgICAgICAgICAgICAgICAgICAgICAgICAgICBjb25zdCBG
bG9hdFBvaW50JiB1MSwKKyAgICAgICAgICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0
UG9pbnQmIHUyKQoreworICAgIEZsb2F0U2l6ZSBkZWx0YSA9IHYxIC0gdjA7CisgICAgLy8gVGVz
dCBlZGdlIHUwLCB1MSBhZ2FpbnN0IHYwLCB2MS4KKyAgICBpZiAoZWRnZUVkZ2VUZXN0KGRlbHRh
LCB2MCwgdTAsIHUxKSkKKyAgICAgICAgcmV0dXJuIHRydWU7CisgICAgLy8gVGVzdCBlZGdlIHUx
LCB1MiBhZ2FpbnN0IHYwLCB2MS4KKyAgICBpZiAoZWRnZUVkZ2VUZXN0KGRlbHRhLCB2MCwgdTEs
IHUyKSkKKyAgICAgICAgcmV0dXJuIHRydWU7CisgICAgLy8gVGVzdCBlZGdlIHUyLCB1MSBhZ2Fp
bnN0IHYwLCB2MS4KKyAgICBpZiAoZWRnZUVkZ2VUZXN0KGRlbHRhLCB2MCwgdTIsIHUwKSkKKyAg
ICAgICAgcmV0dXJuIHRydWU7CisgICAgcmV0dXJuIGZhbHNlOworfQorCisvLyBBIHJvdW5kb2Zm
IGZhY3RvciBpbiB0aGUgY3ViaWMgY2xhc3NpZmljYXRpb24gYW5kIHRleHR1cmUgY29vcmRpbmF0
ZQorLy8gZ2VuZXJhdGlvbiBhbGdvcml0aG1zLiBJdCBwcmltYXJpbHkgZGV0ZXJtaW5lcyB0aGUg
aGFuZGxpbmcgb2YgY29ybmVyCisvLyBjYXNlcyBkdXJpbmcgdGhlIGNsYXNzaWZpY2F0aW9uIHBy
b2Nlc3MuIEJlIGNhcmVmdWwgd2hlbiBhZGp1c3RpbmcgaXQ7CisvLyBpdCBoYXMgYmVlbiBkZXRl
cm1pbmVkIGVtcGlyaWNhbGx5IHRvIHdvcmsgd2VsbC4gV2hlbiBjaGFuZ2luZyBpdCwgeW91Cisv
LyBzaG91bGQgbG9vayBpbiBwYXJ0aWN1bGFyIGF0IHNoYXBlcyB0aGF0IGNvbnRhaW4gcXVhZHJh
dGljIGN1cnZlcyBhbmQKKy8vIGVuc3VyZSB0aGV5IHN0aWxsIGxvb2sgc21vb3RoLiBPbmNlIHBp
eGVsIHRlc3RzIGFyZSBydW5uaW5nIGFnYWluc3QgdGhpcworLy8gYWxnb3JpdGhtLCB0aGV5IHNo
b3VsZCBwcm92aWRlIHN1ZmZpY2llbnQgY292ZXJhZ2UgdG8gZW5zdXJlIHRoYXQKKy8vIGFkanVz
dGluZyB0aGUgY29uc3RhbnQgd29uJ3QgYnJlYWsgYW55dGhpbmcuCitjb25zdCBmbG9hdCBFcHNp
bG9uID0gNS4wZS00ZjsKKworfSAvLyBhbm9ueW1vdXMgbmFtZXNwYWNlCisKKy8vIEV4cG9ydGVk
IHJvdXRpbmVzCisKK2Zsb2F0IHJvdW5kVG9aZXJvKGZsb2F0IHZhbCkKK3sKKyAgICBpZiAodmFs
IDwgRXBzaWxvbiAmJiB2YWwgPiAtRXBzaWxvbikKKyAgICAgICAgcmV0dXJuIDA7CisgICAgcmV0
dXJuIHZhbDsKK30KKworYm9vbCBhcHByb3hFcXVhbChjb25zdCBGbG9hdFBvaW50JiB2MCwgY29u
c3QgRmxvYXRQb2ludCYgdjEpCit7CisgICAgcmV0dXJuICh2MCAtIHYxKS5kaWFnb25hbExlbmd0
aFNxdWFyZWQoKSA8IEVwc2lsb24gKiBFcHNpbG9uOworfQorCitib29sIGFwcHJveEVxdWFsKGNv
bnN0IEZsb2F0UG9pbnQzRCYgdjAsIGNvbnN0IEZsb2F0UG9pbnQzRCYgdjEpCit7CisgICAgcmV0
dXJuICh2MCAtIHYxKS5sZW5ndGhTcXVhcmVkKCkgPCBFcHNpbG9uICogRXBzaWxvbjsKK30KKwor
Ym9vbCBhcHByb3hFcXVhbChmbG9hdCBmMCwgZmxvYXQgZjEpCit7CisgICAgcmV0dXJuIGZhYnNm
KGYwIC0gZjEpIDwgRXBzaWxvbjsKK30KKworYm9vbCBsaW5lc0ludGVyc2VjdChjb25zdCBGbG9h
dFBvaW50JiBwMSwKKyAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgcTEsCisg
ICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIHAyLAorICAgICAgICAgICAgICAg
ICAgICBjb25zdCBGbG9hdFBvaW50JiBxMikKK3sKKyAgICByZXR1cm4gKG9yaWVudGF0aW9uKHAx
LCBxMSwgcDIpICE9IG9yaWVudGF0aW9uKHAxLCBxMSwgcTIpCisgICAgICAgICAgICAmJiBvcmll
bnRhdGlvbihwMiwgcTIsIHAxKSAhPSBvcmllbnRhdGlvbihwMiwgcTIsIHExKSk7Cit9CisKK2Jv
b2wgcG9pbnRJblRyaWFuZ2xlKGNvbnN0IEZsb2F0UG9pbnQmIHBvaW50LAorICAgICAgICAgICAg
ICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgYSwKKyAgICAgICAgICAgICAgICAgICAgIGNvbnN0
IEZsb2F0UG9pbnQmIGIsCisgICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBj
KQoreworICAgIC8vIEFsZ29yaXRobSBmcm9tIGh0dHA6Ly93d3cuYmxhY2twYXduLmNvbS90ZXh0
cy9wb2ludGlucG9seS9kZWZhdWx0Lmh0bWwKKyAgICBmbG9hdCB4MCA9IGMueCgpIC0gYS54KCk7
CisgICAgZmxvYXQgeTAgPSBjLnkoKSAtIGEueSgpOworICAgIGZsb2F0IHgxID0gYi54KCkgLSBh
LngoKTsKKyAgICBmbG9hdCB5MSA9IGIueSgpIC0gYS55KCk7CisgICAgZmxvYXQgeDIgPSBwb2lu
dC54KCkgLSBhLngoKTsKKyAgICBmbG9hdCB5MiA9IHBvaW50LnkoKSAtIGEueSgpOworCisgICAg
ZmxvYXQgZG90MDAgPSB4MCAqIHgwICsgeTAgKiB5MDsKKyAgICBmbG9hdCBkb3QwMSA9IHgwICog
eDEgKyB5MCAqIHkxOworICAgIGZsb2F0IGRvdDAyID0geDAgKiB4MiArIHkwICogeTI7CisgICAg
ZmxvYXQgZG90MTEgPSB4MSAqIHgxICsgeTEgKiB5MTsKKyAgICBmbG9hdCBkb3QxMiA9IHgxICog
eDIgKyB5MSAqIHkyOworICAgIGZsb2F0IGRlbm9taW5hdG9yID0gZG90MDAgKiBkb3QxMSAtIGRv
dDAxICogZG90MDE7CisgICAgaWYgKCFkZW5vbWluYXRvcikKKyAgICAgICAgLy8gVHJpYW5nbGUg
aXMgemVyby1hcmVhLiBUcmVhdCBxdWVyeSBwb2ludCBhcyBub3QgYmVpbmcgaW5zaWRlLgorICAg
ICAgICByZXR1cm4gZmFsc2U7CisgICAgLy8gQ29tcHV0ZQorICAgIGZsb2F0IGludmVyc2VEZW5v
bWluYXRvciA9IDEuMGYgLyBkZW5vbWluYXRvcjsKKyAgICBmbG9hdCB1ID0gKGRvdDExICogZG90
MDIgLSBkb3QwMSAqIGRvdDEyKSAqIGludmVyc2VEZW5vbWluYXRvcjsKKyAgICBmbG9hdCB2ID0g
KGRvdDAwICogZG90MTIgLSBkb3QwMSAqIGRvdDAyKSAqIGludmVyc2VEZW5vbWluYXRvcjsKKwor
ICAgIHJldHVybiAodSA+IDAuMGYpICYmICh2ID4gMC4wZikgJiYgKHUgKyB2IDwgMS4wZik7Cit9
CisKK2Jvb2wgdHJpYW5nbGVzT3ZlcmxhcChjb25zdCBGbG9hdFBvaW50JiBhMSwKKyAgICAgICAg
ICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBiMSwKKyAgICAgICAgICAgICAgICAgICAg
ICBjb25zdCBGbG9hdFBvaW50JiBjMSwKKyAgICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9h
dFBvaW50JiBhMiwKKyAgICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBiMiwK
KyAgICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50JiBjMikKK3sKKyAgICAvLyBE
ZXJpdmVkIGZyb20gY29wbGFuYXJfdHJpX3RyaSgpIGF0CisgICAgLy8gaHR0cDovL2pndC5ha3Bl
dGVycy5jb20vcGFwZXJzL1NoZW5IZW5nVGFuZzAzL3RyaV90cmkuaHRtbCAsCisgICAgLy8gc2lt
cGxpZmllZCBmb3IgdGhlIDJEIGNhc2UgYW5kIG1vZGlmaWVkIHNvIHRoYXQgb3ZlcmxhcHBpbmcg
ZWRnZXMKKyAgICAvLyBkbyBub3QgcmVwb3J0IG92ZXJsYXBwaW5nIHRyaWFuZ2xlcy4KKworICAg
IC8vIFRlc3QgYWxsIGVkZ2VzIG9mIHRyaWFuZ2xlIDEgYWdhaW5zdCB0aGUgZWRnZXMgb2YgdHJp
YW5nbGUgMi4KKyAgICBpZiAoZWRnZUFnYWluc3RUcmlhbmdsZUVkZ2VzKGExLCBiMSwgYTIsIGIy
LCBjMikKKyAgICAgICAgfHwgZWRnZUFnYWluc3RUcmlhbmdsZUVkZ2VzKGIxLCBjMSwgYTIsIGIy
LCBjMikKKyAgICAgICAgfHwgZWRnZUFnYWluc3RUcmlhbmdsZUVkZ2VzKGMxLCBhMSwgYTIsIGIy
LCBjMikpCisgICAgICAgIHJldHVybiB0cnVlOworICAgIC8vIEZpbmFsbHksIHRlc3QgaWYgdHJp
MSBpcyB0b3RhbGx5IGNvbnRhaW5lZCBpbiB0cmkyIG9yIHZpY2UgdmVyc2EuCisgICAgLy8gVGhl
IHBhcGVyIGFib3ZlIG9ubHkgcGVyZm9ybXMgdGhlIGZpcnN0IHR3byBwb2ludC1pbi10cmlhbmds
ZSB0ZXN0cy4KKyAgICAvLyBCZWNhdXNlIHdlIGRlZmluZSB0aGF0IHRyaWFuZ2xlcyBzaGFyaW5n
IGEgdmVydGV4IG9yIGVkZ2UgZG9uJ3QKKyAgICAvLyBvdmVybGFwLCB3ZSBtdXN0IHBlcmZvcm0g
YWRkaXRpb25hbCB0ZXN0cyB0byBzZWUgd2hldGhlciBvbmUKKyAgICAvLyB0cmlhbmdsZSBpcyBj
b250YWluZWQgaW4gdGhlIG90aGVyLgorICAgIGlmIChwb2ludEluVHJpYW5nbGUoYTEsIGEyLCBi
MiwgYzIpCisgICAgICAgIHx8IHBvaW50SW5UcmlhbmdsZShhMiwgYTEsIGIxLCBjMSkKKyAgICAg
ICAgfHwgcG9pbnRJblRyaWFuZ2xlKGIxLCBhMiwgYjIsIGMyKQorICAgICAgICB8fCBwb2ludElu
VHJpYW5nbGUoYjIsIGExLCBiMSwgYzEpCisgICAgICAgIHx8IHBvaW50SW5UcmlhbmdsZShjMSwg
YTIsIGIyLCBjMikKKyAgICAgICAgfHwgcG9pbnRJblRyaWFuZ2xlKGMyLCBhMSwgYjEsIGMxKSkK
KyAgICAgICAgcmV0dXJuIHRydWU7CisgICAgcmV0dXJuIGZhbHNlOworfQorCituYW1lc3BhY2Ug
eworCisvLyBIZWxwZXIgcm91dGluZXMgZm9yIHB1YmxpYyBYUmF5IHF1ZXJpZXMgYmVsb3cuIEFs
bCBvZiB0aGlzIGNvZGUKKy8vIG9yaWdpbmF0ZWQgaW4gU2tpYTsgc2VlIGluY2x1ZGUvY29yZS8g
YW5kIHNyYy9jb3JlLywgU2tTY2FsYXIuaCBhbmQKKy8vIFNrR2VvbWV0cnkue2NwcCxofS4KKwor
Y29uc3QgZmxvYXQgTmVhcmx5WmVyb0NvbnN0YW50ID0gKDEuMGYgLyAoMSA8PCAxMikpOworCiti
b29sIG5lYXJseVplcm8oZmxvYXQgeCwgZmxvYXQgdG9sZXJhbmNlID0gTmVhcmx5WmVyb0NvbnN0
YW50KQoreworICAgIEFTU0VSVCh0b2xlcmFuY2UgPiAwLjBmKTsKKyAgICByZXR1cm4gOjpmYWJz
Zih4KSA8IHRvbGVyYW5jZTsKK30KKworLy8gTGluZWFybHkgaW50ZXJwb2xhdGUgYmV0d2VlbiBh
IGFuZCBiLCBiYXNlZCBvbiB0LgorLy8gSWYgdCBpcyAwLCByZXR1cm4gYTsgaWYgdCBpcyAxLCBy
ZXR1cm4gYjsgZWxzZSBpbnRlcnBvbGF0ZS4KKy8vIHQgbXVzdCBiZSBbMC4uMV0uCitmbG9hdCBp
bnRlcnBvbGF0ZShmbG9hdCBhLCBmbG9hdCBiLCBmbG9hdCB0KQoreworICAgIEFTU0VSVCh0ID49
IDAgJiYgdCA8PSAxKTsKKyAgICByZXR1cm4gYSArIChiIC0gYSkgKiB0OworfQorCitmbG9hdCBl
dmFsdWF0ZUN1YmljKGZsb2F0IGNvbnRyb2xQb2ludDAsIGZsb2F0IGNvbnRyb2xQb2ludDEsIGZs
b2F0IGNvbnRyb2xQb2ludDIsIGZsb2F0IGNvbnRyb2xQb2ludDMsIGZsb2F0IHQpCit7CisgICAg
QVNTRVJUKHQgPj0gMCAmJiB0IDw9IDEpOworCisgICAgaWYgKCF0KQorICAgICAgICByZXR1cm4g
Y29udHJvbFBvaW50MDsKKworICAgIGZsb2F0IGFiID0gaW50ZXJwb2xhdGUoY29udHJvbFBvaW50
MCwgY29udHJvbFBvaW50MSwgdCk7CisgICAgZmxvYXQgYmMgPSBpbnRlcnBvbGF0ZShjb250cm9s
UG9pbnQxLCBjb250cm9sUG9pbnQyLCB0KTsKKyAgICBmbG9hdCBjZCA9IGludGVycG9sYXRlKGNv
bnRyb2xQb2ludDIsIGNvbnRyb2xQb2ludDMsIHQpOworICAgIGZsb2F0IGFiYyA9IGludGVycG9s
YXRlKGFiLCBiYywgdCk7CisgICAgZmxvYXQgYmNkID0gaW50ZXJwb2xhdGUoYmMsIGNkLCB0KTsK
KyAgICByZXR1cm4gaW50ZXJwb2xhdGUoYWJjLCBiY2QsIHQpOworfQorCisvLyBFdmFsdWF0ZXMg
dGhlIHBvaW50IG9uIHRoZSBzb3VyY2UgY3ViaWMgc3BlY2lmaWVkIGJ5IHQsIDAgPD0gdCA8PSAx
LjAuCitGbG9hdFBvaW50IGV2YWx1YXRlQ3ViaWNBdChjb25zdCBGbG9hdFBvaW50IGN1YmljWzRd
LCBmbG9hdCB0KQoreworICAgIHJldHVybiBGbG9hdFBvaW50KGV2YWx1YXRlQ3ViaWMoY3ViaWNb
MF0ueCgpLCBjdWJpY1sxXS54KCksIGN1YmljWzJdLngoKSwgY3ViaWNbM10ueCgpLCB0KSwKKyAg
ICAgICAgICAgICAgICAgICAgICBldmFsdWF0ZUN1YmljKGN1YmljWzBdLnkoKSwgY3ViaWNbMV0u
eSgpLCBjdWJpY1syXS55KCksIGN1YmljWzNdLnkoKSwgdCkpOworfQorCitib29sIHhSYXlDcm9z
c2VzTW9ub3RvbmljQ3ViaWMoY29uc3QgWFJheSYgeFJheSwgY29uc3QgRmxvYXRQb2ludCBjdWJp
Y1s0XSwgYm9vbCYgYW1iaWd1b3VzKQoreworICAgIGFtYmlndW91cyA9IGZhbHNlOworCisgICAg
Ly8gRmluZCB0aGUgbWluaW11bSBhbmQgbWF4aW11bSB5IG9mIHRoZSBleHRyZW1hLCB3aGljaCBh
cmUgdGhlCisgICAgLy8gZmlyc3QgYW5kIGxhc3QgcG9pbnRzIHNpbmNlIHRoaXMgY3ViaWMgaXMg
bW9ub3RvbmljCisgICAgZmxvYXQgbWluWSA9IHN0ZDo6bWluKGN1YmljWzBdLnkoKSwgY3ViaWNb
M10ueSgpKTsKKyAgICBmbG9hdCBtYXhZID0gc3RkOjptYXgoY3ViaWNbMF0ueSgpLCBjdWJpY1sz
XS55KCkpOworCisgICAgaWYgKHhSYXkueSgpID09IGN1YmljWzBdLnkoKQorICAgICAgICB8fCB4
UmF5LnkoKSA8IG1pblkKKyAgICAgICAgfHwgeFJheS55KCkgPiBtYXhZKSB7CisgICAgICAgIC8v
IFRoZSBxdWVyeSBsaW5lIGRlZmluaXRlbHkgZG9lcyBub3QgY3Jvc3MgdGhlIGN1cnZlCisgICAg
ICAgIGFtYmlndW91cyA9ICh4UmF5LnkoKSA9PSBjdWJpY1swXS55KCkpOworICAgICAgICByZXR1
cm4gZmFsc2U7CisgICAgfQorCisgICAgY29uc3QgYm9vbCBwb2ludEF0RXh0cmVtdW0gPSAoeFJh
eS55KCkgPT0gY3ViaWNbM10ueSgpKTsKKworICAgIGZsb2F0IG1pblggPSBzdGQ6Om1pbihzdGQ6
Om1pbihzdGQ6Om1pbihjdWJpY1swXS54KCksIGN1YmljWzFdLngoKSksCisgICAgICAgICAgICAg
ICAgICAgICAgICAgICAgICAgICAgIGN1YmljWzJdLngoKSksCisgICAgICAgICAgICAgICAgICAg
ICAgICAgIGN1YmljWzNdLngoKSk7CisgICAgaWYgKHhSYXkueCgpIDwgbWluWCkgeworICAgICAg
ICAvLyBUaGUgcXVlcnkgbGluZSBkZWZpbml0ZWx5IGNyb3NzZXMgdGhlIGN1cnZlCisgICAgICAg
IGFtYmlndW91cyA9IHBvaW50QXRFeHRyZW11bTsKKyAgICAgICAgcmV0dXJuIHRydWU7CisgICAg
fQorCisgICAgZmxvYXQgbWF4WCA9IHN0ZDo6bWF4KHN0ZDo6bWF4KHN0ZDo6bWF4KGN1YmljWzBd
LngoKSwgY3ViaWNbMV0ueCgpKSwKKyAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAgICAg
Y3ViaWNbMl0ueCgpKSwKKyAgICAgICAgICAgICAgICAgICAgICAgICAgY3ViaWNbM10ueCgpKTsK
KyAgICBpZiAoeFJheS54KCkgPiBtYXhYKQorICAgICAgICAvLyBUaGUgcXVlcnkgbGluZSBkZWZp
bml0ZWx5IGRvZXMgbm90IGNyb3NzIHRoZSBjdXJ2ZQorICAgICAgICByZXR1cm4gZmFsc2U7CisK
KyAgICAvLyBEbyBhIGJpbmFyeSBzZWFyY2ggdG8gZmluZCB0aGUgcGFyYW1ldGVyIHZhbHVlIHdo
aWNoIG1ha2VzIHkgYXMKKyAgICAvLyBjbG9zZSBhcyBwb3NzaWJsZSB0byB0aGUgcXVlcnkgcG9p
bnQuIFNlZSB3aGV0aGVyIHRoZSBxdWVyeQorICAgIC8vIGxpbmUncyBvcmlnaW4gaXMgdG8gdGhl
IGxlZnQgb2YgdGhlIGFzc29jaWF0ZWQgeCBjb29yZGluYXRlLgorCisgICAgLy8gTWF4SXRlcmF0
aW9ucyBpcyBjaG9zZW4gYXMgdGhlIG51bWJlciBvZiBtYW50aXNzYSBiaXRzIGZvciBhIGZsb2F0
LAorICAgIC8vIHNpbmNlIHRoZXJlJ3Mgbm8gd2F5IHdlIGFyZSBnb2luZyB0byBnZXQgbW9yZSBw
cmVjaXNpb24gYnkKKyAgICAvLyBpdGVyYXRpbmcgbW9yZSB0aW1lcyB0aGFuIHRoYXQuCisgICAg
Y29uc3QgaW50IE1heEl0ZXJhdGlvbnMgPSAyMzsKKyAgICBGbG9hdFBvaW50IGV2YWx1YXRlZFBv
aW50OworICAgIGludCBpdGVyID0gMDsKKyAgICBmbG9hdCB1cHBlclQ7CisgICAgZmxvYXQgbG93
ZXJUOworICAgIC8vIE5lZWQgdG8gaW52ZXJ0IGRpcmVjdGlvbiBvZiB0IHBhcmFtZXRlciBpZiBj
dWJpYyBnb2VzIHVwCisgICAgLy8gaW5zdGVhZCBvZiBkb3duCisgICAgaWYgKGN1YmljWzNdLnko
KSA+IGN1YmljWzBdLnkoKSkgeworICAgICAgICB1cHBlclQgPSAxOworICAgICAgICBsb3dlclQg
PSAwOworICAgIH0gZWxzZSB7CisgICAgICAgIHVwcGVyVCA9IDA7CisgICAgICAgIGxvd2VyVCA9
IDE7CisgICAgfQorICAgIGRvIHsKKyAgICAgICAgZmxvYXQgdCA9IDAuNWYgKiAodXBwZXJUICsg
bG93ZXJUKTsKKyAgICAgICAgZXZhbHVhdGVkUG9pbnQgPSBldmFsdWF0ZUN1YmljQXQoY3ViaWMs
IHQpOworICAgICAgICBpZiAoeFJheS55KCkgPiBldmFsdWF0ZWRQb2ludC55KCkpCisgICAgICAg
ICAgICBsb3dlclQgPSB0OworICAgICAgICBlbHNlCisgICAgICAgICAgICB1cHBlclQgPSB0Owor
ICAgIH0gd2hpbGUgKCsraXRlciA8IE1heEl0ZXJhdGlvbnMgJiYgIW5lYXJseVplcm8oZXZhbHVh
dGVkUG9pbnQueSgpIC0geFJheS55KCkpKTsKKworICAgIC8vIEZJWE1FOiBvbmNlIHdlIGhhdmUg
bW9yZSByZWdyZXNzaW9uIHRlc3RzIGZvciB0aGlzIGNvZGUsCisgICAgLy8gZGV0ZXJtaW5lIHdo
ZXRoZXIgdGhpcyBzaG91bGQgYmUgdXNpbmcgYSBmdXp6eSB0ZXN0LgorICAgIGlmICh4UmF5Lngo
KSA8PSBldmFsdWF0ZWRQb2ludC54KCkpIHsKKyAgICAgICAgYW1iaWd1b3VzID0gcG9pbnRBdEV4
dHJlbXVtOworICAgICAgICByZXR1cm4gdHJ1ZTsKKyAgICB9CisgICAgcmV0dXJuIGZhbHNlOwor
fQorCisvLyBEaXZpZGVzIHRoZSBudW1lcmF0b3IgYnkgdGhlIGRlbm9taW5hdG9yIHNhZmVseSBm
b3IgdGhlIGNhc2Ugd2hlcmUKKy8vIHRoZSByZXN1bHQgbXVzdCBsaWUgaW4gdGhlIHJhbmdlICgw
Li4xKS4gUmVzdWx0IGluZGljYXRlcyB3aGV0aGVyCisvLyB0aGUgcmVzdWx0IGlzIHZhbGlkLgor
Ym9vbCBzYWZlVW5pdERpdmlkZShmbG9hdCBudW1lcmF0b3IsIGZsb2F0IGRlbm9taW5hdG9yLCBm
bG9hdCYgcmF0aW8pCit7CisgICAgaWYgKG51bWVyYXRvciA8IDApIHsKKyAgICAgICAgLy8gTWFr
ZSB0aGUgIm51bWVyYXRvciA+PSBkZW5vbWluYXRvciIgY2hlY2sgYmVsb3cgd29yay4KKyAgICAg
ICAgbnVtZXJhdG9yID0gLW51bWVyYXRvcjsKKyAgICAgICAgZGVub21pbmF0b3IgPSAtZGVub21p
bmF0b3I7CisgICAgfQorICAgIGlmICghbnVtZXJhdG9yIHx8ICFkZW5vbWluYXRvciB8fCBudW1l
cmF0b3IgPj0gZGVub21pbmF0b3IpCisgICAgICAgIHJldHVybiBmYWxzZTsKKyAgICBmbG9hdCBy
ID0gbnVtZXJhdG9yIC8gZGVub21pbmF0b3I7CisgICAgaWYgKGlzbmFuKHIpKQorICAgICAgICBy
ZXR1cm4gZmFsc2U7CisgICAgQVNTRVJUKHIgPj0gMCAmJiByIDwgMSk7CisgICAgaWYgKCFyKSAv
LyBjYXRjaCB1bmRlcmZsb3cgaWYgbnVtZXJhdG9yIDw8PDwgZGVub21pbmF0b3IKKyAgICAgICAg
cmV0dXJuIGZhbHNlOworICAgIHJhdGlvID0gcjsKKyAgICByZXR1cm4gdHJ1ZTsKK30KKworLy8g
RnJvbSBOdW1lcmljYWwgUmVjaXBlcyBpbiBDLgorLy8KKy8vICAgcSA9IC0xLzIgKGIgKyBzaWdu
KGIpIHNxcnRbYipiIC0gNCphKmNdKQorLy8gICB4MSA9IHEgLyBhCisvLyAgIHgyID0gYyAvIHEK
Ky8vCisvLyBSZXR1cm5zIHRoZSBudW1iZXIgb2YgcmVhbCByb290cyBvZiB0aGUgZXF1YXRpb24g
WzAuLjJdLiBSb290cyBhcmUKKy8vIHJldHVybmVkIGluIHNvcnRlZCBvcmRlciwgc21hbGxlciBy
b290IGZpcnN0LgoraW50IGZpbmRVbml0UXVhZFJvb3RzKGZsb2F0IGEsIGZsb2F0IGIsIGZsb2F0
IGMsIGZsb2F0IHJvb3RzWzJdKQoreworICAgIGlmICghYSkKKyAgICAgICAgcmV0dXJuIHNhZmVV
bml0RGl2aWRlKC1jLCBiLCByb290c1swXSkgPyAxIDogMDsKKworICAgIGZsb2F0IGRpc2NyaW1p
bmFudCA9IGIqYiAtIDQqYSpjOworICAgIGlmIChkaXNjcmltaW5hbnQgPCAwIHx8IGlzbmFuKGRp
c2NyaW1pbmFudCkpIC8vIGNvbXBsZXggcm9vdHMKKyAgICAgICAgcmV0dXJuIDA7CisgICAgZGlz
Y3JpbWluYW50ID0gc3FydGYoZGlzY3JpbWluYW50KTsKKworICAgIGZsb2F0IHEgPSAoYiA8IDAp
ID8gLShiIC0gZGlzY3JpbWluYW50KSAvIDIgOiAtKGIgKyBkaXNjcmltaW5hbnQpIC8gMjsKKyAg
ICBpbnQgbnVtYmVyT2ZSb290cyA9IDA7CisgICAgaWYgKHNhZmVVbml0RGl2aWRlKHEsIGEsIHJv
b3RzW251bWJlck9mUm9vdHNdKSkKKyAgICAgICAgKytudW1iZXJPZlJvb3RzOworICAgIGlmIChz
YWZlVW5pdERpdmlkZShjLCBxLCByb290c1tudW1iZXJPZlJvb3RzXSkpCisgICAgICAgICsrbnVt
YmVyT2ZSb290czsKKyAgICBpZiAobnVtYmVyT2ZSb290cyA9PSAyKSB7CisgICAgICAgIC8vIFNl
ZW1pbmdseSBoYXZlIHR3byByb290cy4gQ2hlY2sgZm9yIGVxdWFsaXR5IGFuZCBzb3J0LgorICAg
ICAgICBpZiAocm9vdHNbMF0gPT0gcm9vdHNbMV0pCisgICAgICAgICAgICByZXR1cm4gMTsKKyAg
ICAgICAgaWYgKHJvb3RzWzBdID4gcm9vdHNbMV0pCisgICAgICAgICAgICBzdGQ6OnN3YXAocm9v
dHNbMF0sIHJvb3RzWzFdKTsKKyAgICB9CisgICAgcmV0dXJuIG51bWJlck9mUm9vdHM7Cit9CisK
Ky8vIEN1YmljJyh0KSA9IHB0XjIgKyBxdCArIHIsIHdoZXJlCisvLyAgIHAgPSAzKC1hICsgMyhi
IC0gYykgKyBkKQorLy8gICBxID0gNihhIC0gMmIgKyBjKQorLy8gICByID0gMyhiIC0gYSkKKy8v
IFNvbHZlIGZvciB0LCBrZWVwaW5nIG9ubHkgdGhvc2UgdGhhdCBmaXQgYmV0d2VlbiAwIDwgdCA8
IDEuCitpbnQgZmluZEN1YmljRXh0cmVtYShmbG9hdCBhLCBmbG9hdCBiLCBmbG9hdCBjLCBmbG9h
dCBkLCBmbG9hdCB0VmFsdWVzWzJdKQoreworICAgIC8vIERpdmlkZSBwLCBxLCBhbmQgciBieSAz
IHRvIHNpbXBsaWZ5IHRoZSBlcXVhdGlvbnMuCisgICAgZmxvYXQgcCA9IGQgLSBhICsgMyooYiAt
IGMpOworICAgIGZsb2F0IHEgPSAyKihhIC0gYiAtIGIgKyBjKTsKKyAgICBmbG9hdCByID0gYiAt
IGE7CisKKyAgICByZXR1cm4gZmluZFVuaXRRdWFkUm9vdHMocCwgcSwgciwgdFZhbHVlcyk7Cit9
CisKK3ZvaWQgaW50ZXJwb2xhdGVDdWJpY0Nvb3JkcyhmbG9hdCBjb250cm9sUG9pbnQwLCBmbG9h
dCBjb250cm9sUG9pbnQxLCBmbG9hdCBjb250cm9sUG9pbnQyLCBmbG9hdCBjb250cm9sUG9pbnQz
LCBmbG9hdCogZHN0LCBmbG9hdCB0KQoreworICAgIGZsb2F0IGFiID0gaW50ZXJwb2xhdGUoY29u
dHJvbFBvaW50MCwgY29udHJvbFBvaW50MSwgdCk7CisgICAgZmxvYXQgYmMgPSBpbnRlcnBvbGF0
ZShjb250cm9sUG9pbnQxLCBjb250cm9sUG9pbnQyLCB0KTsKKyAgICBmbG9hdCBjZCA9IGludGVy
cG9sYXRlKGNvbnRyb2xQb2ludDIsIGNvbnRyb2xQb2ludDMsIHQpOworICAgIGZsb2F0IGFiYyA9
IGludGVycG9sYXRlKGFiLCBiYywgdCk7CisgICAgZmxvYXQgYmNkID0gaW50ZXJwb2xhdGUoYmMs
IGNkLCB0KTsKKyAgICBmbG9hdCBhYmNkID0gaW50ZXJwb2xhdGUoYWJjLCBiY2QsIHQpOworCisg
ICAgZHN0WzBdID0gY29udHJvbFBvaW50MDsKKyAgICBkc3RbMl0gPSBhYjsKKyAgICBkc3RbNF0g
PSBhYmM7CisgICAgZHN0WzZdID0gYWJjZDsKKyAgICBkc3RbOF0gPSBiY2Q7CisgICAgZHN0WzEw
XSA9IGNkOworICAgIGRzdFsxMl0gPSBjb250cm9sUG9pbnQzOworfQorCisjaWZuZGVmIE5ERUJV
RworYm9vbCBpc1VuaXRJbnRlcnZhbChmbG9hdCB4KQoreworICAgIHJldHVybiB4ID4gMCAmJiB4
IDwgMTsKK30KKyNlbmRpZgorCit2b2lkIGNob3BDdWJpY0F0VFZhbHVlcyhjb25zdCBGbG9hdFBv
aW50IHNyY1s0XSwgRmxvYXRQb2ludCBkc3RbXSwgY29uc3QgZmxvYXQgdFZhbHVlc1tdLCBpbnQg
cm9vdHMpCit7CisjaWZuZGVmIE5ERUJVRworICAgIGZvciAoaW50IGkgPSAwOyBpIDwgcm9vdHMg
LSAxOyArK2kpIHsKKyAgICAgICAgQVNTRVJUKGlzVW5pdEludGVydmFsKHRWYWx1ZXNbaV0pKTsK
KyAgICAgICAgQVNTRVJUKGlzVW5pdEludGVydmFsKHRWYWx1ZXNbaSsxXSkpOworICAgICAgICBB
U1NFUlQodFZhbHVlc1tpXSA8IHRWYWx1ZXNbaSsxXSk7CisgICAgfQorI2VuZGlmCisKKyAgICBp
ZiAoIXJvb3RzKSB7CisgICAgICAgIC8vIG5vdGhpbmcgdG8gY2hvcAorICAgICAgICBmb3IgKGlu
dCBqID0gMDsgaiA8IDQ7ICsraikKKyAgICAgICAgICAgIGRzdFtqXSA9IHNyY1tqXTsKKyAgICAg
ICAgcmV0dXJuOworICAgIH0KKworICAgIGZsb2F0IHQgPSB0VmFsdWVzWzBdOworICAgIEZsb2F0
UG9pbnQgdG1wWzRdOworICAgIGZvciAoaW50IGogPSAwOyBqIDwgNDsgKytqKQorICAgICAgICB0
bXBbal0gPSBzcmNbal07CisKKyAgICBmb3IgKGludCBpID0gMDsgaSA8IHJvb3RzOyArK2kpIHsK
KyAgICAgICAgY2hvcEN1YmljQXQodG1wLCBkc3QsIHQpOworICAgICAgICBpZiAoaSA9PSByb290
cyAtIDEpCisgICAgICAgICAgICBicmVhazsKKworICAgICAgICBkc3QgKz0gMzsKKyAgICAgICAg
Ly8gTWFrZSB0bXAgY29udGFpbiB0aGUgcmVtYWluaW5nIGN1YmljIChhZnRlciB0aGUgZmlyc3Qg
Y2hvcCkuCisgICAgICAgIGZvciAoaW50IGogPSAwOyBqIDwgNDsgKytqKQorICAgICAgICAgICAg
dG1wW2pdID0gZHN0W2pdOworCisgICAgICAgIC8vIFdhdGNoIG91dCBmb3IgdGhlIGNhc2UgdGhh
dCB0aGUgcmVub3JtYWxpemVkIHQgaXNuJ3QgaW4gcmFuZ2UuCisgICAgICAgIGlmICghc2FmZVVu
aXREaXZpZGUodFZhbHVlc1tpKzFdIC0gdFZhbHVlc1tpXSwgMS4wZiAtIHRWYWx1ZXNbaV0sIHQp
KSB7CisgICAgICAgICAgICAvLyBJZiBpdCBpc24ndCwganVzdCBjcmVhdGUgYSBkZWdlbmVyYXRl
IGN1YmljLgorICAgICAgICAgICAgZHN0WzRdID0gZHN0WzVdID0gZHN0WzZdID0gdG1wWzNdOwor
ICAgICAgICAgICAgYnJlYWs7CisgICAgICAgIH0KKyAgICB9Cit9CisKK3ZvaWQgZmxhdHRlbkRv
dWJsZUN1YmljWUV4dHJlbWEoRmxvYXRQb2ludCBjb29yZHNbN10pCit7CisgICAgY29vcmRzWzJd
LnNldFkoY29vcmRzWzNdLnkoKSk7CisgICAgY29vcmRzWzRdLnNldFkoY29vcmRzWzNdLnkoKSk7
Cit9CisKK2ludCBjaG9wQ3ViaWNBdFlFeHRyZW1hKGNvbnN0IEZsb2F0UG9pbnQgc3JjWzRdLCBG
bG9hdFBvaW50IGRzdFsxMF0pCit7CisgICAgZmxvYXQgdFZhbHVlc1syXTsKKyAgICBpbnQgcm9v
dHMgPSBmaW5kQ3ViaWNFeHRyZW1hKHNyY1swXS55KCksIHNyY1sxXS55KCksIHNyY1syXS55KCks
IHNyY1szXS55KCksIHRWYWx1ZXMpOworCisgICAgY2hvcEN1YmljQXRUVmFsdWVzKHNyYywgZHN0
LCB0VmFsdWVzLCByb290cyk7CisgICAgaWYgKHJvb3RzKSB7CisgICAgICAgIC8vIHdlIGRvIHNv
bWUgY2xlYW51cCB0byBlbnN1cmUgb3VyIFkgZXh0cmVtYSBhcmUgZmxhdAorICAgICAgICBmbGF0
dGVuRG91YmxlQ3ViaWNZRXh0cmVtYSgmZHN0WzBdKTsKKyAgICAgICAgaWYgKHJvb3RzID09IDIp
CisgICAgICAgICAgICBmbGF0dGVuRG91YmxlQ3ViaWNZRXh0cmVtYSgmZHN0WzNdKTsKKyAgICB9
CisgICAgcmV0dXJuIHJvb3RzOworfQorCit9IC8vIGFub255bW91cyBuYW1lc3BhY2UKKworLy8g
UHVibGljIGN1YmljIG9wZXJhdGlvbnMuCisKK3ZvaWQgY2hvcEN1YmljQXQoY29uc3QgRmxvYXRQ
b2ludCBzcmNbNF0sIEZsb2F0UG9pbnQgZHN0WzddLCBmbG9hdCB0KQoreworICAgIEFTU0VSVCh0
ID49IDAgJiYgdCA8PSAxKTsKKworICAgIGZsb2F0IG91dHB1dFsxNF07CisgICAgaW50ZXJwb2xh
dGVDdWJpY0Nvb3JkcyhzcmNbMF0ueCgpLCBzcmNbMV0ueCgpLCBzcmNbMl0ueCgpLCBzcmNbM10u
eCgpLCAmb3V0cHV0WzBdLCB0KTsKKyAgICBpbnRlcnBvbGF0ZUN1YmljQ29vcmRzKHNyY1swXS55
KCksIHNyY1sxXS55KCksIHNyY1syXS55KCksIHNyY1szXS55KCksICZvdXRwdXRbMV0sIHQpOwor
ICAgIGZvciAoaW50IGkgPSAwOyBpIDwgNzsgaSsrKQorICAgICAgICBkc3RbaV0uc2V0KG91dHB1
dFsyICogaV0sIG91dHB1dFsyICogaSArIDFdKTsKK30KKworLy8gUHVibGljIFhSYXkgcXVlcmll
cy4KKworYm9vbCB4UmF5Q3Jvc3Nlc0xpbmUoY29uc3QgWFJheSYgeFJheSwgY29uc3QgRmxvYXRQ
b2ludCBwdHNbMl0sIGJvb2wmIGFtYmlndW91cykKK3sKKyAgICBhbWJpZ3VvdXMgPSBmYWxzZTsK
KworICAgIC8vIERldGVybWluZSBxdWljayBkaXNjYXJkcy4KKyAgICAvLyBDb25zaWRlciBxdWVy
eSBsaW5lIGdvaW5nIGV4YWN0bHkgdGhyb3VnaCBwb2ludCAwIHRvIG5vdAorICAgIC8vIGludGVy
c2VjdCwgZm9yIHN5bW1ldHJ5IHdpdGggeFJheUNyb3NzZXNNb25vdG9uaWNDdWJpYy4KKyAgICBp
ZiAoeFJheS55KCkgPT0gcHRzWzBdLnkoKSkgeworICAgICAgICBhbWJpZ3VvdXMgPSB0cnVlOwor
ICAgICAgICByZXR1cm4gZmFsc2U7CisgICAgfQorICAgIGlmICh4UmF5LnkoKSA8IHB0c1swXS55
KCkgJiYgeFJheS55KCkgPCBwdHNbMV0ueSgpKQorICAgICAgICByZXR1cm4gZmFsc2U7CisgICAg
aWYgKHhSYXkueSgpID4gcHRzWzBdLnkoKSAmJiB4UmF5LnkoKSA+IHB0c1sxXS55KCkpCisgICAg
ICAgIHJldHVybiBmYWxzZTsKKyAgICBpZiAoeFJheS54KCkgPiBwdHNbMF0ueCgpICYmIHhSYXku
eCgpID4gcHRzWzFdLngoKSkKKyAgICAgICAgcmV0dXJuIGZhbHNlOworICAgIC8vIERldGVybWlu
ZSBkZWdlbmVyYXRlIGNhc2VzCisgICAgaWYgKG5lYXJseVplcm8ocHRzWzBdLnkoKSAtIHB0c1sx
XS55KCkpKQorICAgICAgICByZXR1cm4gZmFsc2U7CisgICAgaWYgKG5lYXJseVplcm8ocHRzWzBd
LngoKSAtIHB0c1sxXS54KCkpKSB7CisgICAgICAgIC8vIFdlJ3ZlIGFscmVhZHkgZGV0ZXJtaW5l
ZCB0aGUgcXVlcnkgcG9pbnQgbGllcyB3aXRoaW4gdGhlCisgICAgICAgIC8vIHZlcnRpY2FsIHJh
bmdlIG9mIHRoZSBsaW5lIHNlZ21lbnQuCisgICAgICAgIGlmICh4UmF5LngoKSA8PSBwdHNbMF0u
eCgpKSB7CisgICAgICAgICAgICBhbWJpZ3VvdXMgPSAoeFJheS55KCkgPT0gcHRzWzFdLnkoKSk7
CisgICAgICAgICAgICByZXR1cm4gdHJ1ZTsKKyAgICAgICAgfQorICAgICAgICByZXR1cm4gZmFs
c2U7CisgICAgfQorICAgIC8vIEFtYmlndWl0eSBjaGVjaworICAgIGlmICh4UmF5LnkoKSA9PSBw
dHNbMV0ueSgpKSB7CisgICAgICAgIGlmICh4UmF5LngoKSA8PSBwdHNbMV0ueCgpKSB7CisgICAg
ICAgICAgICBhbWJpZ3VvdXMgPSB0cnVlOworICAgICAgICAgICAgcmV0dXJuIHRydWU7CisgICAg
ICAgIH0KKyAgICAgICAgcmV0dXJuIGZhbHNlOworICAgIH0KKyAgICAvLyBGdWxsIGxpbmUgc2Vn
bWVudCBldmFsdWF0aW9uCisgICAgZmxvYXQgZGVsdGFZID0gcHRzWzFdLnkoKSAtIHB0c1swXS55
KCk7CisgICAgZmxvYXQgZGVsdGFYID0gcHRzWzFdLngoKSAtIHB0c1swXS54KCk7CisgICAgZmxv
YXQgc2xvcGUgPSBkZWx0YVkgLyBkZWx0YVg7CisgICAgZmxvYXQgYiA9IHB0c1swXS55KCkgLSBz
bG9wZSAqIHB0c1swXS54KCk7CisgICAgLy8gU29sdmUgZm9yIHggY29vcmRpbmF0ZSBhdCB5ID0g
eFJheS55KCkKKyAgICBmbG9hdCB4ID0gKHhSYXkueSgpIC0gYikgLyBzbG9wZTsKKyAgICByZXR1
cm4geFJheS54KCkgPD0geDsKK30KKworaW50IG51bVhSYXlDcm9zc2luZ3NGb3JDdWJpYyhjb25z
dCBYUmF5JiB4UmF5LCBjb25zdCBGbG9hdFBvaW50IGN1YmljWzRdLCBib29sJiBhbWJpZ3VvdXMp
Cit7CisgICAgaW50IG51bUNyb3NzaW5ncyA9IDA7CisgICAgRmxvYXRQb2ludCBtb25vdG9uaWND
dWJpY3NbMTBdOworICAgIGludCBudW1Nb25vdG9uaWNDdWJpY3MgPSAxICsgY2hvcEN1YmljQXRZ
RXh0cmVtYShjdWJpYywgbW9ub3RvbmljQ3ViaWNzKTsKKyAgICBhbWJpZ3VvdXMgPSBmYWxzZTsK
KyAgICBGbG9hdFBvaW50KiBtb25vdG9uaWNDdWJpY3NQb2ludGVyID0gJm1vbm90b25pY0N1Ymlj
c1swXTsKKyAgICBmb3IgKGludCBpID0gMDsgaSA8IG51bU1vbm90b25pY0N1YmljczsgKytpKSB7
CisgICAgICAgIGlmICh4UmF5Q3Jvc3Nlc01vbm90b25pY0N1YmljKHhSYXksIG1vbm90b25pY0N1
Ymljc1BvaW50ZXIsIGFtYmlndW91cykpCisgICAgICAgICAgICArK251bUNyb3NzaW5nczsKKyAg
ICAgICAgaWYgKGFtYmlndW91cykKKyAgICAgICAgICAgIHJldHVybiAwOworICAgICAgICBtb25v
dG9uaWNDdWJpY3NQb2ludGVyICs9IDM7CisgICAgfQorICAgIHJldHVybiBudW1Dcm9zc2luZ3M7
Cit9CisKK30gLy8gbmFtZXNwYWNlIExvb3BCbGlubk1hdGhVdGlscworfSAvLyBuYW1lc3BhY2Ug
V2ViQ29yZQpJbmRleDogV2ViQ29yZS9wbGF0Zm9ybS9ncmFwaGljcy9ncHUvTG9vcEJsaW5uTWF0
aFV0aWxzLmgKPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09
PT09PT09PT09PT09PT09PT09PQotLS0gV2ViQ29yZS9wbGF0Zm9ybS9ncmFwaGljcy9ncHUvTG9v
cEJsaW5uTWF0aFV0aWxzLmgJKHJldmlzaW9uIDApCisrKyBXZWJDb3JlL3BsYXRmb3JtL2dyYXBo
aWNzL2dwdS9Mb29wQmxpbm5NYXRoVXRpbHMuaAkocmV2aXNpb24gMCkKQEAgLTAsMCArMSwxMDgg
QEAKKy8qCisgKiBDb3B5cmlnaHQgKEMpIDIwMTAgR29vZ2xlIEluYy4gQWxsIHJpZ2h0cyByZXNl
cnZlZC4KKyAqCisgKiBSZWRpc3RyaWJ1dGlvbiBhbmQgdXNlIGluIHNvdXJjZSBhbmQgYmluYXJ5
IGZvcm1zLCB3aXRoIG9yIHdpdGhvdXQKKyAqIG1vZGlmaWNhdGlvbiwgYXJlIHBlcm1pdHRlZCBw
cm92aWRlZCB0aGF0IHRoZSBmb2xsb3dpbmcgY29uZGl0aW9ucworICogYXJlIG1ldDoKKyAqCisg
KiAxLiAgUmVkaXN0cmlidXRpb25zIG9mIHNvdXJjZSBjb2RlIG11c3QgcmV0YWluIHRoZSBhYm92
ZSBjb3B5cmlnaHQKKyAqICAgICBub3RpY2UsIHRoaXMgbGlzdCBvZiBjb25kaXRpb25zIGFuZCB0
aGUgZm9sbG93aW5nIGRpc2NsYWltZXIuCisgKiAyLiAgUmVkaXN0cmlidXRpb25zIGluIGJpbmFy
eSBmb3JtIG11c3QgcmVwcm9kdWNlIHRoZSBhYm92ZSBjb3B5cmlnaHQKKyAqICAgICBub3RpY2Us
IHRoaXMgbGlzdCBvZiBjb25kaXRpb25zIGFuZCB0aGUgZm9sbG93aW5nIGRpc2NsYWltZXIgaW4g
dGhlCisgKiAgICAgZG9jdW1lbnRhdGlvbiBhbmQvb3Igb3RoZXIgbWF0ZXJpYWxzIHByb3ZpZGVk
IHdpdGggdGhlIGRpc3RyaWJ1dGlvbi4KKyAqCisgKiBUSElTIFNPRlRXQVJFIElTIFBST1ZJREVE
IEJZIEFQUExFIEFORCBJVFMgQ09OVFJJQlVUT1JTICJBUyBJUyIgQU5EIEFOWQorICogRVhQUkVT
UyBPUiBJTVBMSUVEIFdBUlJBTlRJRVMsIElOQ0xVRElORywgQlVUIE5PVCBMSU1JVEVEIFRPLCBU
SEUgSU1QTElFRAorICogV0FSUkFOVElFUyBPRiBNRVJDSEFOVEFCSUxJVFkgQU5EIEZJVE5FU1Mg
Rk9SIEEgUEFSVElDVUxBUiBQVVJQT1NFIEFSRQorICogRElTQ0xBSU1FRC4gSU4gTk8gRVZFTlQg
U0hBTEwgQVBQTEUgT1IgSVRTIENPTlRSSUJVVE9SUyBCRSBMSUFCTEUgRk9SIEFOWQorICogRElS
RUNULCBJTkRJUkVDVCwgSU5DSURFTlRBTCwgU1BFQ0lBTCwgRVhFTVBMQVJZLCBPUiBDT05TRVFV
RU5USUFMIERBTUFHRVMKKyAqIChJTkNMVURJTkcsIEJVVCBOT1QgTElNSVRFRCBUTywgUFJPQ1VS
RU1FTlQgT0YgU1VCU1RJVFVURSBHT09EUyBPUiBTRVJWSUNFUzsKKyAqIExPU1MgT0YgVVNFLCBE
QVRBLCBPUiBQUk9GSVRTOyBPUiBCVVNJTkVTUyBJTlRFUlJVUFRJT04pIEhPV0VWRVIgQ0FVU0VE
IEFORAorICogT04gQU5ZIFRIRU9SWSBPRiBMSUFCSUxJVFksIFdIRVRIRVIgSU4gQ09OVFJBQ1Qs
IFNUUklDVCBMSUFCSUxJVFksIE9SIFRPUlQKKyAqIChJTkNMVURJTkcgTkVHTElHRU5DRSBPUiBP
VEhFUldJU0UpIEFSSVNJTkcgSU4gQU5ZIFdBWSBPVVQgT0YgVEhFIFVTRSBPRgorICogVEhJUyBT
T0ZUV0FSRSwgRVZFTiBJRiBBRFZJU0VEIE9GIFRIRSBQT1NTSUJJTElUWSBPRiBTVUNIIERBTUFH
RS4KKyAqLworCisjaWZuZGVmIExvb3BCbGlubk1hdGhVdGlsc19oCisjZGVmaW5lIExvb3BCbGlu
bk1hdGhVdGlsc19oCisKKyNpbmNsdWRlICJGbG9hdFBvaW50LmgiCisjaW5jbHVkZSAiRmxvYXRQ
b2ludDNELmgiCisjaW5jbHVkZSA8bWF0aC5oPgorCituYW1lc3BhY2UgV2ViQ29yZSB7CisKKy8v
IFVzZSBhIG5hbWVzcGFjZSBmb3IgdGhlc2Ugc28gd2UgY2FuIGVhc2lseSBpbXBvcnQgdGhlbS4K
K25hbWVzcGFjZSBMb29wQmxpbm5NYXRoVXRpbHMgeworCitmbG9hdCByb3VuZFRvWmVybyhmbG9h
dCB2YWwpOworYm9vbCBhcHByb3hFcXVhbChjb25zdCBGbG9hdFBvaW50JiB2MCwgY29uc3QgRmxv
YXRQb2ludCYgdjEpOworYm9vbCBhcHByb3hFcXVhbChjb25zdCBGbG9hdFBvaW50M0QmIHYwLCBj
b25zdCBGbG9hdFBvaW50M0QmIHYxKTsKK2Jvb2wgYXBwcm94RXF1YWwoZmxvYXQgZjAsIGZsb2F0
IGYxKTsKKworLy8gRGV0ZXJtaW5lcyB3aGV0aGVyIHRoZSBsaW5lIHNlZ21lbnQgYmV0d2VlbiAo
cDEsIHExKSBpbnRlcnNlY3RzCisvLyB0aGF0IGJldHdlZW4gKHAyLCBxMikuCitib29sIGxpbmVz
SW50ZXJzZWN0KGNvbnN0IEZsb2F0UG9pbnQmIHAxLAorICAgICAgICAgICAgICAgICAgICBjb25z
dCBGbG9hdFBvaW50JiBxMSwKKyAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYg
cDIsCisgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIHEyKTsKKworLy8gRGV0
ZXJtaW5lcyB3aGV0aGVyICJwb2ludCIgaXMgaW5zaWRlIHRoZSAyRCB0cmlhbmdsZSBkZWZpbmVk
IGJ5CisvLyB2ZXJ0aWNlcyBhLCBiLCBhbmQgYy4gVGhpcyB0ZXN0IGRlZmluZXMgdGhhdCBwb2lu
dHMgZXhhY3RseSBvbiBhbgorLy8gZWRnZSBhcmUgbm90IGNvbnNpZGVyZWQgdG8gYmUgaW5zaWRl
IHRoZSB0cmlhbmdsZS4KK2Jvb2wgcG9pbnRJblRyaWFuZ2xlKGNvbnN0IEZsb2F0UG9pbnQmIHBv
aW50LAorICAgICAgICAgICAgICAgICAgICAgY29uc3QgRmxvYXRQb2ludCYgYSwKKyAgICAgICAg
ICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIGIsCisgICAgICAgICAgICAgICAgICAgICBj
b25zdCBGbG9hdFBvaW50JiBjKTsKKworLy8gRGV0ZXJtaW5lcyB3aGV0aGVyIHRoZSB0cmlhbmds
ZXMgZGVmaW5lZCBieSB0aGUgcG9pbnRzIChhMSwgYjEsIGMxKQorLy8gYW5kIChhMiwgYjIsIGMy
KSBvdmVybGFwLiBUaGUgZGVmaW5pdGlvbiBvZiB0aGlzIGZ1bmN0aW9uIGlzIHRoYXQKKy8vIGlm
IHRoZSB0d28gdHJpYW5nbGVzIG9ubHkgc2hhcmUgYW4gYWRqYWNlbnQgZWRnZSBvciB2ZXJ0ZXgs
IHRoZXkKKy8vIGFyZSBub3QgY29uc2lkZXJlZCB0byBvdmVybGFwLgorYm9vbCB0cmlhbmdsZXNP
dmVybGFwKGNvbnN0IEZsb2F0UG9pbnQmIGExLAorICAgICAgICAgICAgICAgICAgICAgIGNvbnN0
IEZsb2F0UG9pbnQmIGIxLAorICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQm
IGMxLAorICAgICAgICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIGEyLAorICAgICAg
ICAgICAgICAgICAgICAgIGNvbnN0IEZsb2F0UG9pbnQmIGIyLAorICAgICAgICAgICAgICAgICAg
ICAgIGNvbnN0IEZsb2F0UG9pbnQmIGMyKTsKKworLy8gR2l2ZW4gYSBzcmMgY3ViaWMgYmV6aWVy
LCBjaG9wcyBpdCBhdCB0aGUgc3BlY2lmaWVkIHQgdmFsdWUsCisvLyB3aGVyZSAwIDwgdCA8IDEs
IGFuZCByZXR1cm5zIHRoZSB0d28gbmV3IGN1YmljcyBpbiBkc3RbMC4uM10KKy8vIGFuZCBkc3Rb
My4uNl0uCit2b2lkIGNob3BDdWJpY0F0KGNvbnN0IEZsb2F0UG9pbnQgc3JjWzRdLCBGbG9hdFBv
aW50IGRzdFs3XSwgZmxvYXQgdCk7CisKKy8vICJYLVJheSIgcXVlcmllcy4gQW4gWFJheSBpcyBh
IGhhbGYtbGluZSBvcmlnaW5hdGluZyBhdCB0aGUgZ2l2ZW4KKy8vIHBvaW50IGFuZCBleHRlbmRp
bmcgdG8geD0raW5maW5pdHkuCit0eXBlZGVmIEZsb2F0UG9pbnQgWFJheTsKKworLy8gR2l2ZW4g
YW4gYXJiaXRyYXJ5IGN1YmljIGJlemllciwgcmV0dXJuIHRoZSBudW1iZXIgb2YgdGltZXMgYW4g
WFJheQorLy8gY3Jvc3NlcyB0aGUgY3ViaWMuIFZhbGlkIHJldHVybiB2YWx1ZXMgYXJlIFswLi4z
XS4KKy8vCisvLyBCeSBkZWZpbml0aW9uIHRoZSBjdWJpYyBpcyBvcGVuIGF0IHRoZSBzdGFydGlu
ZyBwb2ludDsgaW4gb3RoZXIKKy8vIHdvcmRzLCBpZiBwdC5mWSBpcyBlcXVpdmFsZW50IHRvIGN1
YmljWzBdLmZZLCBhbmQgcHQuZlggaXMgdG8gdGhlCisvLyBsZWZ0IG9mIHRoZSBjdXJ2ZSwgdGhl
IGxpbmUgaXMgbm90IGNvbnNpZGVyZWQgdG8gY3Jvc3MgdGhlIGN1cnZlLAorLy8gYnV0IGlmIGl0
IGlzIGVxdWFsIHRvIGN1YmljWzNdLmZZIHRoZW4gaXQgaXMgY29uc2lkZXJlZCB0bworLy8gY3Jv
c3MuCisvLworLy8gT3V0Z29pbmcgImFtYmlndW91cyIgYXJndW1lbnQgaW5kaWNhdGVzIHdoZXRo
ZXIgdGhlIGFuc3dlciBpcyBhbWJpZ3VvdXMKKy8vIGJlY2F1c2UgdGhlIHF1ZXJ5IG9jY3VycmVk
IGV4YWN0bHkgYXQgb25lIG9mIHRoZSBlbmRwb2ludHMnIHkKKy8vIGNvb3JkaW5hdGVzIG9yIGF0
IGEgdGFuZ2VudCBwb2ludCwgaW5kaWNhdGluZyB0aGF0IGFub3RoZXIgcXVlcnkgeQorLy8gY29v
cmRpbmF0ZSBpcyBwcmVmZXJyZWQgZm9yIHJvYnVzdG5lc3MuCitpbnQgbnVtWFJheUNyb3NzaW5n
c0ZvckN1YmljKGNvbnN0IFhSYXkmIHhSYXksCisgICAgICAgICAgICAgICAgICAgICAgICAgICAg
IGNvbnN0IEZsb2F0UG9pbnQgY3ViaWNbNF0sCisgICAgICAgICAgICAgICAgICAgICAgICAgICAg
IGJvb2wmIGFtYmlndW91cyk7CisKKy8vIEdpdmVuIGEgbGluZSBzZWdtZW50IGZyb20gbGluZUVu
ZHBvaW50c1swXSB0byBsaW5lRW5kcG9pbnRzWzFdLCBhbmQgYW4KKy8vIFhSYXksIHJldHVybnMg
dHJ1ZSBpZiB0aGV5IGludGVyc2VjdC4gT3V0Z29pbmcgImFtYmlndW91cyIgYXJndW1lbnQKKy8v
IGluZGljYXRlcyB3aGV0aGVyIHRoZSBhbnN3ZXIgaXMgYW1iaWd1b3VzIGJlY2F1c2UgdGhlIHF1
ZXJ5IG9jY3VycmVkCisvLyBleGFjdGx5IGF0IG9uZSBvZiB0aGUgZW5kcG9pbnRzJyB5IGNvb3Jk
aW5hdGVzLCBpbmRpY2F0aW5nIHRoYXQgYW5vdGhlcgorLy8gcXVlcnkgeSBjb29yZGluYXRlIGlz
IHByZWZlcnJlZCBmb3Igcm9idXN0bmVzcy4KK2Jvb2wgeFJheUNyb3NzZXNMaW5lKGNvbnN0IFhS
YXkmIHhSYXksCisgICAgICAgICAgICAgICAgICAgICBjb25zdCBGbG9hdFBvaW50IGxpbmVFbmRw
b2ludHNbMl0sCisgICAgICAgICAgICAgICAgICAgICBib29sJiBhbWJpZ3VvdXMpOworCit9IC8v
IG5hbWVzcGFjZSBMb29wQmxpbm5NYXRoVXRpbHMKKworfSAvLyBuYW1lc3BhY2UgV2ViQ29yZQor
CisjZW5kaWYgLy8gTG9vcEJsaW5uTWF0aFV0aWxzX2gK
</data>
<flag name="review"
          id="56356"
          type_id="1"
          status="+"
          setter="jamesr"
    />
    <flag name="commit-queue"
          id="56357"
          type_id="3"
          status="-"
          setter="kbr"
    />
          </attachment>
      

    </bug>

</bugzilla>