gx
chenyc
2025-02-12 ea42ff3ebee1eeb3fb29423aa848a249441db81c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
/**
 * @license
 * Copyright 2021 Google LLC. All Rights Reserved.
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 * =============================================================================
 */
import { backend_util, buffer, DataStorage, engine, env, kernel_impls, KernelBackend, util } from '@tensorflow/tfjs-core';
const whereImpl = kernel_impls.whereImpl;
import { assertNotComplex } from './cpu_util';
class MathBackendCPU extends KernelBackend {
    nextDataId() {
        return MathBackendCPU.nextDataId++;
    }
    constructor() {
        super();
        this.blockSize = 48;
        this.firstUse = true;
        this.data = new DataStorage(this, engine());
    }
    write(values, shape, dtype) {
        if (this.firstUse) {
            this.firstUse = false;
            if (env().get('IS_NODE')) {
                backend_util.warn('\n============================\n' +
                    'Hi, looks like you are running TensorFlow.js in ' +
                    'Node.js. To speed things up dramatically, install our node ' +
                    'backend, visit https://github.com/tensorflow/tfjs-node for more details. ' +
                    '\n============================');
            }
        }
        const dataId = { id: this.nextDataId() };
        this.data.set(dataId, { values, dtype, refCount: 1 });
        return dataId;
    }
    /**
     * Create a data bucket in cpu backend.
     * @param shape Shape of the `TensorInfo`.
     * @param dtype DType of the `TensorInfo`.
     * @param values The value of the `TensorInfo` stored as a flattened array.
     */
    makeTensorInfo(shape, dtype, values) {
        let outId;
        if (dtype === 'string' && values != null && values.length > 0 &&
            util.isString(values[0])) {
            const encodedValues = values.map(d => util.encodeString(d));
            outId = this.write(encodedValues, shape, dtype);
        }
        else {
            outId = this.write(values, shape, dtype);
        }
        return { dataId: outId, shape, dtype };
    }
    /** Return refCount of a `TensorData`. */
    refCount(dataId) {
        if (this.data.has(dataId)) {
            const tensorData = this.data.get(dataId);
            return tensorData.refCount;
        }
        return 0;
    }
    /** Increase refCount of a `TensorData`. */
    incRef(dataId) {
        const tensorData = this.data.get(dataId);
        tensorData.refCount++;
    }
    /** Decrease refCount of a `TensorData`. */
    decRef(dataId) {
        if (this.data.has(dataId)) {
            const tensorData = this.data.get(dataId);
            tensorData.refCount--;
        }
    }
    move(dataId, values, shape, dtype, refCount) {
        this.data.set(dataId, { values, dtype, refCount });
    }
    numDataIds() {
        return this.data.numDataIds();
    }
    async read(dataId) {
        return this.readSync(dataId);
    }
    readSync(dataId) {
        const { dtype, complexTensorInfos } = this.data.get(dataId);
        if (dtype === 'complex64') {
            const realValues = this.readSync(complexTensorInfos.real.dataId);
            const imagValues = this.readSync(complexTensorInfos.imag.dataId);
            return backend_util.mergeRealAndImagArrays(realValues, imagValues);
        }
        return util.convertBackendValuesAndArrayBuffer(this.data.get(dataId).values, dtype);
    }
    bufferSync(t) {
        const data = this.readSync(t.dataId);
        if (t.dtype === 'string') {
            try {
                // Decode the bytes into string.
                const strings = data.map(d => util.decodeString(d));
                return buffer(t.shape, t.dtype, strings);
            }
            catch (_a) {
                throw new Error('Failed to decode encoded string bytes into utf-8');
            }
        }
        return buffer(t.shape, t.dtype, data);
    }
    makeOutput(values, shape, dtype) {
        return engine().makeTensorFromTensorInfo(this.makeTensorInfo(shape, dtype, values), this);
    }
    /**
     * Dispose the memory if the dataId has 0 refCount. Return true if the memory
     * is released or memory is not managed in this backend, false if memory is
     * not cleared.
     * @param dataId
     * @oaram force Optional, remove the data regardless of refCount
     */
    disposeData(dataId, force = false) {
        if (this.data.has(dataId)) {
            this.data.get(dataId).refCount--;
            if (!force && this.data.get(dataId).refCount > 0) {
                return false;
            }
            const { complexTensorInfos } = this.data.get(dataId);
            if (complexTensorInfos != null) {
                this.disposeData(complexTensorInfos.real.dataId, true);
                this.disposeData(complexTensorInfos.imag.dataId, true);
            }
            this.data.delete(dataId);
        }
        return true;
    }
    disposeIntermediateTensorInfo(tensorInfo) {
        this.disposeData(tensorInfo.dataId);
    }
    async time(f) {
        const start = util.now();
        f();
        const kernelMs = util.now() - start;
        return { kernelMs };
    }
    memory() {
        return {
            // Unreliable due to automatic gc. The numbers above are cumulative.
            unreliable: true,
            reasons: ['The reported memory is an upper bound. Due to automatic garbage ' +
                    'collection, the true allocated memory may be less.']
        };
    }
    where(condition) {
        assertNotComplex([condition], 'where');
        const condVals = this.readSync(condition.dataId);
        return whereImpl(condition.shape, condVals);
    }
    dispose() { }
    floatPrecision() {
        return 32;
    }
    /** Returns the smallest representable number.  */
    epsilon() {
        return super.epsilon();
    }
}
MathBackendCPU.nextDataId = 0;
export { MathBackendCPU };
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiYmFja2VuZF9jcHUuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi90ZmpzLWJhY2tlbmQtY3B1L3NyYy9iYWNrZW5kX2NwdS50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQTs7Ozs7Ozs7Ozs7Ozs7O0dBZUc7QUFFSCxPQUFPLEVBQUMsWUFBWSxFQUFxQixNQUFNLEVBQUUsV0FBVyxFQUFZLE1BQU0sRUFBRSxHQUFHLEVBQUUsWUFBWSxFQUFFLGFBQWEsRUFBMEUsSUFBSSxFQUFDLE1BQU0sdUJBQXVCLENBQUM7QUFFN04sTUFBTSxTQUFTLEdBQUcsWUFBWSxDQUFDLFNBQVMsQ0FBQztBQUN6QyxPQUFPLEVBQUMsZ0JBQWdCLEVBQUMsTUFBTSxZQUFZLENBQUM7QUFnQjVDLE1BQWEsY0FBZSxTQUFRLGFBQWE7SUFNdkMsVUFBVTtRQUNoQixPQUFPLGNBQWMsQ0FBQyxVQUFVLEVBQUUsQ0FBQztJQUNyQyxDQUFDO0lBRUQ7UUFDRSxLQUFLLEVBQUUsQ0FBQztRQVZILGNBQVMsR0FBRyxFQUFFLENBQUM7UUFHZCxhQUFRLEdBQUcsSUFBSSxDQUFDO1FBUXRCLElBQUksQ0FBQyxJQUFJLEdBQUcsSUFBSSxXQUFXLENBQUMsSUFBSSxFQUFFLE1BQU0sRUFBRSxDQUFDLENBQUM7SUFDOUMsQ0FBQztJQUVRLEtBQUssQ0FDVixNQUFrQyxFQUFFLEtBQWUsRUFDbkQsS0FBZTtRQUNqQixJQUFJLElBQUksQ0FBQyxRQUFRLEVBQUU7WUFDakIsSUFBSSxDQUFDLFFBQVEsR0FBRyxLQUFLLENBQUM7WUFDdEIsSUFBSSxHQUFHLEVBQUUsQ0FBQyxHQUFHLENBQUMsU0FBUyxDQUFDLEVBQUU7Z0JBQ3hCLFlBQVksQ0FBQyxJQUFJLENBQ2Isa0NBQWtDO29CQUNsQyxrREFBa0Q7b0JBQ2xELDZEQUE2RDtvQkFDN0QsMkVBQTJFO29CQUMzRSxnQ0FBZ0MsQ0FBQyxDQUFDO2FBQ3ZDO1NBQ0Y7UUFDRCxNQUFNLE1BQU0sR0FBRyxFQUFD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QUFLLENBQUM7UUFDcEMsT0FBTyxFQUFDLFFBQVEsRUFBQyxDQUFDO0lBQ3BCLENBQUM7SUFFUSxNQUFNO1FBQ2IsT0FBTztZQUNMLG9FQUFvRTtZQUNwRSxVQUFVLEVBQUUsSUFBSTtZQUNoQixPQUFPLEVBQ0gsQ0FBQyxrRUFBa0U7b0JBQ2xFLG9EQUFvRCxDQUFDO1NBQzNELENBQUM7SUFDSixDQUFDO0lBRUQsS0FBSyxDQUFDLFNBQWlCO1FBQ3JCLGdCQUFnQixDQUFDLENBQUMsU0FBUyxDQUFDLEVBQUUsT0FBTyxDQUFDLENBQUM7UUFFdkMsTUFBTSxRQUFRLEdBQUcsSUFBSSxDQUFDLFFBQVEsQ0FBQyxTQUFTLENBQUMsTUFBTSxDQUFlLENBQUM7UUFDL0QsT0FBTyxTQUFTLENBQUMsU0FBUyxDQUFDLEtBQUssRUFBRSxRQUFRLENBQUMsQ0FBQztJQUM5QyxDQUFDO0lBRVEsT0FBTyxLQUFJLENBQUM7SUFFWixjQUFjO1FBQ3JCLE9BQU8sRUFBRSxDQUFDO0lBQ1osQ0FBQztJQUVELGtEQUFrRDtJQUN6QyxPQUFPO1FBQ2QsT0FBTyxLQUFLLENBQUMsT0FBTyxFQUFFLENBQUM7SUFDekIsQ0FBQzs7QUE5TGMseUJBQVUsR0FBRyxDQUFDLEFBQUosQ0FBSztTQUxuQixjQUFjIiwic291cmNlc0NvbnRlbnQiOlsiLyoqXG4gKiBAbGljZW5zZVxuICogQ29weXJpZ2h0IDIwMjEgR29vZ2xlIExMQy4gQWxsIFJpZ2h0cyBSZXNlcnZlZC5cbiAqIExpY2Vuc2VkIHVuZGVyIHRoZSBBcGFjaGUgTGljZW5zZSwgVmVyc2lvbiAyLjAgKHRoZSBcIkxpY2Vuc2VcIik7XG4gKiB5b3UgbWF5IG5vdCB1c2UgdGhpcyBmaWxlIGV4Y2VwdCBpbiBjb21wbGlhbmNlIHdpdGggdGhlIExpY2Vuc2UuXG4gKiBZb3UgbWF5IG9idGFpbiBhIGNvcHkgb2YgdGhlIExpY2Vuc2UgYXRcbiAqXG4gKiBodHRwOi8vd3d3LmFwYWNoZS5vcmcvbGljZW5zZXMvTElDRU5TRS0yLjBcbiAqXG4gKiBVbmxlc3MgcmVxdWlyZWQgYnkgYXBwbGljYWJsZSBsYXcgb3IgYWdyZWVkIHRvIGluIHdyaXRpbmcsIHNvZnR3YXJlXG4gKiBkaXN0cmlidXRlZCB1bmRlciB0aGUgTGljZW5zZSBpcyBkaXN0cmlidXRlZCBvbiBhbiBcIkFTIElTXCIgQkFTSVMsXG4gKiBXSVRIT1VUIFdBUlJBTlRJRVMgT1IgQ09ORElUSU9OUyBPRiBBTlkgS0lORCwgZWl0aGVyIGV4cHJlc3Mgb3IgaW1wbGllZC5cbiAqIFNlZSB0aGUgTGljZW5zZSBmb3IgdGhlIHNwZWNpZmljIGxhbmd1YWdlIGdvdmVybmluZyBwZXJtaXNzaW9ucyBhbmRcbiAqIGxpbWl0YXRpb25zIHVuZGVyIHRoZSBMaWNlbnNlLlxuICogPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT1cbiAqL1xuXG5pbXBvcnQge2JhY2tlbmRfdXRpbCwgQmFja2VuZFRpbWluZ0luZm8sIGJ1ZmZlciwgRGF0YVN0b3JhZ2UsIERhdGFUeXBlLCBlbmdpbmUsIGVudiwga2VybmVsX2ltcGxzLCBLZXJuZWxCYWNrZW5kLCBSYW5rLCBTaGFwZU1hcCwgVGVuc29yLCBUZW5zb3IyRCwgVGVuc29yQnVmZmVyLCBUZW5zb3JJbmZvLCBUeXBlZEFycmF5LCB1dGlsfSBmcm9tICdAdGVuc29yZmxvdy90ZmpzLWNvcmUnO1xuXG5jb25zdCB3aGVyZUltcGwgPSBrZXJuZWxfaW1wbHMud2hlcmVJbXBsO1xuaW1wb3J0IHthc3NlcnROb3RDb21wbGV4fSBmcm9tICcuL2NwdV91dGlsJztcblxuaW50ZXJmYWNlIERhdGFJZCB7fVxuXG5leHBvcnQgaW50ZXJmYWNlIFRlbnNvckRhdGE8RCBleHRlbmRzIERhdGFUeXBlPiB7XG4gIHZhbHVlcz86IGJhY2tlbmRfdXRpbC5CYWNrZW5kVmFsdWVzO1xuICBkdHlwZTogRDtcbiAgLy8gRm9yIGNvbXBsZXggbnVtYmVycywgdGhlIHJlYWwgYW5kIGltYWdpbmFyeSBwYXJ0cyBhcmUgc3RvcmVkIGFzIHRoZWlyIG93blxuICAvLyBpbmRpdmlkdWFsIHRlbnNvcnMsIHdpdGggYSBwYXJlbnQgam9pbmluZyB0aGUgdHdvIHdpdGggdGhlXG4gIC8vIGNvbXBsZXhUZW5zb3JJbmZvcyBmaWVsZC5cbiAgY29tcGxleFRlbnNvckluZm9zPzoge3JlYWw6IFRlbnNvckluZm8sIGltYWc6IFRlbnNvckluZm99O1xuICAvLyByZWZDb3VudCBrZWVwcyB0cmFjayBvZiBob3cgbWFueSB0ZW5zb3JzIHJlZmVyZW5jZSBpdC4gVXNlZCBmb3IgbWVtb3J5XG4gIC8vIG1hbmFnZW1lbnQuXG4gIHJlZkNvdW50OiBudW1iZXI7XG59XG5cbmV4cG9ydCBjbGFzcyBNYXRoQmFja2VuZENQVSBleHRlbmRzIEtlcm5lbEJhY2tlbmQge1xuICBwdWJsaWMgYmxvY2tTaXplID0gNDg7XG5cbiAgZGF0YTogRGF0YVN0b3JhZ2U8VGVuc29yRGF0YTxEYXRhVHlwZT4+O1xuICBwcml2YXRlIGZpcnN0VXNlID0gdHJ1ZTtcbiAgcHJpdmF0ZSBzdGF0aWMgbmV4dERhdGFJZCA9IDA7XG4gIHByaXZhdGUgbmV4dERhdGFJZCgpOiBudW1iZXIge1xuICAgIHJldHVybiBNYXRoQmFja2VuZENQVS5uZXh0RGF0YUlkKys7XG4gIH1cblxuICBjb25zdHJ1Y3RvcigpIHtcbiAgICBzdXBlcigpO1xuICAgIHRoaXMuZGF0YSA9IG5ldyBEYXRhU3RvcmFnZSh0aGlzLCBlbmdpbmUoKSk7XG4gIH1cblxuICBvdmVycmlkZSB3cml0ZShcbiAgICAgIHZhbHVlczogYmFja2VuZF91dGlsLkJhY2tlbmRWYWx1ZXMsIHNoYXBlOiBudW1iZXJbXSxcbiAgICAgIGR0eXBlOiBEYXRhVHlwZSk6IERhdGFJZCB7XG4gICAgaWYgKHRoaXMuZmlyc3RVc2UpIHtcbiAgICAgIHRoaXMuZmlyc3RVc2UgPSBmYWxzZTtcbiAgICAgIGlmIChlbnYoKS5nZXQoJ0lTX05PREUnKSkge1xuICAgICAgICBiYWNrZW5kX3V0aWwud2FybihcbiAgICAgICAgICAgICdcXG49PT09PT09PT09PT09PT09PT09PT09PT09PT09XFxuJyArXG4gICAgICAgICAgICAnSGksIGxvb2tzIGxpa2UgeW91IGFyZSBydW5uaW5nIFRlbnNvckZsb3cuanMgaW4gJyArXG4gICAgICAgICAgICAnTm9kZS5qcy4gVG8gc3BlZWQgdGhpbmdzIHVwIGRyYW1hdGljYWxseSwgaW5zdGFsbCBvdXIgbm9kZSAnICtcbiAgICAgICAgICAgICdiYWNrZW5kLCB2aXNpdCBodHRwczovL2dpdGh1Yi5jb20vdGVuc29yZmxvdy90ZmpzLW5vZGUgZm9yIG1vcmUgZGV0YWlscy4gJyArXG4gICAgICAgICAgICAnXFxuPT09PT09PT09PT09PT09PT09PT09PT09PT09PScpO1xuICAgICAgfVxuICAgIH1cbiAgICBjb25zdCBkYXRhSWQgPSB7aWQ6IHRoaXMubmV4dERhdGFJZCgpfTtcblxuICAgIHRoaXMuZGF0YS5zZXQoZGF0YUlkLCB7dmFsdWVzLCBkdHlwZSwgcmVmQ291bnQ6IDF9KTtcblxuICAgIHJldHVybiBkYXRhSWQ7XG4gIH1cblxuICAvKipcbiAgICogQ3JlYXRlIGEgZGF0YSBidWNrZXQgaW4gY3B1IGJhY2tlbmQuXG4gICAqIEBwYXJhbSBzaGFwZSBTaGFwZSBvZiB0aGUgYFRlbnNvckluZm9gLlxuICAgKiBAcGFyYW0gZHR5cGUgRFR5cGUgb2YgdGhlIGBUZW5zb3JJbmZvYC5cbiAgICogQHBhcmFtIHZhbHVlcyBUaGUgdmFsdWUgb2YgdGhlIGBUZW5zb3JJbmZvYCBzdG9yZWQgYXMgYSBmbGF0dGVuZWQgYXJyYXkuXG4gICAqL1xuICBtYWtlVGVuc29ySW5mbyhcbiAgICAgIHNoYXBlOiBudW1iZXJbXSwgZHR5cGU6IERhdGFUeXBlLFxuICAgICAgdmFsdWVzPzogYmFja2VuZF91dGlsLkJhY2tlbmRWYWx1ZXN8c3RyaW5nW10pOiBUZW5zb3JJbmZvIHtcbiAgICBsZXQgb3V0SWQ7XG4gICAgaWYgKGR0eXBlID09PSAnc3RyaW5nJyAmJiB2YWx1ZXMgIT0gbnVsbCAmJiB2YWx1ZXMubGVuZ3RoID4gMCAmJlxuICAgICAgICB1dGlsLmlzU3RyaW5nKHZhbHVlc1swXSkpIHtcbiAgICAgIGNvbnN0IGVuY29kZWRWYWx1ZXMgPVxuICAgICAgICAgICh2YWx1ZXMgYXMgdW5rbm93biBhcyBzdHJpbmdbXSkubWFwKGQgPT4gdXRpbC5lbmNvZGVTdHJpbmcoZCkpO1xuXG4gICAgICBvdXRJZCA9IHRoaXMud3JpdGUoZW5jb2RlZFZhbHVlcywgc2hhcGUsIGR0eXBlKTtcbiAgICB9IGVsc2Uge1xuICAgICAgb3V0SWQgPSB0aGlzLndyaXRlKHZhbHVlcyBhcyBUeXBlZEFycmF5LCBzaGFwZSwgZHR5cGUpO1xuICAgIH1cblxuICAgIHJldHVybiB7ZGF0YUlkOiBvdXRJZCwgc2hhcGUsIGR0eXBlfTtcbiAgfVxuXG4gIC8qKiBSZXR1cm4gcmVmQ291bnQgb2YgYSBgVGVuc29yRGF0YWAuICovXG4gIG92ZXJyaWRlIHJlZkNvdW50KGRhdGFJZDogRGF0YUlkKTogbnVtYmVyIHtcbiAgICBpZiAodGhpcy5kYXRhLmhhcyhkYXRhSWQpKSB7XG4gICAgICBjb25zdCB0ZW5zb3JEYXRhID0gdGhpcy5kYXRhLmdldChkYXRhSWQpO1xuICAgICAgcmV0dXJuIHRlbnNvckRhdGEucmVmQ291bnQ7XG4gICAgfVxuICAgIHJldHVybiAwO1xuICB9XG5cbiAgLyoqIEluY3JlYXNlIHJlZkNvdW50IG9mIGEgYFRlbnNvckRhdGFgLiAqL1xuICBvdmVycmlkZSBpbmNSZWYoZGF0YUlkOiBEYXRhSWQpOiB2b2lkIHtcbiAgICBjb25zdCB0ZW5zb3JEYXRhID0gdGhpcy5kYXRhLmdldChkYXRhSWQpO1xuICAgIHRlbnNvckRhdGEucmVmQ291bnQrKztcbiAgfVxuXG4gIC8qKiBEZWNyZWFzZSByZWZDb3VudCBvZiBhIGBUZW5zb3JEYXRhYC4gKi9cbiAgZGVjUmVmKGRhdGFJZDogRGF0YUlkKTogdm9pZCB7XG4gICAgaWYgKHRoaXMuZGF0YS5oYXMoZGF0YUlkKSkge1xuICAgICAgY29uc3QgdGVuc29yRGF0YSA9IHRoaXMuZGF0YS5nZXQoZGF0YUlkKTtcbiAgICAgIHRlbnNvckRhdGEucmVmQ291bnQtLTtcbiAgICB9XG4gIH1cblxuICBvdmVycmlkZSBtb3ZlKFxuICAgICAgZGF0YUlkOiBEYXRhSWQsIHZhbHVlczogYmFja2VuZF91dGlsLkJhY2tlbmRWYWx1ZXMsIHNoYXBlOiBudW1iZXJbXSxcbiAgICAgIGR0eXBlOiBEYXRhVHlwZSwgcmVmQ291bnQ6IG51bWJlcik6IHZvaWQge1xuICAgIHRoaXMuZGF0YS5zZXQoZGF0YUlkLCB7dmFsdWVzLCBkdHlwZSwgcmVmQ291bnR9KTtcbiAgfVxuXG4gIG92ZXJyaWRlIG51bURhdGFJZHMoKTogbnVtYmVyIHtcbiAgICByZXR1cm4gdGhpcy5kYXRhLm51bURhdGFJZHMoKTtcbiAgfVxuXG4gIG92ZXJyaWRlIGFzeW5jIHJlYWQoZGF0YUlkOiBEYXRhSWQpOiBQcm9taXNlPGJhY2tlbmRfdXRpbC5CYWNrZW5kVmFsdWVzPiB7XG4gICAgcmV0dXJuIHRoaXMucmVhZFN5bmMoZGF0YUlkKTtcbiAgfVxuICBvdmVycmlkZSByZWFkU3luYyhkYXRhSWQ6IERhdGFJZCk6IGJhY2tlbmRfdXRpbC5CYWNrZW5kVmFsdWVzIHtcbiAgICBjb25zdCB7ZHR5cGUsIGNvbXBsZXhUZW5zb3JJbmZvc30gPSB0aGlzLmRhdGEuZ2V0KGRhdGFJZCk7XG5cbiAgICBpZiAoZHR5cGUgPT09ICdjb21wbGV4NjQnKSB7XG4gICAgICBjb25zdCByZWFsVmFsdWVzID1cbiAgICAgICAgICB0aGlzLnJlYWRTeW5jKGNvbXBsZXhUZW5zb3JJbmZvcy5yZWFsLmRhdGFJZCkgYXMgRmxvYXQzMkFycmF5O1xuICAgICAgY29uc3QgaW1hZ1ZhbHVlcyA9XG4gICAgICAgICAgdGhpcy5yZWFkU3luYyhjb21wbGV4VGVuc29ySW5mb3MuaW1hZy5kYXRhSWQpIGFzIEZsb2F0MzJBcnJheTtcbiAgICAgIHJldHVybiBiYWNrZW5kX3V0aWwubWVyZ2VSZWFsQW5kSW1hZ0FycmF5cyhyZWFsVmFsdWVzLCBpbWFnVmFsdWVzKTtcbiAgICB9XG4gICAgcmV0dXJuIHV0aWwuY29udmVydEJhY2tlbmRWYWx1ZXNBbmRBcnJheUJ1ZmZlcihcbiAgICAgICAgdGhpcy5kYXRhLmdldChkYXRhSWQpLnZhbHVlcywgZHR5cGUpO1xuICB9XG5cbiAgYnVmZmVyU3luYzxSIGV4dGVuZHMgUmFuaywgRCBleHRlbmRzIERhdGFUeXBlPih0OiBUZW5zb3JJbmZvKTpcbiAgICAgIFRlbnNvckJ1ZmZlcjxSLCBEPiB7XG4gICAgY29uc3QgZGF0YSA9IHRoaXMucmVhZFN5bmModC5kYXRhSWQpO1xuICAgIGlmICh0LmR0eXBlID09PSAnc3RyaW5nJykge1xuICAgICAgdHJ5IHtcbiAgICAgICAgLy8gRGVjb2RlIHRoZSBieXRlcyBpbnRvIHN0cmluZy5cbiAgICAgICAgY29uc3Qgc3RyaW5ncyA9IChkYXRhIGFzIFVpbnQ4QXJyYXlbXSkubWFwKGQgPT4gdXRpbC5kZWNvZGVTdHJpbmcoZCkpO1xuICAgICAgICByZXR1cm4gYnVmZmVyKHQuc2hhcGUgYXMgU2hhcGVNYXBbUl0sIHQuZHR5cGUsIHN0cmluZ3MpIGFzXG4gICAgICAgICAgICBUZW5zb3JCdWZmZXI8UiwgRD47XG4gICAgICB9IGNhdGNoIHtcbiAgICAgICAgdGhyb3cgbmV3IEVycm9yKCdGYWlsZWQgdG8gZGVjb2RlIGVuY29kZWQgc3RyaW5nIGJ5dGVzIGludG8gdXRmLTgnKTtcbiAgICAgIH1cbiAgICB9XG4gICAgcmV0dXJuIGJ1ZmZlcih0LnNoYXBlIGFzIFNoYXBlTWFwW1JdLCB0LmR0eXBlLCBkYXRhIGFzIFR5cGVkQXJyYXkpIGFzXG4gICAgICAgIFRlbnNvckJ1ZmZlcjxSLCBEPjtcbiAgfVxuXG4gIG1ha2VPdXRwdXQ8VCBleHRlbmRzIFRlbnNvcj4oXG4gICAgICB2YWx1ZXM6IGJhY2tlbmRfdXRpbC5CYWNrZW5kVmFsdWVzLCBzaGFwZTogbnVtYmVyW10sIGR0eXBlOiBEYXRhVHlwZSk6IFQge1xuICAgIHJldHVybiBlbmdpbmUoKS5tYWtlVGVuc29yRnJvbVRlbnNvckluZm8oXG4gICAgICAgICAgICAgICB0aGlzLm1ha2VUZW5zb3JJbmZvKHNoYXBlLCBkdHlwZSwgdmFsdWVzKSwgdGhpcykgYXMgVDtcbiAgfVxuXG4gIC8qKlxuICAgKiBEaXNwb3NlIHRoZSBtZW1vcnkgaWYgdGhlIGRhdGFJZCBoYXMgMCByZWZDb3VudC4gUmV0dXJuIHRydWUgaWYgdGhlIG1lbW9yeVxuICAgKiBpcyByZWxlYXNlZCBvciBtZW1vcnkgaXMgbm90IG1hbmFnZWQgaW4gdGhpcyBiYWNrZW5kLCBmYWxzZSBpZiBtZW1vcnkgaXNcbiAgICogbm90IGNsZWFyZWQuXG4gICAqIEBwYXJhbSBkYXRhSWRcbiAgICogQG9hcmFtIGZvcmNlIE9wdGlvbmFsLCByZW1vdmUgdGhlIGRhdGEgcmVnYXJkbGVzcyBvZiByZWZDb3VudFxuICAgKi9cbiAgb3ZlcnJpZGUgZGlzcG9zZURhdGEoZGF0YUlkOiBEYXRhSWQsIGZvcmNlID0gZmFsc2UpOiBib29sZWFuIHtcbiAgICBpZiAodGhpcy5kYXRhLmhhcyhkYXRhSWQpKSB7XG4gICAgICB0aGlzLmRhdGEuZ2V0KGRhdGFJZCkucmVmQ291bnQtLTtcbiAgICAgIGlmICghZm9yY2UgJiYgdGhpcy5kYXRhLmdldChkYXRhSWQpLnJlZkNvdW50ID4gMCkge1xuICAgICAgICByZXR1cm4gZmFsc2U7XG4gICAgICB9XG5cbiAgICAgIGNvbnN0IHtjb21wbGV4VGVuc29ySW5mb3N9ID0gdGhpcy5kYXRhLmdldChkYXRhSWQpO1xuXG4gICAgICBpZiAoY29tcGxleFRlbnNvckluZm9zICE9IG51bGwpIHtcbiAgICAgICAgdGhpcy5kaXNwb3NlRGF0YShjb21wbGV4VGVuc29ySW5mb3MucmVhbC5kYXRhSWQsIHRydWUpO1xuICAgICAgICB0aGlzLmRpc3Bvc2VEYXRhKGNvbXBsZXhUZW5zb3JJbmZvcy5pbWFnLmRhdGFJZCwgdHJ1ZSk7XG4gICAgICB9XG5cbiAgICAgIHRoaXMuZGF0YS5kZWxldGUoZGF0YUlkKTtcbiAgICB9XG4gICAgcmV0dXJuIHRydWU7XG4gIH1cblxuICBkaXNwb3NlSW50ZXJtZWRpYXRlVGVuc29ySW5mbyh0ZW5zb3JJbmZvOiBUZW5zb3JJbmZvKTogdm9pZCB7XG4gICAgdGhpcy5kaXNwb3NlRGF0YSh0ZW5zb3JJbmZvLmRhdGFJZCk7XG4gIH1cblxuICBvdmVycmlkZSBhc3luYyB0aW1lKGY6ICgpID0+IHZvaWQpOiBQcm9taXNlPEJhY2tlbmRUaW1pbmdJbmZvPiB7XG4gICAgY29uc3Qgc3RhcnQgPSB1dGlsLm5vdygpO1xuICAgIGYoKTtcbiAgICBjb25zdCBrZXJuZWxNcyA9IHV0aWwubm93KCkgLSBzdGFydDtcbiAgICByZXR1cm4ge2tlcm5lbE1zfTtcbiAgfVxuXG4gIG92ZXJyaWRlIG1lbW9yeSgpIHtcbiAgICByZXR1cm4ge1xuICAgICAgLy8gVW5yZWxpYWJsZSBkdWUgdG8gYXV0b21hdGljIGdjLiBUaGUgbnVtYmVycyBhYm92ZSBhcmUgY3VtdWxhdGl2ZS5cbiAgICAgIHVucmVsaWFibGU6IHRydWUsXG4gICAgICByZWFzb25zOlxuICAgICAgICAgIFsnVGhlIHJlcG9ydGVkIG1lbW9yeSBpcyBhbiB1cHBlciBib3VuZC4gRHVlIHRvIGF1dG9tYXRpYyBnYXJiYWdlICcgK1xuICAgICAgICAgICAnY29sbGVjdGlvbiwgdGhlIHRydWUgYWxsb2NhdGVkIG1lbW9yeSBtYXkgYmUgbGVzcy4nXVxuICAgIH07XG4gIH1cblxuICB3aGVyZShjb25kaXRpb246IFRlbnNvcik6IFRlbnNvcjJEIHtcbiAgICBhc3NlcnROb3RDb21wbGV4KFtjb25kaXRpb25dLCAnd2hlcmUnKTtcblxuICAgIGNvbnN0IGNvbmRWYWxzID0gdGhpcy5yZWFkU3luYyhjb25kaXRpb24uZGF0YUlkKSBhcyBUeXBlZEFycmF5O1xuICAgIHJldHVybiB3aGVyZUltcGwoY29uZGl0aW9uLnNoYXBlLCBjb25kVmFscyk7XG4gIH1cblxuICBvdmVycmlkZSBkaXNwb3NlKCkge31cblxuICBvdmVycmlkZSBmbG9hdFByZWNpc2lvbigpOiAxNnwzMiB7XG4gICAgcmV0dXJuIDMyO1xuICB9XG5cbiAgLyoqIFJldHVybnMgdGhlIHNtYWxsZXN0IHJlcHJlc2VudGFibGUgbnVtYmVyLiAgKi9cbiAgb3ZlcnJpZGUgZXBzaWxvbigpOiBudW1iZXIge1xuICAgIHJldHVybiBzdXBlci5lcHNpbG9uKCk7XG4gIH1cbn1cbiJdfQ==